Win32 API 日本語リファレンス
ホームSystem.Com › IMoniker

IMoniker

COM
IID0000000f-0000-0000-c000-000000000046継承元IPersistStream自前メソッド開始 vtbl8

公式ドキュメント

COM オブジェクトを一意に識別する情報を保持する moniker オブジェクトを利用できるようにします。

解説(Remarks)

ファイルシステムにおけるファイルへのパスと同様に、moniker には COM オブジェクトを特定してアクティブ化するための情報が含まれます。moniker は、ファイルに格納されたドキュメントオブジェクトから、埋め込みオブジェクト内の選択範囲まで、あらゆる種類の COM オブジェクトを識別できます。COM は、システム内で最も一般的に見られるオブジェクトを識別する moniker オブジェクトを作成するための一連の moniker クラスを提供します。たとえば、ファイルに格納されたテキストドキュメントに埋め込まれたスプレッドシート内のセル範囲を表すオブジェクトが存在する場合があります。分散システムでは、このオブジェクトの moniker は、オブジェクトのシステムの場所、そのシステム上のファイルの物理的な場所、そのファイル内の埋め込みオブジェクトのストレージ、そして最後に埋め込みオブジェクト内のセル範囲の場所を識別します。

moniker オブジェクトは IMoniker インターフェイスをサポートします。このインターフェイスは IPersistStream インターフェイスから派生しており、システム内の単一のオブジェクトを一意に識別します。moniker を提供するオブジェクトが moniker オブジェクトを作成した後は、その情報をオブジェクト内で変更することはできません。moniker プロバイダーが情報を変更するには、新しい moniker オブジェクトを作成するしかありません。新しい moniker オブジェクトが、対象のオブジェクトを一意に識別することになります。

moniker には次の 2 つの重要な機能があります。

Anti-Moniker の実装

anti-moniker は、ファイル moniker、item moniker、ポインター moniker の COM 実装の逆です。つまり、ファイル moniker、item moniker、またはポインター moniker の右側に合成された anti-moniker は、何も残らないように合成されます。

moniker クライアントの場合、通常 anti-moniker を使用する必要はありません。moniker の逆が必要な場合は、IMoniker::Inverse を呼び出してください。たとえば、複合 moniker の最後の要素を削除するために逆が必要な場合は、IMoniker::Enum を使用して moniker の各要素を列挙し、最も右側の要素に対して Inverse を呼び出します。複合 moniker の最も右側の要素が anti-moniker を自身の逆とみなすとは限らないため、この目的で anti-moniker を使用しないでください。

anti-moniker を明示的に使用すべき唯一の状況は、新しい moniker クラスを作成していて、その moniker の逆を構築するための特別な要件がない場合です。その場合は、Inverse の実装から anti-moniker を返すことができます。そして IMoniker::ComposeWith の実装では、遭遇した anti-moniker ごとに自身の moniker の 1 つを打ち消す必要があります。

これらの moniker を作成するには、CreateAntiMoniker 関数を使用します。

Class Moniker の実装

class moniker は、オブジェクトクラスを表す moniker です。class moniker は、それが作成されたクラスのクラスオブジェクトにバインドします。

class moniker は、ファイル moniker や item moniker などの他の種類の moniker との合成において最も有用です。class moniker は、IClassActivator インターフェイスへのバインドをサポートする moniker の右側に合成することもできます。これにより、IClassActivator はクラスオブジェクトおよびクラスのインスタンスへのアクセスを提供できます。

class moniker を使用するには、CreateClassMoniker 関数を使用してこれらの moniker を作成する必要があります。

File Moniker の実装

ファイル moniker は、ファイルシステム内のパスを表す moniker です。ファイル moniker は、独自のファイルに保存されたあらゆるオブジェクトを識別できます。ファイル内に含まれるオブジェクトを識別するには、ファイル moniker の右側に他のクラスの moniker(たとえば item moniker)を合成できます。ただし、複合 moniker 内でファイル moniker の左側に置ける moniker は、別のファイル moniker、anti-moniker、または class moniker でなければなりません。たとえば、複合 moniker 内でファイル moniker の左側に item moniker が現れることは不正です。

なお、anti-moniker はファイル moniker 全体の逆であり、moniker が表すパスの一部の逆ではありません。つまり、ファイル moniker の右側に anti-moniker を合成すると、ファイル moniker 全体が削除されます。ファイル moniker が表すパスの最も右側の要素だけを削除したい場合は、".." パスに基づく別のファイル moniker を作成し、それをファイル moniker の末尾に合成する必要があります。

moniker クライアント(moniker を使用してオブジェクトへのインターフェイスポインターを取得する側)は、通常、moniker のクラスを知る必要はありません。単に IMoniker インターフェイスポインターを使用してメソッドを呼び出せます。

moniker プロバイダー(自身のオブジェクトを識別する moniker を配布して、moniker クライアントからアクセスできるようにする側)は、識別するオブジェクトがファイルに格納されている場合、ファイル moniker を使用する必要があります。各オブジェクトが独自のファイルに存在する場合、必要なのはファイル moniker のみです。識別するオブジェクトがファイルより小さい場合は、ファイル moniker に加えて別の種類の moniker(たとえば item moniker)を使用する必要があります。

ファイル moniker を使用するには、CreateFileMoniker 関数を使用して moniker を作成する必要があります。ファイル moniker がバインドされたときにオブジェクトを読み込めるようにするには、オブジェクトが IPersistFile インターフェイスを実装している必要があります。

moniker プロバイダーの最も一般的な例は、リンクをサポートする COM サーバーアプリケーションです。COM サーバーアプリケーションがファイルベースのドキュメント全体へのリンクのみをサポートする場合、必要な moniker はファイル moniker のみです。COM サーバーアプリケーションがドキュメントより小さいオブジェクト(ドキュメントの一部や埋め込みオブジェクトなど)へのリンクをサポートする場合は、ファイル moniker に加えて item moniker も使用する必要があります。

Generic Composite Moniker の実装

generic composite moniker(汎用複合 moniker)は、各構成要素が互いについての特別な知識を持たない複合 moniker です。

合成とは、2 つの moniker を結合する処理です。特定のクラスの 2 つの moniker が特別な方法で結合できる場合があります。たとえば、不完全なパスを表すファイル moniker と相対パスを表す別のファイル moniker を結合して、完全なパスを表す単一のファイル moniker を形成できます。これは非汎用合成の例です。一方、汎用合成は、クラスに関係なく任意の 2 つの moniker を接続できます。非汎用合成は関与する moniker のクラスに依存するため、特定のクラスによる IMoniker::ComposeWith メソッドの実装によってのみ実行できます。新しい moniker クラスを作成する場合、新しい種類の非汎用合成を定義できます。これに対して、汎用合成は CreateGenericComposite 関数によって実行されます。

moniker クライアント(moniker を使用してオブジェクトへのインターフェイスポインターを取得する側)は、通常、moniker のクラスや、それが汎用複合か非汎用複合かを知る必要はありません。単に IMoniker インターフェイスポインターを使用してメソッドを呼び出せます。

moniker プロバイダー(自身のオブジェクトを識別する moniker を配布して、moniker クライアントからアクセスできるようにする側)は、2 つの moniker を合成する必要がある場合があります。(たとえば、item moniker を使用してオブジェクトを識別する場合、それを配布する前にオブジェクトのコンテナーを識別する moniker と合成する必要があります。) これを行うには IMoniker::ComposeWith メソッドを使用し、最初の moniker に対してメソッドを呼び出して 2 番目の moniker をパラメーターとして渡します。このメソッドは、汎用複合または非汎用複合のいずれかを生成することがあります。

generic composite moniker を明示的に作成すべき唯一の場面は、独自の moniker クラスを作成しているときです。IMoniker::ComposeWith の実装では、可能な限り非汎用合成を実行するよう試みるべきです。非汎用合成を実行できず、汎用合成が許容される場合は、CreateGenericComposite 関数を呼び出して generic composite moniker を作成できます。

Item Moniker の実装

item moniker は、ドキュメントの一部、複合ドキュメント内の埋め込みオブジェクト、スプレッドシート内のセル範囲など、コンテナー内のオブジェクトを識別するために使用されます。item moniker は、しばしばファイル moniker と組み合わせて使用されます。ファイル moniker がコンテナーを識別するために使用され、item moniker がコンテナー内の項目を識別するために使用されます。

item moniker にはテキスト文字列が含まれます。この文字列は、コンテナーオブジェクトが含まれる項目を他の項目と区別するために使用されます。コンテナーオブジェクトは IOleItemContainer インターフェイスを実装している必要があります。このインターフェイスにより、item moniker のコードは、オブジェクトを識別する文字列だけをもとにオブジェクトへのポインターを取得できます。

moniker クライアント(moniker を使用してオブジェクトへのインターフェイスポインターを取得する側)は、通常、moniker のクラスを知る必要はありません。単に IMoniker インターフェイスポインターを使用してメソッドを呼び出せます。

moniker プロバイダー(自身のオブジェクトを識別する moniker を配布して、moniker クライアントからアクセスできるようにする側)は、識別するオブジェクトが別のオブジェクト内に含まれ、文字列を使用して個別に識別できる場合、item moniker を使用する必要があります。コンテナーオブジェクトを識別するには、別の種類の moniker(たとえばファイル moniker)を使用します。

item moniker を使用するには、CreateItemMoniker 関数を使用して moniker を作成する必要があります。item moniker がバインドされたときにオブジェクトを読み込めるようにするには、オブジェクトのコンテナーが IOleItemContainer インターフェイスを実装している必要があります。

moniker プロバイダーの最も一般的な例は、リンクをサポートする COM アプリケーションです。COM アプリケーションがファイルベースのドキュメントより小さいオブジェクトへのリンクをサポートする場合、item moniker を使用する必要があります。ドキュメント内の選択範囲へのリンクを許可するサーバーアプリケーションでは、item moniker を使用してそれらのオブジェクトを識別します。埋め込みオブジェクトへのリンクを許可するコンテナーアプリケーションでは、item moniker を使用して埋め込みオブジェクトを識別します。

OBJREF Moniker の実装

OBJREF moniker は、ローカルまたはリモートのアウトオブプロセスサーバー上で実行中のオブジェクトインスタンスへの参照を表します。この moniker は、オブジェクトインスタンスと、そのオブジェクトが実行されているコンピューターを識別します。

OBJREF moniker は多くの点でポインター moniker に似ていますが、実行中のオブジェクトがアウトオブプロセスである点が異なります。クライアントは OBJREF moniker に対して IMoniker::BindToObject を呼び出し、取得したポインターを使用して、場所に関係なく実行中のオブジェクトにアクセスできます。

ポインター moniker との重要な違いは、OBJREF moniker の表示名を HTML ページに埋め込むことができ、moniker が表す実行中のオブジェクトをクライアントスクリプト、アプレット、または ActiveX コントロールからバインドできる点です。

OBJREF moniker の主な用途は、インターネット経由で実行中のオブジェクトインスタンスへのアクセスを取得することです。アクティブサーバーページやその他の動的 HTML コンテンツ生成手段が、OBJREF moniker の表示名をアプレットまたは ActiveX コントロールのパラメーターに配置します。アプレットまたはコントロールのコードは CreateObjrefMoniker 関数を呼び出して表示名に基づく OBJREF moniker を作成し、続いてその OBJREF moniker に対して IMoniker::BindToObject を呼び出して、実行中のオブジェクトインスタンスへのアクセスを取得します。その後、アクティブサーバーページは、実行中のオブジェクトへのポインターをページのクライアントにマーシャリングして返します。

Pointer Moniker の実装

ポインター moniker は、本質的にインターフェイスポインターをラップして moniker のように見せかけ、moniker を必要とするインターフェイスに渡せるようにします。ポインター moniker のバインドは、そのポインターの QueryInterface メソッドを呼び出すことで行われます。

ポインター moniker のインスタンスはシリアル化を拒否します。つまり、IPersistStream::Save はエラーを返します。ただし、これらの moniker は RPC 呼び出しで別のプロセスにマーシャリングできます。内部的には、システムはインターフェイスポインターをマーシャリングする標準的なパラダイムを使用してポインターをマーシャリングおよびアンマーシャリングします。

ポインター moniker が必要になることはまれです。永続的な表現を持たないオブジェクトを識別する moniker が必要な場合にのみ、ポインター moniker を使用します。ポインター moniker により、そのようなオブジェクトが moniker バインド操作に参加できるようになります。

URL Moniker の実装

