博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
山寨版 WP8.1 Cortana 启动 PC
阅读量:7025 次
发布时间:2019-06-28

本文共 4093 字,大约阅读时间需要 13 分钟。

8.1 dev preview 发布以来 Cortana 很受关注

前一段看到有视频演示用 Cortana 来启动 PC

看视频也是启动第三方应用实现的,简单来弄其实就是个语音启动应用 + 网络唤醒么…

也动手山寨一个简单的出来

 

首先先介绍下啥是网络唤醒:

详细去参考维基百科:

基本要求就是网卡支持(现代的PC一般是支持的,不过有的需要设置下,开启这个功能)

然后利用UDP往计算机网段广播地址发送一个包含要唤醒计算机的 mac 地址的 Magic Packet,来唤醒计算机。

魔法封包(Magic Packet)是一个广播性的帧(frame),透过埠7或埠9进行发送,且可以用(Connectionless protocol)的通讯协定(如、)来传递,不过一般而言多是用UDP,原因是的的IPX协定已经愈来愈少机会被使用。

在魔法封包内,每次都会先有连续6个"FF"(十六进制,换算成二进制即:11111111)的资料,即:FF FF FF FF FF FF,在连续6个"FF"后则开始带出资讯,有时还会带出4或6字节的,一旦经由网络卡侦测、解读、研判(广播)魔法封包的内容,内容中的MAC位址、密码若与电脑自身的位址、密码吻合,就会启动唤醒、开机的程序。

 

基本原理介绍完了,下面我们动手实现下吧

首先是计算机设置,我找了一台老机器,貌似板子是G31还是G43来着,先进BIOS里设置下支持远程唤醒

 

这个板子是设置允许 wake up by PCIE Card 就行了,不同板子设置不一样,自己看看设置吧

 

 

设置好了之后,我们的 PC 应该就支持网络唤醒了,先要验证下是否好用,找个程序试试,之前那篇维基百科里介绍了很多工具

这里我用的是Magic Packet Utility (),远程唤醒下试试效果

 

验证没问题后我们开始编写程序,首先新建一个wp工程(其实WP从7.1起就支持UDP,不过为了显得高大上我们建立一个8.1的工程吧,当然为了方便改成其他版本的,我们还是继续用silverlight)

 

选择版本为8.1

 

简单画个UI,要远程唤醒我们需要知道两个信息,1是目标计算机的 MAC 地址,2就是目标计算机所处网段的广播地址(啥是广播地址继续参见百科: 中的广播地址  ,基本上说就是把IP 地址最后一位改成 255…)

 
 

 

我们前面已经看百科的介绍了解的 Magic Packet 的组成(102个字节组成,最前面六个字节为0xFF,其他字节为目的主机的MAC地址(6个字节为一组,共16组))

下面我们需要自己构建 Magic Packet:

byte[] sendBytes = new byte[102];
for (int i = 0; i < 6; i++)
{
sendBytes[i] = 0xFF;
}
for (int i = 0; i < 16; i++)
{
for (int j = 0; j < 6; j++)
{
sendBytes[(i + 1) * 6 + j] = byte.Parse(macAddress.Substring(j * 2, 2), System.Globalization.NumberStyles.HexNumber);
}
}

 

然后发送UDP包的代码就很简单了,主要摘自MSDN:

