เปิดโฟลเดอร์ใน explorer และเลือกไฟล์


150

ฉันพยายามเปิดโฟลเดอร์ใน explorer โดยเลือกไฟล์

รหัสต่อไปนี้สร้างไฟล์ที่ไม่พบข้อยกเว้น:

System.Diagnostics.Process.Start(
    "explorer.exe /select," 
    + listView1.SelectedItems[0].SubItems[1].Text + "\\" 
    + listView1.SelectedItems[0].Text);

ฉันจะรับคำสั่งนี้ให้ดำเนินการใน C # ได้อย่างไร

คำตอบ:


51

ใช้วิธีนี้ :

Process.Start(String, String)

อาร์กิวเมนต์แรกคือแอปพลิเคชัน (explorer.exe) อาร์กิวเมนต์วิธีที่สองเป็นอาร์กิวเมนต์ของแอปพลิเคชันที่คุณเรียกใช้

ตัวอย่างเช่น:

ใน CMD:

explorer.exe -p

ใน C #:

Process.Start("explorer.exe", "-p")

32
นี่ไม่ได้เลือกไฟล์เช่นคำตอบของซามูเอล
หยาง

-p ไม่เพียงพอที่จะเลือกไฟล์
Jek

327
// suppose that we have a test.txt at E:\
string filePath = @"E:\test.txt";
if (!File.Exists(filePath))
{
    return;
}

// combine the arguments together
// it doesn't matter if there is a space after ','
string argument = "/select, \"" + filePath +"\"";

System.Diagnostics.Process.Start("explorer.exe", argument);

1
มันมีความสำคัญสำหรับฉัน :) มันไม่เพียง แต่เปิดไดเรกทอรี แต่เลือกไฟล์โดยเฉพาะเช่นกัน :) ขอขอบคุณด้วย
InfantPro'Aravind '

2
มันใช้งานได้อย่างมีเสน่ห์ แต่มีความคิดใด ๆ ว่าเราจะทำอย่างนั้นกับไฟล์หลาย ๆ ไฟล์ได้อย่างไร?
Pankaj

7
โน้ตเล็ก ๆ อาร์กิวเมนต์ / select ที่มีเส้นทางไฟล์ดูเหมือนจะไม่ทำงานสำหรับฉันหากเส้นทางไฟล์ของฉันใช้เครื่องหมายทับซ้าย ดังนั้นฉันต้องทำ filePath = filePath.Replace ('/', '\\');
Victor Chelaru

6
ตามที่กล่าวไว้ที่อื่นพา ธ ของคุณควรอยู่ในเครื่องหมายคำพูดซึ่งจะช่วยป้องกันปัญหาเกี่ยวกับไดเรกทอรีหรือชื่อไฟล์ที่มีเครื่องหมายจุลภาค
Kaganar

4
ฉันกำลังต่อสู้กับปัญหาบางครั้งวิธีการข้างต้นไม่ได้ผลเนื่องจากไฟล์มีเครื่องหมายจุลภาค ถ้าฉันได้อ่านความคิดเห็นของ Kaganar มันจะช่วยให้ฉันทำงานได้หนึ่งชั่วโมง ฉันขอให้ซามูเอลหยางแก้ไขรหัสด้านบนเป็น: string argument = @ "/ select" + "\" "+ filePath +" \ ""
Wayne Lo

34

หากเส้นทางของคุณมีเครื่องหมายจุลภาคการใส่เครื่องหมายคำพูดรอบ ๆ เส้นทางจะทำงานเมื่อใช้ Process.Start (ProcessStartInfo)

มันจะไม่ทำงานเมื่อใช้ Process.Start (string, string) ดูเหมือนว่า Process.Start (สตริง, สตริง) จริงลบคำพูดใน args ของคุณ

นี่เป็นตัวอย่างง่ายๆที่เหมาะกับฉัน

string p = @"C:\tmp\this path contains spaces, and,commas\target.txt";
string args = string.Format("/e, /select, \"{0}\"", p);

ProcessStartInfo info = new ProcessStartInfo();
info.FileName = "explorer";
info.Arguments = args;
Process.Start(info);

