Win32 API 日本語リファレンス
ホームMedia.DeviceManager › IWMDMStorageControl3

IWMDMStorageControl3

COM
IIDb3266365-d4f3-4696-8d53-bd27ec60993a継承元IWMDMStorageControl2自前メソッド開始 vtbl9

公式ドキュメント

IWMDMStorageControl3 インターフェースは、IWMDMMetaData インターフェース ポインターを受け取る Insert メソッドを提供することで、IWMDMStorageControl2 を拡張します。

メソッド 1

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

vtbl 9 HRESULT Insert3(DWORD fuMode, DWORD fuType, LPWSTR pwszFileSource, LPWSTR pwszFileDest, IWMDMOperation* pOperation, IWMDMProgress* pProgress, IWMDMMetaData* pMetaData, IUnknown* pUnknown, IWMDMStorage** ppNewObject)

Insert3 メソッドは、ストレージ内またはストレージの隣にコンテンツを配置します。このメソッドは、送信するオブジェクトのメタデータと種類をアプリケーションが明示的に指定できるようにすることで、IWMDMStorageControl2::Insert2 を拡張したものです。

fuModeDWORDin

Insert3 操作で使用する処理モード。次の表は、fuMode パラメーターに指定できる処理モードの一覧です。最初の 2 つのモードのうち 1 つ、STORAGECONTROL モードのうち 1 つ、CONTENT モードのうち 1 つを、それぞれ必ず 1 つだけ指定する必要があります。WMDM_MODE_BLOCKWMDM_MODE_THREAD の両方を指定した場合は、ブロック モードが使用されます。WMDM_FILE_ATTR* フラグをこの関数で指定する方が、先にこの関数を呼び出し、ファイルの作成または送信後にこれらの属性を設定するよりも効率的です。

組み合わせ モード 説明
次のいずれか 1 つ: WMDM_MODE_BLOCK 操作はブロック モード処理で実行されます。操作が完了するまで呼び出しは戻りません。
- WMDM_MODE_THREAD 操作はスレッド モード処理で実行されます。呼び出しは直ちに戻り、操作はバックグラウンド スレッドで実行されます。
省略可能 WMDM_MODE_QUERY 挿入操作が成功し得るかどうかを判定するテストが行われますが、実際の挿入は実行されません。
次のいずれか 1 つ: WMDM_STORAGECONTROL_INSERTBEFORE オブジェクトは対象オブジェクトの前に挿入されます。
- WMDM_STORAGECONTROL_INSERTAFTER オブジェクトは対象オブジェクトの後に挿入されます。
- WMDM_STORAGECONTROL_INSERTINTO オブジェクトは現在のオブジェクトの中に挿入されます。これは現在のオブジェクトがフォルダーの場合にのみ機能します。
省略可能 WMDM_FILE_CREATE_OVERWRITE オブジェクトは対象オブジェクトを置き換えます。
次のいずれか 1 つ: WMDM_CONTENT_FILE 挿入されるコンテンツはファイルです。
- WMDM_CONTENT_FOLDER 挿入されるコンテンツはフォルダーです。この場合、フォルダーの中身は転送されません。
省略可能 WMDM_CONTENT_OPERATIONINTERFACE アプリケーションは、データ転送を制御するために IWMDMOperation インターフェースを渡します。
0 個以上: WMDM_FILE_ATTR_READONLY デバイス上でストレージを読み取り専用に設定します。
- WMDM_FILE_ATTR_HIDDEN デバイス上でストレージを隠し属性に設定します。
- WMDM_FILE_ATTR_SYSTEM デバイス上でストレージをシステム属性に設定します。
省略可能 WMDM_MODE_PROGRESS 挿入が進行中です。
省略可能 (いずれか 1 つ): WMDM_MODE_TRANSFER_PROTECTED 挿入は保護された転送モードで行われます。
- WMDM_MODE_TRANSFER_UNPROTECTED 挿入は保護されない転送モードで行われます。
fuTypeDWORDin

現在のストレージを指定する、次のいずれかの種類。

