2017-02-04 59 views
0

我有2个独立的组件内的应用程序组件。第一个是工具栏,另一个是sidenav组件。我想要实现的功能和我已经完成的功能(使用reactive x pattern)是当从工具栏中单击按钮时,sidenav在2个状态(从64px到240px宽度,反之亦然)之间切换。2个独立组件之间的通信angularJS 2

我已经在共享服务中使用了一个通用行为主题,以便在单击工具栏按钮时发出数据,并使用sidenav组件内的订阅者来侦听发出的数据。

我的问题是如果有一种方法可以使用另一种方法(如官方文档中所述的@Input或@Output)完成相同的结果,或者反应灵敏的x模式馈送完全满足我的需求?

app.module.ts

@NgModule({ 
declarations: [ 
    AppComponent, 
    DashboardComponent, 
    LoginComponent, 
    FirmsComponent, 
    SidenavComponent, //sidenav component being injected 
    ToolbarComponent // toolbar component being injected 
], 
imports: [ 
    BrowserModule, 
    FormsModule, 
    HttpModule, 
    JsonpModule, 
    AppRoutingModule, 
    MaterialModule.forRoot(), 
    FlexLayoutModule.forRoot() 
], 
bootstrap: [AppComponent] 

}) 
export class AppModule { } 

app.component.html

<div fxLayout="column" fxFill> 
    <toolbar></toolbar> 
    <div fxLayout="row" fxFill> 
     <sidenav></sidenav> 
     <div fxFlex> 
      <router-outlet></router-outlet> 
     </div> 
    </div> 
</div> 

toolbar.component.ts

@Component({ 
selector: 'toolbar', 
templateUrl: './toolbar.component.html', 
}) 

export class ToolbarComponent implements OnInit, OnDestroy{ 
showNavBar: boolean = false; 

constructor(private globalEventsManager: GlobalEventsManager) {} 

ngOnInit(): void { 
    this.initializeToolbar(); 
} 

ngOnDestroy(): void { 
    // this.globalEventsManager.globalEventsEmitter().unsubscribe(); 
} 

initializeToolbar() { 
    this.globalEventsManager.globalEventsEmitter() 
     .filter(params => params.action === 'handleItemVbl') 
     .subscribe(params => { 
      (params !== null) && (this.showNavBar = params.show); 
    }); 
} 
//emit data when button is clicked 
toggleSidenav() { 
    this.globalEventsManager.emitEvent({ action: 'toggleSidenav' }); 
} 
} 

sidenav.component.ts

@Component({ 
selector: 'sidenav', 
templateUrl: './sidenav.component.html', 
}) 
export class SidenavComponent implements OnInit, OnDestroy{ 
showNavBar: boolean = false; 
isHovered: boolean = false; 
toggled: boolean = false; 

constructor(private globalEventsManager: GlobalEventsManager) {} 

ngOnInit(): void { 
    this.initializeSidenav(); 
} 

ngOnDestroy() { 
    // this.globalEventsManager.globalEventsEmitter().unsubscribe(); 
} 

initializeSidenav() { 
    this.globalEventsManager.globalEventsEmitter() 
      .filter(params => params.action === 'handleItemVbl') 
      .subscribe(params => { 
       (params !== null) && (this.showNavBar = params.show); 

    }); 
    //sidenav component is listening for data emittions 
    this.globalEventsManager.globalEventsEmitter() 
     .filter(params => params.action === 'toggleSidenav') 
     .subscribe(params => { 
      if (params !== null) !this.toggled ? this.toggled = true : this.toggled = false; 
    }); 
} 

onHover() { 
    this.isHovered = true; 
} 

onLeave() { 
    // !this.exp && (this.isHovered = false); 
    this.isHovered = false 
} 
} 

sharedservice.ts

export class GlobalEventsManager { 

private _globalBehaviorSubj: BehaviorSubject<any> = new BehaviorSubject<any>({}); 

constructor() {} 

emitEvent(params) { 
    this._globalBehaviorSubj.next(params); 
} 

globalEventsEmitter(): Observable<any> { 
    return this._globalBehaviorSubj.asObservable(); 
} 
} 
+0

有没有这样的事情angularJS 2. Angular和AngularJS是不同的框架,A2的问题不应该有angularjs标签。 – estus

回答

0

是,AppComponent应该包含sidenav状态,并把它传递到SidenavComponentToolbarComponent应点击按钮时发出事件,因此AppComponent可以更改sidenav的状态。

+0

可否请您在代码中提供更多详细信息? – tsiro