右クリックによるドラッグ&ドロップ時のドロップ先のパスを取得する

右クリックでファイルやフォルダをマウスでドラッグ&ドロップすると,「ここにコピー」や「ここに移動」のようなコンテキストメニューが表示されます.

このメニューで「ここに〜」を選択すると,マウスでドロップしたフォルダへ該当の処理(コピー,移動,...)が行われる訳ですが,「ドロップ先のパス」はどうやって取得しているのか分からなかったので調べてみました.

HRESULT Initialize(
  [in]  PCIDLIST_ABSOLUTE pidlFolder,
  [in]  IDataObject *pdtobj,
  [in]  HKEY hkeyProgID
);

・・・(中略)・・・
A pointer to an ITEMIDLIST structure that uniquely identifies a folder. For property sheet extensions, this parameter is NULL. For shortcut menu extensions, it is the item identifier list for the folder that contains the item whose shortcut menu is being displayed. For nondefault drag-and-drop menu extensions, this parameter specifies the target folder.

IShellExtInit::Initialize method (Windows)

右クリックによるドラッグ&ドロップの場合,IShellExtInit::Initialize の引数 pidFolder にドロップ先の PID? が設定されているようなので,この関数を実装する際に PID から該当パスを記憶しておくようです.

STDMETHODIMP Initialize(LPCITEMIDLIST pIDFolder, LPDATAOBJECT pDataObj, HKEY hKeyID) {
    // ...
    
    if(pIDFolder) {
        this->IsDragAndDrop_ = true;
        TCHAR buffer[MAX_PATH] = {};
        ::SHGetPathFromIDList(pIDFolder, buffer);
        this->DropPath_ = buffer;
    }
    else this->IsDragAndDrop_ = false;
    
    // ...
}