|
|
|
|
@ -231,7 +231,8 @@ Size2 PopupMenu::_get_contents_minimum_size() const {
|
|
|
|
|
real_t body_max_w = 0.0; // Indentation, text, and submenu arrow.
|
|
|
|
|
real_t icon_max_w = 0.0;
|
|
|
|
|
real_t accel_max_w = 0.0;
|
|
|
|
|
bool has_check = false;
|
|
|
|
|
bool has_check_gutter = false;
|
|
|
|
|
bool gutter_compact = theme_cache.gutter_compact;
|
|
|
|
|
|
|
|
|
|
for (int i = 0; i < items.size(); i++) {
|
|
|
|
|
_shape_item(i);
|
|
|
|
|
@ -239,7 +240,10 @@ Size2 PopupMenu::_get_contents_minimum_size() const {
|
|
|
|
|
icon_max_w = MAX(_get_item_icon_size(i).width, icon_max_w);
|
|
|
|
|
|
|
|
|
|
if (items[i].checkable_type && !items[i].separator) {
|
|
|
|
|
has_check = true;
|
|
|
|
|
has_check_gutter = true;
|
|
|
|
|
if (items[i].icon.is_valid()) {
|
|
|
|
|
gutter_compact = false;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (items[i].accel != Key::NONE || (items[i].shortcut.is_valid() && items[i].shortcut->has_valid_event())) {
|
|
|
|
|
@ -258,12 +262,16 @@ Size2 PopupMenu::_get_contents_minimum_size() const {
|
|
|
|
|
|
|
|
|
|
minsize.width += theme_cache.item_start_padding + body_max_w + accel_max_w + theme_cache.item_end_padding;
|
|
|
|
|
|
|
|
|
|
if (icon_max_w > 0) {
|
|
|
|
|
minsize.width += icon_max_w + theme_cache.h_separation;
|
|
|
|
|
}
|
|
|
|
|
if (has_check) {
|
|
|
|
|
int check_w = MAX(theme_cache.checked->get_width(), theme_cache.radio_checked->get_width());
|
|
|
|
|
minsize.width += check_w + theme_cache.h_separation;
|
|
|
|
|
const int check_w = MAX(theme_cache.checked->get_width(), theme_cache.radio_checked->get_width());
|
|
|
|
|
if (gutter_compact) {
|
|
|
|
|
minsize.width += MAX(icon_max_w, check_w) + theme_cache.h_separation;
|
|
|
|
|
} else {
|
|
|
|
|
if (icon_max_w > 0) {
|
|
|
|
|
minsize.width += icon_max_w + theme_cache.h_separation;
|
|
|
|
|
}
|
|
|
|
|
if (has_check_gutter) {
|
|
|
|
|
minsize.width += check_w + theme_cache.h_separation;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (is_inside_tree()) {
|
|
|
|
|
@ -801,31 +809,29 @@ void PopupMenu::_draw_items() {
|
|
|
|
|
float display_width = control->get_size().width;
|
|
|
|
|
|
|
|
|
|
// Find the widest icon and whether any items have a checkbox, and store the offsets for each.
|
|
|
|
|
float icon_ofs = 0.0;
|
|
|
|
|
bool has_check = false;
|
|
|
|
|
real_t icon_max_w = 0.0;
|
|
|
|
|
real_t check_max_w = 0.0;
|
|
|
|
|
bool has_check_gutter = false;
|
|
|
|
|
bool gutter_compact = theme_cache.gutter_compact;
|
|
|
|
|
for (int i = 0; i < items.size(); i++) {
|
|
|
|
|
if (items[i].separator) {
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
Size2 icon_size = _get_item_icon_size(i);
|
|
|
|
|
icon_ofs = MAX(icon_size.width, icon_ofs);
|
|
|
|
|
icon_max_w = MAX(_get_item_icon_size(i).width, icon_max_w);
|
|
|
|
|
|
|
|
|
|
if (items[i].checkable_type) {
|
|
|
|
|
has_check = true;
|
|
|
|
|
has_check_gutter = true;
|
|
|
|
|
if (items[i].icon.is_valid()) {
|
|
|
|
|
gutter_compact = false;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
if (icon_ofs > 0.0) {
|
|
|
|
|
icon_ofs += theme_cache.h_separation;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
float check_ofs = 0.0;
|
|
|
|
|
if (has_check) {
|
|
|
|
|
if (has_check_gutter) {
|
|
|
|
|
for (int i = 0; i < 4; i++) {
|
|
|
|
|
check_ofs = MAX(check_ofs, check[i]->get_width());
|
|
|
|
|
check_ofs = MAX(check_ofs, uncheck[i]->get_width());
|
|
|
|
|
check_max_w = MAX(check_max_w, check[i]->get_width());
|
|
|
|
|
check_max_w = MAX(check_max_w, uncheck[i]->get_width());
|
|
|
|
|
}
|
|
|
|
|
check_ofs += theme_cache.h_separation;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
Point2 ofs;
|
|
|
|
|
@ -911,10 +917,11 @@ void PopupMenu::_draw_items() {
|
|
|
|
|
separator_ofs += icon_size.width + theme_cache.h_separation;
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
const real_t check_w = (gutter_compact || !has_check_gutter) ? 0 : (check_max_w + theme_cache.h_separation);
|
|
|
|
|
if (rtl) {
|
|
|
|
|
icon_pos = Size2(control->get_size().width - item_ofs.x - check_ofs - icon_size.width, item_ofs.y);
|
|
|
|
|
icon_pos = Size2(control->get_size().width - item_ofs.x - check_w - icon_size.width, item_ofs.y);
|
|
|
|
|
} else {
|
|
|
|
|
icon_pos = item_ofs + Size2(check_ofs, 0);
|
|
|
|
|
icon_pos = item_ofs + Size2(check_w, 0);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
@ -941,8 +948,16 @@ void PopupMenu::_draw_items() {
|
|
|
|
|
items[i].text_buf->draw(ci, text_pos, theme_cache.font_separator_color);
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
item_ofs.x += icon_ofs + check_ofs;
|
|
|
|
|
|
|
|
|
|
if (gutter_compact) {
|
|
|
|
|
item_ofs.x += MAX(icon_max_w, check_max_w) + theme_cache.h_separation;
|
|
|
|
|
} else {
|
|
|
|
|
if (icon_max_w > 0) {
|
|
|
|
|
item_ofs.x += icon_max_w + theme_cache.h_separation;
|
|
|
|
|
}
|
|
|
|
|
if (has_check_gutter) {
|
|
|
|
|
item_ofs.x += check_max_w + theme_cache.h_separation;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
if (rtl) {
|
|
|
|
|
Vector2 text_pos = Size2(control->get_size().width - items[i].text_buf->get_size().width - item_ofs.x, item_ofs.y) + Point2(0, Math::floor((h - items[i].text_buf->get_size().y) / 2.0));
|
|
|
|
|
if (theme_cache.font_outline_size > 0 && theme_cache.font_outline_color.a > 0) {
|
|
|
|
|
@ -3136,6 +3151,7 @@ void PopupMenu::_bind_methods() {
|
|
|
|
|
BIND_THEME_ITEM(Theme::DATA_TYPE_CONSTANT, PopupMenu, item_start_padding);
|
|
|
|
|
BIND_THEME_ITEM(Theme::DATA_TYPE_CONSTANT, PopupMenu, item_end_padding);
|
|
|
|
|
BIND_THEME_ITEM(Theme::DATA_TYPE_CONSTANT, PopupMenu, icon_max_width);
|
|
|
|
|
BIND_THEME_ITEM(Theme::DATA_TYPE_CONSTANT, PopupMenu, gutter_compact);
|
|
|
|
|
|
|
|
|
|
BIND_THEME_ITEM(Theme::DATA_TYPE_ICON, PopupMenu, checked);
|
|
|
|
|
BIND_THEME_ITEM(Theme::DATA_TYPE_ICON, PopupMenu, checked_disabled);
|
|
|
|
|
|