Podnoszenie zdarzenie

Jeśli chcesz, aby klasy, aby wygenerować zdarzenie, należy podać trzy następujące elementy:

  • Klasa, która dostarcza dane zdarzenie.

  • Delegata zdarzenia.

  • Klasa, która wywołuje zdarzenie.

Definiowanie klasy, aby dostarczyć dane zdarzenie

Przez Konwencję w .NET Framework, gdy zdarzenie jest wywoływane, przekazuje dane zdarzeń do jego obsługi zdarzeń. Dane zdarzenia są dostarczane przez System.EventArgs klasy lub przez klasę, która jest uzyskane z niego.

Często zdarzenia nie zawiera niestandardowych danych; fakt, że zdarzenie zostało wywołane zawiera wszystkie informacje, które wymagają obsługi zdarzeń. W takim przypadku można przekazać zdarzenia EventArgs obiektu do jego obsługi. EventArgs Klasy ma tylko jeden składnik, Empty, to znaczy nie są dziedziczone z System.Object. Mogą być używane do utworzenia wystąpienia nowego EventArgs klasy.

Jeśli zdarzenie niestandardowe dane, można przekazać instancję klasy pochodzącej od EventArgs do obsługi zdarzeń. W zależności od dokładne dane zdarzenie przechodzi do obsługi może być mogli korzystać z istniejącej klasy danych zdarzeń w .NET Framework. Na przykład, jeśli modułu obsługi zdarzenia pozwala na akcję skojarzoną ze zdarzeniem odwołana, można użyć CancelEventArgs klasy.

Kiedy należy podać dane niestandardowe do obsługi i istniejącej klasy nie jest dostępna, można zdefiniować własne klasy danych zdarzenia. Musi pochodzić od System.EventArgs. Umownie, nosi nazwę tej klasy EventNameEventArgs. Poniższy przykład ilustruje takie klasy danych zdarzenia niestandardowego. Definiuje klasę o nazwie AlarmEventArgs , która zapewnia dwie pozycje danych do obsługi zdarzeń: tylko do odczytu Time właściwość, która wskazuje, kiedy alarm minął; i Snooze właściwość, która wskazuje, czy alarmu należy go ponownie po upływie wyznaczonego czasu lub czy anulowane przyszłych alarmów.

Public Class AlarmEventArgs : Inherits EventArgs
   Private alarmTime As Date
   Private snoozeOn As Boolean = True

   Public Sub New(time As Date)
      Me.alarmTime = time
   End Sub

   Public ReadOnly Property Time As Date
      Get
         Return Me.alarmTime
      End Get
   End Property

   Public Property Snooze As Boolean
      Get
         Return Me.snoozeOn
      End Get
      Set
         Me.snoozeOn = value
      End Set   
   End Property   
End Class
public class AlarmEventArgs : EventArgs
{
   private DateTime alarmTime;
   private bool snoozeOn = true;

   public AlarmEventArgs(DateTime time)
   {
      this.alarmTime = time;
   }

   public DateTime Time
   {
      get { return this.alarmTime; }
   }

   public bool Snooze
   {
      get { return this.snoozeOn; }
      set { this.snoozeOn = value; }
   }   
}
public ref class AlarmEventArgs : public EventArgs
{
private: 
   System::DateTime^ alarmTime;
   bool snoozeOn;

public:
   AlarmEventArgs(System::DateTime^ time) 
   {
      this->alarmTime = time;
      this->snoozeOn = true;
   }

   property DateTime^ Time 
   {
      System::DateTime^ get()
      { return this->alarmTime; }
   }

   property bool Snooze
   {
      bool get()
      { return this->snoozeOn; }
      void set(bool snooze)
      { this->snoozeOn = snooze; }
   }
};

Definiowanie delegata zdarzenia

Pełnomocnika zdarzeń jest używany do definiowania podpisu zdarzenia. Pełnomocnik określonego zdarzenia zazwyczaj odpowiada klasy danych określonego zdarzenia. Umownie zdarzeń w .NET Framework mają podpis EventName(sender, e), gdzie sender jest Object , która zapewnia odwołanie do klasy lub struktury, że wyzwolenie zdarzenia, i e jest EventArgs obiektu lub obiektu pochodzących z EventArgs zapewnia dane zdarzenie. Następnie definicję delegata zwykle ma postać EventNameHandler(sender, e).

Jeśli używasz klasy danych zdarzenia, który jest już zdefiniowana w.NET Framework class library lub w bibliotece strony trzeciej, jest prawdopodobne, że odpowiedniego delegata zdarzenia jest także zdefiniowane w tej bibliotece. Na przykład EventHandler pełnomocnik może być używany razem z EventArgs klasy. Podobnie CancelEventHandler pełnomocnik może być używany razem z CancelEventArgs klasy.

