How to keep the context of a page when you go to another page and go back on Vue
Imagine you’re on page A and this page has an infinite scroll with movies, and when you click on one of the movies, you go to page B. Page B is a page with the details of that movie: rating, comments, actors, actresses, etc. Now you want to go back to page A, and the movies loaded again. You lost where you were. That it’s not a good UX.
I had a similar problem to solve. In my case, I had a list of files, and when I clicked on a file, it would open a special modal that changed the route, removed the list of files, and when I closed this special modal, I had to keep the context of the list of files (including the scroll position). To solve this problem, I could use two approaches: Vuex or vue keep-alive.
Using Vuex to solve this problem, we would have to manually save all the context of all pages that opened the special modal. For us, that solution was neither feasible nor scalable. On the other hand, keep alive saves the component in memory automatically. So, we were afraid of saving all the components that opened the special modal, which could become a performance issue for our users.
I found a way of solving this problem using a hybrid solution between Vuex and Vue keep alive. The idea of that solution was before open the special modal, I would save in Vuex the name of the component that I wanted to save the context, save the route path of this component and save the scroll position.
Given that we saved the page’s information that opened the modal, we could use Vue keep alive to only save the data for that page specifically. Thanks to that, we removed the downside of the two approaches when used alone.
Let’s see the code!
<template> <keep-alive :include="[componentToKeepAlive.name]"> <router-view ref="routerView"></router-view> </keep-alive></template><script> import { mapGetters } from 'vuex';
export default { computed: { ...mapGetters({ componentToKeepAlive: 'global/componentToKeepAlive' }) } }</script>
Here I just needed to access the store to get the component’s name that I wanted to save the context. As you can see, the “:include” is an array, and you can put as many names of components as you want to. In my case, I just wanted to save the last one.
export default [{ path: '', component: MaterialViewer, children: [...], beforeEnter: saveComponentToKeepAlive}]async function saveComponentToKeepAlive(to, from, next) { if (from.name) { const component = { name: _getComponentName(from), path: from.path, scrollY: window.scrollY }; await store.dispatch('global/updateComponentToKeepAlive', component); } next();}
Here I have the routes.js of my special modal. To save the component I wanted to keep, I added logic to the “beforeEnter” guard and held the name, path, and scroll position.
scrollBehaviour: (to, from, savedPosition) => { const currentY = store.state.global.componentToKeepAlive.scrollY || 0; return { x: 0, y currentY }}
At the main app routes.js, I applied the saved position scroll.
That’s it! I hope I could help you somehow.
You can check this article and others on my website: https://www.marinahaack.com/articles/How-to-keep-the-context-of-a-page-when-you-go-to-another-page-and-go-back-on-Vue