Event ステートメント
更新 : 2007 年 11 月
ユーザー定義のイベントを宣言します。
[ <attrlist> ] [ accessmodifier ] _
[ Shared ] [ Shadows ] Event eventname[(parameterlist)] _
[ Implements implementslist ]
' -or-
[ <attrlist> ] [ accessmodifier ] _
[ Shared ] [ Shadows ] Event eventname As delegatename _
[ Implements implementslist ]
' -or-
[ <attrlist> ] [ accessmodifier ] _
[ Shared ] [ Shadows ] Custom Event eventname As delegatename _
[ Implements implementslist ]
[ <attrlist> ] AddHandler(ByVal value As delegatename)
[ statements ]
End AddHandler
[ <attrlist> ] RemoveHandler(ByVal value As delegatename)
[ statements ]
End RemoveHandler
[ <attrlist> ] RaiseEvent(delegatesignature)
[ statements ]
End RaiseEvent
End Event
指定項目
指定項目 |
説明 |
---|---|
attrlist |
省略可能です。このイベントに適用される属性の一覧を指定します。複数の属性を指定するときは、コンマ (,) で区切ります。属性リストは山かっこ ("<" および ">") で囲む必要があります。 |
accessmodifier |
省略可能です。どのようなコードからイベントにアクセスできるのかを指定します。次のいずれかになります。
Protected Friend と指定すると、イベントのクラス、その派生クラス、または同じアセンブリ内のコードからのみアクセスできます。 |
Shared |
省略可能です。このイベントがクラスや構造体の特定のインスタンスに関連付けられていないことを指定します。 |
Shadows |
省略可能です。このイベントが、基本クラスにある、同じ名前を持つプログラミング要素、またはオーバーロードされる要素を宣言し直して隠ぺいすることを示します。宣言された要素は、他の任意の種類の要素でシャドウできます。 シャドウされた要素は、その要素をシャドウする派生クラスからは使用できません。ただし、シャドウする要素がアクセスできない要素の場合は例外です。たとえば、Private 要素が基本クラスの要素をシャドウすると、Private 要素へのアクセス許可を持たないコードは、基本クラスにアクセスします。 |
eventname |
必ず指定します。イベントの名前を指定します。イベントの標準的な名前付け規則に従って名前を付けます。 |
parameterlist |
省略可能です。このイベントのパラメータを表すローカル変数の一覧です。パラメータの一覧 はかっこで囲む必要があります。 |
Implements |
省略可能です。このイベントがインターフェイスのイベントを実装することを示します。 |
implementslist |
Implementsが指定されている場合は、必ず指定します。実装される Sub プロシージャのリストです。複数のプロシージャを指定するときは、コンマ (,) で区切ります。 implementedprocedure [ , implementedprocedure ...] implementedprocedure の構文と指定項目は次のとおりです。 interface.definedname
指定項目説明
interface 必ず指定します。このプロシージャの包含クラスまたは包含構造体が実装しているインターフェイスの名前です。
definedname 必ず指定します。interface の中で、プロシージャを定義するために使われている名前を指定します。これは name、つまり定義されているプロシージャを実装するために、このプロシージャが使用している名前と同じである必要はありません。
|
Custom |
必ず指定します。Custom で宣言されたイベントには、カスタムな AddHandler、RemoveHandler、および RaiseEvent の各アクセサを定義する必要があります。 |
delegatename |
省略可能です。イベント ハンドラのシグネチャを指定するデリゲートの名前です。 |
AddHandler |
必ず指定します。AddHandler アクセサを宣言します。ここにはイベント ハンドラが追加されたとき実行するステートメントを、AddHandler ステートメントを使って明示的に指定するか、Handles 句を使って暗黙的に指定します。 |
End AddHandler |
必ず指定します。AddHandler ブロックを終了します。 |
value |
必ず指定します。パラメータ名です。 |
RemoveHandler |
必ず指定します。RemoveHandler アクセサを宣言します。ここではイベント ハンドラが削除されたときに実行するステートメントを、RemoveHandler ステートメントを使って指定します。 |
End RemoveHandler |
必ず指定します。RemoveHandler ブロックを終了します。 |
RaiseEvent |
必ず指定します。RaiseEvent アクセサを宣言します。ここではイベントが発生したときに実行するステートメントを、RaiseEvent ステートメントを使って指定します。通常は、AddHandler アクセサと RemoveHandler アクセサが保持するリストに含まれるデリゲートが起動されます。 |
End RaiseEvent |
必ず指定します。RaiseEvent ブロックを終了します。 |
delegatesignature |
必ず指定します。delegatename デリゲートに必要なパラメータと一致するパラメータのリストです。パラメータの一覧 はかっこで囲む必要があります。 |
statements |
省略可能です。AddHandler、RemoveHandler、および RaiseEvent の各メソッドの本体に含まれるステートメントです。 |
End Event |
必ず指定します。Event ブロックを終了します。 |
解説
宣言したイベントは、RaiseEvent ステートメントを使って発生させます。通常、イベントの宣言と発生は、次のように行われます。
Public Class EventSource
' Declare an event.
Public Event LogonCompleted(ByVal UserName As String)
Sub CauseEvent()
' Raise an event on successful logon.
RaiseEvent LogonCompleted("AustinSteele")
End Sub
End Class
メモ : |
---|
イベントの引数は、プロシージャの引数と同様に宣言できます。ただし、イベントに対して名前付き引数、ParamArray 引数、または Optional 引数を指定することはできません。イベントは値を返しません。 |
イベントを処理するためには、Handles ステートメントまたは AddHandler ステートメントを使用して、イベント ハンドラをイベントに関連付ける必要があります。サブルーチンとイベントのシグネチャは一致していることが必要です。共有イベントを処理するには、AddHandler ステートメントを使う必要があります。
Event は、モジュール レベルでのみ使用できます。つまり、イベントの宣言コンテキストは、クラス、構造体、モジュール、またはインターフェイスであることが必要で、ソース ファイル、名前空間、プロシージャ、ブロックでは宣言できません。詳細については、「宣言コンテキストと既定のアクセス レベル」を参照してください。
ほとんどの状況で、このトピックの「構文」のセクションにある最初の構文を使ってイベントを宣言できますが、一部のシナリオでは、イベントの動作をより詳細に制御することが必要になります。このトピックの「構文」セクションの最後に Custom キーワードを使用した構文がありますが、これを使用すると、カスタム イベントを定義してイベントを詳細に制御できます。カスタム イベントでは、コードでイベント ハンドラを追加または削除するときに、つまりコードでイベントを生成するときに、何が起こるかを正確に指定します。使用例については、「方法 : メモリの使用量を節約するイベントを宣言する」および「方法 : ブロックを回避するイベントを宣言する」を参照してください。
使用例
次の例では、イベントを使用して 10 秒から 0 秒までをカウントダウンします。このコードは、イベント関連のいくつかのメソッド、プロパティ、ステートメントの例を示しています。RaiseEvent ステートメントの使用例も含まれています。
イベントを発生させるクラスをイベント ソース、イベントを処理するメソッドをイベント ハンドラと呼びます。イベント ソースには、そこで生成される複数のイベント ハンドラを設定できます。クラスでイベントが発生すると、そのイベントは、オブジェクトのインスタンスに対するイベントを処理するために選択されたすべてのクラスで発生します。
また、このコード例では、ボタン (Button1) および テキスト ボックス (TextBox1) のあるフォーム (Form1) を使用します。ボタンをクリックすると、10 秒から 0 秒までカウント ダウンする最初のテキスト ボックスが表示されます。カウント時間 (10 秒) が経過すると、最初のテキスト ボックスに "Done" と表示されます。
Form1 のコードでは、フォームの初期状態と終了状態を指定します。イベント発生時に実行されるコードも含まれます。
この例を使用するには、新しい Windows Forms プロジェクトを開きます。次に、Button1 という名前のボタンと TextBox1 という名前のテキスト ボックスを、Form1 という名前のメイン フォームに追加します。続いてフォームを右クリックし、[コードの表示] をクリックして、コード エディタを開きます。
Form1 クラスの宣言セクションに、WithEvents 変数を追加します。
Private WithEvents mText As TimerState
Form1 のコードに以下のコードを追加します。Form_Load や Button_Click など、重複して存在する可能性のあるプロシージャを置き換えます。
Private Sub Form1_Load(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles MyBase.Load
Button1.Text = "Start"
mText = New TimerState
End Sub
Private Sub Button1_Click(ByVal sender As System.Object, _
ByVal e As System.EventArgs) _
Handles Button1.Click
mText.StartCountdown(10.0, 0.1)
End Sub
Private Sub mText_ChangeText() Handles mText.Finished
TextBox1.Text = "Done"
End Sub
Private Sub mText_UpdateTime(ByVal Countdown As Double) _
Handles mText.UpdateTime
TextBox1.Text = Format(Countdown, "##0.0")
' Use DoEvents to allow the display to refresh.
My.Application.DoEvents()
End Sub
Class TimerState
Public Event UpdateTime(ByVal Countdown As Double)
Public Event Finished()
Public Sub StartCountdown(ByVal Duration As Double, _
ByVal Increment As Double)
Dim Start As Double = DateAndTime.Timer
Dim ElapsedTime As Double = 0
Dim SoFar As Double = 0
Do While ElapsedTime < Duration
If ElapsedTime > SoFar + Increment Then
SoFar += Increment
RaiseEvent UpdateTime(Duration - SoFar)
End If
ElapsedTime = DateAndTime.Timer - Start
Loop
RaiseEvent Finished()
End Sub
End Class
F5 キーを押して上のコード例を実行し、"Start" というラベルのボタンをクリックしてください。最初のテキスト ボックスが、秒のカウント ダウンを開始します。カウント時間 (10 秒) が経過すると、最初のテキスト ボックスに "Done" と表示されます。
メモ : |
---|
My.Application.DoEvents メソッドがイベントを処理する方法は、フォームと同じではありません。フォームがイベントを直接処理するようにするには、マルチスレッドを使用します。詳細については、「Visual Basic におけるマルチスレッド」を参照してください。 |