Scroll down to the script below, click on any sentence (including terminal blocks!) to jump to that spot in the video!
With a Subscription, click any sentence in the script to jump to that part of the video!Login Subscribe
Our collapsing sidebar works, but yikes, it looks terrible! We need to fix this! Let's hide the text and links entirely when the sidebar is in its collapsed state.
sidebar.vue. In the template, we want to hide the
<ul> and the
<hr />: basically everything except the button.
In Vue, there are two ways to do this and both of them come in the form of directives. To make this work, I'm going to add a new
<div> to wrap all the elements that we need to hide.
The first directive is
v-if. We can write
!collapsed. So: show this if we are not collapsed. If we go over to our browser, we don't even need to refresh because we're using hot module replacement. And... it works! Much better!
|... lines 3 - 4|
|... lines 7 - 33|
|... lines 35 - 42|
|... lines 45 - 85|
The key thing here, if you inspect the HTML, is that with
v-if, the elements are removed entirely. So if we click the button again, the elements come back, and if we collapse, they're gone!
The other way to hide things is by using
v-show things will look the same. The difference is that, when we click
collapse, the HTML is still there.
v-show just adds
display: none to the element when it needs to. Sneaky!
|... lines 1 - 5|
|... lines 7 - 33|
|... lines 35 - 85|
v-if accomplish the same thing. Which you should use just depends on the situation.
v-show is usually better if you're hiding and showing a lot, like a drop-down menu. That's because
v-show is super fast.
But if what you're hiding isn't shown often or is complex - like a modal -
v-if might be better because Vue won't spend any time even rendering the element until you need it.
Ok! While we're here, I also want to clean things up. Let's refactor our
width away from
style to a proper class. But before we do that, there's one thing I wanted to do earlier that I forgot about. Notice that down here in our styles, we have a single class called
sidebar... and we're applying that to the root element of our template. This is great! But sometimes, as a convention, when you have a class that is applied to the root element of a component, you'll use the generic name
|... line 1|
|:class="[$style.component, 'p-3', 'mb-5']"|
|... line 4|
|... lines 6 - 42|
|... lines 44 - 85|
style, update the class name to match.
|... lines 1 - 71|
|<style lang="scss" module>|
|... lines 73 - 74|
|... lines 76 - 82|
This won't make any difference, it's just a nice standard when you need a class on your outer element.
To remove this
width style, go back down to the style block and, inside
.component add a new class called
|... lines 1 - 78|
|... lines 80 - 81|
|... lines 85 - 90|
|... lines 92 - 93|
If you're not familiar with this syntax, it means that if an element has both the
component and the
collapsed classes, then it will get this width.
Back in the template, delete the
The tricky part here is that we need to conditionally add the
collapsed class to our root element. But... there's not really a good way to do that.
Vue is here again to rescue us! It turns out,
:class has another superhero syntax.
Instead of an array, pass an object where every key in the object will be the class name that you want to add, and the value will be true or false for whether or not you want this class. Since we always want these three classes, we'll say
'p-3': true and
To add the
collapsed class conditionally. I'll use that funny syntax again to say
$style.collapsed, because every time we reference a class within modular CSS, we need to use
$style.. And since we want the
collapsed class to show if the collapsed state is
true, we'll just set it to
|... lines 10 - 46|
|... lines 49 - 93|
Back in the browser, click on
>> Collapse and... perfect! You can see our class hiding and showing in the DOM.
But... there's a slightly better way to accomplish all of this... and it will use one of my favorite features of Vue: computed properties. Let's talk about them next.