IMoniker の URL moniker 実装は URL moniker オブジェクト上にあります。このオブジェクトは IUnknown および IAsyncMoniker インターフェイスもサポートします。IMoniker インターフェイスは、その定義を IPersistStreamIUnknown から継承し、IPersistStreamIPersist から継承します。したがって、IMoniker の実装には IPersistStreamIPersist のサポートが含まれます。

IAsyncMoniker インターフェイスは単なる IUnknown です。(追加のメソッドはありません。) これは、moniker が非同期バインドをサポートするかどうかをクライアントが判断できるようにするために使用されます。

このオブジェクトの IMoniker インターフェイスへのポインターを取得するには、CreateURLMonikerEx 関数を呼び出します。

moniker クライアント(moniker を使用してオブジェクトへのインターフェイスポインターを取得する側)は、通常、使用している moniker のクラスを知る必要はありません。単に IMoniker インターフェイスポインターを使用してメソッドを呼び出せます。

moniker プロバイダー(自身のオブジェクトを識別する moniker を配布して、moniker クライアントからアクセスできるようにする側)は、識別するオブジェクトが別のオブジェクト内に含まれ、文字列を使用して個別に識別できる場合、item moniker を使用する必要があります。また、コンテナーオブジェクトを識別するために別の種類の moniker(たとえばファイル moniker)も使用する必要があります。

item moniker を使用するには、CreateItemMoniker 関数を使用して moniker を作成する必要があります。item moniker がバインドされたときにオブジェクトを読み込めるようにするには、オブジェクトのコンテナーが IOleItemContainer インターフェイスを実装している必要があります。

moniker プロバイダーの最も一般的な例は、リンクをサポートする COM アプリケーションです。COM アプリケーションがファイルベースのドキュメントより小さいオブジェクトへのリンクをサポートする場合、item moniker を使用する必要があります。ドキュメント内の選択範囲へのリンクを許可するサーバーアプリケーションでは、item moniker を使用してそれらのオブジェクトを識別します。埋め込みオブジェクトへのリンクを許可するコンテナーアプリケーションでは、item moniker を使用して埋め込みオブジェクトを識別します。

メソッド 15

vtbl = vtable インデックス(0始まり)。HSP等からCOMメソッドをインデックス指定で呼ぶ際に使用します。0〜2 は IUnknown。

vtbl 8 HRESULT BindToObject(IBindCtx* pbc, IMoniker* pmkToLeft, GUID* riidResult, void** ppvResult)

指定されたオブジェクトにバインドします。バインド処理では、オブジェクトを見つけ、必要に応じて実行状態にし、識別されたオブジェクトの指定されたインターフェイスへのポインターを呼び出し元に提供します。

pbcIBindCtx*inこのバインド操作で使用されるバインドコンテキストオブジェクトの IBindCtx インターフェイスへのポインターです。バインドコンテキストは、バインド処理中にバインドされたオブジェクトをキャッシュし、そのバインドコンテキストを使用するすべての操作に適用されるパラメーターを保持し、moniker の実装が自身の環境に関する情報を取得する手段を提供します。
pmkToLeftIMoniker*inoptionalmoniker が複合 moniker の一部である場合、この moniker の左側にある moniker へのポインターです。このパラメーターは主に moniker の実装者が、複合 moniker の各構成要素間の連携を可能にするために使用します。moniker クライアントは NULL を使用してください。
riidResultGUID*inmoniker が識別するオブジェクトとの通信に使用したいインターフェイスの IID です。
ppvResultvoid**outriid で要求されたインターフェイスポインターを受け取るポインター変数のアドレスです。正常に返された場合、ppvResult には moniker が識別するオブジェクトへの要求されたインターフェイスポインターが格納されます。成功した場合、実装は moniker に対して AddRef を呼び出す必要があります。Release を呼び出すのは呼び出し元の責任です。エラーが発生した場合、ppvResultNULL でなければなりません。

戻り値

このメソッドは、標準の戻り値 E_OUTOFMEMORY および E_UNEXPECTED のほか、次の値を返すことがあります。

戻り値 説明
S_OK
バインド操作は成功しました。
MK_E_NOOBJECT
この moniker が識別するオブジェクト、またはこの moniker が一部を構成する複合 moniker が識別する何らかのオブジェクトが見つかりませんでした。
MK_E_EXCEEDEDDEADLINE
バインドコンテキストの BIND_OPTS 構造体で指定された制限時間内にバインド操作を完了できませんでした。
MK_E_CONNECTMANUALLY
バインド操作にはエンドユーザーの支援が必要です。この値が返される最も一般的な理由は、パスワードが必要な場合、またはフロッピーをマウントする必要がある場合です。この値が返された場合、キー "ConnectManually" を指定して IBindCtx::GetObjectParam を呼び出し、エラーの原因となった moniker を取得します。その後、IMoniker::GetDisplayName を呼び出して表示名を取得し、フロッピーのマウント指示やパスワードの要求など、必要な情報を伝えるダイアログボックスを表示してから、バインド操作を再試行できます。
MK_E_INTERMEDIATEINTERFACENOTSUPPORTED
中間オブジェクトが見つかりましたが、バインド操作を完了するために必要なインターフェイスをサポートしていませんでした。たとえば、item moniker は、そのコンテナーが IOleItemContainer インターフェイスをサポートしていない場合、この値を返します。
STG_E_ACCESSDENIED
ストレージオブジェクトにアクセスできませんでした。

このメソッドは、IOleItemContainer::GetObject メソッドに関連するエラーを返すこともあります。

解説(Remarks)

BindToObject は moniker の主要な機能を実装します。すなわち、moniker が識別するオブジェクトを特定し、そのインターフェイスの 1 つへのポインターを返すことです。

呼び出し元への注意

2 つのオブジェクト間の永続的な接続として moniker を使用している場合は、BindToObject を呼び出して接続をアクティブ化します。

通常、次の手順で BindToObject を呼び出します。

  1. CreateBindCtx 関数を呼び出してバインドコンテキストオブジェクトを作成します。
  2. moniker を使用して BindToObject を呼び出し、識別されたオブジェクトの目的のインターフェイスへのポインターを取得します。
  3. バインドコンテキストを解放します。
  4. 取得したインターフェイスポインターを通じて、オブジェクトに対して目的の操作を実行します。
  5. オブジェクトの使用が完了したら、オブジェクトのインターフェイスポインターを解放します。
次のコードフラグメントは、これらの手順を示しています。
HRESULT hr;       // An error code
IMoniker * pMnk;  // A previously acquired interface moniker

// Obtain an IBindCtx interface.
IBindCtx * pbc; 
hr = CreateBindCtx(NULL, &pbc); 
if (FAILED(hr)) exit(0);  // Handle errors here. 
   
// Obtain an implementation of pCellRange. 
ICellRange * pCellRange; 
hr = pMnk->BindToObject(pbc, NULL, IID_ICellRange, &pCellRange); 
if (FAILED(hr)) exit(0);  // Handle errors here. 

// Use pCellRange here. 

// Release interfaces after use. 
pbc->Release(); 
pCellRange->Release(); 

バインド操作が 1 回だけで、バインドコンテキストオブジェクトを保持する必要がない場合は、BindMoniker 関数を使用することもできます。このヘルパー関数は、バインドコンテキストの作成、BindToObject の呼び出し、およびバインドコンテキストの解放をカプセル化します。

オブジェクトへのリンクをサポートする COM コンテナーは、moniker を使用してリンク先のオブジェクトを特定してアクセスしますが、通常は BindToObject を直接呼び出しません。代わりに、ユーザーがコンテナー内のリンクをアクティブ化すると、リンクコンテナーは通常、リンクハンドラーの実装を使用して IOleObject::DoVerb を呼び出します。この実装は、(自身で動詞を処理できない場合)リンクされたオブジェクトに格納された moniker に対して BindToObject を呼び出します。

実装者への注意

実装が行うべき内容は、moniker にプレフィックスがあると想定するかどうか、つまり pmkToLeft パラメーターが NULL になるかどうかによって異なります。たとえば、コンテナー内のオブジェクトを識別する item moniker は、pmkToLeft がコンテナーを識別することを想定しています。したがって item moniker は、そのコンテナーからサービスを要求するために pmkToLeft を使用します。moniker にプレフィックスがあると想定する場合は、pmkToLeft パラメーターを使用して(たとえば、それに対して BindToObject を呼び出して)、それが識別するオブジェクトからサービスを要求すべきです。

moniker にプレフィックスがないと想定する場合、BindToObject の実装ではまず実行中オブジェクトテーブル(ROT)を確認して、オブジェクトが既に実行中かどうかを調べるべきです。ROT へのポインターを取得するには、pbc パラメーターに対して IBindCtx::GetRunningObjectTable を呼び出します。次に IRunningObjectTable::GetObject メソッドを呼び出して、現在の moniker が ROT に登録されているかどうかを確認できます。登録されている場合は、直ちに QueryInterface を呼び出して、呼び出し元が要求したインターフェイスへのポインターを取得できます。

BindToObject の実装が何らかのオブジェクトにバインドする場合、pbc パラメーターを使用して IBindCtx::RegisterObjectBound を呼び出し、バインドされたオブジェクトへの参照をバインドコンテキストに格納すべきです。これにより、バインドコンテキストが解放されるまでバインドされたオブジェクトが実行状態を維持し、後続のバインド操作で再度読み込む手間を回避できます。

バインドコンテキストの BIND_OPTS 構造体が BINDFLAGS_JUSTTESTEXISTENCE フラグを指定している場合、実装は ppvResultNULL を返すことを選択できます(ただし、このフラグを無視して完全なバインド操作を実行することもできます)。

実装固有の注意

実装 注意
Anti-moniker このメソッドは実装されていません。E_NOTIMPL を返します。
Class moniker pmkLeftNULL の場合、class moniker が(CreateClassMoniker または MkParseDisplayName を通じて)初期化された CLSID と、現在の pbc(IBindCtx)の CLSCTX を使用して CoGetClassObject を呼び出します。

pmkLeft が非 NULL の場合、IClassActivator を求めて pmkLeft->BindToObject を呼び出し、初期化された CLSID と、現在の pbc(IBindCtx)の CLSCTX およびロケールパラメーターを指定して IClassActivator::GetClassObject を呼び出します。

File moniker pmkToLeftNULL の場合、このメソッドは ROT 内で moniker を探し、見つかった場合は取得したオブジェクトに対して要求されたインターフェイスポインターをクエリします。ROT 内で moniker が見つからない場合は、ファイルシステムからオブジェクトを読み込み、要求されたインターフェイスポインターを取得します。

pmkLeftNULL でない場合、GetClassFile(またはその他の手段)を使用してファイル moniker が参照するファイルの内容でインスタンス化および初期化するクラスを決定する代わりに、IClassFactory および IClassActivator を求めて pmkLeft->BindToObject を呼び出し、このポインターを pcf で取得します。これが E_NOINTERFACE で失敗した場合は、MK_E_INTERMEDIATEINTERFACENOTSUPPORTED を返します。

IClassFactory ポインターの取得に成功した場合は、pcf->CreateInstance(IID_IPersistFile, (void**)&ppf) を呼び出して初期化するクラスの新しいインスタンスを取得し、ファイル moniker の既存の初期化パスに従って IPersistFile またはその他の適切な手段を使用して初期化します。

Generic composite moniker pmkToLeftNULL の場合、このメソッドは ROT 内で moniker を探し、見つかった場合は取得したオブジェクトに対して要求されたインターフェイスポインターをクエリします。pmkToLeftNULL でない場合、このメソッドは複合 moniker の最も右側の要素に対して再帰的に BindToObject を呼び出し、残りの複合 moniker をその呼び出しの pmkToLeft パラメーターとして渡します。
Item moniker pmkToLeftNULL の場合、このメソッドは E_INVALIDARG を返します。そうでない場合、このメソッドは pmkToLeft パラメーターに対して BindToObject を呼び出し、IOleItemContainer インターフェイスポインターを要求します。次に IOleItemContainer::GetObject を呼び出し、moniker 内に含まれる文字列を渡して、要求されたインターフェイスポインターを返します。
OBJREF moniker pmkToLeft パラメーターは NULL でなければなりません。OBJREF moniker は実行中のオブジェクトを表すため、アクティブ化は行われません。表現されるオブジェクトがもはや実行されていない場合、BindToObjectE_UNEXPECTED で失敗します。
Pointer moniker このメソッドは、ラップされたポインターに対して要求されたインターフェイスをクエリします。
URL moniker URL Moniker は非同期バインドをサポートするため、BindToObject の実際の戻り値は、バインドコンテキストで設定されたオブジェクトパラメーターによって異なる場合があります。詳細については、以下を参照してください。

