📜  keep-alive vuejs 路由器 - Javascript (1)

📅  最后修改于: 2023-12-03 15:02:29.943000             🧑  作者: Mango

保持VueJS路由器的 Keep-Alive

在使用 VueJS 构建 Web 应用程序时,经常会遇到使用路由器在不同页面之间进行导航的情况。但是,每当我们导航回之前查看过的页面时,VueJS 会重新渲染整个页面,这可能会导致页面速度缓慢或卡顿。为了解决这个问题,VueJS 引入了一个称为 Keep-Alive 的功能,它可以缓存组件并在需要时重新激活它们,从而提高了 Web 应用程序的性能。

基本概念

在使用 Keep-Alive 功能时,我们需要了解以下几个基本概念。

包装组件

要使用 Keep-Alive,您需要创建一个包装组件并将它传递给 <keep-alive> 元素。包装组件应该包含需要保持活动的组件。

<template>
  <keep-alive>
    <router-view/>
  </keep-alive>
</template>

在这个例子中,我们将一个空的 <router-view> 元素封装在一个 <keep-alive> 标签中。这将告诉 VueJS 在 <router-view> 中显示的任何组件都应该被缓存。

缓存标识符

为了帮助 Keep-Alive 跟踪哪些组件需要保持活动,每个被包装的组件需要有一个唯一的缓存标识符。缓存标识符可以是字符串或函数。当缓存标识符是字符串时,它将用作组件的唯一键。当缓存标识符是函数时,它将用于计算组件的键。在大多数情况下,我们可以将缓存标识符设置为组件的名称。

export default {
  name: 'MyComponent'
}
<template>
  <div>
    <p>{{message}}</p>
  </div>
</template>
生命周期钩子

在使用 Keep-Alive 时,我们需要在组件的生命周期钩子中添加额外的逻辑。activateddeactivated 钩子将在组件被缓存和从缓存中移除时分别被调用。在这些钩子中,您可以执行一些需要在组件暂停活动时执行的任务,例如释放资源或取消订阅。

export default {
  name: 'MyComponent',
  data () {
    return {
      message: 'Hello, World!'
    }
  },
  activated() {
    console.log('Component activated.')
  },
  deactivated() {
    console.log('Component deactivated.')
  }
}
实例

下面是一个包含两个页面的示例 VueJS 应用程序:首页和关于页面。在首页中,我们将显示一个简单的计数器组件,该计数器组件在每次导航到页面时都会重新渲染。在关于页面中,我们将显示一个花哨的文本特效组件,该组件会在导航回之前查看过的页面时重新渲染。

// Home.vue
<template>
  <div>
    <h1>Home Page</h1>
    <counter />
  </div>
</template>

<script>
import Counter from '@/components/Counter.vue'

export default {
  name: 'Home',
  components: {
    Counter
  }
}
</script>

// About.vue
<template>
  <div>
    <h1>About Page</h1>
    <fancy-text />
  </div>
</template>

<script>
import FancyText from '@/components/FancyText.vue'

export default {
  name: 'About',
  components: {
    FancyText
  }
}
</script>

我们发现,每当我们在首页和关于页面之间切换时,计数器组件和文本特效组件都会重新渲染。这是因为 VueJS 实例在导航到新页面时会丢弃旧的实例并创建一个新实例。

为了解决这个问题,我们可以使用 Keep-Alive 包装 <router-view>,并将缓存标识符设置为每个页面的名称。这将告诉 VueJS 缓存每个页面的实例,以便在导航回该页面时将其重用。

// App.vue
<template>
  <div>
    <nav>
      <router-link to="/">Home</router-link> |
      <router-link to="/about">About</router-link>
    </nav>
    <keep-alive>
      <router-view :key="$route.name"/>
    </keep-alive>
  </div>
</template>

此时,我们会发现当我们从首页导航到关于页面时,计数器组件不再重新渲染,只有文本特效组件被重用。

我们可以在计数器组件和花哨的文本特效组件中添加 activateddeactivated 钩子来执行额外的逻辑。例如,我们可以在计数器组件被暂停活动时重置计数器。

// Counter.vue
<template>
  <div>
    <h2>Counter: {{count}}</h2>
    <button @click="incrementCount">Increment</button>
  </div>
</template>

<script>
export default {
  name: 'Counter',
  data() {
    return {
      count: 0
    }
  },
  methods: {
    incrementCount() {
      this.count++
    }
  },
  activated() {
    console.log('Counter component activated.')
  },
  deactivated() {
    console.log('Counter component deactivated.')
    this.count = 0
  }
}
</script>
// FancyText.vue
<template>
  <div v-html="text"></div>
</template>

<script>
export default {
  name: 'FancyText',
  data() {
    return {
      text: '<span style="font-size: 72px; color: red;">Fancy Text!</span>'
    }
  },
  activated() {
    console.log('FancyText component activated.')
  },
  deactivated() {
    console.log('FancyText component deactivated.')
  }
}
</script>

现在,每当我们从首页导航到关于页面时,计数器组件会被暂停活动,并在导航回首页时重新激活。在计数器组件被缓存时,它的 activateddeactivated 钩子不会被调用。而在花哨的文本特效组件中,我们只是打印了一些日志以演示 activateddeactivated 钩子如何工作。