たとえば、ファイルパスを渡すことができる関数をコーディングしたいと思います。
C:\FOLDER\SUBFOLDER\FILE.TXT
ファイルを含むフォルダーでWindowsエクスプローラーを開き、フォルダー内でこのファイルを選択します。 (多くのプログラムで使用されている「フォルダに表示」の概念に似ています。)
これどうやってするの?
Win32シェル関数を使用しない最も簡単な方法は、/select
パラメーターを指定してExplorer.exeを起動することです。たとえば、プロセスの起動
Explorer.exe /select,"C:\Folder\subfolder\file.txt"
file.txtが選択されたC:\ Folder\subfolderに新しいエクスプローラウィンドウが開きます。
新しいプロセスを起動せずにプログラムで実行する場合は、シェル関数 SHOpenFolderAndSelectItems
を使用する必要があります。これは、Explorer.exeに対する/select
コマンドです。内部的に使用します。これにはPIDLの使用が必要であり、シェルAPIの動作に慣れていない場合は、実際のPITAになる可能性があることに注意してください。
以下は、/select
アプローチの完全なプログラムによる実装で、@ Bhushanと@tehDorfからの提案のおかげでパスをクリーンアップしています。
public bool ExploreFile(string filePath) {
if (!System.IO.File.Exists(filePath)) {
return false;
}
//Clean up file path so it can be navigated OK
filePath = System.IO.Path.GetFullPath(filePath);
System.Diagnostics.Process.Start("Explorer.exe", string.Format("/select,\"{0}\"", filePath));
return true;
}
リファレンス: Explorer.exeコマンドラインスイッチ
パスに複数のスラッシュが含まれている場合にコマンドを実行すると、フォルダーが開かず、ファイルが適切に選択されませんファイルパスが次のようになっていることを確認してください
C:\ a\b\x.txt
の代わりに
C:\\ a \\ b \\ x.txt
@Mahmoud Al-Qudsiの回答をフォローアップします。彼が「プロセスを開始する」と言うとき、これは私のために働いたものです:
// assume variable "path" has the full path to the file, but possibly with / delimiters
for ( int i = 0 ; path[ i ] != 0 ; i++ )
{
if ( path[ i ] == '/' )
{
path[ i ] = '\\';
}
}
std::string s = "Explorer.exe /select,\"";
s += path;
s += "\"";
PROCESS_INFORMATION processInformation;
STARTUPINFOA startupInfo;
ZeroMemory( &startupInfo, sizeof(startupInfo) );
startupInfo.cb = sizeof( STARTUPINFOA );
ZeroMemory( &processInformation, sizeof( processInformation ) );
CreateProcessA( NULL, (LPSTR)s.c_str(), NULL, NULL, FALSE, 0, NULL, NULL, &startupInfo, &processInformation );
supportedメソッドは、Windows XP(つまり、Windows 2000以前ではサポートされていません)は SHOpenFolderAndSelectItems :
void OpenFolderAndSelectItem(String filename)
{
// Parse the full filename into a pidl
PIDLIST_ABSOLUTE pidl;
SFGAO flags;
SHParseDisplayName(filename, null, out pidl, 0, out flags);
try
{
// Open Explorer and select the thing
SHOpenFolderAndSelectItems(pidl, 0, null, 0);
}
finally
{
// Use the task allocator to free to returned pidl
CoTaskMemFree(pidl);
}
}