Jeżeli zdefiniowanie klasy danych zdarzenia niestandardowego, można także zdefiniować niestandardowe pełnomocnika do definiowania podpisu zdarzenia lub można użyć rodzajową Action<T1, T2> delegować.

Poniższy przykład definiuje delegata zdarzenia o nazwie AlarmEventHandler.

Public Delegate Sub AlarmEventHandler(sender As Object, e As AlarmEventArgs)
public delegate void AlarmEventHandler(object sender, AlarmEventArgs e);
public delegate void AlarmEventHandler(System::Object^ sender, AlarmEventArgs^ e);

Definiowanie klasy podnieść zdarzenia

Klasa, która wywołuje zdarzenie musi dostarczyć deklarację zdarzenia i zdefiniować metodę, która wywołuje zdarzenie. Dodatkowo musi ono zapewnić logikę podnieść zdarzenia w klasie właściwości lub metody.

Określenie członka zdarzeń w sieci za pomocą klasy event słowa kluczowego w C# lub Event instrukcję w języku Visual Basic. Gdy kompilator napotka deklaracji zdarzenia w klasie, tworzy członek prywatny takich jak:

private EventNameHandler eh = null;

Kompilator tworzy również dwie metody publiczne, add_EventName i remove_EventName. Metody te są zdarzeń haków ładunkowych, zezwalające na delegatów, które mają być połączone lub usuwane z delegata zdarzenia eh. Szczegóły są ukryte przed programista.

Uwaga

W językach innych niż C# i Visual Basic 2005, kompilator nie może automatycznie wygenerować kod odpowiadający członka zdarzeń i trzeba jawnie zdefiniować zdarzeń haków ładunkowych i pola prywatne delegata.

Poniższy przykład deklaruje zdarzenia o nazwie AlarmEvent. Jest fragmentem z przykład klasę o nazwie Alarm którego pełnego kodu źródłowego jest pokazany poniżej. Należy zauważyć, że ma podpis z AlarmEventHandler delegować.

Event AlarmEvent As AlarmEventHandler
public event AlarmEventHandler AlarmEvent;
public:
   event AlarmEventHandler^ AlarmEvent; 

Po zdefiniowaniu implementacji zdarzenia, należy określić, kiedy zdarzenie. Podnoszenie zdarzenie, wywołując chronionego OnEventName metoda w klasie zdefiniowane zdarzenie lub w klasie pochodnej. OnEventNamemetoda następnie wywołuje zdarzenie.

Uwaga

Chronione OnEventNamemetoda umożliwia również klas pochodnych zastąpić zdarzenia bez dołączania pełnomocnika do niego.Klasa pochodna musi zawsze używaj wywołania OnEventNamemetoda klasy bazowej, aby zapewnić delegatów zarejestrowane zdarzenie.

Poniższy przykład definiuje OnAlarmEvent metodę, która jest odpowiedzialny za AlarmEvent zdarzenia.

Protected Sub OnAlarmEvent(e As AlarmEventArgs)
   RaiseEvent AlarmEvent(Me, e)
End Sub  
protected void OnAlarmEvent(AlarmEventArgs e)
{
   AlarmEvent(this, e);
}  
protected:
   void OnAlarmEvent(AlarmEventArgs^ e)
   {
      AlarmEvent(this, e);
   }

Poniższy przykład definiuje metodę o nazwie Set zawierający logiki ognia zdarzenie, wywołując OnAlarmEvent metody. Jeśli godzin i minut czasu alarmu równa godzin i minut bieżący czas Set uruchamia metodę AlarmEventArgs obiektu i dostarcza czas, jaki minął alarmu. Po wykonanie procedury obsługi zdarzeń, sprawdza wartość Snooze właściwości. Jeśli Snooze jest false, zdarzenia alarm nie więcej mają być wywoływane tak Set metody można zakończyć. Jeśli Snooze jest true, czas, alarm jest wyłączyć jest zwiększany o wartość Interval właściwości.

Public Sub [Set]()
   Do
      System.Threading.Thread.Sleep(2000)
      Dim currentTime As DateTime = Date.Now
      ' Test whether it is time for the alarm to go off.
      If currentTime.Hour = alarmTime.Hour And _
         currentTime.Minute = AlarmTime.Minute Then
         Dim args As New AlarmEventArgs(currentTime)
         OnAlarmEvent(args)
         If args.Snooze = False Then 
            Exit Sub
         Else
            Me.alarmTime = Me.alarmTime.AddMinutes(Me.interval)
         End If      
      End If          
   Loop
