基於mint-ui的移動應用開發案例四(應用中心)

本節主要包括如下內容:javascript

  1. 應用中心界面的佈局
  2. mt-swipe,loadmore,mt-cell,mt-actionsheet等組件的使用
  3. echarts的使用

1.應用中心界面的佈局

頁面的大致結構是一個頭標題,走馬燈的圖片展現區域,和下面的子應用的icon展現。html

<template>
  <div id="tool">
    <!--頭部-->
    <mt-header fixed title="應用中心"></mt-header>
    <!---內容區域-->
    <div class="content">
      <!--圖片輪播展現-->
      <div class="slider-img">
        <mt-swipe :auto="4000">
          <mt-swipe-item>
            <img src="../assets/tool/swipe1.jpg" height="120" width="100%"/>
          </mt-swipe-item>
          <mt-swipe-item><img src="../assets/tool/swipe2.jpg" height="120" width="100%"/></mt-swipe-item>
          <mt-swipe-item><img src="../assets/tool/swipe3.jpg" height="120" width="100%"/></mt-swipe-item>
        </mt-swipe>
      </div>
      <div class="group-title">| - 經常使用應用</div>
      <!--一條分割線-->
      <div class="line"></div>
      <!--應用展現-->
      <div class="apps">
        <div @click="go('chart')">
          <img src="static/chart.png"/>
          <span>業務統計</span>
        </div>
        <div @click="go('loadmore')">
          <img src="static/data.png"/>
          <span>測試數據</span>
        </div>
        <div @click="go('memolist')">
          <img src="static/note.png"/>
          <span>個人備忘</span>
        </div>
      </div>
    </div>
  </div>
</template>
<style scoped>

  .mint-button {
    display: flex;
    flex-direction: column;
  }

  .content {
    margin-top: 40px;
    text-align: left;
  }

  .group-title {
    margin-top: 10px;
    font-size: 11px;
    color: #0c60ee;
  }

  .line {
    margin-top: 10px;
    height: 1px;
    background-color: #c4e3f3;
  }

  .apps {
    display: flex;
    flex-direction: row;
    justify-content: space-around;
    flex-wrap: wrap;
  }

  .apps div {
    display: flex;
    height: 70px;
    width: 70px;
    justify-content: center;
    align-items: center;
  }

  .apps div {
    display: flex;
    flex-direction: column;
  }

  .apps div span {
    margin-top: 5px;
    font-size: 10px;
  }

  .apps img {
    height: 40px;
    width: 40px;
  }

  .slider-img {
    height: 120px;
    width: 100%;
  }
</style>
<script>
  export default {
    methods: {
      go(index){
        this.$router.push('/tool/' + index);
      }
    },
    created(){
      let _footer = this.$store.state.footerVisible;
      if (!_footer) {
        this.$store.commit('TOGGLE_FOOTER');
      }
      this.$store.commit('SELECT_TAB', 'tool')
    }
  }
</script>
這裏採用了flex佈局。

mt-swipe的使用很簡單,就是在裏面加上mt-swipe-item的slot,mt-swipe-item裏面的slot就是展現內容,我這裏是用幾張圖片代替了。在每一個應用icon的div上添加了點擊事件,點擊後會跳入對應的界面。咱們如今要新建三個子應用界面,而且要配置路由。vue

2.子應用1--業務統計---echarts,mt-actionsheet的使用

<template>
  <div id="chart">
    <mt-header fixed title="統計圖表">
      <router-link to="/tool" slot="left">
        <mt-button icon="back">返回</mt-button>
      </router-link>
      <mt-button slot="right" @click="showSheet">切換</mt-button>
    </mt-header>
    <div id="chart-container">
      <div id="myChart" :style="{  height: '300px'}"></div>
    </div>
    <mt-actionsheet
      :actions="actions"
      v-model="sheetVisible">
    </mt-actionsheet>
  </div>
</template>
<style>
  .chart-container {
    margin-top: 40px;
    display: flex;
  }
