programing

Vuex에서 개체의 속성을 업데이트할 때 Getter가 반응하지 않음

sourcetip 2022. 8. 8. 23:08
반응형

Vuex에서 개체의 속성을 업데이트할 때 Getter가 반응하지 않음

응용 프로그램에서 반응성에 대해 몇 가지 문제가 있습니다.

Vuex 스토어에서 'songs' 오브젝트를 포함하는 오브젝트 'songs'를 취급하고 있습니다.여기서 키는 오브젝트의 ID입니다.각 곡 오브젝트에 대해 다양한 속성을 가지고 있으며, 해당 오브젝트는 부울값을 '재생'하고 있습니다.

예.

songs = {
   2: {playing: false},
   7: {playing: true)
}

앱에는 모든 곡에 대해 v-for를 사용하여 곡의 재생 속성을 전환하는 버튼이 있습니다.버튼을 누르면 누른 버튼과 연관된 songid로 전달하여 작성한 액션을 디스패치합니다.

this.$store.dispatch('toggleSongPlaying', {songid: songid})

노래 재생 여부에 따라 적절한 아이콘을 표시하고 싶습니다.

문제의 단순화된 vuex 스토어는 다음과 같이 구성됩니다.

const state = {
  songs: {}
};

const mutations = {
  update_song_playing(state, payload) {
     var songObj = state.songs[payload.songid]
     var playingBool = !songObj.playing
     Vue.set(songObj, 'playing', playingBool)
  }
};

const actions = {
  toggleSongPlaying({ commit }, payload) {
     commit("update_song_playing", payload)
  }
};

const getters = {
  getSongs: state => state.songs
};

설정 기능은 정상적으로 동작하고 있습니다.반응성에 문제가 있습니다.전환 버튼을 눌러도 아이콘은 변경되지 않습니다.그러나 렌더를 트리거하면 아이콘이 변경됩니다.컴포넌트 내에서 다음과 같이 mapGetters를 사용하고 있습니다.

computed: {
    ...mapGetters({
      songs: "getSongs"
    })
}

이 네스트된 오브젝트에서 올바르게 동작하기 위해 필요한 것이 있습니까?

제안해 주셔서 감사합니다!

편집 - 목록 및 아이콘 템플릿 코드

<v-list dense>
   <v-subheader>Songs List</v-subheader>
   <v-list-item-group v-model="activeSong" color="primary">
         <v-list-item
              v-for="(song, songID) in songs"
              :key="songID"
         >
               <v-icon class="mr-3" @click.stop="toggleSongPlaying(songID)">{{song.playing ? 'mdi-pause' : 'mdi-play'}}</v-icon>

                // song details etc...
                <v-list-item-content>
                    <v-list-item-title>
                    </v-list-item-title>
                </v-list-item-content>
                    
          </v-list-item>
   </v-list-item-group>
</v-list>
methods: {
   toggleSongPlaying(songid) {
       this.$store.dispatch('toggleSongPlaying', {songid: songid})
   }
},

EDIT2 에서 작성한 다른 컴포넌트에 songs 객체를 다음과 같은 곡으로 채웁니다.

created() {
    var songid = "12"
    var song = {
        length: ...,
        playing: false,
    }

    var payload = {
        song: song,
        songid: songid
    }

    this.$store.dispatch('addSong', payload)
},

Vuex 내

액션:

addSong({ commit }, payload) {
   commit("add_song", payload);
}

뮤테이터:

add_song(state, payload) {
    state.songs[payload.songid] = payload.song
},

자신의 주에 노래를 할당하는 방법은 반응적이지 않습니다.

오브젝트의 경우

Vue가 속성 추가 또는 삭제를 감지할 수 없음

변경하다add_song치환하는 돌연변이songs새 노래도 포함해서 새 노래도 주 소유지입니다.이것은 대접할 수 있다songs불변의

add_song: (state, { songid, song }) => {
  state.songs = {
    ...state.songs,
    [ songid ]: { ...song } // break any object references, thank me later
  }
},

이제 사용할 필요가 없습니다.Vue.set왜냐하면payload속성이 반응적으로 추가되었습니다.당신의.update_song_playing간단히 말하면 될 수 있다

update_song_playing: (state, { songid }) => {
  const song = state.songs[songid];
  if (song) {
    song.playing = !song.playing;
  }
}

를 사용할 수도 있습니다.Vue.set당신의 안에서add_song하지만 플럭스 기반 스토어가 불변의 데이터에 가장 적합하다고 항상 생각해 왔습니다.

언급URL : https://stackoverflow.com/questions/63785843/getter-not-reactive-when-updating-the-property-of-an-object-in-vuex

반응형