欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

vue使用keep-alive如何實現(xiàn)多頁簽并支持強(qiáng)制刷新

 更新時間:2022年08月13日 10:25:19   作者:囂張的胖頭魚  
這篇文章主要介紹了vue使用keep-alive如何實現(xiàn)多頁簽并支持強(qiáng)制刷新,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教

使用keep-alive實現(xiàn)多頁簽并支持強(qiáng)制刷新

需求

我司有一款使用Vue構(gòu)建的SPA 后臺管理系統(tǒng),此時客戶提出一個需求。

1:要求支持打開多頁簽

2:多頁簽保留狀態(tài),即切換頁簽的時候不重新刷新內(nèi)容。

3:關(guān)閉某一頁簽之后,重新打開之后,需要進(jìn)行刷新

4:在當(dāng)前頁面可以進(jìn)行強(qiáng)制刷新功能。

如圖示意(左側(cè)箭頭為多頁簽,右側(cè)為強(qiáng)制刷新按鈕,圖是網(wǎng)圖,非本公司后臺管理系統(tǒng)頁面,效果類似)

思路

1:首先編寫Tags(多頁簽)

2:使用Keep-alive包裹 router-view。

3:利用router-view key值變化會導(dǎo)致內(nèi)容刷新來實現(xiàn)頁面強(qiáng)制刷新

已打開菜單組件

Tags(多頁簽)左側(cè)箭頭指出功能

<template>
    <div class="vtag" id="nTabs">
        <div class="overFlowWapper" ref="overFlowWapper">
            <div class="tagItemWapper" ref="tagItemWapper" v-bind:style="{ width:tagsList.length*110+'px',marginLeft:curGo+'px'}">
                <div class="tagItem" v-for="(item,index) in tagsList" v-bind:class="{ active: isActive(item.path) }"
                     @contextmenu="showMenu" @click="goMe(item)" :title="(myRouter[item.name]||item.title)+(item.queryName||'')">
                    <a class="leftx" v-bind:class="{canCloseNot:!item.canClose}">
                        {{(myRouter[item.name]||item.title)+(item.queryName||'')}}
 
                    </a>
                    <a class="rightx" v-if="item.canClose" @click.stop="delTags(index)"><span>×</span></a>
                    <vue-context-menu :contextMenuData="contextMenuData" @delAll="delAll">
                    </vue-context-menu>
                </div>
            </div>
        </div>
        <div class="tagBtn tagleft" @click="tagLeft" v-if="tagsButtonShow">
            <img src="static/img/svg/icon_narrow.svg">
        </div>
        <div class="tagBtn tagRight" @click="tagRight" v-if="tagsButtonShow">
            <img src="static/img/svg/icon_narrow.svg">
        </div>
        <div class="tagBtn tagRefresh" @click="refreshCurrent">
            <img src="static/img/svg/icon_refresh.svg">
        </div>
    </div>
</template>
 