URL moniker のバインド操作のセマンティクスは、同期使用か非同期使用かに関係なく同一であり、次のとおりです。

  1. URL moniker は、バインド操作のためのさらなる情報をバインドコンテキストから取得します。たとえば、moniker はバインドコンテキストに登録された IBindStatusCallback および IEnumFORMATETC インターフェイスへのポインターを取得できます。さらなる情報には、IBindCtx::SetBindOptions を通じてバインドコンテキストに指定された追加のバインドオプション(dwTickCountDeadline パラメーターや BIND_MAYBOTHERUSERgrfFlags 値など)が含まれる場合があります。
  2. 次に moniker は、バインドコンテキストの ROT を確認して、参照先のオブジェクトが既に実行中かどうかを判断します。moniker は次の呼び出しでこの情報を取得できます。
    IBindCtx::GetRunningObjectTable(&prot)
    prot->IsRunning(this)
    
  3. オブジェクトが既に実行中の場合、moniker は次の呼び出しで実行中のオブジェクトを取得します。
    prot->GetObject(this, &punk)
    
  4. その後、moniker は要求されたインターフェイスに対して QueryInterface を呼び出します。
  5. そうでない場合、moniker は IBindStatusCallback::GetBindInfo を呼び出してクライアントに問い合わせ、追加のバインド情報を取得します。次に moniker はバインド操作を開始し、結果として得られる IBinding インターフェイスを IBindStatusCallback::OnStartBinding を呼び出してクライアントに返します。
  6. 手順 1 でこれが非同期バインドであると判断された場合、BindToObject はこの時点で ppvNULL を格納して MK_S_ASYNCHRONOUS を返します。呼び出し元は、後の時点で IBindStatusCallback::OnObjectAvailable メソッド中に実際のオブジェクトポインターを受け取ります。以降の手順は、通常は別の実行スレッド上で、呼び出し元に対して非同期に実行されます。
  7. URL Moniker が指定するリソースのクラスは、次のいずれかの方法で決定されます。
    • URL moniker はデータのメディアタイプを調べます。メディアタイプが application/x-oleobject の場合、実際のデータ(Content-Body)の先頭 16 バイトにはリソースの CLSID が含まれ、後続のデータはクラス自身によって解釈されます。それ以外のすべてのメディアタイプについては、URL Moniker はシステムレジストリの HKEY_CLASSES_ROOT\MIME\Database\Content-Type\<media-type>\CLSID キーを調べます。なお、application/oleobject が承認されるまでは application/x-oleobject が使用されます。
    • URL moniker は、到着したデータの一部を、システムレジストリの HKEY_CLASSES_ROOT\FileTypes に登録されたパターンと照合します。
    • 最後に、他のすべてが失敗した場合、URL Moniker は、GetClassFile やシェルが行うのと同様に、システムレジストリの HKEY_CLASSES_ROOT\.??? キーを使用して、リソースの末尾の拡張子(存在する場合)を CLSID に対応付けます。
  8. クラスを決定した後、URL moniker は IUnknown インターフェイスを要求して CLSCTX_SERVERCoCreateInstance を使用してインスタンスを作成します。
  9. 次に URL moniker は、新しく作成したオブジェクトの QueryInterface メソッドを呼び出して IPersistMoniker インターフェイスを取得しようとします。QueryInterface が成功した場合、URL moniker は自身(this)を moniker パラメーターとして渡して IPersistMoniker::Load を呼び出します。オブジェクトは通常、関心のあるストレージインターフェイスを求めて BindToStorage を呼び出します。
  10. そうでない場合、URL moniker は IPersistStream に対して QueryInterface を呼び出し、成功した場合は IPersistStream::Load を呼び出して、トランスポートによって非同期に満たされるストリームオブジェクトの IStream ポインターをオブジェクトに渡します。

    呼び出されるクラスがカテゴリ CATID_AsyncAware でマークされていない場合、まだ利用できないデータを参照する ISequentialStream::Read または ISequentialStream::Write の呼び出しは、データが利用可能になるまでブロックします。これらの呼び出しは、従来の COM の意味でブロックします。特定のメッセージを処理できるメッセージループに入り、スレッドの IMessageFilter が適切に呼び出されます。

    クラスがカテゴリ CATID_AsyncAware でマークされている場合、まだ利用できないデータを参照する ISequentialStream::Read または ISequentialStream::Write の呼び出しは E_PENDING を返します。

  11. そうでない場合、URL moniker は IPersistFile に対して QueryInterface を呼び出し、成功した場合は一時ファイルへのダウンロードを完了します。完了時に、URL moniker は IPersistFile::Load を呼び出します。作成されたファイルは、他のインターネットからダウンロードしたデータと共にキャッシュされます。クライアントは、このファイルを削除しないよう注意する必要があります。
  12. 前述の手順で説明したいずれかの Load 呼び出しからオブジェクトが返ると、URL moniker は IBindStatusCallback::OnObjectAvailable メソッドを呼び出して、クライアントが BindToObject を呼び出したときに最初に要求したインターフェイスポインターを返します。
vtbl 9 HRESULT BindToStorage(IBindCtx* pbc, IMoniker* pmkToLeft, GUID* riid, void** ppvObj)

指定されたオブジェクトのストレージにバインドします。IMoniker::BindToObject メソッドとは異なり、このメソッドは moniker が識別するオブジェクトをアクティブ化しません。

pbcIBindCtx*inこのバインド操作で使用されるバインドコンテキストオブジェクトの IBindCtx インターフェイスへのポインターです。バインドコンテキストは、バインド処理中にバインドされたオブジェクトをキャッシュし、そのバインドコンテキストを使用するすべての操作に適用されるパラメーターを保持し、moniker の実装が自身の環境に関する情報を取得する手段を提供します。
pmkToLeftIMoniker*inoptionalmoniker が複合 moniker の一部である場合、この moniker の左側にある moniker へのポインターです。このパラメーターは主に moniker の実装者が、複合 moniker の各構成要素間の連携を可能にするために使用します。moniker クライアントは NULL を使用してください。
riidGUID*in要求するストレージインターフェイスの識別子への参照です。そのポインターは ppvObj で返されます。一般的に要求されるストレージインターフェイスには、IStorageIStreamILockBytes などがあります。
ppvObjvoid**outriid で要求されたインターフェイスポインターを受け取るポインター変数のアドレスです。正常に返された場合、ppvObj には moniker が識別するオブジェクトのストレージへの要求されたインターフェイスポインターが格納されます。成功した場合、実装はストレージに対して AddRef を呼び出す必要があります。Release を呼び出すのは呼び出し元の責任です。エラーが発生した場合、ppvObjNULL でなければなりません。

戻り値

このメソッドは、標準の戻り値 E_UNEXPECTED のほか、次の値を返すことがあります。

戻り値 説明
S_OK
バインド操作は成功しました。
MK_E_NOSTORAGE
この moniker が識別するオブジェクトは独自のストレージを持っていません。
MK_E_EXCEEDEDDEADLINE
バインドコンテキストの BIND_OPTS 構造体で指定された制限時間内にバインド操作を完了できませんでした。
MK_E_CONNECTMANUALLY
ストレージに接続できませんでした。ネットワークデバイスに接続できなかったことが原因である可能性があります。詳細については、IMoniker::BindToObject を参照してください。
MK_E_INTERMEDIATEINTERFACENOTSUPPORTED
中間オブジェクトが見つかりましたが、バインド操作を完了するために必要なインターフェイスをサポートしていませんでした。たとえば、item moniker は、そのコンテナーが IOleItemContainer インターフェイスをサポートしていない場合、この値を返します。
STG_E_ACCESSDENIED
ストレージオブジェクトにアクセスできませんでした。

このメソッドは、IOleItemContainer::GetObject メソッドに関連するエラーを返すこともあります。

解説(Remarks)

BindToObject メソッドと BindToStorage メソッドには重要な違いがあります。たとえば、スプレッドシートオブジェクトを識別する moniker がある場合、BindToObject を呼び出すとスプレッドシートオブジェクト自体へのアクセスが提供されるのに対し、BindToStorage を呼び出すとスプレッドシートが存在するストレージオブジェクトへのアクセスが提供されます。

呼び出し元への注意

COM の moniker クラスはいずれもバインド操作でこのメソッドを呼び出しませんが、新しい moniker クラスの実装では呼び出すことが適切な場合があります。pmkToLeft パラメーターで識別されるオブジェクトからの情報を必要とし、その情報をアクティブ化せずにオブジェクトの永続ストレージから取得できる BindToObject の実装で、このメソッドを呼び出すことができます。たとえば、コンテナーをアクティブ化せずにアクティブ化できるオブジェクトを識別するために moniker を使用している場合、このメソッドが役立つことがあります。

moniker が識別するオブジェクトのストレージを読み取れるクライアントも、このメソッドを呼び出すことができます。

実装者への注意

実装は、現在の moniker が識別するオブジェクトの永続ストレージを特定し、目的のインターフェイスポインターを返すべきです。一部の種類の moniker は、独自の永続ストレージを持たない疑似オブジェクトを表します。そのようなオブジェクトは、コンテナーの内部状態の一部(たとえばスプレッドシート内のセル範囲)を構成します。moniker クラスがこの種のオブジェクトを識別する場合、BindToStorage の実装はエラー MK_E_NOSTORAGE を返すべきです。

バインドコンテキストの BIND_OPTS 構造体が BINDFLAGS_JUSTTESTEXISTENCE フラグを指定している場合、実装は ppvObjNULL を返すことを選択できます(ただし、このフラグを無視して完全なバインド操作を実行することもできます)。

実装固有の注意

実装 注意
Anti-moniker このメソッドは E_NOTIMPL を返します。
Class moniker このメソッドは class moniker の BindToObject に転送します。
File moniker このメソッドは moniker が表すパスで指定されたファイルを開き、そのファイルへの IStorage ポインターを返します。このメソッドは IStorage インターフェイスへのバインドのみをサポートします。riidIStream または ILockBytes が要求された場合、このメソッドは E_UNSPEC を返し、その他のインターフェイスが要求された場合は E_NOINTERFACE を返します。pmkToLeft が class moniker でない限り、IMoniker::BindToObject の実装と同様に、pmkToLeftNULL でなければなりません。
Generic composite moniker このメソッドは複合 moniker の最も右側の要素に対して再帰的に BindToStorage を呼び出し、残りの複合 moniker をその呼び出しの pmkToLeft パラメーターとして渡します。
Item moniker pmkToLeftNULL の場合、このメソッドは E_INVALIDARG を返します。そうでない場合、このメソッドは pmkToLeft パラメーターに対して IMoniker::BindToObject を呼び出し、IOleItemContainer インターフェイスポインターを要求します。次に、要求されたインターフェイスに対して IOleItemContainer::GetObjectStorage を呼び出します。
OBJREF moniker このメソッドは、実行中のオブジェクトを含むストレージ上の要求されたインターフェイスへのマーシャリングされたポインターを取得します。OBJREF moniker は実行中のオブジェクトを表すため、アクティブ化は行われません。表現されるオブジェクトがもはや実行されていない場合、BindToStorageE_UNEXPECTED で失敗します。
Pointer moniker このメソッドは、ラップされたポインターに対して要求されたインターフェイスをクエリします。
URL moniker URL moniker のシステム実装は、すべての URL 上のストリームオブジェクトに対して BindToStorage をサポートし、指定されたリソースが複合ファイルである場合はストレージオブジェクトに対してもサポートします。

URL moniker は非同期バインドをサポートするため、BindToStorage の実際の戻り値は、バインドコンテキストで設定されたオブジェクトパラメーターによって異なる場合があります。ただし、バインド操作のセマンティクスは、同期使用か非同期使用かに関係なく同一であり、次のとおりです。

  • URL moniker は、バインド操作のためのさらなる情報をバインドコンテキストから取得します。たとえば、moniker はバインドコンテキストに登録された IBindStatusCallback および IEnumFORMATETC インターフェイスへのポインターを取得できます。さらなる情報には、IBindCtx::SetBindOptions を通じてバインドコンテキストに指定された追加のバインドオプション(dwTickCountDeadline パラメーターや BIND_MAYBOTHERUSERgrfFlags 値など)が含まれる場合があります。次に moniker は IBindStatusCallback::GetBindInfo を呼び出してクライアントに問い合わせ、トランスポートとのバインド操作を開始し、結果として得られる IBinding を IBindStatusCallback::OnStartBinding を呼び出してクライアントに渡します。
  • 呼び出し元が、IBindStatusCallback::GetBindInfo から取得した BINDINFO 構造体に BINDF_ASYNCSTORAGE フラグを指定して非同期の IStream または IStorage を要求した場合、URL moniker は可能な限り速やかにオブジェクトを返します。まだ利用できないデータを参照するこれらの IStorage または IStream オブジェクトへの呼び出しは E_PENDING を返します。
  • 上記のように非同期の IStream または IStorage を呼び出し元が指定しない場合でも、URL moniker は可能な限り速やかに IBindStatusCallback::OnDataAvailable メソッドを通じてオブジェクトを返します。ただし、まだ利用できないデータを参照するこれらのオブジェクトへの呼び出しは、データが利用可能になるまでブロックします。一部のアプリケーションでは、これにより既存の I/O コードの変更が最小限で済み、アクセスパターンによってはパフォーマンスの向上が得られる場合があります。
