如果在Angular 5中单击其子菜单菜单,则如何关闭弹出菜单

时间:2018-04-15 08:58:53

标签: angular typescript

我有一个弹出菜单和一个菜单项组件,我正在一起使用它来显示一个弹出列表菜单列表。

代码示例:

<div class="main">
    <popover-menu>
        <menu-item> Menu 1 </menu-item>  
        <menu-item> Menu 2 </menu-item>  
        <menu-item> Menu 3 </menu-item>                           
    </popover-menu>
</main

所以基本上我被困在这里:

  1. 如果点击菜单项,如何关闭/隐藏popover菜单。
  2. 如何在popover-menu之外使用布尔值来了解弹出菜单何时打开/关闭。
  3. 例如:

    <div class="main" [class.menu-open]="isMenuOpen"></div>
    

    非常感谢任何帮助,谢谢。

    修改

    我想在HTML页面上使用popover-menu和menu-item选择器

    PopoverMenuComponent

    @Component({
      selector: 'popover-menu',
      template: `
      <div>
        <ng-content></ng-content>
      <div>
      `
    })
    

    MenuItemComponent

    @Component({
          selector: 'menu-item',
          template: `
          <div>
            <ng-content></ng-content>
          <div>
          `
        })
    

    HTML

    <div class="main">
        <popover-menu>
            <menu-item> Menu 1 </menu-item>  
            <menu-item> Menu 2 </menu-item>  
            <menu-item> Menu 3 </menu-item>                           
        </popover-menu>
    </main
    

2 个答案:

答案 0 :(得分:1)

<强> menu.component.ts

import { Component, Input, Output, EventEmitter } from '@angular/core';

@Component({
  selector: 'menu',
  template: `
  <div *ngIf="opened">
    <ng-content></ng-content>
  </div>
  `
})
export class MenuComponent  {
  @Output() openedChange = new EventEmitter<boolean>();

  private _opened: boolean;
   @Input() set opened(v: boolean) {
     this._opened = v;
     this.openedChange.next(v)
   }

   get opened() {
     return this._opened;
   }

   toggle() {
     this.opened = !this.opened;
   }

}

菜单-item.component.ts

import { Component, HostListener } from '@angular/core';
import { MenuComponent } from './menu.component';

@Component({
  selector: 'menu-item',
  template: `<ng-content></ng-content>`
})
export class MenuItemComponent {

  @HostListener('click') onClick() {
    this.menu.toggle();
  }

  constructor(private menu: MenuComponent) { }
}

<强> app.component.ts

import { Component } from '@angular/core';

@Component({
  selector: 'my-app',
  template: `
  <div> Opened in the component class: {{ opened }} </div>
  <div> Menu component internal state: {{ menu.opened }} </div>

  <button (click)="toggle()">Toggle</button>

  <menu #menu [(opened)]="opened">
    <menu-item>One</menu-item>
    <menu-item>Two</menu-item>
    <menu-item>Three</menu-item>
  </menu>
  `
})
export class AppComponent  {
  opened = true;

  toggle() {
    this.opened = !this.opened;
  }
}

Live demo

通过此实施,点击任意menu-item将切换menu组件。它是通过在MenuComponent的构造函数中注入MenuItemComponent的引用来实现的。现在,孩子MenuItemComponent可以触发父toggle()的{​​{1}}方法。

MenuComponent也组件公开了<menu> [opened]@Input (openedChange),它允许通过想要使用的组件双向绑定菜单状态菜单。

答案 1 :(得分:0)

使用EventEmitters

MenuItemComponent中,添加

@Output() clicked: EventEmitter<bool> = new EventEmitter();

itemClicked() {
     this.clicked.emit(true);
}

此外,在其模板中,为单击项目时添加事件侦听器。像

<li (click)="itemClicked()"> menu Item 1</li>

在html中,

<div class="main" [class.menu-open]="isMenuOpen">
    <popover-menu>
        <menu-item (clicked)="isMenuOpen = true"> Menu 1 </menu-item>  
        <menu-item (clicked)="isMenuOpen = true"> Menu 2 </menu-item>  
        <menu-item (clicked)="isMenuOpen = true"> Menu 3 </menu-item>                           
    </popover-menu>
</div>

我使用的方法是https://angular.io/guide/component-interaction#parent-listens-for-child-event)。 该文档还列出了您可以执行此操作的其他方法。