您的位置:首页 > 其它

MTK MMI event 小结 5

2010-08-06 01:21 316 查看
昨天说了一下key event 的基本情况,今天直接从代码开始吧
先看执行key event 函数 mmi_frm_key_handle
 
void mmi_frm_key_handle(void *paraBuff)
{
kbd_data k;
U32 msg_count;
mmi_eq_keypad_detect_ind_struct *p;

// 判断参数是否为空
// 在 初始化时,系统就注册了 MSG_ID_MMI_EQ_KEYPAD_DETECT_IND 的回调函数为 mmi_frm_key_handle
// 当收到这个消息是,表示有按键事件要处理,
// 这个paraBuff 是 keyTask 传过来的参数,里面的内容是获取按键信息的函数指针
if (paraBuff != NULL)
{
drv_get_key_func new_key_ptr;

p = (mmi_eq_keypad_detect_ind_struct*) paraBuff;

new_key_ptr = (drv_get_key_func) (p->func);
//判断是否是新的函数指针,如果是的话,需要进行一些清理工作
if (new_key_ptr != keypad_ptr)
{
// 新的函数指针,则进行清理,并且判断是否有按键需要处理
if (!mmi_kbd_process_keyptr_change((void *)new_key_ptr))
{
return;
}
//清理 按键 事件缓存buffer
ClearKeyEvents();
keypad_ptr = new_key_ptr;
}
}

// 通过 while 1 来 不停的从 按键缓存里获取按键信息
// 当然这里不会无限死循环,后面会进行相应处理
while (1)
{
//1)判读是否是挂起,2)是否key需要处理
if ((g_mmi_suspend_key_flag == MMI_FALSE) && keypad_ptr &&((*(keypad_ptr))(&k) == MMI_TRUE))
{
if (k.Keydata[0] != KEY_INVALID)
{
#if defined(__MMI_TOUCH_SCREEN__) || defined(__MMI_HANDWRITING_PAD__)
kal_bool is_pen_enabled, is_pen_down;
// 获得触摸屏状态
mmi_pen_get_state(&is_pen_enabled, &is_pen_down);
#endif /* defined(__MMI_TOUCH_SCREEN__) || defined(__MMI_HANDWRITING_PAD__) */

#if defined(__MMI_TOUCH_SCREEN__) || defined(__MMI_HANDWRITING_PAD__)
//如果触摸屏按下,那么保存状态
if (is_pen_down && (k.Keyevent == WM_KEYPRESS))
{

U16 KeyMapIndex;
// 不允许 按键处理
is_allow_key_action = MMI_FALSE;
// 把驱动的按键和MMI 按键进行转换
KeyMapIndex = mmi_frm_get_idx_from_device_key_code(k.Keydata[0]);
if (nKeyPadStatus[KeyMapIndex] == KEY_EVENT_UP)
{
KEYBRD_MESSAGE KeyBrdMsg;

KeyBrdMsg.nKeyCode = nKeyPadMap[KeyMapIndex].nMMIKeyCode;
if (mmi_frm_is_2step_keyCode(KeyBrdMsg.nKeyCode))
{
nKeyPadStatus[KeyMapIndex] = KEY_HALF_PRESS_DOWN;
pressKey = HALF_DOWN_STATUS;
key_is_pressing_count++;
}
else
{
nKeyPadStatus[KeyMapIndex] = KEY_EVENT_DOWN;
pressKey = FULL_DOWN_STATUS;
key_is_pressing_count++;
}
}
}
else
#endif /* defined(__MMI_TOUCH_SCREEN__) || defined(__MMI_HANDWRITING_PAD__) */
//如果按键是弹起,那么还原原来按键状态,也就是弹起状态
//
if ((k.Keyevent == WM_KEYRELEASE) && (is_allow_key_action == MMI_FALSE))
{
#if defined(__MMI_TOUCH_SCREEN__) || defined(__MMI_HANDWRITING_PAD__)
/* Reset allow key flag and Update key status even if pen is down*/
U16 KeyMapIndex;

KeyMapIndex = mmi_frm_get_idx_from_device_key_code(k.Keydata[0]);
if ((nKeyPadStatus[KeyMapIndex] == KEY_EVENT_DOWN)
|| (nKeyPadStatus[KeyMapIndex] == KEY_HALF_PRESS_DOWN)
|| (nKeyPadStatus[KeyMapIndex] == KEY_LONG_PRESS)
|| (nKeyPadStatus[KeyMapIndex] == KEY_REPEAT))
{
nKeyPadStatus[KeyMapIndex] = KEY_EVENT_UP;
key_is_pressing_count--;
}
prevKeyMapIndex = prevKeyMapIndex;
#endif /* defined(__MMI_TOUCH_SCREEN__) || defined(__MMI_HANDWRITING_PAD__) */

is_allow_key_action = MMI_TRUE;
}
// 按键是否可以处理
if (is_allow_key_action == MMI_TRUE)
{
if (((k.Keyevent == WM_KEYPRESS) && (mmi_kbd_get_key_is_pressing_count() == 0))
|| k.Keyevent == DRV_WM_KEYLONGPRESS || k.Keyevent == DRV_WM_KEYREPEATED || k.Keyevent == DRV_WM_KEYFULLPRESS)
{
#if defined(__MMI_TOUCH_SCREEN__) || defined(__MMI_HANDWRITING_PAD__)
//关闭触摸屏
mmi_pen_disable();
#endif

}
//真正处理按键事件
mmi_frm_convert_process_key_event(k.Keyevent, k.Keydata[0]);

if ((k.Keyevent == WM_KEYRELEASE) && (mmi_kbd_get_key_is_pressing_count() == 0))
{
#if defined(__MMI_TOUCH_SCREEN__) || defined(__MMI_HANDWRITING_PAD__)
//重新打开触摸屏
mmi_pen_enable();
#endif

}
}
}
// 获得MMI task 消息队列消息个数
msg_get_ext_queue_info(mmi_ext_qid, &msg_count);
//如果外部有消息或者内部消息,则跳出该循环
if (msg_count > 0 || OslNumOfCircularQMsgs() > 0)
{
//表示还有key需要处理,在MMI task 里会直接调用这个函数进行再处理
g_keypad_flag = MMI_TRUE;
break;
}
}
else
{
// 没有key消息要处理
g_keypad_flag = MMI_FALSE;
break;
}
}   /* while(1) */
MMI_TRACE(MMI_FW_TRC_G1_FRM, MMI_FRM_KEY_HDLR_END);
}


 

1) 这里key 用while (1)来处理,不停的从key 消息buffer里取出按键信息,然后处理,这么做可以防止task中不停的发送消息,可以理解为共享内存。同样当有其他消息来时,需要跳出来处理其他消息,处理完毕后还需要再来处理。

2)这里跟触摸屏的事件进行了冲突处理,也就是按键和触摸屏不能同时工作,这两者也没有优先级。

3)实际真正处理按键 是在 mmi_frm_convert_process_key_event里面,下次在分析
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: