我正在try 从字符串呈现VUE组件的模板.我在简单的html上测试了它,但我想呈现包含另一个组件的Komplex字符串.

我使用vuejs版本3.3.4,并从‘vue-模板-编译器’进行编译导入{Compile}; 我不能使用vue中的vue,因为在我的版本中它不存在.

我try 了几个版本,我达到了这一点,我可以用我不能使用的渲染函数将字符串编译成对象.

我用Render方法制作了组件,它调用字符串上的Compile方法,并用Render函数返回对象.问题是无法调用呈现函数. 首先是因为它是函数串,而不是函数. 第二个问题是,当我通过new Function()将它转换为函数并调用它时,它崩溃为未定义的函数,如_c(),_v(),这些函数都在生成的函数中.

我的组件:

<FsDynamicHtml :html="content"></FsDynamicHtml>

content="<h1> Test </h1>"


<script lang="ts">
    import { defineComponent } from 'vue'
    import { compile } from 'vue-template-compiler';

export default defineComponent({
    name: "FsDynamicHtml",
    components: { compile },
    props: {
        html: { type: String},
    },
    computed: {
       
        
    },
    methods: {
        template: function (){
            if (this.html) {
                const compiled = compile(this.html); //returns object with render (string) "with(this){return _c('h1',[_v(" Test ")])}"
                return compiled;
            }
            return null;
        },
    },
    render(createElement) {
        if (this.template) { 
            const render = this.template().render
            const fnc = new Function(render);  
            return fnc();  //Uncaught (in promise) ReferenceError: _c is not defined
            //I tried bind createElement and this to function like (new Function(render).bind(this))
            //return render; //write text: with(this){return _c('h1',[_v(" Test ")])}
            //return this.template(); //[Vue warn]: Invalid VNode type: undefined (undefined)  at <FsDynamicHtml html = "<h1>Test</h1>"> 
            //return new Function(this.template().render)(); //Uncaught (in promise) ReferenceError: _c is not defined
            
        }
        return null;
    }
})
</script>

<style scoped>

</style>

我在代码中 comments 了一些try 过的方法,并取得了效果.

我真的不知道我应该从渲染函数返回什么,我期望编译后的html函数渲染的结果.

谢谢你的帮助.

编辑: 我的工作版本(谢谢阿里·巴赫拉米):

<script lang="ts">
    import { defineComponent, compile } from 'vue';

    export default defineComponent({
        name: "FsDynamicHtml",
        props: {
            html: { type: String },
        },
        computed: {
            compiledRenderFn() {
                if (this.html) {
                    var  render = compile("<span style='color: red'>zzz</span>"+this.html);
                    return render;
                }
                return null;
            },
        },
        render() {
            if (this.compiledRenderFn) {
                return this.compiledRenderFn(this);
            }
            return null;
        },
    });
</script>

COMPILE返回需要_ctx参数的函数(如下所示),并且必须为this.cobledRenderFn(This);使用此参数或任何参数调用.

(function anonymous(Vue
) {
const _Vue = Vue
const { createElementVNode: _createElementVNode } = _Vue

const _hoisted_1 = /*#__PURE__*/_createElementVNode("span", { style: {"color":"red"} }, "zzz", -1 /* HOISTED */)
const _hoisted_2 = /*#__PURE__*/_createElementVNode("h1", null, " Test ", -1 /* HOISTED */)

return function render(_ctx, _cache) {
  with (_ctx) {
    const { createElementVNode: _createElementVNode, Fragment: _Fragment, openBlock: _openBlock, createElementBlock: _createElementBlock } = _Vue

    return (_openBlock(), _createElementBlock(_Fragment, null, [
      _hoisted_1,
      _hoisted_2
    ], 64 /* STABLE_FRAGMENT */))
  }
}
})

推荐答案

您似乎正在try 使用vue-template-compiler在运行时编译一个Vue模板.但是,您使用的是Vue 3,而vue-template-compiler表示Vue 2.在Vue 3中,等价的包被称为@vue/compiler-sfc.

所以,安装它吧:

npm install @vue/compiler-sfc

然后更新脚本以从VUE包中导入编译函数,并使用它将模板编译为呈现函数:

<script lang="ts">
import { defineComponent, compile } from 'vue';

export default defineComponent({
    name: "FsDynamicHtml",
    props: {
        html: { type: String },
    },
    computed: {
        compiledRenderFn() {
            if (this.html) {
                const { render } = compile(this.html);
                return render;
            }
            return null;
        },
    },
    render() {
        if (this.compiledRenderFn) {
            return this.compiledRenderFn();
        }
        return null;
    },
});
</script>

希望这个能帮上忙!

Vue.js相关问答推荐

Visual Studio代码中的VUE/VLAR扩展不断崩溃:JS/TS语言服务立即崩溃5次…

Vuejs 通过数据键迭代复杂对象

在vuejs中使用表单追加时如何使用布尔值

props至少应该定义它们的类型

如何对对象数组进行 v-model

Vuex:如何等待动作完成?

指定一个 vue-cli vue.config.js 位置

如何在 vue.js 模板中显示空间而不是 undefined 和 null?

VueJS 禁用特定属性的react性

Vue 和 TypeScript 所需的props

如何在nuxt路由中添加meta?

在组件外使用 VueI18n 的问题

SassError:媒体查询表达式必须以(开头

Vue路由安全

将 VueJS 数据属性重置为初始值

Vue如何将动态ID与v-for循环+字符串中的字段连接起来?

Vue路由在新页面上回到顶部

NPM:403 禁止 - PUT http://registry.npmjs.org/[package-name] - 禁止

VueJS 复选框更新

Vue组件如何命名