</style>
<script>

  export default {
    data(){
      let that = this;
      return {
        sheetVisible: false,
        actions: [{
          name: '柱狀圖', method(){
            //在切換圖類型時重畫表格
            that.chartType = 'bar';
            that.drawLine();
          }
        }, {
          name: '折線圖', method(){
            //在切換圖類型時重畫表格
            that.chartType = 'line';
            that.drawLine();
          }
        }],
        chartType: 'bar'
      }
    },
    created(){
      let _footer = this.$store.state.footerVisible;
      if (_footer) {
        this.$store.commit('TOGGLE_FOOTER');
      }
    },
    mounted(){
      this.drawLine();
    },
    methods: {
      showSheet() {
        this.sheetVisible = true
      },
      drawLine(){
        // 基於準備好的dom,初始化echarts實例
        //這裏能用this.$echarts是由於在main.js裏面添加了Vue.prototype.$echarts=echarts
       let myChart = this.$echarts.init(document.getElementById('myChart'));
        // 繪製圖表
        myChart.setOption({
          color: ['#3398DB', '#ef1111'],
          tooltip: {
            trigger: 'axis',
            axisPointer: {            // 座標軸指示器,座標軸觸發有效
              type: 'shadow'        // 默認爲直線,可選爲:'line' | 'shadow'
            }
          },
          //提示塊,可點擊
          legend: {
            x: 'center',
            data: ['第一季度', '第二季度'],
            top: 50,
            selectedMode: 'multiple',
          },
          //X軸
          xAxis: {
            data: ["襯衫", "羊毛衫", "雪紡衫", "褲子"]
          },
          grid: {
            show: true,
            top: 80,//grid 組件離容器上側的距離,默認60;上同
          },
          yAxis: {},
          //顯示數據
          series: [{
            name: '第一季度',
            type: this.chartType,
            data: [5, 20, 9, 360]
          }, {
            name: '第二季度',
            type: this.chartType,
            data: [51, 2, 190, 26]
          }]
        });
      }
    }
  }
</script>
1.actionsheet默認是隱藏的,點擊右上角的切換按鈕時會顯示出來(改變了sheetVisible的可見屬性),它接收一個action屬性,action接收一個對象數組,每一個對象包含一個name屬性顯示名稱和一個method方法用於處理選中相應條目後的回調函數。

2.echarts的顯示分三部分,第一步是要使用一個div塊初始化(init),第二步是設置屬性(setOption),第三步是顯示到界面上(drawLine)。具體的文檔:http://echarts.baidu.com/examples.html#chart-type-bar
java

3.這裏的created鉤子裏是將footerbar給隱藏掉了git

4.注意在函數的回調裏,this指代的已經不是當前vue對象了,使用this來調用vue中的方法時會報錯。若是要在回調中操做vue中的數據或者方法,要在使用回調函數以前將vue本地化,即用一個變量保存this,而後在回調中使用這個變量操做vue的屬性和方法。github

5.頭部標題欄的左側是一個返回按鈕,是利用路由來進行頁面跳轉的。vue-router

3.子應用2--加載數據--loadmore組件的使用

<template>
  <div id="loadmore">
    <mt-header fixed title="load more">
      <router-link to="/tool" slot="left">
        <mt-button icon="back">返回</mt-button>
      </router-link>
    </mt-header>
    <div class="content">
      <mt-loadmore :top-method="loadTop" 
                   :bottom-all-loaded="bottomAllLoaded" 
                   :auto-fill="false"
                   @top-status-change="handleTopChange"
                   :bottom-method="loadBottom" ref="loadmore">

        <div slot="top" class="mint-loadmore-top">
          <span v-show="topStatus === 'loading'" :class="{ 'rotate': topStatus === 'drop' }">↓</span>
          <span v-show="topStatus === 'drop'">我在加載數據</span>
          <span v-show="topStatus === 'pull'">下拉我就更新給你看</span>
        </div>

        <mt-cell v-for="(item,index) in list" :title="item+'s'" :key="index"></mt-cell>
      </mt-loadmore>

    </div>
  </div>
