亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb

首頁 > 編程 > JavaScript > 正文

從零開始搭建vue移動端項目到上線的步驟

2019-11-19 12:41:41
字體:
來源:轉載
供稿:網友

初始化項目

1、在安裝了node.js的前提下,使用以下命令

npm install --g vue-cli

2、在將要構建項目的目錄下

vue init webpack myproject(項目目錄名稱)

一路回車如下

中間會讓選擇ESLint進行項目代碼風格檢查,為了美觀和效率,可以開起來,vue-router用起來,紅框框中的兩個測試,不要也罷,后面是問要使用哪個進行install依賴包,默認npm好了;然后回車,等待下載依賴;慢的話可以用鏡像。

下載完成之后會看到如下提示:

按照步驟往下走就好了

接下來在瀏覽器里輸入localhost:8080,就可以進入到vue的世界了

只有這些還不夠,這距離一個響應式的app框架還差好多,接下來就正式搭建一個移動端的項目吧。

首先我們來看一下剛構建好的vue的項目結構

可以發現項目中有assets和static兩個文件夾可存放靜態文件,那豈不是沖突了?其實不然,assets中存放的靜態文件是會經過webpack處理的,一般放一些圖片之類的靜態資源,而static則不會收到webpack的影響,調用的時候也是通過絕對路徑調用的,通常用來存放一些第三方的靜態資源庫。

此項目將基于vue-cli的項目目錄進行改造,使其集成vue-router、vuex、axios,而且可以自動適配移動端大小。

在開始寫代碼之前,先說一下ESlint警告和報錯,可以選擇性修改校驗規則,點擊參考修改,也可以使用 /* eslint-disable */ 選擇性忽略校驗

路由(vue-router)

一個項目的路由是一個項目的基礎,我們先從路由開始,在剛一開始初始化項目的時候,vue-router就被引進項目里來了,上面的圖片里在src/router里面放的就是路由配置文件,按照個人習慣我將對上面的目錄結構進行調整,如下

新建page目錄存放主邏輯頁面,components存放公共組件,router統一管理路由

如圖引入新的頁面,路由跳轉可通過this.$router.push('/Home')

路由vue-cli都給封裝的差不多了,倒也沒什么要大改的地方,接下來來看下vuex

vuex(狀態管理模塊)

關于vuex的介紹官網也給了比較詳細的介紹,對其作用不太了解的話可以參考什么是vuex,這里只說怎么集成在項目里面,并且簡單介紹其用法

(1)安裝vuex

npm install vuex --save

(2)配置vuex

根據個人開發習慣,項目中vuex的配置也不相同,不過大體都差不多,也有差別大的地方,比方說官網推薦在actions里寫異步操作改變state狀態,但是我還是比較喜歡將請求數據等異步操作放在store外面操作,在通過commit去改變狀態,具體將會在下面的數據請求模塊的封裝里提到

廢話不多說了,看下面圖片

首先創建了一個狀態的文件夾,用于管理整個狀態;在modules里面分開來寫各個模塊的狀態,如下

/** * home.js * 用于home模塊的狀態管理 */import * as types from '../mutation-type' // 引入定義的方法const home = { state: { number: 1 }, mutations: { [types.SET_NUM](state, num) { // 修改state 可通過mapMutations調用 state.number = num } }, actions: {}, getters: {  // 定義getters,可以通過mapGetters拓展函數調用 number: state => { return state.number } }}export default home // 輸出home模塊

mutation-type定義了一些修改state的方法,如下

在index.js統一輸出,如下