นี่ควรเป็นคำตอบที่ยอมรับได้ มันขาดการจัดการข้อยกเว้นที่เหมาะสมสำหรับความล้มเหลวต่าง ๆ ที่เป็นไปได้ (ปัญหาสิทธิ์เส้นทางผิด ฯลฯ )
หยุด

นี่คือคำตอบที่ถูกต้องคำตอบที่ยอมรับไม่ได้ผลคำตอบของหยางก็ไม่ทำงานเช่นกัน
VK

31

เพียง 2 เซ็นต์ของฉันมีค่าถ้าชื่อไฟล์ของคุณมีช่องว่างเช่น "c: \ My File ประกอบด้วย Spaces.txt" คุณจะต้องล้อมชื่อไฟล์ด้วยเครื่องหมายคำพูดมิฉะนั้น explorer จะถือว่าคำ othe เป็นอาร์กิวเมนต์ที่ต่างกัน ...

string argument = "/select, \"" + filePath +"\"";

4
ที่จริงแล้วคุณไม่ทำ ตัวอย่างของ @Samuel Yang ทำงานกับเส้นทางพร้อมช่องว่าง (ทดสอบ Win7)
Courtney Christensen

8
อ่านคำตอบของ Phil Hustwick ด้านล่างว่าทำไมคุณควรใส่เครื่องหมายคำพูดไว้รอบ ๆ
Akku

18

ซามูเอลหยางตอบผมเพิ่มขึ้นนี่คือ 3 เซนต์ของฉันมีค่า

Adrian Hum ถูกต้องตรวจสอบให้แน่ใจว่าคุณใส่เครื่องหมายคำพูดรอบชื่อไฟล์ของคุณ ไม่ใช่เพราะมันไม่สามารถจัดการช่องว่างได้ตามที่ zourtney ชี้ให้เห็น แต่เพราะมันจะรับรู้เครื่องหมายจุลภาค (และตัวละครอื่น ๆ ) ในชื่อไฟล์เป็นอาร์กิวเมนต์แยกต่างหาก ดังนั้นควรดูตามที่ Adrian Hum แนะนำ

string argument = "/select, \"" + filePath +"\"";

1
และตรวจสอบให้แน่ใจว่าfilePathไม่มี"ในนั้น เห็นได้ชัดว่าตัวละครนี้ผิดกฎหมายในระบบ Windows แต่ได้รับอนุญาตจากผู้อื่นทั้งหมด (เช่นระบบ POSIXish) ดังนั้นคุณต้องใช้รหัสมากขึ้นหากคุณต้องการความสะดวกในการพกพา
binki

14

ใช้Process.Startบนexplorer.exeกับ/selectอาร์กิวเมนต์ทำงานผิดปกติเท่านั้นสำหรับเส้นทางที่น้อยกว่า 120 ตัวอักษรยาว

ฉันต้องใช้วิธี windows พื้นเมืองเพื่อให้มันทำงานในทุกกรณี:

[DllImport("shell32.dll", SetLastError = true)]
public static extern int SHOpenFolderAndSelectItems(IntPtr pidlFolder, uint cidl, [In, MarshalAs(UnmanagedType.LPArray)] IntPtr[] apidl, uint dwFlags);

[DllImport("shell32.dll", SetLastError = true)]
public static extern void SHParseDisplayName([MarshalAs(UnmanagedType.LPWStr)] string name, IntPtr bindingContext, [Out] out IntPtr pidl, uint sfgaoIn, [Out] out uint psfgaoOut);

public static void OpenFolderAndSelectItem(string folderPath, string file)
{
    IntPtr nativeFolder;
    uint psfgaoOut;
    SHParseDisplayName(folderPath, IntPtr.Zero, out nativeFolder, 0, out psfgaoOut);

    if (nativeFolder == IntPtr.Zero)
    {
        // Log error, can't find folder
        return;
    }

    IntPtr nativeFile;
    SHParseDisplayName(Path.Combine(folderPath, file), IntPtr.Zero, out nativeFile, 0, out psfgaoOut);

    IntPtr[] fileArray;
    if (nativeFile == IntPtr.Zero)
    {
        // Open the folder without the file selected if we can't find the file
        fileArray = new IntPtr[0];
    }
    else
    {
        fileArray = new IntPtr[] { nativeFile };
    }

    SHOpenFolderAndSelectItems(nativeFolder, (uint)fileArray.Length, fileArray, 0);

    Marshal.FreeCoTaskMem(nativeFolder);
    if (nativeFile != IntPtr.Zero)
    {
        Marshal.FreeCoTaskMem(nativeFile);
    }
}