public string Send(string BroadcastIP, string macAddress)
{
string response = "Operation Timeout";
 
// We are re-using the _socket object that was initialized in the Connect method
if (_socket != null)
{
// Create SocketAsyncEventArgs context object
SocketAsyncEventArgs socketEventArg = new SocketAsyncEventArgs();
 
// Set properties on context object
socketEventArg.RemoteEndPoint = new DnsEndPoint(BroadcastIP, 7);
 
// Inline event handler for the Completed event.
// Note: This event handler was implemented inline in order to make this method self-contained.
socketEventArg.Completed += new EventHandler
(delegate(object s, SocketAsyncEventArgs e)
{
response = e.SocketError.ToString();
 
// Unblock the UI thread
_clientDone.Set();
});
 
 
byte[] sendBytes = new byte[102];
for (int i = 0; i < 6; i++)
{
sendBytes[i] = 0xFF;
}
for (int i = 0; i < 16; i++)
{
for (int j = 0; j < 6; j++)
{
sendBytes[(i + 1) * 6 + j] = byte.Parse(macAddress.Substring(j * 2, 2), System.Globalization.NumberStyles.HexNumber);
}
}
 
 
 
// Add the data to be sent into the buffer
byte[] payload = sendBytes;
socketEventArg.SetBuffer(payload, 0, payload.Length);
 
// Sets the state of the event to nonsignaled, causing threads to block
_clientDone.Reset();
 
// Make an asynchronous Send request over the socket
_socket.SendToAsync(socketEventArg);
 
// Block the UI thread for a maximum of TIMEOUT_MILLISECONDS milliseconds.
// If no response comes back within this time then proceed
_clientDone.WaitOne(TIMEOUT_MILLISECONDS);
}
else
{
response = "Socket is not initialized";
}
 
return response;
}

 

程序的唤醒部分基本就完成了,下面我们要添加应用支持语音启动,首先在清单文件中设置程序支持语音:

 

然后我们在工程中添加一个“语音命令定义”,名称为:SupportedVoiceCommands.xml

 

修改下内容,我们只是为了语音启动,所以后面的内容就不用了

 
start
open start
 
......
 
 
 

 

 

然后修改 App.xaml.cs ,加入对该语音指令文件的注册,函数命名为 InitializeVoiceCommands

async private static void InitializeVoiceCommands()
{
var filename = "SupportedVoiceCommands.xml";
try
{
var location = Windows.ApplicationModel.Package.Current.InstalledLocation.Path;
var fileUriString = String.Format("file://{0}/{1}", location, filename);
await Windows.Phone.Speech.VoiceCommands.VoiceCommandService.InstallCommandSetsFromFileAsync(new Uri(fileUriString));
}
catch (Exception ex)
{
System.Diagnostics.Debug.WriteLine(ex.Message);
}
}

然后修改 App.xaml.cs 里的构造函数,加入InitializeVoiceCommands()

public App()
{
// 未捕获的异常的全局处理程序。
UnhandledException += Application_UnhandledException;
 
// 标准 XAML 初始化
InitializeComponent();
 
// 特定于电话的初始化
InitializePhoneApplication();
 
// 语言显示初始化
InitializeLanguage();
 
//语音初始化
InitializeVoiceCommands();
 
// 调试时显示图形分析信息。
if (Debugger.IsAttached)

 

完成收工,运行下试试效果。

 

  

 

 

最后源码:

 

 

参考:

转载地址:http://bisxl.baihongyu.com/

你可能感兴趣的文章
Oracle常用单行函数
查看>>
虚拟机客户端安装操作系统
查看>>
(fork)在局域网中部署微信服务器 (PHP)
查看>>
如何做好SEO
查看>>
Linux命令之free
查看>>
Go语言 -- Mysql数据库
查看>>
Cocos2d-x_Node详解
查看>>
基本Android应用流程
查看>>
我的友情链接
查看>>
SSH公钥免密登录其他主机
查看>>
ExtJS表单提交时,不用鼠标点击按钮提交,直接通过回车键提交
查看>>
运行浏览器的最高版本
查看>>
PHP中解决ajax请求session过期退出登录问题
查看>>
拆分功能:第一步,建立 会员管理系统
查看>>
Android判断当前网络是否可用--示例代码
查看>>
NAT转换
查看>>
获取网站Web服务器类型的办法
查看>>
我的友情链接
查看>>
CXF+Spring+Hibernate实现RESTful webservice服务端示例
查看>>
HTML网络效果收集---HTML
查看>>