winform关于任务栏图标进程结束后图标无法自动清除的问题!(代码片段)

lpq21314 lpq21314     2022-12-22     178

关键词:

       最近在做一个项目,有2个进程,A进程需要定时把B进程强行kill掉,然后再启动,当时这样会有一个问题,就是强行kill掉的进程在任务栏的托盘图标不会自动消失,必须用鼠标经过那个位置才会消失。这样就导致事件久了,任务栏出现一大堆图标,非常影响形象。

      后来网上看到一个方法,说是通过进程间的通讯,就是由A发送通知给B,告诉B应该要退出程序了,然后由B自己来结束进程,这样任务栏的图标才会正常的消失。废话少说,直接看代码吧:

对于A进程来说,需要先找到B进程的句柄,然后才能给它发送通知,代码如下:

/// <summary>
        /// 根据端口号结束某个进程
        /// </summary>
        /// <param name="port">端口号,如:7012  </param>
        /// <returns></returns>
        private void KillPortProcess(int port)
         
            int pid = 0;

            try
            
                IntPtr hwnd = FindWindow(null, port.ToString());
                int ihWnd = (int)hwnd;
                GetWindowThreadProcessId(hwnd, out pid);
                var p = Process.GetProcessById(pid);
                if (p != null)
                
                    if (p.ProcessName == "MySvr")
                    
                        //强制杀掉进程(这种模式不能自动销毁任务栏图标)
                        //p.Kill();                        
                          
                        //利用发送消息方式,通知进程自杀(这种模式可以自动销毁任务栏图标)
                        byte[] sarr = System.Text.Encoding.Default.GetBytes("SelfKill");
                        int len = sarr.Length;
                        COPYDATASTRUCT cds;

                        cds.dwData = (IntPtr)Convert.ToInt16("1");//可以是任意值 
                        cds.cbData = len + 1;//指定lpData内存区域的字节数 
                        cds.lpData = "SelfKill";//发送给目标窗口所在进程的数据

                        int iflag = SendMessage(ihWnd, WM_COPYDATA, 0, ref cds); 
                    
                
            
            catch (Exception e)
             
             
        

我这个函数是根据进程的窗体标题来查找的,因为我的标题都是一个固定的端口号,所以按这种方式来做,当然也可以根据进程名称来做,在这里就不举例了。

这里用到了Windows的API函数:  SendMessage  , 要引用这个函数,必须事先做以下的声明才能使用:

 消息结构体:

public struct COPYDATASTRUCT
    

        public IntPtr dwData;

        public int cbData;

        [MarshalAs(UnmanagedType.LPStr)]

        public string lpData;

    

声明要引用的API函数:

        [DllImport("User32.dll", EntryPoint = "FindWindow")]
        public static extern IntPtr FindWindow(string lpClassName, string lpWindowName);

        [DllImport("user32", EntryPoint = "GetWindowThreadProcessId")]
        public static extern int GetWindowThreadProcessId(IntPtr hwnd, out int pid);

        [DllImport("User32.dll", EntryPoint = "SendMessage")]
        private static extern int SendMessage(int hWnd, int Msg, int wParam, ref COPYDATASTRUCT lParam);
 

        const int WM_COPYDATA = 0x004A;

-------------------------------------------------------------------------------------------------------------------------------------------------------

那么对于B进程来说,需要做的事情就是接收A进程发来的消息,根据消费的内容来做出对应的动作,

只要重载 DefWndProc 函数即可实现消息的接收处理,代码如下:

/// <summary>
        /// 消息接受处理函数
        /// </summary>
        /// <param name="m"></param>
        protected override void DefWndProc(ref Message m)
        

            switch (m.Msg)
            

                case WM_COPYDATA: 
                    COPYDATASTRUCT cds = new COPYDATASTRUCT(); 
                    Type t = cds.GetType(); 
                    cds = (COPYDATASTRUCT)m.GetLParam(t); 
                    string strResult = cds.dwData.ToString() + ":" + cds.lpData;

                    AppendText(strResult);
                     
                    //强制退出
                    if (strResult == "1:SelfKill")
                    
                        Thread.Sleep(1000);
                        this.mainNotifyIcon.Dispose();
                        Application.Exit();
                    
                    break; 
                default: 
                    base.DefWndProc(ref m); 
                    break; 
            

        

在B进程退出前,只要把 NotifyIcon.Dispose() , 那么任务栏托盘图标就会自动消失了。

 

删除win7任务栏通知区域图标的方法

大家都知道程序运行后会在任务栏的通知区域显示表明正在运行,但是有很多失效的图标也会在此显示,那么怎么样删除那些没用的图标呢?1、在开始运行里输入:regedit进入注册表编辑器2、进入注册表编辑器后,依次点击文件... 查看详情

电脑图标点击没有效果解决方法

...下所有操作使用enter键或者快捷键完成。1、在屏幕最下面任务栏空白处,鼠标右键启动任务管理器,或者使用快捷键Ctrl+Shift+Esc打开任务管理器;2、切换到“进程”标签,找到explorer.exe进程,右键结束进程;3、切换到&ldquo... 查看详情

windows任务栏和桌面图标不见啦!!!解决重赏

我装了一个主题包,是美化windows的图标任务栏等等,当我卸载此软件后,重开机时任务栏和桌面图标不见拉,鼠标点左键右键后没反应,但是可以按ctrl+alt+del后运行新任务打开文件一切又正常,打开控制面板后发现一个【任务... 查看详情