</template>
<style scoped>
  .content {
    margin-top: 40px;
    height: auto;
  }
</style>
<script>
  export default {
    data(){
      return {
        bottomAllLoaded: false,
        topStatus: '',
        list: []
      }
    },
    methods: {
      loadTop(){
        let that = this;
        for (let i = 0; i < 10; i++) {
          this.list.unshift('unshift' + i)
        }
        setTimeout(function () {
          that.$refs.loadmore.onTopLoaded();
        }, 1000)

      },
      loadBottom(){
        for (let i = 0; i < 10; i++) {
          this.list.push('push' + i)
        }
        if (this.list.length > 100) {
          this.bottomAllLoaded = true;
        }
        this.$refs.loadmore.onBottomLoaded();
      },
      handleTopChange(status){
        this.topStatus = status;
      }
    },
    mounted(){
      for (let i = 0; i < 40; i++) {
        this.list.push(i)
      }
    }
  }
</script>

1.loadmore的使用方法能夠參考官方文檔:http://mint-ui.github.io/docs/#/zh-cn2/loadmore。這裏介紹幾個相關的屬性方法。topMethod和bottomMethod分別是下拉刷新和上拉加載更多的回調方法,這裏的距離是默認70px。bottom-all-loaded屬性是在數據徹底記載完成時的一個標記,若是爲true的話,則不會調用加載數據的方法,而且上拉也不會有任何反應。auto-fill屬性是組件會計算初始的數據是否會佔滿整個屏幕,沒有的話會自動調用bottomMethod來填充,我用的時候它是一直在加載的,而後瀏覽器都關不掉。因此我將其設置爲false。另外top-status-change事件是用來監聽頂部欄狀態變化的,有三個值:pull,drop,loading對應三個狀態,在自定義加載動畫時可使用。自定義加載動畫是loadmore組件的一個名爲top的slot插槽,能夠在裏面判斷topStatus來進行不一樣內容的加載。
數組

2.在調用topMethod加載完數據後必定要執行 this.$refs.loadmore.onTopLoaded();,bottomMethod也同樣。瀏覽器

4.子應用3-個人備忘-mt-cell,mt-field,mt-datetime-picker組件使用

這些組件的使用比較簡單,直接看代碼和文檔就能夠了:app

memolist.vue

<template>
  <div id="memo-list">
    <mt-header fixed title="個人備忘列表">
      <router-link to="/tool" slot="left">
        <mt-button icon="back">返回</mt-button>
      </router-link>
      <mt-button slot="right" @click="newMemo">-|-</mt-button>
    </mt-header>
    <div class="content">
      <template v-for="(item,index) in memoList">
        <mt-cell isLink @click.native="showDetail(item)">
          <span slot="title">{{item.title}}</span>
          <span>{{item.content}}</span>
        </mt-cell>
      </template>
    </div>
  </div>
</template>
<style scoped>
  .content {
    margin-top: 40px;
  }

  span {
    font-size: 13px;
    /**設置文字超出元素寬度後的省略號**/
    width: 150px; /*必須設置寬度*/
    overflow: hidden; /*溢出隱藏*/
    text-overflow: ellipsis; /*以省略號...顯示*/
    white-space: nowrap; /*強制不換行*/
  }
</style>
<script>
  import {MessageBox} from 'mint-ui';

  export default {
    created(){
      let _footer = this.$store.state.footerVisible;
      if (_footer) {
        this.$store.commit('TOGGLE_FOOTER');
      }
    },
    methods: {
      newMemo(){
        this.$router.push('/tool/memonew');
      },
      showDetail(item){
        MessageBox(item.title, item.content);
      }
    },
    mounted(){

    },
    data(){
      return {
        memoList: [{
          title: '週報',
          content: '週五以前記得提交週報和周總結週五以前記得提交週報和周總結週五以前記得提交週報和周總結週五以前記得提交週報和周總結週五以前記得提交週報和周總結'
        }, {title: '鍛鍊提醒', content: '晚上記得三俯臥撐'}]
      }
    }
  }
