为了账号安全,请及时绑定邮箱和手机立即绑定

带路由器的可移动Vuetify选项卡

带路由器的可移动Vuetify选项卡

猛跑小猪 2022-09-23 21:25:05

在我的 vue 应用程序中,我有一个包含一些选项卡的页面。我想根据不同的路线更改/显示选项卡。


为此,我用这个答案作为参考。


总的来说,这工作正常!我甚至可以通过在移动设备上滑动来更改选项卡(这要归功于.@changev-tabs-items


但是:单击选项卡标签时,由 加载的组件将安装两次。滑动时,它只安装一次。<router-view>


原因必须与s循环内的存在有关。<router-view><v-tab-item>


如果我把它放在这个环路之外,子组件就会正确安装一次。不幸的是,我不能再使用滑动来更改选项卡,因为内容是分离的。


所以:是否有机会同时具有这两种功能(动态路由内容和可移动性)?


谢谢你们!


维尤:


<template>

 <!-- [...] -->

 <v-tabs centered="centered" grow v-model="activeTab">

    <v-tab v-for="tab of tabs" :key="tab.id" :id="tab.id" :to="tab.route" exact>

      <v-icon>{{ tab.icon }}</v-icon>

    </v-tab>


    <v-tabs-items v-model="activeTab" @change="updateRouter($event)">

      <v-tab-item v-for="tab of tabs" :key="tab.id" :value="resolvePath(tab.route)" class="tab_content">

        <!-- prevent loading multiple route-view instances -->

        <router-view v-if="tab.route === activeTab" />

      </v-tab-item>

    </v-tabs-items>

  </v-tabs>

  <!-- [...] -->

</template>


<script>

data: () => ({

    activeTab: '',

    tabs: [

      {id: 'profile', icon: 'mdi-account', route: '/social/profile'},

      {id: 'friends', icon: 'mdi-account-group', route: '/social/friends'},

      {id: 'settings', icon: 'mdi-cogs', route: '/social/settings'},

    ]

  }),

  methods: {

    updateRouter(tab:string) {

      this.$router.push(tab)

    }

  },

</script>

路由器:


{

    path: "/social",

    component: () => import("../views/Social.vue"),

    meta: {

      requiresAuth: true

    },

    children: [

      {

        path: "profile",

        component: () => import("@/components/social/Profile.vue")

      },

      {

        path: "friends",

        component: () => import("@/components/social/Friendlist.vue")

      },

      {

        path: "settings",

        component: () => import("@/components/social/ProfileSettings.vue")

      }

    ]

  }


查看完整描述

2 回答

?
一只甜甜圈

TA贡献1481条经验 获得超5个赞

这种行为能描述事物的秩序吗?@change更新路径后活动选项卡,单击选项卡更新路线,然后激活选项卡?因此,在选项卡视图更新之前,路由器视图位于下一个视图上,因此它在同一路径上显示两个不同的路由器视图。

要解决此问题,只需更改

<router-view v-if="tab.route === activeTab" />

<router-view v-if="tab.route === $route.fullPath && tab.route === activeTab" />

<router-view v-if="tab.route === $route.path && tab.route === activeTab" />


查看完整回答
反对 回复 5天前
?
元芳怎么了

TA贡献1451条经验 获得超7个赞

我有一个不同的答案要提供。@Estradiaz的答案对我不起作用,因为我的某些选项卡中有子视图,并且从选项卡重定向到该选项卡上的第一个子视图。最终结果是,我有很多情况,其中$route.path 与 tab.route 不匹配,因为 tab.route 是选项卡的路由,而 $route.path 指向该选项卡的一个子级。


我确实找到了一种我认为更好,更普遍适用的替代解决方案。但在我开始讨论之前,我想充分解释一下正在发生的事情。


因为我们使用的是 的 :to 属性,所以我们让路由器处理组件的所有选择和显示。这意味着在基础设施有机会做出反应之前,路由会发生变化。例如,如果我们有2个选项卡,而我显示的是选项卡1,那么显示的是这个(你可以在你的html中看到这个)


<v-tabs-items>

  <v-tab-item><router-view>tab 1 component</router-view></v-tab-item>

  <--- tab 2 commented out --->

</v-tabs-items>

然后,当我们单击选项卡2时,会发生什么:


<v-tabs-items>

  <v-tab-item><router-view>tab 2 component</router-view></v-tab-item>

  <--- tab 2 commented out --->

</v-tabs-items>

然后一段时间过去了,代码开始更新,你过渡到这个:


<v-tabs-items>

  <--- tab 1 commented out --->

  <v-tab-item><router-view>tab 2 component</router-view></v-tab-item>

</v-tabs-items>

但是由于 v-if 已更改,因此我们正在销毁 for 选项卡 1 和新的选项卡 2 组件,结果只有 for 选项卡 2 创建选项卡 2 组件的新实例。


基础结构上似乎没有任何内容可用于知道显示的选项卡和 中的组件不匹配。@Estradiaz的解决方案适用于简单的选项卡组件,但它并不可靠。


我没有试图阻止不匹配的情况,而是通过此解决方案来接受它,并在我们吹走选项卡1时使用保持活动状态的基础结构来“重用”。以下是问题中给出的原始标记的样子:


<template>

 <!-- [...] -->

 <v-tabs centered="centered" grow v-model="activeTab">

    <v-tab v-for="tab of tabs" :key="tab.id" :id="tab.id" :to="tab.route" exact>

      <v-icon>{{ tab.icon }}</v-icon>

    </v-tab>


    <v-tabs-items v-model="activeTab" @change="updateRouter($event)">

      <v-tab-item v-for="tab of tabs" :key="tab.id" :value="resolvePath(tab.route)" class="tab_content">

        <div v-if="tab.route === activeTab">

          <keep-alive>

            <router-view key="1"  />

          </keep-alive>

        </div>

      </v-tab-item>

    </v-tabs-items>

  </v-tabs>

  <!-- [...] -->

</template>

现在,当您单击选项卡2时,将发生以下情况:


<v-tabs-items>

  <v-tab-item><router-view>tab 2 component</router-view></v-tab-item>

  <--- tab 2 commented out --->

</v-tabs-items>

路由器视图现在创建选项卡 2 组件并显示它。一段时间过去了,v-Tab 基础结构更新,标记也发生了变化:


<v-tabs-items>

  <--- tab 1 commented out --->

  <v-tab-item><router-view>tab 2 component</router-view></v-tab-item>

</v-tabs-items>

但是现在,当从dom中删除原始文件时,它不会被删除,而是被缓存。当创建新的组件时,它来自缓存,准备与已经构建的选项卡2组件一起使用。


就我而言,这可以完美地消除正在发生的双重安装。而且它可能更快一些,因为它不必在每次切换时重新创建。


查看完整回答
反对 回复 5天前
  • 2 回答
  • 0 关注
  • 9 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信