/** * 功能:取消指定部件的焦点 * 说明:该部件会得到EVENT_FOCUSOUT事件,并且,会将焦点转移至其它部件 * */ LCUI_API LCUI_BOOL Widget_CancelFocus( LCUI_Widget *widget ) { int i, total, focus_pos; LCUI_Widget *other_widget, **focus_widget; LCUI_Queue *queue_ptr; LCUI_WidgetEvent event; if( !widget || !widget->focus ) { return FALSE; } focus_widget = &RootWidget_GetSelf()->focus_widget; queue_ptr = Widget_GetChildList( widget->parent ); /* 如果该部件并没获得焦点 */ if( *focus_widget != widget ) { return FALSE; } event.type = EVENT_FOCUSOUT; Widget_DispatchEvent( widget, &event ); /* 寻找可获得焦点的其它部件 */ total = Queue_GetTotal( queue_ptr ); focus_pos = WidgetQueue_FindPos( queue_ptr, *focus_widget ); for( i=0; i<focus_pos; ++i ) { other_widget = (LCUI_Widget*)Queue_Get( queue_ptr, i); if( other_widget && other_widget->visible && other_widget->focus ) { event.type = EVENT_FOCUSIN; Widget_DispatchEvent( widget, &event ); *focus_widget = other_widget; break; } } if( i < focus_pos ) { return TRUE; } /* 排在该部件前面的符合条件的部件没找到,就找排在该部件后面的 */ for( i=focus_pos+1; i<total; ++i ) { other_widget = (LCUI_Widget*)Queue_Get( queue_ptr, i); if( other_widget && other_widget->visible && other_widget->focus ) { event.type = EVENT_FOCUSIN; Widget_DispatchEvent( other_widget, &event ); *focus_widget = other_widget; break; } } /* 没找到就复位焦点 */ if( i >= total ) { *focus_widget = NULL; } return TRUE; }
/** 获取指定部件内的已获得焦点的子部件 */ LCUI_API LCUI_Widget* Get_FocusWidget( LCUI_Widget *widget ) { int i, focus_pos, total; LCUI_Widget **focus_widget; LCUI_Queue *queue_ptr; //printf( "Get_FocusWidget(): widget: %p\n", widget ); //print_widget_info( widget ); queue_ptr = Widget_GetChildList( widget ); if( !widget ) { widget = RootWidget_GetSelf(); } else { /* 如果部件不需要焦点,则返回NULL */ if( !widget->focus ) { return NULL; } } queue_ptr = &widget->child; focus_widget = &widget->focus_widget; if( !focus_widget ) { return NULL; } total = Queue_GetTotal( queue_ptr ); if( total <= 0 ) { return NULL; } focus_pos = WidgetQueue_FindPos( queue_ptr, *focus_widget ); if( focus_pos < 0 ) { *focus_widget = NULL; return NULL; } /* 查找可获取焦点的有效部件 */ for( i=focus_pos; i<total; ++i ) { widget = (LCUI_Widget*)Queue_Get( queue_ptr, i ); if( widget && widget->focus ) { break; } } if( i>=total ) { *focus_widget = NULL; widget = NULL; } return widget; }
LCUI_API void WidgetMsg_Proc( LCUI_Widget *widget ) { int i,n; WidgetMsgData *data_ptr; LCUI_Widget *child; LCUI_Queue *msg_buff, *child_list; if( widget == NULL ) { widget = RootWidget_GetSelf(); } msg_buff = Widget_GetMsgBuff( widget ); child_list = Widget_GetChildList( widget ); Queue_Lock( msg_buff ); n = Queue_GetTotal( msg_buff ); for(i=0; i<n; ++i) { DEBUG_MSG("[%d/%d]get msg\n", i, n); data_ptr = (WidgetMsgData*)Queue_Get( msg_buff, i ); DEBUG_MSG("[%d/%d]dispatch msg\n", i, n); if( WidgetMsg_Dispatch( widget, data_ptr ) ) { DEBUG_MSG("[%d/%d]delete msg\n", i, n); Queue_Delete( msg_buff, i ); n = Queue_GetTotal( msg_buff ); --i; } DEBUG_MSG("[%d/%d]skip msg\n", i, n); } Queue_Unlock( msg_buff ); n = Queue_GetTotal( child_list ); /* 从尾到首,递归处理子部件的更新 */ while(n--) { child = (LCUI_Widget*)Queue_Get( child_list, n ); if( child ) { DEBUG_MSG("proc child msg\n"); WidgetMsg_Proc( child ); } } }
/** 判断指定部件是否被允许响应事件 */ LCUI_API LCUI_BOOL Widget_IsAllowResponseEvent( LCUI_Widget *widget ) { int i, n; LCUI_Queue *child_list; LCUI_Widget *child, *root_widget, *up_widget; root_widget = RootWidget_GetSelf(); if( widget == NULL || widget == root_widget ) { return TRUE; } /* 开始判断该部件的上级部件 */ up_widget = widget->parent; while( widget && widget != root_widget ) { child_list = Widget_GetChildList( up_widget ); n = Queue_GetTotal( child_list ); for(i=0; i<n; ++i) { child = (LCUI_Widget*)Queue_Get( child_list, i ); if( !child || !child->visible ) { continue; } if( child == widget ) { break; } if( child->modal ) { return FALSE; } } /* 记录这一级部件 */ widget = up_widget; if( widget ) { /* 切换至上级部件 */ up_widget = widget->parent; } } return TRUE; }