起因:谁在抢镜头?!
为了开始Windows Phone 8的开发,这两天将系统升级到了Windows8.1,安装倒是又快又方便的,解压ISO镜像双击Setup一路下一步(嘛其实还输了密钥之类的)就安装好了~
不过不知道为什么去年买的正版密钥激活不了了,于是按照指示拨打了微软的客服电话,客服妹纸问了几个问题就给激活了~然后花了两三个小时进行各种配置美化和常用软件安装,看起来好极了~
可耻的晒桌面(其实和之前用Win7时没啥区别……已经一年多没换过主题了……)
刚开始用着感觉没啥问题啊,速度也挺快,可是打开VS写了几行代码就发现有些不对劲了,智能感应总是会莫名其妙的半路消失,然后发现聊QQ时经常打一半字输入法不见了,更糟糕的是逛B站全屏视频时会时不时跳出到窗口模式……根据十几年(啊天哪我怎么这么老了= -)的视窗操作系统(其实就是Windows~听起来逼格高那么一点?)使用经验,首先想到的是焦点被抢占了~之后用一般窗口程序观察了一下,发现的确是这样,时不时就会失去焦点半秒然后再恢复,网上查了一下,大多数说是支付宝安全控件之类的,可是我貌似不是因为这个引起的……那么究竟是谁干的呢?
经过:捕捉熊孩子,我有特殊的技巧
作为半个程序猿,当然就要用程序猿的方式解决咯(事实上是因为我找不到其它方法……),很久很久以前就知道了Windows有提供获得焦点窗口句柄(handle,话说为什么要翻译成“句柄”这种不明所以的东西? )的API,看来这次是可以用的上咯~
网上查了查发现不难而且有相关例子,直接打开VS,新建一个WinForm程序,拖了一个Label一个TextBox和一个Timer
就这么简单~
Timer设为10ms检测一次焦点窗口并输出相关信息,包括句柄号、进程PID号、进程名称、窗口名称和窗口类名,Label显示句柄号,TextBox记录相关变化
以下为代码
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Runtime.InteropServices;
using System.Diagnostics;
namespace WindowsFormsApplication1
{
public partial class Form1 : Form
{
[DllImport("user32", EntryPoint = "GetWindowThreadProcessId")]
private static extern int GetWindowThreadProcessId(
IntPtr hwnd, //窗口句柄
out int pid //输出所在进程的PID
);//通过句柄获取PID
[DllImport("user32", CharSet = CharSet.Auto, ExactSpelling = true)]
public static extern IntPtr GetForegroundWindow();//获取当前激活窗口
[DllImport("user32", SetLastError = true)]
public static extern int GetWindowText(
IntPtr hWnd, //窗口句柄
StringBuilder lpString, //标题
int nMaxCount //最大值
);
[DllImport("user32")]
private static extern int GetClassName(
IntPtr hWnd, //句柄
StringBuilder lpString, //类名
int nMaxCount //最大值
);
public Form1()
{
InitializeComponent();
timer1.Start();
}
private void Form1_Load(object sender, EventArgs e)
{
}
private void timer1_Tick(object sender, EventArgs e)
{
IntPtr myPtr = GetForegroundWindow();
int pid = 0;
// 窗口进程PID
GetWindowThreadProcessId(myPtr, out pid);
// 窗口标题
StringBuilder title = new StringBuilder(512);
GetWindowText(myPtr, title, title.Capacity);
// 窗口进程
Process localById = Process.GetProcessById(pid);
// 窗口类名
StringBuilder className = new StringBuilder(512);
GetClassName(myPtr, className, className.Capacity);
//如果焦点窗体发生变化则记录
if (label1.Text != myPtr.ToString())
{
label1.Text = myPtr.ToString();
textBox1.Text = DateTime.UtcNow
+ "\r\n" + pid.ToString()
+ "\r\n" + localById.ProcessName
+ "\r\n" + title.ToString()
+ "\r\n" + className.ToString()
+ "\r\n\r\n===================================================\r\n\r\n"
+ textBox1.Text;
}
}
}
}
运行起来一切正常,就差熊孩纸出现了!
点我下载熊孩子探测器
结果:嘿嘿我捉到你了!
写完代码运行了一段时间才猛然发现,在这期间居然没有出现过被抢占焦点的问题,难道狡猾的熊孩纸发现了我的阴谋?
当然这不可能啦~该出现的迟早是要出现的,于是先让它运行着,然后继续聊QQ看视频……
又过了一个小时,熊孩纸终于按捺不止又开始捣乱啦~赶快切换到探测器,终于发现了……
原来是这个名为DrUpdate.exe的进程,看名字就知道,这是我们万恶的校园网登入客户端Dr.Com的自动升级进程,
这哪里是熊孩子捣乱,分明是州官放火啊
没办法,又不能删掉,试着用资源监视器挂起了这个进程,没想到这货居然会自动重启,最后一怒之下直接把这个文件重命名了……然后一切都安宁了~~
后记
虽然通过重命名执行文件的方式暂时解决了问题,不过后来发现重启电脑或关闭客户端后会导致无法再次打开客户端,于是只能再重命名回来(还好留了个心眼没有直接删掉),等客户端启动后再次重命名,感觉真是麻烦,不过就暂时先这样咯,反正我一般不关电脑的~