I'm trying to implement the tippy.js
tooltip and change the theme based on the local storage value darkMode
as an AlpineJs
custom directive .
The code below works more or less fine with the latest bit that if I toggle the dark-mode switch, which changes the local localStorage item value of darkMode
, I need a page refresh to get the new value.
How can I get the value ( JSON.parse(localStorage.getItem('darkMode'))
) while I change it?
document.addEventListener('alpine:init', () => {
Alpine.directive('tooltip', (el, {expression, modifiers}) => {
tippy(el, {
content: expression,
placement: modifiers[0] ?? 'auto',
theme: JSON.parse(localStorage.getItem('darkMode')) ?'blue':'light-border'
})
})
})
<button type="button" x-tooltip.left="I'm a tooltip">Hover me</button>
<body class="font-sans antialiased h-full"
x-data="{'darkMode': false}"
x-init="
darkMode = JSON.parse(localStorage.getItem('darkMode'));
$watch('darkMode', value => localStorage.setItem('darkMode', JSON.stringify(value)))"
x-cloak
>
<!-- some html -->
</body>
<input id="toggle" type="checkbox" :value="darkMode" @change="darkMode = !darkMode"/>
As you see a Tippy.js instance and the localStorage
is not reactive. After creating a Tippy.js instance we need to use the _tippy
property on each element if we want to change a property. To make it a little bit easier, I modified the tooltip directive to add a custom class tooltips
, that we use to loop over each Tippy.js instance.
document.addEventListener('alpine:init', () => {
Alpine.directive('tooltip', (el, { expression, modifiers }) => {
tippy(el, {
content: expression,
placement: modifiers[0] ?? 'auto',
theme: JSON.parse(localStorage.getItem('darkMode')) ? 'blue' : 'light-border'
})
el.classList.add('tooltips')
})
})
And in the $watch
magic, we use the tooltips
class to find all of the Tippy.js instances and set the new theme on them.
<body class="font-sans antialiased h-full"
x-data="{'darkMode': false}"
x-init="
darkMode = JSON.parse(localStorage.getItem('darkMode'));
$watch('darkMode', value => {
localStorage.setItem('darkMode', JSON.stringify(value))
Array.from(document.querySelectorAll('.tooltips')).forEach(
el => el._tippy.setProps({ theme: value ? 'blue' : 'light-border' }))
})"
x-cloak
>
<!-- some html -->
</body>
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.