Vue.js教程
3.3.4 使用 JavaScript 代替模板功能
阅读(

Vue.js 基础

Vue.js 过渡和动画

Vue.js 可复用性和组合

Vue.js 混入

Vue.js 自定义指令

Vue.js 渲染函数 & JSX

createElement 参数

节点、树以及虚拟 DOM

基础

使用 JavaScript 代替模板功能

v-ifv-for

由于使用原生的 JavaScript 来实现某些东西很简单,Vue 的 render 函数没有提供专用的 API。比如,template 中的v-ifv-for

<ul v-if="items.length">
  <li v-for="item in items">{{ item.name }}</li>
</ul>
<p v-else>No items found.</p>

这些都会在 render 函数中被 JavaScript 的if/elsemap重写:

props: ['items'],
render: function (createElement) {
  if (this.items.length) {
    return createElement('ul', this.items.map(function (item) {
      return createElement('li', item.name)
    }))
  } else {
    return createElement('p', 'No items found.')
  }
}

v-model

render 函数中没有与v-model相应的 api - 你必须自己来实现相应的逻辑:

props: ['value'],
render: function (createElement) {
  var self = this
  return createElement('input', {
    domProps: {
      value: self.value
    },
    on: {
      input: function (event) {
        self.$emit('input', event.target.value)
      }
    }
  })
}

这就是深入底层要付出的,尽管麻烦了一些,但相对于v-model来说,你可以更灵活地控制。

事件 & 按键修饰符

对于.passive.capture.once事件修饰符, Vue 提供了相应的前缀可以用于on

Modifier(s) Prefix
.passive &
.capture !
.once ~
.capture.onceor.once.capture ~!

例如:

on: {
  '!click': this.doThisInCapturingMode,
  '~keyup': this.doThisOnce,
  '~!mouseover': this.doThisOnceInCapturingMode
}

对于其他的修饰符,前缀不是很重要,因为你可以在事件处理函数中使用事件方法:

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(change13toanother key codefor other key modifiers)
Modifiers Keys:.ctrl,.alt,.shift,.meta if (!event.ctrlKey) return(changectrlKeytoaltKey,shiftKey,ormetaKey, respectively)

这里是一个使用所有修饰符的例子:

on: {
  keyup: function (event) {
  // 如果触发事件的元素不是事件绑定的元素
  // 则返回
  if (event.target !== event.currentTarget) return
  // 如果按下去的不是 enter 键或者
  // 没有同时按下 shift 键
  // 则返回
  if (!event.shiftKey || event.keyCode !== 13) return
  // 阻止事件冒泡
   event.stopPropagation()
  // 阻止该元素默认的 keyup 事件
  event.preventDefault()
    // ...
  }
}

插槽

你可以从this.$slots获取 VNodes 列表中的静态内容:

render: function (createElement) {
  // `<div><slot></slot></div>`
  return createElement('div', this.$slots.default)
}

还可以从this.$scopedSlots中获得能用作函数的作用域插槽,这个函数返回 VNodes:

props: ['message'],
render: function (createElement) {
  // `<div><slot :text="message"></slot></div>`
  return createElement('div', [
    this.$scopedSlots.default({
      text: this.message
    })
  ])
}

如果要用渲染函数向子组件中传递作用域插槽,可以利用 VNode 数据中的scopedSlots域:

render: function (createElement) {
  return createElement('div', [
    createElement('child', {
      // pass `scopedSlots` in the data object
      // in the form of { name: props => VNode | Array<VNode> }
      scopedSlots: {
        default: function (props) {
          return createElement('span', props.text)
        }
      }
    })
  ])
}

如果本教程对您帮助很大,请随意打赏。您的支持,将鼓励我们提供更好的教程!

← 键盘方向键翻页 →
返回顶部 手机访问 关注微信 返回底部

扫码访问歪脖网

随时随地,想看就看

关注歪脖网微信

分享 web 知识、交流 web 经验