vue中的checkbox全選和反選


前幾天有個博客園的朋友問小穎,小穎之前寫的vue2.0在table中實現全選和反選  、Vue.js實現checkbox的全選和反選,為什么他將里面的js復制下來,但是實現不了全選和反選。小穎當時看他給的截圖,也沒太明白,后來手動巧了一下,發現一個疑問,雖然問題是解決了,但是至於為什么小穎還是不太明白,希望有哪位vue大神看到了能幫忙解答一下,嘻嘻,小穎先在這里提前說聲:謝謝啦,嘻嘻。

      我們先來看看第一種實現全選和反選的方法:直接使用   script   標簽調用vue。

復制代碼
    <div id="app">
        <input type="checkbox" v-model='checked' v-on:click='checkedAll'> 全選{{checked}}
        <template v-for="(list,index) in checkboxList">
            <input type="checkbox" v-model='checkList' :value="list.id"> {{list.product_inf}}
        </template>
        {{checkList}}
    </div>
復制代碼
復制代碼
    <script>
    var vm = new Vue({
        el: '#app',
        data: {
            checkboxList: [{
                'id': '1',
                'product_inf': '女士銀手鏈'
            }, {
                'id': '2',
                'product_inf': '女士銀手鐲'
            }, {
                'id': '3',
                'product_inf': '女士銀耳環'
            }],
            checked: false, //全選框
            checkList: []
        },
        methods: {
            checkedAll: function() {
                var _this = this;
                console.log(_this.checkList);
                console.log(_this.checked);
                if (!_this.checked) { //實現反選
                    _this.checkList = [];
                } else { //實現全選
                    _this.checkList = [];
                    this.checkboxList.forEach(function(item, index) {
                        _this.checkList.push(item.id);
                    });
                }
            }
        },
        watch: {
            'checkList': {
                handler: function(val, oldVal) {
                    if (val.length === this.checkboxList.length) {
                        this.checked = true;
                    } else {
                        this.checked = false;
                    }
                },
                deep: true
            }
        },
    })
    </script>
復制代碼

打印結果:

 

 

 

第二種實現方式:在vue腳手架環境中:

復制代碼
  <div class="container">
    <input type="checkbox" v-model='checked' v-on:click='checkedAll'> 全選{{checked}}
    <template v-for="(list,index) in checkboxList">
      <input type="checkbox" v-model='checkList' :value="list.id">{{list.product_inf}}
    </template>
    {{checkList}}
    <button @click="ceshi">ceshi</button>
  </div>
復制代碼
復制代碼
<script>
export default {
  data() {
    return {
      checkboxList: [{
        'id': '1',
        'product_inf': '女士銀手鏈'
      }, {
        'id': '2',
        'product_inf': '女士銀手鐲'
      }, {
        'id': '3',
        'product_inf': '女士銀耳環'
      }],
      checked: false, //全選框
      checkList: []
    }
  },
  methods: {
    ceshi: function() {
      console.log(this.checked)
    },
    checkedAll: function() {
      var _this = this;
      console.log(_this.checkList);
      console.log(_this.checked);
      this.$nextTick(function() {
        // DOM 現在更新了
        console.log(_this.checked);
      });
      if (_this.checked) { //實現反選
        _this.checkList = [];
      } else { //實現全選
        _this.checkList = [];
        _this.checkboxList.forEach(function(item, index) {
          _this.checkList.push(item.id);
        });
      }
    }
  },
  watch: { //深度 watcher
    'checkList': {
      handler: function(val, oldVal) {
        if (val.length === this.checkboxList.length) {
          this.checked = true;
        } else {
          this.checked = false;
        }
      },
      deep: true
    }
  }
}

</script>
復制代碼

 打印結果:

大家看完上面的四張圖有沒有發現一個問題:

同樣是在 click 事件 checkedAll 中執行:   console.log(_this.checked);  但是結果卻不一樣,第一種環境中,在修改數據之后checkedAll事件中的_this.checked立馬就變了,但是在第二種環境中,在修改數據之后checkedAll事件中的_this.checked不會立馬變,而是等到下一次調用時,才發生變化,但是在 click 事件 checkedAll   的this.$nextTick事件中,能將回調延遲到下次 DOM 更新循環之后執行。在修改數據之后立即使用它,然后等待 DOM 更新。

    所以在兩種環境中,判斷全選和反選的條件也不一樣:

第一種

復制代碼
                if (!_this.checked) { //實現反選
                    _this.checkList = [];
                } else { //實現全選
                    _this.checkList = [];
                    this.checkboxList.forEach(function(item, index) {
                        _this.checkList.push(item.id);
                    });
                }
復制代碼

第二種:

復制代碼
      if (_this.checked) { //實現反選
        _this.checkList = [];
      } else { //實現全選
        _this.checkList = [];
        _this.checkboxList.forEach(function(item, index) {
          _this.checkList.push(item.id);
        });
      }
復制代碼

當然也可以將第二種修改為:

復制代碼
    checkedAll: function() {
      var _this = this;
      console.log(_this.checkList);
      this.$nextTick(function() {
        console.log(_this.checked);
        // DOM 現在更新了
        if (!_this.checked) { //實現反選
          _this.checkList = [];
        } else { //實現全選
          _this.checkList = [];
          _this.checkboxList.forEach(function(item, index) {
            _this.checkList.push(item.id);
          });
        }
      });
    }
復制代碼

好啦今天的分享就到這里啦,希望大神們能幫小穎解答這個疑惑呦。。。。嘻嘻。

疑問解決啦,哈哈,原來是版本問題,之前博友給的低版本的,用了最新的版本后發現也要用Vue.nextTick方法

用新版本后,點擊事件:

復制代碼
            checkedAll: function() {
                var _this = this;
                console.log(_this.checkList);
                Vue.nextTick(function() {
                    // DOM 更新了
                    console.log(_this.checked);
                    if (!_this.checked) { //實現反選
                        _this.checkList = [];
                    } else { //實現全選
                        _this.checkList = [];
                        _this.checkboxList.forEach(function(item, index) {
                            _this.checkList.push(item.id);
                        });
                    }
                })
            }
復制代碼

 

本博客文章大多為原創,轉載請請在文章頁面明顯位置給出原文連接,否則保留追究法律責任的權利。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM