Можно ли передать массив в качестве реквизита после mounted()?

#javascript #spring #vue.js #vuejs2 #vuetify.js

#javascript #весна #vue.js #vuejs2 #vuetify.js

Вопрос:

У меня есть приложение, использующее VueJS Vuetify Spring. Я получаю список перемещений с сервера и хочу отобразить список имен в окне навигации. Я создал travelList массив и хочу получить этот список перемещений, прежде drawerElements чем передавать его в панель навигации в качестве реквизита.

Возможно ли это? Мой текущий код не работает — возможно, я сделал что-то не так, может быть, есть другой, лучший и правильный способ.

 <template>
  <v-app>
    <app-bar/>
    <navigation-drawer :links="drawerElements"/>
    <v-main>
      <router-view></router-view>
    </v-main>
  </v-app>
</template>

<script>
import AppBar from "@/views/components/AppBar";
import NavigationDrawer from "@/views/components/NavigationDrawer";
import TravelService from "@/services/travel.service";

export default {
  name: "Home",
  components: {AppBar, NavigationDrawer},
  data() {
    return {
      travelList: [],
      drawerElements: [
        {
          to: '/menu/home',
          icon: 'mdi-view-dashboard',
          text: 'Home',
        },
        {
          icon: 'mdi-book-multiple',
          text: 'Travels',
          subLinks: this.travelList,
        }
      ]
    }
  },
  computed: {
    currentUser() {
      return this.$store.state.auth.user;
    }
  },
  mounted() {
    if (!this.currentUser) {
      this.$router.push('/login');
    }
    this.getTravelList();

  },
  methods: {
    getTravelList() {
      TravelService.getLoggedUserTravels().then(
          response => {
            this.convertTravelToDrawerElements(response.data);
          }
      )
    },
    convertTravelToDrawerElements(response) {
      let travels = [];
      response.forEach(element => {
        let travel = {};
        travel.text = element.name;
        travel.to = '/trip/'   element.id;
        travel.icon = "mdi-menu-right";
        travels.push(travel);
      })
      this.travelList = travels;
    }
  },
}
</script>
<style>

</style>
  

Комментарии:

1. Может быть, попробуйте изменить подссылки к функции: subLinks: function () { return this.travelList }

2. @BrandonPratt к сожалению, это не работает.

3. как насчет использования v-if ?

4. Поскольку drawerElements основано на travelList , сделайте его вычисляемым реквизитом.

5. @bbbbburton спасибо, я использовал второй способ из комментариев Михала Леви. Но я думаю, что ваша идея тоже работает.

Ответ №1:

У вас есть два варианта

  1. Внутри вашего convertTravelToDrawerElements метода push каждый создается travel непосредственно в this.travelList вместо замены его новым массивом
  2. Преобразовать drawerElements из data в вычисляемое свойство
 computed: {
  getDrawerElements() {
    return [
        {
          to: '/menu/home',
          icon: 'mdi-view-dashboard',
          text: 'Home',
        },
        {
          icon: 'mdi-book-multiple',
          text: 'Travels',
          subLinks: this.travelList,
        }
      ]
  }
}
  
 <template>
  <v-app>
    <app-bar/>
    <navigation-drawer :links="getDrawerElements"/>
    <v-main>
      <router-view></router-view>
    </v-main>
  </v-app>
</template>
  

Причина

… ваш код работает не так, как ожидалось, потому data() что функция вызывается только один раз при создании вашего компонента. В это время массив this.travelList пуст. Этот пустой массив (или, лучше сказать, ссылка на массив) присваивается subLinks свойству нового объекта data() , который создает и возвращает функция. Когда вы позже this.travelList заменяете массив новым массивом, операция не влияет на содержимое subLinks свойства, оно по-прежнему содержит ссылку на предыдущий (и полностью пустой) массив….

Комментарии:

1. Второй способ решил мою проблему, спасибо! Прежде чем я задал свой вопрос, я попытался сделать это решение, но оно не работает.

2. Рад, что это помогло. Вы действительно понимаете, почему ваш код работал не так, как ожидалось?

3. Я не знаю, правильно ли я прочитал… Переменные в computed реагируют на изменения и автоматически повторно отображают компоненты, а data нет, поэтому нам нужно использовать watcher?

4. data также исправлено в Vue. Надеюсь, мой обновленный ответ сделает его более понятным. Продолжайте учиться!