using Microsoft.Win32; using System; using System.Collections.Generic; using System.IO; using System.Linq; using System.Reflection; using System.Runtime.InteropServices; using System.Security.Principal; using System.Text; using System.Threading.Tasks; namespace PDF_Master.Helper { /// /// 设置成默认阅读器的辅助类 /// public static class Win32Helper { [StructLayout(LayoutKind.Sequential)] public struct SECURITY_ATTRIBUTES { public int nLength; public IntPtr lpSecurityDescriptor; public int bInheritHandle; } [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)] public struct STARTUPINFO { public Int32 cb; public string lpReserved; public string lpDesktop; public string lpTitle; public Int32 dwX; public Int32 dwY; public Int32 dwXSize; public Int32 dwYSize; public Int32 dwXCountChars; public Int32 dwYCountChars; public Int32 dwFillAttribute; public Int32 dwFlags; public Int16 wShowWindow; public Int16 cbReserved2; public IntPtr lpReserved2; public IntPtr hStdInput; public IntPtr hStdOutput; public IntPtr hStdError; } [StructLayout(LayoutKind.Sequential)] public struct PROCESS_INFORMATION { public IntPtr hProcess; public IntPtr hThread; public int dwProcessId; public int dwThreadId; } [Flags] public enum HChangeNotifyEventID { SHCNE_ALLEVENTS = 0x7FFFFFFF, SHCNE_ASSOCCHANGED = 0x08000000, SHCNE_ATTRIBUTES = 0x00000800, SHCNE_CREATE = 0x00000002, SHCNE_DELETE = 0x00000004, SHCNE_DRIVEADD = 0x00000100, SHCNE_DRIVEADDGUI = 0x00010000, SHCNE_DRIVEREMOVED = 0x00000080, SHCNE_EXTENDED_EVENT = 0x04000000, SHCNE_FREESPACE = 0x00040000, SHCNE_MEDIAINSERTED = 0x00000020, SHCNE_MEDIAREMOVED = 0x00000040, SHCNE_MKDIR = 0x00000008, SHCNE_NETSHARE = 0x00000200, SHCNE_NETUNSHARE = 0x00000400, SHCNE_RENAMEFOLDER = 0x00020000, SHCNE_RENAMEITEM = 0x00000001, SHCNE_RMDIR = 0x00000010, SHCNE_SERVERDISCONNECT = 0x00004000, SHCNE_UPDATEDIR = 0x00001000, SHCNE_UPDATEIMAGE = 0x00008000, } [Flags] public enum HChangeNotifyFlags { SHCNF_DWORD = 0x0003, SHCNF_IDLIST = 0x0000, SHCNF_PATHA = 0x0001, SHCNF_PATHW = 0x0005, SHCNF_PRINTERA = 0x0002, SHCNF_PRINTERW = 0x0006, SHCNF_FLUSH = 0x1000, SHCNF_FLUSHNOWAIT = 0x2000 } [Flags] public enum FileMapProtection : uint { PageReadonly = 0x02, PageReadWrite = 0x04, PageWriteCopy = 0x08, PageExecuteRead = 0x20, PageExecuteReadWrite = 0x40, SectionCommit = 0x8000000, SectionImage = 0x1000000, SectionNoCache = 0x10000000, SectionReserve = 0x4000000, } [Flags] public enum FileMapAccessType : uint { Copy = 0x01, Write = 0x02, Read = 0x04, AllAccess = 0x08, Execute = 0x20, } [DllImport("kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)] public static extern bool CreateProcess(string lpApplicationName, string lpCommandLine, ref SECURITY_ATTRIBUTES lpProcessAttributes, ref SECURITY_ATTRIBUTES lpThreadAttributes, bool bInheritHandles, uint dwCreationFlags, IntPtr lpEnvironment, string lpCurrentDirectory, [In] ref STARTUPINFO lpStartupInfo, out PROCESS_INFORMATION lpProcessInformation); [DllImport("kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)] public static extern uint GetModuleFileName([In] IntPtr hModule, [Out] StringBuilder lpFilename, [In][MarshalAs(UnmanagedType.U4)] int nSize); [DllImport("kernel32.dll")] public static extern void ExitProcess(uint uExitCode); [DllImport("shell32.dll")] static extern void SHChangeNotify(HChangeNotifyEventID wEventId, HChangeNotifyFlags uFlags, IntPtr dwItem1, IntPtr dwItem2); [DllImport("kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)] public static extern UInt32 WaitForSingleObject(IntPtr hHandle, UInt32 dwMilliseconds); [DllImport("User32.dll", SetLastError = true, CharSet = CharSet.Auto)] public static extern uint RegisterWindowMessage(string lpString); [DllImport("User32.dll", SetLastError = true, CharSet = CharSet.Auto)] public static extern int PostMessage(IntPtr hWnd, uint msg, IntPtr wParam, IntPtr lParam); [DllImport("kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)] public static extern bool SetEvent(IntPtr hEvent); [DllImport("kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)] public static extern IntPtr CreateFileMapping(IntPtr hFile, IntPtr lpFileMappingAttributes, FileMapProtection flProtect, uint dwMaximumSizeHigh, uint dwMaximumSizeLow, [MarshalAs(UnmanagedType.LPStr)] string lpName); [DllImport("kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)] public static extern IntPtr MapViewOfFileEx(IntPtr hFileMappingObject, FileMapAccessType dwDesiredAccess, uint dwFileOffsetHigh, uint dwFileOffsetLow, UIntPtr dwNumberOfBytesToMap, IntPtr lpBaseAddress); [DllImport("Kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)] public static extern int UnmapViewOfFile(IntPtr lpBaseAddress); [DllImport("Kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)] public static extern bool CloseHandle(IntPtr hObject); [DllImport("Kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)] public static extern IntPtr OpenFileMapping(int dwDesiredAccess, int bInheritHandle, [MarshalAs(UnmanagedType.LPStr)] string lpName); [DllImport("Kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)] public static extern IntPtr CreateEvent(IntPtr lpEventAttributes, bool bManualReset, bool bInitialState, string lpName); [DllImport("Kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)] public static extern IntPtr OpenEvent(uint dwDesiredAccess, bool bInheritHandle, string lpName); /// /// 注册为默认PDF浏览器 /// /// /// public static bool RegisterDefaultApp(bool isDefault) { bool isWin8OrHigher = false; if (Environment.OSVersion.Version.Major > 6 || (Environment.OSVersion.Version.Major == 6 && Environment.OSVersion.Version.Minor > 1)) { isWin8OrHigher = true; } try { AssemblyName assemblyName = Assembly.GetExecutingAssembly().GetName(); /*********** register APP Path *******************/ RegistryKey appPathKey = Registry.LocalMachine.OpenSubKey("SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\App Paths", true); if (appPathKey == null) { return false; } RegistryKey appKey = appPathKey.CreateSubKey(assemblyName.Name + ".exe"); if (appKey != null) { appKey.SetValue("", Assembly.GetExecutingAssembly().Location); appKey.SetValue("Path", Directory.GetParent(assemblyName.FullName).FullName); appKey.Close(); } appPathKey.Close(); /*********** register ProgID *******************/ RegistryKey progIdKey = Registry.ClassesRoot.CreateSubKey(assemblyName.Name + ".pdf.1"); if (progIdKey == null) { return false; } progIdKey.SetValue("", assemblyName.Name); RegistryKey openKey = progIdKey.CreateSubKey("Shell\\Open\\Command"); openKey.SetValue("", Assembly.GetExecutingAssembly().Location + " \"%s\" \"%1\""); openKey.Close(); progIdKey.Close(); /*********** register Default File Association *******************/ RegistryKey softwareKey = Registry.LocalMachine.CreateSubKey("Software\\" + assemblyName.Name); if (softwareKey == null) { return false; } RegistryKey capabKey = softwareKey.CreateSubKey("Capabilities\\FileAssociations"); capabKey.SetValue(".pdf", assemblyName.Name + ".pdf.1"); capabKey.Close(); capabKey = softwareKey.CreateSubKey("Capabilities", true); capabKey.SetValue("ApplicationDescription", assemblyName.Name); capabKey.Close(); softwareKey.Close(); /*********** register Default App List *******************/ RegistryKey regiserAppKeys = Registry.LocalMachine.OpenSubKey("SOFTWARE\\RegisteredApplications", true); if (regiserAppKeys == null) { return false; } regiserAppKeys.SetValue(assemblyName.Name, "SOFTWARE\\" + assemblyName.Name + "\\Capabilities"); regiserAppKeys.Close(); Registry.ClassesRoot.SetValue(".pdf", assemblyName.Name + ".pdf.1"); if (isDefault) { if (isWin8OrHigher) { PROCESS_INFORMATION pInfo = new PROCESS_INFORMATION(); STARTUPINFO sInfo = new STARTUPINFO(); SECURITY_ATTRIBUTES pSec = new SECURITY_ATTRIBUTES(); SECURITY_ATTRIBUTES tSec = new SECURITY_ATTRIBUTES(); pSec.nLength = Marshal.SizeOf(pSec); tSec.nLength = Marshal.SizeOf(tSec); string commandLine = " \".pdf\" \"" + assemblyName.Name + ".pdf.1\""; CreateProcess("Resources\\exe\\SFTA.exe", commandLine, ref pSec, ref tSec, false, 0, IntPtr.Zero, null, ref sInfo, out pInfo); WaitForSingleObject(pInfo.hProcess, 3000); } else { RegistryKey defaultKey = Registry.CurrentUser.CreateSubKey("SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Explorer\\FileExts\\.pdf\\UserChoice", true); defaultKey.SetValue("ProgId", assemblyName.Name + ".pdf.1"); defaultKey.Close(); SHChangeNotify(HChangeNotifyEventID.SHCNE_ASSOCCHANGED, HChangeNotifyFlags.SHCNF_IDLIST, IntPtr.Zero, IntPtr.Zero); } } else { RegistryKey defaultKey = Registry.CurrentUser.OpenSubKey("SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Explorer\\FileExts\\.pdf", true); RegistryKey userChoice = defaultKey.OpenSubKey("UserChoice"); string checkId = userChoice.GetValue("ProgId").ToString(); if (checkId == (assemblyName.Name + ".pdf.1") || checkId == "PDF Technologies, Inc..PDF Master") { defaultKey.DeleteSubKey("UserChoice"); SHChangeNotify(HChangeNotifyEventID.SHCNE_ASSOCCHANGED, HChangeNotifyFlags.SHCNF_IDLIST, IntPtr.Zero, IntPtr.Zero); } defaultKey.Close(); } return true; } catch { } return false; } /// /// 判断是否是默认pdf阅读器 /// /// public static bool IsDefaultApp() { try { AssemblyName assemblyName = Assembly.GetExecutingAssembly().GetName(); var asm = Assembly.GetExecutingAssembly(); RegistryKey defaultKey = Registry.CurrentUser.OpenSubKey("SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Explorer\\FileExts\\.pdf\\UserChoice"); AssemblyCompanyAttribute asmcpn = (AssemblyCompanyAttribute)Attribute.GetCustomAttribute(asm, typeof(AssemblyCompanyAttribute)); AssemblyProductAttribute aspro = (AssemblyProductAttribute)Attribute.GetCustomAttribute(asm, typeof(AssemblyProductAttribute)); string id = string.Format("{0}.{1}", asmcpn.Company, aspro.Product); if (defaultKey != null) { string checkId = defaultKey.GetValue("ProgId").ToString(); if (checkId == "PDF Technologies, Inc..PDF Reader Pro" || checkId == id) { return true; } defaultKey.Close(); if (checkId == (assemblyName.Name + ".pdf.1")) { return true; } } } catch { } return false; } /// /// 判断当前程序是否以管理员身份运行 /// /// public static bool IsRunAsAdmin() { WindowsIdentity id = WindowsIdentity.GetCurrent(); WindowsPrincipal principal = new WindowsPrincipal(id); return principal.IsInRole(WindowsBuiltInRole.Administrator); } } }