説明
WMDM_FILE_ATTR_FILE 現在のストレージはファイルです。
WMDM_FILE_ATTR_FOLDER 現在のストレージはフォルダーです。
pwszFileSourceLPWSTRinoptional挿入操作の対象コンテンツの場所を示す、ワイド文字の null 終端文字列へのポインター。fuModeWMDM_CONTENT_OPERATIONINTERFACE を指定した場合、このパラメーターは NULL でなければなりません。プレイリストまたはアルバムを作成する場合は、NULL を指定できます。
pwszFileDestLPWSTRinoptionalデバイス上のファイル名 (省略可能)。指定されておらず、アプリケーションが pOperationIWMDMOperation ポインターを渡している場合、Windows Media Device Manager は IWMDMOperation::GetObjectName を呼び出して転送先の名前を要求します。指定されておらず、アプリケーションが pOperation を使用しない場合は、元のファイル名と拡張子が (パスを除いて) 使用されます。
pOperationIWMDMOperation*inoptionalメディア デバイスへのコンテンツ転送を制御する IWMDMOperation インターフェースへのポインター (省略可能)。指定する場合、fuModeWMDM_CONTENT_OPERATIONINTERFACE フラグを含める必要があります。fuModeWMDM_CONTENT_FILE または WMDM_CONTENT_FOLDER を指定した場合、このパラメーターは NULL でなければなりません。
pProgressIWMDMProgress*inoptional処理の進行状況をアプリケーションに報告する IWMDMProgress インターフェースへのポインター (省略可能)。このパラメーターには NULL を指定できます。
pMetaDataIWMDMMetaData*inoptionalメタデータ オブジェクトへのポインター (省略可能)。新しいメタデータ オブジェクトは IWMDMStorage3::CreateEmptyMetadataObject を呼び出して作成します。このパラメーターを使用すると、デバイス上でのオブジェクト作成時に設定するメタデータ (フォーマットを含む) を指定でき、後からメタデータを設定するよりも効率的です。ファイル フォーマット (g_wszWMDMFormatCode で指定) は必ず設定してください。このメソッドの使用時にファイルのフォーマット コードを指定しないと、MTP デバイスではそのファイルがユーザー インターフェイスに表示されず、MTP 以外のデバイスでは動作が予測できなくなります。
pUnknownIUnknown*inoptionalセキュア コンテンツ プロバイダーに渡す任意のカスタム COM オブジェクトの IUnknown ポインター (省略可能)。これにより、アプリケーションがセキュア コンテンツ プロバイダーについて十分な情報を持っている場合に、カスタム情報をセキュア コンテンツ プロバイダーへ渡すことができます。
ppNewObjectIWMDMStorage**inoutoptional新しいコンテンツを保持する IWMDMStorage インターフェースへのポインター。呼び出し元は、使用を終えたらこのインターフェースを解放する必要があります。

戻り値

このメソッドは HRESULT を返します。Windows Media Device Manager のすべてのインターフェース メソッドは、次のいずれかの分類のエラー コードを返す可能性があります。

考えられるエラー コードの詳細な一覧については、Error Codes を参照してください。

解説(Remarks)

ストレージをデバイスへ送信した後にメタデータを設定することもできますが、このメソッドの pMetaData パラメーターで情報を設定する方が効率的です。そうすることで、デバイスに追加情報が提供され、ファイルを適切に転送・処理したり (たとえば正しい場所へ保存するなど)、有用な情報 (画像に対してユーザーが記述した説明など) を表示したりできるようになります。

Windows Portable Devices (WPD) デバイスのプロパティを設定するには、アプリケーションは IPortableDeviceValues オブジェクトを作成し、各プロパティをこのコレクションに設定します。次に、アプリケーションはそのコレクションをバイナリ ラージ オブジェクト (BLOB) にシリアル化します。データをシリアル化したら、g_wszWPDPassthroughPropertyValues メタデータ定数を使用して、pMetadata 引数が参照する IWMDMMetaData に追加します。

WMDM_MODE_THREAD フラグを指定した場合は、IWMDMProgress2::End2 または IWMDMProgress3::End3 を呼び出して完了状態を取得してください。これらのメソッドは操作が完了したことを保証し、成功または失敗の情報を含む HRESULT も返します。

アプリケーションが WMDM_MODE_THREAD を使用し、null ではない pProgress パラメーターを渡す場合、Windows Media Device Manager がそのオブジェクトへ進行状況の通知を送信するため、読み取り操作が完了するまで pProgress が属するオブジェクトが破棄されないようにする必要があります。このオブジェクトは、終了通知を受け取った後にのみ破棄できます。これを守らないとアクセス違反が発生します。

プレイリストなどの参照オブジェクトを作成する場合、"挿入" されるオブジェクトは実際にはデータを含まず、他のオブジェクト (音楽ファイルなど) へのメタデータ参照の集まりとしてデバイス上に格納されるだけです。このような "抽象" オブジェクトの作成については、Creating a Playlist on the Device を参照してください。

次の C++ 関数は、ファイルをデバイスへ送信します。転送の一環として、新しいストレージの種類を指定するメタデータをストレージに追加する必要があります。


