本项目综合运用了 Vue3.0 的新特性。

  • 基于 Composition API 即 Function-based API 进行改造,配合 Vue Cli,优先体验 Vue3 特性
  • 使用单例对象模式进行组件通信
  • 使用 axios 库进行网络请求,weui 库实现 UI 界面
# 安装依赖npm install# 在浏览器打开localhost:8080查看页面,并实时热更新npm run serve# 发布项目npm run build

建议配合 Visual Studio Code 和 Vue 3 Snippets 代码插件

Dependencies

以下是项目运用到的依赖,@vue/composition-api 配合 vue 模块让我们 Vue2.0 版本可以抢先体验 Vue3.0 的新特性,axios 是辅助我们发送网络请求得到数据的工具库,weui是一套与微信原生视觉一致的基础样式库,方便我们快速搭建项目页面。

"@vue/composition-api": "^0.3.4","axios": "^0.19.0","core-js": "^3.4.3","vue": "^2.6.10","weui": "^2.1.3"

Directory Structure

├── src│   ├── App.vue                          # 组件入口│   ├── assets                           # 资源目录│   ├── stores/index.js                  # 状态管理│   ├── components                       # 组件目录│   │   ├── Header.vue                   # 头部组件│   │   ├── Search.vue                   # 搜索框组件│   │   ├── Panel.vue                    # 列表组件│   ├── main.js                          # 项目入口├── public                               # 模板文件├── vue.config.js                        # 脚手架配置文件├── screenshot                           # 程序截图

Composition API

npm install @vue/composition-api --save

使用 npm 命令下载了 @vue/composition-api 插件以后,引入该模块后,需要显式调用 Vue.use(VueCompositionApi) ,按照文档在 main.js 引用便开启了 Composition API 的能力。

// main.jsimport Vue from 'vue'import App from './App.vue'// 1.引入Composition API模块import VueCompositionApi from '@vue/composition-api'Vue.config.productionTip = false// 2.不要漏了显式调用 VueCompositionApiVue.use(VueCompositionApi)new Vue({  render: h => h(App),}).$mount('#app')
npm install weui --save

我们同样使用 npm 安装 weui 模块,然后在 main.js 中引入 weui的基础样式库,方便我们可以在全局使用微信基础样式构建项目页面。

// main.jsimport Vue from 'vue'import App from './App.vue'// 全局引入 `weui` 的基础样式库import 'weui'import VueCompositionApi from '@vue/composition-api'Vue.config.productionTip = falseVue.use(VueCompositionApi)new Vue({  render: h => h(App),}).$mount('#app')

回到 App.vue,保留 components 属性值清空 模板的内容,删除

Hello World

在 src/components 目录下新建第一个组件,取名为 Header.vue 写入以下代码:

{{title}}

setup

这里运用了一个全新的属性 setup ,这是一个组件的入口,让我们可以运用 Vue3.0 暴露的新接口,它运行在组件被实例化时候,props 属性被定义之后,实际上等价于 Vue2.0 版本的 beforeCreate 和 Created 这两个生命周期,setup 返回的是一个对象,里面的所有被返回的属性值,都会被合并到 Vue2.0 的 render 渲染函数里面,在单文件组件中,它将配合 模板的内容,完成 Model 到 View 之间的绑定,在未来版本中应该还会支持返回 JSX 代码片段。

{{name}}

reactive

在 setup 函数里面, 我们适应了 Vue3.0 的第一个新接口 reactive 它主要是处理你的对象让它经过 Proxy 的加工变为一个响应式的对象,类似于 Vue2.0 版本的 data 属性,需要注意的是加工后的对象跟原对象是不相等的,并且加工后的对象属于深度克隆的对象。

const state = reactive({ name: 'Eno Yao' })

props

在 Vue2.0 中我们可以使用 props 属性值完成父子通信,在这里我们需要定义 props 属性去定义接受值的类型,然后我们可以利用 setup 的第一个参数获取 props 使用。

