基礎javascript
vue推薦在絕大多數狀況下使用template來建立你的html。然而在一些場景中,你真的須要javascript的徹底編程能力。這就是render函數。它比template更接近編譯器html
當咱們開始寫一個經過level prop動態生成heading標籤的組件,你可能很快這樣實現:vue
anchored-heading
中的hello world!這些子元素被存儲在組件實例中的
$slots.default
中。若是你還不瞭解,在深刻render函數前,須要瞭解實例的API.
{
// 和`v-bind:class`同樣的 API
'class': {
foo: true,
bar: false
},
// 和`v-bind:style`同樣的 API
style: {
color: 'red',
fontSize: '14px'
},
// 正常的 HTML 特性
attrs: {
id: 'foo'
},
// 組件 props
props: {
myProp: 'bar'
},
// DOM 屬性
domProps: {
innerHTML: 'baz'
},
// 事件監聽器基於 `on`
// 因此再也不支持如 `v-on:keyup.enter` 修飾器
// 須要手動匹配 keyCode。
on: {
click: this.clickHandler
},
// 僅對於組件,用於監聽原生事件,而不是組件內部使用 `vm.$emit` 觸發的事件。
nativeOn: {
click: this.nativeClickHandler
},
// 自定義指令. 注意事項:不能對綁定的舊值設值
// Vue 會爲您持續追蹤
directives: [
{
name: 'my-custom-directive',
value: '2',
expression: '1 + 1',
arg: 'foo',
modifiers: {
bar: true
}
}
],
// Scoped slots in the form of
// { name: props => VNode | Array<VNode> }
scopedSlots: {
default: props => createElement('span', props.text)
},
// 若是組件是其餘組件的子組件,需爲 slot 指定名稱
slot:
'name-of-slot',
// 其餘特殊頂層屬性
key:
'myKey',
ref: 'myRef'
}
|
約束java
VNodes必須惟一express
組件樹中的全部VNodes必須是惟一的。這意味着下面的render函數是無效的編程
render:function(creatElement){api
var myParagraphVNode = createElement('p', 'hi');數組
}babel
若是你真的須要重複不少次的元素/組件,你可使用工廠函數來實現,例如,下面這個例子中render函數完美有效的渲染了20個重複的段落:app
render:function(createElement){
return createElement('div',Array.apply(null,{length:20}).map(function(){
return createElement('p','hi');
}))
}
使用javascript代替模板功能
v-if and v-for
因爲使用原生的javascript來實現某些東西很簡單,vue的render函數沒有提供專用的API,好比:template中的v-if 和v-for.
Modifier(s) | Prefix |
---|---|
.passive |
& |
.capture |
! |
.once |
~ |
.capture.once or.once.capture |
~! |
Modifier(s) | Equivalent in Handler |
---|---|
.stop |
event.stopPropagation() |
.prevent |
event.preventDefault() |
.self |
if (event.target !== event.currentTarget) return |
Keys:.enter , .13 |
if (event.keyCode !== 13) return (change 13 to another key code for other key modifiers) |
Modifiers Keys:.ctrl , .alt , .shift , .meta |
if (!event.ctrlKey) return (change ctrlKey to altKey , shiftKey , or metaKey , respectively) |
下面是使用了全部修飾符的例子:
on:{
keyup:function(event){
//若是觸發事件的元素不是事件綁定的元素
//則返回
if(event.target !== event.currentTarget)return
if(!event.shiftKey || event.keyCode !== 13)return
}
}
slots
你能夠從this.$slots獲取VNode列表中的靜態內容。
render:function(createElement){
createElement('div',this.$slots.default)
}
還能夠從this.$scopedSlots中得到能用做函數的做用域插槽,這個函數返回VNodes:
render:function(createElement){
return createElement('div',[this.$scopedSlots.default({text:this.msg})])
}
若是要用render函數向子組件中傳遞做用域插槽,能夠利用VNode數據中的scopedSlots域:
render:function(createElement){
return createElement('div',[
createElement('child',{
scopedSlots:{
default:function(props){
return createElement('span',props.text)
}
}
})
])
}
jsx
若是你寫了不少render函數,可能會以爲痛苦:
h
做爲
createElement
的別名是 Vue 生態系統中的一個通用慣例,實際上也是 JSX 所要求的,若是在做用域中
h
失去做用, 在應用中會觸發報錯。
在添加functional:true以後,錨點標題組件的render函數之間,簡單更新增長context參數。