End Sub 
public void Set()
{
   while (true) {
      System.Threading.Thread.Sleep(2000);
      DateTime currentTime = DateTime.Now;
      // Test whether it is time for the alarm to go off.
      if (currentTime.Hour == alarmTime.Hour && 
          currentTime.Minute == alarmTime.Minute)
      {    
         AlarmEventArgs args = new AlarmEventArgs(currentTime);
         OnAlarmEvent(args);
         if (! args.Snooze) 
            return;
         else
            this.alarmTime = this.alarmTime.AddMinutes(this.interval);
      }
   }
} 
void Set()
{
   do {
      Thread::Sleep(2000);
      System::DateTime^ currentTime = DateTime::Now;
      // Test whether it's time for the alarm to go off.
      if (currentTime->Hour == alarmTime->Hour && currentTime->Minute == alarmTime->Minute)
      {
         AlarmEventArgs^ args = gcnew AlarmEventArgs(currentTime);
         OnAlarmEvent(args);
         if (args->Snooze == false)
            return;
         else
            this->alarmTime = this->alarmTime->AddMinutes(this->interval);
      }
   } while (true);
}

Poniższy przykład zawiera wszystkie kod źródłowy dla klasy alarmu.

Public Class Alarm
   Private alarmTime As Date
   Private interval As Integer = 10

   Event AlarmEvent As AlarmEventHandler

   Public Sub New(time As Date)
      Me.New(time, 10)
   End Sub

   Public Sub New(time As Date, interval As Integer)
      Me.alarmTime = time
      Me.interval = interval
   End Sub

   Public Sub [Set]()
      Do
         System.Threading.Thread.Sleep(2000)
         Dim currentTime As DateTime = Date.Now
         ' Test whether it is time for the alarm to go off.
         If currentTime.Hour = alarmTime.Hour And _
            currentTime.Minute = AlarmTime.Minute Then
            Dim args As New AlarmEventArgs(currentTime)
            OnAlarmEvent(args)
            If args.Snooze = False Then 
               Exit Sub
            Else
               Me.alarmTime = Me.alarmTime.AddMinutes(Me.interval)
            End If      
         End If          
      Loop
   End Sub 

   Protected Sub OnAlarmEvent(e As AlarmEventArgs)
      RaiseEvent AlarmEvent(Me, e)
   End Sub  
End Class
public class Alarm
{
   private DateTime alarmTime;
   private int interval = 10;

   public event AlarmEventHandler AlarmEvent;

   public Alarm(DateTime time) : this(time, 10)
   {
   }

   public Alarm(DateTime time, int interval)
   {
      this.alarmTime = time;
      this.interval = interval;
   }

   public void Set()
   {
      while (true) {
         System.Threading.Thread.Sleep(2000);
         DateTime currentTime = DateTime.Now;
         // Test whether it is time for the alarm to go off.
         if (currentTime.Hour == alarmTime.Hour && 
             currentTime.Minute == alarmTime.Minute)
         {    
            AlarmEventArgs args = new AlarmEventArgs(currentTime);
            OnAlarmEvent(args);
            if (! args.Snooze) 
               return;
            else
               this.alarmTime = this.alarmTime.AddMinutes(this.interval);
         }
      }
   } 

   protected void OnAlarmEvent(AlarmEventArgs e)
   {
      AlarmEvent(this, e);
   }  
}
public ref class Alarm 
{
private:
   System::DateTime^ alarmTime;
   int interval;

public:
   event AlarmEventHandler^ AlarmEvent; 
   Alarm(System::DateTime^ time) : alarmTime(time), interval(10) { };
   Alarm(System::DateTime^ time, int interval) : alarmTime(time), interval(interval) {};

   void Set()
   {
      do {
         Thread::Sleep(2000);
         System::DateTime^ currentTime = DateTime::Now;
         // Test whether it's time for the alarm to go off.
         if (currentTime->Hour == alarmTime->Hour && currentTime->Minute == alarmTime->Minute)
         {
            AlarmEventArgs^ args = gcnew AlarmEventArgs(currentTime);
            OnAlarmEvent(args);
            if (args->Snooze == false)
               return;
            else
               this->alarmTime = this->alarmTime->AddMinutes(this->interval);
         }
      } while (true);
   }

protected:
   void OnAlarmEvent(AlarmEventArgs^ e)
   {
      AlarmEvent(this, e);
   }
};

Zobacz też

Zadania

Jak: podnoszenie i zużywają zdarzeń

Jak: wdrożenie zdarzenia w klasie

Koncepcje

Zdarzenia i pełnomocnicy

Inne zasoby

Obsługa i podnoszenie zdarzeń