HRESULT mySendFile(LPCWSTR pwszFileName, IWMDMStorage* pStorage, IWMDMOperation* pOperation)
{
   HRESULT hr = S_OK;

   // A dummy loop to handle unrecoverable errors. When we hit an error we
   // can't handle or don't like, we just use a 'break' statement.
   // The custom BREAK_HR macro checks for failed HRESULT values and does this.
   do
   {
      if (pwszFileName == NULL || pStorage == NULL)
      {
         BREAK_HR(E_POINTER,"","Bad pointer passed in.");
         return E_POINTER;
      }

      // Make sure the destination is a folder.
      DWORD attributes = 0;
      _WAVEFORMATEX format;
      hr = pStorage->GetAttributes(&attributes, &format);
      if (!(attributes | WMDM_FILE_ATTR_FOLDER))
      {
         BREAK_HR(E_FAIL, "", "Storage submitted to mySendFile is not a folder.");
         return E_FAIL;
      }

      // Transcode the file
      hr = myTranscodeMethod(pwszFileName);
      BREAK_HR(hr, "Couldn't transcode the file in mySendFile.", "Transcoded the file in mySendFile.");
      //
      // Let's set some metadata in the storage.
      //
      CComPtr<IWMDMStorage3> pStorage3;
      hr = pStorage->QueryInterface(__uuidof(IWMDMStorage3), (void**)(&pStorage3));
      BREAK_HR(hr, "Got an IWMDMStorage3 interface in mySendFile.","Couldn't get an IWMDMStorage3 in mySendFile.");

      // First create the IWMDMMetaData interface.
      IWMDMMetaData* pMetadata;
      hr = pStorage3->CreateEmptyMetadataObject(&pMetadata);
      BREAK_HR(hr,"Created an IWMDMMetaData interface in mySendFile.","Couldn't create an IWMDMMetaData interface in mySendFile.");

      //
      // Set the file format.
      //
      WMDM_FORMATCODE fileFormat = myGetWMDM_FORMATCODE(pwszFileName);
      hr = pMetadata->AddItem(WMDM_TYPE_DWORD, g_wszWMDMFormatCode, (BYTE*)&fileFormat, sizeof(WMDM_TYPE_DWORD));


      //
      // Get the proper interface and transfer the file.
      //
      CComPtr<IWMDMStorageControl3> pStgCtl3;
      CComPtr<IWMDMStorage> pNewStorage;
      hr = pStorage->QueryInterface(__uuidof(IWMDMStorageControl3),(void**)(&pStgCtl3));

      // Get the simple file name to use for the destination file.
      wstring destFile = pwszFileName;
      destFile = destFile.substr(destFile.find_last_of(L"\\") + 1);

      // Get a progress indicator.
      CComQIPtr<IWMDMProgress> pProgress(this);

      // Set the flags for the operation.
      UINT flags = WMDM_MODE_BLOCK | // Synchronous call. 
         WMDM_STORAGECONTROL_INSERTINTO | // Insert it into the destination folder.
         WMDM_CONTENT_FILE | // We're inserting a file.
         WMDM_FILE_CREATE_OVERWRITE; // Overwrite existing files.
      if (pOperation != NULL)
         flags |= WMDM_CONTENT_OPERATIONINTERFACE;

      // Send the file and metadata.
      hr = pStgCtl3->Insert3(
         flags,
         WMDM_FILE_ATTR_FOLDER, // The current storage is a folder.
         const_cast<WCHAR*>(pwszFileName), // Source file.
         NULL, // Destination file name.
         pOperation, // Null to allow Windows Media Device Manager to read 
                     // the file; non-null to present raw data bytes to 
                     // Windows Media Device Manager.
         pProgress, // Interface to send simple progress notifications.
         pMetadata, // IWMDMMetaData interface previously created and filled.
         NULL, 
         &pNewStorage);
      if (FAILED(hr))
         m_pLogger->LogDword(WMDM_LOG_SEV_ERROR, NULL, "Error calling Insert3 in mySendFile: %lX", hr);
      BREAK_HR(hr, "Wrote a file to the device in mySendFile", "Couldn't write to the device in mySendFile.");

   } while (FALSE); // End of dummy loop

   return hr;
}
出典・ライセンス: 上記「公式ドキュメント」の内容は 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_IWMDMStorageControl3 "{B3266365-D4F3-4696-8D53-BD27EC60993A}"
#usecom global IWMDMStorageControl3 IID_IWMDMStorageControl3 "{}"
#comfunc global IWMDMStorageControl3_Insert3  9 int,int,wstr,wstr,sptr,sptr,sptr,sptr,sptr
; ※数字は vtbl インデックス(0始まり)。0/1/2 は IUnknown(QueryInterface/AddRef/Release)。
; ※このインターフェースは直接 CoCreateInstance するクラスIDが無いため "{}"(他メソッド/アクティベーションで取得)。
; ※ハンドル/void*等の不透明ポインタは IronHSP では intptr 指定が可能。