Events in Components
You can write events specifically for components.
There are three ways to set up your component for handling events:
- A component set with the option strictlyPrivateEvents. Inner elements in this component cannot be affected by outside events. This means that any events that you write will only take action on that component and any inner component.
- A component set with the option privateEvents. This type of component will allow its inner elements to be affected by outside events. But, any events that you write inside the component itself will only apply to that component and any inner components.
- A component that shares events with any surrounding components or the DOM. This is most useful when writing components that are nested inside a main component. It makes it easier to reference elements in an outer scope. But if you were writing events for the DOM scope, or in other words the document scope, you would normally just write regular events outside of the component for clarity and not write the events inside a component.
All types of components follow the same format.
Only assign events to elements in components when the element that you are assigning the event to is actually in the component. Events won't work in a component if the element that receives the event is not in the component.
Here is an example of a fully encapsulated component:
@component hello-world strictlyPrivateEvents {
button:click {
alert: "Hello world";
}
.anotherButton:mouseover {
console-log: "This one has a console message instead.";
}
html {
<button>Click me</button>
<button class="anotherButton">Mouseover me</button>
}
}
You can use all the regular events inside the component in the same way as above.
In that example, because of the use of the strictlyPrivateEvents option, the button click event will only apply to that component. It will not affect buttons outside of the component.
If the strictlyPrivateEvents option was not used in that example, nor the privateEvents option, the button click event would apply to all buttons outside the component too, including the document, so this is why it is better to just write events outside of the component in the usual document scope to make things clearer for yourself if you are writing events for the page rather than for a component.
Inner components that are not given the strictlyPrivateEvents option will inherit the events from the upper component. It's like the component has it's own personal DOM. CSS stylesheet rules are unaffected by these types of components.
Shadow DOM use
If you want isolated CSS to apply to a component, you would use the shadow option which turns the component into a shadow DOM component.
All shadow DOM components follow the behaviour of the strictlyPrivateEvents option, regardless of what option you choose. This follows the native rules of shadow DOMs and events.
The private option
Using private as an option is a shorthand for privateEvents and privateVars.
The strictlyPrivate option
Using strictlyPrivate as an option is a shorthand for strictlyPrivateEvents and strictlyPrivateVars.
Important note for table and ul/ol tags
There is always a parent element that holds the scope for a private component. That parent element is the element outside the component that contains the actual component. Internally in the core, the scoping details for the inner component are stored in that outer parent element.
Currently, scoping (using any of the private or strictlyPrivate options) requires the parent element to contain only one scoped component. If multiple scoped components appear inside a parent, a surrogate acss tag will be created inside the parent, around each component, to act as the host to contain the necessary scope - because the parent cannot currently hold multiple scope details. The special scoping ACSS tag will only appear when it cannot find a dedicated parent element.
This isn't usually a problem in practice, until you try and put private scopes on li or tr element components. If you do attempt to do this, the parent element (the ul, for example) has to then contain multiple inner scopes, which it currently can't. You will see the surrogate host wrapper suddenly appear surrounding the second tr or li when it gets rendered to try and account for this, and for subsequent li elements, and unsurprisingly these items will not then render correctly.
The workaround is, if you do need to scope li elements or tr elements, put the table, ol or ul element inside the component and then put a private scope on that component. Then you can have inner non-scoped li tag components.
The li, tr and td elements can have their own components, which is really useful, but they cannot be privately scoped in any way. It generally makes more sense to have the private events working on the whole table rather than individual li tags. So do that instead of trying to do it on each li or tr component.
If you do have specific event or variable scoping requirement inside li or td tags, have inner host parent elements actually appear inside those li or td and render further private components from there.