typescript - Angular 2: Stoppa spridning av förälderelementets händelse när man klickar på en länk


Jag har ett fall av event bubbling. Exempel :

<td (click)="doSomething()">
  <text [innerHtml]="content"> 
        //  content of innerHtml is :  <a href="http://google.com"></a>
  </text>
</td>

Taggen renderas från en annan komponent genom innerHtml. Problemet: när jag klickar på länken, utlöses klickhändelsen på elementet också. Hur löser man problemet (stoppa propagation av doSomething()), med vetskapen att eventhanterare (eller någon Angular 2-kod) inte kan skickas genom innerHtml?

Tack!

Svar #1

Workaround kan helt enkelt vara att placera (click)="$event.stopPropagation()" över text-komponenten, så att händelsen inte bubbla upp från värdkomponenten. Samma sak kan förbättras genom att skriva en Directive.

<td (click)="doSomething()">
  <text (click)="$event.stopPropagation()" [innerHtml]="content"> 
        //  content of innerHtml is :  <a href="http://google.com"></a>
  </text>
</td>

Svar #2

Du kan dra nytta av bubbling. Från din hanterare kan du titta på event.target för att se om en A klickades på, och i så fall hoppa över din åtgärd.

Var försiktig, dock, eftersom event.target kan vara SPAN! Du behöver inte bara kontrollera om eventets mål är en A-tagg, utan också gå upp i DOM-trädet i en enkel simulering av bubblande.

Så här är en möjlig lösning:

mall

(click)="doSomething($event)"

komponent

export class AppComponent {
  content = '<a href="http://google.com">Link text <span>Nested text</span></a>'

  doSomething(e) {
    let target = e.target;

    while (target !== e.currentTarget) {
      if (target.tagName == 'A') return;
      target = target.parentNode;
    }

    alert('do something')
  }
}

Plunker-exempel

Relaterade artiklar