Comment : implémenter des événements dans votre classe
Les procédures suivantes décrivent comment implémenter un événement dans une classe. La première procédure implémente un événement qui ne possède pas de données associées ; elle utilise les classes System.EventArgs et System.EventHandler pour les données d'événement et le gestionnaire délégué. La deuxième procédure implémente un événement avec des données personnalisées ; elle définit des classes personnalisées pour les données d'événement et le gestionnaire d'événements délégué.
Notes
Cette rubrique indique comment déclarer et déclencher un événement dans une classe.Elle ne montre pas comment définir un gestionnaire d'événements qui utilise cet événement.Pour plus d'informations sur l'utilisation d'événements, consultez Consommation d'événements et Comment : déclencher et utiliser des événements.
Pour obtenir un exemple complet qui illustre le déclenchement et la gestion d'événements, consultez Comment : déclencher et utiliser des événements.
Pour implémenter un événement sans données spécifiques à l'événement
Définissez un membre d'événement public dans votre classe. Affectez le type du membre d'événement à un délégué System.EventHandler.
Public Class Countdown ' ... Public Event CountdownCompleted As EventHandler End Class
public class Countdown { // ... public event EventHandler CountdownCompleted; }
Fournissez une méthode protégée à votre classe qui déclenche l'événement. Nommez la méthode OnEventName. Déclenchez l'événement dans la méthode. Notez que le code C# doit vérifier si l'événement est null avant de le déclencher. Cela évite d'avoir à gérer le NullReferenceException qui est levé lorsqu'un événement est déclenché mais qu'aucun gestionnaire d'événements ne lui a été associé. Ce contrôle est nécessaire dans le cas-là, car la classe CountDown déclenche simplement l'événement mais ne lui fournit pas de gestionnaire.
Public Class Countdown ' ... Public Event CountdownCompleted As EventHandler Protected Overridable Sub OnCountdownCompleted(e As EventArgs) RaiseEvent CountdownCompleted(Me, e) End Sub End Class
public class Countdown { public event EventHandler CountdownCompleted; protected virtual void OnCountdownCompleted(EventArgs e) { if (CountdownCompleted != null) CountdownCompleted(this, e); } }
Déterminez quand déclencher l'événement dans votre classe. Appelez OnEventName pour déclencher l'événement.
Public Class Countdown Dim internalCounter As Integer = 0 ' ... Public Event CountdownCompleted As EventHandler Protected Overridable Sub OnCountdownCompleted(e As EventArgs) RaiseEvent CountdownCompleted(Me, e) End Sub Public Sub Decrement() internalCounter -= 1 If internalCounter = 0 OnCountdownCompleted(New EventArgs()) End If End Sub End Class
public class Countdown { int internalCounter = 0; // ... public event EventHandler CountdownCompleted; protected virtual void OnCountdownCompleted(EventArgs e) { if (CountdownCompleted != null) CountdownCompleted(this, e); } public void Decrement() { internalCounter--; if (internalCounter == 0) OnCountdownCompleted(new EventArgs()); } }
Pour implémenter un événement avec des données spécifiques à l'événement
Définissez une classe qui fournit des données pour l'événement. Nommez la classe EventNameArgs, dérivez la classe de System.EventArgs et ajoutez tous les membres spécifiques à l'événement.
Public Class AlarmEventArgs : Inherits EventArgs Private nRings As Integer = 0 Private pressed As Boolean = False Private text As String = "The alarm is ringing!" ' Constructor. Public Sub New(ByVal snoozePressed As Boolean, ByVal nRings As Integer) Me.pressed = snoozePressed Me.nRings = nRings End Sub ' Properties. Public Property AlarmText() As String Get Return Me.text End Get Set Me.text = value End Set End Property Public ReadOnly Property NumRings() As Integer Get Return Me.nRings End Get End Property Public ReadOnly Property SnoozePressed() As Boolean Get Return Me.pressed End Get End Property End Class
public class AlarmEventArgs : EventArgs { private readonly int nRings = 0; private readonly bool pressed = false; private string text = "The alarm is ringing!"; // Constructor. public AlarmEventArgs(bool snoozePressed, int nRings) { this.pressed = snoozePressed; this.nRings = nRings; } // Properties. public string AlarmText { get { return text; } set { this.text = value; } } public int NumRings { get { return nRings; } } public bool SnoozePressed { get { return pressed; } } }
Déclarez un délégué pour l'événement. Nommez le délégué EventNameEventHandler.
Public Delegate Sub AlarmEventHandler(sender As Object, e As AlarmEventArgs)
public delegate void AlarmEventHandler(object sender, AlarmEventArgs e);
Définissez un membre d'événement public nommé EventName dans votre classe. Affectez le type du membre d'événement au type du délégué d'événement.
Public Class AlarmClock ' ... Public Event Alarm As AlarmEventHandler End Class
public class AlarmClock { // ... public event AlarmEventHandler Alarm; }
Définissez une méthode protégée dans votre classe qui déclenche l'événement. Nommez la méthode OnEventName. Déclenchez l'événement dans la méthode. Notez que le code C# doit vérifier si l'événement est null avant de le déclencher. Cela évite d'avoir à gérer le NullReferenceException qui est levé lorsqu'un événement est déclenché mais qu'aucun gestionnaire d'événements ne lui a été associé. Ce contrôle est nécessaire dans le cas-là, car la classe CountDown déclenche simplement l'événement mais ne lui fournit pas de gestionnaire.
Public Class AlarmClock ' ... Public Event Alarm As AlarmEventHandler Protected Overridable Sub OnAlarm(e As AlarmEventArgs) RaiseEvent Alarm(Me, e) End Sub End Class
public class AlarmClock { // ... public event AlarmEventHandler Alarm; protected virtual void OnAlarm(AlarmEventArgs e) { if (Alarm != null) Alarm(this, e); } }
Déterminez quand déclencher l'événement dans votre classe. Appelez OnEventName pour déclencher l'événement et passer les données spécifiques à l'événement à l'aide de EventNameEventArgs.
Public Class AlarmClock Public Sub Start ' ... System.Threading.Thread.Sleep(300) Dim e As AlarmEventArgs = New AlarmEventArgs(False, 0) OnAlarm(e) End Sub Public Event Alarm As AlarmEventHandler Protected Overridable Sub OnAlarm(e As AlarmEventArgs) RaiseEvent Alarm(Me, e) End Sub End Class
public class AlarmClock { public void Start() { // ... System.Threading.Thread.Sleep(300); AlarmEventArgs e = new AlarmEventArgs(false, 0); OnAlarm(e); } public event AlarmEventHandler Alarm; protected virtual void OnAlarm(AlarmEventArgs e) { if (Alarm != null) Alarm(this, e); } }
Exemple
L'exemple suivant définit une classe DiskSpaceMonitor qui utilise un événement pour produire un avertissement chaque fois que l'espace disque libre devient inférieur à un pourcentage défini dans un fichier de configuration. Il définit également une classe DiskSpaceWarningEventArgs pour fournir des données personnalisées sur l'espace disque libre aux gestionnaires d'événements.
Imports System.Collections.Specialized
Imports System.Configuration
Imports System.IO
Public Class DiskSpaceWarningEventArgs : Inherits EventArgs
Dim currentFreeSpace As Long
Dim currentTotalSpace As Long
Dim driveName As String
Public Sub New(name As String, freeSpace As Long, totalSpace As Long)
Me.driveName = name
Me.currentFreeSpace = freeSpace
Me.currentTotalSpace = totalSpace
End Sub
Public ReadOnly Property Name As String
Get
Return Me.driveName
End Get
End Property
Public ReadOnly Property FreeSpace As Long
Get
Return Me.currentFreeSpace
End Get
End Property
Public ReadOnly Property TotalSpace As Long
Get
Return Me.currentTotalSpace
End Get
End Property
End Class
Public Delegate Sub DiskSpaceWarningEventHandler(sender As Object, _
e As DiskSpaceWarningEventArgs)
Public Class DiskSpaceMonitor
Public Event DiskSpaceWarning As DiskSpaceWarningEventHandler
Private threshhold As Decimal
Public Sub New()
' Retrieve threshhold to fire event from configuration file.
Try
Dim settings As NameValueCollection = ConfigurationManager.AppSettings
Me.threshhold = CDec(settings.Item("Threshhold"))
' If there is no configuration file, provide a default value.
Catch e As ConfigurationErrorsException
Me.threshhold = 10d
Catch e As InvalidCastException
Me.threshhold = 10d
End Try
End Sub
Public Sub CheckFreeSpace
' Get drives present on system.
Dim drives() As DriveInfo = DriveInfo.GetDrives()
For Each drive As DriveInfo In drives
If drive.IsReady Then
If drive.TotalFreeSpace/drive.TotalSize <= Me.threshhold Then
OnDiskSpaceWarning(New DiskSpaceWarningEventArgs(drive.Name, _
drive.TotalFreeSpace, drive.TotalSize))
End If
End If
Next
End Sub
Protected Sub OnDiskSpaceWarning(e As DiskSpaceWarningEventArgs)
RaiseEvent DiskSpaceWarning(me, e)
End Sub
End Class
using System;
using System.Collections.Specialized;
using System.Configuration;
using System.IO;
public class DiskSpaceWarningEventArgs : EventArgs
{
private long currentFreeSpace;
private long currentTotalSpace;
private string driveName;
public DiskSpaceWarningEventArgs(string name, long freeSpace, long totalSpace)
{
this.driveName = name;
this.currentFreeSpace = freeSpace;
this.currentTotalSpace = totalSpace;
}
public string Name
{
get { return this.driveName; }
}
public long FreeSpace
{
get { return this.currentFreeSpace; }
}
public long TotalSpace
{
get { return this.currentTotalSpace; }
}
}
public delegate void DiskSpaceWarningEventHandler(object sender,
DiskSpaceWarningEventArgs e);
public class DiskSpaceMonitor
{
public event DiskSpaceWarningEventHandler DiskSpaceWarning;
private decimal threshhold;
public DiskSpaceMonitor()
{
// Retrieve threshhold to fire event from configuration file.
try
{
NameValueCollection settings = ConfigurationManager.AppSettings;
this.threshhold = Convert.ToDecimal(settings["Threshhold"]);
}
// If there is no configuration file, provide a default value.
catch (ConfigurationErrorsException)
{
this.threshhold = 10m;
}
catch (InvalidCastException)
{
this.threshhold = 10m;
}
}
public void CheckFreeSpace()
{
// Get drives present on system.
DriveInfo[] drives = DriveInfo.GetDrives();
foreach (DriveInfo drive in drives)
{
if (drive.IsReady)
{
if (drive.TotalFreeSpace/drive.TotalSize <= this.threshhold)
OnDiskSpaceWarning(new DiskSpaceWarningEventArgs(drive.Name,
drive.TotalFreeSpace, drive.TotalSize));
}
}
}
protected void OnDiskSpaceWarning(DiskSpaceWarningEventArgs e)
{
if (DiskSpaceWarning != null)
DiskSpaceWarning(this, e);
}
}
Au lieu d'utiliser la classe EventArgs pour fournir les données d'événement, l'exemple définit une classe de données d'événement personnalisée nommée DiskSpaceWarningEventArgs. Il fournit aux gestionnaires d'événements le nom de lecteur, ainsi que la quantité d'espace libre et total disponible sur le lecteur. L'exemple définit également un délégué, DiskSpaceWarningEventHandler, qui représente la signature de l'événement.
La classe DiskSpaceMonitor définit l'événement DiskSpaceWarning et fournit également une méthode OnDiskSpaceWarning qui déclenche l'événement. La méthode OnDiskSpaceWarning est, à son tour, appelée par la méthode CheckFreeSpace lorsqu'elle détecte que l'espace libre disponible sur un lecteur est inférieur ou égal à un pourcentage défini dans un fichier de configuration.
Voir aussi
Tâches
Comment : déclencher et utiliser des événements