背景:
我们经常需要使用到诸如swiper的第3方库,这种第3方库,有的提供相应的npm引入方式,有的没有,对于没有的,我们又想像传统web开发一样使用script引入,在nuxt3下面如何处理?
解决方式:
1.在nuxt.config.ts下面配置对应的js和css
app: {
baseURL: "/路径名称/",//
head: {
title: "",
link: [
{
rel: "icon",
type: "images/x-icon",
href: "网站ico图标",
},
],
script: [
{src: "导入需要的内容文件", type: "text/javascript" },
],
meta: [
{ charset: "utf-8" },
{ name: "viewport", content: "width=device-width, initial-scale=1" },
{ hid: "keywords", name: "keywords", content: "" },
{ hid: "description", name: "description", content: "" },
],
},
},
这种配置方式是全局,就是页面本身没有使用到的js可能会引用到,这就影响首页的加载体验
2.使用useHead在具体的组件动态加载,例如:
useHead({
link: [
{
rel: "stylesheet",
type: "text/css",
href: "https://unpkg.com/swiper@8.4.7/swiper-bundle.css",
},
],
script: [
{
type: "text/javascript",
src: "https://unpkg.com/swiper@8.4.7/swiper-bundle.js",
},
],
});
这种配置确实可以在使用组件的时候进行加载,但有个问题就是什么时候加载完是不清楚的,没找到有相关的api,这样就会导致,功能可能出现时而正常时而异常的问题。
使用setTimeout等方式延迟渲染可能可以缓解,但延迟多久合适?所以也不是个靠谱的方案,建议官方useHead要么做成promise的要么去掉加载js和css的配置,避免出问题。
3.实现个函数完成加载的事情
在utils/index.ts里面写这2个函数,后续添加新的第3方库可参考修改
export async function loadJsCss({
js = [],
css = [],
}: {
js?: string[];
css?: string[];
}) {
const loadScript = (src: string) => {
return new Promise((resolve, reject) => {
const script = document.createElement("script");
script.type = "text/javascript";
script.src = src;
script.onload = resolve;
script.onerror = reject;
document.head.appendChild(script);
});
};
const loadStyle = (href: string) => {
return new Promise((resolve, reject) => {
const link = document.createElement("link");
link.rel = "stylesheet";
link.href = href;
link.onload = resolve;
document.head.appendChild(link);
});
};
const loadResources = async () => {
const promises: Promise<any>[] = [];
for (const jsSrc of js) {
promises.push(loadScript(jsSrc));
}
for (const cssHref of css) {
promises.push(loadStyle(cssHref));
}
await Promise.all(promises);
};
await loadResources();
}
export async function loadSwiperLib() {
if (!window.Swiper) {
await loadJsCss({
css: ["https://unpkg.com/swiper@8.4.7/swiper-bundle.css"],
js: ["https://unpkg.com/swiper@8.4.7/swiper-bundle.js"],
});
}
return window.Swiper;
}
调用方式:
onMounted(async () => {
const Swiper = await loadSwiperLib();
let swiper = new Swiper(".mySwiper", {...})
})
其他补充
window.Swiper在ts环境下可能会报错找不到,需要添加个evn.d.ts定义下
declare module "@wangeditor/editor-for-vue";
interface Window {
Swiper: any;
}
采用正常vue方式引入swiper的一些参考: