diff --git a/include/LCUI/gui/widget.h b/include/LCUI/gui/widget.h index 8581920db..174bc5685 100644 --- a/include/LCUI/gui/widget.h +++ b/include/LCUI/gui/widget.h @@ -47,8 +47,8 @@ #include #include -void LCUI_InitWidget(void); +LCUI_API void LCUI_InitWidget(void); -void LCUI_FreeWidget(void); +LCUI_API void LCUI_FreeWidget(void); #endif diff --git a/include/LCUI/gui/widget_base.h b/include/LCUI/gui/widget_base.h index 1386ef48c..9213aae8d 100755 --- a/include/LCUI/gui/widget_base.h +++ b/include/LCUI/gui/widget_base.h @@ -407,6 +407,8 @@ LCUI_API void Widget_UpdateDisplay(LCUI_Widget w); /** 设置部件为顶级部件 */ LCUI_API int Widget_Top(LCUI_Widget w); +LCUI_API void Widget_SortChildrenShow(LCUI_Widget w); + /** 刷新堆叠顺序 */ LCUI_API void Widget_UpdateZIndex(LCUI_Widget w); diff --git a/src/gui/widget_base.c b/src/gui/widget_base.c index e9685048b..05bf04f4c 100755 --- a/src/gui/widget_base.c +++ b/src/gui/widget_base.c @@ -233,7 +233,7 @@ void Widget_Empty(LCUI_Widget w) LinkedList_ClearData(&w->children_show, NULL); LinkedList_Concat(&LCUIWidget.trash, &w->children); Widget_InvalidateArea(w, NULL, SV_GRAPH_BOX); - Widget_AddTask(w, LCUI_WTASK_LAYOUT); + Widget_UpdateStyle(w, TRUE); } void Widget_GetOffset(LCUI_Widget w, LCUI_Widget parent, float *offset_x, @@ -309,12 +309,12 @@ LCUI_BOOL Widget_InVisibleArea(LCUI_Widget w) continue; } DEBUG_MSG("rect: (%g,%g,%g,%g), child rect: " - "(%g,%g,%g,%g), child: %s %s\n", - rect.x, rect.y, rect.width, rect.height, - child->box.border.x, child->box.border.y, - child->box.border.width, - child->box.border.height, child->type, - child->id); + "(%g,%g,%g,%g), child: %s %s\n", + rect.x, rect.y, rect.width, rect.height, + child->box.border.x, child->box.border.y, + child->box.border.width, + child->box.border.height, child->type, + child->id); if (!LCUIRectF_IsIncludeRect(&child->box.border, &rect)) { continue; @@ -468,7 +468,7 @@ size_t Widget_GetHashList(LCUI_Widget w, unsigned *hash_list, size_t maxlen) child = child->node.next->data; break; } - } while(1); + } while (1); } return count; } @@ -632,12 +632,51 @@ void Widget_UpdateZIndex(LCUI_Widget w) Widget_AddTask(w, LCUI_WTASK_ZINDEX); } +void Widget_SortChildrenShow(LCUI_Widget w) +{ + LCUI_Widget child, target; + LCUI_WidgetStyle *s, *ts; + LinkedListNode *node, *target_node; + LinkedList *list; + + list = &w->children_show; + LinkedList_ClearData(list, NULL); + for (LinkedList_Each(node, &w->children)) { + child = node->data; + s = &child->computed_style; + if (child->state < LCUI_WSTATE_READY) { + continue; + } + for (LinkedList_Each(target_node, list)) { + target = target_node->data; + ts = &target->computed_style; + if (s->z_index == ts->z_index) { + if (s->position == ts->position) { + if (child->index < target->index) { + continue; + } + } else if (s->position < ts->position) { + continue; + } + } else if (s->z_index < ts->z_index) { + continue; + } + LinkedList_Link(list, target_node->prev, + &child->node_show); + break; + } + if (!target_node) { + LinkedList_AppendNode(list, &child->node_show); + } + } +} + void Widget_ExecUpdateZIndex(LCUI_Widget w) { int z_index; - LinkedList *list; - LinkedListNode *cnode, *csnode, *snode; + ; LCUI_Style s = &w->style->sheet[key_z_index]; + if (s->is_valid && s->type == LCUI_STYPE_INT) { z_index = s->val_int; } else { @@ -652,31 +691,6 @@ void Widget_ExecUpdateZIndex(LCUI_Widget w) } } w->computed_style.z_index = z_index; - snode = &w->node_show; - list = &w->parent->children_show; - LinkedList_Unlink(list, snode); - for (LinkedList_Each(cnode, list)) { - LCUI_Widget child = cnode->data; - LCUI_WidgetStyle *ccs = &child->computed_style; - - csnode = &child->node_show; - if (w->computed_style.z_index < ccs->z_index) { - continue; - } else if (w->computed_style.z_index == ccs->z_index) { - if (w->computed_style.position == ccs->position) { - if (w->index < child->index) { - continue; - } - } else if (w->computed_style.position < ccs->position) { - continue; - } - } - LinkedList_Link(list, csnode->prev, snode); - break; - } - if (!cnode) { - LinkedList_AppendNode(list, snode); - } if (w->computed_style.position != SV_STATIC) { Widget_AddTask(w, LCUI_WTASK_REFRESH); } @@ -1160,7 +1174,7 @@ static void Widget_ComputeSize(LCUI_Widget w) Widget_HasFillAvailableWidth(w)) { width = Widget_ComputeFillAvailableWidth(w); width = ToContentBoxWidth(w, width); - if (!Widget_HasStaticWidthParent(w)) { + if (!Widget_HasStaticWidthParent(w) && w->parent) { default_width = w->parent->box.content.width; if (w->computed_style.box_sizing == SV_BORDER_BOX) { default_width = diff --git a/src/gui/widget_task.c b/src/gui/widget_task.c index 24a9fc5f3..31056f21c 100644 --- a/src/gui/widget_task.c +++ b/src/gui/widget_task.c @@ -467,6 +467,7 @@ size_t Widget_UpdateWithContext(LCUI_Widget w, LCUI_WidgetTaskContext ctx) count += 1; } count += Widget_UpdateChildren(w, self_ctx); + Widget_SortChildrenShow(w); Widget_EndUpdate(self_ctx); return count; } diff --git a/src/gui/widget_tree.c b/src/gui/widget_tree.c index 545ad3f2b..6e56e7370 100644 --- a/src/gui/widget_tree.c +++ b/src/gui/widget_tree.c @@ -37,9 +37,7 @@ int Widget_Append(LCUI_Widget parent, LCUI_Widget widget) { - LCUI_Widget child; LCUI_WidgetEventRec ev = { 0 }; - LinkedListNode *node, *snode; if (!parent || !widget) { return -1; @@ -51,17 +49,7 @@ int Widget_Append(LCUI_Widget parent, LCUI_Widget widget) widget->parent = parent; widget->state = LCUI_WSTATE_CREATED; widget->index = parent->children.length; - node = &widget->node; - snode = &widget->node_show; - LinkedList_AppendNode(&parent->children, node); - LinkedList_AppendNode(&parent->children_show, snode); - /** 修改它后面的部件的 index 值 */ - node = node->next; - while (node) { - child = node->data; - child->index += 1; - node = node->next; - } + LinkedList_AppendNode(&parent->children, &widget->node); ev.cancel_bubble = TRUE; ev.type = LCUI_WEVENT_LINK; Widget_UpdateStyle(widget, TRUE); @@ -78,7 +66,7 @@ int Widget_Prepend(LCUI_Widget parent, LCUI_Widget widget) { LCUI_Widget child; LCUI_WidgetEventRec ev = { 0 }; - LinkedListNode *node, *snode; + LinkedListNode *node; if (!parent || !widget) { return -1; @@ -92,9 +80,7 @@ int Widget_Prepend(LCUI_Widget parent, LCUI_Widget widget) widget->parent = parent; widget->state = LCUI_WSTATE_CREATED; node = &widget->node; - snode = &widget->node_show; LinkedList_InsertNode(&parent->children, 0, node); - LinkedList_InsertNode(&parent->children_show, 0, snode); /** 修改它后面的部件的 index 值 */ node = node->next; while (node) { @@ -117,14 +103,13 @@ int Widget_Unwrap(LCUI_Widget widget) { size_t len; LCUI_Widget child; - LinkedList *children, *children_show; - LinkedListNode *target, *node, *prev, *snode; + LinkedList *children; + LinkedListNode *target, *node, *prev; if (!widget->parent) { return -1; } children = &widget->parent->children; - children_show = &widget->parent->children_show; len = widget->children.length; if (len > 0) { node = LinkedList_GetNode(&widget->children, 0); @@ -140,12 +125,9 @@ int Widget_Unwrap(LCUI_Widget widget) assert(node->data != NULL); prev = node->prev; child = node->data; - snode = &child->node_show; LinkedList_Unlink(&widget->children, node); - LinkedList_Unlink(&widget->children_show, snode); child->parent = widget->parent; LinkedList_Link(children, target, node); - LinkedList_AppendNode(children_show, snode); Widget_AddTaskForChildren(child, LCUI_WTASK_REFRESH_STYLE); Widget_UpdateTaskStatus(child); node = prev; @@ -162,27 +144,26 @@ int Widget_Unwrap(LCUI_Widget widget) return 0; } -int Widget_Unlink(LCUI_Widget widget) +int Widget_Unlink(LCUI_Widget w) { LCUI_Widget child; LCUI_WidgetEventRec ev = { 0 }; - LinkedListNode *node, *snode; + LinkedListNode *node; - if (!widget->parent) { + if (!w->parent) { return -1; } - node = &widget->node; - snode = &widget->node_show; - if (widget->index == widget->parent->children.length - 1) { - Widget_RemoveStatus(widget, "last-child"); - child = Widget_GetPrev(widget); + node = &w->node; + if (w->index == w->parent->children.length - 1) { + Widget_RemoveStatus(w, "last-child"); + child = Widget_GetPrev(w); if (child) { Widget_AddStatus(child, "last-child"); } } - if (widget->index == 0) { - Widget_RemoveStatus(widget, "first-child"); - child = Widget_GetNext(widget); + if (w->index == 0) { + Widget_RemoveStatus(w, "first-child"); + child = Widget_GetNext(w); if (child) { Widget_AddStatus(child, "first-child"); } @@ -194,14 +175,15 @@ int Widget_Unlink(LCUI_Widget widget) child->index -= 1; node = node->next; } - node = &widget->node; + node = &w->node; ev.cancel_bubble = TRUE; ev.type = LCUI_WEVENT_UNLINK; - Widget_TriggerEvent(widget, &ev, NULL); - LinkedList_Unlink(&widget->parent->children, node); - LinkedList_Unlink(&widget->parent->children_show, snode); - Widget_PostSurfaceEvent(widget, LCUI_WEVENT_UNLINK, TRUE); - widget->parent = NULL; + Widget_TriggerEvent(w, &ev, NULL); + LinkedList_Unlink(&w->parent->children, node); + LinkedList_Unlink(&w->parent->children_show, &w->node_show); + Widget_PostSurfaceEvent(w, LCUI_WEVENT_UNLINK, TRUE); + Widget_UpdateLayout(w->parent); + w->parent = NULL; return 0; }