Vue对象已更改,但不会重新呈现

时间:2019-05-04 11:05:26

标签: javascript vue.js components render

当我按向右箭头键时,它会更改对象,但不会重新渲染它:

<div class="map">
   <div class="map-page" tabindex="0"  @keyup.arrow-keys="show"  ref="mapPage">
     <template  v-for="mapRow in mapMatrix">
       <div  v-for="cell in mapRow" @click="(cell.view === '1') ? showAlert() : false " v-bind:class="['map-cell',{'cell-active' : cell.active}]">
              {{cell.view}}
       </div>
     </template>
   </div>
<div>

通过按下键(@ keyup.arrow-keys =“ show”)想要更改活动单元格。

show: function (event) {
        if(event.keyCode === 39){
          if (this.selectedCellId !== CELL_NUMBER){
            this.moveRight();
          }
        }
    },
moveRight: function(){
      this.$set(this.mapMatrix[this.selectedRowId][this.selectedCellId],'active',false);
      this.selectedCellId++;
      this.$set(this.mapMatrix[this.selectedRowId][this.selectedCellId],'active',true);
    },

它与静态对象配合得很好:

 mapMatrix: {
        0 : {
            0 : {
                  "view" : "-1",
                  "available" : true,
                  "active": false
            },
            1 : {
                  "view" : "1",
                  "available" : true,
                  "active": false
            },
            2 : {
              "view" : "1",
              "available" : true,
              "active": false
            },

          },
...
}

但不适用于:

fillMatrix: function(){
      var i;
      var g;
      for(i = 0; i <= CELL_NUMBER; i++){
          this.mapMatrix[i] = {};
          for(g = 0; g <= CELL_NUMBER; g++){
            var view = this.setVeiw(g);
            this.mapMatrix[i][g] =
              {
                    "view" : view,
                    "available" : true,
                    "active": false
              };
        }
      }
    }

它可以正确更改对象,但对html渲染无反应。有什么区别?

2 个答案:

答案 0 :(得分:0)

您使用Vue无法正确构建矩阵对象。它可能最终不会做出反应(请参见Change Detection Caveats)。

要么在构建矩阵时使用this.$set,要么先在局部变量中构建然后,最后将其分配给this.mapMatrix,以确保整个对象都是可响应的。

类似这样的东西:

fillMatrix() {
  // This is a fresh new unobserved object
  const mapMatrix = {};

  for (let i = 0; i <= CELL_NUMBER; i++) {
    mapMatrix[i] = {};

    for(let g = 0; g <= CELL_NUMBER; g++) {
      mapMatrix[i][g] = {
        view: this.setView(g),
        available: true,
        active: false,
      };
    }
  }

  // Since the this.mapMatrix property is reactive, Vue will detect this
  // assignment and make the new mapMatrix object reactive
  this.mapMatrix = mapMatrix;
}

答案 1 :(得分:0)

应将对象填充功能更改为更具反应性的方式(如@jcbdrn注释中所示):

fillMatrix: function(){
      var i;
      var g;
      for(i = 0; i <= CELL_NUMBER; i++){
          this.$set(this.mapMatrix,i,{});
          for(g = 0; g <= CELL_NUMBER; g++){
            var view = this.setVeiw(g);
             this.$set(this.mapMatrix[i],g,
               {
                   "view" : view,
                   "available" : true,
                   "active": false
             }
           );

        }
      }
    },

那解决了这个问题。