可复用性&组合
mixins混入
用我的话来解释就是包含了一些组件选项的对象,然后可以在不同的组件中引用。一个例子来演示:
Vue.component('tooltip', {
template: `
我是内容1
`,
methods: {
show: function () {
this.visible = true
},
hide: function () {
this.visible = false
}
},
data: function () {
return {
visible: false
}
}
})
Vue.component('popup', {
template: `
我是内容2
`,
data: function () {
return {
visible: false
}
},
methods: {
toggle: function () {
this.visible = !this.visible
},
hide: function () {
this.visible = false
}
}
})
new Vue({
el: '#app'
})
例子中两个组件,重复的功能太多,比如data中的visible,methods中的hide方法。此时我们要让代码变得简约,就用到了mixins,定义一个对象,然后在组件中用数组来引入。代码改进如下:
var myMix = {
methods: {
show: function () {
this.visible = true
},
hide: function () {
this.visible = false
},
toggle: function () {
this.visible = !this.visible
}
},
data: function () {
return {
visible: false
}
}
};
Vue.component('tooltip', {
template: `
我是内容1
`,
mixins: [myMix]
})
Vue.component('popup', {
template: `
我是内容2
`,
mixins: [myMix]
})
值得注意的是,在组件中定义和mixins相同的选项时,会覆盖mixins中的选项。比如我在popul组件中定义data,默认visible:ture,则会覆盖掉mixins中默认的visible:false.
自定义指令
跟自定义组件类似,还是用一个例子来看比较明白:
我是相片
Lorem ipsum dolor sit amet consectetur, adipisicing elit. Dolor suscipit ad consequuntur quia ipsam eius consequatur eum
sint, minima adipisci nemo error, delectus quaerat sit magni non praesentium maiores? Voluptas. Lorem ipsum dolor sit
amet consectetur adipisicing elit. Ipsa, molestias, a dicta commodi harum, ducimus iusto quo natus eos reprehenderit
est ipsam nemo error tempora? Reprehenderit iure ipsum at similique! Lorem, ipsum dolor sit amet consectetur adipisicing
elit. Asperiores saepe iusto dolore, magnam ex earum illo. Non, necessitatibus dignissimos libero sed dolorem ipsa ea
sunt quo optio omnis praesentium atque. Lorem ipsum dolor sit amet consectetur adipisicing elit. Iste quibusdam ratione,
quisquam dolorem doloribus delectus deserunt ab sit error placeat explicabo, ea, animi magnam. Ad, aperiam temporibus.
Eos, exercitationem laborum. Lorem ipsum dolor, sit amet consectetur adipisicing elit. Accusamus fugiat incidunt sit
deserunt consequatur molestias dicta praesentium corrupti autem nostrum dolorum facilis, quidem ipsa obcaecati ipsum
saepe? Aliquid, inventore suscipit. Lorem, ipsum dolor sit amet consectetur adipisicing elit. Suscipit voluptatem debitis
delectus veritatis, laboriosam repudiandae, ea non minima ipsam eligendi nam tempora porro id quae maxime doloribus nulla,
accusantium animi. Lorem ipsum dolor sit amet consectetur, adipisicing elit. Iste temporibus molestias ratione. Porro
itaque aperiam vero, voluptatum natus animi adipisci necessitatibus, quidem ipsam possimus molestias officiis, fugit
velit quibusdam soluta! Lorem ipsum dolor sit amet consectetur adipisicing elit. Perferendis minus commodi architecto
consectetur nesciunt totam sit aspernatur quas placeat fugit aut esse dolorum sed doloribus fugiat, nihil hic possimus
rerum.
.card {
background: #ccc;
padding: 15px;
margin: 15px;
width: 80px;
height: 80px;
text-align: center;
}
Vue.directive('pin', function (el, binding) {
var val = binding.value;
if (val) {
el.style.position = 'fixed';
} else {
el.style.position = 'static'
}
})
new Vue({
el: '#app',
data: {
pinned: false
}
})
在本例子中,点击按钮就可以切换相片的position属性。
解释一下,例子中pin是自定义指令的名字,在全局中用v-pin来表示。函数中el代表指令所在的DOM元素,binding是指令的值的一些属性,这里直接从官网上copy了:
- name:指令名,不包括 v- 前缀。
- value:指令的绑定值,例如:v-my-directive="1 + 1" 中,绑定值为 2。
- oldValue:指令绑定的前一个值,仅在 update 和 componentUpdated 钩子中可用。无论值是否改变都可用。
- expression:字符串形式的指令表达式。例如 v-my-directive="1 + 1" 中,表达式为 "1 + 1"。
- arg:传给指令的参数,可选。例如 v-my-directive:foo 中,参数为 "foo"。
- modifiers:一个包含修饰符的对象。例如:v-my-directive.foo.bar 中,修饰符对象为 { foo: true, bar: true }。
好,比如我们在指令上添加一些修饰符:
Vue.directive('pin', function (el, binding) {
var val = binding.value;
var position = binding.modifiers;
var warning = binding.arg;
if (val) {
el.style.position = 'fixed';
for(var key in position) {
if(position[key]){
el.style[key] = '20px'
}
}
if (warning === 'true') {
el.style.background = 'red'
}
} else {
el.style.position = 'static';
el.style.background = '#ccc'
}
})
这样点击按钮,相片就变为红色,位置移到了右下方。
过滤器filter
过滤器其实就是作一个优化的作用。它可以用在双花括号插值和 v-bind 表达式。来个例子吧:
毫米 {{length | meter}}
{{price | current}}
Vue.filter('meter', function (val, unit) {
var val = val || 0;
var unit = unit || '米';
return (val / 1000).toFixed(3) + unit
})
Vue.filter('current', function (val, unit) {
var val = val || 0;
var unit = unit || '元';
return val + unit
})
new Vue({
el: '#app',
data: {
price: 10,
length: 10
}
})
第二个小例子中,默认的单位就是元,如果我们把过滤器后面加个括号,加了美元符号。就可以变更视图。
{{price | current('$')}}
简单的一些单位换算可以用过滤器,如果比较复杂, 最好还是用计算属性computed