Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/source
diff options
context:
space:
mode:
authorCampbell Barton <ideasman42@gmail.com>2018-04-22 18:16:39 +0300
committerCampbell Barton <ideasman42@gmail.com>2018-04-22 18:45:14 +0300
commite6d1fb87c6b0184416ce202ccba6a96a3ee04552 (patch)
tree39e1e321364129dfae355ecff938f0bafb5eae33 /source
parentb8e7991811dcf6fa698077f850fef17be83d2abb (diff)
UI: Initial popover support for panels
- UILayout.popover(.. panel_type ..) A single panel - UILayout.popover_group(.. panel categories ..) Expands all panels matching args. Currently used in the topbar for redo and paint options.
Diffstat (limited to 'source')
-rw-r--r--source/blender/editors/include/UI_interface.h26
-rw-r--r--source/blender/editors/interface/CMakeLists.txt1
-rw-r--r--source/blender/editors/interface/interface_handlers.c12
-rw-r--r--source/blender/editors/interface/interface_intern.h12
-rw-r--r--source/blender/editors/interface/interface_layout.c114
-rw-r--r--source/blender/editors/interface/interface_region_popover.c283
-rw-r--r--source/blender/editors/interface/interface_widgets.c2
-rw-r--r--source/blender/makesrna/RNA_access.h1
-rw-r--r--source/blender/makesrna/intern/rna_ui_api.c46
-rw-r--r--source/blender/makesrna/intern/rna_wm.c17
-rw-r--r--source/blender/makesrna/intern/rna_wm_api.c34
11 files changed, 547 insertions, 1 deletions
diff --git a/source/blender/editors/include/UI_interface.h b/source/blender/editors/include/UI_interface.h
index 67b9f391ac6..191c34fc7f2 100644
--- a/source/blender/editors/include/UI_interface.h
+++ b/source/blender/editors/include/UI_interface.h
@@ -265,6 +265,7 @@ typedef enum {
UI_BTYPE_CHECKBOX_N = (14 << 9),
UI_BTYPE_COLOR = (15 << 9),
UI_BTYPE_TAB = (16 << 9),
+ UI_BTYPE_POPOVER = (17 << 9),
UI_BTYPE_SCROLL = (18 << 9),
UI_BTYPE_BLOCK = (19 << 9),
UI_BTYPE_LABEL = (20 << 9),
@@ -409,6 +410,17 @@ int UI_popup_menu_invoke(struct bContext *C, const char *idname, struct ReportLi
void UI_popup_menu_retval_set(const uiBlock *block, const int retval, const bool enable);
void UI_popup_menu_but_set(uiPopupMenu *pup, struct ARegion *butregion, uiBut *but);
+/* interface_region_popover.c */
+
+typedef struct uiPopover uiPopover;
+
+uiPopover *UI_popover_begin(
+ struct bContext *C) ATTR_NONNULL();
+uiPopover *UI_popover_begin_ex(
+ struct bContext *C, const char *block_name) ATTR_NONNULL();
+void UI_popover_end(struct bContext *C, struct uiPopover *head);
+struct uiLayout *UI_popover_layout(uiPopover *head);
+
/* interface_region_menu_pie.c */
/* Pie menus */
typedef struct uiPieMenu uiPieMenu;
@@ -911,6 +923,7 @@ void uiLayoutSetContextPointer(uiLayout *layout, const char *name, struct Pointe
void uiLayoutContextCopy(uiLayout *layout, struct bContextStore *context);
const char *uiLayoutIntrospect(uiLayout *layout); // XXX - testing
struct MenuType *UI_but_menutype_get(uiBut *but);
+struct PanelType *UI_but_paneltype_get(uiBut *but);
void UI_menutype_draw(struct bContext *C, struct MenuType *mt, struct uiLayout *layout);
/* Only for convenience. */
@@ -1090,6 +1103,19 @@ void uiItemM(uiLayout *layout, struct bContext *C, const char *menuname, const c
void uiItemV(uiLayout *layout, const char *name, int icon, int argval); /* value */
void uiItemS(uiLayout *layout); /* separator */
+void uiItemPopoverPanel_ptr(
+ uiLayout *layout, struct bContext *C,
+ struct PanelType *pt,
+ const char *name, int icon);
+void uiItemPopoverPanel(
+ uiLayout *layout, struct bContext *C,
+ int space_id, int region_id, const char *panelname,
+ const char *name, int icon);
+void uiItemPopoverPanelFromGroup(
+ uiLayout *layout, struct bContext *C,
+ int space_id, int region_id,
+ const char *context, const char *category);
+
void uiItemMenuF(uiLayout *layout, const char *name, int icon, uiMenuCreateFunc func, void *arg);
void uiItemMenuEnumO_ptr(uiLayout *layout, struct bContext *C, struct wmOperatorType *ot, const char *propname, const char *name, int icon);
void uiItemMenuEnumO(uiLayout *layout, struct bContext *C, const char *opname, const char *propname, const char *name, int icon);
diff --git a/source/blender/editors/interface/CMakeLists.txt b/source/blender/editors/interface/CMakeLists.txt
index c023816b52c..cc5c580ad38 100644
--- a/source/blender/editors/interface/CMakeLists.txt
+++ b/source/blender/editors/interface/CMakeLists.txt
@@ -59,6 +59,7 @@ set(SRC
interface_region_color_picker.c
interface_region_menu_pie.c
interface_region_menu_popup.c
+ interface_region_popover.c
interface_region_popup.c
interface_region_search.c
interface_region_tooltip.c
diff --git a/source/blender/editors/interface/interface_handlers.c b/source/blender/editors/interface/interface_handlers.c
index 9e88c3cbb7f..4fbb8025af1 100644
--- a/source/blender/editors/interface/interface_handlers.c
+++ b/source/blender/editors/interface/interface_handlers.c
@@ -3431,6 +3431,7 @@ static void ui_block_open_begin(bContext *C, uiBut *but, uiHandleButtonData *dat
uiBlockCreateFunc func = NULL;
uiBlockHandleCreateFunc handlefunc = NULL;
uiMenuCreateFunc menufunc = NULL;
+ uiMenuCreateFunc popoverfunc = NULL;
void *arg = NULL;
switch (but->type) {
@@ -3450,6 +3451,11 @@ static void ui_block_open_begin(bContext *C, uiBut *but, uiHandleButtonData *dat
menufunc = but->menu_create_func;
arg = but->poin;
break;
+ case UI_BTYPE_POPOVER:
+ BLI_assert(but->menu_create_func);
+ popoverfunc = but->menu_create_func;
+ arg = but->poin;
+ break;
case UI_BTYPE_COLOR:
ui_but_v3_get(but, data->origvec);
copy_v3_v3(data->vec, data->origvec);
@@ -3474,6 +3480,11 @@ static void ui_block_open_begin(bContext *C, uiBut *but, uiHandleButtonData *dat
if (but->block->handle)
data->menu->popup = but->block->handle->popup;
}
+ else if (popoverfunc) {
+ data->menu = ui_popover_panel_create(C, data->region, but, popoverfunc, arg);
+ if (but->block->handle)
+ data->menu->popup = but->block->handle->popup;
+ }
#ifdef USE_ALLSELECT
{
@@ -7046,6 +7057,7 @@ static int ui_do_button(bContext *C, uiBlock *block, uiBut *but, const wmEvent *
retval = ui_do_but_TEX(C, block, but, data, event);
break;
case UI_BTYPE_MENU:
+ case UI_BTYPE_POPOVER:
case UI_BTYPE_BLOCK:
case UI_BTYPE_PULLDOWN:
retval = ui_do_but_BLOCK(C, but, data, event);
diff --git a/source/blender/editors/interface/interface_intern.h b/source/blender/editors/interface/interface_intern.h
index e0b0a8eeaab..b9e680f009a 100644
--- a/source/blender/editors/interface/interface_intern.h
+++ b/source/blender/editors/interface/interface_intern.h
@@ -615,6 +615,18 @@ uiPopupBlockHandle *ui_popup_menu_create(
struct bContext *C, struct ARegion *butregion, uiBut *but,
uiMenuCreateFunc create_func, void *arg);
+/* interface_region_popover.c */
+uiBlock *ui_popover_block_refresh(
+ struct bContext *C, uiPopupBlockHandle *handle,
+ ARegion *butregion, uiBut *but);
+uiPopupBlockHandle *ui_popover_block_create(
+ struct bContext *C, struct ARegion *butregion, uiBut *but,
+ uiBlockCreateFunc create_func, uiBlockHandleCreateFunc handle_create_func,
+ void *arg);
+uiPopupBlockHandle *ui_popover_panel_create(
+ struct bContext *C, struct ARegion *butregion, uiBut *but,
+ uiMenuCreateFunc create_func, void *arg);
+
/* interface_region_menu_pie.c */
void ui_pie_menu_level_create(
uiBlock *block, struct wmOperatorType *ot, const char *propname, IDProperty *properties,
diff --git a/source/blender/editors/interface/interface_layout.c b/source/blender/editors/interface/interface_layout.c
index 7193ad64359..3ea6ae08173 100644
--- a/source/blender/editors/interface/interface_layout.c
+++ b/source/blender/editors/interface/interface_layout.c
@@ -1824,6 +1824,35 @@ static void ui_item_menutype_func(bContext *C, uiLayout *layout, void *arg_mt)
layout->root->block->flag ^= UI_BLOCK_IS_FLIP;
}
+static void ui_item_paneltype_func(bContext *C, uiLayout *layout, void *arg_mt)
+{
+ PanelType *pt = (PanelType *)arg_mt;
+
+ /* TODO: move into UI_paneltype_draw */
+ Panel *panel = MEM_callocN(sizeof(Panel), "popover panel");
+ panel->type = pt;
+
+ if (layout->context) {
+ CTX_store_set(C, layout->context);
+ }
+
+ if (pt->draw_header) {
+ panel->layout = uiLayoutRow(layout, false);
+ pt->draw_header(C, panel);
+ panel->layout = NULL;
+ }
+
+ panel->layout = layout;
+ pt->draw(C, panel);
+ panel->layout = NULL;
+
+ if (layout->context) {
+ CTX_store_set(C, NULL);
+ }
+
+ MEM_freeN(panel);
+}
+
static uiBut *ui_item_menu(
uiLayout *layout, const char *name, int icon, uiMenuCreateFunc func, void *arg, void *argN,
const char *tip, bool force_menu)
@@ -1901,6 +1930,79 @@ void uiItemM(uiLayout *layout, bContext *UNUSED(C), const char *menuname, const
ui_item_menu(layout, name, icon, ui_item_menutype_func, mt, NULL, TIP_(mt->description), false);
}
+/* popover */
+void uiItemPopoverPanel_ptr(uiLayout *layout, bContext *UNUSED(C), PanelType *pt, const char *name, int icon)
+{
+ if (!name) {
+ name = CTX_IFACE_(pt->translation_context, pt->label);
+ }
+
+ if (layout->root->type == UI_LAYOUT_MENU && !icon)
+ icon = ICON_BLANK1;
+
+ uiBut *but = ui_item_menu(layout, name, icon, ui_item_paneltype_func, pt, NULL, NULL, false);
+ but->type = UI_BTYPE_POPOVER;
+}
+
+void uiItemPopoverPanel(
+ uiLayout *layout, bContext *C,
+ int space_id, int region_id, const char *panel_type,
+ const char *name, int icon)
+{
+ SpaceType *st = BKE_spacetype_from_id(space_id);
+ if (st == NULL) {
+ RNA_warning("space type not found %d", space_id);
+ return;
+ }
+ ARegionType *art = BKE_regiontype_from_id(st, region_id);
+ if (art == NULL) {
+ RNA_warning("region type not found %d", region_id);
+ return;
+ }
+
+ PanelType *pt;
+ for (pt = art->paneltypes.first; pt; pt = pt->next) {
+ if (STREQ(pt->idname, panel_type)) {
+ break;
+ }
+ }
+
+ if (pt == NULL) {
+ RNA_warning("area type not found %s", panel_type);
+ return;
+ }
+
+ uiItemPopoverPanel_ptr(layout, C, pt, name, icon);
+}
+
+void uiItemPopoverPanelFromGroup(
+ uiLayout *layout, bContext *C,
+ int space_id, int region_id, const char *context, const char *category)
+{
+ SpaceType *st = BKE_spacetype_from_id(space_id);
+ if (st == NULL) {
+ RNA_warning("space type not found %d", space_id);
+ return;
+ }
+ ARegionType *art = BKE_regiontype_from_id(st, region_id);
+ if (art == NULL) {
+ RNA_warning("region type not found %d", region_id);
+ return;
+ }
+
+ for (PanelType *pt = art->paneltypes.first; pt; pt = pt->next) {
+ /* Causes too many panels, check context. */
+ if (/* (*context == '\0') || */ STREQ(pt->context, context)) {
+ if ((*category == '\0') || STREQ(pt->category, category)) {
+ if (pt->poll == NULL || pt->poll(C, pt)) {
+ uiItemPopoverPanel_ptr(layout, C, pt, NULL, ICON_NONE);
+ }
+ }
+ }
+ }
+}
+
+
/* label item */
static uiBut *uiItemL_(uiLayout *layout, const char *name, int icon)
{
@@ -3604,6 +3706,18 @@ MenuType *UI_but_menutype_get(uiBut *but)
}
}
+/* this is a bit of a hack but best keep it in one place at least */
+PanelType *UI_but_paneltype_get(uiBut *but)
+{
+ if (but->menu_create_func == ui_item_paneltype_func) {
+ return (PanelType *)but->poin;
+ }
+ else {
+ return NULL;
+ }
+}
+
+
void UI_menutype_draw(bContext *C, MenuType *mt, struct uiLayout *layout)
{
Menu menu = {
diff --git a/source/blender/editors/interface/interface_region_popover.c b/source/blender/editors/interface/interface_region_popover.c
new file mode 100644
index 00000000000..035efb368a6
--- /dev/null
+++ b/source/blender/editors/interface/interface_region_popover.c
@@ -0,0 +1,283 @@
+/*
+ * ***** BEGIN GPL LICENSE BLOCK *****
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * The Original Code is Copyright (C) 2008 Blender Foundation.
+ * All rights reserved.
+ *
+ * Contributor(s): Blender Foundation
+ *
+ * ***** END GPL LICENSE BLOCK *****
+ */
+
+/** \file blender/editors/interface/interface_region_popover.c
+ * \ingroup edinterface
+ *
+ * Pop-Over Region
+ *
+ * \note This is very close to 'interface_region_menu_popup.c'
+ *
+ * We could even merge them, however menu logic is already over-loaded.
+ * PopOver's have the following differences.
+ *
+ * - UI is not constrained to a list.
+ * - Pressing a button won't close the pop-over.
+ * - Different draw style (to show this is has different behavior from a menu).
+ * - #PanelType are used insetead of #MenuType.
+ * - No menu flipping support.
+ * - No moving the menu to fit the mouse cursor.
+ * - No key accelerators to access menu items
+ * (if we add support they would work differently).
+ * - No arrow key navigation.
+ * - No menu memory.
+ * - No title.
+ */
+
+#include <stdarg.h>
+#include <stdlib.h>
+#include <string.h>
+#include <assert.h>
+
+#include "MEM_guardedalloc.h"
+
+#include "DNA_userdef_types.h"
+
+#include "BLI_math.h"
+#include "BLI_listbase.h"
+
+#include "BLI_string.h"
+#include "BLI_rect.h"
+#include "BLI_utildefines.h"
+#include "BLI_ghash.h"
+
+#include "BKE_context.h"
+#include "BKE_screen.h"
+#include "BKE_report.h"
+
+#include "WM_api.h"
+#include "WM_types.h"
+
+#include "RNA_access.h"
+
+#include "UI_interface.h"
+
+#include "BLT_translation.h"
+
+#include "ED_screen.h"
+
+#include "interface_intern.h"
+#include "interface_regions_intern.h"
+
+/* -------------------------------------------------------------------- */
+/** \name Popup Menu with Callback or String
+ * \{ */
+
+struct uiPopover {
+ uiBlock *block;
+ uiLayout *layout;
+ uiBut *but;
+ ARegion *butregion;
+
+ int mx, my;
+ bool popover, slideout;
+
+ uiMenuCreateFunc menu_func;
+ void *menu_arg;
+};
+
+static uiBlock *ui_block_func_POPOVER(bContext *C, uiPopupBlockHandle *handle, void *arg_pup)
+{
+ uiBlock *block;
+ uiPopover *pup = arg_pup;
+ int offset[2], minwidth, width, height;
+
+ if (pup->menu_func) {
+ pup->block->handle = handle;
+ pup->menu_func(C, pup->layout, pup->menu_arg);
+ pup->block->handle = NULL;
+ }
+
+ if (pup->but) {
+ /* minimum width to enforece */
+ minwidth = BLI_rctf_size_x(&pup->but->rect);
+ }
+ else {
+ minwidth = 50;
+ }
+
+ block = pup->block;
+
+ /* in some cases we create the block before the region,
+ * so we set it delayed here if necessary */
+ if (BLI_findindex(&handle->region->uiblocks, block) == -1)
+ UI_block_region_set(block, handle->region);
+
+ block->direction = UI_DIR_DOWN;
+
+ UI_block_layout_resolve(block, &width, &height);
+
+ UI_block_flag_enable(block, UI_BLOCK_MOVEMOUSE_QUIT | UI_BLOCK_KEEP_OPEN);
+
+ if (pup->popover) {
+ UI_block_flag_enable(block, UI_BLOCK_LOOP);
+ UI_block_direction_set(block, block->direction);
+ block->minbounds = minwidth;
+ UI_block_bounds_set_popup(block, 1, offset[0], offset[1]);
+ }
+ else {
+ /* for a header menu we set the direction automatic */
+ block->minbounds = minwidth;
+ UI_block_bounds_set_normal(block, 1);
+ }
+
+ /* if menu slides out of other menu, override direction */
+ if (pup->slideout)
+ UI_block_direction_set(block, UI_DIR_RIGHT);
+
+ return pup->block;
+}
+
+uiPopupBlockHandle *ui_popover_panel_create(
+ bContext *C, ARegion *butregion, uiBut *but,
+ uiMenuCreateFunc menu_func, void *arg)
+{
+ wmWindow *window = CTX_wm_window(C);
+ uiStyle *style = UI_style_get_dpi();
+ uiPopupBlockHandle *handle;
+ uiPopover *pup;
+
+ pup = MEM_callocN(sizeof(uiPopover), __func__);
+ pup->block = UI_block_begin(C, NULL, __func__, UI_EMBOSS);
+ UI_block_emboss_set(pup->block, UI_EMBOSS);
+ pup->layout = UI_block_layout(pup->block, UI_LAYOUT_VERTICAL, UI_LAYOUT_PANEL, 0, 0, 200, 0, MENU_PADDING, style);
+ pup->slideout = false; // but ? ui_block_is_menu(but->block) : false;
+ pup->but = but;
+ uiLayoutSetOperatorContext(pup->layout, WM_OP_INVOKE_REGION_WIN);
+
+ if (!but) {
+ /* no button to start from, means we are a popover */
+ pup->mx = window->eventstate->x;
+ pup->my = window->eventstate->y;
+ pup->popover = true;
+ pup->block->flag |= UI_BLOCK_NO_FLIP;
+ }
+ /* some enums reversing is strange, currently we have no good way to
+ * reverse some enum's but not others, so reverse all so the first menu
+ * items are always close to the mouse cursor */
+ else {
+ if (but->context)
+ uiLayoutContextCopy(pup->layout, but->context);
+ }
+
+ /* menu is created from a callback */
+ pup->menu_func = menu_func;
+ pup->menu_arg = arg;
+
+ handle = ui_popup_block_create(C, butregion, but, NULL, ui_block_func_POPOVER, pup);
+
+ if (!but) {
+ handle->popup = true;
+
+ UI_popup_handlers_add(C, &window->modalhandlers, handle, 0);
+ WM_event_add_mousemove(C);
+ }
+
+ handle->can_refresh = false;
+ MEM_freeN(pup);
+
+ return handle;
+}
+
+/** \} */
+
+/* -------------------------------------------------------------------- */
+/** \name Popup Menu API with begin & end
+ * \{ */
+
+/**
+ * Only return handler, and set optional title.
+ * \param block_name: Assigned to uiBlock.name (useful info for debugging).
+ */
+uiPopover *UI_popover_begin_ex(bContext *C, const char *block_name)
+{
+ uiStyle *style = UI_style_get_dpi();
+ uiPopover *pup = MEM_callocN(sizeof(uiPopover), "popover menu");
+
+ pup->block = UI_block_begin(C, NULL, block_name, UI_EMBOSS);
+ pup->layout = UI_block_layout(pup->block, UI_LAYOUT_VERTICAL, UI_LAYOUT_PANEL, 0, 0, 200, 0, MENU_PADDING, style);
+
+ /* Copied from menus, change if needed. */
+ uiLayoutSetOperatorContext(pup->layout, WM_OP_EXEC_REGION_WIN);
+
+ /* create in advance so we can let buttons point to retval already */
+ pup->block->handle = MEM_callocN(sizeof(uiPopupBlockHandle), "uiPopupBlockHandle");
+
+ return pup;
+}
+
+uiPopover *UI_popover_begin(bContext *C)
+{
+ return UI_popover_begin_ex(C, __func__);
+}
+
+/**
+ * Setting the button makes the popover open from the button instead of the cursor.
+ */
+#if 0
+void UI_popover_panel_but_set(uiPopover *pup, struct ARegion *butregion, uiBut *but)
+{
+ pup->but = but;
+ pup->butregion = butregion;
+}
+#endif
+
+/* set the whole structure to work */
+void UI_popover_end(bContext *C, uiPopover *pup)
+{
+ wmWindow *window = CTX_wm_window(C);
+ uiPopupBlockHandle *menu;
+ uiBut *but = NULL;
+ ARegion *butregion = NULL;
+
+ pup->popover = true;
+ pup->mx = window->eventstate->x;
+ pup->my = window->eventstate->y;
+
+ if (pup->but) {
+ but = pup->but;
+ butregion = pup->butregion;
+ }
+
+ menu = ui_popup_block_create(C, butregion, but, NULL, ui_block_func_POPOVER, pup);
+ menu->popup = true;
+
+ UI_popup_handlers_add(C, &window->modalhandlers, menu, 0);
+ WM_event_add_mousemove(C);
+
+ menu->can_refresh = false;
+ MEM_freeN(pup);
+}
+
+uiLayout *UI_popover_layout(uiPopover *pup)
+{
+ return pup->layout;
+}
+
+/** \} */
+
+/* We may want to support this in futurew */
+/* Similar to UI_popup_menu_invoke */
+// int UI_popover_panel_invoke(bContext *C, const char *idname, ReportList *reports);
diff --git a/source/blender/editors/interface/interface_widgets.c b/source/blender/editors/interface/interface_widgets.c
index 5eafd6cf596..f1b1ef44bef 100644
--- a/source/blender/editors/interface/interface_widgets.c
+++ b/source/blender/editors/interface/interface_widgets.c
@@ -4414,7 +4414,7 @@ void ui_draw_menu_back(uiStyle *UNUSED(style), uiBlock *block, rcti *rect)
wt->draw(&wt->wcol, rect, block->flag, block->direction);
else
wt->draw(&wt->wcol, rect, 0, 0);
-
+
if (block) {
float draw_color[4];
unsigned char *color = (unsigned char *)wt->wcol.text;
diff --git a/source/blender/makesrna/RNA_access.h b/source/blender/makesrna/RNA_access.h
index 80eaa8f2649..fd83e386004 100644
--- a/source/blender/makesrna/RNA_access.h
+++ b/source/blender/makesrna/RNA_access.h
@@ -664,6 +664,7 @@ extern StructRNA RNA_TransformSequence;
extern StructRNA RNA_UILayout;
extern StructRNA RNA_UIList;
extern StructRNA RNA_UIPieMenu;
+extern StructRNA RNA_uiPopover;
extern StructRNA RNA_UIPopupMenu;
extern StructRNA RNA_UVWarpModifier;
extern StructRNA RNA_UVProjectModifier;
diff --git a/source/blender/makesrna/intern/rna_ui_api.c b/source/blender/makesrna/intern/rna_ui_api.c
index 367efd71519..a8ae3374b16 100644
--- a/source/blender/makesrna/intern/rna_ui_api.c
+++ b/source/blender/makesrna/intern/rna_ui_api.c
@@ -268,6 +268,29 @@ static void rna_uiItemM(uiLayout *layout, bContext *C, const char *menuname, con
uiItemM(layout, C, menuname, name, icon);
}
+static void rna_uiItemPopoverPanel(
+ uiLayout *layout, bContext *C,
+ int space_type, int region_type, const char *panel_type,
+ const char *name, const char *text_ctxt,
+ int translate, int icon, int icon_value)
+{
+ /* Get translated name (label). */
+ name = rna_translate_ui_text(name, text_ctxt, NULL, NULL, translate);
+
+ if (icon_value && !icon) {
+ icon = icon_value;
+ }
+
+ uiItemPopoverPanel(layout, C, space_type, region_type, panel_type, name, icon);
+}
+
+static void rna_uiItemPopoverPanelFromGroup(
+ uiLayout *layout, bContext *C,
+ int space_id, int region_id, const char *context, const char *category)
+{
+ uiItemPopoverPanelFromGroup(layout, C, space_id, region_id, context, category);
+}
+
static void rna_uiTemplateAnyID(uiLayout *layout, PointerRNA *ptr, const char *propname, const char *proptypename,
const char *name, const char *text_ctxt, int translate)
{
@@ -670,6 +693,29 @@ void RNA_api_ui_layout(StructRNA *srna)
parm = RNA_def_property(func, "icon_value", PROP_INT, PROP_UNSIGNED);
RNA_def_property_ui_text(parm, "Icon Value", "Override automatic icon of the item");
+ func = RNA_def_function(srna, "popover", "rna_uiItemPopoverPanel");
+ RNA_def_function_flag(func, FUNC_USE_CONTEXT);
+ parm = RNA_def_enum(func, "space_type", rna_enum_space_type_items, 0, "Space Type", "");
+ RNA_def_parameter_flags(parm, 0, PARM_REQUIRED);
+ parm = RNA_def_enum(func, "region_type", rna_enum_region_type_items, RGN_TYPE_WINDOW, "Region Type", "");
+ RNA_def_parameter_flags(parm, 0, PARM_REQUIRED);
+ parm = RNA_def_string(func, "panel_type", NULL, 0, "", "Identifier of the panel");
+ api_ui_item_common(func);
+ RNA_def_parameter_flags(parm, 0, PARM_REQUIRED);
+ parm = RNA_def_property(func, "icon_value", PROP_INT, PROP_UNSIGNED);
+ RNA_def_property_ui_text(parm, "Icon Value", "Override automatic icon of the item");
+
+ func = RNA_def_function(srna, "popover_group", "rna_uiItemPopoverPanelFromGroup");
+ RNA_def_function_flag(func, FUNC_USE_CONTEXT);
+ parm = RNA_def_enum(func, "space_type", rna_enum_space_type_items, 0, "Space Type", "");
+ RNA_def_parameter_flags(parm, 0, PARM_REQUIRED);
+ parm = RNA_def_enum(func, "region_type", rna_enum_region_type_items, RGN_TYPE_WINDOW, "Region Type", "");
+ RNA_def_parameter_flags(parm, 0, PARM_REQUIRED);
+ parm = RNA_def_string(func, "context", NULL, 0, "", "panel type context");
+ RNA_def_parameter_flags(parm, 0, PARM_REQUIRED);
+ parm = RNA_def_string(func, "category", NULL, 0, "", "panel type category");
+ RNA_def_parameter_flags(parm, 0, PARM_REQUIRED);
+
func = RNA_def_function(srna, "separator", "uiItemS");
RNA_def_function_ui_description(func, "Item. Inserts empty space into the layout between items");
diff --git a/source/blender/makesrna/intern/rna_wm.c b/source/blender/makesrna/intern/rna_wm.c
index d7718d2e0f2..0fa7f53da9b 100644
--- a/source/blender/makesrna/intern/rna_wm.c
+++ b/source/blender/makesrna/intern/rna_wm.c
@@ -629,6 +629,17 @@ static PointerRNA rna_PopupMenu_layout_get(PointerRNA *ptr)
return rptr;
}
+static PointerRNA rna_PopoverMenu_layout_get(PointerRNA *ptr)
+{
+ struct uiPopover *pup = ptr->data;
+ uiLayout *layout = UI_popover_layout(pup);
+
+ PointerRNA rptr;
+ RNA_pointer_create(ptr->id.data, &RNA_UILayout, layout, &rptr);
+
+ return rptr;
+}
+
static PointerRNA rna_PieMenu_layout_get(PointerRNA *ptr)
{
struct uiPieMenu *pie = ptr->data;
@@ -1978,6 +1989,11 @@ static void rna_def_popupmenu(BlenderRNA *brna)
rna_def_popup_menu_wrapper(brna, "UIPopupMenu", "uiPopupMenu", "rna_PopupMenu_layout_get");
}
+static void rna_def_popovermenu(BlenderRNA *brna)
+{
+ rna_def_popup_menu_wrapper(brna, "UIPopover", "uiPopover", "rna_PopoverMenu_layout_get");
+}
+
static void rna_def_piemenu(BlenderRNA *brna)
{
rna_def_popup_menu_wrapper(brna, "UIPieMenu", "uiPieMenu", "rna_PieMenu_layout_get");
@@ -2415,6 +2431,7 @@ void RNA_def_wm(BlenderRNA *brna)
rna_def_event(brna);
rna_def_timer(brna);
rna_def_popupmenu(brna);
+ rna_def_popovermenu(brna);
rna_def_piemenu(brna);
rna_def_window(brna);
rna_def_windowmanager(brna);
diff --git a/source/blender/makesrna/intern/rna_wm_api.c b/source/blender/makesrna/intern/rna_wm_api.c
index 28d8115f8c6..c053f980ff3 100644
--- a/source/blender/makesrna/intern/rna_wm_api.c
+++ b/source/blender/makesrna/intern/rna_wm_api.c
@@ -348,6 +348,24 @@ static void rna_PopMenuEnd(bContext *C, PointerRNA *handle)
UI_popup_menu_end(C, handle->data);
}
+/* popover wrapper */
+static PointerRNA rna_PopoverBegin(bContext *C)
+{
+ PointerRNA r_ptr;
+ void *data;
+
+ data = (void *)UI_popover_begin(C);
+
+ RNA_pointer_create(NULL, &RNA_UIPopover, data, &r_ptr);
+
+ return r_ptr;
+}
+
+static void rna_PopoverEnd(bContext *C, PointerRNA *handle)
+{
+ UI_popover_end(C, handle->data);
+}
+
/* pie menu wrapper */
static PointerRNA rna_PieMenuBegin(bContext *C, const char *title, int icon, PointerRNA *event)
{
@@ -541,6 +559,22 @@ void RNA_api_wm(StructRNA *srna)
parm = RNA_def_pointer(func, "menu", "UIPopupMenu", "", "");
RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_RNAPTR);
+
+ /* wrap UI_popover_panel_begin */
+ func = RNA_def_function(srna, "popover_begin__internal", "rna_PopoverBegin");
+ RNA_def_function_flag(func, FUNC_NO_SELF | FUNC_USE_CONTEXT);
+ /* return */
+ parm = RNA_def_pointer(func, "menu", "UIPopover", "", "");
+ RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_RNAPTR);
+ RNA_def_function_return(func, parm);
+
+ /* wrap UI_popover_panel_end */
+ func = RNA_def_function(srna, "popover_end__internal", "rna_PopoverEnd");
+ RNA_def_function_flag(func, FUNC_NO_SELF | FUNC_USE_CONTEXT);
+ parm = RNA_def_pointer(func, "menu", "UIPopover", "", "");
+ RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_RNAPTR);
+
+
/* wrap uiPieMenuBegin */
func = RNA_def_function(srna, "piemenu_begin__internal", "rna_PieMenuBegin");
RNA_def_function_flag(func, FUNC_NO_SELF | FUNC_USE_CONTEXT);