mixin,就是混合。混合可以混到组件里一些功能,全局混合可以混合到应用的所有组件里。下面我们一块儿创建一个混合,用它设置页面的标题。
现在所有页面的标题都是项目的名字,我想在页面组件里可以通过一个选项来设置页面的标题。
回到项目,找到这个内容列表页面的组件, src/post/index 下面的 post-index, 在组件里可以添加一个 title,用这个选项设置一下页面的标题,这个 title 可以是一个属性,也可以是一个方法,如果是方法的话,可以用这个方法返回要设置的页面标题的内容。
现在还没有效果,我们可以创建一个混合,在混合里获取到组件里的这个 title 属性,然后再去设置一下页面的标题。
应用配置
创建一个混合,放在 src/app 的下面,新建一个文件叫 app.mixin.ts。 页面标题里面可以包含一个应用的名字,打开项目根目录下的 .env.development,添加一个环境变量,名字叫 VUE_APP_APP_NAME,复制一下。再打开 .env.production,在这里也添加一个 VUE_APP_APP_NAME。
再打开应用的配置, app.config,在里面添加一个新的配置,导出这个配置,配置的名字叫 APP_NAME,它的值就是环境变量里的 VUE_APP_APP_NAME。
回到终端,重新运行一下项目的开发服务,先停止,然后再执行一下 serve 命令。
创建混合
再回到这个混合模块,在这里创建一个标题混合,导出一个东西,名字叫 titleMixin ,类型可以设置成 ComponentOptions。它的值是一个对象,里面可以添加组件的生命周期,比如 created ,在这个生命周期里,可以在控制台上输出点东西,比如 标题混合。
这个混合可以用在应用的全局,打开应用的入口,main.ts , 在创建了应用的下面,找个地方,用一下 app 上面的 mixin ,在全局应用一个混合。混合的名字叫 titleMixin。 编辑器自动帮我们从 app.mixin 里面导入了这个 titleMixin 。
在浏览器上观察一下控制台上输出的内容,你会发现,标题混合 这几个字输出了很多次。因为我们把 titleMixin 用在了应用的全局,应用里创建了每个组件之后都会输出这行文字。
回来继续再编辑一下这个标题混合,这里可以执行一个方法,名字是 setTitle,把 this 交给这个方法。 下面再添加一个 updated 生命周期,在这个方法里也执行一下 setTitle,把 this 交给它。
设置标题
然后在上面我们可以去定义一下这个设置页面标题用的方法,方法的名字叫 setTitle,方法接收一个 vm 参数,类型可以设置成 ComponentPublicInstance。
在方法里可以先获取到组件里的 title 选项。 把 title 从 vm 的 $options 里解构出来。 然后可以做一下判断,如果组件里有 title 这个选项。
先声明一个 titleContent ,然后继续做一下判断, typeof title 如果是 function ,因为这个 title 选项可能是个函数,如果是函数我们就让 titleContent 的值等于执行了这个函数之后返回的结果,title.call(vm)
不然的话,就让 titleContent 等于这个 title 选项的值。
下面再设置一下 document 里的 title 属性,这个属性的值就是页面的标题,让它等于 titleContent。 小横线,再加上应用的名字,APP_NAME,它是之前我们在应用的配置里添加的一个配置选项。
预览
再回到浏览器观察一下这个内容列表页面的标题,你会发现,这个页面的标题已经变成了内容列表了。打开内容列表里的一个内容页面。这个内容页面的标题也可以再设置一下。
在项目里找到页面对应的那个组件, src/post/show/post-show 这个组件,找到以后,在组件里添加一个 title ,它可以是一个属性也可以是一个方法,这里我们用一个方法。 方法里做一下判断,如果 showPost 是真的,就 return this.post.title ,用内容的 title 属性的值作为页面的标题。
在浏览器上观察一下这个内容页面的标题,你会发现这个标题就是内容的标题。 后面加上了应用的名字。
回到应用的首页,首页的标题可以特别处理一下,在这个 setTitle 方法里面,在这个判断 title 区块的外面,再做一下判断,如果 vm.$route.path 等于 / ,意思就是如果路由地址是应用的根,也就是应用的首页。我们可以直接把页面的标题设置成 APP_NAME 这个选项的值。
最后再到浏览器上观察一下,现在首页的页面标题就会是应用的名字。