Nuta
Dostęp do tej strony wymaga autoryzacji. Możesz spróbować się zalogować lub zmienić katalog.
Dostęp do tej strony wymaga autoryzacji. Możesz spróbować zmienić katalogi.
Zdarzenia na platformie .NET są oparte na modelu delegatów. Model delegata jest zgodny ze wzorcem projektowania obserwatora , który umożliwia subskrybentowi rejestrowanie się i odbieranie powiadomień od dostawcy. Nadawca zdarzeń przesyła powiadomienie, gdy wystąpi zdarzenie. Odbiorca zdarzeń definiuje odpowiedź. W tym artykule opisano główne składniki modelu delegata, sposób korzystania z zdarzeń w aplikacjach oraz sposób implementowania zdarzeń w kodzie.
Zgłaszanie zdarzeń za pomocą nadawcy zdarzeń
Zdarzenie jest komunikatem wysyłanym przez obiekt w celu zasygnalizowania wystąpienia akcji. Akcja może być interakcją użytkownika, taką jak naciśnięcie przycisku, lub może wynikać z innej logiki programu, takiej jak zmiana wartości właściwości. Obiekt, który zgłasza zdarzenie, jest nazywany nadawcą zdarzeń . Nadawca zdarzeń nie zna obiektu ani metody, która odbiera (obsługuje) zdarzenia, które zgłasza. Zdarzenie jest zazwyczaj związane z nadawcą zdarzeń. Na przykład zdarzenie Click jest elementem członkowskim klasy Button, a zdarzenie PropertyChanged jest elementem członkowskim klasy, która implementuje interfejs INotifyPropertyChanged.
Aby zdefiniować zdarzenie, należy użyć słowa kluczowego języka C# lub słowa kluczowego Event języka Visual Basic w sygnaturze klasy zdarzenia i określić typ delegata dla zdarzenia. Delegaci są opisywani w następnej sekcji.
Zazwyczaj w celu wywołania zdarzenia należy dodać metodę oznaczoną jako protected i virtual (w języku C#) lub Protected i Overridable (w Visual Basic). Konwencja nazewnictwa metody jest On<EventName>, na przykład OnDataReceived. Metoda powinna przyjąć jeden parametr określający obiekt danych zdarzenia, który jest obiektem typu EventArgs lub typem pochodnym. Należy dostarczyć tę metodę, aby umożliwić klasom pochodnym zastąpienie logiki wywołania zdarzenia. Klasa pochodna powinna zawsze wywoływać metodę On<EventName> klasy bazowej, aby upewnić się, że zarejestrowani delegaci odbierają zdarzenie.
W poniższym przykładzie pokazano, jak zadeklarować zdarzenie o nazwie ThresholdReached. Zdarzenie jest skojarzone z delegatem EventHandler i wywoływane w metodzie o nazwie OnThresholdReached:
class Counter
{
public event EventHandler ThresholdReached;
protected virtual void OnThresholdReached(EventArgs e)
{
ThresholdReached?.Invoke(this, e);
}
// provide remaining implementation for the class
}
Public Class Counter
Public Event ThresholdReached As EventHandler
Protected Overridable Sub OnThresholdReached(e As EventArgs)
RaiseEvent ThresholdReached(Me, e)
End Sub
' provide remaining implementation for the class
End Class
Deklarowanie podpisów delegatów dla programów obsługi zdarzeń
Delegat to typ, który zawiera odwołanie do metody. Delegat jest zadeklarowany z podpisem, który pokazuje zwracany typ i parametry metod, do których się odwołuje. Może zawierać odwołania tylko do metod, które pasują do jego podpisu. Delegat jest odpowiednikiem wskaźnika do funkcji typowo-bezpiecznej lub wywołania zwrotnego. Deklaracja delegata jest wystarczająca do zdefiniowania klasy delegata.
Delegaci mają wiele zastosowań na platformie .NET. W kontekście zdarzeń delegat jest pośrednikiem (lub mechanizmem przypominającym wskaźnik) między źródłem zdarzeń a kodem, który obsługuje zdarzenie. Delegat jest skojarzony ze zdarzeniem, uwzględniając typ delegata w deklaracji zdarzenia, jak pokazano w przykładzie w poprzedniej sekcji. Aby uzyskać więcej informacji na temat delegatów, zobacz klasę Delegate.
Platforma .NET udostępnia delegatów EventHandler i EventHandler<TEventArgs> do obsługi większości scenariuszy zdarzeń. Użyj delegata EventHandler dla wszystkich zdarzeń, które nie zawierają danych dotyczących zdarzenia. Użyj delegata EventHandler<TEventArgs> w przypadku zdarzeń zawierających dane dotyczące zdarzenia. Te delegaty nie mają zwracanej wartości typu i przyjmują dwa parametry (obiekt dla źródła zdarzenia i obiekt dla danych zdarzenia).
Delegaty są obiektami klasy multicast, co oznacza, że mogą przechowywać odwołania do więcej niż jednej metody obsługującej zdarzenia. Aby uzyskać więcej informacji, zobacz stronę referencyjną Delegate. Delegacje zapewniają elastyczność i szczegółową kontrolę w obsłudze zdarzeń. Delegat działa jako dyspozytor zdarzeń dla klasy, która zgłasza zdarzenie, utrzymując listę zarejestrowanych obsługi zdarzenia.
Użyj typów delegatów EventHandler i EventHandler<TEventArgs>, aby zdefiniować wymagany delegat. W deklaracji oznaczasz delegata delegate z typem w języku C# lub Delegate typem w języku Visual Basic . W poniższym przykładzie pokazano, jak zadeklarować delegata o nazwie ThresholdReachedEventHandler:
public delegate void ThresholdReachedEventHandler(object sender, ThresholdReachedEventArgs e);
Public Delegate Sub ThresholdReachedEventHandler(sender As Object, e As ThresholdReachedEventArgs)
Praca z klasami danych zdarzeń
Dane skojarzone ze zdarzeniem mogą być udostępniane za pośrednictwem klasy danych zdarzenia. Platforma .NET udostępnia wiele klas danych zdarzeń, których można używać w aplikacjach. Na przykład klasa SerialDataReceivedEventArgs to klasa danych zdarzenia dla zdarzenia SerialPort.DataReceived. Platforma .NET jest zgodna ze wzorcem nazewnictwa, w którym wszystkie klasy danych zdarzeń kończą się sufiksem EventArgs. Należy określić, która klasa danych zdarzenia jest skojarzona ze zdarzeniem, sprawdzając delegata zdarzenia. Na przykład delegat SerialDataReceivedEventHandler zawiera klasę SerialDataReceivedEventArgs jako parametr.
Klasa EventArgs jest zazwyczaj podstawowym typem klas danych zdarzeń. Ta klasa jest również używana, jeśli zdarzenie nie ma żadnych skojarzonych z nim danych. Podczas tworzenia zdarzenia, które powiadamia subskrybentów, że coś się stało bez żadnych dodatkowych danych, dołącz klasę EventArgs jako drugi parametr w delegatu. Wartość EventArgs.Empty można przekazać, gdy nie podano żadnych danych. Delegat EventHandler zawiera klasę EventArgs jako parametr.
Możesz utworzyć klasę pochodzącą z klasy EventArgs, aby udostępnić wszystkie elementy członkowskie potrzebne do przekazania danych związanych ze zdarzeniem. Zazwyczaj należy użyć tego samego wzorca nazewnictwa co platforma .NET i zakończyć nazwę klasy danych zdarzenia sufiksem EventArgs.
W poniższym przykładzie przedstawiono klasę danych zdarzeń o nazwie ThresholdReachedEventArgs zawierającą właściwości specyficzne dla zgłaszanego zdarzenia:
public class ThresholdReachedEventArgs : EventArgs
{
public int Threshold { get; set; }
public DateTime TimeReached { get; set; }
}
Public Class ThresholdReachedEventArgs
Inherits EventArgs
Public Property Threshold As Integer
Public Property TimeReached As DateTime
End Class
Reagowanie na zdarzenia za pomocą programów obsługi
Aby odpowiedzieć na zdarzenie, należy zdefiniować metodę obsługi zdarzeń w odbiorniku zdarzeń. Ta metoda musi być zgodna z podpisem delegata dla zdarzenia, które obsługujesz. W procedurze obsługi zdarzeń należy wykonać akcje wymagane po wystąpieniu zdarzenia, takie jak zbieranie danych wejściowych użytkownika po naciśnięciu przycisku przez użytkownika. Aby otrzymywać powiadomienia po wystąpieniu zdarzenia, metoda obsługi zdarzeń musi subskrybować zdarzenie.
W poniższym przykładzie przedstawiono metodę obsługi zdarzeń o nazwie c_ThresholdReached zgodną z podpisem delegata EventHandler. Metoda subskrybuje zdarzenie ThresholdReached:
class ProgramTwo
{
static void Main()
{
var c = new Counter();
c.ThresholdReached += c_ThresholdReached;
// provide remaining implementation for the class
}
static void c_ThresholdReached(object sender, EventArgs e)
{
Console.WriteLine("The threshold was reached.");
}
}
Module Module1
Sub Main()
Dim c As New Counter()
AddHandler c.ThresholdReached, AddressOf c_ThresholdReached
' provide remaining implementation for the class
End Sub
Sub c_ThresholdReached(sender As Object, e As EventArgs)
Console.WriteLine("The threshold was reached.")
End Sub
End Module
Używanie statycznych i dynamicznych programów obsługi zdarzeń
Platforma .NET umożliwia subskrybentom rejestrowanie się w celu otrzymywania powiadomień o zdarzeniach statycznie lub dynamicznie. Statyczne procedury obsługi zdarzeń obowiązują przez cały czas istnienia klasy, której zdarzenia obsługują. Dynamiczne programy obsługi zdarzeń są jawnie aktywowane i dezaktywowane podczas wykonywania programu, zwykle w odpowiedzi na logikę programu warunkowego. Programy obsługi dynamicznej można używać, gdy powiadomienia o zdarzeniach są potrzebne tylko w określonych warunkach lub gdy warunki środowiska uruchomieniowego określają konkretną procedurę obsługi do wywołania. W przykładzie w poprzedniej sekcji pokazano, jak dynamicznie dodać procedurę obsługi zdarzeń. Aby uzyskać więcej informacji, zobacz Events (w Visual Basic) i Events (w języku C#).
Generuj wiele zdarzeń
Jeśli klasa zgłasza wiele zdarzeń, kompilator generuje jedno pole dla każdej instancji delegata zdarzenia. Jeśli liczba zdarzeń jest duża, koszt przechowywania jednego pola na delegata może nie być akceptowalny. W tych scenariuszach .NET oferuje właściwości zdarzeń, które można wykorzystać z dowolnie wybraną strukturą danych do przechowywania delegatów zdarzeń.
Właściwości zdarzenia składają się z deklaracji zdarzenia wraz z akcesorami zdarzenia. Akcesory zdarzeń to metody zdefiniowane do dodawania lub usuwania instancji delegatów zdarzeń ze struktury do przechowywania danych.
Uwaga
Właściwości zdarzenia są wolniejsze niż pola zdarzeń, ponieważ każdy delegat zdarzenia musi zostać pobrany przed jego wywołaniem.
Kompromis między pamięcią a szybkością. Jeśli klasa definiuje wiele zdarzeń, które są rzadko wywoływane, należy zaimplementować właściwości zdarzenia. Aby uzyskać więcej informacji, zobacz Obsługa wielu zdarzeń przy użyciu właściwości zdarzeń.
Eksplorowanie powiązanych zadań
Następujące zasoby opisują inne zadania i pojęcia związane z pracą ze zdarzeniami:
- Wywołaj i obsłuż zdarzenia: znajdź przykłady wywoływania i obsługi zdarzeń.
- Obsługa wielu zdarzeń z właściwościami zdarzeń: Dowiedz się, jak używać właściwości zdarzeń do obsługi wielu zdarzeń.
- Eksploruj wzorzec projektowania obserwatora: Przejrzyj wzorzec projektu, który umożliwia subskrybentowi rejestrowanie się i odbieranie powiadomień od dostawcy.
Przejrzyj odniesienie specyfikacji
Dokumentacja referencyjna specyfikacji jest dostępna dla interfejsów API obsługujących obsługę zdarzeń:
| Nazwa interfejsu API | Typ API | Źródło |
|---|---|---|
| Program obsługi zdarzeń | Delegat | EventHandler |
| EventHandler<TEventArgs> | Delegat | EventHandler<TEventArgs> |
| EventArgs | Klasa | EventArgs |
| Delegat | Klasa | Delegate |
Powiązana zawartość
- Zdarzenia (Visual Basic)
- Zdarzenia (Przewodnik programowania w języku C#)
- Omówienie zdarzeń i zdarzeń routowanych — aplikacje platformy uniwersalnej Windows (UWP)
- zdarzenia w aplikacjach ze Sklepu Windows 8.x