1. 程式人生 > 實用技巧 >vue基礎

vue基礎

一、概覽

1、vue 是一套構建使用者介面的漸進式框架
npm安裝命令:cnpm install --global vue-cli
也可以直接把vue.js下載下來在檔案中直接引用;

每個 Vue 應用都需要通過例項化 Vue 來實現:

var vm = new Vue({
  el: '選擇器',
  data:{},
  ...
  methods:{}
});

2、helloworld

<!DOCTYPE html>
<html>
    <head>
        <meta charset="utf-8">
        <
title>helloworld</title> <script src="F://vue.js"></script> </head> <body> <div id="vue_det"> <h1>title1 : {{header1}}</h1> <h1>{{helloworldMethod()}}</h1> </div> <script type
="text/javascript"> var vm = new Vue({ el: '#vue_det', data: { header1: "helloworld !", alexa: "10000" }, methods: { helloworldMethod: function() {
return 'helloworldMethod'; } } }) </script> </body> </html>

data   用於定義屬性,例項中有三個屬性分別為:site、url、alexa。
methods 用於定義的函式,可以通過 return 來返回函式值
computed 用於定義計算屬性,定義同methods,但在呼叫時不用(),可直接以函式名呼叫;計算屬性是基於它們的響應式依賴進行快取的,而methods每次都會計算
watch   監聽屬性,可與v-model聯合使用;

3、響應式
當一個 Vue 例項被建立時,它將 data 物件中的所有的屬性加入到 Vue 的響應式系統中。當這些屬性的值發生改變時,檢視將會產生“響應”,即匹配更新為新的值;後期新增的屬性不具備響應式屬性,同Object.freeze(obj)方法使用後,obj裡的屬性也不具備響應式;

4、基本語法
vue使用了基於 HTML 的模板語法,允許開發者宣告式地將 DOM 繫結至底層 Vue 例項的資料。

 {{變數或方法}}    插入文字值: <p>{{ message }}</p>,通過使用 v-once 指令,你也能執行一次性地插值,當資料改變時,插值處的內容不會更新;<p v-once>{{ message }}</p>;
 v-html      插入html程式碼: <div v-html="message"></div> 
 v-bind      設定屬性,縮寫:":",例: <div v-bind:class="{'class1': message}"   //v-bind:class可縮寫為:class,此處message是可選的,值為true或false,false就不顯示此class1;從 2.6.0 開始,可以用方括號括起來的 JavaScript 表示式作為一個指令的引數,<a v-on:[eventName]="doSomething"> ... </a>
 v-on        監聽DOM事件,縮寫:"@":    <a v-on:click="doSomething">    //v-on:click可縮寫為@click
 v-model     用於input、select、text、checkbox、radio 等表單控制元件元素上建立雙向資料繫結: <p>{{ message }}</p> <input v-model="message">  //寫在input裡的值會同時改變;
 v-if        條件語句:<p v-if="seen">現在你看到我了</p>  #seen為true時顯示內容,否則不顯示;可以使用 v-else 指令來表示 v-if 的“else 塊”;2.1還新增了v-else-if
 v-for       迴圈    <li v-for="message in messages">{{message.id}}</li>  //messages可以為數字,messages也可以為object,用key,value,index同時或單獨來取值,<li v-for="(value, key) in object"></li>
 {{ message | filterA | filterB(1) }}    過濾器,filter為函式,可接受引數,message就是第一個引數,表示先用filterA處理message內容,接著用filterB處理;
    filterA、B在傳參時以filters屬性來定義,例:filters:{filterA:function(agrv0){return 1}, filterB:function(agrv0,a){return a}}

二、修飾符

1、事件修飾符

<!-- 阻止單擊事件冒泡 -->
<a v-on:click.stop="doThis"></a>

<!-- 提交事件不再過載頁面 -->
<form v-on:submit.prevent="onSubmit"></form>

<!-- 修飾符可以串聯  -->
<a v-on:click.stop.prevent="doThat"></a>

<!-- 只有修飾符 -->
<form v-on:submit.prevent></form>

<!-- 新增事件偵聽器時使用事件捕獲模式 -->
<div v-on:click.capture="doThis">...</div>

