IPrintAsyncNotifyChannel
COM公式ドキュメント
印刷スプーラーによってホストされるコンポーネントが、アプリケーションへ通知を送信するために使用する通信チャネルを表します。チャネルが双方向の場合、アプリケーションは同じチャネルを使用して、コンポーネントへ応答を返すことができます。
解説(Remarks)
このインターフェイスを実装するオブジェクトは、印刷スプーラーがホストするコンポーネントによる CreatePrintAsyncNotifyChannel の呼び出しに応じて、印刷スプーラーが作成します。
IPrintAsyncNotifyChannel::Release は、次の場合にのみ呼び出してください。
- 先行する IPrintAsyncNotifyChannel::AddRef の呼び出しと明示的に対応する場合。
- チャネルが単方向 (UniDirectional) チャネルであり、CreatePrintAsyncNotifyChannel の呼び出しが成功して受け取ったポインターを破棄する場合。
- 双方向 (BiDirectional) チャネルを作成した後、または IPrintAsyncNotifyCallback::OnEventNotify の実装内で、次のいずれかに該当する場合。
- IPrintAsyncNotifyChannel::SendNotification または IPrintAsyncNotifyChannel::CloseChannel を呼び出さなかった場合。または
- 失敗した IPrintAsyncNotifyChannel::SendNotification または IPrintAsyncNotifyChannel::CloseChannel の呼び出しを再試行しなかった場合。または
- サーバー側で、戻り値 NO_LISTENER で成功した IPrintAsyncNotifyChannel::SendNotification の呼び出しを再試行しなかった場合。または
- クライアント側で、戻り値 CHANNEL_ACQUIRED で成功した IPrintAsyncNotifyChannel::SendNotification の呼び出しを再試行しなかった場合。
メソッド 2
vtbl = vtable インデックス(0始まり)。HSP等からCOMメソッドをインデックス指定で呼ぶ際に使用します。0〜2 は IUnknown。
印刷スプーラーによってホストされるコンポーネントから、リッスンしている 1 つ以上のアプリケーションへ通知を送信します。または、アプリケーションからコンポーネントへ応答を返します。
| pData | IPrintAsyncNotifyDataObject* | in | 通知の内容と、そのサイズおよび種類へのポインター。 |
戻り値
| HRESULT | 重大度 | 意味 |
|---|---|---|
| S_OK | SUCCESS | 関数は正常に完了しました。 |
| ASYNC_CALL_ALREADY_PARKED | ERROR | 受信側が前の通知をまだ消費していないため、通知を送信できません。 |
| ASYNC_CALL_IN_PROGRESS | ERROR | チャネルは別の通知または応答の処理中です。 |
| ASYNC_NOTIFICATION_FAILURE | ERROR | このチャネル上のリスナーのいずれも、この通知の種類を受信するように構成されていません。または、この呼び出しを完了するために必要なリソースの割り当てに問題が発生しました。 |
| CHANNEL_ACQUIRED | ERROR | 別のリスナーがこのチャネルを取得しました。通知は送信されませんでした。元のリスナーは以後、通知を受信しません。 |
| CHANNEL_ALREADY_CLOSED | ERROR | この呼び出しの前にチャネルが閉じられていたため、通知を送信できませんでした。 |
| CHANNEL_NOT_OPENED | ERROR | この呼び出しの前にチャネルが開かれていなかったため、通知を送信できませんでした。 |
| CHANNEL_WAITING_FOR_CLIENT_NOTIFICATION | ERROR | 直前の通知に対する応答をまだ受信していないため、通知を送信できません。 |
| INVALID_NOTIFICATION_TYPE | ERROR | 指定された通知の種類が無効です。 |
| MAX_NOTIFICATION_SIZE_EXCEEDED | ERROR | 通知データの最大サイズを超えました。既定では、許可される最大データ サイズは 10 メガバイトです。 |
| NO_LISTENERS | SUCCESS | 登録済みのリッスン中アプリケーションが存在しないことを示します。 |
| UNIRECTIONAL_NOTIFICATION_LOST | SUCCESS | 1 つ以上のリスナーがこの通知を受信しませんでしたが、少なくとも 1 つのリスナーはこの通知を受信しました。 |
戻り値は COM エラー コードです。この関数は操作を正常に完了しても S_OK 以外の HRESULT を返す場合があるため、呼び出しの成否を判定するには SUCCEEDED マクロまたは FAILED マクロを使用してください。関数が返した具体的な HRESULT を取得するには、HRESULT_CODE マクロを使用します。次のコード例は、これらのマクロの使用方法を示しています。
その他の戻り値については、PrintAsyncNotifyError を参照してください。
COM エラー コードの詳細については、Error Handling を参照してください。
if (SUCCEEDED(hr)) {
// Call succeeded, check HRESULT value returned
switch (HRESULT_CODE(hr)){
case S_OK:
// Some action
break;
case NO_LISTENERS:
// Some action
break;
case UNIRECTIONAL_NOTIFICATION_LOST:
// Some action
break;
default:
// Default action
break;
}
} else {
// Call failed, check HRESULT value returned
switch (HRESULT_CODE(hr)){
case ASYNC_NOTIFICATION_FAILURE:
// Some action
break;
case CHANNEL_ALREADY_CLOSED:
// Some action
break;
case CHANNEL_NOT_OPENED:
// Some action
break;
//
// ... Test for other error cases
//
default:
// Default action
break;
}
}
解説(Remarks)
単方向チャネルの場合、印刷スプーラーが先行する SendNotification の呼び出しを処理している最中に SendNotification が呼び出されると、印刷スプーラーは保留中の通知をキューに入れます。印刷スプーラーがホストするコンポーネントまたはアプリケーションが IPrintAsyncNotifyChannel::CloseChannel を呼び出すと、キューに入れられた通知は破棄されます。
双方向チャネルの場合、印刷スプーラーが先行する SendNotification の呼び出しを処理している最中に SendNotification が呼び出されると、その保留中の呼び出しは失敗します。この場合、呼び出し元が印刷スプーラー内部の送信側であれば、SendNotification は CHANNEL_WAITING_FOR_CLIENT_NOTIFICATION を返します。呼び出し元が応答を送信するリスナーであれば、SendNotification は ASYNC_CALL_IN_PROGRESS を返します。
同一の双方向チャネルに複数のリスナーが存在する場合、そのチャネルで最初に送信された通知はすべてのリスナーに配信されます。最初に応答したリスナーがそのチャネルを取得します。チャネルが取得された後に SendNotification を呼び出したリスナーは、エラー CHANNEL_ACQUIRED で失敗します。
双方向チャネルで最初の通知を受け取ったリスナーが、そのチャネルの取得を望まない場合もあります。その場合、リスナーは IUnknown::Release メソッドを呼び出すことができます。SendNotification メソッドまたは IPrintAsyncNotifyChannel::CloseChannel メソッドを呼び出す場合は、IUnknown::Release メソッドを呼び出す必要はありません。
チャネルを閉じます。(IPrintAsyncNotifyChannel.CloseChannel)
| pData | IPrintAsyncNotifyDataObject* | in | チャネルが閉じられた理由を指定する通知へのポインター。このポインターは NULL でもかまいません。 |
戻り値
| HRESULT | 重大度 | 意味 |
|---|---|---|
| S_OK | SUCCESS | 関数は正常に完了しました。 |
| CHANNEL_ACQUIRED |
ERROR
または SUCCESS |
このチャネル上の別のリスナーが既に応答しています。送信側との通信を継続できるのは、最初に応答したリスナーだけです。
この HRESULT の重大度が ERROR の場合、呼び出し側の関数はエラー状態を処理する必要があります。 |
| CHANNEL_ALREADY_CLOSED |
ERROR
または SUCCESS |
チャネルは既に閉じられています。チャネルは既に閉じられて解放されているため、この HRESULT が返された場合は IPrintAsyncNotifyChannel::Release を呼び出してはいけません。
この HRESULT の重大度が ERROR の場合、呼び出し側の関数はエラー状態を処理する必要があります。 |
| CHANNEL_CLOSED_BY_ANOTHER_LISTENER | ERROR | 呼び出し元以外のリッスン中アプリケーションが、通信チャネルを閉じました。 |
| CHANNEL_CLOSED_BY_SAME_LISTENER | ERROR | 呼び出し元は既に通信チャネルを閉じています。 |
| INVALID_NOTIFICATION_TYPE | ERROR | 指定された通知の種類が無効です。 |
戻り値は COM エラー コードです。この関数は操作を正常に完了しても S_OK 以外の HRESULT を返す場合があるため、呼び出しの成否を判定するには SUCCEEDED マクロまたは FAILED マクロを使用してください。関数が返した具体的な HRESULT を取得するには、HRESULT_CODE マクロを使用します。次のコード例は、これらのマクロの使用方法を示しています。
その他の戻り値については、PrintAsyncNotifyError を参照してください。
COM エラー コードの詳細については、Error Handling を参照してください。
if (SUCCEEDED(hr)) {
// Call succeeded, check HRESULT value returned
switch (HRESULT_CODE(hr)){
case CHANNEL_ACQUIRED:
// Some action
break;
case CHANNEL_ALREADY_CLOSED:
// Some action
break;
default:
// Default action
break;
}
} else {
// Call failed, check HRESULT value returned
switch (HRESULT_CODE(hr)){
case CHANNEL_CLOSED_BY_ANOTHER_LISTENER:
// Some action
break;
case CHANNEL_CLOSED_BY_SAME_LISTENER:
// Some action
break;
case INVALID_NOTIFICATION_TYPE:
// Some action
break;
case CHANNEL_ACQUIRED:
// This can be an error and a successful return
// some action
break;
case CHANNEL_ALREADY_CLOSED:
// This can be an error and a successful return
// some action
break;
default:
// Default action
break;
}
}
解説(Remarks)
CloseChannel は、通信チャネルのいずれの側からでも呼び出すことができます。つまり、印刷スプーラーによってホストされるコンポーネントからでも、リッスン中のアプリケーションからでも呼び出せます。
印刷スプーラーが先行する SendNotification の呼び出しを処理している最中に IPrintAsyncNotifyChannel::SendNotification が呼び出されると、印刷スプーラーは通知をキューに入れます。印刷スプーラーがホストするコンポーネントまたはアプリケーションが CloseChannel を呼び出すと、キューに入れられた通知は破棄されます。
CloseChannel は、CreatePrintAsyncNotifyChannel の呼び出し直後に呼び出すことはできません。
Microsoft 公式リファレンス: 英語 (en-us) · 日本語 (ja-jp) · 原文ソース (GitHub)
HSP用 COM定義
#usecom / #comfunc によるHSPのCOM呼び出し定義。数字は vtbl インデックス(0始まり)。クラスIDが無い場合 #usecom の末尾は "{}"、ある場合は "{CLSID}"。
#define global IID_IPrintAsyncNotifyChannel "{4A5031B1-1F3F-4DB0-A462-4530ED8B0451}"
#usecom global IPrintAsyncNotifyChannel IID_IPrintAsyncNotifyChannel "{}"
#comfunc global IPrintAsyncNotifyChannel_SendNotification 3 sptr
#comfunc global IPrintAsyncNotifyChannel_CloseChannel 4 sptr
; ※数字は vtbl インデックス(0始まり)。0/1/2 は IUnknown(QueryInterface/AddRef/Release)。
; ※このインターフェースは直接 CoCreateInstance するクラスIDが無いため "{}"(他メソッド/アクティベーションで取得)。
; ※ハンドル/void*等の不透明ポインタは IronHSP では intptr 指定が可能。