This article mainly introduces the perfect solution for the vuex method in the parent component to update the state subcomponent that cannot be updated and rendered in time. Friends in need can refer to the following
Scenario:
What I actually use is this. My parent component refers to the child component related. The parent component calls the method to get the page details, updates the state value related, and the child component renders related based on the related. News content, but the subcomponent is always loaded first when the page is opened. The subcomponent has not obtained the updated related value when rendering. Even if the change of the value is watched in the subcomponent, the relevant news of the subcomponent cannot be rendered. content.
My solution:
The parent component passes the value to the child component. When the parent component executes the method of getting page details After that, the state value related is updated and then passed to the subcomponent, which is then rendered and can be obtained normally.
Parent component code:
<template> <p id="newsDetails"> <mt-header title="详情"> <router-link to="/" slot="left"> <mt-button icon="back"></mt-button> </router-link> </mt-header> <p class="details clearfloat"> <h1 class="titleFont"> {{ title }} </h1> <p class="clearfloat sourceWrap"> <ul class="sourceFont"> <li v-if="(pubNews==true)"> <span class="source">{{pubName}}</span> </li> <li> <span class="authorName">{{authorName}}</span> <span class="time">{{createAt|formatTime}}</span> </li> </ul> <span v-if="(pubNews==true)" class='btnFollow' @click="follow">关注</span> </p> <p class="bodyFont clearfloat" id="bodyFont" ref="bodyFont" :class="{bodyHeight:contentStatus}"> <p v-html="content"></p> <p class="editor" v-if="editorName">责任编辑:{{editorName}}</p> </p> <p class="contentToggle" @click="contentStatus=!contentStatus" v-if="contentStatus">阅读全文</p> <Related :related="related"></Related> <!--重点是这里 父组件向子组件传值--> </p> </p> </template> import { Toast } from 'mint-ui'; import {mapState} from 'vuex' import Related from './Related.vue' import moment from 'moment'; export default{ name:"NewsDetails", components:{ Related, }, data(){ return { id:this.$route.params.id, topicType:"news", contentStatus:false, curHeight:0, bodyHeight:5000, hotCommentScrollTop:0 } }, created(){ this.id=this.$route.params.id; this.fetchData(); moment.locale('zh-cn'); }, mounted(){ setTimeout(()=>{ this.contentToggle(); },500) }, watch: { '$route'(to,from){ this.id=this.$route.params.id; this.fetchData(); } }, computed: { ...mapState({ title: state => state.newsDetails.title, authorName: state => state.newsDetails.authorName, pubNews: state => state.newsDetails.pubNews, pubName: state => state.newsDetails.pubName, editorName: state => state.newsDetails.editorName, createAt: state => state.newsDetails.createAt, content: state => state.newsDetails.content, myFavourite: state => state.newsDetails.myFavourite, related: state => state.newsDetails.related, }) }, filters:{ formatTime(time){ return moment(time).fromNow(); }, }, methods:{ fetchData(){ this.$store.dispatch('getDetails',this.id); }, follow(){ Toast('登录后进行关注'); this.$router.push("/login"); }, contentToggle(){ this.curHeight=this.$refs.bodyFont.offsetHeight; if(parseFloat(this.curHeight)>parseFloat(this.bodyHeight)){ this.contentStatus=true; }else{ this.contentStatus=false; } // this.hotCommentScrollTop=this.$refs.hotComment.height; console.log(this.hotCommentScrollTop); }, } }
Child component related.vue
<template> <p v-if="lists.length>0"> <p class="tagTitle"><span>相关新闻</span></p> <p class="listItem" v-if="(item.type=='little')" v-for="(item,index) in lists" :to="{name:'details',params:{id:item.id}}" :key="index" @click="browserDetection()"> <p class="listImg1"> <!--<img :src="{lazy==loaded?item.thumb[0]:lazy==loading?'../../assets/images/little_loading.png':lazy==error?'../../assets/images/little_loading.png'}" alt="" v-lazy="item.thumb[0]">--> <img :src="item.thumb[0]" alt="" v-lazy="item.thumb[0]"> </p> <p class='titleBox1'> <p class="listTitle">{{item.title}}</p> <p class="titleInfo"> <span class="openApp">打开唐人家</span> <span v-if="item.top==true" class="toTop">置顶</span> <!--<svg class="icon" aria-hidden="true"> <use xlink:href="#icon-dianzan" rel="external nofollow" ></use> </svg>--> <span class="like">阅读 {{item.read}}</span> <span class="time">{{item.createAt|formatTime}}</span> </p> </p> </p> </p> </template> <script> import {mapActions, mapState, mapGetters} from 'vuex' import moment from 'moment' export default{ data(){ return { lists: [], id:this.$route.params.id, } }, props:{ related:Array //重点是这里 }, created(){ moment.locale('zh-cn'); }, /*computed: { ...mapState({ related: state => state.newsDetails.related, }) },*/ filters:{ formatTime(time){ return moment(time).fromNow(); }, }, methods:{ }, watch: { related (val) { this.lists = val; }, '$route'(to,from){ this.id=this.$route.params.id } } } </script>
The effect is as shown in the figure:
The above is the entire content of this article, I hope it will be helpful to everyone’s learning For help, please pay attention to the PHP Chinese website for more related content!
Related recommendations:
How vue achieves the effect of forward refresh and backward without refresh
About the implementation of Vue comment framework ( Implementation of parent component)
The above is the detailed content of How to solve the problem that the vuex method in the parent component updates the state and the child component cannot be updated and rendered in time. For more information, please follow other related articles on the PHP Chinese website!