vue的音樂webapp總結

使用fastclick包減少移動端觸動div元素時的3ms延遲

import fastclick from 'fastclick';
fastclick.attach(document.body);

圖片懶加載

//使用vue-lazyload第三方插件
npm i vue-lazyload -s
//main.js
import vueLazyload from 'vue-lazyload'
Vue.use(vueLazyload)

抽離普通組件

在移動端中像banner圖,滑動組件和加載組件等這些基礎組件可以抽離為子組件。利用props和slot將父組件中的數(shù)據(jù)和模板傳遞給子組件。

<div>
<slot><slot>    //子組件中使用slot標簽,可以將父組件中把子組件包裹的標簽傳遞給子組件
<div>

//子組件
<script>
export default{
props:{
data:'',
}
}
</script>
//父組件
<子組件 :data='123'></子組件>  //如此就將父組件的data相對于的傳給了子組件中props的data中。

重復性的數(shù)據(jù)聚合可以另外封裝一個類

//這個類把繁瑣的avatar聚合過程封裝成了類
export default class Singer {
  constructor({id, name}) {
    this.id = id
    this.name = name
    this.avatar = `https://y.gtimg.cn/music/photo_new/T001R300x300M000${id}.jpg?max_age=2592000`
  }
}
//類中的構造函數(shù)需要傳兩個參數(shù)
var singer = new Siner({
name:'123',
id:'123'
})

eslint下的paops的array屬性

其中的default如果設置為[]會報錯,需要()=>[]才不會報錯

es6的sort和map方法

// 3.將字母用sort方法,將title的charcodeat進行比較排序
      ret.sort((a, b) => {
        return a.title.charCodeAt(0) - b.title.charCodeAt(0)
      })
//map方法就是將本數(shù)組進行遍歷修改后賦值給新數(shù)組
shortcutList() {
      return this.data.map((group) => {
        return group.title.substr(0, 1)
      })
    }

dom的attribute方法

是在dom元素中添加和獲取屬性的值,如id type class name等等屬性,也可以自定義屬性名

function getData(el, name, val) {
  const prefix = 'data-'
  name = prefix + name    //自定義屬性名
  if (val) {
    return el.setAttribute(name, val) //在el的dom元素添加設置name屬性值val
  } else {
    return el.getAttribute(name)   //獲取el的dom元素值
  }
}

vue數(shù)據(jù)的響應

在vue的data,props和computed等屬性中創(chuàng)建的變量都會自動創(chuàng)建get,set等方法來監(jiān)聽數(shù)據(jù)的變化,來達到數(shù)據(jù)的響應。如果有些數(shù)據(jù)不需要監(jiān)聽,可以在created屬性中創(chuàng)建。

created(){
this.message={} //這樣就創(chuàng)建了一個message變量,但不會被監(jiān)聽
}

右側導航與主體導航的聯(lián)動

1.首先我們需要實時的檢測滾動到的位置

// 可以使用bscroll插件提供的listenscroll方法監(jiān)聽所處的位置
      if (this.listenScroll) {
        let me = this
        this.scroll.on('scroll', (pos) => {
          me.$emit('scroll', pos)
        })
      }
//使用emit派發(fā)一個事件給父組件,父組件接收
 scroll(pos) {
      this.scrollY = pos.y  //講y位置傳給父組件scrolly值
    },

2.將主體的每個導航的位置保存為數(shù)組

 _calculateHeight() {
      this.listHeight = []
      let height = 0
      this.listHeight.push(height)
      let list = this.$refs.listGroup
      for (let i = 0; i < list.length; i++) {
        height += list[i].clientHeight
        this.listHeight.push(height)
      }
    }

3.使用watch監(jiān)聽滾動的位置跟主體位置數(shù)組的區(qū)間[i,i+1)進行比較,計算出所處的區(qū)間

 watch: {
    data() {
      setTimeout(() => {
        this._calculateHeight()
      }, 20)
    },
//鑒定scrollY的變化
    scrollY(newY) {
      const listHeight = this.listHeight
      // 拉到最頂部的情況
      if (newY > 0) {
        this.currentIndex = 0
      }
      // 在中間部分的情況
      for (let i = 0; i < listHeight.length - 1; i++) {
        let height1 = listHeight[i]
        let height2 = listHeight[i + 1]
        if (!height2 || (-newY >= height1 && -newY < height2)) {
          this.currentIndex = i
          // console.log(this.currentIndex)
          return
        }
      }
      // 最底部
      this.currentIndex = listHeight.length - 2
    }
  }

4.將右側導航進行高亮

//判斷位置,動態(tài)添加current樣式
:class="{'current':index == currentIndex}"