vtbl 10 HRESULT Reduce(IBindCtx* pbc, DWORD dwReduceHowFar, IMoniker** ppmkToLeft, IMoniker** ppmkReduced)

moniker を最も単純な形式に簡約します。

pbcIBindCtx*inこのバインド操作で使用されるバインドコンテキストの IBindCtx インターフェイスへのポインターです。バインドコンテキストは、バインド処理中にバインドされたオブジェクトをキャッシュし、そのバインドコンテキストを使用するすべての操作に適用されるパラメーターを保持し、moniker の実装が自身の環境に関する情報を取得する手段を提供します。
dwReduceHowFarDWORDinこの moniker をどこまで簡約するかを指定します。このパラメーターは MKRREDUCE 列挙型のいずれかの値でなければなりません。
ppmkToLeftIMoniker**inout

入力時には、この moniker の左側にある moniker へのインターフェイスポインターを保持する IMoniker ポインター変数へのポインターです。このパラメーターは主に moniker の実装者が、複合 moniker の各構成要素間の連携を可能にするために使用します。moniker クライアントは通常 NULL を渡せます。

戻り時には、通常 ppmkToLeftNULL に設定され、左側の元の moniker に変更がないことを示します。まれに、ppmkToLeft が moniker を示す場合があり、これは以前の左側の moniker を無視し、*ppmkToLeft で返される moniker がその置き換えであることを意味します。そのような場合、実装はこの moniker の左側にあった古い moniker に対して Release を呼び出し、新しく返される moniker に対して AddRef を呼び出す必要があります。呼び出し元は後でそれを解放する必要があります。エラーが発生した場合、実装はインターフェイスポインターを変更しないままにするか、NULL に設定できます。

ppmkReducedIMoniker**outこの moniker の簡約された形式へのインターフェイスポインターを受け取る IMoniker ポインター変数へのポインターです。エラーが発生した場合、またはこの moniker が何も残らないように簡約された場合は、NULL になることがあります。この moniker を簡約できない場合、ppmkReduced は単にこの moniker に設定され、戻り値は MK_S_REDUCED_TO_SELF になります。ppmkReduced が非 NULL の場合、実装は新しい moniker に対して AddRef を呼び出す必要があります。Release を呼び出すのは呼び出し元の責任です。(*ppmkReduced がこの moniker に設定された場合でも同様です。)

戻り値

このメソッドは、標準の戻り値 E_OUTOFMEMORY および E_UNEXPECTED のほか、次の値を返すことがあります。

戻り値 説明
S_OK
メソッドは正常に完了しました。
MK_S_REDUCED_TO_SELF
この moniker はこれ以上簡約できなかったため、ppmkReduced はこの moniker を指します。
MK_E_EXCEEDEDDEADLINE
バインドコンテキストの BIND_OPTS 構造体で指定された制限時間内に操作を完了できませんでした。

解説(Remarks)

このメソッドは、次の用途を想定しています。

dwReduceHowFar パラメーターで渡される MKRREDUCE フラグの意図は、moniker をプログラムによって、その表示名がユーザーにとって認識可能な形式に簡約できるようにすることです。たとえば、ファイルシステム内のパス、ワードプロセッサドキュメント内のブックマーク、スプレッドシート内の範囲名は、すべてユーザーにとって認識可能です。これに対して、moniker にカプセル化されたマクロやエイリアスはユーザーにとって認識可能ではありません。

呼び出し元への注意

上記のシナリオは、現在システム提供の moniker クラスでは実装されていません。

2 つの moniker を IMoniker::IsEqual メソッドで比較する前に Reduce を呼び出すべきです。簡約された moniker は最も具体的な形式になっているためです。IsEqual は、簡約前の 2 つの moniker に対して S_FALSE を返し、簡約後には S_OK を返すことがあります。

実装者への注意

現在の moniker を簡約できる場合、実装は moniker をその場で簡約してはなりません。代わりに、現在の moniker の簡約された状態を表す新しい moniker を返す必要があります。これにより、呼び出し元は簡約されていない moniker を使用する選択肢(たとえば、その構成要素を列挙するなど)を保持できます。実装は、少なくとも要求された程度まで moniker を簡約すべきです。

実装固有の注意

実装 注意
Anti-moniker このメソッドは MK_S_REDUCED_TO_SELF を返し、同じ moniker を返します。
Class moniker このメソッドは MK_S_REDUCED_TO_SELF を返し、同じ moniker を返します。
File moniker このメソッドは MK_S_REDUCED_TO_SELF を返し、同じ moniker を返します。
Generic composite moniker このメソッドは、各構成 moniker に対して再帰的に Reduce を呼び出します。いずれかの構成要素が自身を簡約した場合、このメソッドは S_OK を返し、簡約された構成要素の複合を返します。簡約が発生しなかった場合、このメソッドは同じ moniker を返し、MK_S_REDUCED_TO_SELF を返します。
Item moniker このメソッドは MK_S_REDUCED_TO_SELF を返し、同じ moniker を返します。
OBJREF moniker このメソッドは MK_S_REDUCED_TO_SELF を返し、同じ moniker を返します。
Pointer moniker このメソッドは MK_S_REDUCED_TO_SELF を返し、同じ moniker を返します。
URL moniker このメソッドは MK_S_REDUCED_TO_SELF を返し、同じ moniker を返します。
vtbl 11 HRESULT ComposeWith(IMoniker* pmkRight, BOOL fOnlyIfNotGeneric, IMoniker** ppmkComposite)

現在の moniker を指定された moniker と結合して、新しい複合 moniker を作成します。

pmkRightIMoniker*inこの moniker の末尾に合成する moniker の IMoniker インターフェイスへのポインターです。
fOnlyIfNotGenericBOOLinTRUE の場合、呼び出し元は非汎用合成を必要とするため、pmkRight がこの moniker と generic composite を形成する以外の方法で合成できる moniker クラスである場合にのみ操作を続行すべきです。FALSE の場合、このメソッドは必要に応じて generic composite を作成できます。ほとんどの呼び出し元は、このパラメーターを FALSE に設定すべきです。
ppmkCompositeIMoniker**out複合 moniker のポインターを受け取る IMoniker ポインター変数へのポインターです。成功した場合、実装は結果の moniker に対して AddRef を呼び出す必要があります。Release を呼び出すのは呼び出し元の責任です。エラーが発生した場合、または moniker が何も残らないように合成される場合(たとえば、anti-moniker と item moniker やファイル moniker を合成する場合)、*ppmkCompositeNULL に設定されるべきです。

戻り値

このメソッドは、標準の戻り値 E_OUTOFMEMORY および E_UNEXPECTED のほか、次の値を返すことがあります。

戻り値 説明
S_OK
moniker は正常に結合されました。
MK_E_NEEDGENERIC
fOnlyIfNotGenericTRUE でしたが、generic composite moniker を作成せずに moniker を合成できなかったことを示します。

解説(Remarks)

2 つの moniker を結合することを合成と呼びます。同じクラスの 2 つの moniker が、非汎用合成と呼ばれる方法で結合できる場合があります。たとえば、不完全なパスを表すファイル moniker と相対パスを表す別のファイル moniker を結合して、完全なパスを表す単一のファイル moniker を形成できます。特定の moniker クラスの非汎用合成は、その moniker クラスの ComposeWith の実装でのみ処理できます。

任意のクラスの 2 つの moniker を結合することを汎用合成と呼びます。これは CreateGenericComposite 関数を呼び出すことで実現できます。

moniker の合成は結合的な操作です。つまり、A、B、C が moniker であるとき、Comp() が合成操作を表すとすると、Comp( Comp( A, B ), C ) は常に Comp( A, Comp( B, C ) ) と等しくなります。

呼び出し元への注意

2 つの moniker を結合するには、最初の moniker に非汎用合成を実行する機会を与えるため、CreateGenericComposite 関数を呼び出すのではなく、ComposeWith を呼び出すべきです。

自身のオブジェクトを識別するために item moniker を提供するオブジェクトは、オブジェクトの場所を完全に識別する moniker を提供するために ComposeWith を呼び出します。これは、たとえばドキュメントの一部へのリンクをサポートするサーバーや、ドキュメント内の埋め込みオブジェクトへのリンクをサポートするコンテナーに当てはまります。そのような場合は、次のようにします。

  1. オブジェクトを識別する item moniker を作成します。
  2. オブジェクトのコンテナーを識別する moniker を取得します。
  3. コンテナーを識別する moniker に対して ComposeWith を呼び出し、item moniker を pmkRight パラメーターとして渡します。

実装者への注意

現在の moniker を pmkRight が指す moniker と合成するには、非汎用合成または汎用合成のいずれかを使用できます。pmkRight が示す moniker のクラスが現在の moniker と同じである場合、pmkRight の内容を使用して、より高度な非汎用合成を実行できる可能性があります。

新しい moniker クラスを作成する場合、自身のクラスまたは別のクラスのいずれであっても、特別な扱いをしたい moniker の種類があるかどうかを判断する必要があります。ある場合は、pmkRight がその扱いを受けるべき種類の moniker であるかどうかをチェックするように ComposeWith を実装します。これを行うには、moniker の IPersist::GetClassID メソッドを呼び出すか、カスタムインターフェイスをサポートする moniker オブジェクトを定義している場合は、そのインターフェイスに対して moniker の QueryInterface を呼び出します。特別な扱いの例としては、絶対ファイル moniker と相対ファイル moniker の非汎用合成があります。特別な moniker の最も一般的なケースは、自身の moniker クラスの逆(IMoniker::Inverse の実装から返すもの)です。

pmkRight が受け手を完全に打ち消し、結果の複合が空になる場合は、ppmkCompositeNULL を返し、状態コード S_OK を返すべきです。

pmkRight パラメーターが特別な扱いをするクラスでない場合は、fOnlyIfNotGeneric を調べて次にどうするかを判断します。fOnlyIfNotGenericTRUE の場合は、ppmkCompositeNULL を返し、状態コード MK_E_NEEDGENERIC を返します。fOnlyIfNotGenericFALSE の場合は、CreateGenericComposite 関数を呼び出して汎用的に合成を実行します。

実装固有の注意

