Ben*_*oit 7 .net windows explorer winapi windows-explorer
我正在开发一个Windows shell扩展,不幸的是,在更改DLL时,我必须重新启动Windows资源管理器(因为它将DLL保存在内存中).
我从Dino Esposito找到了这个程序,但它对我不起作用.
void SHShellRestart(void)
{
HWND hwnd;
hwnd = FindWindow("Progman", NULL );
PostMessage(hwnd, WM_QUIT, 0, 0 );
ShellExecute(NULL, NULL, "explorer.exe", NULL, NULL, SW_SHOW );
return;
}
Run Code Online (Sandbox Code Playgroud)
有人可以分享他们可以分享的东西吗?
PS我意识到我可以去任务管理器并杀死资源管理器进程,但我只是想以懒惰的方式去做.此外,这可实现自动化.
PPS我使用.NET进行开发,但shell重启功能可以是C,C++或.NET语言.它只是一个小的独立可执行文件.
Chu*_*nce 10
在解析了一些早期的答案并做了一些研究后,我在C#中创建了一个完整的例子.这将关闭资源管理器shell,然后等待它完全关闭并重新启动它.希望这会有所帮助,这个帖子中有很多有趣的信息.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Runtime.InteropServices;
using System.Diagnostics;
using System.Threading;
namespace RestartExplorer
{
class Program
{
[DllImport("user32.dll", SetLastError = true)]
static extern bool PostMessage(IntPtr hWnd, [MarshalAs(UnmanagedType.U4)] uint Msg, IntPtr wParam, IntPtr lParam);
[DllImport("user32.dll", SetLastError = true)]
static extern IntPtr FindWindow(string lpClassName, string lpWindowName);
const int WM_USER = 0x0400; //http://msdn.microsoft.com/en-us/library/windows/desktop/ms644931(v=vs.85).aspx
static void Main(string[] args)
{
try
{
var ptr = FindWindow("Shell_TrayWnd", null);
Console.WriteLine("INIT PTR: {0}", ptr.ToInt32());
PostMessage(ptr, WM_USER + 436, (IntPtr)0, (IntPtr)0);
do
{
ptr = FindWindow("Shell_TrayWnd", null);
Console.WriteLine("PTR: {0}", ptr.ToInt32());
if (ptr.ToInt32() == 0)
{
Console.WriteLine("Success. Breaking out of loop.");
break;
}
Thread.Sleep(1000);
} while (true);
}
catch (Exception ex)
{
Console.WriteLine("{0} {1}", ex.Message, ex.StackTrace);
}
Console.WriteLine("Restarting the shell.");
string explorer = string.Format("{0}\\{1}", Environment.GetEnvironmentVariable("WINDIR"), "explorer.exe");
Process process = new Process();
process.StartInfo.FileName = explorer;
process.StartInfo.UseShellExecute = true;
process.Start();
Console.ReadLine();
}
}
}
Run Code Online (Sandbox Code Playgroud)
小智 6
我注意到没有人解决启动explorer.exe作为shell的问题,而不是只打开一个资源管理器窗口.花了一些时间来弄清楚这一点,事实证明它很简单:
string explorer = string.Format("{0}\\{1}", Environment.GetEnvironmentVariable("WINDIR"), "explorer.exe");
Process process = new Process();
process.StartInfo.FileName = explorer;
process.StartInfo.UseShellExecute = true;
process.Start();
Run Code Online (Sandbox Code Playgroud)
您必须将StartInfo.UseshellExecute设置为true才能使其作为shell重新启动.
一个万无一失的解决方案:
foreach (Process p in Process.GetProcesses())
{
// In case we get Access Denied
try
{
if (p.MainModule.FileName.ToLower().EndsWith(":\\windows\\explorer.exe"))
{
p.Kill();
break;
}
}
catch
{ }
}
Process.Start("explorer.exe");
Run Code Online (Sandbox Code Playgroud)