<script>
    import bus from './bus';
    export default {
        data() {
            return {
                contextMenuData: {
                    // the contextmenu name(@1.4.1 updated)
                    menuName: 'demo',
                    // The coordinates of the display(菜單顯示的位置)
                    axis: {
                        x: null,
                        y: null
                    },
                    // Menu options (菜單選項)
                    menulists: [
                        {
                            fnHandler: 'delAll', // Binding events(綁定事件)
                            icoName: 'fa fa-home fa-fw', // icon (icon圖標(biāo) )
                            btnName: '關(guān)閉所有' // The name of the menu option (菜單名稱)
                        },
                    ]
                },
                tagsList: [],//tag集合
                myRouter: {},
                curGo:0,// 當(dāng)前往左走的步伐,往左為正數(shù),往右為負(fù)數(shù)
                tagsButtonShow:false,//是不是應(yīng)該顯示左右側(cè)按鈕
                defaultPage:{
                    path:"",
                    name: "",
                    canClose:false,
                    title:"",
                    keepAlive:true
                }
            }
        },
        methods: {
            //右鍵菜單的使用
            showMenu () {
                event.preventDefault();
                let x = event.clientX;
                let y = event.clientY;
                // Get the current location
                this.contextMenuData.axis = {
                    x, y
                }
            },
            delAll()
            {
                this.tagsList = [];
                this.$router.push('/');
                this.tagsList.push(this.defaultPage);
            },
            //刷新當(dāng)前頁
            refreshCurrent() {
                bus.$emit('keyCurName', 1);
            },
            //按鈕
            tagLeft() {
                this.curGo = 0;
            },
            //按鈕
            tagRight() {
                let owidth = this.$refs.overFlowWapper.offsetWidth;
                let twidth = this.$refs.tagItemWapper.offsetWidth;
                this.curGo =owidth-twidth;
            },
            //切換是不是顯示左右側(cè)按鈕的狀態(tài),規(guī)則:當(dāng)tagItemWapper的寬度大于overFlowWapper時,顯示兩側(cè)按鈕
            tagsButtonShowChange() {
                if(typeof this.$refs.overFlowWapper == "undefined") {
                    this.tagsButtonShow = false;
                    return
                }
                let owidth = this.$refs.overFlowWapper.offsetWidth;
                // let twidth = this.$refs.tagItemWapper.offsetWidth;  這里不能用這個,這里有動畫會延遲
                let twidth = 10 + this.tagsList.length*110;
                if(twidth > owidth + 15) {
                    this.tagsButtonShow = true;
                }
                else {
                    this.tagsButtonShow = false;
                    //測試提出:當(dāng)導(dǎo)航標(biāo)簽數(shù)量較多出現(xiàn)左右滾動條時,向右滾動標(biāo)簽后從右邊依次關(guān)閉標(biāo)簽,當(dāng)空間足夠展示當(dāng)前打開的所有標(biāo)簽時,左側(cè)被遮擋的標(biāo)簽沒有自動展示
                    this.curGo = 0;
                }
            },
            goMe(item)
            {
                this.$router.push(item.path);
            },
            delTags(index)
            {
                //工作看板不可以被關(guān)閉喲
                if(index == 0) {
                    return;
                }
                const delItem = this.tagsList.splice(index, 1)[0];
                const item = this.tagsList[index] ? this.tagsList[index] : this.tagsList[index - 1];
                if (item) {
                    delItem.path === this.$route.fullPath && this.$router.push(item.path);
                }else{
                    this.$router.push('/');
                }
            },
            isActive(path) {
                return path === this.$route.fullPath;
            },
            //根據(jù)路由切換Tags標(biāo)簽
            setTags(route)
            {
                if(this.tagsList.length < 1) {
                    if(this.defaultPage.name == "")
                    {
                        let path = this.$router.options.routes[0].redirect;
                        let children = this.$router.options.routes[1].children;
                        for(let i=0;i<children.length;i++) {
                            let copy_i = children[i];
                            if(copy_i.path == path ) {
                                this.defaultPage.name = copy_i.name;
                                this.defaultPage.path = copy_i.path;
                                this.defaultPage.title = copy_i.meta.title;
                                this.defaultPage.keepAlive = copy_i.meta.keepAlive;
                            }
                        }
                    }
                    this.tagsList.push(this.defaultPage);
                }
                let isExist = false; //是不是已經(jīng)打開了這個標(biāo)簽
                for(let i=0;i<this.tagsList.length;i++) {
                    if(this.tagsList[i].path === route.fullPath) {
                        isExist = true;
                        break;
                    }
                }
                if(!isExist)
                {
                    if(this.tagsList.length>11) {
                        this.tagsList.splice(1,1);
                    }
                    this.tagsList.push({
                        title: (this.myRouter[route.name]||route.meta.title),
                        path: route.fullPath,
                        name: route.matched[1].name,
                        keepAlive:route.meta.keepAlive,
                        canClose:true,
                        //詳情頁 附加名稱
                        queryName: (route.query.name?"-"+route.query.name : "")
                    })
                }
                this.changePosition(route);
            },
            //測試提出:當(dāng)導(dǎo)航標(biāo)簽數(shù)量較多出現(xiàn)左右滾動條時,通過導(dǎo)航菜單打開新標(biāo)簽或激活被隱藏的標(biāo)簽時,沒有自動將導(dǎo)航標(biāo)簽移動到活動標(biāo)簽處
            changePosition(route) {
                let currentPosition = 1;//當(dāng)前位置,從1開始
                for(let i=0;i<this.tagsList.length;i++) {
                    if(this.tagsList[i].name == route.name) {
                        currentPosition = i+1;
                    }
                }
                let currentPositionRight = 110*currentPosition-10;//當(dāng)前標(biāo)簽最右側(cè)的位置
                //如果當(dāng)前標(biāo)簽最右側(cè)的位置超出了邊界,那么讓他拽出來
                if(this.$refs.overFlowWapper) {
                    if(currentPositionRight>this.$refs.overFlowWapper.offsetWidth) {
                        let owidth = this.$refs.overFlowWapper.offsetWidth;
                        let twidth = this.tagsList.length*110;
                        this.curGo =owidth-twidth;
                    }
                }
 
 
            },
        },
        computed: {
 
        },
        watch:{
            $route:{
                immediate:true,
                handler:function(newValue){
                    this.setTags(newValue);
                },
                deep:true
            },
            tagsList:{
                immediate:true,
                handler:function(newValue) {
                    bus.$emit('keepList', this.tagsList);
                    this.tagsButtonShowChange();
                },
            },
            '$store.state.myRouter':{
                immediate:true,
                handler:function(newValue){
                    let myRouter = {};
                    if(newValue != null) {
                        for(let i=0; i<newValue.length; i++) {
                            myRouter[newValue[i].url] = newValue[i].label;
                        }
                    }
                    this.myRouter = myRouter;
                },
                deep:true
            },
        },
        created(){
 
        },
        mounted()
        {
            //當(dāng)頁面分辨率發(fā)生變化時,將curGo 偏移量修改為0
            this.addResizeFunctions({
                type: "const",
                name: "tags",
                callback: ()=>{
                    this.curGo = 0;
                    this.tagsButtonShowChange();
                }
            });
        }
    }
 