実装 注意
Anti-moniker fOnlyIfNotGenericTRUE の場合、このメソッドは ppmkCompositeNULL moniker に設定し、MK_E_NEEDGENERIC を返します。そうでない場合、このメソッドは 2 つの moniker を generic composite に結合した結果を返します。なお、ファイル moniker、item moniker、またはポインター moniker を anti-moniker の右側に合成すると、合成の順序が逆の場合のように何も残らないように合成されるのではなく、generic composite が生成される点に注意してください。
Class moniker 契約に従い、item moniker と同様に動作します。すなわち、E_INVALIDARGMK_E_NEEDGENERIC などを返すことができます。
File moniker pmkRight が anti-moniker の場合、返される moniker は NULL です。pmkRight が最も左側の構成要素が anti-moniker である複合 moniker の場合、返される moniker は最も左側の anti-moniker を削除した複合です。pmkRight がファイル moniker の場合、このメソッドは可能であれば 2 つの moniker を単一のファイル moniker に折りたたみます。不可能な場合(たとえば、d:\work と e:\reports のように両方のファイル moniker が絶対パスを表す場合)、返される moniker は NULL となり、戻り値は MK_E_SYNTAX になります。pmkRight が anti-moniker でもファイル moniker でもない場合、このメソッドは fOnlyIfNotGeneric パラメーターをチェックします。それが FALSE の場合、このメソッドは 2 つの moniker を generic composite に結合します。TRUE の場合、*ppmkCompositeNULL に設定し、MK_E_NEEDGENERIC を返します。
Generic composite moniker fOnlyIfNotGenericTRUE の場合、このメソッドは *pmkCompositeNULL に設定し、MK_E_NEEDGENERIC を返します。そうでない場合、このメソッドは CreateGenericComposite 関数を呼び出して 2 つの moniker を結合した結果を返します。
Item moniker pmkRight が anti-moniker の場合、返される moniker は NULL です。pmkRight が最も左側の構成要素が anti-moniker である複合 moniker の場合、返される moniker は最も左側の anti-moniker を削除した後の複合です。pmkRight が anti-moniker でない場合、fOnlyIfNotGenericFALSE であればこのメソッドは 2 つの moniker を generic composite に結合します。fOnlyIfNotGenericTRUE の場合、このメソッドは NULL moniker と戻り値 MK_E_NEEDGENERIC を返します。
OBJREF moniker pmkRight が anti-moniker の場合、返される moniker は NULL です。pmkRight が最も左側の構成要素が anti-moniker である複合 moniker の場合、返される moniker は最も左側の anti-moniker を削除した複合です。pmkRight が anti-moniker でも、最も左側の構成要素が anti-moniker である複合 moniker でもない場合、このメソッドは fOnlyIfNotGeneric パラメーターをチェックします。それが FALSE の場合、このメソッドは 2 つの moniker を generic composite に結合します。TRUE の場合、*ppmkCompositeNULL に設定し、MK_E_NEEDGENERIC を返します。
Pointer moniker pmkRight が anti-moniker の場合、返される moniker は NULL です。pmkRight が最も左側の構成要素が anti-moniker である複合 moniker の場合、返される moniker は最も左側の anti-moniker を削除した後の複合です。fOnlyIfNotGenericFALSE の場合、返される moniker は 2 つの moniker の generic composite です。そうでない場合、このメソッドは *ppmkCompositeNULL に設定し、MK_E_NEEDGENERIC を返します。
URL moniker URL moniker は、2 つの URL の合成(ベース URL と相対 URL の合成)をサポートします。この合成は相対 URL に関する RFC に従って行われます。fOnlyIfNotGenericTRUE の場合、このメソッドは MK_E_NEEDGENERIC を返します。そうでない場合、このメソッドは単に CreateGenericComposite(this, pmkRight, ppmkComposite) を返します。
vtbl 12 HRESULT Enum(BOOL fForward, IEnumMoniker** ppenumMoniker)

複合 moniker の構成要素の列挙子へのポインターを取得します。

fForwardBOOLinTRUE の場合、moniker を左から右へ列挙します。FALSE の場合、右から左へ列挙します。
ppenumMonikerIEnumMoniker**outmoniker の列挙子オブジェクトへのインターフェイスポインターを受け取る IEnumMoniker ポインター変数へのポインターです。成功した場合、実装は列挙子オブジェクトに対して AddRef を呼び出す必要があります。Release を呼び出すのは呼び出し元の責任です。エラーが発生した場合、または moniker に列挙可能な構成要素がない場合、実装は *ppenumMonikerNULL に設定します。

戻り値

このメソッドは、標準の戻り値 E_OUTOFMEMORYE_UNEXPECTED、および S_OK を返すことがあります。

解説(Remarks)

このメソッドは、moniker の構成要素を列挙できる列挙子への IEnumMoniker ポインターを提供する必要があります。たとえば、generic composite moniker の IMoniker::Enum メソッドの実装は、複合を構成する個々の moniker を判別できる列挙子を作成します。一方、ファイル moniker の IMoniker::Enum メソッドは、パス内の各構成要素を表す moniker を返す列挙子を作成します。

呼び出し元への注意

複合 moniker を構成する要素を調べるには、このメソッドを呼び出します。

実装者への注意

新しい moniker クラスに識別可能な内部構造がない場合、このメソッドの実装は単に S_OK を返し、ppenumMonikerNULL に設定できます。

実装固有の注意

実装 注意
Anti-moniker このメソッドは S_OK を返し、ppenumMonikerNULL に設定します。
Class moniker このメソッドは S_OK を返し、ppenumMonikerNULL に設定します。
File moniker このメソッドは S_OK を返し、ppenumMonikerNULL に設定します。
Generic composite moniker 成功した場合、このメソッドは S_OK を返し、複合を構成する構成 moniker を列挙する列挙子を返します。そうでない場合、このメソッドは E_OUTOFMEMORY を返します。
Item moniker このメソッドは S_OK を返し、ppenumMonikerNULL に設定します。
OBJREF moniker このメソッドは S_OK を返し、ppenumMonikerNULL に設定します。
Pointer moniker このメソッドは E_NOTIMPL を返します。
URL moniker このメソッドは S_OK を返し、ppenumMonikerNULL に設定します。
vtbl 13 HRESULT IsEqual(IMoniker* pmkOtherMoniker)

この moniker が指定された moniker と同一かどうかを判定します。

pmkOtherMonikerIMoniker*inこの moniker(このメソッドを呼び出す元の moniker)との比較に使用する moniker の IMoniker インターフェイスへのポインターです。

戻り値

このメソッドは、2 つの moniker が同一であることを示す場合は S_OK を返し、そうでない場合は S_FALSE を返します。

解説(Remarks)

以前の実行中オブジェクトテーブル(ROT)の実装は、このメソッドを呼び出していました。現在の ROT の実装では、代わりに IROTData インターフェイスを使用します。

呼び出し元への注意

2 つの moniker が同一かどうかを判定するには、このメソッドを呼び出します。moniker の簡約された形式は、簡約されていない形式とは異なるものとみなされます。IsEqual を呼び出す前に IMoniker::Reduce メソッドを呼び出すべきです。簡約された moniker は最も具体的な形式になっているためです。IsEqual は、簡約前の 2 つの moniker に対して S_FALSE を返し、簡約後には S_OK を返すことがあります。

実装者への注意

実装は、比較を実行する前に現在の moniker を簡約すべきではありません。簡約された moniker を比較するために IMoniker::Reduce を呼び出すのは呼び出し元の責任です。

等しいと比較される 2 つの moniker は、IMoniker::Hash を使用したときに同じ値にハッシュされる必要があります。

実装固有の注意

実装 注意
Anti-moniker このメソッドは、両方が anti-moniker の場合は S_OK を返します。そうでない場合は S_FALSE を返します。
Class moniker pmkOther が自身と同じ CLSID 情報で構築された class moniker の場合、このメソッドは S_OK を返します。そうでない場合、このメソッドは S_FALSE を返します。pmkOther が無効なポインターの場合は E_INVALIDARG を返すことがあります。
File moniker *pmkOther がファイル moniker で、両方の moniker のパスが(大文字と小文字を区別しない比較を使用して)同一の場合、このメソッドは S_OK を返します。そうでない場合、このメソッドは S_FALSE を返します。
Generic composite moniker 両方の moniker の構成要素を左から右の順に比較して等しい場合、このメソッドは S_OK を返します。
Item moniker 両方の moniker が item moniker で、それらの表示名が(大文字と小文字を区別しない比較を使用して)同一の場合、このメソッドは S_OK を返します。そうでない場合、このメソッドは S_FALSE を返します。
OBJREF moniker *pmkOther が OBJREF moniker で、両方の moniker のパスが(大文字と小文字を区別しない比較を使用して)同一の場合、このメソッドは S_OK を返します。そうでない場合、このメソッドは S_FALSE を返します。
Pointer moniker 両方がポインター moniker で、それらがラップするインターフェイスポインターが同一である場合にのみ、このメソッドは S_OK を返します。
URL moniker もう一方の moniker(pmkOtherMoniker)が URL moniker でない場合、S_FALSE を返します。これは、IPersist::GetClassID を使用して CLSID が CLSID_URLMoniker かどうかを確認することでチェックします。もう一方の moniker が URL moniker の場合、moniker の表示名が等しいかどうかを比較し、同一であれば S_OK を、そうでなければ S_FALSE を返します。
vtbl 14 HRESULT Hash(DWORD* pdwHash)

moniker の内部状態を使用してハッシュ値を作成します。

pdwHashDWORD*outハッシュ値を受け取る変数へのポインターです。

戻り値

このメソッドは、ハッシュ値が正常に取得されたことを示す S_OK を返します。

解説(Remarks)

呼び出し元への注意

このメソッドが返す値を使用して、moniker のハッシュテーブルを維持できます。ハッシュ値はテーブル内のハッシュバケットを決定します。そのようなテーブルで指定された moniker を検索するには、そのハッシュ値を計算し、IMoniker::IsEqual を使用して、そのハッシュバケット内の moniker と比較します。

実装者への注意

ハッシュ値は、moniker の存続期間中一定でなければなりません。IMoniker::IsEqual を使用して等しいと比較される 2 つの moniker は、同じ値にハッシュされる必要があります。

moniker をマーシャリングしてからアンマーシャリングしても、そのハッシュ値に影響を与えてはなりません。したがって、IMoniker::Hash の実装は、moniker のメモリアドレスではなく、moniker の内部状態のみに依存すべきです。

実装固有の注意

実装 注意
Anti-moniker このメソッドは moniker のハッシュ値を計算します。
Class moniker このメソッドは moniker のハッシュ値を計算し、S_OK を返します。pdwHash が無効なポインターの場合は E_INVALIDARG を返すことがあります。
File moniker このメソッドは moniker のハッシュ値を計算します。
Generic composite moniker このメソッドは moniker のハッシュ値を計算します。
Item moniker このメソッドは moniker のハッシュ値を計算します。
OBJREF moniker このメソッドは moniker のハッシュ値を計算します。
Pointer moniker このメソッドは moniker のハッシュ値を計算します。
URL moniker moniker の URL 文字列に基づいてハッシュ値を作成します。このハッシュ値は、URL 文字列が同一の場合は同一になりますが、異なる URL 文字列に対して同一になることもあります。このメソッドは、IMoniker::IsEqual を呼び出す必要がある時間を削減することで、比較を高速化するために使用されます。
vtbl 15 HRESULT IsRunning(IBindCtx* pbc, IMoniker* pmkToLeft, IMoniker* pmkNewlyRunning)

この moniker が識別するオブジェクトが現在読み込まれて実行中かどうかを判定します。

pbcIBindCtx*inこのバインド操作で使用されるバインドコンテキストの IBindCtx インターフェイスへのポインターです。バインドコンテキストは、バインド処理中にバインドされたオブジェクトをキャッシュし、そのバインドコンテキストを使用するすべての操作に適用されるパラメーターを保持し、moniker の実装が自身の環境に関する情報を取得する手段を提供します。
pmkToLeftIMoniker*inこの moniker が複合の一部である場合、この moniker の左側にある moniker の IMoniker インターフェイスへのポインターです。このパラメーターは主に moniker の実装者が、複合 moniker の各構成要素間の連携を可能にするために使用します。moniker クライアントは通常 NULL を渡せます。
pmkNewlyRunningIMoniker*in実行中オブジェクトテーブル(ROT)に最も最近追加された moniker の IMoniker インターフェイスへのポインターです。これは NULL でもかまいません。非 NULL の場合、実装は pmkNewlyRunning パラメーターに対して現在の moniker を渡して IMoniker::IsEqual を呼び出した結果を返すことができます。このパラメーターは、単に ROT を検索するよりも効率的な IsRunning の実装を可能にすることを意図していますが、実装は害を及ぼすことなく pmkNewlyRunning を無視することを選択できます。

戻り値

このメソッドは、標準の戻り値 E_UNEXPECTED のほか、次の値を返すことがあります。

戻り値 説明
S_OK
moniker は実行中です。
S_FALSE
moniker は実行中ではありません。

解説(Remarks)

呼び出し元への注意

moniker が識別するオブジェクトからサービスを要求する際に速度が重要な場合、オブジェクトが既に実行中の場合にのみそれらのサービスを求めたいことがあります(オブジェクトを実行状態に読み込むのは時間がかかる可能性があるため)。そのような状況では、IsRunning を呼び出してオブジェクトが実行中かどうかを判定すべきです。

リンクされたオブジェクト内に格納された moniker については、IsRunning は主に既定のハンドラーによる IOleLink::BindIfRunning の実装から呼び出されます。

実装者への注意

ROT へのポインターを取得するには、実装は pbc パラメーターに対して IBindCtx::GetRunningObjectTable を呼び出すべきです。次に実装は IRunningObjectTable::IsRunning を呼び出して、moniker が識別するオブジェクトが実行中かどうかを判定できます。moniker が識別するオブジェクトは、最初に実行を開始したときに ROT に自身を登録している必要があります。

実装固有の注意

実装 注意
Anti-moniker このメソッドは ROT を確認して、オブジェクトが実行中かどうかを調べます。
Class moniker このメソッドは E_NOTIMPL を返します。
File moniker pmkNewlyRunning が非 NULL の場合、その moniker がこの moniker と等しければ、このメソッドは TRUE を返します。そうでない場合、このメソッドは ROT にこの moniker が実行中かどうかを問い合わせます。このメソッドは pmkToLeft を無視します。
Generic composite moniker pmkToLeft が非 NULL の場合、このメソッドは pmkToLeft をこの moniker と合成し、その結果に対して IsRunning を呼び出します。

