I have a product page and I got sick of putting tons of Vue code in a div with a class of hidden because a lot of the content is for modals. I found a way to render some Vue code on the fly inside of a javascript function only if the function is invoked.
The cool thing about this is I can refer to the parent app's data, when using normal Vue templates, this is not possible.
This code is not using a build step and Vue is being imported from unpkg.
In the first example I am using Vue.render()
and this does work, the only thing is I found this answer from chat gpt, and I have never seen this in the docs and I could not find anything on it, but looking at unpkg, a render method is exported and available through Vue.render()
.
I don't know why there are no docs on this but the second example uses the render method again but inside a Vue app and there is some documentation on this.
I am wondering if anyone can explain the Vue.render()
method a bit and if one approach is better than the other, and by better I mean more reliable and robust. The render method is documented and shown to be used inside an app.
Call Vue.render()
and render vnode to regular DOM element without creating a new Vue app
const product_app_options = {
data() {
return {
sizeOptions: [/* ... */],
product: { /* ... */ }
}
},
methods: {
openModal() {
const vnode = Vue.h(
'div',
{
class: [
'size-modal-swatches',
'swatches'
]
},
this.sizeVariants.map(variant =>
Vue.h(
'button',
{
class: [
{
'soldout': !variant.available,
'selected': variant[product.size_option.option] === _this.selected_size
},
'pw-button',
'size-modal__swatch',
'swatch'
],
tabIndex: 0,
onClick: e => _this.selectVariant(e, variant),
ariaLabel: variant.available
? `size ${variant[this.product.size_option.option]} available`
: `size ${variant[this.product.size_option.option]} not available`
},
[
Vue.h(
'div',
{
class: [
'pw-button__inner'
]
},
[
Vue.h(
'span',
{
class: [
'size-modal__swatch-value'
]
},
variant[this.product.size_option.option]
)
]
)
]
)
)
);
// append modal to DOM
// after appending modal grab it's content selector
Vue.render(vnode, document.querySelector('.modal-content'))
}
}
}
Call render()
from inside a Vue app and mount the app to a DOM element
const product_app_options = {
data() {
return {
sizeOptions: [/* ... */],
product: { /* ... */ }
}
},
methods: {
openModal() {
const app = Vue.createApp({
render: () => Vue.h(
'div',
{
class: [
'size-modal-swatches',
'swatches'
]
},
this.sizeVariants.map(variant =>
Vue.h(
'button',
{
class: [
{
'soldout': !variant.available,
'selected': variant[product.size_option.option] === _this.selected_size
},
'pw-button',
'size-modal__swatch',
'swatch'
],
tabIndex: 0,
onClick: e => _this.selectVariant(e, variant),
ariaLabel: variant.available
? `size ${variant[this.product.size_option.option]} available`
: `size ${variant[this.product.size_option.option]} not available`
},
[
Vue.h(
'div',
{
class: [
'pw-button__inner'
]
},
[
Vue.h(
'span',
{
class: [
'size-modal__swatch-value'
]
},
variant[this.product.size_option.option]
)
]
)
]
)
)
);
})
// append modal to DOM
app.mount('.modal-content')
}
}
}
Via Active questions tagged javascript - Stack Overflow https://ift.tt/rH9ija7
Comments
Post a Comment