MC新手入门(四十七)------ 重力感应

 在手机游戏的世界里,我们经常能找到一类这样的游戏:它们不是用按键,而是通过向左向右倾斜来实现赛车的转弯;

9-2-1.png


图9-2-1


再比如,在一个桌面上,放一个小铁球,通过倾斜手机,小球也会跟着滚动,最终滚到洞里。

9-2-2.png


图9-2-2


    这两个游戏的共同点是:需要感应到手机所受的重力情况,再进行判断。在第一个例子的卡丁车里,首先要得到手机所受的重力情况,来判断手机是处于向左倾斜还是向右倾斜的状态,然后进一步做出让赛车向左或向右转的动作。


重力感应原理
    重力感应跟检测手机的重力状态分不开。现在大部分的智能手机都内置了重力感应的装置。
    目前大部分智能手机感应器的实现靠的是内置加速计,它是一个三轴加速计,分为X轴、Y轴和Z轴。这三个轴所构成的立体空间足以侦测到你在手机上的各种动作。

9-2-1-1.png


图9-2-1-1


通过感知特定方向的惯性力总量,加速计可以测量出加速度和重力。这样就能够检测到三维空间中的运动或重力引力。因此,加速计不但可以指示握持电话的方式(或自动旋转功能),而且如果电话放在桌子上的话,还可以指示电话的正面朝上还是朝下。
在实际应用时通常是以这三个轴(或任意两个轴)所构成的角度来计算手机倾斜的角度,从而计算出重力加速度的值。


实例重力小球的实现
我们先来介绍一下一个关键函数:
                       void getAccel(float *x, float *y, float *z);
        这个函数能将轴加速计三个轴的参数存入这里的x,y,z。这三个参数构成的方向向量(x,y,z)指示的就是相对于地平面的手机的方向向量,其坐标系如图9-2-1-1所示


        也可以理解为,x的大小代表的是手机的侧边感受到的压力;y的大小代表的是手机的底边感受到的压力;z的大小代表的是手机的屏幕感受到的压力。


我们再来做一个能在手机上滚动的珠子。
第一步:先创立几个角色,按图9-2-2-1的位置摆放

9-2-2-1.png


图9-2-2-1


  球,角色名命名为actBall,普通类型,添加动画animBall   退出按钮,角色名 actButtonExit,普通类型,添加动画animExit
  绿色边界,角色名WireFrame,线框类型,然后克隆三个,按上图摆放
  文字显示,角色名 txtT,普通类型,添加文字,如下图所示

9-2-2-2.png


图9-2-2-2


9-2-2-3.png


图9-2-2-3


第二步:为各角色添加事件和行为
退出按钮:
创建“鼠标键按下”事件,“脚本编辑器”行为代码:
                      ExitGame();
小球:
添加“角色绘制”事件,“脚本编辑器”行为
                       float ax,ay,az;
                       getAccel(&ax,&ay,&az);

      //在屏幕上显示三个参数
                       sprintf(txtT.text,"x= %.3f y= %.3f z = %.3f",ax,ay,az);
         //定义时间,假设是一秒三十帧
                       #define t (1.0/30.0)
         //定义一个像素与米的转换参数
                       #define k 5
         //计算物体速度的,其中ax,ay是x,y方向的加速度
                       if( ( (ax<0.2)&&(ax>-0.2) ) && ((ay<0.2)&&(ay>-0.2)) )
                       {    
                               ax = 0;
                                ay = 0;
                       }
                       else
                          {
                                xvelocity = xvelocity - k*ax*t;
                                yvelocity = yvelocity + k*ay*t;
                       }                                      
绿色边界:
添加“物体碰撞”事件,“脚本编辑器”行为代码:

9-2-2-4.png


图9-2-2-4


               PhysicalResponse(MOVE_COLLIDE_ACTOR_ONLY,USE_CALCULATED_MASS, 3, 1, 0, 0.4);
接下来,将文件导出为apk文件,在手机上运行。
在手机上运行的时候,你可以任意倾斜,摇晃你的手机,然后观察小球的运动情况。你会发现,随着手机倾斜,小球也会往倾斜的方向滚动。


数据分析
下面我们来分析轴坐标对应的数值与手机的状态的关系。
我们以图9-2-1-1提供的坐标系来分析,将重力加速度的值设为10m/s2
当手机处于缓慢移动的时候,x,y,z的范围是-10~0、0~10。这个时候,其他外力大小可以忽略不计,那么各个分量方向的加速度大小都不会大于重力加速度。
而当我们用力甩动手机的时候,手机受到除了重力以外的外力,它的分量方向加速度就可能会大于10。
下面我们来分析手机的放置状态:
1)当 x=y=0 时,手机处于水平放置状态。
2)当 x=0 并且 y>0 时,手机顶部的水平位置要大于底部,也就是一般接听电话时手机所处的状态。
3)当 x=0 并且 y<0 时,手机顶部的水平位置要小于底部。手机一般很少处于这种状态。
4)当 y=0 并且 x>0 时,手机右侧的水平位置要大于左侧,也就是右侧被抬起。
5)当 y=0 并且 x<0 时,手机右侧的水平位置要小于左侧,也就是左侧被抬起。
6)当 z=0 时,手机平面与水平面垂直。
7)当 z>0 时,手机屏幕朝上。
8)当 z<0 时,手机屏幕朝下。

然而,上面的数据那只是 理想状态下的情况,也就是说,手机水平放置的时候可以很准确的让x,y等于0。可是实际情况下,手机的感应器并没有那么精确,它会有一点点误差,所以实际编程中,我们可以将水平放置情况下的取值范围适当扩大一点,在本例中,我们让水平状态下的取值范围扩大到-0.2到0.2。

Demo下载地址:http://www.dongyo.cn/bbs/forum.php?mod=viewthread&tid=2529&extra=page%3D1%26filter%3Dauthor%26orderby%3Ddateline%26orderby%3Ddateline



  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值