import Vue from 'vue'import Vuex from 'vuex'import home from './modules/home'import createLogger from 'vuex/dist/logger'Vue.use(Vuex)const debug = trueexport default new Vuex.Store({ modules: { home }, plugins: debug ? [createLogger()] : [] // 是否開啟vuex的debug模式})

這里用到了一個vuex的內置插件,如上圖,開啟之后狀態的每次改變都可以在console里面查看修改信息如下圖

這里的index配置好之后就是要在main.js里注冊一下

通過以上幾步設置,就可以在項目里面使用狀態了,這里以home.vue為例,看下面代碼

import {mapMutations, mapGetters, mapState} from 'vuex' // 引入map方法export default { data () { return { num: 0 } }, methods: { ...mapMutations({  // 調用setNum方法 setNum: 'SET_NUM' }), increase() { this.num++ this.setNum(this.num) // 將this.num轉入setNum } }, computed: { // ...mapGetters([  // 通過getters獲取state數據 // 'number' // ]), ...mapState({  // 通過state獲取state數據 number: state => state.home.number }) }

到這里vuex的引入就結束了,下面來繼續看數據請求模塊(axios)

axios(數據請求模塊)

之前vue數據請求模塊用的是vue-resource,官方不推薦,棄之;說下axios的集成步驟,以及需要注意的一些地方

(1)安裝axios和js-cookie

npm install axios --save

(2)配置axios

在src目錄下面新建apiconfig文件夾,用來封裝請求和定義一些關于請求的全局變量;同時創建api文件夾,用來分別聲明各個模塊的請求方法,如下圖

先來看apiconfig里的公共封裝部分;這里會對請求做以下處理

  • 定義一些像請求返回成功的狀態、請求超時時間等常量,
  • 對請求做一次公共的封裝,
  • 對token的存儲和攔截當操作,

下面看代碼

/* eslint-disable */import axios from 'axios'/*** 定義請求常量* TIME_OUT、ERR_OK*/export const TIME_OUT = 1000; // 請求超時時間export const ERR_OK = true; // 請求成功返回狀態,字段和后臺統一export const baseUrl = process.env.BASE_URL // 引入全局url,定義在全局變量process.env中,開發環境為了方便轉發,值為空字符串// 請求超時時間axios.defaults.timeout = TIME_OUT// 封裝請求攔截axios.interceptors.request.use( config => { let token = localStorage.getItem('token') // 獲取token config.headers['Content-Type'] = 'application/json;charset=UTF-8' config.headers['Authorization'] = '' if(token != null){    // 如果token不為null,否則傳token給后臺  config.headers['Authorization'] = token } return config }, error => { return Promise.reject(error) })// 封裝響應攔截,判斷token是否過期axios.interceptors.response.use( response => { let {data} = response if (data.message === 'token failure!') { // 如果后臺返回的錯誤標識為token過期,則重新登錄 localStorage.removeItem('token')  // token過期,移除token // 進行重新登錄操作 } else { return Promise.resolve(response) } }, error => { return Promise.reject(error) })// 封裝post請求export function fetch(requestUrl, params = '') { return axios({ url: requestUrl, method: 'post', data: { 'body': params } })}

以上代碼以post請求為例,對請求進行公共封裝,并且定義了一些常量以供請求使用,另外分別對請求和響應進行了攔截,方便在請求或者數據返回時,對數據進行統一處理,具體在代碼的注釋里都可以看到,下面就以登錄為例,對封裝的請求方法進行調用。

下面來看api模塊部分,以home-api為例,看代碼

/** * 引入fetch、baseUrl * @param params * @returns {*} */import {fetch, baseUrl} from 'config/index'// 登錄接口export function loginUserNo(params) { return fetch(`${baseUrl}/root/login/checkMemberLogin`, params)}

在文件里引入fetch方法和baseUrl,這里為什么可以簡寫成'config/index'呢,需要在'build/webpack.base.conf.js'里添加以下代碼,后面引入api同理

這里export登錄方法loginUserNo之后,就可以在組件里面使用這個登錄方法了,如下代碼

import * as homeApi from 'api/home-api' // 引入apiimport { ERR_OK } from 'config/index' // 引入請求成功狀態// 請求方法login() { let params = { password: '*******', storeNo: '', userName: '*********' } homeApi.loginUserNo(params).then((res) => { let {data} = res if (data.success === ERR_OK) {  // 請求成功操作,存儲token  localStorage.setItem('token', data.value.token) } else { } }).catch(() => { }) }}

在點擊登錄之后執行登錄方法,就可以調用請求方法了,但是這里還有一個問題

關于數據請求,避不開的一個老生常談的問題就是跨域,同樣的上面點擊登錄也會涉及到跨域無法請求的問題,不過好在vue-cli里面已經配置了解決跨域問題的模塊,我們可以在config/index.js里面配置以下要代理的地址,如下圖

將以root開頭的api轉發出去,將地址指向接口地址,這樣就解決了跨域的問題。

到此,vue全家桶的引入及應用就基本完成了,但是到目前為止這個項目還只能進行簡單的路由跳轉、狀態存儲以及數據請求,而我們的目標是一個移動端應用框架,接下來我們還要解決如下幾個問題

  • 移動端適配問題
  • 移動端ui框架的引入
  • 項目組織架構的優化問題

下面我們就先從移動端適配問題入手

項目的適配

因為移動端設備屏幕大小,屏幕比例什么的差別比較大,所以移動端項目的適配問題就顯得尤為重要,這里我們主要使用flexible.js進行適配,關于flexible.js,不懂得話可以點這里,這里我們以最常用的750*1334的尺寸為例

引入flexible.js,在main.js里引入flexible.js文件,可將flexible.js作為靜態文件放在最外層static文件夾里引入,如下圖

使用less作為css預處理器,首先安裝less

(1)安裝less和less-loader

npm install lessless-loader --save-dev

(2)配置less

在build/webpack.base.conf.js 的module.exports.module.rules 里面添加

{ test: //.less$/, loader: 'style-loader!css-loader!less-loader' },

然后在組件里面使用的時候,在style標簽上加上 lang="less",就可以正常的使用less了,這里我們來引入幾個初始化項目的less文件,在src下面創建styles文件夾,放入以下文件

在每個組件里的style標簽里引入index.less和variable.less

<style scoped lang="less">@import "~styles/index.less";@import "~styles/variable.less";.hello{ h1{ color: red; .fs(38); // mixin里數字大小函數 }}</style>

然后上面寫關于像素的樣式的時候,都在mixin.less定義下,就可以實現對所有移動端的適配問題。

移動端頁面切換及切換動畫

此處將切換動畫單獨拿出來說以下,作為移動端一般要實現的需求是,第一級菜單切換不需要轉場動畫,第一級菜單向第二級菜單轉場時需要過渡動畫;針對這一需求提供以下解決方案。

需要用到動畫的話肯定會用到vue的transition,不熟悉的話可以看這里,這里實現動畫的解決方案是判斷要執行路由的方向,如下代碼,在路由配置文件里定義路由的方法

// 需要左方向動畫的路由用this.$router.to('****')Router.prototype.togo = function (path) { this.isleft = true this.isright = false this.push(path)}// 需要右方向動畫的路由用this.$router.goRight('****')Router.prototype.goRight = function (path) { this.isright = true this.isleft = false this.push(path)}// 需要返回按鈕動畫的路由用this.$router.goBack(),返回上一個路由Router.prototype.goBack = function () { this.isright = true this.isleft = false this.go(-1)}// 點擊瀏覽器返回按鈕執行,此時不需要路由回退Router.prototype.togoback = function () { this.isright = true this.isleft = false}

上面在執行路由跳轉的時候,在App.vue里面判斷滑動的方向,來指定動畫的方向,不需要動畫的話,可以直接使用this.$router.push('****'),下面是App.vue里處理的動畫代碼

<template> <div id="app"> <transition :name="transitionName"> <router-view class="Router"></router-view> </transition> </div></template><script>export default { name: 'App', data() { return { transitionName: 'slideleft' } }, watch: { $route() { // 監聽路由變化重新賦值 if (this.$router.isleft) { this.transitionName = 'slideleft' } if (this.$router.isright) { this.transitionName = 'slideright' } } }}</script><style>#app { font-family: 'Avenir', Helvetica, Arial, sans-serif; -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale; text-align: center; color: #2c3e50;}.Router { position: absolute; top: 0; left: 0; right: 0; width: 100%; height: 100%; transition: all .5s ease; -webkit-transition: all .5s ease; -moz-transition: all .5s ease;}.slideleft-enter, .slideright-leave-active { opacity: 0; -webkit-transform: translate(100%, 0); transform: translate(100%, 0);}.slideleft-leave-active,.slideright-enter { opacity: 0; -webkit-transform: translate(-100%, 0); transform: translate(-100%, 0);}</style>

在組件中使用的話則使用

this.$router.goBack() // 返回this.$router.to('****') // 進入到詳情

還有一步,就是監聽點擊瀏覽器返回按鈕,在main.js里寫如下代碼

 window.addEventListener('popstate', function(e) { router.togoback() // router已經在上面import進來}, false)

移動端UI框架選擇

作為移動端項目,上面步驟其實已經算完善了,但是往往會遇到項目工期緊,或者缺少人手的時候,這個時候引入一個移動端的UI就如虎添翼了,不用自己去封裝一些ui組件了,這里使用mint-ui,優點可自行搜索,這里講一下對mint-ui的引入。

(1)安裝mint-ui

npm install mint-ui --save

(2)引入mint-ui

在main.js里引入mint-ui

import Mint from 'mint-ui'import 'mint-ui/lib/style.css' // 引入cssVue.use(Mint) // 全局使用

這樣就可以在整個vue項目里面使用mint-ui的組件了。

打包

打包遇到的一些問題

(1)打包之后在ios上點擊元素會閃出來一個半透明的灰色框,這里需要加一句css做下兼容-webkit-tap-highlight-color:rgba(0,0,0,0); 放入#app的css里

(2)點擊事件右300ms的延遲,可采用fastclick.js解決,參考以下代碼

npm install fastclick --save// 在main.js引入import FastClick from 'fastclick'FastClick.attach(document.body)

打包注意事項

如果將項目打包用于移動端瀏覽器,則直接打包,不需要更改其它的東西,在包之后上傳至服務器,使用nginx做下接口轉發即可

如果想將打包的靜態文件進一步打包成移動端應用,則需要修改以下config/index.js

在config/prod.env.js新增baseUrl

打包成app之后,移動端不會存在跨域問題。

寫在最后

上面項目純屬個人搭建,適用于移動端項目,包括瀏覽器端,微信公眾號以及打包之后的android,ios應用,目前還存在一些不足的地方,不過基本功能可以正常使用,具體的代碼,如有需要可在我的github中下載使用,如果覺得對你有用,請給我點贊,如有修改建議,請提出。

項目地址:https://github.com/MrKaKaluote/vue-mobile.git

以上就是本文的全部內容,希望對大家的學習有所幫助,也希望大家多多支持武林網。

發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb
精品国产一区久久久| 国产又爽又黄的激情精品视频| 欧美视频一二三| 欧美日韩国产一中文字不卡| 久久久在线免费观看| 亚洲精品一区二三区不卡| 亚洲丁香久久久| 亚洲人精选亚洲人成在线| 国产aⅴ夜夜欢一区二区三区| 欧美大码xxxx| 国产精品一香蕉国产线看观看| 日本一欧美一欧美一亚洲视频| 欧美一级电影久久| 亚洲第一福利网站| 97精品一区二区三区| 成人免费激情视频| 久久精品最新地址| 欧美极品美女视频网站在线观看免费| 国产成人久久久精品一区| 日本高清视频精品| 欧美与黑人午夜性猛交久久久| 日韩精品在线视频| 精品久久久国产精品999| 在线视频日本亚洲性| 亚洲第一级黄色片| 国产亚洲精品久久久久久777| 国产精品成人国产乱一区| 成人黄色在线播放| 亚洲最大激情中文字幕| 欧美日韩爱爱视频| 日韩精品免费视频| 岛国视频午夜一区免费在线观看| 福利一区视频在线观看| 亚洲视频自拍偷拍| 午夜精品一区二区三区在线视频| 日本最新高清不卡中文字幕| 亚洲xxx视频| 97精品伊人久久久大香线蕉| 亚洲欧美国内爽妇网| 久久激情视频免费观看| 日韩成人av网址| 亚洲国产精品资源| 日韩欧美国产骚| 成人免费在线视频网站| 久久久久久久久久婷婷| 国产精品高清网站| 亚洲最大av网站| 精品久久久久久久久中文字幕| 中文字幕日韩在线播放| 欧美午夜女人视频在线| 精品调教chinesegay| 欧美另类69精品久久久久9999| 欧美在线亚洲一区| 国内精久久久久久久久久人| 国产精品9999| 欧洲亚洲免费视频| 亚洲精品在线观看www| 日韩av一区二区在线观看| 日本午夜人人精品| 欧美大尺度电影在线观看| 日韩在线免费视频观看| 久久天天躁狠狠躁夜夜躁| 国产91色在线播放| 日韩福利在线播放| 久久精品视频va| 欧美精品生活片| 日韩av影院在线观看| 日韩在线视频观看正片免费网站| 亚洲国产日韩精品在线| 欧美成人免费在线视频| 亚洲电影在线看| 欧美大肥婆大肥bbbbb| 久久久久久久91| 欧美一区二区大胆人体摄影专业网站| 久久综合伊人77777尤物| 日韩欧美综合在线视频| 亚洲女人天堂网| 一区二区三区四区视频| 日日噜噜噜夜夜爽亚洲精品| 国产精品久久久| 亚洲区在线播放| 亚洲人成网在线播放| 日韩av片免费在线观看| 日韩av一区二区在线| 国产成人精品久久久| 亚洲加勒比久久88色综合| 热re99久久精品国产66热| 日韩av网站在线| 亚洲免费成人av电影| 中文.日本.精品| 日本午夜人人精品| 日韩精品视频在线观看网址| 欧洲成人在线视频| 中文字幕亚洲欧美| 欧美一区亚洲一区| 精品国内自产拍在线观看| 黑人巨大精品欧美一区二区一视频| 狠狠干狠狠久久| 亚洲18私人小影院| 精品一区二区三区三区| 亚洲色图35p| 久久精品国产91精品亚洲| 国产美女久久精品香蕉69| 久久久久久久久亚洲| 中文字幕亚洲欧美| 国产精品欧美一区二区| 欧美一性一乱一交一视频| 日韩动漫免费观看电视剧高清| 中文字幕亚洲一区二区三区五十路| 国产精品电影观看| 91久久久久久| 久久影院模特热| 国产精品久久久久久久久久新婚| 91久久嫩草影院一区二区| 欧美一区亚洲一区| 日韩视频在线免费| 91久热免费在线视频| 日韩在线观看网站| 久久久女女女女999久久| 亚洲欧美视频在线| 好吊成人免视频| 日韩免费在线视频| 国内精品久久久久久久久| 午夜伦理精品一区| 另类少妇人与禽zozz0性伦| 国产综合色香蕉精品| 精品久久久久久久久久久久| www.亚洲天堂| 中文字幕精品—区二区| 2019最新中文字幕| 国产精品综合网站| 精品国产一区二区三区久久久| 欧美劲爆第一页| 川上优av一区二区线观看| 萌白酱国产一区二区| 91色精品视频在线| 九九热r在线视频精品| 久热在线中文字幕色999舞| 欧美俄罗斯性视频| 国产精品免费小视频| 国产美女扒开尿口久久久| 亚洲精品白浆高清久久久久久| 国产91免费看片| 粉嫩老牛aⅴ一区二区三区| 色av吧综合网| 欧美精品久久久久| 国产一区二区成人| 国产精品美女久久久免费| 日韩一区av在线| 亚洲美女在线视频| 国产精品自产拍在线观| www.欧美精品一二三区| 亚洲色图狂野欧美| 成人xvideos免费视频| 久久久久国产一区二区三区| 国产成人91久久精品| 亚洲一区二区在线| 亚洲片在线资源| 国产视频一区在线| 日韩国产高清污视频在线观看| 色哟哟亚洲精品一区二区| 日韩精品高清视频| 青青草国产精品一区二区| 九色精品美女在线|