<!-- 只當事件在該元素本身(而不是子元素)觸發時觸發回撥 -->
<div v-on:click.self="doThat">...</div>

<!-- click 事件只能點選一次,2.1.4版本新增 -->
<a v-on:click.once="doThis"></a>

<!-- 在 "change" 而不是 "input" 事件中更新 -->
<input v-model.lazy="msg" >

<!--將值轉換為數值-->
<input v-model.number="age" type="number">

<!--去掉首尾空格-->
<input v-model.trim="msg">

<!-- 點選事件將只會觸發一次 -->
<a v-on:click.once="doThis"></a>

2、按鍵修飾符

<!-- 只有在 keyCode 是 13 時呼叫 vm.submit() -->
<input v-on:keyup.13="submit">
<!-- 同上 -->
<input v-on:keyup.enter="submit">
<!-- 縮寫語法 -->
<input @keyup.enter="submit">
所有按鍵別名: .enter .tab .delete (捕獲 "刪除" 和 "退格" 鍵) .esc .space .up .down .left .right .ctrl .alt .shift .meta 

三、元件(Component)

1、定義

元件可以擴充套件 HTML 元素,封裝可重用的程式碼。
例:

<div id="app">
    <mycomponent></mycomponent>
</div>
 
<script>
// 註冊
Vue.component('mycomponent', {
  template: '<h1>自定義元件!</h1>'
})
// 建立根例項
new Vue({
  el: '#app'
})
</script>

以上<mycomponent>為全域性可用,也可以在例項Vue時以components屬性來實現區域性屬性

2、prop

prop 是父元件用來傳遞資料的一個自定義屬性
例:

<child message="hello!"></child>
// 註冊
Vue.component('child', {
  // 宣告 props
  props: ['message'],
  // 同樣也可以在 vm 例項中像 "this.message" 這樣使用
  template: '<span>{{ message }}</span>'
})
// 建立根例項
new Vue({
  el: '#app'
})

prop 是一個物件而不是字串陣列時,它可包含驗證要求
例:

props: {
    // 基礎型別檢測 (`null` 意思是任何型別都可以)
    propA: Number,
    // 多種型別
    propB: [String, Number],
    // 必傳且是字串
    propC: {
      type: String,
      required: true
    },
    // 數字,有預設值
    propD: {
      type: Number,
      default: 100
    },
    // 陣列/物件的預設值應當由一個工廠函式返回
    propE: {
      type: Object,
      default: function () {
        return { message: 'hello' }
      }
    },
    // 自定義驗證函式
    propF: {
      validator: function (value) {
        return value > 10
      }
    }
  }
type值有:String Number Boolean Function Object Array  (type 也可以是一個自定義構造器,使用 instanceof 檢測)

3、元件之間通訊

//vue原型鏈掛載匯流排
Vue.prototype.bus = new Vue();

//子元件傳送資料
this.bus.$emit("change",data);

//子元件接收資料
this.bus.$on("change",function(data){
})
自定義事件寫在methonds屬性中

4、slot-scop 插槽(示例)

<!--元件內容-->
<template>
    <!--如果不指定name屬性,則預設為default-->
    <slot name="action" v-bind:row="scope.row"></slot>
</template>
<!--呼叫方式-->
<template v-slot:action="{row}">
    <!--row這裡接收引數處也可以不加花括號,但收到的引數會多包一層object-->
    <el-button size="small" @click="handleEdit2(row)">編輯2</el-button>
</template>

5、自定義指令

// 註冊一個全域性自定義指令 v-focus
Vue.directive('focus', {
  // 當繫結元素插入到 DOM 中。
  inserted: function (el) {
    // 聚焦元素
    el.focus()
  }
})

可以在例項使用 directives屬性 選項來註冊區域性指令,這樣指令只能在這個例項中使用

6、鉤子

類似於TestNG中after,before之類功能的函式;

7、路由:router

Vue.js 路由需要載入 vue-router 庫,路由允許我們通過不同的 URL 訪問不同的內容。
路由傳參 params 與 query兩種方式的區別,query的引數型別於get請求會寫到url上,params方式不會

this.$router.push({ name: 'testCase', params: {interfaceId : val.id}})
this.$router.push({path: 'scyProblemDetailHtml', query: {problemId: row.id}})
<router-link :to="{name: 'scyProblemDetail', params: preParams}">
引數接收:let interfaceId = this.$route.params.interfaceId;