vuex

//vuex的常用配置(index.js,state.js,mutations.js,mutation-type.js,getters.js,actions,js)
//vuex提供了許多語法糖,map系列(mapmutation,mapgetters,map...)

//解構賦值出mapMutation方法,進行存數(shù)據(jù)操作
 import {mapMutations} from 'vuex'
methods:{
其他的方法(singer){
this.setSinger(singer)
},
...mapMutations({ 
  setSinger: 'SET_SINGER'   //對mutations的一個映射
})
//這樣就可以在其他方法中用this.setSinger使用mutation中的SET_SINGER方法
//等同于使用this.$store.commit(SET_SINGER,singer)
}
//解構賦值出mapGetters方法,進行取數(shù)據(jù)操作
import {mapGetters} from 'vuex'
computed:{
...mapGetters([
'singer'     //將getters的singer映射掛載到vue實例中
]),
created(){
console.log(this.singer)    //就可以使用this.singer取到getter中singer的映射了
}
}

promise

//promise的用法,先新建一個promise方法,將異步方法放進里面,resolve出你要的值,這里axios是一個異步方法
function getSongUrl(id) {
  return new Promise((resolve, reject) => {
    axios.get('/song/url?id=' + id).then(res => {
      // console.log(res.data.data[0].url)
      resolve(res.data.data[0].url)
    })
  })
}

//然后,asnyc 一個函數(shù)里面,await上面的函數(shù),url總是獲取不到,是因為在初始化的時候,getSongUrl已經運行完了
export async function createSongs(musicData) {
  return new Song({
    id: musicData.id,
    singer: filterSinger(musicData.ar),
    name: musicData.name,
    album: musicData.al.name,
    duration: musicData.l.size,
    image: musicData.al.picUrl,
    url: await getSongUrl(musicData.id)
  })
}

//這樣就把createSongs方法定義成了一個promise方法,這樣就能取到它的url值,直接調用createSongs,用.then處理promise回來的數(shù)據(jù)
    _normalizeSongs(list) {
      list.forEach(item => {
        // ret.push(createSongs(item).then(data => data))
        createSongs(item).then(data => this.songs.push(data))
      })
    }

自定義prefixStyle根據(jù)瀏覽器添加樣式前綴

let elementStyle = document.createElement('div').style

let vendor = (() => {
  let transformNames = {
    webkit: 'webkitTransform',
    Moz: 'MozTransform',
    O: 'OTransform',
    ms: 'msTransform',
    standard: 'transform'
  }

  for (let key in transformNames) {
    if (elementStyle[transformNames[key]] !== undefined) {
      return key
    }
  }

  return false
})()

export function prefixStyle(style) {
  if (vendor === false) {
    return false
  }

  if (vendor === 'standard') {
    return style
  }

  return vendor + style.charAt(0).toUpperCase() + style.substr(1)
}

//使用自定義prefixStyle
import {prefixStyle} from 'common/js/dom'

const transform = prefixStyle('transform')
const backdrop = prefixStyle('backdrop-filter')

this.$refs.imgheight.style[transform] = `scale(${scale})`

使用create-keyframe-animation插件可以在js使用animation動畫

//導入animation包
import animations from 'create-keyframe-animation'

const animation = {
0:{干嘛干嘛},
60:{干嘛干嘛},
100:{干嘛干嘛}
}
//注冊animation動畫的方法
animations.registerAnimation({
name: 'move',
//動畫樣式
animation,
//基礎設置
presets: {
//持續(xù)時間
duration: 400,
easing: linear   //線性動畫
}
})
//將動畫掛載到dom中
animations.runAnimation(this.$refs.cdWrapper,'move',done)  //第一個參數(shù)是dom,第二個是動畫名,第三個是結束的回調

