问题描述

当双击打开自定义格式的文件时,希望使用当前正在运行的进程,而不是另起一个进程。

本文介绍一种方式解决如上问题,方案参考user3582780的解答

设置自定义文件格式的默认打开方式

参考链接,具体步骤如下:

  1. 在HKEY_CLASSES_ROOT中新建项,命名为自定义文件格式(如.custom),设置其默认值(如mycustom);
  2. 在HKEY_CLASSES_ROOT中新建项,命名为步骤1中的默认值,即mycustom;
  3. 在mycustom中新建项,命名为DefaultIcon,设置默认值(Icon路径);
  4. 在mycustom中新建项,命名为shell,在shell中继续新建项open,在open中新建项command,设置其默认值(格式:程序路径 "%1")

使用当前实例打开文件

首先,当双击自定义格式文件进行打开时,会将该文件的路径作为参数传递给程序,因此打开程序应响应启动参数。

在WPF应用程序中,Application的OnStartup方法会携带程序的启动参数(通过Environment也可获取启动参数)。

当双击自定义格式文件时,若有一个实例正在运行,并不会直接使用该实例打开文件,而是会重新打开一个实例。此时需要将新实例的启动参数传递给当前实例并关闭新实例。

本文使用发送窗口消息的方式处理该问题,即使用Win32的SendMessage接口发送参数给当前实例窗口,当前实例响应消息处理即可。具体实现方案如下:

// App
private static Mutex mutex;
protected override void OnStartup(StartupEventArgs e)
{
mutex = new Mutex(true, "myapp", out bool ret); if(!ret)
Reopen(e); // ...
} private void Reopen(StartupEventArgs e)
{
// IntPtr hwnd = FindWindow(null, "window title");
if(e.Args.Length > 0)
SendMessage(); Environment.Exit(0);
} private void SendMessage(IntPtr hwnd, string data)
{
CopyDataStruct cds = new CopyDataStruct();
try
{
cds.cbData = (data.Length + 1) * 2; // number of bytes
cds.lpData = Win32.LocalAlloc(0x40, cds.cbData); // known local-pointer in RAM
Marshal.Copy(data.ToCharArray(), 0, cds.lpData, data.Length); // Copy data to preserved local-pointer
cds.dwData = (IntPtr)1;
SendMessage(hwnd, WM_COPYDATA, IntPtr.Zero, ref cds);
}
finally
{
cds.Dispose();
}
} // Window
private IntPtr WndProc(IntPtr hwnd, int msg, IntPtr wParam, IntPtr lParam, ref bool handled)
{
if(msg == WM_COPYDATA)
{
CopyDataStruct st = (CopyDataStruct)Marshal.PtrToStructure(lParam, typeof(CopyDataStruct));
string strData = Marshal.PtrToStringUni(st.lpData);
OpenFile(strData);
Activate();
} return IntPtr.Zero;
}

