Angular: открыть sidenav с другим компонентом, ОШИБКА TypeError: Невозможно прочитать свойство 'toggle' из неопределенного - PullRequest
1 голос
/ 21 апреля 2020

Не могу открыть sidenav из другого компонента Ошибка на изображении, прикрепленном к этому вопросу. действительно, я хотел бы использовать этот стиль sidenav в моем коде:

https://stackblitz.com/angular/lronayrmlye?file=src%2Fapp%2Fsidenav-autosize-example.ts

, но я хочу иметь возможность открывать sidenav из другого компонента

компонент, содержащий кнопку: navigation.component

компонент, содержащий sidenav: layouts.component

sidebar.service.ts

import { Injectable, EventEmitter } from '@angular/core';
import { MatSidenav, MatDrawer } from '@angular/material/sidenav';
import { BehaviorSubject } from 'rxjs';
@Injectable()
export class SidenavService {
 public sideNavToggleSubject: BehaviorSubject<any> = new BehaviorSubject(null);

  constructor() { }   
  private drawer: MatDrawer;

  setDrawer(drawer: MatDrawer) {
      this.drawer = drawer;
  }

  toggle(): void {
      this.drawer.toggle();
  }
}

navigation.component.html 

 <mat-toolbar-row>
<button type="button"  class= "open-sidebar" mat-button (click)="toggled()">
        Toggle sidenav
      </button>

  </mat-toolbar-row>


navigation.component.ts

import { Component, OnInit , ChangeDetectorRef} from '@angular/core';
import { MediaMatcher } from '@angular/cdk/layout';
import { SidenavService } from '../services/sidenav.service';
import { MatSidenav } from '@angular/material/sidenav';

@Component({
  selector: 'app-navigation',
  templateUrl: './navigation.component.html',
  styleUrls: ['./navigation.component.scss']
})
export class NavigationComponent  {
  constructor(

    private sidenavService: SidenavService) { }

    toggled() {
      this.sidenavService.toggle();
  }

}


layouts.component.html



<div>


<div class="mat-typography">
  <app-navigation></app-navigation>
  <router-outlet></router-outlet>
</div>

<mat-drawer-container class="example-container colorred" autosize>

  <mat-drawer #drawer class="example-sidenav" position="end" mode="side">
    <p>Auto-resizing sidenav</p>
    <p *ngIf="showFiller">Lorem, ipsum dolor sit amet consectetur.</p>
    <button (click)="showFiller = !showFiller" mat-raised-button>
      Toggle extra text
    </button>
  </mat-drawer>

</mat-drawer-container>

</div>



layouts.component.ts




import { Component, VERSION as ngv , ViewChild} from '@angular/core';
import {MatSidenavModule,MatDrawer} from '@angular/material/sidenav';
import {SidenavService} from 'src/app/layouts/services/sidenav.service';
@Component({
  selector: 'app-layouts',
  templateUrl: './layouts.component.html',
  styleUrls: ['./layouts.component.scss']
})
export class LayoutsComponent {
  constructor(private sidenavService: SidenavService) {

  }

  @ViewChild('drawer') public drawer: MatDrawer;

  ngOnInit() {
      this.sidenavService.setDrawer(this.drawer);
  }
  showFiller = false;
}

error image

Ответы [ 2 ]

1 голос
/ 26 апреля 2020

В вашем коде все верно, за исключением того, что вы не установили stati c для выдвижного ящика в ViewChild в компоненте макета.

@ ViewChild ('hook', {stati c: true} ) publi c ящик: MatDrawer;

0 голосов
/ 21 апреля 2020

В вашем сервисе вы должны обновить ваш @Injectable декоратор следующим образом:

@Injectable({
  providedIn: 'root'
})

Ошибка, которую вы видите, в основном говорит о том, что сервис не определен в вашем компоненте. Другими словами, это вводится неправильно. Приведенный выше код - это самый простой способ предоставить свой сервис на root (AppModule), чтобы его можно было вводить в ваши компоненты.

...