哪个 Windows 进程正在显示给定的任务栏系统托盘图标?

】哪个Windows进程正在显示给定的任务栏系统托盘图标?【英文标题】:WhichWindowsprocessisdisplayingagiventaskbarsystemtrayicon?【发布时间】:2011-03-0211:03:09【问题描述】:如何找到正在显示给定任务栏系统托盘图标的Windows进程?【问题... 查看详情

如何将不同的进程任务栏图标与 Windows 7 结合使用

】如何将不同的进程任务栏图标与Windows7结合使用【英文标题】:howtocombinedifferentprocesstaskbariconwithwindows7【发布时间】:2014-05-2907:27:49【问题描述】:我想组合两个不同的进程任务栏图标,一个进程是mfc创建的,另一个进程是pyth... 查看详情

c#winform启动最小化到任务栏右侧通知栏并交互操作

C#winForm启动最小化到任务栏右侧通知栏并交互操作一。主要功能:(1)、程序启动自动隐藏到任务栏右侧通知栏显示。(与系统托盘同义)(2)、双击系统托盘图标显示、隐藏窗口;(3)、右击系统托盘图标提供三个菜单选项,“... 查看详情

为啥任务栏没有图标

参考技术A问题一:为什么打开程序任务栏没显示图标打开任务管理器(CTRL+ALT+DEL),找到explorer.exe右键点击explorer.exe选择结束进程这时你会发现桌面上只剩下背景图了,不要急,现在在任务管理器工具栏点击文件->新建任务打... 查看详情

获取window任务栏已经打开应用程序窗口(也就是任务管理器中前台进程)的图标

获取window任务栏已经打开应用程序窗口(也就是任务管理器中前台进程)的图标1.功能描述  获取到window任务栏已经打开的应用程序的窗口图标。如下:(要获取到QQ,浏览器,文件夹的图标,但是任务栏中隐藏的图标不... 查看详情

如何设置在电脑右下角显示网络连接图标

...设置了自动隐藏。先从图标状态栏右键鼠标的【属性】在任务栏板面选择【自定义】2查找到本地连接项目后面的【选择框】选择【总是显示】再点击【确定】这样网络连接图标就永远显示在右下角了。 参考技术B打开显示通知栏... 查看详情

winform之窗口最小化到托盘及右键图标显示菜单

...om最小化到系统托盘,本例子基于VS2019编写。用C#开发winform桌面程序时,程序启动后,默认是显示在桌面而且在任务栏中有对应的图标。有的时候,需要在程序最小行后,将程序图标仅仅显示在系统托盘,... 查看详情

怎么删除过去的项目

在WindowsXP系统任务栏上单击鼠标右键选择“属性”,在“任务栏”的“通知区域”中勾选“隐藏不活动的图标”,再点“自定义”,会弹出一个对话框,里面有“当前项目”和“过去的项目”,该如何才能删掉过去项目中的所有... 查看详情

winform之窗口最小化到托盘及右键图标显示菜单

  Form最小化是指整个Form都缩小到任务栏上,但是窗体以Form的标题栏形式显示在任务栏上,若是想让Form以Icon的形式显示在任务栏右下角,则需要给Form添加一个NotifyIcon控件。一、添加NotifyIcon控件  1如下图为窗体添加一个Not... 查看详情

win10桌面图标消失开始菜单占据了桌面是啥原因

...入“资源管理器总是崩溃”查找方案修复。  ②输入“任务显示异常”查找方案修复。  3、桌面图标没了,有任务栏,鼠标右键正常。  桌面空处右键--查看--勾选“自动排列图标”、“显示桌面图标”。之后,取消勾选... 查看详情

qt单击任务栏图标实现最小化(代码片段)

...essWindowHint);去掉边框,此时会发现,当程序打开后,单击任务栏的按钮,会发现无法最小化,隐藏窗口。解决的方法是:setWindowFlags(Qt::Window|Qt::F 查看详情

win10任务栏图标大小设置了不生效?

win10任务栏图标大小设置了不生效,在注册表上设置了大小,重启电脑后还是原来的图标宽度。方法一:1、点击桌面左下角的开始按钮,在弹出菜单中点击“设置”按钮。2、在打开的Windows10设置窗口中,点击“个性化”图标。3... 查看详情

win10自带应用图标显示感叹号无法打开如何解决

...用无法运行的解决方法。 解决步骤具体如下:1、在任务栏上单击右键,选择【任务栏设置】;2、在任务栏设置右边 查看详情

桌面上的快捷键图标无法正常显示?怎么办?

...图标缓存出现问题所致,可这样设置:按Ctrl+Shift+Del打开任务管理器(也可右击任务栏,在打开的快捷菜单中单击任务管理器来打开),在进程列表中找到explorer.exe并将其结束,接下来在单击任务管理器菜单“文件→运行”,输... 查看详情

如何在 TaskManager 中更改 C# WinForms exe 的图标

】如何在TaskManager中更改C#WinFormsexe的图标【英文标题】:HowtochangetheiconofaC#WinFormsexe,inTaskManager【发布时间】:2020-02-0610:30:04【问题描述】:我已经在项目属性和FormControl图标中设置了图标。因此,我的图标(.ico文件)位于:任务... 查看详情