WPF -- 使用当前进程打开自定义文件的一种方式的更多相关文章

  1. C#中的Excel操作【1】——设置Excel单元格的内容,打开Excel文件的一种方式

    前言 作为项目管理大队中的一员,在公司里面接触最多的就是Excel文件了,所以一开始就想从Excel入手,学习简单的二次开发,开始自己的编程之路! 程序界面 功能说明 打开文件按钮,可以由使用者指定要 ...

  2. Linux 利用进程打开的文件描述符(/proc)恢复被误删文件

    Linux 利用进程打开的文件描述符(/proc)恢复被误删文件 在 windows 上删除文件时,如果文件还在使用中,会提示一个错误:但是在 linux 上删除文件时,无论文件是否在使用中,甚至是还 ...

  3. s11.1 lsof:查看进程打开的文件

    功能说明 lsof 全名为list open files,也就是列举系统中已经被打开的文件,通过lsof命令,就可以根据文件找到对应的进程信息,也可以根据进程信息找到进程打开的文件. [语法格式] l ...

  4. lsof恢复进程打开的文件

    工作原理:进程每打开文件都会生成一个文件句柄FD来标识一个文件,进程打开的文件如果没有被释放,可以通过文件句柄FD来恢复删除的文件 注意:适合恢复进程一直在打开一个文件,例如日志文件,如果配置文件进程 ...

  5. Linux 系统管理命令 - lsof - 查看进程打开的文件

    命令详解 重要星级: ★★★★★ 功能说明: 全名为 list open files,也就是列举系统中已经被打开的文件,通过 lsof 命令,就可以根据文件找到对应的进程信息,也可以根据进程信息找到进 ...

  6. lsof 查看打开了一个文件的有哪些进程 统计那个进程打开的文件最多

    lsof | grep /lib64/libc-2.12.so | wc   == 查看打开了一个文件的有哪些进程 lsof | awk '{print $2,$1}' | sort | uniq - ...

  7. 打开cad文件的几种方法

    转自原文 打开cad文件的几种方法 IWorkspaceFactory pWorkspaceFactory; IFeatureWorkspace pFeatureWorkspace; IFeature ...

  8. 加载xib文件的两种方式

    一.加载xib文件的两种方式 1.方法一(NewsCell是xib文件的名称) NSArray *objects = [[NSBundle mainBundle] loadNibNamed:@&quo ...

  9. PHP导出excel文件的几种方式

    PHP导出excel文件的几种方式 先说说动态生成的内容当作文件来下载的方法: 1.通过把Content-Type设置为application/octet-stream,可以把动态生成的内容当作文件来 ...

随机推荐

  1. regex read once bug

    regex read once bug read once bug StackOverflow Question https://stackoverflow.com/questions/5916796 ...

  2. DOMParser & SVG

    DOMParser & SVG js parse html to dom https://developer.mozilla.org/zh-CN/docs/Web/API/DOMParser ...

  3. NGK乘势而上打造生态所,建立全方位的区块链生态系统

    当金融理财变成了生活的一部分,购买金融衍生品的眼光成为了影响生活质量重要组成部分.这是一个不缺少黄金的年代,一夜间实现财务自由的故事每天都在上演,但是由于太多人缺少发现黄金的眼睛,只能被财富和机遇拒之 ...

  4. DeFi热下的冷思考 NGK以更深层次的方式参与DeFi建设

    独具慧眼,深度挖掘DeFi潜力项目 作为早期DeFi的探索者和推动者,NGK在此轮热潮席卷市场前就已经开始构建自己的DeFi生态,独具慧眼的NGK上线了Baccarat流动性挖矿项目,完成了首个由平台 ...

  5. Python 股票市场分析实战

    目标: 1.股票数据获取 2.历史趋势分析及可视化 3.风险分析 实验数据:来源于Yahoo Finance / Stooq,该网站提供了很多API接口,本文用的工具是pandas-datareade ...

  6. apply方法的实现原理

    apply 的核心原理: 将函数设为对象的属性 执行和删除这个函数 指定 this 到函数并传入给定参数执行函数 如果不传参数,默认指向 window Function.prototype.myApp ...

  7. spring boot的 yml和properties的对比

    Spring Boot 虽然做了大量的工作来简化配置,但其配置依然是相当的复杂!支持的外部配置方式就有很多种,笔者没有去统计,也许是为了灵活使用吧.   application.yml 和 appli ...

  8. Django Static与Media

    关于Django中Static和Media的设置问题(尤其是css和js静态文件加载的问题),网上有很多回答,但是发现有相当一部分回答并不能解决问题.有的可能是Django版本问题,有的是把media ...

  9. JavaFX桌面应用-版本升级

    好久没有写博客,2021年就以 "JavaFX桌面应用-版本升级" 开篇吧,记录一下JavaFX应用版本升级的开发流程. 桌面应用升级的方案应该很多,这里只是自己想到的方案. 1. ...

  10. Python3+pygame实现Windows经典扫雷

    今天给大家分享一个由Python3(当然python3.5 3.6 3.7 3.8 ...都行)与pygame模块结合制作的一个经典小游戏"扫雷" 代码是完全可运行的,请大家放心运 ...