pmkToLeftNULL の場合、pmkNewlyRunning が非 NULL でこの moniker と等しければ、このメソッドは TRUE を返します。

pmkToLeftpmkNewlyRunning の両方が NULL の場合、このメソッドは ROT を確認して moniker が実行中かどうかを調べます。実行中の場合、このメソッドは S_OK を返します。そうでない場合、複合の最も右側の要素に対して再帰的に IsRunning を呼び出し、複合の残りをその呼び出しの pmkToLeft パラメーターとして渡します。これは、moniker が実行中として登録されていない疑似オブジェクトを識別する場合を処理します。詳細については、item moniker の実装を参照してください。

Item moniker pmkToLeft が NULL の場合、pmkNewlyRunning が非 NULL でこの moniker と等しければ、このメソッドは TRUE を返します。そうでない場合、このメソッドは ROT を確認して、この moniker が実行中かどうかを調べます。

pmkToLeft が非 NULL の場合、このメソッドは pmkToLeft パラメーターに対して IMoniker::BindToObject を呼び出し、IOleItemContainer インターフェイスポインターを要求します。次に、この moniker 内に含まれる文字列を渡して IOleItemContainer::IsRunning を呼び出します。

OBJREF moniker OBJREF moniker は実行中のオブジェクトインスタンスを表すため、最近の呼び出しが失敗したことによりオブジェクトがもはや実行されていないことが判明している場合を除き、このメソッドは TRUE を返します。このメソッドは pmkToLeft を無視します。
Pointer moniker ポインター moniker が識別するオブジェクトは常に実行中でなければならないため、このメソッドは常に S_OK を返します。
URL moniker この moniker が現在実行中の場合、S_OK を返します。そうでない場合、S_FALSE を返します。URL moniker は、まず自身が新しく実行中の moniker と等しいかどうかを、次の呼び出しを行って確認することで、実行中かどうかを判定します: pmkNewlyRunning->IsEqual。通常、この呼び出しは低コストな操作です。これが成功しない場合、moniker は次に、渡されたバインドコンテキストの ROT に登録されているかどうかを確認します。
vtbl 16 HRESULT GetTimeOfLastChange(IBindCtx* pbc, IMoniker* pmkToLeft, FILETIME* pFileTime)

この moniker が識別するオブジェクトが最後に変更された時刻を取得します。

pbcIBindCtx*inこのバインド操作で使用されるバインドコンテキストへのポインターです。バインドコンテキストは、バインド処理中にバインドされたオブジェクトをキャッシュし、そのバインドコンテキストを使用するすべての操作に適用されるパラメーターを保持し、moniker の実装が自身の環境に関する情報を取得する手段を提供します。詳細については、IBindCtx を参照してください。
pmkToLeftIMoniker*inmoniker が複合 moniker の一部である場合、この moniker の左側にある moniker へのポインターです。このパラメーターは主に moniker の実装者が、複合 moniker の各構成要素間の連携を可能にするために使用します。moniker クライアントは NULL を渡してください。
pFileTimeFILETIME*out最終変更時刻を受け取る FILETIME 構造体へのポインターです。{0xFFFFFFFF,0x7FFFFFFF} という値はエラー(たとえば、制限時間の超過、情報が利用不可)を示します。

戻り値

このメソッドは、標準の戻り値 E_OUTOFMEMORY のほか、次の値を返すことがあります。

戻り値 説明
S_OK
メソッドは正常に完了しました。
MK_E_EXCEEDEDDEADLINE
バインドコンテキストの BIND_OPTS 構造体で指定された制限時間内にバインド操作を完了できませんでした。
MK_E_CONNECTMANUALLY
このオブジェクトのストレージに接続できませんでした。ネットワークデバイスに接続できなかったことが原因である可能性があります。詳細については、IMoniker::BindToObject を参照してください。
MK_E_UNAVAILABLE
変更時刻は利用不可であり、使用する制限時間に関係なく利用できません。

解説(Remarks)

正確には、返される時刻は、それ以降に変更が発生していないと COM が識別できる最も早い時刻です。したがって、この時刻はオブジェクトへの最終変更時刻より後になる場合があります。

呼び出し元への注意

moniker が識別するオブジェクトから返された情報をキャッシュしている場合、その情報が最新であることを確認したいことがあります。そのためには、GetTimeOfLastChange を呼び出し、返された時刻を、オブジェクトから情報を最後に取得した時刻と比較します。

リンクされたオブジェクト内に格納された moniker については、GetTimeOfLastChange は主に既定のハンドラーによる IOleObject::IsUpToDate の実装から呼び出されます。コンテナーアプリケーションは IOleObject::IsUpToDate を呼び出して、リンクされたオブジェクト(またはリンクされたオブジェクトを含む埋め込みオブジェクト)が、実際にオブジェクトにバインドすることなく最新かどうかを判定します。これにより、アプリケーションはエンドユーザーがドキュメントを開いたときに、どのリンクされたオブジェクトを更新する必要があるかを素早く判断できます。その後、アプリケーションは、ドキュメント内のすべてのリンクされたオブジェクトをバインドする代わりに、(更新すべきかどうかをエンドユーザーに確認した後で)更新が必要なリンクされたオブジェクトだけをバインドできます。

実装者への注意

リンクされたオブジェクトについては、このメソッドはユーザーが複合ドキュメントを最初に開いたときに呼び出されるため、この操作を素早く実行することが重要です。したがって、GetTimeOfLastChange の実装は、いかなるオブジェクトにもバインドすべきではありません。さらに、実装はバインドコンテキストの制限時間パラメーターをチェックし、指定された時刻までに操作を完了できない場合は MK_E_EXCEEDEDDEADLINE を返すべきです。

実装で使用できる方針をいくつか示します。

実装固有の注意

実装 注意
Anti-moniker このメソッドは E_NOTIMPL を返します。
Class moniker このメソッドは MK_E_UNAVAILABLE を返します。
File moniker この moniker が ROT 内にある場合、このメソッドはそこに登録された最終変更時刻を返します。そうでない場合は、ファイルの最終書き込み時刻を返します。ファイルが見つからない場合、このメソッドは MK_E_NOOBJECT を返します。
Generic composite moniker このメソッドは pmkToLeft(非 NULL の場合)とこの moniker の複合を作成し、ROT を使用して最終変更時刻を取得します。オブジェクトが ROT 内にない場合、複合の最も右側の要素に対して再帰的に GetTimeOfLastChange を呼び出し、複合の残りをその呼び出しの pmkToLeft パラメーターとして渡します。
Item moniker pmkToLeftNULL の場合、このメソッドは MK_E_NOTBINDABLE を返します。そうでない場合、このメソッドは pmkToLeft とこの moniker の複合を作成し、ROT を使用して最終変更時刻にアクセスします。オブジェクトが ROT 内にない場合、pmkToLeft パラメーターに対して GetTimeOfLastChange を呼び出します。
OBJREF moniker このメソッドは E_NOTIMPL を返します。
Pointer moniker このメソッドは E_NOTIMPL を返します。
URL moniker このメソッドは、ROT に登録されているオブジェクトの最終変更時刻を返します。
vtbl 17 HRESULT Inverse(IMoniker** ppmk)

この moniker の逆となる moniker を作成します。この moniker または類似の構造を持つ moniker の右側に合成されると、その moniker は何も残らないように合成されます。

ppmkIMoniker**outこの moniker の逆となる moniker へのインターフェイスポインターを受け取る IMoniker ポインター変数のアドレスです。成功した場合、実装は新しい逆 moniker に対して AddRef を呼び出す必要があります。Release を呼び出すのは呼び出し元の責任です。エラーが発生した場合、実装は *ppmkNULL に設定すべきです。

戻り値

このメソッドは、標準の戻り値 E_OUTOFMEMORY のほか、次の値を返すことがあります。

戻り値 説明
S_OK
逆 moniker が正常に返されました。
MK_E_NOINVERSE
この moniker クラスには逆がありません。

解説(Remarks)

moniker の逆は、MS-DOS ファイルシステムにおける ".." ディレクトリに似ています。".." ディレクトリは、他の任意のディレクトリ名に対する逆として機能します。ディレクトリ名に ".." を追加すると空のパスになるためです。同様に、moniker の逆は通常、同じクラスのすべての moniker の逆でもあります。ただし、必ずしも別のクラスの moniker の逆であるとは限りません。

複合 moniker の逆は、元の moniker の構成要素の逆を逆順に並べた複合です。たとえば、A の逆を Inv( A )、A、B、C の複合を Comp( A, B, C ) とすると、Inv( Comp( A, B, C ) ) は Comp( Inv( C ), Inv( B ), Inv( A ) ) と等しくなります。

すべての moniker が逆を持つわけではありません。anti-moniker のように、それ自体が逆である moniker のほとんどは逆を持ちません。逆を持たない moniker では、それが識別するオブジェクトの内部から、外部の他のオブジェクトへの相対 moniker を形成することはできません。

呼び出し元への注意

他のオブジェクトを特定するために moniker を使用しているオブジェクトは、通常、使用している moniker のクラスを知りません。moniker の逆を取得するには、常に CreateAntiMoniker 関数ではなく IMoniker::Inverse を呼び出すべきです。使用している moniker が anti-moniker を自身の逆とみなすとは限らないためです。

Inverse メソッドは、相対 moniker の構築を支援するために、IMoniker::RelativePathTo メソッドの実装からも呼び出されます。

実装者への注意

moniker に内部構造がない場合、IMoniker::Inverse の実装で CreateAntiMoniker 関数を呼び出して anti-moniker を取得できます。IMoniker::ComposeWith の実装では、Inverse の実装で提供する逆をチェックする必要があります。

実装固有の注意

実装 注意
Anti-moniker このメソッドは MK_E_NOINVERSE を返し、*ppmkNULL に設定します。
Class moniker このメソッドは anti-moniker(すなわち CreateAntiMoniker を呼び出した結果)を返します。
File moniker このメソッドは anti-moniker(すなわち CreateAntiMoniker を呼び出した結果)を返します。
Generic composite moniker このメソッドは、元の複合の各構成要素の逆を逆順に格納した複合 moniker を返します。たとえば、A の逆を Inv( A ) とすると、A、B、C の複合の逆は Comp(Inv( C ), Inv( B ), Inv( A ) ) です。
Item moniker このメソッドは anti-moniker(すなわち CreateAntiMoniker を呼び出した結果)を返します。
OBJREF moniker このメソッドは anti-moniker(すなわち CreateAntiMoniker を呼び出した結果)を返します。
Pointer moniker このメソッドは anti-moniker(すなわち CreateAntiMoniker を呼び出した結果)を返します。
URL moniker このメソッドは MK_E_NOINVERSE を返し、*ppmkNULL に設定します。
vtbl 18 HRESULT CommonPrefixWith(IMoniker* pmkOther, IMoniker** ppmkPrefix)

この moniker が指定された moniker と共通に持つプレフィックスに基づいて、新しい moniker を作成します。

pmkOtherIMoniker*in共通のプレフィックスがあるかどうかを判定するために、この moniker と比較する別の moniker の IMoniker インターフェイスへのポインターです。
ppmkPrefixIMoniker**outこの moniker と pmkOther の共通プレフィックスとなる moniker へのインターフェイスポインターを受け取る IMoniker* ポインター変数のアドレスです。成功した場合、実装は結果の moniker に対して AddRef を呼び出す必要があります。Release を呼び出すのは呼び出し元の責任です。エラーが発生した場合、または共通プレフィックスがない場合、実装は *ppmkPrefixNULL に設定すべきです。

戻り値

このメソッドは、標準の戻り値 E_OUTOFMEMORY のほか、次の値を返すことがあります。

戻り値 説明
S_OK
この moniker でも pmkOther でもない共通プレフィックスが存在します。
MK_S_NOPREFIX
共通プレフィックスが存在しません。
MK_S_HIM
pmkOther 全体がこの moniker のプレフィックスです。
MK_S_US
2 つの moniker は同一です。
MK_S_ME
この moniker が pmkOther moniker のプレフィックスです。
MK_S_NOTBINDABLE
このメソッドが相対 moniker に対して呼び出されました。相対 moniker に対して共通プレフィックスを取得することは意味がありません。

解説(Remarks)