</script>
memonew.vue:

<template>
  <div id="memo">
    <mt-header fixed title="個人備忘">
      <router-link to="/tool/memolist" slot="left">
        <mt-button icon="back">返回</mt-button>
      </router-link>
      <mt-button slot="right" @click="saveMemo">保存</mt-button>
    </mt-header>
    <div class="content">
      <mt-field label="標題" v-model="title"></mt-field>
      <mt-field label="是否提醒">
        <mt-switch v-model="isRemind"></mt-switch>
      </mt-field>
      <mt-cell title="提醒時間" v-show="isRemind">
        <div @click="chooseDatetime">{{dateTimeText}}</div>
      </mt-cell>
      <mt-field class="memo-content" placeholder="備忘錄" type="textarea" rows="8" v-model="content"></mt-field>
      <mt-datetime-picker
        @confirm="confirm"
        ref="picker"
        type="datetime"
        v-model="datetime">
      </mt-datetime-picker>
    </div>
  </div>
</template>
<style scoped>
  .content {
    margin-top: 40px;
  }

  .mint-cell {
    min-height: 40px;
  }

  .memo-content {
    border-bottom: 1px solid #b9def0;
  }
</style>
<script>
  import * as types from '../../store/index.js'

  export default {
    data(){
      return {
        title: '',
        content: '',
        datetime: '',
        dateTimeText: '請選擇提醒時間',
        isRemind: false
      }
    },
    created(){
      let _footer = this.$store.state.footerVisible;
      if (_footer) {
        this.$store.commit('TOGGLE_FOOTER');
      }
    },
    methods: {
      chooseDatetime(){
        this.$refs.picker.open();
      },
      confirm(val){
        this.dateTimeText = val.toLocaleString()
      },
      saveMemo(){
        localStorage.setItem('memo', JSON.stringify({
          title: this.title,
          content: this.content,
          dateTime: this.dateTimeText
        }));
        console.info(localStorage.getItem('memo'))
      }
    }
  }
</script>


1.列表界面的文字超出div區域後顯示省略號的樣式::

/**設置文字超出元素寬度後的省略號**/ width: 150px; /*必須設置寬度*/ overflow: hidden; /*溢出隱藏*/ text-overflow: ellipsis; /*以省略號...顯示*/ white-space: nowrap; /*強制不換行*/  2.備忘列表界面,備忘item的點擊顯示是用MessageBox來實現的,使用以前要記得引入:import {MessageBox} from 'mint-ui' 

3.新建備忘界面,在選中一個日期後的confirm回調中,接收一個val的參數,能夠用toLocaleString()將其轉換成本地的字符串。

4.這裏的saveMemo只是測試,不涉及具體的保存數據功能。


5.路由配置

import Vue from 'vue'
import Router from 'vue-router'
import Main from '../pages/main.vue'
import Tool from '../pages/tool.vue'
import My from '../pages/my.vue'
import MemoNew from '../pages/tool/memonew.vue'
import MemoList from '../pages/tool/memolist.vue'
import Chart from '../pages/tool/chart.vue'
import Loadmore from '../pages/tool/Loadmore.vue'

Vue.use(Router);

export default new Router({
  routes: [
    {
      path: '/main', component: Main
    }, {
      path: '/tool', component: Tool
    }, {
      path: '/my', component: My
    }, {
      path: '/tool/memonew', component: MemoNew
    }, {
      path: '/tool/memolist', component: MemoList
    }, {
      path: '/tool/chart', component: Chart
    },
    {
      path: '/tool/loadmore', component: Loadmore
    }
  ]
})

當前完成的效果演示:


2018-07-12更新:因爲後續增長和改進的東西比較多,強烈建議參考github上最新的項目:
https://github.com/JerryYuanJ/a-vue-app-template
    若是你項目搭建中遇到問題,請提交issue或者及時與我聯繫,謝謝。
相關文章
相關標籤/搜索