</script>

Home頁面

<v-tags></v-tags>  <!--剛才的tags組件-->
            <div class="content">
                <keep-alive :include="myKeepList">
                    <router-view :key="key"> 
                    </router-view>
                </keep-alive>
            </div>
 
export default {
        data(){
            return {
                myKeepList: [""],
                bindKeys:{
                    addEs: "24",
                    addWorkflow: "30",
                    announceIssuerWatching: "45",
                    approvalHistory: "33",
                    approvalTask: "32",
                    bondDetail: "50",
                },
            }
        },
        components:{
            vTags
        },
        computed: {
            key() {
                return this.bindKeys[this.$route.name];
            },
            ...mapState(['routerKey','copyRight'])
        },
        watch:{
            '$route': {
                immediate: true,
                handler: function (val) {//監(jiān)聽路由是否變化
                    this.showFooter = (val.name =="dashboard"?false:true);
                }
            }
        },
        methods: {
        },
        created(){
            // 只有在標(biāo)簽頁列表里的頁面才使用keep-alive,即關(guān)閉標(biāo)簽之后就不保存到內(nèi)存中了。
            bus.$on('keepList', msg => {
                let arr = [];
                for(let i=0;i<msg.length;i++) {
                    let copy_m = msg[i];
                    if(copy_m.keepAlive) {
                        arr.push(copy_m.name);
                    }
                }
                this.myKeepList = arr;
            });
            // 點(diǎn)擊強(qiáng)制刷新按鈕會觸發(fā)這里。
            bus.$on('keyCurName', msg => {
                this.bindKeys[this.$route.name] = new Date().getTime();
            });
        },
        mounted() {
        },
    }

使用keep-alive以后刷新部分?jǐn)?shù)據(jù)如何解決

項目中遇到得問題

描述如下:

上圖頁面使用了keep-alive,所以當(dāng)從其其他頁面跳轉(zhuǎn)到這個頁面得時候不會刷新數(shù)據(jù),因此解決方式為

如下圖所示就可以

上圖中activated和created使用方法一致,在這個方法里重新獲取一下數(shù)據(jù)就好了,我們得業(yè)務(wù)場景是

點(diǎn)擊圖標(biāo)選取地理位置

以上為個人經(jīng)驗,希望能給大家一個參考,也希望大家多多支持腳本之家。

相關(guān)文章

最新評論