CommonPrefixWith は、この moniker オブジェクトの moniker と別の moniker の共通プレフィックスからなる新しい moniker を作成します。たとえば、一方の moniker がパス "c:\projects\secret\art\pict1.bmp" を表し、もう一方の moniker がパス "c:\projects\secret\docs\chap1.txt" を表す場合、これら 2 つの moniker の共通プレフィックスは、パス "c:\projects\secret" を表す moniker になります。

呼び出し元への注意

CommonPrefixWith メソッドは、主に IMoniker::RelativePathTo メソッドの実装から呼び出されます。moniker を使用してオブジェクトを特定するクライアントがこのメソッドを呼び出す必要があることはめったにありません。

このメソッドは、pmkOther とこの moniker の両方が絶対 moniker である場合にのみ呼び出してください。絶対 moniker とは、ファイル moniker、または最も左側の構成要素が絶対パスを表すファイル moniker である generic composite のいずれかです。相対 moniker に対してこのメソッドを呼び出さないでください。意味のある結果が得られないためです。

実装者への注意

実装はまず、pmkOther が認識可能で特別な処理を提供できるクラスの moniker であるかどうか(たとえば、この moniker と同じクラスであるかどうか)を判断すべきです。そうである場合、実装は 2 つの moniker の共通プレフィックスを判定すべきです。そうでない場合、汎用的なケースを正しく処理する MonikerCommonPrefixWith 関数への呼び出しに両方の moniker を渡すべきです。

実装固有の注意

実装 注意
Anti-moniker もう一方の moniker も anti-moniker の場合、このメソッドは MK_S_US を返し、ppmkPrefix をこの moniker に設定します。そうでない場合、このメソッドは MonikerCommonPrefixWith 関数を呼び出します。この関数は、もう一方の moniker が generic composite である場合を正しく処理します。
Class moniker pmkOther がこの moniker と等しい場合、この moniker へのポインターを取得して MK_S_US を返します。pmkOther が class moniker であるがこの moniker と等しくない場合、MK_E_NOPREFIX を返します。そうでない場合、pmkThis として自身を、pmkOtherppmkPrefix を指定して MonikerCommonPrefixWith を呼び出した結果を返します。これにより、pmkOther が generic composite moniker である場合が処理されます。
File moniker 両方の moniker がファイル moniker の場合、このメソッドは、2 つのファイル moniker の先頭にある共通の構成要素に基づくファイル moniker を返します。ファイル moniker の構成要素は次の型のいずれかです。
  • \\server\share の形式のコンピューター名。コンピューター名は単一の構成要素として扱われるため、パス "\\myserver\public\work" と "\\myserver\private\games" を表す 2 つの moniker は "\\myserver" を共通プレフィックスとして持ちません。
  • ドライブ指定(たとえば "C:")。
  • ディレクトリ名またはファイル名。
もう一方の moniker がファイル moniker でない場合、このメソッドは両方の moniker を MonikerCommonPrefixWith 関数への呼び出しに渡します。この関数は、もう一方の moniker が generic composite である場合を正しく処理します。

共通プレフィックスがない場合、このメソッドは MK_E_NOPREFIX を返します。

Generic composite moniker もう一方の moniker が複合の場合、このメソッドは各複合の構成要素を左から右へ比較します。返される共通プレフィックス moniker は、両方の moniker に共通する最も左側の構成要素の数に応じて、複合 moniker になる場合もあります。もう一方の moniker が複合でない場合、このメソッドは単にそれをこの moniker の最も左側の構成要素と比較します。

moniker が等しい場合、このメソッドは MK_S_US を返し、ppmkPrefix をこの moniker に設定します。もう一方の moniker がこの moniker のプレフィックスの場合、このメソッドは MK_S_HIM を返し、ppmkPrefix をもう一方の moniker に設定します。この moniker がもう一方のプレフィックスの場合、このメソッドは MK_S_ME を返し、ppmkPrefix をこの moniker に設定します。

共通プレフィックスがない場合、このメソッドは MK_E_NOPREFIX を返し、ppmkPrefixNULL に設定します。

Item moniker もう一方の moniker がこの moniker と等しい item moniker の場合、このメソッドは *ppmkPrefix をこの moniker に設定し、MK_S_US を返します。そうでない場合、このメソッドは MonikerCommonPrefixWith 関数を呼び出します。この関数は、もう一方の moniker が generic composite である場合を正しく処理します。
OBJREF moniker 2 つの moniker が等しい場合、このメソッドは MK_S_US を返し、*ppmkPrefixNULL に設定します。もう一方の moniker が OBJREF moniker でない場合、このメソッドは両方の moniker を MonikerCommonPrefixWith 関数に渡します。この関数は、もう一方の moniker が generic composite である場合を正しく処理します。

共通プレフィックスがない場合、このメソッドは MK_E_NOPREFIX を返します。

Pointer moniker 2 つの moniker が等しい場合、このメソッドは MK_S_US を返し、*ppmkPrefix をこの moniker に設定します。そうでない場合、このメソッドは MK_E_NOPREFIX を返し、*ppmkPrefixNULL に設定します。
URL moniker このメソッドは E_NOTIMPL を返します。
vtbl 19 HRESULT RelativePathTo(IMoniker* pmkOther, IMoniker** ppmkRelPath)

この moniker と指定された moniker の間の相対 moniker を作成します。

pmkOtherIMoniker*in相対パスを取得する対象の moniker の IMoniker インターフェイスへのポインターです。
ppmkRelPathIMoniker**out相対 moniker へのインターフェイスポインターを受け取る IMoniker ポインター変数へのポインターです。成功した場合、実装は新しい moniker に対して AddRef を呼び出す必要があります。Release を呼び出すのは呼び出し元の責任です。エラーが発生した場合、実装は *ppmkRelPathNULL に設定します。

戻り値

このメソッドは、標準の戻り値 E_OUTOFMEMORY および E_UNEXPECTED のほか、次の値を返すことがあります。

戻り値 説明
S_OK
メソッドは正常に完了しました。
MK_S_HIM
2 つの moniker に共通のプレフィックスがなく、ppmkRelPath で返される moniker は pmkOther です。
MK_E_NOTBINDABLE
この moniker は item moniker などの相対 moniker です。相対パスを判定する前に、この moniker をそのコンテナーの moniker と合成する必要があります。

解説(Remarks)

相対 moniker は、相対パス(たとえば "..\backup")に似ています。たとえば、パス "c:\projects\secret\art\pict1.bmp" を表す moniker と、パス "c:\projects\secret\docs\chap1.txt" を表す別の moniker があるとします。最初の moniker に対して RelativePathTo を呼び出し、2 番目の moniker を pmkOther パラメーターとして渡すと、パス "..\docs\chap1.txt" を表す相対 moniker が作成されます。

呼び出し元への注意

moniker クライアントは通常 RelativePathTo を呼び出す必要はありません。このメソッドは主に、リンクされたオブジェクトの既定のハンドラーによって呼び出されます。リンクされたオブジェクトは、リンクソースを識別するために絶対 moniker と相対 moniker の両方を保持します。(これにより、ユーザーがコンテナーファイルとソースファイルの両方を含むディレクトリツリーを移動した場合でも、リンクの追跡が可能になります。) 既定のハンドラーは、このメソッドを呼び出して、コンテナードキュメントからリンクソースへの相対 moniker を作成します。(つまり、コンテナードキュメントを識別する moniker に対して RelativePathTo を呼び出し、リンクソースを識別する moniker を pmkOther パラメーターとして渡します。)

RelativePathTo を呼び出す場合は、絶対 moniker(たとえば、ファイル moniker、または最も左側の構成要素がファイル moniker であり、そのファイル moniker が絶対パスを表す複合 moniker)に対してのみ呼び出してください。相対 moniker に対してこのメソッドを呼び出さないでください。

実装者への注意

RelativePathTo の実装はまず、pmkOther が認識可能で特別な処理を提供できるクラスの moniker であるかどうか(たとえば、この moniker と同じクラスであるかどうか)を判断すべきです。そうである場合、実装は相対パスを判定すべきです。そうでない場合、汎用的なケースを正しく処理する MonikerRelativePathTo 関数への呼び出しに両方の moniker を渡すべきです。

相対パスを判定する最初のステップは、この moniker と pmkOther の共通プレフィックスを判定することです。次のステップは、この moniker と pmkOther をそれぞれ 2 つの部分、すなわち (P, myTail) と (P, otherTail) に分割することです。ここで P は共通プレフィックスです。正しい相対パスは、myTail の逆と otherTail を合成したものです。

Comp( Inv( myTail ), otherTail )

ここで Comp() は合成操作を、Inv() は逆操作を表します。

特定の種類の moniker では、myTail の逆を構築するために IMoniker::Inverse メソッドを使用できません。たとえば、ファイル moniker は逆として anti-moniker を返しますが、その RelativePathTo メソッドは、myTail の逆を構築するために、それぞれパス ".." を表す 1 つ以上のファイル moniker を使用する必要があります。

実装固有の注意

実装 注意
Anti-moniker このメソッドは MK_S_HIM を返し、*ppmkRelPath をもう一方の moniker に設定します。
Class moniker このメソッドは、pmkSrc をこの moniker、pmkOtherppmkRelPath、そして dwReserved として TRUE を指定して MonikerRelativePathTo を呼び出した結果を返します。
File moniker このメソッドは、この moniker の右側に合成するともう一方の moniker になる moniker を計算します。たとえば、この moniker のパスが "C:\work\docs\report.doc" で、もう一方の moniker が "C:\work\art\picture.bmp" の場合、計算される moniker のパスは "..\..\art\picture.bmp" になります。
Generic composite moniker このメソッドは、2 つの moniker の共通プレフィックスを見つけ、共通プレフィックスを削除したときの残りからなる 2 つの moniker を作成します。次に、この moniker の残りの逆を作成し、その右側にもう一方の moniker の残りを合成します。
Item moniker このメソッドは MK_E_NOTBINDABLE を返し、*ppmkRelPathNULL に設定します。
OBJREF moniker このメソッドは E_NOTIMPL を返します。
Pointer moniker このメソッドは E_NOTIMPL を返します。
URL moniker このメソッドは E_NOTIMPL を返します。
vtbl 20 HRESULT GetDisplayName(IBindCtx* pbc, IMoniker* pmkToLeft, LPWSTR* ppszDisplayName)

moniker の表示名を取得します。

pbcIBindCtx*inこの操作で使用されるバインドコンテキストの IBindCtx インターフェイスへのポインターです。バインドコンテキストは、バインド処理中にバインドされたオブジェクトをキャッシュし、そのバインドコンテキストを使用するすべての操作に適用されるパラメーターを保持し、moniker の実装が自身の環境に関する情報を取得する手段を提供します。
pmkToLeftIMoniker*inmoniker が複合 moniker の一部である場合、この moniker の左側にある moniker へのポインターです。このパラメーターは主に moniker の実装者が、複合 moniker の各構成要素間の連携を可能にするために使用します。moniker クライアントは NULL を渡してください。
ppszDisplayNameLPWSTR*outmoniker の表示名文字列へのポインターを受け取るポインター変数のアドレスです。実装は ppszDisplayName で返す文字列を割り当てるために IMalloc::Alloc を使用する必要があり、それを解放するために IMalloc::Free を呼び出すのは呼び出し元の責任です。このメソッドの呼び出し元と実装の両方が、CoGetMalloc によって返される COM タスクアロケーターを使用します。エラーが発生した場合、実装は *ppszDisplayNameNULL に設定する必要があります。

戻り値

このメソッドは、標準の戻り値 E_OUTOFMEMORY のほか、次の値を返すことがあります。

戻り値 説明
S_OK
メソッドは正常に完了しました。
MK_E_EXCEEDEDDEADLINE
バインドコンテキストの BIND_OPTS 構造体で指定された制限時間内にバインド操作を完了できませんでした。
E_NOTIMPL
表示名がありません。

解説(Remarks)

GetDisplayName は、moniker の表示可能な表現である文字列を提供します。表示名は moniker の内部状態の完全な表現ではなく、単にユーザーが読める形式です。そのため、まれに 2 つの異なる moniker が同じ表示名を持つことがあります。moniker の表示名を MkParseDisplayName 関数に渡してその moniker に解析し直せる保証はありませんが、解析できないことはまれです。

呼び出し元への注意

moniker の表示名の取得はコストの高い操作である可能性があります。効率のため、繰り返し呼び出すのではなく、最初に成功した GetDisplayName 呼び出しの結果をキャッシュするとよいでしょう。

実装者への注意

