[Bf-blender-cvs] [a33720329bb] property-search-ui: Property Search: New method that reuses existing layouts
Hans Goudey
noreply at git.blender.org
Fri Jun 19 13:41:21 CEST 2020
Commit: a33720329bba1204feee6f2e1bee8edb99e4619d
Author: Hans Goudey
Date: Thu Jun 18 17:00:38 2020 -0400
Branches: property-search-ui
https://developer.blender.org/rBa33720329bba1204feee6f2e1bee8edb99e4619d
Property Search: New method that reuses existing layouts
This method just transforms each layout into a row or a column, without
adding any new layouts at all. There are a few problems with this method
though, the columns have a fixed width for some reason, and it becomes
more difficult to add the label column.
===================================================================
M source/blender/editors/interface/interface_layout.c
===================================================================
diff --git a/source/blender/editors/interface/interface_layout.c b/source/blender/editors/interface/interface_layout.c
index 8cf1fb5ce5b..54282664116 100644
--- a/source/blender/editors/interface/interface_layout.c
+++ b/source/blender/editors/interface/interface_layout.c
@@ -5072,7 +5072,7 @@ int uiLayoutGetEmboss(uiLayout *layout)
* \{ */
// #define PROPERTY_SEARCH_USE_TOOLTIPS
-// #define DEBUG_LAYOUT_ROOTS
+#define DEBUG_LAYOUT_ROOTS
static void ui_layout_free(uiLayout *layout);
@@ -5149,38 +5149,13 @@ static void debug_print_layout(uiItem *item, int depth)
#endif /* DEBUG_LAYOUT_ROOTS */
/**
- * Free all layouts except if a child layout has a
+ * Tag all buttons with whether they matched the search filter or not.
*
- * \return True if the layout was filtered.
+ * \note This doesn't actually remove any buttons, and buttons that were tagged might
+ * not even be removed if they were in a layout with property search turned off.
*/
-// static bool ui_layout_free_filtered(uiLayout *layout)
-// {
-// bool children_filtered = true;
-// bool filter_layout = layout->item.flag & UI_ITEM_USE_SEARCH_FILTER;
-// LISTBASE_FOREACH_MUTABLE (uiItem *, item, &layout->items) {
-// if (filter_layout && item->type == ITEM_BUTTON) {
-// MEM_freeN(item);
-// }
-// else {
-// children_filtered &= ui_layout_free_filtered((uiLayout *)item);
-// }
-// }
-
-// filter_layout &= children_filtered;
-
-// if (filter_layout) {
-// MEM_freeN(layout);
-// }
-
-// return filter_layout;
-// }
-
-/**
- * \return True if all buttons were tagged for removal.
- */
-static bool ui_block_search_filter_tag_buttons(uiBlock *block)
+static void ui_block_search_filter_tag_buttons(uiBlock *block)
{
- bool empty = true;
LISTBASE_FOREACH (uiBut *, but, &block->buttons) {
/* Flag all buttons with no RNA property. This is probably too strict. */
if (but->rnaprop == NULL) {
@@ -5204,159 +5179,159 @@ static bool ui_block_search_filter_tag_buttons(uiBlock *block)
}
but->flag |= UI_FILTERED;
- empty = false;
}
- return empty;
}
-static void move_button_to_search_filter_layout(uiItem *item,
- uiLayout *source_layout,
- uiLayout *labels,
- uiLayout *properties)
+/**
+ * Recursive implementation for #ui_block_search_filter_clean.
+ */
+static bool ui_layout_search_filter_clean_recursive(uiLayout *layout)
{
- BLI_assert(item->type == ITEM_BUTTON);
- uiButtonItem *button_item = (uiButtonItem *)item;
-
- /* Move the item. */
- BLI_remlink(&source_layout->items, item);
- BLI_addtail(&properties->items, item);
-
- /* Add a label if the text isn't contained in the button. */
- if (button_item->but->rnaprop) {
- char name[MAX_NAME];
- strcpy(name, RNA_property_ui_name(button_item->but->rnaprop));
- if (ELEM(button_item->but->type,
- UI_BTYPE_CHECKBOX,
- UI_BTYPE_TOGGLE_N,
- UI_BTYPE_ICON_TOGGLE_N,
- UI_BTYPE_CHECKBOX_N,
- UI_BTYPE_LABEL)) {
- /* Toggle buttons with no outside label and have their text changed to the RNA name. */
- uiItemL(labels, "", ICON_NONE);
- strcpy(button_item->but->str, name);
- }
- else {
- uiItemL(labels, name, ICON_NONE);
- /* Add a decorator for animatable properties. */
- if (/* RNA_property_animateable(...) */ 1) {
- // uiItemL(decorators, "", ICON_NONE);
+ /* Remove all search filtered button items. */
+ bool layout_emptied = true;
+ if (uiLayoutGetPropSearch(layout)) {
+ LISTBASE_FOREACH_MUTABLE (uiItem *, item, &layout->items) {
+ if (item->type == ITEM_BUTTON) {
+ uiButtonItem *button_item = (uiButtonItem *)item;
+ if (button_item->but->flag & UI_FILTERED) {
+ button_item->but->flag |= UI_HIDDEN;
+ BLI_remlink(&layout->items, item);
+ MEM_freeN(item);
+ }
+ else {
+ layout_emptied = false;
+ }
}
}
}
- else {
- uiItemL(labels, "BUTTON NO RNA PROP", ICON_NONE);
+
+ /* Recursively clean sub-layouts. */
+ bool all_children_empty = true;
+ LISTBASE_FOREACH_MUTABLE (uiItem *, item, &layout->items) {
+ if (item->type == ITEM_BUTTON) {
+ BLI_assert(!layout_emptied || !uiLayoutGetPropSearch(layout));
+ continue;
+ }
+
+ bool empty = ui_layout_search_filter_clean_recursive((uiLayout *)item);
+ all_children_empty &= empty;
+
+ if (empty) {
+ BLI_assert(BLI_findindex(&layout->items, item) != -1);
+ BLI_remlink(&layout->items, item);
+ MEM_freeN(item);
+ }
}
+
+ return layout_emptied && all_children_empty;
}
/**
- * Check for an expanded / aligned row or column, and move the buttons over to the property search
- * layout if the special case applies. Assumes all filtered buttons have already been removed.
- *
- * \return True if this special case applied and the function did anything.
+ * Remove buttons on layouts with property search set to true,
+ * and remove layouts with no buttons and empty child layouts.
*/
-static bool move_aligned_layout_special_case(uiLayout *labels,
- uiLayout *properties,
- uiLayout *layout)
+static bool ui_block_search_filter_clean(uiBlock *block)
{
- /* Check for simple special case conditions. */
- if (!layout->align || !ELEM(((uiItem *)layout)->type, ITEM_LAYOUT_ROW)) {
- return false;
- }
-
- /* Only apply the special case if there are no sublayouts. */
- LISTBASE_FOREACH (uiItem *, item, &layout->items) {
- if (item->type != ITEM_BUTTON) {
- return false;
+ bool all_roots_empty = true;
+ LISTBASE_FOREACH_MUTABLE (uiLayoutRoot *, root, &block->layouts) {
+ /* Find exceptions to search layout. */
+ if (root->type == UI_LAYOUT_HEADER) {
+ continue;
}
- }
-
- /* Add a label to the label column based on the first button. */
- uiButtonItem *button_item = (uiButtonItem *)layout->items.first;
- char name[MAX_NAME];
- strcpy(name, RNA_property_ui_name(button_item->but->rnaprop));
- uiItemL(labels, name, ICON_NONE);
- /* Move the buttons to a subrow of the search layout. */
- uiLayout *aligned_row = uiLayoutRow(properties, true);
- LISTBASE_FOREACH_MUTABLE (uiItem *, item, &layout->items) {
- BLI_assert(item->type == ITEM_BUTTON);
+ bool empty = ui_layout_search_filter_clean_recursive(root->layout);
+ all_roots_empty &= empty;
- /* Move the item. */
- BLI_remlink(&layout->items, item);
- BLI_addtail(&aligned_row->items, item);
+ /* Empty roots should have all sublayouts freed, but they needs to be freed too. */
+ if (empty) {
+ BLI_assert(BLI_findindex(&block->layouts, root) != -1);
+ BLI_remlink(&block->layouts, root);
+ MEM_freeN(root);
+ }
}
- return true;
+ return all_roots_empty;
}
-/* HANS-TODO: Use uiLayoutRowWithHeading instead of keeping track of labels
- * and properties separately. */
-
-static bool ui_search_layout_fill(uiLayout *labels, uiLayout *properties, uiLayout *layout)
+static void ui_layout_search_build_recursive(uiLayout *layout,
+ int depth,
+ bool has_had_horizontal_vertical_switch)
{
- BLI_assert(layout->item.type != ITEM_BUTTON);
+ BLI_assert(uiLayoutGetPropSearch(layout) || !BLI_listbase_is_empty(&layout->items));
- /* Don't affect the search layouts. */
- if (ELEM(layout, labels, properties)) {
- return true;
- }
+ uiLayoutSetPropSep(layout, true);
- if (!(layout->item.flag & UI_ITEM_USE_SEARCH_FILTER)) {
- return false;
- }
+ bool is_horizontal = uiLayoutGetLocalDir(layout) == UI_LAYOUT_HORIZONTAL &&
+ (layout->item.type != ITEM_LAYOUT_ROOT);
+ // bool is_horizontal = uiLayoutGetLocalDir(layout) == UI_LAYOUT_HORIZONTAL;
+ bool build_horizontal = is_horizontal && !has_had_horizontal_vertical_switch;
- bool empty = true;
+ layout->item.type = build_horizontal ? ITEM_LAYOUT_ROW : ITEM_LAYOUT_COLUMN;
- /* Remove filtered buttons, checking if the layout will be empty without them. */
LISTBASE_FOREACH_MUTABLE (uiItem *, item, &layout->items) {
if (item->type == ITEM_BUTTON) {
uiButtonItem *button_item = (uiButtonItem *)item;
- if (button_item->but->flag & UI_FILTERED) {
- button_item->but->flag |= UI_HIDDEN;
- BLI_remlink(&layout->items, item);
- MEM_freeN(item);
+ char name[MAX_NAME];
+ if (button_item->but->rnaprop) {
+ strcpy(name, RNA_property_ui_name(button_item->but->rnaprop));
+
+ /* Toggle buttons have no outside label and so their text is changed to the RNA name. */
+ if (ELEM(button_item->but->type,
+ UI_BTYPE_CHECKBOX,
+ UI_BTYPE_TOGGLE_N,
+ UI_BTYPE_ICON_TOGGLE_N,
+ UI_BTYPE_CHECKBOX_N,
+ UI_BTYPE_LABEL)) {
+ strcpy(button_item->but->str, name);
+ }
+ else {
+ // uiLayout *row = uiLayoutRowWithHeading(layout, true, name);
+ // BLI_remlink(&layout->items, item);
+ // BLI_addtail(&row->items, item);
+ }
}
- else {
- empty = false;
+ }
+ else {
+ if (depth > 2) {
+ bool parent_is_horizontal = (layout->parent != NULL) &&
+ (uiLayoutGetLocalDir(layout->parent) == UI_LAYOUT_HORIZONTAL);
+ has_had_horizontal_vertical_switch |= (!parent_is_horizontal && is_horizontal);
}
+ ui_layout_search_build_recursive(
+ (uiLayout *)item, depth + 1, has_had_horizontal_vertical_switch);
}
}
+}
- /* Move the remaining filtered items to the property search layout. */
- if (empty) {
- /* Pass and move on to the sublayouts. */
- }
- else if (move_aligned_layout_special_case(labels, properties, layout)) {
- }
- else {
- /* General case. */
- LISTBASE_FOREACH_MUTABLE (uiItem *, item, &layout->items) {
- if (item->type == ITEM_BUTTON) {
- uiButtonItem *button_item = (uiButtonItem *)it
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list