Vue Dynamic组件未重新呈现

时间:2018-11-13 13:01:51

标签: vue.js

我的所有输入字段都有一个基本组件,该组件包装了一个动态组件。

 Intent intent = new Intent(this, MainActivity.class);
        intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
        PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, intent, PendingIntent.FLAG_ONE_SHOT);

        Uri soundUri = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
        NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this,"x")
                .setSmallIcon(R.mipmap.ic_launcher)
                .setContentTitle("your title")
                .setAutoCancel(true)
                .setSound(soundUri)
                .setContentIntent(pendingIntent)
                .setPriority(Notification.PRIORITY_HIGH);

        NotificationManager notificationManager =
                (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);

        notificationManager.notify(0, notificationBuilder.build());

我使用计算属性来填充该组件。

<my-input v-model="book_id" as="select" :options="availableBooks"
            label="Books" :dirty="changed.includes('book_id')"/>

在my-input组件内部,我动态渲染了一个组件/my-input.vue

availableBooks () {
  if(this.books.length === 0) {
    return [{id: '1', text: 'test1'}]
  } else {
    return [{id: '2', text: 'test2'}]
  }
}

然后我有第二个组件选择select-input.vue

<template>
  <div class="live-input" :class="cssClass">
   <component :is="inputType" :state="currentState" :value="value" :errors="errors"
           v-on="$listeners" v-bind="$attrs" class="d-inline-block"/>
  </div>
</template>

props: {
  as: { type: String, default: 'text' },
  label: { type: String },
  hint: { type: String },
  inline: { type: Boolean, default: false },
},

data() {
  return {
    inputType: this.as || TextInput,
    currentDirty: this.dirty,
    selfUpdate: false,
  }
}

首先this.books.length等于零,然后我更新了async并添加了一些条目,当我跟踪availableBooks对象似乎已正确更新但select下拉列表未更新时。

似乎prop属性已经更新,但组件仍未重新呈现。

<template>
   <b-select :value="value" @input="$emit('input', $event)" 
              ref="input" :state="state" :options="optionsForSelect"/>
</template>

props: {
  options: { type: Array },
},

data() {
  const sampleOption = this.options[0]
  const valueMethod = tryProperties(sampleOption, ['value', 'id'])
  const textMethod = tryProperties(sampleOption, 
                       ['text', 'name', 'label', 'toS']
                     )

return {
  localOptions: this.options,
  optionsForSelect: this.options.map(option => {
    if (typeof option === 'string') {
      return { value: option, text: option }
    } else {
      return {value: option[valueMethod], text: option[textMethod]}
    }
  }),
}
},

2 个答案:

答案 0 :(得分:1)

如果您想获取options道具的更新以便在options更改时重新渲染组件,则应该为computed使用optionsForSelect属性data个。使用data时,该值将被复制到组件中,并且仅当data属性在本地更改时才会重新呈现。

如果您使用computed属性,则当父组件更改prop options值时,computed属性将得到重新评估,并且组件将再次呈现。

computed: {
   optionsForSelect() {
       if (typeof option === 'string') {
           return { value: option, text: option }
       } else {
          return {value: option[valueMethod], text: option[textMethod]}
       }
   }
}

computed属性将是我的首选方法。

但是,您也可以使用您拥有的data属性来完成此操作。您将必须为options道具添加观察者,并在每次将道具更新为optionsForSelect数据属性时分配新值。

watch: {
    options: function(newVal, oldVal) {
        // Update this.optionsForSelect value here
   }
}

希望有帮助。

答案 1 :(得分:0)

一旦进入了WATCH功能,您可以使用 this。$ forceUpdate()更新选择输入视图。

watch: {
  options: function(newVal, oldVal) { // [{id: '2', text: 'test2'}]
    // console.log('Prop changed: ', newVal, ' | was: ', oldVal)
    this.$forceUpdate()
  }
}
相关问题