đ This post mentions Glitch, which has now shut down. Check my After Glitch page.
Make an animated expanding list/accordion in Vue
I had to do a bit of research to put together all the parts for this feature, so itâs worth writing down for future reference I think! Here is a demo:
Yeah, I used Taco Bell locations again because itâs handy JSON data that I have lying around.
There are two sides to building this feature: the animation, and controlling the child components visibility state.
A summary of what I learned
(âTILâ for the kids)
- You canât animate CSS height. Animate
max-heightinstead and use an arbitrarily large figure for the expanded height - You have to use the Vue
<transition>element and match up the transitionnamewith some CSS classes which implement the animation - A Vue component shouldnât alter parent state but can pass changes up to the parent by emitting a custom event, captured by a handler (at parent level) on the child element. See code samples below:
In the parent:
<!-- Pass in the show/hide status, the site data, and attach event handler for when the child wants to collapse itself -->
<site-details :show="site.show" :site="site" @collapse="toggleShow(site)"></site-details>
In the child component:
<!-- The close button -->
<span class="fr pointer f1" @click="$emit('collapse')">×</span>
For more technical info, I wrote documentation in the README on Glitch
Also
One more gotcha I discovered in this process: Initially the source JSON data didnât have a show property, so I had a snippet in Vueâs mounted event something like this.locations.forEach(s => s['show'] = false) to set the data up. But, when this was in place, nothing would show or hide. I donât know if it was because I used array indexers or because modifying the state object like that makes a mutable copy. Either way, it didnât work. So I had to modify the original JSON and add a show property to every item by hand (that is, with a Notepad++ macro).