一、介紹
通過vue-music-app項目,初步熟悉vue中的數據交互和傳參方式,此項目中使用到了
vuex,vue-router,props,solt傳參方式進行頁面傳參,以及如何設置代理服務器對訪問的ip地址進行管理
,並且使用到了vant按需引入輪播圖組件。
二、傳參方式
1、插槽分發內容
- 定義一個組件,在組件內寫入
<slot></slot>
標簽,當調用組件時,組件中如果有內容,則會替換slot標簽渲染數據。 - 新建一個slider組件:
<template> <!-- TODO:vue通過ref設置dom元素,通過$refs方法獲取此dom節點 --> <div class="slider" ref="slider"> <div class="sliderGroup" ref="sliderGroup"> <slot></slot> </div> </div> </template>
- 新建一個recommend.vue組件,調用slider組件
<template> <div class="recommend"> <h2 class="recommendlist">推薦歌單</h2> <slider> <!-- TODO:使用插槽,通過組件的slot標簽,替換數據 --> <div v-for="item in slider" :key="item.id"> {{ item.songName }} </div> </slider> </div> </template> <script> import slider from "./slider.vue"; export default { data() { return { slider: [] }; }, components: { //調用slider組件 slider }, methods: { getSlider() { //獲取數據存儲在slider數組中 this.$axios.get("http://www.wanandroid.com/tools/mockapi/9664/songlist").then(resp => { if (resp.status == 200) { this.slider = resp.data; } }); }, } </script>

頁面效果.png
2、通過props進行父子組件傳參
- 有些時候,我們定義一個組件,在多個地方調用,而所需展示的數據不同,可以通過props傳參方式對組件進行頁面渲染
- 新建一個Songlist.vue組件
<!-- 不同數據調用此模板 --> <template> <div> <ul> <li class="songli" v-for="item in songList" @click="selectSong(item)"> <div class="songinfor"> <p class="title">{{item.songName}}</p> <p class="singer" style="font-size:12px;color:#888">{{item.singer}}</p> </div> <p class="start"> <img src="../../static/img/start.png"> </p> </li> </ul> </div> </template> <script> export default { props: ["songList"], //通過props接收父組件傳送的數據 }; </script>
- 新建一個recommend.vue,調用子組件SongList
<template> <div class="recommend"> <!-- TODO:動態綁定數據songList數據,子組件通過props接收數據 --> <songList :song-list="songList"></songList> </div> </template> <script> import songList from "./Songlist.vue" export default { data() { return { songList: [] }; }, components: { songList, }, methods: { getSongList() { this.$axios.get("http://www.wanandroid.com/tools/mockapi/9664/recommend").then(resp => { if (resp.status == 200) { this.songList = resp.data; } }); } } }; </script>

頁面效果.png
- 新建一個Hot.vue組件,也調用子組件Songlist
<template> <div id="hot"> <div class="banner"> 熱門歌曲 </div> <!-- 動態綁定數據hotList數據 --> <songList :song-list="hotList"></songList> </div> </template> <script> import songList from "./Songlist.vue" export default { data() { return {hotList: []} }, methods: { getHotList() { this.$axios.get("http://www.wanandroid.com/tools/mockapi/9664/recommend").then(resp => { if (resp.status == 200) { this.hotList = resp.data; } }); } }, mounted() { this.getHotList() }, components: { songList } } </script>

頁面效果.png
3、使用vue-router進行頁面傳參
- 點擊某個菜單項,跳轉到另一個組件頁面時可以使用vue-router進行傳參
-
對路由進行配置
路由配置.png - 在songList組件添加點擊事件跳轉查看詳情頁
<!-- 不同數據調用此模板 --> <template> <div> <ul> <li class="songli" v-for="item in songList" @click="selectSong(item)"> <div class="songinfor"> <p class="title">{{item.songName}}</p> <p class="singer" style="font-size:12px;color:#888">{{item.singer}}</p> </div> <p class="start"> <img src="../../static/img/start.png"> </p> </li> </ul> </div> </template> <script> export default { props: ["songList"], methods: { selectSong(item) { // 直接調用$router.push,實現攜帶參數的跳轉 // this.$router.push({ // "name" : "Detail", //發送跳轉頁面名字 // "params" : {item,item} //TODO: 通過路由的params進行傳參 // }) this.$router.push({ "path": "/detail/:item", "query": {item: JSON.stringify(item)} //TODO: 通過路由的query進行傳參 }) }, } }; </script>
- 新建detail.vue組件,接收頁面傳參
<template> <transition name="slider"> <div class="detail"> <div class="songimg"> <img :src="songDetail.songImgSrc"> </div> <div class="songtitle"> {{songDetail.songName}} </div> <div class="songaudio"> <audio autoplay="autoplay"> <source src="static/song/song.ogg" type="audio/ogg" /> <source src="static/song/song.mp3" type="audio/mpeg" /> </audio> </div> </div> </transition> </template> <script> export default { data() { return { songDetail: {} } }, mounted () { //TODO:parmas傳參不可以刷新,會丟失數據,query可以刷新頁面 // console.log(this.$route.params) //$route接收傳遞的參數 // this.songDetail = this.$route.params.item //TODO: params接收路由傳遞的參數 this.songDetail = JSON.parse(this.$route.query.item); //TODO: query接收路由傳遞的參數 }, } </script>
4、使用vuex進行數據管理
- 使用vuex可以更好的管理數據狀態,使數據得到共享
- 安裝vuex
npm install vuex --save
-
新建store文件夾,同一組織store文件
store文件結構.png
(1) 在main.js引入store
import Vue from 'vue' import App from './App' import router from './router' import axios from 'axios' import store from './store/index' //導入store主文件index Vue.prototype.$axios = axios //將axios添加到vue的原型上,所有vue實例上都可以使用axios Vue.config.productionTip = false new Vue({ el: '#app', store, //添加在vue實例上 router, components: { App }, template: '<App/>' })
(2) 編寫store文件夾
- index.js
import Vue from 'vue' import Vuex from 'vuex' import getters from './getters' import state from './state' import mutations from './mutations' import actions from './action' Vue.use(Vuex) export default new Vuex.Store({ getters, state, mutations, actions })
- state.js //數據管理
const state = { song: {} } export default { state }
- getters.js //管理數據狀態,相當於computed(計算)屬性
const getters={ getSong(state){ return state.song; } } export default getters;
- actions.js //提交數據變化,一把用於異步獲取數據,相當於methods(方法)屬性
import types from './types.js' import axios from 'axios' const actions = { getSongAsync({commit,state}) { axios.get("/recommend/").then(resp => { if (resp.status == 200) { commit(types.GET_SONG, resp.data); //提交突變 } }); } } export default actions;
- mutations.js //改變數據狀態,也就相當於對state數據進行更新
import types from './types' const mutations = { [types.GET_SONG](state,data) { state.song = data console.log(data) } } export default mutations
- types.js //定義方法名常量,管理方法名
const GET_SONG = "GET_SONG" export default { GET_SONG }
(3) 在detail.vue組件調用state中的數據
<script> import { mapGetters, mapActions } from "vuex"; export default { computed: { ...mapGetters(["getSong"]) //此數據可以直接在頁面模板調用 }, created() { this.$store.dispatch("getSongAsync"); //頁面初始化時發送事件 } }; </script>
三、引入Vant
Vant按需引入組件
1、安裝
npm i vant -S
- babel-plugin-import 是一款 babel 插件,它會在編譯過程中將 import 的寫法自動轉換為按需引入的方式
# 安裝 babel-plugin-import 插件 npm i babel-plugin-import -D
// .babelrc 中配置 // 注意:webpack 1 無需設置 libraryDirectory { "plugins": [ ["import", { "libraryName": "vant", "libraryDirectory": "es", "style": true }] ] }
!注意:配置 babel-plugin-import 插件后將不允許導入所有組件
2、新建--src/vant-components.js按需使用swiper組件
import Vue from 'vue' import { Swipe, SwipeItem } from 'vant'; Vue.use(Swipe).use(SwipeItem);
3、在main引入vant-components.js即可在所有頁面使用引入的組件

引入組件.png
4、此時就可以在vue組件中使用vant的swipe組件了

使用組件.png
四、配置代理服務器
編譯打包前要做的事
1、修改文件--config/index.js
- 找到build中
assetsPublicPath
選項進行修改
修改assetsPublicPath選項.png
2、修改文件--config/index.js,進行代理服務器配置
- 找到dev中的
proxyTable
進行代理服務器配置,統一管理接口
proxyTable: { '/song': { //匹配項,放在項目調用中 target: 'http://www.wanandroid.com/tools/mockapi/9664/songlist', // 接口域名 // secure: false, // 如果是https接口,需要配置這個參數 changeOrigin: true, //是否跨域 pathRewrite: { //重寫地址 '^/song': '' //因為接口中沒有這個匹配項,所以要重寫地址,才能正常訪問 } }, }
3、修改文件--build/utils.js
- 找到
ExtractTextPlugin.extract
,添加publicPath
選項
if (options.extract) { return ExtractTextPlugin.extract({ publicPath: '../../', //TODO:css中用到資源時需要加的屬性 use: loaders, fallback: 'vue-style-loader' }) } else { return ['vue-style-loader'].concat(loaders) }
------------------------------------------------------------------------
鏈接:https://www.jianshu.com/p/b54c6127bfc9