Angular2+, animation and css controlling transform of sidebar

Viewed 496

I have a sidebar, that has a menu icon, upon pressing the icon it will shift the sidebar out of view, and resize the width of the main content. But I also want it to automatically shift out of view too when it the browser window width say goes below 500px, and automatically jump out again when above 500px, while still keeping the ability that the user can still open and close the sidebar, how would I do this? I'm open to either doing it all with css classes, all ts-logic or a combination of both, I just don't know how, The code I have is:

<div class="sidenav" [@slideInOut]="menuState">
  <span (click)="toggleMenu()" class="ham-menu"><b>☰</b></span>
</div>

<div [@contentMargin]="contentWidth" class="content">
  content
</div>

With a little styling:

.sidenav {
    background-color: #262a35;
    color: #dbabab;
    width: 200px;
    height: 100vh;
    font-size: 10px;
    padding: 10px;
    position: fixed;
    z-index: 999;
}

.content {
    width: 100vw;
    position: fixed;
    padding-top: 40px;
}

.ham-menu {
    position: fixed;
    color: #262a35;
    font-size: 14px;
    margin-left: 210px;
    cursor: pointer;
}

With the component.ts animations part:

animations: [
    trigger('slideInOut', [
      state('out', style({
        transform: 'translate3d(0px, 0, 0)'
      })),
      state('in', style({
        transform: 'translate3d(-200px, 0, 0)'
      })),
      transition('in => out', animate('400ms ease-in-out')),
      transition('out => in', animate('400ms ease-in-out'))
    ]),
    trigger('contentMargin', [
      state('full', style({
        marginLeft: '210px',
        width: 'calc(100% - 210px)'
      })),
      state('reduced', style({
        marginLeft: '10px',
        width: 'calc(100% - 10px)'
      })),
      transition('reduced => full', animate('400ms ease-in-out')),
      transition('full => reduced', animate('400ms ease-in-out'))
    ]),
  ]

and logic:

menuState = 'out';
contentWidth = 'full';    

toggleMenu() {
  this.menuState = this.menuState === 'out' ? 'in' : 'out';
  this.contentWidth = this.contentWidth === 'full' ? 'reduced' : 'full';
}

And then for the automatic resizing based on screenwidth I tried below, but it didn't work...

@media (max-width: 499.9px) {
  .sidenav {
    transition: 400ms ease-in-out;
    transform: translate3d(-200px, 0, 0);
  }
}

@media (min-width: 500px) {
  .sidenav {
    transition: 400ms ease-in-out;
    transform: translate3d(0px, 0, 0);
  }
}
1 Answers

A simple way to do it would be to use the HostListener decorator of Angular to detect the change of width of the window, and add the logic wanted.

You would only have to add this to your component.ts :

@HostListener('window:resize', ['$event'])
onResize(event) {
    console.log("Width: " + event.target.innerWidth);
    this.windowWidth = event.target.innerWidth;
    if(this.windowWidth<500) {
        this.menuState = 'in';
    } else {
        this.menuState = 'out';
    }
}
Related