ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

vue3进阶学习

2022-08-31 19:04:28  阅读:213  来源: 互联网

标签:axios const 进阶 app router 学习 vue vue3 import


vue3进阶学习

官方网站:https://v3.vuejs.org/

中文文档: https://staging-cn.vuejs.org/guide/introduction.html

目的

  • 加强对vue3的学习
  • 了解vue3在生产环境下需要安装什么插件。

1、Vue3安装

上节我们采用NPM 的方法来学习vue。

这次使用构建工具来构建Vue项目。

现在官方推荐使用 create-vue 来创建基于 Vite 的新项目

1.1、Vite简单了解

官方中文文档:https://cn.vitejs.dev/

官方推荐使用Vite来构建vue项目,这里简单了解一下。

Vite主要功能是用于打包场景的增强功能。

Vite作为一个基于浏览器原生ESM的构建工具,它省略了开发环境的打包过程,利用浏览器去解析imports,在服务端按需编译返回。同时,在开发环境拥有速度快到惊人的模块热更新,且热更新的速度不会随着模块增多而变慢。因此,使用Vite进行开发,至少会比Webpack快10倍左右。

1.2、项目构建

前提条件

  • 已安装 15.0 或更高版本的 Node.js
  • 用Visual Studio Code + Volar 扩展。

1、通过命令来初始化 vue3 项目。

npm init vue@latest

创建项目时,可以根据自己需求去添加组件。

2、启动项目

# 进入刚刚创建项目的目录
cd vue3-demo
# 更新依赖
npm install
# 启动项目
npm run dev

访问 http://127.0.0.1:5173/

1.3、项目结构说明

1、新建目录如下:

打开APP.vue,你会发现Vue 的单文件组件是网页开发中 HTML、CSS 和 JavaScript 三种语言经典组合的自然延伸。<template><script><style> 三个块在同一个文件中封装、组合了组件的视图、逻辑和样式。完整的语法定义可以查阅 SFC 语法说明

1.4、添加登录页面

1、把对应没有用的页面先删除。

2、编写登录页

App.vue

<script setup>
import Login from './views/Login.vue'
</script>
<template>
  <main>
    <Login />
  </main>
</template>

<style scoped>
</style>

创建views文件夹,我们一般会将页面放在views里。

Login.vue

<script setup>
</script>

<template>
    <div class="container">
        <div class="login-wrapper">
            <div class="header">登录</div>
            <div class="form-wrapper">
                <input type="text" name="username" placeholder="账号" class="input-item">
                <input type="password" name="password" placeholder="密码" class="input-item">
                <div class="btn">登录</div>
            </div>
        </div>
    </div>
</template>

