2017-03-15 57 views
5

我試圖添加一個類,它將改變它的外觀(,例如漢堡到x),到一個菜單觸發DOM元素,它有自己的方法來顯示覆蓋菜單,但我無法弄清楚如何做到這一點。Angular 2 - 在點擊時向DOM元素添加一個類

這裏是我迄今爲止 - 這是呼籲菜單本身的外部方法:

import { Component, ElementRef, ViewChild, Renderer, AfterViewInit } from '@angular/core'; 

import { LayoutService } from 'app/core/services/layout.service'; 

@Component({ 
    moduleId: module.id, 
    selector: 'header-main', 
    templateUrl: 'header-main.component.html', 
}) 


export class HeaderMainComponent { 

    @ViewChild('nav-trigger') el: ElementRef; 

    constructor(private layoutService: LayoutService) { } 

    menuToggle() { 
     this.layoutService.mainMenuToggle(); 
     this.el.nativeElement.classList.add('opened'); 
    } 
} 

我是新來的角2.這是如何工作了呢?我應該使用Renderer,爲什麼我應該使用Renderer?等問題


編輯:用絕對click事件(選擇子,不是父)的問題是,我們必須使用一個reference tag@ViewChild裝飾爲使配對:

@ViewChild('navTrigger') navTrigger: ElementRef;它涉及HTML模板中的#navTrigger引用。

因此:

export class HeaderMainComponent { 
    logoAlt = 'We Craft beautiful websites'; // Logo alt and title texts 

    @ViewChild('navTrigger') navTrigger: ElementRef; 

    constructor(private layoutService: LayoutService, private renderer: Renderer) { } 

    menuToggle(event: any) { 
     this.layoutService.mainMenuToggle(); 
     this.renderer.setElementClass(this.navTrigger.nativeElement, 'opened', true); 
    } 
} 
+0

https://angular.io/docs/ts/latest/guide/template -syntax.html#!#ngClass –

回答

8

來完成你想要什麼,你需要使用的渲染器(將其注入構造與private renderer: Renderer)。渲染器提供對本地元素的抽象,並提供了一種與DOM交互的安全方式。

在您的模板,你應該能夠做這樣的事情:

<div (click)="menuToggle($event)"></div> 

這捕獲click事件,並把它傳遞給menuToggle功能。

然後在你的組件,你應該能夠使用這樣的渲染與DOM交互:

menuToggle(event:any) { 
    this.renderer.setElementClass(event.target,"opened",true); 
} 

setElementClass函數簽名,根據docssetElementClass(renderElement: any, className: string, isAdd: boolean) : void

進一步的閱讀在Renderer上,this is a good article on Medium。在談到使用ViewChild和訪問DOM通過nativeElement與使用Renderer,它說:

也能正常工作(使用nativeElement從ViewChild)。我們使用ViewChild裝飾器幫助獲取輸入元素,然後訪問本地DOM元素,並在輸入上調用focus()方法。

這種方法 的問題是,當我們直接訪問本地元素,我們在 角的DOM抽象放棄和錯過的機會,能夠 在無-DOM環境下也執行如:本地移動, 原生桌面,網絡工作者或服務器端渲染。

請記住, Angular是一個平臺,瀏覽器只是我們的 可以呈現我們的應用程序的一個選項。

希望這會有所幫助。

+0

答案令人難以置信的精確度。我有一個小問題,雖然在標記' '這是被添加到內部子元素,而不是該類的直接所有者。我怎樣才能解決這個問題? – snkv

3

由於泰勒的回答,事情已經改變了一點。 Renderer已折舊並由Renderer2取代。在Renderer 2中,類setElementClass被替換爲addClass。並根據docsaddClass新功能的簽名,是

addClass(el: any, name: string): void 

所以更新menuToggle功能應該讀

menuToggle(event:any) { 
    this.renderer.addClass(event.target,"opened"); 
} 
相關問題