//在結束的回調記得將動畫銷毀
animations.unregisterAnimation(‘move')

使用三目運算符和computed屬性改變icon的圖標和動態(tài)改變keyframe動畫

字符串補零的方法

// 其中num為你傳的字符串,n為你要補到的位數(shù)
_pad(num, n = 2) {
  let len = num.toString().length 
//其中用while是當n>2時的情況所需,‘0’為你要補的字符串,可在前或后補
while(len < n){
  num = '0' +num
len++
}
return num     //此方法可為前后補字符串用。
}

移動端事件方法

//對于移動端,瀏覽器提供了touchStart,touchMove,touchEnd三個方法
<scroll
@touchStart = 'touchStart'
@touchMove = 'touchMove'
@touchStart = 'touchEnd'
>

//在methods中定義
methods: {
//參數(shù)默認為調用事件的元素
  touchStart(e){
  let x = e.touchs[0].pageX    //e.touches[0],代表點擊的第一個位置,pageX是第一個位置的x坐標
}
......
}
</scroll>

getBoundingClientRect()

getBoundingClientRect用于獲取某個元素相對于視窗的位置集合。集合中有top, right, bottom, left等屬性。


image.png
<!
返回值類型:
 rectObject.top:元素上邊到視窗上邊的距離;

rectObject.right:元素右邊到視窗左邊的距離;

rectObject.bottom:元素下邊到視窗上邊的距離;

rectObject.left:元素左邊到視窗左邊的距離;
!>
//一般是過去一個元素,然后去調用他對于視窗的距離,進行動態(tài)改變樣式
rectObject = object.getBoundingClientRect();
rectObject.left   //這就獲取到元素左邊到視窗左邊的距離

vue中的mixins屬性

<meta charset="utf-8">

minxin其實是一個對象,里面的結構大致跟普通組件的script里面的一樣,有data屬性,鉤子函數(shù)和方法等
混入 (mixins) 是一種分發(fā) Vue 組件中可復用功能的非常靈活的方式。混入對象可以包含任意組件選項。當組件使用混入對象時,所有混入對象的選項將被混入該組件本身的選項。

在實際項目中,可以新建一個js文件,導出一個minxin對象 在引用的組件中引入使用即可
這里例子就簡單的跟官網一樣幫助理解即可

選項合并

當組件和混入對象含有同名選項時,這些選項將以恰當?shù)姆绞交旌稀?/p>

比如,數(shù)據(jù)對象在內部會進行淺合并 (一層屬性深度),在和組件的數(shù)據(jù)發(fā)生沖突時以組件數(shù)據(jù)優(yōu)先。

var mixin = {
  data: function () {
    return {
      message: 'hello',
      foo: 'abc'
    }
  }
}

new Vue({
  mixins: [mixin],
  data: function () {
    return {
      message: 'goodbye',
      bar: 'def'
    }
  },
  created: function () {
    console.log(this.$data)
    // => { message: "goodbye", foo: "abc", bar: "def" }
  }
})

同名鉤子函數(shù)將混合為一個數(shù)組,因此都將被調用。另外,混入對象的鉤子將在組件自身鉤子之前調用。

var mixin = {
  created: function () {
    console.log('混入對象的鉤子被調用')
  }
}

new Vue({
  mixins: [mixin],
  created: function () {
    console.log('組件鉤子被調用')
  }
})

// => "混入對象的鉤子被調用"
// => "組件鉤子被調用"

值為對象的選項,例如 methods, components 和 directives,將被混合為同一個對象。兩個對象鍵名沖突時,取組件對象的鍵值對

var mixin = {
  methods: {
    foo: function () {
      console.log('foo')
    },
    conflicting: function () {
      console.log('from mixin')
    }
  }
}

var vm = new Vue({
  mixins: [mixin],
  methods: {
    bar: function () {
      console.log('bar')
    },
    conflicting: function () {
      console.log('from self')
    }
  }
})

vm.foo() // => "foo"
vm.bar() // => "bar"
vm.conflicting() // => "from self"
最后編輯于
?著作權歸作者所有,轉載或內容合作請聯(lián)系作者
【社區(qū)內容提示】社區(qū)部分內容疑似由AI輔助生成,瀏覽時請結合常識與多方信息審慎甄別。
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發(fā)布,文章內容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

相關閱讀更多精彩內容

  • vue去哪網跟學筆記 記錄學習點滴 1. 初始化項目 1.1 手機顯示配適 minimum-scale=1.0,m...
    noobakong閱讀 2,424評論 0 16
  • Vue 課程學習筆記 基礎部分 方法創(chuàng)建在 method 的大括號里面 可以將 v-on:click 簡寫為 @c...
    ThornFUN閱讀 715評論 0 0
  • 01 今天,春節(jié),又叫“年節(jié)”、“大年”,是中華民族的傳統(tǒng)佳節(jié),春節(jié)是新的開始...
    好時光生活薈閱讀 541評論 0 1
  • 第一次來澳門,感覺到了一個童話城堡里。除了大三巴和媽祖廟好像沒有特別的景點。但這里的每一處都很特別。街上到處鋪滿五...
    熱愛運動的小雨兒閱讀 516評論 0 0
  • 星姐作業(yè)讓我們看我的少女時代,我大概搜一下,是一部臺灣校園青春劇。演員除了特別出演的三位其他均不認識。又是臺灣劇,...
    灰姑的書房閱讀 321評論 0 1

友情鏈接更多精彩內容