export default {  props: {    // 标题    title: String,    // 颜色    color: String  },  setup(props) {    // 这里可以使用父组件传过来的 props 属性值  }};

我们在 App.vue 里面就可以使用该头部组件,有了上面的 props 我们可以根据传进来的值,让这个头部组件呈现不同的状态。

context

setup 函数的第二个参数是一个上下文对象,这个上下文对象中包含了一些有用的属性,这些属性在 Vue2.0 中需要通过 this 才能访问到,在 vue3.0 中,访问他们变成以下形式:

setup(props, ctx) {  console.log(ctx) // 在 setup() 函数中无法访问到 this  console.log(this) // undefined}

具体能访问到以下有用的属性:

rootparentrefsattrslistenersisServerssrContextemit

完成上面的 Header.vue 我们就编写 Search.vue 搜索框组件,继续再 src/components 文件夹下面新建 Search.vue 文件,点击查看源代码。

搜索 取消

toRefs

可以看到我们上面用了很多的新属性,我们先介绍 toRefs ,函数可以将 reactive() 创建出来的响应式对象,转换为普通的对象,只不过,这个对象上的每个属性节点,都是 ref() 类型的响应式数据,配合 v-model 指令能完成数据的双向绑定,在开发中非常高效。

import { reactive, toRefs } from "@vue/composition-api";export default {  setup() {    const state = reactive({ name: 'Eno Yao' })  }  return {    // 直接返回 state 那么数据会是非响应式的, MV 单向绑定    // ...state,    // toRefs 包装后返回 state 那么数据会是响应式的, MVVM 双向绑定    ...toRefs(state),  };}

template refs

这里的输入框拥有两个状态,一个是有输入框的状态和无输入框的状态,所以我们需要一个布尔值 isFocus 来控制状态,封装了一个 toggle 方法,让 isFocus 值切换真和假两个状态。

const toggle = () => {  // isFocus 值取反  state.isFocus = !state.isFocus;};

然后配合 v-bind:class 指令,让 weui-search-bar_focusing 类名根据 isFocus 值决定是否出现,从而更改搜索框的状态。

这里的搜索输入框放入了 v-model 指令,用于接收用户的输入信息,方便后面配合列表组件执行检索逻辑,还放入了 ref 属性,用于获取该 标签的元素节点,配合state.inputElement.focus() 原生方法,在切换搜索框状态的时候光标自动聚焦到输入框,增强用户体验。

watch

watch() 函数用来监视某些数据项的变化,从而触发某些特定的操作,使用之前还是需要按需导入,监听 searchValue 的变化,然后触发回调函数里面的逻辑,也就是监听用户输入的检索值,然后触发回调函数的逻辑把 searchValue 值存进我们创建 store 对象里面,方面后面和 Panel.vue 列表组件进行数据通信:

import { reactive, watch } from "@vue/composition-api";import store from "../stores";export default {  setup() {    const state = reactive({      searchValue: "",    });    // 监听搜索框的值    watch(      () => {        return state.searchValue;      },      () => {        // 存储输入框到状态 store 中心,用于组件通信        store.setSearchValue(state.searchValue);      }    );    return {      ...toRefs(state)    };  }};

state management

在这里我们维护一份数据来实现共享状态管理,也就是说我们新建一个 store.js 暴露出一个 store 对象共享 Panel 和 Search 组件的 searchValue 值,当 Search.vue 组件从输入框接受到 searchValue 检索值,就放到 store.js 的 store 对象中,然后把该对象注入到 Search 组件中,那么两个组件都可以共享 store 对象中的值,为了方便调试我们还分别封装了 setSearchValue 和 getSearchValue 来去操作该 store 对象,这样我们就可以跟踪状态的改变。

// store.jsexport default {    state: {        searchValue: ""    },    // 设置搜索框的值    setSearchValue(value) {        this.state.searchValue = value    },    // 获取搜索框的值    getSearchValue() {        return this.state.searchValue    }}

完成上面的 Search.vue 我们紧接着编写 Panel.vue 搜索框组件,继续再 src/components 文件夹下面新建 Panel.vue 文件。

查看更多

lifecycle hooks

Vue3.0 的生命周期钩子和之前不一样,新版本都是以 onXxx() 函数注册使用,同样需要局部引入生命周期的对应模块:

import { onMounted, onUpdated, onUnmounted } from "@vue/composition-api";export default {  setup() {    const loadMore = () => {};    onMounted(() => {      loadMore();    });    onUpdated(() => {      console.log('updated!')    })    onUnmounted(() => {      console.log('unmounted!')    })    return {      loadMore    };  }};

以下是新旧版本生命周期的对比:

beforeCreate -> use setup()created -> use setup()beforeMount -> onBeforeMountmounted -> onMountedbeforeUpdate -> onBeforeUpdateupdated -> onUpdatedbeforeDestroy -> onBeforeUnmountdestroyed -> onUnmountederrorCaptured -> onErrorCaptured

同时新版本还提供了两个全新的生命周期帮助我们去调试代码:

onRenderTrackedonRenderTriggered

在 Panel 列表组件中,我们注册 onMounted 生命周期,并在里面触发请求方法 loadMore 以便从后端获取数据到数据层,这里我们使用的是 axios 网络请求库,所以我们需要安装该模块:

npm install axios --save

封装了一个请求列表数据方法,接口指向的是 Cnode 官网提供的 API ,由于 axios 返回的是 Promise ,所以配合 async 和 await 可以完美的编写异步逻辑,然后结合onMounted 生命周期触发,并将方法绑定到视图层的查看更多按钮上,就可以完成列表首次的加载和点击查看更多的懒加载功能。

// 发送 ajax 请求获取列表数据const loadMore = async () => {  // 获取列表数据  let data = await axios.get("https://cnodejs.org/api/v1/topics", {    params: {      // 每一页的主题数量      limit: 10,      // 页数      page: state.page    }  });  // 叠加页数  state.page += 1;  // 合并列表数据  state.news = [...state.news, ...data.data.data];};onMounted(() => {  // 首屏加载的时候触发请求  loadMore();});

computed

接下来我们就使用另外一个属性 computed 计算属性,跟 Vue2.0 的使用方式很相近,同样需要按需导入该模块:

import { computed } from '@vue/composition-api';

计算属性分两种,只读计算属性和可读可写计算属性:

// 只读计算属性let newsComputed = computed(() => news.value + 1)// 可读可写let newsComputed = computed({  // 取值函数  get: () => news.value + 2,  // 赋值函数  set: val => {    news.value = news.value - 3  }})

这里我们使用可读可写计算属性去处理列表数据,还记得我们上一个组件 Search.vue 吗,我们可以结合用户在搜索框输入的检索值,配合 computed 计算属性来筛选对我们用户有用列表数据,所以我们首先从 store 的共享实例里面拿到 Search.vue 搜索框共享的 searchValue ,然后利用原生字符串方法 indexOf 和 数组方法 filter 来过滤列表的数据,然后重新返回新的列表数据 newsComputed,并在视图层上配合 v-for 指令去渲染新的列表数据,这样做既可以在没搜索框检索值的时候返回原列表数据 news ,而在有搜索框检索值的时候返回新列表数据 newsComputed。

import store from "../stores";export default {  setup() {    const state = reactive({      // 原列表数据      news: [],      // 通过搜索框的值去筛选后的新列表数据      newsComputed: computed(() => {        // 判断是否输入框是否输入了筛选条件,如果没有返回原始的 news 数组        if (store.state.searchValue) {          return state.news.filter(item => {            if (item.title.indexOf(store.state.searchValue) >= 0) {              return item;            }          });        } else {          return state.news;        }      }),      searchValue: store.state    });  }}

vue3 main.js引入 axios_Vue3.0新特性探索相关推荐

  1. VUE3对比VUE2的优势及新特性原理

    1.Vue3.0新特性 性能比Vue2.x快1.2~2倍 原因1: diff方法优化: vue2中的虚拟dom是全量的对比(每个节点不论写死的还是动态的都会比较) vue3新增了静态标记(patchf ...

  2. C#6.0,C#7.0新特性

    C#6.0,C#7.0新特性 C#6.0新特性 Auto-Property enhancements(自动属性增强) Read-only auto-properties (真正的只读属性) Auto- ...

  3. C# 7.0 新特性:本地方法

    C# 7.0:本地方法 VS 2017 的 C# 7.0 中引入了本地方法,本地方法是一种语法糖,允许我们在方法内定义本地方法.更加类似于函数式语言,但是,本质上还是基于面向对象实现的. 1. 本地方 ...

  4. 大数据技术之_11_HBase学习_03_HBase 实战之谷粒微博(练习API) + 扩展知识(布隆过滤器+HBase2.0 新特性)

    大数据技术之_11_HBase学习_03 第8章 HBase 实战之谷粒微博 8.1 需求分析 8.2 代码实现 第9章 扩展知识 9.1 HBase 在商业项目中的能力 9.2 布隆过滤器 9.3 ...

  5. 深圳Java培训学习:Java8.0新特性之Lambda表达式--【千锋】

    深圳Java培训学习:Java8.0新特性之Lambda表达式–[千锋] 前言 Java 8 已经发布很久了,很多报道表明Java 8 是一次重大的版本升级.本篇文章,主要给大家介绍的是lambda表 ...

  6. GreenDao3.0新特性解析(配置、注解、加密)

    Greendao3.0release与7月6日发布,其中最主要的三大改变就是:1.换包名 2.实体注解 3.加密支持的优化 本文里面会遇到一些代码示例,就摘了官方文档和demo里的例子了,因为他们的例 ...

  7. Servlet 3.0 新特性概述

    Servlet 3.0 新特性概述 Servlet 3.0 作为 Java EE 6 规范体系中一员,随着 Java EE 6 规范一起发布.该版本在前一版本(Servlet 2.5)的基础上提供了若 ...

  8. Redis 6.0 新特性-多线程连环13问!

    来自:码大叔 导读:支持多线程的Redis6.0版本于2020-05-02终于发布了,为什么Redis忽然要支持多线程?如何开启多线程?开启后性能提升效果如何?线程数量该如何设置?开启多线程后会不会有 ...

  9. 【收藏】C# 2.03.0新特性总结

    c#2.0新特性 范型 我们知道通用的数据结构可以采用object存储任何数据类型.使用object问题是: 显示的强制转带来的代码复杂性 换装箱拆箱的性能损失(为什么有性能损失?因为涉及动态内存分配 ...

  10. 返璞归真 asp.net mvc (10) - asp.net mvc 4.0 新特性之 Web API

    返璞归真 asp.net mvc (10) - asp.net mvc 4.0 新特性之 Web API 原文:返璞归真 asp.net mvc (10) - asp.net mvc 4.0 新特性之 ...

最新文章

  1. javase基础回顾(三) 动态代理
  2. Python之区块链简单记账本实现
  3. Maven-生命周期
  4. python Modbus基础
  5. 地图事件触发_使用地图触发功能处理相干事件
  6. Spring--quartz中cronExpression配置说明
  7. java窗口添加标签页_在新标签页中打开新窗口
  8. shell脚本:判断本地和远程文件是否存在
  9. 解决Mysql安装之后没有my.ini配置文件问题
  10. 企业文化是数字化转型最大障碍-解读《2022年首席数据官调查报告》
  11. timestamp显示毫秒_Oracle date timestamp 毫秒 - 时间函数总结
  12. 我真要戒游戏了毒奶粉再见!
  13. Sklearn上机笔记--标准化
  14. 查看用友NC的版本方法(不启动NC,只看NCHOME)
  15. Python 第八篇:异常处理、Socket语法、SocketServer实现多并发、进程和线程、线程锁、GIL、Event、信号量、进程间通讯...
  16. 可以搜索相似网站的网站
  17. 【转】常用的隧道技术
  18. 游戏王计算机器人,游戏王:时花之贤者以一换二即可召唤,鲜花机器人可获取抽牌机会...
  19. Linux查看进程 ps aux指令详解
  20. 动森大头菜价格变化分析(1)——不同价格走势的变换

热门文章

  1. 简单的spring mvc实例
  2. 列和相减 L3-L2
  3. P2341 [HAOI2006]受欢迎的牛
  4. WPF Visifire 图表控件
  5. 中国网站备案制度——祸国殃民
  6. 大数据虚拟化零起点-7基础运维第六步-安装Big Data Extensions Plugin
  7. 【珍藏】 2012Android开发热门资料(110个)
  8. linux内核IO模块plug/unplug机制
  9. 漫画:寻找无序数组的第k大元素
  10. C++简介(3)--引用和指针