<style scoped>
        .container {
            height: 100%;
        }
        .login-wrapper {
            background-image: linear-gradient(to right, #fbc2eb, #a6c1ee);
            width: 358px;
            height: 588px;
            border-radius: 15px;
            padding: 0 50px;
            margin: 0 auto;
        }
        .header {
            font-size: 38px;
            font-weight: bold;
            text-align: center;
            line-height: 200px;
        }
        .input-item {
            display: block;
            width: 100%;
            margin-bottom: 20px;
            border: 0;
            padding: 10px;
            border-bottom: 1px solid rgb(128, 125, 125);
            font-size: 15px;
            outline: none;
        }
        .input-item:placeholder {
            text-transform: uppercase;
        }
        .btn {
            text-align: center;
            padding: 10px;
            width: 100%;
            margin-top: 40px;
            background-image: linear-gradient(to right, #a6c1ee, #fbc2eb);
            color: #fff;
        }
</style>

效果如果下:

1.5、模拟登录成功跳转页面

Vue Router官方文档:https://router.vuejs.org/zh/

1、添加Vue Router依赖

由于页面跳转需要路由(相当于控制你要去哪个页面的控制器)。

# 在项目的根目录下
npm install vue-router@4

2、添加router文件

可以新增routers文件夹,存放router文件,看个人习惯。

添加router文件

import { createRouter, createWebHistory } from 'vue-router'

// 导入路由组件.
import Login from './views/Login.vue'
import UserList from './views/UserList.vue'

// 创建路由实例
export const router = createRouter({
    history: createWebHistory(),
    // 定义路由
    routes: [
        { path: '/', component: Login },
        { path: '/userList', component: UserList }
    ]
})

UserList是用来登录成功后跳转的页面。

<script>
export default {
}
</script>
    
    <template>
    <div>
        <h1>用户管理</h1>
    </div>
</template>
    
<style scoped>
</style>

3、修改main.js

import { createApp } from 'vue'
import App from './App.vue'
import { router } from './router'

// import './assets/main.css'

// createApp(App).mount('#app')

const app = createApp(App)
// 注册路由
app.use(router)
app.mount('#app')

4、修改Login.vue

主要是添加点击事件和路由跳转

export default {
    data() {
        return {
            login: {
                username: '',
                password: ''
            }
        }
    },
    methods: {
        toLogin() {
            // 这里可以判断账号和密码是否为空。
           this.$router.push('/userList')
        }
    }
}

5、修改App.vue

router-view 显示与路由的页面。按创建顺序来,默认显示第一个。

类似html的iframe标签。

6、验证路由是否生效

点击登录,发现url产生变化,也发现页面跳转了,证明路由生效了。

1.6、指令复习

演示一个用户管理功能,用于快速学习vue为目的。

UserList.vue

<script>
export default {
    data(){
        return {
            userForm:{
                name: '',
                age: ''
            },
            userList: [{ name: '小明', age:22 },
                        { name: '大白', age:23 },
                        { name: '张三', age:24 }],
            delIds:[]
        }
    },
    methods:{
        addUser(){
            this.userList.push(this.userForm)
            this.userForm = {
                name: '',
                age: ''
            }
        },
        delUser(){
            let i = 0;
            for (const del of this.delIds.sort()) {
                this.userList.splice(del-i,1);
                i++;
            }
            this.delIds=[]
        }
    }
}
</script>
    
    <template>
    <div>
        <h1>用户管理</h1>
        <form action="">
            <input type="text" placeholder="用户名" v-model="userForm.name" >
            <input type="text" placeholder="年龄" v-model.number="userForm.age" @keyup.enter="addUser">
            <input type="button" value="添加" @click="addUser">
            <input type="button" value="删除" @click="delUser">
        </form>
        <ul>
            <li v-for="(user,index) in userList">
                <input type="checkbox" v-model="delIds" :value="index" />
                姓名:{{user.name}},
                年龄:{{user.age}}
            </li>
        </ul>
    </div>
</template>
    
<style scoped>
</style>

发现页面并不美观,下面我们引用UI组件库。

2、安装 UI 组件库

目前常用于VUE3的几款UI组件库:

适用于VUE3的几款高颜值UI组件库

2.1、安装Element Plus

# 在项目的根目录下
npm install element-plus --save

2.2、项目使用

main.js

import { createApp } from 'vue'
import App from './App.vue'
import { router } from './router'
import ElementPlus from 'element-plus'
import 'element-plus/dist/index.css'

// import './assets/main.css'

// createApp(App).mount('#app')

const app = createApp(App)
// 注册路由
app.use(router)
app.use(ElementPlus)
app.mount('#app')

改造UserList.vue

<script>
export default {
    data(){
        return {
            userForm:{
                name: '',
                age: ''
            },
            userList: [{ name: '小明', age:22 },
                        { name: '大白', age:23 },
                        { name: '张三', age:24 }],
            delIds:[]
        }
    },
    methods:{
        addUser(){
            this.userList.push(this.userForm)
            this.userForm = {
                name: '',
                age: ''
            }
        },
        delUser(){
            let i = 0;
            for (const del of this.delIds.sort()) {
                this.userList.splice(del-i,1);
                i++;
            }
            this.delIds=[]
        }
    }
}
</script>
    
    <template>
    <div>
        <h1>用户管理</h1>
        <form action="">
            <input type="text" placeholder="用户名" v-model="userForm.name" >
            <input type="text" placeholder="年龄" v-model.number="userForm.age" @keyup.enter="addUser">
            <input type="button" value="添加" @click="addUser">
            <input type="button" value="删除" @click="delUser">
        </form>
        <ul>
            <li v-for="(user,index) in userList">
                <input type="checkbox" v-model="delIds" :value="index" />
                姓名:{{user.name}},
                年龄:{{user.age}}
            </li>
        </ul>
    </div>
</template>
    
<style scoped>
</style>

发现比之前好看多了。

3、axios

官网文档:http://www.axios-js.com/zh-cn/docs/vue-axios.html

3.1、axios是什么?

Axios 是一个基于 promise 的 HTTP 库,可以用在浏览器和 node.js 中。

功能与Ajax是一样的。都是请求后端接口获取数据。

3.2、安装axios

# 在项目的根目录下
npm install --save axios vue-axios

请求方法的别名:

为方便使用,官方为所有支持的请求方法提供了别名,可以直接使用别名来发起请求:

axios.request(config)
axios.get(url[, config])
axios.delete(url[, config])
axios.head(url[, config])
axios.post(url[, data[, config]])
axios.put(url[, data[, config]])
axios.patch(url[, data[, config]])

注意:在使用别名方法时, url、method、data 这些属性都不必在配置中指定。

3.3、项目使用

main.js

import { createApp } from 'vue'
import App from './App.vue'
import { router } from './router'
import ElementPlus from 'element-plus'
import 'element-plus/dist/index.css'
import axios from 'axios'
import VueAxios from 'vue-axios'

// import './assets/main.css'

// createApp(App).mount('#app')

const app = createApp(App)
// 注册路由
app.use(router)
app.use(ElementPlus)
app.use(VueAxios, axios)
app.mount('#app')

public添加测试数据userList.json

[
    { "name": "小明", "age": 22 },
    { "name": "大白", "age": 23 },
    { "name": "张三", "age": 24 }
]

改造UserList.vue

<script>
export default {
    created(){
        this.getUserList()
    },
    data(){
        return {
            userForm:{
                name: '',
                age: ''
            },
            userList: [],
            delIds:[]
        }
    },
    methods:{
        getUserList(){
        // 获取public下的test.json文件数据
        this.axios.get('/userList.json')
            .then(res => (
                //console.log(res)
                this.userList = res.data

            ))
            .catch(error => ( // 请求失败处理
                console.log(error)
            ))
        },
        addUser(){
            this.userList.push(this.userForm)
            this.userForm = {
                name: '',
                age: ''
            }
        },
        delUser(val){
            let i = 0;
            for (const del of this.delIds.sort()) {
                this.userList.splice(del-i,1);
                i++;
            }
            this.delIds=[]
        },
        selectObjs(val){
            this.delIds = [];
            for (const it of val) {
                this.delIds.push(this.userList.indexOf(it));
            }
        }
    }
}
</script>
    
    <template>
    <div>
        <h1>用户管理</h1>
        <el-form :model="userForm" :inline="true">
            <el-form-item>
                <el-input placeholder="用户名" v-model="userForm.name"  />
            </el-form-item>
            <el-form-item>
                <el-input placeholder="年龄" v-model.number="userForm.age" @keyup.enter="addUser" />
            </el-form-item>
            <el-form-item>
                <el-button type="primary" @click="addUser">添加</el-button>
                <el-button type="danger" @click="delUser">删除</el-button>
            </el-form-item>
        </el-form>
        <el-table :data="userList" stripe @selection-change="selectObjs">
            <el-table-column type="selection" width="55" />
            <el-table-column prop="name" label="名称" width="180" />
            <el-table-column prop="age" label="年龄" width="180" />
        </el-table>
    </div>
</template>
    
<style scoped>
</style>

4、组合式函数

为什么要使用setup组合?

  • 在 Vue 应用的概念中,“组合式函数”(Composables) 是一个利用 Vue 的组合式 API 来封装和复用有状态逻辑的函数。
  • 有点像把功能封装好之后,其它地方调用即可

鼠标跟踪器示例

<script setup>
import { ref, onMounted, onUnmounted } from 'vue'

const x = ref(0)
const y = ref(0)

function update(event) {
  x.value = event.pageX
  y.value = event.pageY
}

onMounted(() => window.addEventListener('mousemove', update))
onUnmounted(() => window.removeEventListener('mousemove', update))
</script>

<template>Mouse position is at: {{ x }}, {{ y }}</template>

但是,如果我们想在多个组件中复用这个相同的逻辑呢?我们可以把这个逻辑以一个组合式函数的形式提取到外部文件中

// mouse.js
import { ref, onMounted, onUnmounted } from 'vue'

// 按照惯例,组合式函数名以“use”开头
export function useMouse() {
  // 被组合式函数封装和管理的状态
  const x = ref(0)
  const y = ref(0)

  // 组合式函数可以随时更改其状态。
  function update(event) {
    x.value = event.pageX
    y.value = event.pageY
  }

  // 一个组合式函数也可以挂靠在所属组件的生命周期上
  // 来启动和卸载副作用
  onMounted(() => window.addEventListener('mousemove', update))
  onUnmounted(() => window.removeEventListener('mousemove', update))

  // 通过返回值暴露所管理的状态
  return { x, y }
}

下面是它在组件中使用的方式:

<script setup>
import { useMouse } from './mouse.js'

const { x, y } = useMouse()
</script>

<template>Mouse position is at: {{ x }}, {{ y }}</template>

组合式与普通的写法在于:

  • 组合式有setup

  • 组合式不能直接使用生命周期钩子,需要通过import { onMounted } from 'vue'才可以。

5、自定义指令

除了 Vue 内置的一系列指令 (比如 v-modelv-show) 之外。Vue 还允许你注册自定义的指令。

下面是一个自定义指令的例子,当一个 input 元素被 Vue 插入到 DOM 中后,它会被自动聚焦:

const focus = {
  mounted: (el) => el.focus()
}

export default {
  directives: {
    // 在模板中启用 v-focus
    focus
  }
}
<input v-focus />

上面是局部使用,如果我们想全局使用怎么做?

const app = createApp({})

// 使 v-focus 在所有组件中都可用
app.directive('focus', {
  /* ... */
})

6、Router进阶

官方文档:https://router.vuejs.org/

在上面我们只是简单使用Router来进行跳转。

实际上Router的功能很强大。

因为它是控制页面的跳转的,你完全可以在跳转前判断要不要跳转当前页面。

6.1、路由带参数

const routes = [
  // 动态字段以冒号开始
  { path: '/users/:id', component: User },
]

//接收参数
this.$route.params

6.2、嵌套路由

iframe标签里套iframe标签是一样的。

const routes = [
  {
    path: '/user/:id',
    component: User,
    // 请注意,只有子路由具有名称
    children: [{ path: '', name: 'user', component: UserHome }],
  },
]	

6.3、导航守卫

主要用来通过跳转前来处理请求。

使用 router.beforeEach 注册一个全局前置守卫:

const router = createRouter({ ... })

router.beforeEach((to, from) => {
  // to: 即将要进入的目标,
  // from: 当前导航正要离开的路由 
  // ...
  // 返回 false 取消跳转,这里也可以重定向到别的页面。
  return false
  // 将用户重定向到登录页面
  // return { name: 'Login' }
})

6.4、路由元信息

可以自定义一定属性在路由上,例如,某一个路由需要登录后才能访问。

const routes = [
  {
    path: '/posts',
    component: PostsLayout,
    children: [
      {
        path: 'new',
        component: PostsNew,
        // 只有经过身份验证的用户才能创建帖子
        meta: { requiresAuth: true }
      },
      {
        path: ':id',
        component: PostsDetail
        // 任何人都可以阅读文章
        meta: { requiresAuth: false }
      }
    ]
  }
]

例子:判断页面是否要登录才能访问

router.beforeEach((to, from) => {
  if (to.meta.requiresAuth && !auth.isLoggedIn()) {
    // 此路由需要授权,请检查是否已登录
    // 如果没有,则重定向到登录页面
    return {
      path: '/login',
      // 保存我们所在的位置,以便以后再来
      query: { redirect: to.fullPath },
    }
  }
})

7、axios进阶

1、主要对axios进行封装成工具来使用。

import axios from 'axios'
import { MessageBox, Message } from 'element-ui'
import store from '@/store'
import { getToken } from '@/utils/auth'

// create an axios instance
const service = axios.create({
  baseURL: process.env.VUE_APP_BASE_API, // api 的 base_url
  withCredentials: true, // 跨域请求时发送 cookies
  timeout: 5000 // request timeout
})

// request interceptor
service.interceptors.request.use(
  config => {
    // Do something before request is sent
    if (store.getters.token) {
      // 让每个请求携带token-- ['X-Token']为自定义key 请根据实际情况自行修改
      config.headers['X-Token'] = getToken()
    }
    return config
  },
  error => {
    // Do something with request error
    console.log(error) // for debug
    Promise.reject(error)
  }
)

// response interceptor
service.interceptors.response.use(
  /**
   * If you want to get information such as headers or status
   * Please return  response => response
  */
  /**
   * 下面的注释为通过在response里,自定义code来标示请求状态
   * 当code返回如下情况则说明权限有问题,登出并返回到登录页
   * 如想通过 XMLHttpRequest 来状态码标识 逻辑可写在下面error中
   * 以下代码均为样例,请结合自生需求加以修改,若不需要,则可删除
   */
  response => {
    const res = response.data
    if (res.code !== 20000) {
      Message({
        message: res.message,
        type: 'error',
        duration: 5 * 1000
      })
      // 50008:非法的token; 50012:其他客户端登录了;  50014:Token 过期了;
      if (res.code === 50008 || res.code === 50012 || res.code === 50014) {
        // 请自行在引入 MessageBox
        // import { Message, MessageBox } from 'element-ui'
        MessageBox.confirm('你已被登出,可以取消继续留在该页面,或者重新登录', '确定登出', {
          confirmButtonText: '重新登录',
          cancelButtonText: '取消',
          type: 'warning'
        }).then(() => {
          store.dispatch('user/resetToken').then(() => {
            location.reload() // 为了重新实例化vue-router对象 避免bug
          })
        })
      }
      return Promise.reject('error')
    } else {
      return res
    }
  },
  error => {
    console.log('err' + error) // for debug
    Message({
      message: error.message,
      type: 'error',
      duration: 5 * 1000
    })
    return Promise.reject(error)
  }
)

export default service

配置来源:https://github.com/PanJiaChen/vue-element-admin/blob/v4.0.0/src/utils/request.js

使用:

import request from '@/utils/request'

export function getList(query) {
  return request({
    url: '/demo/list',
    method: 'get',
    params: query
  })
}

8、项目发布

# 在项目的根目录下
npm run build

执行完成后,会在 Vue 项目下会生成一个 dist 目录

9、后话

写到这里,日常开发也差不多满足了

如果想更快理解,可以参照一些优秀项目来进行学习。

多练即可。

文章参考:

https://cn.vuejs.org/guide/introduction.html

https://zhuanlan.zhihu.com/p/482851017

https://www.runoob.com/vue3/vue3-tutorial.html

推荐后台管理模板:

https://vvbin.cn/doc-next/

http://blog.lgf196.top/ant-simple-pro-document/

https://gitee.com/codeZyZ_admin/vue3-composition-admin

https://gitee.com/panjiachen/vue-element-admin/tree/master/

标签:axios,const,进阶,app,router,学习,vue,vue3,import
来源: https://www.cnblogs.com/galenblog/p/16644181.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有