Tüm sayfadaki tuşa basma olayını nasıl dinleyebilirim?


109

Bir işlevi tüm sayfama bağlamanın bir yolunu arıyorum (bir kullanıcı bir tuşa bastığında, bileşenimdeki bir işlevi tetiklemesini istiyorum)

AngularJS'de a ile kolaydı ng-keypressama ile çalışmıyor (keypress)="handleInput($event)".

Tüm sayfada bir div sarmalayıcıyla denedim ama işe yaramıyor gibi görünüyor. sadece odak noktası üzerindeyken çalışır.

<div (keypress)="handleInput($event)" tabindex="1">

Denedin window:keypressmi
KarolDepka

Yanıtlar:


203

Bileşeninizde @HostListener dekoratörünü kullanırdım :

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

@Component({
  ...
})
export class AppComponent {

  @HostListener('document:keypress', ['$event'])
  handleKeyboardEvent(event: KeyboardEvent) { 
    this.key = event.key;
  }
}

Aşağıdakiler gibi başka seçenekler de vardır:

@Componentdekoratör içinde barındırma özelliği

Angular @HostListener, ana mülkün yerine dekoratör kullanılmasını önerir https://angular.io/guide/styleguide#style-06-03

@Component({
  ...
  host: {
    '(document:keypress)': 'handleKeyboardEvent($event)'
  }
})
export class AppComponent {
  handleKeyboardEvent(event: KeyboardEvent) {
    console.log(event);
  }
}

renderer.listen

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

@Component({
  ...
})
export class AppComponent {
  globalListenFunc: Function;

  constructor(private renderer: Renderer2) {}

  ngOnInit() {
    this.globalListenFunc = this.renderer.listen('document', 'keypress', e => {
      console.log(e);
    });
  }

  ngOnDestroy() {
    // remove listener
    this.globalListenFunc();
  }
}

Observable.fromEvent

import { Observable } from 'rxjs/Observable';
import 'rxjs/add/observable/fromEvent';
import { Subscription } from 'rxjs/Subscription';

@Component({
  ...
})
export class AppComponent {
  subscription: Subscription;

  ngOnInit() {
    this.subscription = Observable.fromEvent(document, 'keypress').subscribe(e => {
      console.log(e);
    })
  }

  ngOnDestroy() {
    this.subscription.unsubscribe();
  }
}

2
İyi sallanıyor. '@ angular / core'dan {HostListener} içe aktarım eklemek zorunda. ve bileşenin herhangi bir yerinde bile arayın. Yan
müteahhit

23
Bunun için teşekkürler, ancak gelecekteki okuyucular için bir uyarı: ok tuşlarına ihtiyacınız varsa, tuşa basmak yerine tuşa basmayı kullanın.
Troels Larsen

14
escAnahtara ihtiyacınız varsa , keyupetkinliği kullanın . Teşekkürler @TroelsLarsen
Aron Lorincz

@yurzui, bu etkinliği belirli bir bileşen için nasıl kullanabilirim. tüm sayfada değil
kamalav

1
@yurzui a function-key(F1, F2, F3, ...) nasıl tespit edebilirim ?
Arpit Kumar

18

yurzui'nin cevabı benim için işe yaramadı, farklı bir RC versiyonu olabilir veya benim açımdan bir hata olabilir. Her iki durumda da, Angular2 RC4'teki bileşenimle bunu şu şekilde yaptım (şimdi oldukça modası geçmiş).

@Component({
    ...
    host: {
        '(document:keydown)': 'handleKeyboardEvents($event)'
    }
})
export class MyComponent {
    ...
    handleKeyboardEvents(event: KeyboardEvent) {
        this.key = event.which || event.keyCode;
    }
}

3
Bu aynı, sadece alternatif sözdizimi ve keydownonun yerine kullandınızkeypress
Günter Zöchbauer

Dediğim gibi, muhtemelen benim açımdan bir hata, ama benim için işe yaraması için gereken buydu. :)
Adam

Document.addEventListener kullanmak yerine bunun avantajı ne olabilir? Bu sadece DOM'u soyutlama meselesi mi?
Ixonal

Bu makalelerdeki @Ixonal # 2, yapabileceğimden daha iyi açıklıyor : angularjs.blogspot.ca/2016/04/… Temelde, bu 'Açısal' yol değil, çünkü tarayıcıyla birleştirildi ve test edilemez. Belki şu anda büyük bir anlaşma değil, ama takip edilmesi iyi bir model.
Adam

1
En yeni dokümanlara @HostListener kullanılmasını öneriyoruz: angular.io/docs/ts/latest/guide/...
saschwarz

11

Sadece buna eklemek için 2019 w Angular 8,

tuşa basmak yerine tuşa basmayı kullanmak zorunda kaldım

@HostListener('document:keypress', ['$event'])

-e

@HostListener('document:keydown', ['$event'])

Stacklitz Çalışma


Açısal 9 raporu: hem tuşa basma hem de tuşa basma, normal "asdf" tuşlarını kaydeder, ancak yalnızca tuşa basma F4 ve diğer işlev tuşlarını alır. Tuşa basma, CTRL-Z gibi bazı tuş kombinasyonlarını alabilir, tuş basımı bunları ayrı ayrı yorumlar (bir CTRL tuşu, ardından milisaniyeler sonra, bir Z tuşu).
Anders8

4

Herhangi bir klavye düğmesine basıldığında herhangi bir olay gerçekleştirmek istiyorsanız, bu durumda @HostListener kullanabilirsiniz. Bunun için, bileşen ts dosyanıza HostListener'ı içe aktarmanız gerekir.

{HostListener} öğesini '@ angular / core'dan içe aktarın;
daha sonra bileşen ts dosyanızın herhangi bir yerinde aşağıdaki işlevi kullanın.

@HostListener('document:keyup', ['$event'])
  handleDeleteKeyboardEvent(event: KeyboardEvent) {
    if(event.key === 'Delete')
    {
      // remove something...
    }
  }


0

Bunun en iyi işi yaptığını düşünüyorum

https://angular.io/api/platform-browser/EventManager

örneğin app.component içinde

constructor(private eventManager: EventManager) {
    const removeGlobalEventListener = this.eventManager.addGlobalEventListener(
      'document',
      'keypress',
      (ev) => {
        console.log('ev', ev);
      }
    );
  }
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.