【问题标题】:Vue functional component throws _c is not defined errorVue 功能组件抛出 _c is not defined 错误
【发布时间】:2020-03-10 03:44:37
【问题描述】:

我使用渲染方法创建了以下功能组件:

import Vue from "vue"

const { render, staticRenderFns } = Vue.compile(`<div>Hello World</div>`)

Vue.component("HelloWorld", {
    functional: true,
    render,
    staticRenderFns
})

然后在App.vue:

<template>
    <div id="app">
        <HelloWorld />
    </div>
</template>

<script>
export default {
    data() {
        return {
            compiled: false
        }
    }
}
</script>

<style>
</style>

我得到了错误:

_c is not defined.

我在这里做错了吗?

【问题讨论】:

  • 看这个 - stackoverflow.com/questions/44369839/… 你需要导入你的组件
  • 导入我的组件?但它已经被声明为一个全局组件。而且,此问题仅与功能组件有关。普通组件工作正常,即如果我删除 functional: true 它工作正常。
  • @webnoob 该死的,这很有用。非常感谢。虽然不确定功能组件。

标签: javascript vue.js vuejs2 vue-component


【解决方案1】:

据我所知,Vue.compile 生成的渲染函数不能用于渲染功能组件。

【讨论】:

  • 哦,废话!真可惜。有没有办法通过传递模板字符串来构建功能组件?
  • 我不这么认为。 Vue 捆绑的模板编译器无法编译功能模板。我相信只有vue-loader 提供的编译器才能在构建时做到这一点。
  • 请问您为什么需要使用Vue.compile?也许有更好的解决方案来解决您的问题。
  • 其实我是从服务器获取 html 并将其渲染为 Vue 组件。
  • 您获取的是纯 HTML 还是 Vue 模板?如果它是经过净化的 HTML,那么您可以使用 v-html 来呈现它。
【解决方案2】:

我认为最接近从模板字符串创建功能组件的方法是解析字符串以获取元素类型和属性并呈现为:

Vue.component("hello-world", {
      functional: true,
      render: function(createElement, context) {
        return createElement(
          "div",
         'example text'         
        );
      }
});

【讨论】:

    【解决方案3】:

    正如 Decade Moon 已经提到的,Vue.compile 返回的渲染函数不能用作函数组件中的渲染函数。当您检查 Vue.compile 返回的函数的签名时,原因就很清楚了:

    const render: (createElement: any) => VNode
    

    如您所见,function 缺少第二个参数,这是功能组件的渲染函数所必需的:

    render: (createElement: CreateElement, context: RenderContext<Record<never, any>>) => VNode
    

    功能组件是无实例的。这意味着没有 this 上下文 - 这就是为什么需要额外的 context 参数来携带 props\listeners 等。

    如果你看一下this post on Vue forum

    compile() 创建的渲染函数依赖于组件的私有属性。要访问这些属性,必须将方法分配给组件的属性(因此它可以通过this 访问这些属性)

    但这并不意味着您不能使用模板创建功能组件。可以,只是不能使用Vue.compile 动态传递模板文本。如果你对静态模板没问题,你可以这样做:

    // component.vue
    
    <template functional>
      <div>Hello World</div>
    </template>
    
    <script>
    export default {
      name: "hello"
    };
    </script>
    

    ...并像使用任何其他 SFC 一样使用该组件(单个文件组件 = VUE 文件)

    如果您需要动态模板文本,请改用非功能组件...

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2019-06-22
      • 1970-01-01
      • 1970-01-01
      • 2018-06-28
      • 2022-01-11
      • 1970-01-01
      • 2015-12-06
      • 2020-12-03
      相关资源
      最近更新 更多