Instance parameters
The advanced API is used to create more advanced Modjool elements.
This is a list of parameters available to hooks in the advanced API.
<an-element width="wide"></an-element>modjool.create({
tag: 'an-element',
js: ({ attr }) => {
// 'wide'
console.log(attr.width)
// Sets attribute: <an-element width="slim">
attr.width = 'slim'
}
})
Kebab/camel case conversion<new-element attribute-name="A value"></new-element>js: ({ attr }) => {
// Correctly access 'attribute-name' with 'attributeName':
attr.attributeName = 'New value'
// Will not work:
attr['attribute-name'] = 'A third value'
}
An object designed to be used for passing data between hooks. data is reactive, and the body
will update on any root-level changes to data. The data_[property]
hook is called after root-level properties are changed.
To update on other changes, use self.update()data: () => ({
name: 'Chris',
info: {
age: 27
}
}),
js: ({ data }) => {
// Reactive change, root-level property
data.name = 'Adam'
// Non-reactive change, inside a nested object
data.info.age = 23
}
Note: The above change will be reflected if data.info.age is used directly in body,
because the element body is always updated after the js hook.
js: ({ data, self }) => {
find`div`.onmouseover = () => {
// Async code within listener, nested object, always non-reactive
data.info.age = 27
// Call self.update() to update
self.update()
}
}
The elem instance parameter is equal to the current custom element.
This is especially useful for setting events and getting various properties held by the element.
To select child elements inside of the custom element, use
find or findAll<custom-element></custom-element>modjool.create({
tag: 'custom-element',
js: ({ data, elem }) => {
// true (while one custom-element on the page)
console.log(elem === document.querySelector('custom-element'))
// Click event on <custom-element>
elem.onclick = event => data.counter++
// Using properties
data.height = elem.offsetWidth / 2
}
})
Takes one argument, a CSS selector, and returns the first matching child element of the
current custom element, similar to querySelector.
Works as a tagged template literal, or as a regular function.
To select the custom element itself, use elem.
js: ({ find }) => ({
// Also works like this: find('span')
const span = find`span`
// 'A single element'
console.log(span.innerHTML)
// Setting a click event
find`button`.onclick = () => console.log('Button clicked!')
},
html: () => `
<span>A single element</span>
<button>Click me</button>
`
Takes one argument, a CSS selector, and returns an array of matching child element of the
current custom element, similar to querySelectorAll.
Works as a tagged template literal, or as a regular function.
To select the custom element itself, use elem.
js: ({ find }) => ({
// Also works like this: findAll('span')
const spans = findAll`span`
// ['First element', 'Second element']
console.log(spans.map(el => el.innerHTML)
// Setting click events
spans.map(span => {
span.onclick = event => console.log(`${event.target} clicked!`)
})
},
html: () => `
<span>First element</span>
<span>Second element</span>
`
Used to return the outer HTMLElement of a slot.
Works as a tagged template literal, or as a regular function.
Return value differs depending on arguments and number of slots:
Zero slots: returns undefined.
---
One slot: returns the HTMLElement that corresponds to the root-level element within the slot.
If there is no root level element, undefined will be returned.
---
Multiple slots (with argument): returns the HTMLElement that corresponds to the slot
element with the same name.
---
Multiple slots (without argument): returns a NodeList of all slot elements used within the tags.
Single slot (with containing root-level <div> element):
In this example
modjool.create({
tag: 'single-slot',
js: ({ findSlot }) => {
// <div class="title">This is a title</div>
const slotElement = findSlot``
// Use like any other element
slotElement.onclick = () => console.log('Clicked')
}
})<!-- Contains root-level div -->
<single-slot>
<div class="title">This is a title</div>
</single-slot>Single slot (without a containing element):
modjool.create({
tag: 'single-slot-uncontained',
js: ({ findSlot }) => {
// undefined - findSlot can't return an element if it doesn't exist
const slotElement = findSlot``
}
})<!-- No root-level element in slot, just a text node -->
<single-slot-uncontained>
This is a title
</single-slot-uncontained>Multiple slots:
modjool.create({
tag: 'multi-slot',
js: ({ findSlot }) => {
// <h1 slot="title">Title</h1>
const titleSlot = findSlot`title`
// Use like any other element
titleSlot.onclick = () => console.log('Clicked')
// [<h1 slot="title">Title</h1>, <div slot="text">This is some text</div>]
const slotArray = findSlot``
// true
console.log(titleSlot === slotArray[0])
}
})<multi-slot>
<h1 slot="title">Title</h1>
<div slot="text">This is some text</div>
</multi-slot>
id | {String} | The mj-id of the element (eg 'e2nztc').
---
tag | {String} | The tag name of the element.
---
options | {Object} | The Modjool options attached to the element.
---
select | {Function} | A CSS selector for the element, more info below.
---
update | {Function} | Updates the body. No params.
---
updateSlot | {Function} | Updates the slots. No params.
---
updateAttr | {Function} | Updates the attributes. No params.
---
remove | {Function} | Removes the element from the DOM. No Params.
---
html | {Function} | Override html with function argument.
---
css | {Function} | Override css with function argument.
---
enter | {Function} | Override enter with function argument.
---
data | {Function} | Override data with function argument.
---
ready | {Function} | Override ready with function argument.
---
js | {Function} | Override js with function argument.
---
complete | {Function} | Override complete with function argument.
---
leave | {Function} | Override leave with function argument.
---
attrHook | {Function} | Override attr_[name] (the first argument, a string) with the second argument (a function). Example below.
---
dataHook | {Function} | Override data_[property] (the first argument, a string) with the second argument (a function). Example below.
Assorted examplesjs: ({ self }) => {
// Adds a class to the current element
self.element.classList.add('active_class')
// Manually updates the body
self.update()
// Replacing html: () for this element
self.html(({ slot }) => `
<h1>New body</h1><div>${slot}</div>
`)
// Replacing leave: () for this element
self.leave(({ self }) => {
console.log(`Element ${self.id} leaving body`)
})
// Replacing custom reactive data hook "attr_titleText: ()" (title-text="") for this element
self.attrHook('titleText', ({ oldVal, newVal }) => {
console.log(`Old title-text: ${oldVal}`, `New title-text: ${newVal}`)
})
// Replacing custom reactive data hook "data_subtitle: ()" for this element
self.dataHook('subtitle', ({ oldVal, newVal }) => {
console.log(`Old subtitle: ${oldVal}`, `New subtitle: ${newVal}`)
})
}
self.select()self.select() is the function used to convert :self and :self([option])
into valid CSS. This is done automatically in the background, but the function is available for public use too.
// Shadow dom DISABLED
modjool.create({
tag: 'test-element-one',
shadowDom: false,
js: ({ self }) => {
// n92hc8
console.log(self.id)
// test-element-one[mj-id="n92hc8"]
console.log(self.select())
// test-element-one[mj-id="n92hc8"][bold]
console.log(self.select('[bold]'))
}
})
// Shadow dom ENABLED
modjool.create({
tag: 'test-element-two',
shadowDom: true,
js: ({ self }) => {
// n92hc8
console.log(self.id)
// :host(test-element-two[mj-id="n92hc8"])
console.log(self.select())
// test-element-two[mj-id="n92hc8"].custom_class
console.log(self.select('.custom_class'))
}
})
Returns a string or object corresponding to the slot(s) used in the element. This does not return the innerHtml
of slots, but a value that will display the slot in the DOM. The value will differ depending on whether the
shadow dom is enabled or not. To return the innerHtml,
use slotVal.
Zero slots: returns ''.
---
One slot: returns a string containing an HTML string that will display the slot.
---
Multiple slots: returns an object with properties corresponding to the name of each slot.
Single slot:
<single-slot>This is a single slot</single-slot>
modjool.create({
tag: 'single-slot',
js: ({ slot }) => {
// If shadow dom DISABLED: 'This is a single slot'
// If shadow dom ENABLED: '<slot></slot>'
console.log(slot)
},
// Will always output slot correctly
html: ({ slot }) => `${slot}`
})
Multiple slots:
<multi-slot>
<span slot="one">Slot one here</span>
<div slot="two">Slot two here</div>
</multi-slot>
modjool.create({
tag: 'multi-slot',
js: ({ slot }) => {
// If shadow dom DISABLED: '<div slot="two">This is a single slot</div>'
// If shadow dom ENABLED: '<slot name="two"></slot>'
console.log(slot.two)
},
// Will always output slot correctly
html: ({ slot }) => `${slot.two}`
})
Returns a string or object corresponding to the innerHtml of slot(s) used in the element.
This will return the same value regardless of whether the shadow DOM is enabled or not.
To output the slot directly to the HTML, with its containing tag, use slot.
Zero slots: returns ''.
---
One slot: returns a string containing the innerHtml the slot.
---
Multiple slots: returns an object with properties corresponding to the name of each slot.
Single slot:
<single-slot>This is a single slot</single-slot>
modjool.create({
tag: 'single-slot',
js: ({ slotVal }) => {
// 'This is a single slot'
console.log(slotVal)
}
})
Multiple slots:
<multi-slot>
<span slot="one">Slot one here</span>
<div slot="two">Slot two here</div>
</multi-slot>
modjool.create({
tag: 'multi-slot',
js: ({ slotVal }) => {
// 'Slot two here'
console.log(slotVal.two)
}
})
Instance object outline
Entire list of default properties for the instance.
{
attr: {
// Attributes on element
},
data: {
// Data properties
},
self: {
id,
tag,
select,
element,
update,
updateSlot,
updateAttr,
updateAll,
remove,
html,
css,
enter,
data,
ready,
js,
complete,
leave,
attrHook,
dataHook
},
slot: {
// HTML string to output slots
},
slotVal: {
// innerHtml of slots
}
}