Blog>
Snippets

Adding Custom Directives with a Plugin

Demonstrate the creation of a plugin that adds globally available custom directives for tasks like click-outside or focus.
Vue.createApp({
    /* ... your app setup ... */
})
.use(clickOutsidePlugin)
.mount('#app');
This is a Vue.js code snippet that initializes the Vue application and uses a plugin named 'clickOutsidePlugin'. The plugin is assumed to be defined elsewhere and is responsible for adding the 'click-outside' directive globally.
const clickOutsidePlugin = {
    install(app) {
        // Directive to detect clicks outside an element
        app.directive('click-outside', {
            beforeMount(el, binding) {
                el.clickOutsideEvent = function (event) {
                    if (!(el == event.target || el.contains(event.target))) {
                        binding.value(event);
                    }
                };
                document.addEventListener('click', el.clickOutsideEvent);
            },
            unmounted(el) {
                document.removeEventListener('click', el.clickOutsideEvent);
            },
        });
    }
};
This is the definition of the 'clickOutsidePlugin' which is a Vue.js plugin. It defines a custom directive 'click-outside' that listens for click events on the document and executes the provided method if the click occurs outside the bound element.
<template>
    <div v-click-outside="handleClickOutside">
       <!-- your component content here -->
    </div>
</template>

<script>
export default {
    methods: {
        handleClickOutside() {
            // Logic to run when click outside detected
        }
    }
}
</script>
This Vue.js component template uses the 'v-click-outside' directive. When a click is detected outside the 'div', the 'handleClickOutside' method is executed.
html {
    height: 100%;
}

body {
    margin: 0;
    height: 100%;
}

#app {
    height: 100%;
}
Minimal CSS to style the HTML, body, and the Vue app container. This ensures the app fills the whole viewport height and has no margin.