前のトピック     次のトピック

第 27 章 C++ による VISIO アプリケーションのプログラミング

セクション 3   C++ プログラムでの Visio のイベントの処理

Event オブジェクトを使用して、Visio® のイベントを C++ プログラムで処理することができます。Event オブジェクトでは、イベントとアクションが対になっています。このアクションは、指定したイベントが発生したときにアドオンを実行するか、別のオブジェクトに通知を送るかのどちらかになります。この通知される側のオブジェクトをシンク オブジェクトと呼びます。Microsoft Visual Basic プログラムでの Event オブジェクトの動作、およびその実装方法の詳細については、「第 21 章 Visio のイベントの処理」を参照してください。

Visio エンジンは、コントロールがコントローラ コンテナに提供する標準の IConnectionPoint プロトコルを使って、Visual Basic の WithEvents と同様の形式のイベント処理をサポートします。C++ プログラムは、Event オブジェクトの代わりに IConnectionPoint プロトコルを使って Visio のインスタンスからのイベントを受け取ることができますが、その場合、そのイベントを渡す側の Visio オブジェクトに対して宣言されているイベント セット インターフェース全体を実装する必要があります。IConnectionPoint とその関連するインターフェースの詳細については、COM のマニュアルを参照してください。

このセクションでは、EventList.Add または EventList.AddAdvise を呼び出して作成された Event オブジェクトを使って C++ プログラムで Visio イベントを受け取る方法を説明します。IConnectionPoint は Visio 固有のプロトコルですが、C++ プログラムにイベント セット インターフェース全体を実装する必要はありません。C++ プログラムでは、イベント セット内のすべてのイベントではなく、IConnectionPoint が必要とするイベントだけを登録できます。

このセクションの内容...

シンク オブジェクトの実装

CVisioAddonSink の使用

シンク オブジェクトの実装

C++ プログラムでの Visio のイベントの処理は、Microsoft Visual Basic プログラムでの処理と同じ方法で実装できますが、次の点が異なります。

STDMETHOD(VisEventProc) (
     WORD
     IUnknown FAR*
     DWORD
     DWORD
     IUnknown FAR*
     VARIANT
);


wEvent,
ipSource,
dwEventID,
dwSeq,
ipSubject,
VextraInfo


//Event code of the event that is firing
//Pointer to IUnknown on object firing the event
//The ID of the event that is firing
//The sequence number of the event
//Pointer to IUnknown on event subject
//Additional information (usually a context string)

AddAdvise メソッドを呼び出して Event オブジェクトを作成する場合、シンク オブジェクトの IUnknown または IDispatch インターフェースにポインタを渡します。

TOP へ

CVisioAddonSink の使用

独自のシンク オブジェクトを作成する代わりに、Visio 2000 で提供されている CVisioAddonSink クラスを使用することができます。このクラスは、\DVS\Libraries\C-CPP\Vao_inc にある Addsink.h ファイル内で宣言されています。

CVisioAddonSink を使用するには

  1. プロジェクト ソース ファイルに Addsink.h をインクルードします。Visiwrap.h で定義されているラップ クラスを使用する場合は、この手順は必要ありません。
  2. シンク オブジェクトに送られたイベント通知を受け取るためのコールバック関数を作成します。
  3. コールバック関数へのポインタと IUnknown インターフェースのアドレスを引数に指定して、CoCreateAddonSink インターフェースを呼び出します。CoCreateAddonSink インターフェースは、コールバック関数の情報を持つシンク オブジェクトのインスタンスを作成し、指定されたアドレスにシンク オブジェクトの IUnknown インターフェースへのポインタを返します。
  4. 通知の送信元となる Visio オブジェクトの EventList コレクションへの参照を取得します。
  5. 手順 3 で取得した IUnknown インターフェース、および対象となる Visio のイベントのイベント コードを指定して、手順 4 で取得した EventList コレクションの AddAdvise メソッドを呼び出します。イベントが発生したとき、Visio のインスタンスは手順 2 で作成したコールバック関数を呼び出します。
  6. シンク オブジェクトの使用が終わったら、オブジェクトを解放します。

サンプル プログラム Generic.cpp は CVisioAddonSink クラスを使用して、DocumentCreatedShapeAdded の 2 つのイベントを処理します。このプログラムは、それぞれのイベントについてコールバック関数を宣言しています。コールバック関数のシグネチャは、Addsink.h で定義されている VISEVENTPROC に適合していなければなりません。下の例は、宣言の 1 つを示しています。この関数の実装については、Generic.cpp を参照してください。

HRESULT STDMETHODCALLTYPE ReceiveNotifyFromVisio (

IUnknown FAR*
WORD
IUnknown FAR*
DWORD
DWORD
IUnknown FAR*
VARIANT

IpSink,
wEvent,
ipSource,
nEventID,
dwEventSeq,
ipSubject,
eventExtra);

このプログラムは、シンク オブジェクトを作成するために、Application オブジェクト (CVisioapplication 型変数の app にあたる) の EventList コレクションを取得し、CoCreateAddonSink を呼び出してシンク オブジェクトを作成し、EventList オブジェクトに対して AddAdvise を呼び出して Visio のインスタンスに Event オブジェクトを作成します。プログラムはフラグ bFirstTime に TRUE を設定します。これは、Event オブジェクトがプログラムの実行中に 1 度だけ作成されるようにするためのフラグです。後で参照できるように、Event オブジェクトの ID が静的変数 stc_nEventID に格納されます。AddAdvise の呼び出しによってシンク オブジェクトへのもう 1 つの参照が作成されるので、プログラムは pSink を解放できます。

static long
Iunknown FAR*
Iunknown FAR*
static BOOL
CvisioApplication
CvisioEventList
CvisioEvent
...

stc_nEventID = visEvtIDInval;
pSink = NULL;
pAnotherSink = NULL;
bFirstTime = TRUE;
app;
eList;
event;

if (bFirstTime && (SUCCEEDED(app.EventList(eList))))
{
     bFirstTime= FALSE;
     if (SUCCEEDED(CoCreateAddonSink(ReceiveNotifyFromVisio, &pSink)))
     {
          if (SUCCEEDED(eList.AddAdvise(visEvtCodeDocCreate,
               VVariant(pSink), VBstr(""), VBstr(""), event)))
          {
               event.ID(&stc_nEventID);
          }
          //If AddAdvise succeeded, Visio now holds a reference to the sink object
          //via the event object, and pSink can be released
          pSink->Release();
          pSink= NULL;
     }
...
}

AddAdvise によって作成された Event オブジェクトは、Event オブジェクトが削除され、ソース オブジェクトへのすべての参照が解放されるか、Visio のインスタンスが閉じられるまで持続します。Visio のインスタンスが終了する前にプログラムでなんらかの後処理を行わなければならない場合は、BeforeQuit イベントを使います。

Visio ライブラリ (VSL) で CVisioAddonSink が使用されている場合、そのアンロード ハンドラは Event.Delete を呼び出す必要があります。

Top