{"id":16568,"library":"v-click-outside","title":"v-click-outside Vue Directive","description":"v-click-outside is a Vue.js directive that enables developers to detect and react to click events originating outside of a specific HTML element. This functionality is crucial for implementing UI patterns such as closing dropdown menus, modals, and context menus when a user clicks anywhere else on the page. The current stable version is 3.2.0. The package maintains an irregular release cadence, typically driven by bug fixes, dependency updates, and minor enhancements. A key differentiator of v-click-outside is its design to detect outside clicks without intrinsically halting event propagation, offering greater flexibility for developers managing complex event flows. It also supports configuration for various event types (e.g., 'click', 'dblclick'), detection of clicks within iframes, and the option to use the capture phase for event listeners.","status":"active","version":"3.2.0","language":"javascript","source_language":"en","source_url":"https://github.com/ndelvalle/v-click-outside","tags":["javascript"],"install":[{"cmd":"npm install v-click-outside","lang":"bash","label":"npm"},{"cmd":"yarn add v-click-outside","lang":"bash","label":"yarn"},{"cmd":"pnpm add v-click-outside","lang":"bash","label":"pnpm"}],"dependencies":[{"reason":"This package provides a Vue.js custom directive, requiring Vue as a peer dependency for functionality.","package":"vue","optional":false}],"imports":[{"note":"CommonJS `require` syntax is typically not used in modern Vue projects, which favor ES Modules. This import is used for global registration via `Vue.use()`.","wrong":"const vClickOutside = require('v-click-outside')","symbol":"vClickOutside","correct":"import vClickOutside from 'v-click-outside'"},{"note":"When registering the directive locally within a Vue component's `directives` option, access the `directive` property from the default export.","wrong":"import { directive } from 'v-click-outside'; /* This works but is less common for local component registration */","symbol":"directive (local registration)","correct":"import vClickOutside from 'v-click-outside'; /* then in component: directives: { clickOutside: vClickOutside.directive } */"},{"note":"For programmatic access to the directive's `bind` and `unbind` lifecycle hooks, destructure them directly from the `directive` export.","wrong":"import vClickOutside from 'v-click-outside'; const { bind, unbind } = vClickOutside;","symbol":"{ bind, unbind } (programmatic hooks)","correct":"import { directive } from 'v-click-outside'; const { bind, unbind } = directive;"}],"quickstart":{"code":"import Vue from 'vue';\nimport vClickOutside from 'v-click-outside';\n\n// Globally register the directive\nVue.use(vClickOutside);\n\n// Define a simple root Vue component\nnew Vue({\n  el: '#app',\n  data () {\n    return {\n      showMenu: false,\n      vcoConfig: {\n        handler: this.handleOutsideClickWithConfig,\n        middleware: this.middleware,\n        events: ['click', 'touchstart'], // Respond to both mouse and touch events\n        isActive: true,\n        detectIFrame: true,\n        capture: false\n      }\n    }\n  },\n  methods: {\n    toggleMenu() {\n      this.showMenu = !this.showMenu;\n      console.log('Menu toggled:', this.showMenu);\n    },\n    handleOutsideClickWithConfig (event) {\n      if (this.showMenu) { // Only close if menu is open\n        this.showMenu = false;\n        console.log('Clicked outside (config handler). Event type:', event.type);\n      }\n    },\n    // Middleware returns true to fire handler, false to prevent\n    middleware (event) {\n      // Example: Do not close if the click was on an element with class 'ignore-outside'\n      const ignoreElement = event.target.closest('.ignore-outside');\n      if (ignoreElement) {\n        console.log('Middleware ignored click on element with class:', ignoreElement.className);\n        return false;\n      }\n      return true; // Allow handler to fire\n    }\n  },\n  template: `\n    <div id=\"app-container\" style=\"padding: 20px; border: 1px solid #ccc; font-family: sans-serif;\">\n      <h1>v-click-outside Demo</h1>\n      <button @click=\"toggleMenu\" style=\"padding: 8px 15px; background-color: #007bff; color: white; border: none; border-radius: 4px; cursor: pointer;\">Toggle Menu</button>\n\n      <div v-if=\"showMenu\"\n           v-click-outside=\"vcoConfig\"\n           style=\"background: #e0e0e0; border: 1px solid #999; padding: 10px; margin-top: 10px; width: 200px; box-shadow: 2px 2px 8px rgba(0,0,0,0.2);\">\n        <h2 style=\"margin-top: 0; font-size: 1.2em;\">My Menu</h2>\n        <ul style=\"list-style: none; padding: 0;\">\n          <li style=\"margin-bottom: 5px;\">Item 1</li>\n          <li style=\"margin-bottom: 5px;\">Item 2</li>\n        </ul>\n        <button class=\"ignore-outside\" style=\"padding: 5px 10px; background-color: #6c757d; color: white; border: none; border-radius: 3px; cursor: pointer;\">Don't close me</button>\n      </div>\n\n      <div style=\"margin-top: 30px; padding: 10px; border: 1px dashed grey; background-color: #f8f9fa;\">\n        Click here or anywhere outside the menu to see the directive in action.\n        <p class=\"ignore-outside\" style=\"margin-top: 10px; font-style: italic; color: #555;\">This text is inside an element with class 'ignore-outside' and clicks here will be ignored by the middleware.</p>\n      </div>\n    </div>\n  `\n});","lang":"javascript","description":"This quickstart demonstrates how to globally register and use the `v-click-outside` directive with advanced configuration options, including a handler function, a middleware for conditional execution, and custom event types like `click` and `touchstart`."},"warnings":[{"fix":"Update your callback functions to only expect the `event` object as an argument. If access to the bound element is required, capture it through other means within your component's context (e.g., using `this.$refs`).","message":"In v3.0.0, the `el` (element) argument was removed from the callback function passed to the directive. The callback now exclusively receives the native `event` object.","severity":"breaking","affected_versions":">=3.0.0"},{"fix":"If specific scenarios require preventing further event propagation, manually call `event.stopPropagation()` within your directive's handler or middleware, or adjust your event listener design accordingly.","message":"The `v-click-outside` directive is explicitly designed *not* to stop event propagation. If your application logic relies on event propagation being halted, you might encounter unexpected behavior where events continue to bubble up the DOM.","severity":"gotcha","affected_versions":">=1.0.0"},{"fix":"Ensure your `middleware` function performs only synchronous checks and consistently returns a boolean value to correctly control whether the main handler is invoked.","message":"The `middleware` function, if provided, must execute synchronously and return a boolean value (`true` to allow the handler to fire, `false` to prevent it). Asynchronous operations within the middleware will not effectively block the handler's execution.","severity":"gotcha","affected_versions":">=1.0.0"},{"fix":"If experiencing unexpected behavior with `v-click-outside` in IE11 or similar older browsers, particularly involving focus or element activation, review the interaction with `document.activeElement` and consider your application's focus management strategies.","message":"An Internet Explorer 11 (IE11) specific fix implemented in `v3.1.2` added a check for `document.activeElement`. This change could potentially influence how certain focus-related events are handled, especially in older browser environments or in applications with complex focus management.","severity":"gotcha","affected_versions":">=3.1.2"}],"env_vars":null,"last_verified":"2026-04-22T00:00:00.000Z","next_check":"2026-07-21T00:00:00.000Z","problems":[{"fix":"Ensure `vClickOutside` is imported as the default export: `import vClickOutside from 'v-click-outside';`.","cause":"Attempting to access `vClickOutside.directive` when `vClickOutside` was imported as a named export or incorrectly.","error":"TypeError: Cannot read properties of undefined (reading 'directive')"},{"fix":"For global registration: `Vue.use(vClickOutside);` in your main app file. For local component registration: `directives: { clickOutside: vClickOutside.directive }` within your component options.","cause":"The `v-click-outside` directive was not properly registered, either globally using `Vue.use()` or locally within the component's `directives` option.","error":"Vue error: Failed to resolve directive: click-outside"},{"fix":"Since v3.0.0, the handler function only receives the `event` object. Ensure your handler's signature is `myHandler(event)`.","cause":"This error often occurs when the callback function expects a second argument (the element), which was removed in v3.0.0, or when the `v-click-outside` handler is passed incorrectly.","error":"The callback function receives 'undefined' instead of the event object."}],"ecosystem":"npm"}