6.4案例:使用渲染函数渲染列表

本节将使用render()函数实现列表的渲染功能。为了渲染特定样式的列表,需要先实现单个列表项的组件ListItem,假设场景为帖子列表,则每个列表项将展示帖子的简介内容。

代码如下

app.component('listitem', {

props: {

content: {

type: Object,

required: true

}

},

render() {

return Vue.h('li', [

Vue.h('p', [

Vue.h('span', `标题: ${this.content.title}`),

Vue.h('span', ` | 发贴人: ${this.content.author}`),

Vue.h('span', ` | 发贴时间: ${this.content.date}`),

Vue.h('span', ` | 点赞数: ${this.content.vote}`),

Vue.h('button', {

onclick: () => this.$emit('vote')

}, '赞')

])

]);

}

});

Vue.h()函数的两个参数都是可选的,区分第二个参数和第三个参数呢的简单方式是看是看对象传参还是数组传参,对象传参是第二个参数(设置元素的属性信息),数组传参是第三个参数(设置字节的信息)

j接下来是列表组件ContentList的代码,其中粗体显示的部分是针对子组件的处理方式代码如下:

//父组件

app.component('contentlist', {

data() {

return {

contents: [

{ id: 1, title: '如何学好前端开发', author: '张三', date: '3个月前', vote: 0 },

{ id: 2, title: 'Vue3.0与Vue2.0的差异', author: '李四', date: '1个月前', vote: 0 },

{ id: 3, title: 'Web3.0初探', author: '王五', date: '2天前', vote: 0 }

]

};

},

methods: {

handleVote(id) {

this.contents = this.contents.map(item => {

return item.id === id? {...item, vote: item.vote + 1 } : item;

});

}

},

render() {

let contentNodes = [];

this.contents.map(item => {

let node = Vue.h(Vue.resolveComponent('listitem'), {

content: item,

onVote: () => this.handleVote(item.id)

});

contentNodes.push(node);

});

return Vue.h('div', [

Vue.h('ul', contentNodes)

]);

}

});

完整代码如下:

html 复制代码
<!DOCTYPE html>
<html>

<head>
    <meta charset="UTF-8">
    <title>Vue 3 App</title>
</head>

<body>
    <div id="app">
        <contentlist></contentlist>
    </div>
    <script src="http://unpkg.com/vue@3"></script>
    <script>
        const app = Vue.createApp({});

        // 列表项组件
        app.component('listitem', {
            props: {
                content: {
                    type: Object,
                    required: true
                }
            },
            render() {
                return Vue.h('li', [
                    Vue.h('p', [
                        Vue.h('span', `标题: ${this.content.title}`),
                        Vue.h('span', ` | 发贴人: ${this.content.author}`),
                        Vue.h('span', ` | 发贴时间: ${this.content.date}`),
                        Vue.h('span', ` | 点赞数: ${this.content.vote}`),
                        Vue.h('button', {
                            onclick: () => this.$emit('vote')
                        }, '赞')
                    ])
                ]);
            }
        });

        // 内容列表组件
        app.component('contentlist', {
            data() {
                return {
                    contents: [
                        { id: 1, title: '如何学好前端开发', author: '张三', date: '3个月前', vote: 0 },
                        { id: 2, title: 'Vue3.0与Vue2.0的差异', author: '李四', date: '1个月前', vote: 0 },
                        { id: 3, title: 'Web3.0初探', author: '王五', date: '2天前', vote: 0 }
                    ]
                };
            },
            methods: {
                handleVote(id) {
                    this.contents = this.contents.map(item => {
                        return item.id === id? {...item, vote: item.vote + 1 } : item;
                    });
                }
            },
            render() {
                let contentNodes = [];
                this.contents.map(item => {
                    let node = Vue.h(Vue.resolveComponent('listitem'), {
                        content: item,
                        onVote: () => this.handleVote(item.id)
                    });
                    contentNodes.push(node);
                });
                return Vue.h('div', [
                    Vue.h('ul', contentNodes)
                ]);
            }
        });

        // 挂载应用
        app.mount('#app');
    </script>
</body>

</html>

代码运行结果:

相关推荐
Nueuis29 分钟前
微信小程序前端面经
前端·微信小程序·小程序
_r0bin_3 小时前
前端面试准备-7
开发语言·前端·javascript·fetch·跨域·class
IT瘾君3 小时前
JavaWeb:前端工程化-Vue
前端·javascript·vue.js
zhang98800003 小时前
JavaScript 核心原理深度解析-不停留于表面的VUE等的使用!
开发语言·javascript·vue.js
potender3 小时前
前端框架Vue
前端·vue.js·前端框架
站在风口的猪11084 小时前
《前端面试题:CSS预处理器(Sass、Less等)》
前端·css·html·less·css3·sass·html5
程序员的世界你不懂4 小时前
(9)-Fiddler抓包-Fiddler如何设置捕获Https会话
前端·https·fiddler
MoFe14 小时前
【.net core】天地图坐标转换为高德地图坐标(WGS84 坐标转 GCJ02 坐标)
java·前端·.netcore
去旅行、在路上5 小时前
chrome使用手机调试触屏web
前端·chrome
Aphasia3115 小时前
模式验证库——zod
前端·react.js