(1)基礎例子

<script src="https://unpkg.com/vue/dist/vue.js"></script>
<script src="https://unpkg.com/vue-router/dist/vue-router.js"></script>

<div id="app">
  <h1>Hello App!</h1>
  <p>
    <!-- 使用 router-link 元件來導航. -->
    <!-- 通過傳入 `to` 屬性指定連結. -->
    <!-- <router-link> 預設會被渲染成一個 `<a>` 標籤 -->
    <router-link to="/foo">Go to Foo</router-link>
    <router-link to="/bar">Go to Bar</router-link>
  </p>
  <!-- 路由出口 -->
  <!-- 路由匹配到的元件將渲染在這裡 -->
  <router-view></router-view>
</div>

// 0. 如果使用模組化機制程式設計,匯入Vue和VueRouter,要呼叫 Vue.use(VueRouter)

// 1. 定義 (路由) 元件。
// 可以從其他檔案 import 進來
const Foo = { template: '<div>foo</div>' }
const Bar = { template: '<div>bar</div>' }

// 2. 定義路由
// 每個路由應該對映一個元件。 其中"component" 可以是
// 通過 Vue.extend() 建立的元件構造器,
const routes = [
  { path: '/foo', component: Foo },
  { path: '/bar', component: Bar }
]

// 3. 建立 router 例項,然後傳 `routes` 配置
const router = new VueRouter({
  routes // (縮寫) 相當於 routes: routes
})

// 4. 建立和掛載根例項。
// 記得要通過 router 配置引數注入路由,
// 從而讓整個應用都有路由功能
const app = new Vue({
  router
}).$mount('#app')

// Home.vue
export default {
  computed: {
    username() {
      // 通過注入路由器,我們可以在任何元件內通過 this.$router 訪問路由器,也可以通過 this.$route 訪問當前路由
      return this.$route.params.username
    }
  },
  methods: {
    goBack() {
      window.history.length > 1 ? this.$router.go(-1) : this.$router.push('/')
    }
  }
}

(2)動態路由

routes: [
    // 動態路徑引數 以冒號開頭
    { path: '/user/:id', component: User } ]
/user/foo 和 /user/bar 都將對映到相同的路由,而且會自動新增一個引數id到this.$route.params,對應的值就是'foo','bar';

模式    匹配路徑    $route.params
/user/:username    /user/evan    { username: 'evan' }
/user/:username/post/:post_id    /user/evan/post/123    { username: 'evan', post_id: '123' }

history
router.replace()    功能和router.push()類似,但它不會向 history 新增新記錄
router.go(n)        在 history 記錄中向前或者後退多少步,正數是向前,負數向後

const router = new VueRouter({
  routes: [
    { path: '/a', redirect: '/b' },   //重定向
    { path: '/a', redirect: { name: 'foo' }},   //重定向
    { path: '/a', redirect: to => {
      // 方法接收 目標路由 作為引數
      // return 重定向的 字串路徑/路徑物件
    }},
    { path: '/a', component: A, alias: '/b' }, //別名
    
  ]
})

四、其他

1、methods內方法呼叫this指向問題;

methods: {
            funA(){
                console.log(this.hello);
            },
            funB(){
                console.log(this.hello);
            },
            funC(that){
                console.log(that.hello);
            },
            fun(){
                //方式一
                this.funA();  
                //方式二
                this.$options.methods.funB.bind(this)();
                //方式三
                var that = this;
                this.$options.methods.funC(that);
            }
        }

2、偵聽watch

  data: {
    question: '',
    answer: 'I cannot give you an answer until you ask a question!'
  },
  watch: {
    // 如果 `question` 發生改變,這個函式就會執行
    question: function (newQuestion, oldQuestion) {
      this.answer = 'Waiting for you to stop typing...'
      this.debouncedGetAnswer()
    }
  }

3、API

相關例項屬性

vm.$data === data // => true
vm.$el === document.getElementById('example') // => true
vm.$props
vm.$options
vm.$parent
vm.$root
vm.$children
vm.$slots
vm.$scopedSlots
vm.$refs
vm.$isServer
vm.$attrs
vm.$listeners