สิ่งนี้ช่วยให้ฉันใช้โฟลเดอร์เดียวอีกครั้ง Process.Start ("explorer.exe", "/ select xxx") เปิดโฟลเดอร์ใหม่ทุกครั้ง!
Mitkins

นี่คือวิธีที่ควรทำฉันยังจะสร้างธงสำหรับ sfgao และส่งผ่าน enum นั้นแทน uint
L.Trabacchin

สิ่งนี้ใช้ได้แม้ว่าจะมีปัญหาเล็กน้อย ครั้งแรกที่โฟลเดอร์เปิดอยู่จะไม่มีการเน้น ฉันเรียกสิ่งนี้ว่าภายในวิธีการคลิกปุ่มและเมื่อโฟลเดอร์เปิดถ้าฉันคลิกปุ่มอีกครั้งมันจะไฮไลต์ไฟล์ / โฟลเดอร์ที่เลือก มีปัญหาอะไร
Sach

13

ใช้ "/select,c:\file.txt"

สังเกตเห็นว่าควรมีเครื่องหมายจุลภาคหลังจาก / เลือกแทนการเว้นวรรค ..


6

คุณต้องใส่อาร์กิวเมนต์เพื่อผ่าน ("/ select etc") ในพารามิเตอร์ตัวที่สองของวิธีการเริ่มต้น


5
string windir = Environment.GetEnvironmentVariable("windir");
if (string.IsNullOrEmpty(windir.Trim())) {
    windir = "C:\\Windows\\";
}
if (!windir.EndsWith("\\")) {
    windir += "\\";
}    

FileInfo fileToLocate = null;
fileToLocate = new FileInfo("C:\\Temp\\myfile.txt");

ProcessStartInfo pi = new ProcessStartInfo(windir + "explorer.exe");
pi.Arguments = "/select, \"" + fileToLocate.FullName + "\"";
pi.WindowStyle = ProcessWindowStyle.Normal;
pi.WorkingDirectory = windir;

//Start Process
Process.Start(pi)

5

สาเหตุที่เป็นไปได้มากที่สุดที่ไม่พบไฟล์คือพา ธ ที่มีช่องว่างตัวอย่างเช่นจะไม่พบ "explorer / select, c: \ space space \ space.txt"

เพียงเพิ่มเครื่องหมายคำพูดคู่ก่อนและหลังเส้นทางเช่น;

explorer /select,"c:\space space\space.txt"

หรือทำเช่นเดียวกันใน C # ด้วย

System.Diagnostics.Process.Start("explorer.exe","/select,\"c:\space space\space.txt\"");

1

อาจเป็น overkill นิดหน่อย แต่ฉันชอบฟังก์ชั่น convinience ลองใช้อันนี้:

    public static void ShowFileInExplorer(FileInfo file) {
        StartProcess("explorer.exe", null, "/select, "+file.FullName.Quote());
    }
    public static Process StartProcess(FileInfo file, params string[] args) => StartProcess(file.FullName, file.DirectoryName, args);
    public static Process StartProcess(string file, string workDir = null, params string[] args) {
        ProcessStartInfo proc = new ProcessStartInfo();
        proc.FileName = file;
        proc.Arguments = string.Join(" ", args);
        Logger.Debug(proc.FileName, proc.Arguments); // Replace with your logging function
        if (workDir != null) {
            proc.WorkingDirectory = workDir;
            Logger.Debug("WorkingDirectory:", proc.WorkingDirectory); // Replace with your logging function
        }
        return Process.Start(proc);
    }

นี่คือฟังก์ชั่นส่วนขยายที่ฉันใช้เป็น <string> .Quote ():

static class Extensions
{
    public static string Quote(this string text)
    {
        return SurroundWith(text, "\"");
    }
    public static string SurroundWith(this string text, string surrounds)
    {
        return surrounds + text + surrounds;
    }
}
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.