表示名が変化しない moniker クラスを作成する場合は、単に表示名をキャッシュし、要求されたときにキャッシュされた名前を提供します。表示名が時間とともに変化する可能性がある場合、現在の表示名を取得するには、moniker がオブジェクトのストレージにアクセスするか、オブジェクトにバインドする必要があることがあり、いずれもコストの高い操作になり得ます。この場合、GetDisplayName の実装は、バインドコンテキストの BIND_OPTS 構造体で指定された時刻までに名前を取得できない場合、MK_E_EXCEEDEDDEADLINE を返すべきです。

generic composite moniker の一部となることを意図した moniker は、先行する区切り文字(たとえば '')を表示名の一部として含めるべきです。たとえば、item moniker が返す表示名には、CreateItemMoniker 関数で作成されたときに指定された区切り文字が含まれます。ファイル moniker の表示名には区切り文字は含まれません。ファイル moniker は常に複合の最も左側の構成要素であることが期待されるためです。

実装固有の注意

実装 注意
Anti-moniker この moniker に含まれる anti-moniker ごとに、このメソッドは "\.." を 1 つ返します。
Class moniker class moniker の表示名は次の形式です: clsid:string-clsid-no-curly-braces *[";" clsid-param=value]:。たとえば、clsid:a7b90590-36fd-11cf-857d-00aa006d2ea4: です。
File moniker このメソッドは moniker が表すパスを返します。
Generic composite moniker このメソッドは、複合の各構成 moniker が返す表示名を連結したものを返します。
Item moniker このメソッドは、item moniker の作成時に指定された区切り文字と項目名を連結したものを返します。
OBJREF moniker このメソッドは OBJREF moniker の表示名を取得します。表示名は、実行中のオブジェクトのマシンの場所、プロセスエンドポイント、およびインターフェイスポインター ID(IPID)をカプセル化した 64 ビットのエンコーディングです。将来の互換性のため、表示名は URL の一部として指定できる文字に制限されます。
Pointer moniker このメソッドは E_NOTIMPL を返します。
URL moniker URL moniker は完全な URL 文字列を返そうとします。moniker が部分的な URL 文字列で作成された場合(CreateURLMonikerEx を参照)、まず SZ_URLCONTEXT の下でバインドコンテキスト内の URL moniker を探し、次にコンテキスト情報を得るためにその左側の moniker を調べます。完全な URL 文字列を返せない場合は、部分的な URL 文字列を返します。
vtbl 21 HRESULT ParseDisplayName(IBindCtx* pbc, IMoniker* pmkToLeft, LPWSTR pszDisplayName, DWORD* pchEaten, IMoniker** ppmkOut)

表示名を moniker に変換します。

pbcIBindCtx*inこのバインド操作で使用されるバインドコンテキストの IBindCtx インターフェイスへのポインターです。バインドコンテキストは、バインド処理中にバインドされたオブジェクトをキャッシュし、そのバインドコンテキストを使用するすべての操作に適用されるパラメーターを保持し、moniker の実装が自身の環境に関する情報を取得する手段を提供します。
pmkToLeftIMoniker*inここまでで表示名から構築された moniker の IMoniker インターフェイスへのポインターです。
pszDisplayNameLPWSTRin解析する残りの表示名です。
pchEatenDWORD*outこのステップで消費された pszDisplayName 内の文字数を受け取る変数へのポインターです。
ppmkOutIMoniker**outpszDisplayName から構築された moniker へのインターフェイスポインターを受け取る IMoniker ポインター変数へのポインターです。成功した場合、実装は新しい moniker に対して AddRef を呼び出す必要があります。Release を呼び出すのは呼び出し元の責任です。エラーが発生した場合、実装は *ppmkOutNULL に設定します。

戻り値

このメソッドは、標準の戻り値 E_OUTOFMEMORY および E_UNEXPECTED のほか、次の値を返すことがあります。

戻り値 説明
S_OK
解析操作は正常に完了しました。
MK_E_SYNTAX
入力された構成要素(pmkToLeft、この moniker、および pszDisplayName)の構文にエラーがあります。たとえば、ファイル moniker は pmkToLeft が非 NULL の場合にこのエラーを返し、item moniker は pmkToLeftNULL の場合にこのエラーを返します。

このメソッドは、IMoniker::BindToObject メソッドに関連するエラーを返すこともあります。

解説(Remarks)

呼び出し元への注意

moniker クライアントは通常 ParseDisplayName を直接呼び出しません。代わりに、表示名を moniker に変換したい場合(たとえば、コンテナーアプリケーションの リンク ダイアログボックスを実装する場合や、ドキュメント外のオブジェクトへの参照をサポートするマクロ言語を実装する場合)には、MkParseDisplayName 関数を呼び出します。その関数は、まず表示名の先頭部分を自身で解析します。

次に、作成したばかりの moniker に対して ParseDisplayName を呼び出し、表示名の残りを渡して、新しい moniker を返してもらいます。このステップは、表示名全体が解析されるまで繰り返されます。

実装者への注意

moniker クラスが特定の種類のオブジェクトのみを指すように設計されている場合、実装はこの解析を自身で実行できることがあります。そうでない場合は、ここまでの moniker(すなわち pmkToLeft とこの moniker の合成)が識別するオブジェクトの IParseDisplayName インターフェイスポインターを取得し、IParseDisplayName::ParseDisplayName を呼び出した結果を返す必要があります。

IParseDisplayName ポインターを取得するには、次のようにいくつかの方針があります。

バインドされたオブジェクトは、解析操作の間実行状態を維持するため、バインドコンテキストに登録する必要があります(IBindCtx::RegisterObjectBound を参照)。

実装固有の注意

実装 注意
Anti-moniker このメソッドは E_NOTIMPL を返します。
Class moniker このメソッドは、IParseDisplayName を求めて自身にバインドし、バインドされたオブジェクトに表示名を moniker に解析するよう依頼することで、表示名を解析します。次のとおりです。
  hr = BindToObject(pbc, pmkToLeft, IID_IParseDisplayName, (void**)&ppdn);
  if (SUCCEEDED(hr)) {
    hr = ppdn->ParseDisplayName(pbc, lpszDisplayName, pchEaten, ppmkOut);
    ppdn->Release();
  }
  return hr;

このメソッドは、まず moniker が識別するオブジェクトのクラスファクトリにバインドし、次にオブジェクト自体にバインドすることで、IParseDisplayName ポインターを取得しようとします。これらのバインド操作のいずれかが成功した場合、ファイル moniker は表示名の未解析部分を IParseDisplayName::ParseDisplayName メソッドに渡します。

pmkToLeft が非 NULL の場合、このメソッドは MK_E_SYNTAX を返します。

File moniker このメソッドは、まず moniker が識別するオブジェクトのクラスファクトリにバインドし、次にオブジェクト自体にバインドすることで、IParseDisplayName ポインターを取得しようとします。これらのバインド操作のいずれかが成功した場合、ファイル moniker は表示名の未解析部分を IParseDisplayName::ParseDisplayName メソッドに渡します。
Generic composite moniker このメソッドは、複合の最も右側の要素に対して再帰的に IMoniker::ParseDisplayName を呼び出し、それ以外のすべてをその呼び出しの pmkToLeft パラメーターとして渡します。
Item moniker pmkToLeftNULL の場合、このメソッドは MK_E_SYNTAX を返します。そうでない場合、このメソッドは pmkToLeft パラメーターに対して IMoniker::BindToObject を呼び出し、IOleItemContainer インターフェイスポインターを要求します。次に IOleItemContainer::GetObject を呼び出して、moniker が識別するオブジェクトの IParseDisplayName インターフェイスポインターを要求し、表示名を IParseDisplayName::ParseDisplayName に渡します。
OBJREF moniker pmkToLeftNULL でない場合、このメソッドは MK_E_SYNTAX を返します。
Pointer moniker このメソッドは、ラップされたポインターに対して IParseDisplayName インターフェイスをクエリし、表示名を IParseDisplayName::ParseDisplayName に渡します。
URL moniker 完全または部分的な URL 文字列を結果 moniker(ppmkOut)に解析します。szDisplayName が完全な URL 文字列(たとえば "http://foo.com/default.html")を表す場合、結果は新しい完全な URL moniker です。szDisplayName が部分的な URL 文字列(たとえば "..\default.html")を表す場合、結果は、バインドコンテキストの SZ_URLCONTEXT オブジェクトパラメーターまたはこの URL moniker からコンテキストを取得する完全な URL です。たとえば、コンテキスト moniker が "http://foo.com/pub/list.html" で szDisplayName が "..\default.html" の場合、結果の URL moniker は "http://foo.com/default.html" を表します。
vtbl 22 HRESULT IsSystemMoniker(DWORD* pdwMksys)

この moniker がシステム提供の moniker クラスの 1 つであるかどうかを判定します。

pdwMksysDWORD*outMKSYS 列挙型のいずれかの値を受け取るポインターで、COM の moniker クラスの 1 つを指します。このパラメーターは NULL にできません。

戻り値

このメソッドは、moniker がシステム moniker であることを示す場合は S_OK を返し、そうでない場合は S_FALSE を返します。

解説(Remarks)

呼び出し元への注意

MKSYS 列挙型の新しい値が将来定義される可能性があります。したがって、関心のある各値について明示的にテストすべきです。

実装者への注意

このメソッドの実装は MKSYS_NONE を返す必要があります。この関数を使用して自身の moniker を識別することはできません(たとえば、IMoniker::ComposeWith の実装内で)。代わりに、moniker の IPersist::GetClassID の実装を使用するか、QueryInterface を使用して自身のプライベートインターフェイスをテストすべきです。

実装固有の注意

実装 注意
Anti-moniker このメソッドは S_OK を返し、MKSYS_ANTIMONIKER を返します。
Class moniker このメソッドは S_OK を返し、MKSYS_CLASSMONIKER を返します。
File moniker このメソッドは S_OK を返し、MKSYS_CLASSMONIKER を返します。
Generic composite moniker このメソッドは S_OK を返し、MKSYS_GENERICCOMPOSITE を返します。
Item moniker このメソッドは S_OK を返し、MKSYS_ITEMMONIKER を返します。
OBJREF moniker このメソッドは S_OK を返し、MKSYS_OBJREFMONIKER を返します。
Pointer moniker このメソッドは S_OK を返し、MKSYS_POINTERMONIKER を返します。
URL moniker このメソッドは S_OK を返し、MKSYS_URLMONIKER を返します。
出典・ライセンス: 上記「公式ドキュメント」の内容は Microsoft の Win32 API ドキュメント(MicrosoftDocs/sdk-api)を日本語に翻訳・改変したものです。© Microsoft Corporation. CC BY 4.0 で提供。
Microsoft 公式リファレンス: 英語 (en-us) · 日本語 (ja-jp) · 原文ソース (GitHub)

HSP用 COM定義

#usecom / #comfunc によるHSPのCOM呼び出し定義。数字は vtbl インデックス(0始まり)。クラスIDが無い場合 #usecom の末尾は "{}"、ある場合は "{CLSID}"

出力引数:
#define global IID_IMoniker "{0000000F-0000-0000-C000-000000000046}"
#usecom global IMoniker IID_IMoniker "{}"
#comfunc global IMoniker_BindToObject         8 sptr,sptr,var,sptr
#comfunc global IMoniker_BindToStorage        9 sptr,sptr,var,sptr
#comfunc global IMoniker_Reduce               10 sptr,int,sptr,sptr
#comfunc global IMoniker_ComposeWith          11 sptr,int,sptr
#comfunc global IMoniker_Enum                 12 int,sptr
#comfunc global IMoniker_IsEqual              13 sptr
#comfunc global IMoniker_Hash                 14 var
#comfunc global IMoniker_IsRunning            15 sptr,sptr,sptr
#comfunc global IMoniker_GetTimeOfLastChange  16 sptr,sptr,var
#comfunc global IMoniker_Inverse              17 sptr
#comfunc global IMoniker_CommonPrefixWith     18 sptr,sptr
#comfunc global IMoniker_RelativePathTo       19 sptr,sptr
#comfunc global IMoniker_GetDisplayName       20 sptr,sptr,var
#comfunc global IMoniker_ParseDisplayName     21 sptr,sptr,wstr,var,sptr
#comfunc global IMoniker_IsSystemMoniker      22 var
; ※数字は vtbl インデックス(0始まり)。0/1/2 は IUnknown(QueryInterface/AddRef/Release)。
; ※このインターフェースは直接 CoCreateInstance するクラスIDが無いため "{}"(他メソッド/アクティベーションで取得)。
; ※出力/バッファ引数は var(変数直渡し)。varptr 方式にも切替可。
; ※ハンドル/void*等の不透明ポインタは IronHSP では intptr 指定が可能。