﻿<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>YuYuYouEr工作室 &#187; 体感浏览器</title>
	<atom:link href="http://www.yuyuyouer.cn/blog/?feed=rss2&#038;tag=%E4%BD%93%E6%84%9F%E6%B5%8F%E8%A7%88%E5%99%A8" rel="self" type="application/rss+xml" />
	<link>http://www.yuyuyouer.cn/blog</link>
	<description>AREA OF 雨雨油儿 ~~ 承接体感互动软件、游戏定制开发 ~~</description>
	<lastBuildDate>Sat, 30 Mar 2024 16:41:59 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.1.4</generator>
		<item>
		<title>Kinect超时按钮实现 &#8211; 基于qfFSM有限状态自动机类库</title>
		<link>http://www.yuyuyouer.cn/blog/?p=347</link>
		<comments>http://www.yuyuyouer.cn/blog/?p=347#comments</comments>
		<pubDate>Tue, 23 Jul 2013 17:06:20 +0000</pubDate>
		<dc:creator>rabbit5455</dc:creator>
				<category><![CDATA[kinect]]></category>
		<category><![CDATA[qfFSM有限自动机]]></category>
		<category><![CDATA[体感浏览器]]></category>
		<category><![CDATA[Button]]></category>
		<category><![CDATA[fsm]]></category>
		<category><![CDATA[Web体感应用]]></category>
		<category><![CDATA[YuYuYouEr]]></category>
		<category><![CDATA[有限状态自动机]]></category>
		<category><![CDATA[有限自动机]]></category>
		<category><![CDATA[状态机]]></category>

		<guid isPermaLink="false">http://www.yuyuyouer.cn/blog/?p=347</guid>
		<description><![CDATA[qfFSM有限状态自动机类库目前拥有C++、C#、Java、JavaScript版本，对于同一份UML状态图，不同语言均可用qfFSM来实现。 本文使用JavaScript版本在浏览器中实现一个超时按钮，为方便测试，我使用鼠标指针来模拟Kinect关节，接入Kinect数据后，只需将手部关节坐标替换进来即可。 首先看超时按钮的UML状态图： 主状态机中有STATE_Normal、STATE_PointIn、STATE_PointOut三个状态，其中后面两个作为子状态机存在，他们内部分别含有3个状态：激活/非激活开始状态、正在激活/非激活状态、已激活/非激活状态。 设计 正在激活/非激活状态 是为了配合相应动画机制，如经典的按钮注水、按钮转满一周等计时方式。 事件方面支持UserLeave、PointIn、PointOut，以及MultiActive（多次连续激活）。 MultiActive机制可以很方便的实现 保持按住按钮，系统会周期触发某个事件。 源码中分为以下几个部分： 1、首先定义了各种常量：状态名称、事件名称、属性名称： var timeoutButton_const_def = { &#8230; }; 2、定义数据模型Model实现类： var TimeoutButton_Model = { &#8230; }; 在Model中定义各种属性，如激活时间、指针是否在对象可视范围内、计时器开始和结束。 3、定义各个子状态机、状态的实现类，他们分别继承自qfStateMachine/qfState基类，并实现doAction()事件： var State_Normal = { &#8230; }; var STATE_PointIn = { &#8230; }; var STATE_PointOut = { &#8230; }; var STATE_Active_start = { &#8230; }; var STATE_Activing = { [...]]]></description>
			<content:encoded><![CDATA[<p>qfFSM有限状态自动机类库目前拥有C++、C#、Java、JavaScript版本，对于同一份UML状态图，不同语言均可用qfFSM来实现。</p>
<p>本文使用JavaScript版本在浏览器中实现一个超时按钮，为方便测试，我使用鼠标指针来模拟Kinect关节，接入Kinect数据后，只需将手部关节坐标替换进来即可。</p>
<p>首先看超时按钮的UML状态图：</p>
<p><a href="http://www.yuyuyouer.cn/blog/wp-content/uploads/2013/07/kinect_NUI_Button_timeout_detect.jpg"><img class="alignnone size-full wp-image-348" title="kinect_NUI_Button_timeout_detect" src="http://www.yuyuyouer.cn/blog/wp-content/uploads/2013/07/kinect_NUI_Button_timeout_detect.jpg" alt="" width="491" height="293" /></a></p>
<p>主状态机中有STATE_Normal、STATE_PointIn、STATE_PointOut三个状态，其中后面两个作为子状态机存在，他们内部分别含有3个状态：激活/非激活开始状态、正在激活/非激活状态、已激活/非激活状态。</p>
<p>设计 正在激活/非激活状态 是为了配合相应动画机制，如经典的按钮注水、按钮转满一周等计时方式。</p>
<p>事件方面支持UserLeave、PointIn、PointOut，以及MultiActive（多次连续激活）。</p>
<p>MultiActive机制可以很方便的实现 保持按住按钮，系统会周期触发某个事件。</p>
<p>源码中分为以下几个部分：</p>
<p><span id="more-347"></span></p>
<p>1、首先定义了各种常量：状态名称、事件名称、属性名称：</p>
<blockquote><p>var timeoutButton_const_def = { &#8230; };</p></blockquote>
<p>2、定义数据模型Model实现类：</p>
<blockquote><p>var TimeoutButton_Model = { &#8230; };</p>
<p>在Model中定义各种属性，如激活时间、指针是否在对象可视范围内、计时器开始和结束。</p></blockquote>
<p>3、定义各个子状态机、状态的实现类，他们分别继承自qfStateMachine/qfState基类，并实现doAction()事件：</p>
<blockquote><p>var State_Normal =  { &#8230; };</p>
<p>var STATE_PointIn = { &#8230; };</p>
<p>var STATE_PointOut = { &#8230; };</p>
<p>var STATE_Active_start = { &#8230; };</p>
<p>var STATE_Activing = { &#8230; };</p>
<p>var STATE_Actived = { &#8230; };</p>
<p>var STATE_DeActive_start = {&#8230; };</p>
<p>var STATE_DeActiving = { &#8230; };</p>
<p>var STATE_DeActived = { &#8230; };</p></blockquote>
<p>4、定义了主逻辑状态机，继承自qfFsmLogic基类：</p>
<blockquote><p>var timeoutButton_Logic = { &#8230; };</p>
<p>其中核心方法为状态机初始化函数（initTimeoutButtonMachine()成员函数），包含三个方面：</p>
<p>1）设置状态机环境变量，此处只设置数据模型Model，以便各个状态获取数据属性。</p>
<p>2）实例化各个子状态机、状态，并绑定到各自父状态机中。</p>
<p>3）配置状态转移规则，这里完成对UML状态图的描述翻译。</p></blockquote>
<p>5、实例化主逻辑状态机，并调用他的start()方法：</p>
<blockquote><p>var timeoutButton = timeoutButton_Logic.createNewInstance();</p>
<p>timeoutButton.start();</p></blockquote>
<p>6、绑定mouseover、mouseout事件，完成OnTimer()函数，将来的Kinect数据获取也是一个周期性事件，直接放在此处即可。</p>
<p>7、最后是界面的Html代码，其中包含一个多次激活标志checkbox、还有一个支持超时激活的按钮（DIV实现），如下图：</p>
<blockquote><p>其中Current State为状态机当前状态，可以实时看到状态转移过程。</p>
<p><a href="http://www.yuyuyouer.cn/blog/wp-content/uploads/2013/07/kinect_timeoutButton_UI.jpg"><img class="alignnone size-full wp-image-356" title="kinect_timeoutButton_UI" src="http://www.yuyuyouer.cn/blog/wp-content/uploads/2013/07/kinect_timeoutButton_UI.jpg" alt="" width="394" height="356" /></a></p></blockquote>
<p>实现DEMO展示Url：<a href="http://www.YuYuYouEr.cn/code/qfFSM_for_javascript_kinect_timeoutButton/timeoutButton_State_Machine_Test.html" target="_blank">qfFSM_for_javascript_kinect_timeoutButton</a></p>
<p>源代码右键查看即可。</p>
<p>qfFSM各版本源码下载：<a href="http://www.yuyuyouer.cn/blog/?p=290" target="_blank">http://www.YuYuYouEr.cn/blog/?p=290</a></p>
<p>&nbsp;</p>
]]></content:encoded>
			<wfw:commentRss>http://www.yuyuyouer.cn/blog/?feed=rss2&#038;p=347</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>使用体感浏览器开发Web体感应用简介</title>
		<link>http://www.yuyuyouer.cn/blog/?p=249</link>
		<comments>http://www.yuyuyouer.cn/blog/?p=249#comments</comments>
		<pubDate>Tue, 27 Nov 2012 15:09:13 +0000</pubDate>
		<dc:creator>rabbit5455</dc:creator>
				<category><![CDATA[kinect]]></category>
		<category><![CDATA[体感浏览器]]></category>
		<category><![CDATA[Web体感应用]]></category>
		<category><![CDATA[YuYuYouEr]]></category>

		<guid isPermaLink="false">http://www.yuyuyouer.cn/blog/?p=249</guid>
		<description><![CDATA[本文主要介绍chrome版本体感浏览器使用过程，由于目前kinect社区开发者居多，所以本文也侧重介绍如何基于体感浏览器做开发，并假定您能搞定一些SDK安装相关的小问题。 直接切入正题吧，首先您得下载体感浏览器，这是一个zip包，解压即可，您需要掌握的基本技能：JavaScript、HTML、HTML5 Canvas。 体感浏览器目前发布在国内最大的体感开发社区cnKinect.com首页，体感浏览器目前有两个版本，分别支持微软MS Kinect SDK和开源OpenNI SDK，确保您的机器已经安装好相应的SDK驱动。 对于运行在体感浏览器中的Web应用来说，并不需要关心底层SDK驱动类型，Web应用主要使用我们提供的JavaScript API来获取Kinect识别结果，目前浏览器在启动时默认会打开体感硬件（请先将硬件接入PC，这里将来会完善，做到即插即用）。 体感浏览器启动后，默认会打开cnKinect.com中app页面，目前我们编写的Web体感应用都发布在这里，如果您有博客空间，那么可以将编写的Web体感应用发布在自己的站点，给提供朋友一个url即可，他们便可体验您完成的酷炫效果。 OK，接下来发一张图片，是目前我最满意的Web体感应用：体感浏览器版-捕鱼达人截图(由原HTML5版捕鱼达人移植而来,感谢捕鱼达人团队，他们编写了这个很难酷的游戏)。 以捕鱼达人为例(URL：http://app.cnkinect.com/fishjoy/)，在体感浏览器加载完成之后，玩家站在kinect视野内，将看到一个绿色人影，此时，玩家将左手或右手从胸前推出，游戏中将发射一枚渔网，您技术够好的话，也能像我一样逮到两条大家伙。 接下来介绍如何开发一款可以运行在体感浏览器中的Web体感应用。 首先要明确体感浏览器也是一款标准的Web浏览器，可以用他打开baidu，google这些网站，体感浏览器内核为Webkit，对HTML5支持相当好，上图中小绿人便是用HTML5中Canvas绘制得到。 体感浏览器发布的zip包中包含有ReadMe.txt，其中介绍了主要的目录结构： 目录结构说明：&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212; cnkinect_broswer/cnkinect_broswer.exe：浏览器主程序。 sample/api/api.js：提供一个基本的javascript函数来获取骨骼数据。 sample/example_kinect_javascript：基本示例，打开体感浏览器后，拖进去就ok，最新版本新增加视频、深度数据流，内部非常简单。 体感浏览器提供3条API，分别对应Kinect3中基本数据流，如下： qfKinectGetSkeletonData()函数获取kinect骨骼节点数据，目前仅提供一名用户节点数据； qfKinectGetVideoData()函数获取kinect视频数据； qfKinectGetDepthData()函数获取kinect深度数据； API函数说明： 1、qfKinectGetSkeletonData()函数返回一个JSON格式字符串，可以使用JQuery、eval，或者第三方JSON解析库转为JavaScript对象，如下： function deal_Skeleton()  { var strJsonSkl = qfKinectGetSkeletonData(); if (strJsonSkl == null &#124;&#124; strJsonSkl == &#8220;&#8221;) { return ; } var skl = eval( &#8220;(&#8221; + strJsonSkl + &#8220;)&#8221; ); //下面以获取右手坐标x,y,z分量为例，单位为米 [...]]]></description>
			<content:encoded><![CDATA[<p>本文主要介绍chrome版本体感浏览器使用过程，由于目前kinect社区开发者居多，所以本文也侧重介绍如何基于体感浏览器做开发，并假定您能搞定一些SDK安装相关的小问题。</p>
<p>直接切入正题吧，首先您得下载体感浏览器，这是一个zip包，解压即可，您需要掌握的基本技能：JavaScript、HTML、HTML5 Canvas。</p>
<p>体感浏览器目前发布在国内最大的体感开发社区<a title="cnKinect.com" href="http://www.cnkinect.com" target="_blank">cnKinect.com</a>首页，体感浏览器目前有两个版本，分别支持微软MS Kinect SDK和开源OpenNI SDK，确保您的机器已经安装好相应的SDK驱动。</p>
<p>对于运行在体感浏览器中的Web应用来说，并不需要关心底层SDK驱动类型，Web应用主要使用我们提供的JavaScript API来获取Kinect识别结果，目前浏览器在启动时默认会打开体感硬件（请先将硬件接入PC，这里将来会完善，做到即插即用）。</p>
<p>体感浏览器启动后，默认会打开cnKinect.com中app页面，目前我们编写的Web体感应用都发布在这里，如果您有博客空间，那么可以将编写的Web体感应用发布在自己的站点，给提供朋友一个url即可，他们便可体验您完成的酷炫效果。</p>
<p>OK，接下来发一张图片，是目前我最满意的Web体感应用：体感浏览器版-捕鱼达人截图(由原HTML5版捕鱼达人移植而来,感谢捕鱼达人团队，他们编写了这个很难酷的游戏)。</p>
<div id="attachment_251" class="wp-caption alignnone" style="width: 490px"><a href="http://www.yuyuyouer.cn/blog/wp-content/uploads/2012/11/tiganbuyu.jpg"><img class="size-full wp-image-251  " title="tiganbuyu" src="http://www.yuyuyouer.cn/blog/wp-content/uploads/2012/11/tiganbuyu.jpg" alt="体感浏览器-捕鱼达人" width="480" height="347" /></a><p class="wp-caption-text">www.YuYuYouEr.cn</p></div>
<p>以捕鱼达人为例(URL：<a href="http://app.cnkinect.com/fishjoy/">http://app.cnkinect.com/fishjoy/</a>)，在体感浏览器加载完成之后，玩家站在kinect视野内，将看到一个绿色人影，此时，玩家将左手或右手从胸前推出，游戏中将发射一枚渔网，您技术够好的话，也能像我一样逮到两条大家伙。</p>
<p>接下来介绍如何开发一款可以运行在体感浏览器中的Web体感应用。</p>
<p>首先要明确体感浏览器也是一款标准的Web浏览器，可以用他打开baidu，google这些网站，体感浏览器内核为Webkit，对HTML5支持相当好，上图中小绿人便是用HTML5中Canvas绘制得到。</p>
<p>体感浏览器发布的zip包中包含有ReadMe.txt，其中介绍了主要的目录结构：</p>
<blockquote><p><span style="color: #993300;">目录结构说明：&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;</span><br />
<span style="color: #993300;">cnkinect_broswer/cnkinect_broswer.exe：浏览器主程序。</span><br />
<span style="color: #993300;">sample/api/api.js：提供一个基本的javascript函数来获取骨骼数据。</span><br />
<span style="color: #993300;">sample/example_kinect_javascript：基本示例，打开体感浏览器后，拖进去就ok，最新版本新增加视频、深度数据流，内部非常简单。</span></p></blockquote>
<p>体感浏览器提供3条API，分别对应Kinect3中基本数据流，如下：</p>
<blockquote><p><span style="color: #993300;">qfKinectGetSkeletonData()函数获取kinect骨骼节点数据，目前仅提供一名用户节点数据；</span><br />
<span style="color: #993300;">qfKinectGetVideoData()函数获取kinect视频数据；</span><br />
<span style="color: #993300;">qfKinectGetDepthData()函数获取kinect深度数据；</span></p></blockquote>
<p>API函数说明：</p>
<p>1、qfKinectGetSkeletonData()函数返回一个JSON格式字符串，可以使用JQuery、eval，或者第三方JSON解析库转为JavaScript对象，如下：</p>
<blockquote><p><span style="color: #993300;">function deal_Skeleton()  {</span></p>
<p style="padding-left: 30px;"><span style="color: #993300;"> var strJsonSkl = qfKinectGetSkeletonData();</span><br />
<span style="color: #993300;"> if (strJsonSkl == null || strJsonSkl == &#8220;&#8221;)		{			return ;		}</span></p>
<p style="padding-left: 30px;"><span style="color: #993300;"> var skl = eval( &#8220;(&#8221; + strJsonSkl + &#8220;)&#8221; );</span></p>
<p style="padding-left: 30px;"><span style="color: #993300;"> //下面以获取右手坐标x,y,z分量为例，单位为米</span><br />
<span style="color: #993300;"> skl["hand_right"].x;      //ok，各位coding大仙可以用这个数据天马行空一番了</span><br />
<span style="color: #993300;"> skl["hand_right"].y;      //ok，您现在知道玩家右手的高度了，请继续天马，继续行空</span><br />
<span style="color: #993300;"> skl["hand_right"].z;       //ok，z即是用户右手相对kinect的距离， 捕鱼达人前推动作判定，小z功不可没</span></p>
<p><span style="color: #993300;">}</span></p></blockquote>
<p>2、视频数据、深度图数据结构非常简单，首先你看视频数据：</p>
<blockquote><p><span style="color: #993300;">//获取得到VideoData，再获取HTML5中Canvas对象的context，直接putImageData()即可</span><br />
<span style="color: #993300;">var kinectVideo = qfKinectGetVideoData();</span><br />
<span style="color: #993300;">var context = canvas.getContext(&#8217;2d&#8217;); </span><br />
<span style="color: #993300;"> context.putImageData(kinectVideo, 0, 0, 0, 0, 640, 480);</span></p></blockquote>
<p>不会使用Canvas的同学可以搜索“Canvas”，查看相关资料，非常简单。<br />
w3school中也有相关科普教材：<a href="http://www.w3school.com.cn/html5/html5_canvas.asp">http://www.w3school.com.cn/html5/html5_canvas.asp</a></p>
<p>3、深度数据与上述Video数据类似，演示一下显示绿色小人代码，说明如何处理深度数据：</p>
<p>首先你需要知道深度原始数据是到kinect的距离，单位毫米，体感浏览器得到的为32位整形，长度4个字节，低3位存放UserID，<br />
SDK驱动中通过C语言得到的深度为2字节。</p>
<blockquote><p><span style="color: #993300;">var kinectDepth = qfKinectGetDepthData();</span><br />
<span style="color: #993300;">var size = kinectDepth.width * kinectDepth.height * 4; </span><br />
<span style="color: #993300;"> for (var i=0; i&lt;size; i+=4)					{</span></p>
<p style="padding-left: 30px;"><span style="color: #993300;">//遍历每个深度数据项，判断UserID，如果为0则令此像素透明，否则不透明并显示为绿色调</span><br />
<span style="color: #993300;">//这样小绿人就抠出来了</span><br />
<span style="color: #993300;"> if (0 != (kinectDepth.data[i+0] &amp; 0&#215;07))						{  //判断UserID</span></p>
<p style="padding-left: 60px;"><span style="color: #993300;"> </span><span style="color: #993300;">kinectDepth.data[i+3] = 255;    //绿色分量最大</span><br />
<span style="color: #993300;">kinectDepth.data[i+1] = 255;    //完全不透明</span></p>
<p style="padding-left: 30px;"><span style="color: #993300;"> }</span><br />
<span style="color: #993300;"> else</span><span style="color: #993300;"> </span><span style="color: #993300;">{</span></p>
<p style="padding-left: 60px;"><span style="color: #993300;">kinectDepth.data[i+3] = 0;   //完全透明</span></p>
<p style="padding-left: 30px;"><span style="color: #993300;"> }</span></p>
<p><span style="color: #993300;"> </span><span style="color: #993300;">}</span></p></blockquote>
<p>OK，科普完毕，如果大家折腾的过程中有需要讨论的地方，欢迎在群中找我，我是YuYuYouEr；</p>
<p>我的EMail：YuYuYouEr@qq.com<br />
我的博客：http://www.YuYuYouEr.cn</p>
<p>最后附上 捕鱼达人视频、骨骼视频深度数据测试视频：</p>

      <div id="banner_0_container" class="jj_swf_object_container" style="height:400px;overflow:hidden;">
        <div id="banner_0" class="jj_swf_object_container_wrapper" style="width:480px;height:400px;overflow:hidden;">
        </div>
      </div>
      <script type="text/javascript">
        swfobject.embedSWF("http://player.youku.com/player.php/sid/XNDI4Nzg5NTcy/v.swf", "banner_0", "480", "400", "9.0.0", "http://www.yuyuyouer.cn/blog/wp-content/plugins/jj-swfobject/swfobject/expressInstall.swf", {}, {}, {});
      </script>

      <div id="banner_1_container" class="jj_swf_object_container" style="height:400px;overflow:hidden;">
        <div id="banner_1" class="jj_swf_object_container_wrapper" style="width:480px;height:400px;overflow:hidden;">
        </div>
      </div>
      <script type="text/javascript">
        swfobject.embedSWF("http://player.youku.com/player.php/sid/XNDI1MjMyNDg0/v.swf", "banner_1", "480", "400", "9.0.0", "http://www.yuyuyouer.cn/blog/wp-content/plugins/jj-swfobject/swfobject/expressInstall.swf", {}, {}, {});
      </script>
<p><span style="color: #800000;">本文也发布在 </span><a title="追求高质量高效率的技术交流" href="http://www.kinectutorial.com/" target="_blank"><span style="color: #800000;">KTU – Kinect体感开发者协作博客</span></a><span style="color: #800000;">，标题为《chrome体感浏览器详细使用过程》，</span></p>
<p><span style="color: #800000;">KTU博客文章质量相当高，值得kinect研发者细看一番。</span></p>
]]></content:encoded>
			<wfw:commentRss>http://www.yuyuyouer.cn/blog/?feed=rss2&#038;p=249</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>kinect在体感浏览器中缩放、旋转图片</title>
		<link>http://www.yuyuyouer.cn/blog/?p=154</link>
		<comments>http://www.yuyuyouer.cn/blog/?p=154#comments</comments>
		<pubDate>Fri, 25 May 2012 18:07:55 +0000</pubDate>
		<dc:creator>rabbit5455</dc:creator>
				<category><![CDATA[kinect]]></category>
		<category><![CDATA[体感浏览器]]></category>

		<guid isPermaLink="false">http://www.yuyuyouer.cn/blog/?p=154</guid>
		<description><![CDATA[&#160;]]></description>
			<content:encoded><![CDATA[<p>&nbsp;</p>

      <div id="kinect_browser_image_control_container" class="jj_swf_object_container" style="height:400px;overflow:hidden;">
        <div id="kinect_browser_image_control" class="jj_swf_object_container_wrapper" style="width:480px;height:400px;overflow:hidden;">
        </div>
      </div>
      <script type="text/javascript">
        swfobject.embedSWF("http://player.youku.com/player.php/sid/XNDAyNDQ1NDM2/v.swf", "kinect_browser_image_control", "480", "400", "9.0.0", "http://www.yuyuyouer.cn/blog/wp-content/plugins/jj-swfobject/swfobject/expressInstall.swf", {}, {}, {});
      </script>
]]></content:encoded>
			<wfw:commentRss>http://www.yuyuyouer.cn/blog/?feed=rss2&#038;p=154</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>
