BREW按键及其他事件的处理

当一个事件通过同步函数ISHELL_SendEvent()或者AEE_Event()发送给BREW时,函数的返回值表明了该事件是否被BREW或者BREW应用处理了。而如果使用异步函数ISHELL_PostEvent(), 返回值指示标识该事件是否已经排队,而不是处理了。

发送按键事件

将按键事件及时发送给BREW十分重要。虽然事件通过AEE_Event()同步发送给BREW处理,而AEE_Event()函数的返回值只是表明了按键事件是否排入队列。

在不需要将按键事件发送给BREW的时候,当触发按键事件时,你必须调用AEE_Active()函数。这允许BREW正确处理屏幕保护。

当每个按键被按下和释放时,必须将按键转化为AEE Virtual Key 代码(AVK)并且通过下面的函数将按键事件发送出去。

AEE_KeyPress() EVT_KEY_PRESS  (按下按键时发送)

AEE_KeyRelease() EVT_KEY_RELEASE (释放按键时发送)

AEE_KEY() EVT_KEY (在Key press后发送)

在按键被按住时,BREW会发送重复按键事件给BREW应用。BREW在EVT_KEY_PRESS事件之后第一次收到EVT_KEY按键事件时,会立刻启动一个内部时钟。这个时钟用于在按键被按住的时间段中重复发送EVT_KEY事件给BREW应用,直到BREW收到EVT_KEY_RELEASE事件时结束。同样,这也是为什么在松开按键时要及时的将EVT_KEY_RELEASE事件发送给BREW的原因。如果只是发送了EVT_KEY事件而不发送EVT_KEY_RELEASE事件,会导致EVT_KEY事件重复发送被BREW。

BREW以前的版本支持EVT_KEY_HELD事件,用来表明一个按键被按住。这个事件现在已经不支持了,而是使用重复的发送EVT_KEY事件给BREW来标识一个按键被按住。

记住OEM_GetDeviceInfoEx()对AEE_DEVICEITEM_KEY_SUPPORT和AEE_DEVICESTATE_KEY_INFO参数的实现非常重要。

设置按键重复事件时钟

涉及文件:

AEEVCodes.h

定义了两个常量:

KB_AUTOREPEAT_START-在EVT_KEY事件后开始自动重复按键事件的默认开始时间。

KB_AUTOREPEAT_RATE -定义自动发出EVT_KEY事件的事件间隔。

OEMConfig.h

定义了一个新的结构体和CFGI_KB_AUTOREPEAT设置项

OEMKBAutoRepeat

OEMKBAutoRepeat.dwStart--定义了EVT_KEY事件后多少毫秒再发生按键重复事件。如果deStart等于0,则不发生重复事件,默认值是KB_AUTOREPEAT_START。

OEMKBAutoRepeat.dwRate --定义了重复EVT_KEY事件的时间间隔。如果值为0, 只发生一次EVT_KEY事件。默认是KB_AUTOREPEAT_RATE。

可以通过修改OEMKBAutoRepeat的值来控制重复按键的行为:

case CFGI_KB_AUTOREPEAT:
{
    OEMKBAutoRepeat *par= (OEMKBAutoRepeat *)pBuff;
    
    if(!pBuff || nSize != sizeof(OEMKBAutoRepeat))
    return EBADPARM;
   
    if(par)
    {
      par->dwStart = NNNN;
      par->dwRate = NNNN;
      return 0;
    }
}


应用行为

EVK_KEY_PRESS

EVT_KEY(wParam = Key, dwParam = 0)

如果KB_AUTOREPEAT_START不等于0,BREW使用该值设定一个定时器。
如果已经设定自动重复为关(OEMKBAutoRepeat.dwStart = 0),BREW不会启动自动重复。

当定时器超时并且按键被按住时,BREW会

EVT_KEY(wParam=key, dwParam= KB_AUTOREPEAT)。

如果KB_AUTOREPEAT_RATE不为0,则再次设定定时器。如果设置OEMKBAutoRepeat.dwRate = 0,则事件不会重复。

 

 

EVT_KEY_RELEASE

按键的流程图:

image

 

BREW按键事件处理

在BREW 3.1之前,按键事件只能有激活的(top-visible)应用接收到。在BREW 3.1中,特权应用可以在其他应用之前接收到按键事件之前捕获所有的按键事件。特权应用可以在创建MIF时设定。

创建特权应用的步骤:

1、使用3.x MIF编辑器,在应用选项卡中,选择Notifications, Flags,Settings。 在弹出的窗口中, 选中phone标识。这会为应用设置AFLAG_PHONE标识。

2、激活应用的system privilege。这可以通过在Privileges选项卡中选中System privilege权限来实现。

当这些完成后,拥有AFLAG_PHONE权限的应用在每个按键按下后都会接收到EVT_KEY_HOOK,EVT_KEY_HOOK_PRESS,EVT_KEY_RELEASE事件。按键的事件代码AVK_code会通过参数wParam传给应用的事件处理函数。

如果AFLAG_PHONE特权应用在按键事件处理中返回TRUE,那么这个按键事件就会被消耗掉,这个按键事件就不会继续传给激活(top-visible)应用。这提供了一个使用特权应用处理特殊按键事件的途径,比如AVK_END。

注意:应该只有少数(最好只有一个)的应用拥有AFLAG_PHONE权限。不然,在按键传给激活的应用之前,按键事件会实现传给每个正在运行的AFLAG_PHONE特权应用,这会导致设备运行缓慢。

在BREW 3.1中,应用可以注册在后台运行时要接受的特殊按键事件。注册特殊按键事件可以通过调用ISHELL_RegisterNotify(),并传递一个32位的dw掩码参数,该参数的格式是:低16位使用NMASK_SHELL_KEY填充而高16位使用按键的AVK码填充。

如果要注册所有的按键事件,可以使用NOTIFIER_VAL_ANY代替AVK码。应用也可以在应用的MIF中注册特殊的按键事件而不使用ISHELL_RegisterNotify()函数。对于注册的按键触发时,应用都会接收到EVT_NOTIFY事件,wParam为按键的AVK码,dwParam是AEENotify结构类型。AEENotify结构的pData成员是NotifyKeyEvent类型。

typedef struct _NotifyKeyEvent {
   AEEEvent eCode;
   uint16   wParam;
   uint32   dwParam;
   AEECLSID clsHandled
} NotifyKeyEvent;

按键事件首先发送给注册了key hook(按键钩子)事件的特权应用。如果这些特权应用处理完按键事件但并没有消耗掉,通过EVT_NOTIFY事件收到的NotifyKeyEvent结构中的clsHandled成员就会被设置成特权应用的class id,如果没有应用注册按键hook事件,那么按键事件会被发送给当前的激活应用,如果当前激活引用处理了按键事件,那么clsHandled就被设置成当前激活应用的class id。激活的应用不会消耗按键事件也不会阻止其传送给注册的应用。

注册了按键通知事件的应用可以阻止通过消耗按键事件来阻止按键事件继续发给其他应用。方式是在EVT_NOTIFY事件处理过程返回前,设置dwParam参数的st成员等于NSTAT_STOP。

case EVT_NOTIFY:
    (AEENotify *)wp = (AEENotify *)dwParam;
    wp->st = NSTAT_STOP;
    return TRUE;

如果多个应用注册了按键通知(不是按键钩子),那么通知发送的顺序依赖于应用注册按键通知的顺序。通知传递的顺序与应用注册的顺序相反。如果先注册A1再注册A2,通知发送的顺序是先发送到A2,然后A1。如果应用是通过MIF文件注册的按键通知事件,则事件发送的顺序是不确定的。

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值