Fixing vue-js-modal Library for Vue 3: A Guide to Restoring Modal Functionality

RMAG news

In one of my Vue 2 projects, I utilized the vue-js-modal library. However, after migrating the project from Vue 2 to Vue 3, the modal didn’t work properly. Despite extensive research, I couldn’t find any documentation or discussions addressing this issue, which led me to write this article.

In this article, I will share the changes I made to adapt vue-js-modal for Vue 3. I hope you find these insights helpful!

First, please review the GitHub thread and apply the changes suggested here: https://github.com/euvl/vue-js-modal/issues/814

After following the suggestions from the GitHub thread, you might still encounter issues with the modal in your Vue 3 project. To fully resolve these problems, I made several changes to the PluginCore.js and Plugin.js files. Below, you’ll find the details of these changes.

Changes in Plugin.js
Modify the plugin:

import Modal from ./components/Modal.vue;
import Dialog from ./components/Dialog.vue;
import PluginCore from ./PluginCore;

const Plugin = {
install(app, options = {}) {
if (app.config.globalProperties.$modal) {
return;
}

const plugin = PluginCore(options);

app.config.globalProperties.$modal = plugin;
app.provide($modal, plugin);

app.mixin({
mounted() {
if (this.$root === this) {
if (!plugin.context.root) {
plugin.setDynamicModalContainer(this);
}
}
},
});

app.component(plugin.context.componentName, Modal);

if (options.dialog) {
app.component(Dialog, Dialog);
}
},
};

export default Plugin;

Changes in PluginCore.js
Imports and Initialization:

Replace the existing imports and initialization with the following:

import { h, render, createVNode } from vue;

Show Dynamic Modal:

Update the logic for showing dynamic modals:

const showDynamicModal = (
component,
componentProps,
componentSlots,
modalProps = componentSlots || {},
modalEvents
) => {
const container = context.root?.__modalContainer;
const defaults = options.dynamicDefaults || {};

if (!container) {
console.warn(Modal container not found. Make sure the dynamic modal container is set.);
return;
}
container.add(
component,
componentProps,
componentSlots,
{ defaults, modalProps },
modalEvents
);
};

Set Dynamic Modal Container:

Modify the function responsible for setting the modal container:

const setDynamicModalContainer = (root) => {
context.root = root;

if (!root) {
console.warn(Root component is undefined. Make sure the root instance is passed correctly.);
return;
}

const element = createDivInBody();

const vnode = createVNode(ModalsContainer);
vnode.appContext = root.$.appContext;

try {
return render(vnode, element);
} catch (error) {
console.error(Error rendering vnode:, error);
}
};

Final Changes in ModalsContainer.vue
As part of the migration to Vue 3, it was necessary to make a specific adjustment in the ModalsContainer.vue component.

Updating Event Listeners:

In the ModalsContainer.vue file, remove the existing v-on=”$listeners” directive and replace it with:

von=modal.componentListeners

This change should be made at line number 13.

By making these adjustments, you should be able to successfully migrate the vue-js-modal library to work seamlessly with Vue 3. I hope these steps help you resolve any remaining issues with your modals! If you need further assistance, please don’t hesitate to ask in the comments section. Additionally, I would appreciate any feedback or insights you have, so feel free to leave your comments below.

https://www.aliozzaim.com

references
https://github.com/euvl/vue-js-modal/issues/814
https://github.com/euvl/vue-js-modal

Please follow and like us:
Pin Share