From d8a0bfd2c70693e89c5b4a75f42c8ddf87fd7b34 Mon Sep 17 00:00:00 2001 From: Vas Crabb Date: Sun, 10 Jul 2016 15:38:37 +1000 Subject: [PATCH] UI refactoring: [Vas Crabb] * Move more main menu stuff out of the base menu class * Get rid of the rest of the troublesome static members in ui::menu (there are still problematic function statics in some menu classes) --- src/frontend/mame/ui/datmenu.cpp | 2 +- src/frontend/mame/ui/menu.cpp | 159 ++++++------------------------- src/frontend/mame/ui/menu.h | 43 ++++----- src/frontend/mame/ui/selgame.cpp | 41 +++----- src/frontend/mame/ui/selmenu.cpp | 128 ++++++++++++++++++++++--- src/frontend/mame/ui/selmenu.h | 26 +++-- src/frontend/mame/ui/selsoft.cpp | 37 ++----- 7 files changed, 205 insertions(+), 231 deletions(-) diff --git a/src/frontend/mame/ui/datmenu.cpp b/src/frontend/mame/ui/datmenu.cpp index 7ac8095c725..346d3572bf8 100644 --- a/src/frontend/mame/ui/datmenu.cpp +++ b/src/frontend/mame/ui/datmenu.cpp @@ -328,7 +328,7 @@ void menu_dats_view::custom_render(void *selectedref, float top, float bottom, f if (bcolor != UI_TEXT_BG_COLOR) ui().draw_textured_box(container, x1 - (space / 2), y1, x1 + width + (space / 2), y2, bcolor, rgb_t(255, 43, 43, 43), - hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); ui().draw_text_full(container, elem.label.c_str(), x1, y1, 1.0f, ui::text_layout::LEFT, ui::text_layout::NEVER, mame_ui_manager::NORMAL, fcolor, bcolor, &width, nullptr); x1 += width + space; diff --git a/src/frontend/mame/ui/menu.cpp b/src/frontend/mame/ui/menu.cpp index 60d0193e93a..107ee64d695 100644 --- a/src/frontend/mame/ui/menu.cpp +++ b/src/frontend/mame/ui/menu.cpp @@ -25,6 +25,7 @@ #include "uiinput.h" #include +#include #include #include @@ -42,12 +43,6 @@ namespace ui { std::mutex menu::s_global_state_guard; menu::global_state_map menu::s_global_states; -std::unique_ptr menu::hilight_bitmap; -render_texture *menu::hilight_texture; -render_texture *menu::snapx_texture; -render_texture *menu::hilight_main_texture; -std::unique_ptr menu::snapx_bitmap; -std::unique_ptr menu::hilight_main_bitmap; /*************************************************************************** INLINE FUNCTIONS @@ -89,6 +84,10 @@ bool menu::exclusive_input_pressed(int &iptkey, int key, int repeat) menu::global_state::global_state(running_machine &machine, ui_options const &options) : m_machine(machine) , m_cleanup_callbacks() + , m_hilight_bitmap(std::make_unique(256, 1)) + , m_hilight_texture() + , m_hilight_main_bitmap(std::make_unique(1, 128)) + , m_hilight_main_texture() , m_bgrnd_bitmap() , m_bgrnd_texture() , m_stack() @@ -97,6 +96,28 @@ menu::global_state::global_state(running_machine &machine, ui_options const &opt render_manager &render(machine.render()); auto const texture_free([&render](render_texture *texture) { render.texture_free(texture); }); + // create a texture for hilighting items + for (unsigned x = 0; x < 256; ++x) + { + unsigned const alpha((x < 25) ? (0xff * x / 25) : (x > (256 - 25)) ? (0xff * (255 - x) / 25) : 0xff); + m_hilight_bitmap->pix32(0, x) = rgb_t(alpha, 0xff, 0xff, 0xff); + } + m_hilight_texture = texture_ptr(render.texture_alloc(), texture_free); + m_hilight_texture->set_bitmap(*m_hilight_bitmap, m_hilight_bitmap->cliprect(), TEXFORMAT_ARGB32); + + // create a texture for hilighting items in main menu + for (unsigned y = 0; y < 128; ++y) + { + constexpr unsigned r1(0), g1(169), b1 = (255); // any start color + constexpr unsigned r2(0), g2(39), b2 = (130); // any stop color + unsigned const r = r1 + (y * (r2 - r1) / 128); + unsigned const g = g1 + (y * (g2 - g1) / 128); + unsigned const b = b1 + (y * (b2 - b1) / 128); + m_hilight_main_bitmap->pix32(y, 0) = rgb_t(r, g, b); + } + m_hilight_main_texture = texture_ptr(render.texture_alloc(), texture_free); + m_hilight_main_texture->set_bitmap(*m_hilight_main_bitmap, m_hilight_main_bitmap->cliprect(), TEXFORMAT_ARGB32); + // create a texture for arrow icons m_arrow_texture = texture_ptr(render.texture_alloc(render_triangle), texture_free); @@ -194,26 +215,12 @@ void menu::init(running_machine &machine, ui_options &mopt) { std::lock_guard guard(s_global_state_guard); auto const ins(s_global_states.emplace(&machine, std::make_shared(machine, mopt))); + assert(ins.second); // calling init twice is bad if (ins.second) machine.add_notifier(MACHINE_NOTIFY_EXIT, machine_notify_delegate(FUNC(menu::exit), &machine)); // add an exit callback to free memory else ins.first->second->stack_reset(); } - - // create a texture for hilighting items - hilight_bitmap = std::make_unique(256, 1); - for (int x = 0; x < 256; x++) - { - int alpha = 0xff; - if (x < 25) alpha = 0xff * x / 25; - if (x > 256 - 25) alpha = 0xff * (255 - x) / 25; - hilight_bitmap->pix32(0, x) = rgb_t(alpha,0xff,0xff,0xff); - } - hilight_texture = machine.render().texture_alloc(); - hilight_texture->set_bitmap(*hilight_bitmap, hilight_bitmap->cliprect(), TEXFORMAT_ARGB32); - - // initialize ui - init_ui(machine, mopt); } @@ -228,12 +235,6 @@ void menu::exit(running_machine &machine) std::lock_guard guard(s_global_state_guard); s_global_states.erase(&machine); } - - // free textures - render_manager &mre = machine.render(); - mre.texture_free(hilight_texture); - mre.texture_free(snapx_texture); - mre.texture_free(hilight_main_texture); } @@ -258,6 +259,8 @@ menu::menu(mame_ui_manager &mui, render_container *_container) , m_resetpos(0) , m_resetref(nullptr) { + assert(m_global_state); // not calling init is bad + container = _container; reset(reset_options::SELECT_FIRST); @@ -1260,7 +1263,7 @@ void menu::render_triangle(bitmap_argb32 &dest, bitmap_argb32 &source, const rec void menu::highlight(render_container *container, float x0, float y0, float x1, float y1, rgb_t bgcolor) { - container->add_quad(x0, y0, x1, y1, bgcolor, hilight_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE) | PRIMFLAG_PACKABLE); + container->add_quad(x0, y0, x1, y1, bgcolor, m_global_state->hilight_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE) | PRIMFLAG_PACKABLE); } @@ -1273,106 +1276,6 @@ void menu::draw_arrow(render_container *container, float x0, float y0, float x1, container->add_quad(x0, y0, x1, y1, fgcolor, m_global_state->arrow_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXORIENT(orientation) | PRIMFLAG_PACKABLE); } -//------------------------------------------------- -// init - initialize the ui menu system -//------------------------------------------------- - -void menu::init_ui(running_machine &machine, ui_options &mopt) -{ - render_manager &mrender = machine.render(); - // create a texture for hilighting items in main menu - hilight_main_bitmap = std::make_unique(1, 128); - int r1 = 0, g1 = 169, b1 = 255; //Any start color - int r2 = 0, g2 = 39, b2 = 130; //Any stop color - for (int y = 0; y < 128; y++) - { - int r = r1 + (y * (r2 - r1) / 128); - int g = g1 + (y * (g2 - g1) / 128); - int b = b1 + (y * (b2 - b1) / 128); - hilight_main_bitmap->pix32(y, 0) = rgb_t(r, g, b); - } - - hilight_main_texture = mrender.texture_alloc(); - hilight_main_texture->set_bitmap(*hilight_main_bitmap, hilight_main_bitmap->cliprect(), TEXFORMAT_ARGB32); - - // create a texture for snapshot - snapx_bitmap = std::make_unique(0, 0); - snapx_texture = mrender.texture_alloc(render_texture::hq_scale); -} - - -//------------------------------------------------- -// draw common arrows -//------------------------------------------------- - -void menu::draw_common_arrow(float origx1, float origy1, float origx2, float origy2, int current, int dmin, int dmax, float title_size) -{ - auto line_height = ui().get_line_height(); - auto lr_arrow_width = 0.4f * line_height * machine().render().ui_aspect(); - auto gutter_width = lr_arrow_width * 1.3f; - - // set left-right arrows dimension - float ar_x0 = 0.5f * (origx2 + origx1) + 0.5f * title_size + gutter_width - lr_arrow_width; - float ar_y0 = origy1 + 0.1f * line_height; - float ar_x1 = 0.5f * (origx2 + origx1) + 0.5f * title_size + gutter_width; - float ar_y1 = origy1 + 0.9f * line_height; - - float al_x0 = 0.5f * (origx2 + origx1) - 0.5f * title_size - gutter_width; - float al_y0 = origy1 + 0.1f * line_height; - float al_x1 = 0.5f * (origx2 + origx1) - 0.5f * title_size - gutter_width + lr_arrow_width; - float al_y1 = origy1 + 0.9f * line_height; - - rgb_t fgcolor_right, fgcolor_left; - fgcolor_right = fgcolor_left = UI_TEXT_COLOR; - - // set hover - if (mouse_hit && ar_x0 <= mouse_x && ar_x1 > mouse_x && ar_y0 <= mouse_y && ar_y1 > mouse_y && current != dmax) - { - ui().draw_textured_box(container, ar_x0 + 0.01f, ar_y0, ar_x1 - 0.01f, ar_y1, UI_MOUSEOVER_BG_COLOR, rgb_t(43, 43, 43), - hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); - hover = HOVER_UI_RIGHT; - fgcolor_right = UI_MOUSEOVER_COLOR; - } - else if (mouse_hit && al_x0 <= mouse_x && al_x1 > mouse_x && al_y0 <= mouse_y && al_y1 > mouse_y && current != dmin) - { - ui().draw_textured_box(container, al_x0 + 0.01f, al_y0, al_x1 - 0.01f, al_y1, UI_MOUSEOVER_BG_COLOR, rgb_t(43, 43, 43), - hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); - hover = HOVER_UI_LEFT; - fgcolor_left = UI_MOUSEOVER_COLOR; - } - - // apply arrow - if (current == dmin) - draw_arrow(container, ar_x0, ar_y0, ar_x1, ar_y1, fgcolor_right, ROT90); - else if (current == dmax) - draw_arrow(container, al_x0, al_y0, al_x1, al_y1, fgcolor_left, ROT90 ^ ORIENTATION_FLIP_X); - else - { - draw_arrow(container, ar_x0, ar_y0, ar_x1, ar_y1, fgcolor_right, ROT90); - draw_arrow(container, al_x0, al_y0, al_x1, al_y1, fgcolor_left, ROT90 ^ ORIENTATION_FLIP_X); - } -} - -//------------------------------------------------- -// draw info arrow -//------------------------------------------------- - -void menu::info_arrow(int ub, float origx1, float origx2, float oy1, float line_height, float text_size, float ud_arrow_width) -{ - rgb_t fgcolor = UI_TEXT_COLOR; - UINT32 orientation = (!ub) ? ROT0 : ROT0 ^ ORIENTATION_FLIP_Y; - - if (mouse_hit && origx1 <= mouse_x && origx2 > mouse_x && oy1 <= mouse_y && oy1 + (line_height * text_size) > mouse_y) - { - ui().draw_textured_box(container, origx1 + 0.01f, oy1, origx2 - 0.01f, oy1 + (line_height * text_size), UI_MOUSEOVER_BG_COLOR, - rgb_t(43, 43, 43), hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); - hover = (!ub) ? HOVER_DAT_UP : HOVER_DAT_DOWN; - fgcolor = UI_MOUSEOVER_COLOR; - } - - draw_arrow(container, 0.5f * (origx1 + origx2) - 0.5f * (ud_arrow_width * text_size), oy1 + 0.25f * (line_height * text_size), - 0.5f * (origx1 + origx2) + 0.5f * (ud_arrow_width * text_size), oy1 + 0.75f * (line_height * text_size), fgcolor, orientation); -} //------------------------------------------------- // draw - draw palette menu diff --git a/src/frontend/mame/ui/menu.h b/src/frontend/mame/ui/menu.h index d0df364d3fe..e024d4551b9 100644 --- a/src/frontend/mame/ui/menu.h +++ b/src/frontend/mame/ui/menu.h @@ -97,9 +97,6 @@ public: // test if one of the menus in the stack requires hide disable static bool stack_has_special_main_menu(running_machine &machine) { return get_global_state(machine)->stack_has_special_main_menu(); } - // highlight - static void highlight(render_container *container, float x0, float y0, float x1, float y1, rgb_t bgcolor); - // master handler static UINT32 ui_handler(render_container *container, mame_ui_manager &mui); @@ -118,9 +115,6 @@ public: virtual bool menu_has_search_active() { return false; } private: - static std::unique_ptr hilight_bitmap; - static render_texture *hilight_texture; - virtual void draw(UINT32 flags); void draw_text_box(); @@ -141,9 +135,6 @@ public: // draw right panel virtual void draw_right_panel(void *selectedref, float origx1, float origy1, float origx2, float origy2) { }; - // Global initialization - static void init_ui(running_machine &machine, ui_options &mopt); - // get arrows status template UINT32 get_arrow_flags(_T1 min, _T2 max, _T3 actual) @@ -255,10 +246,12 @@ protected: // test if the given key is pressed and we haven't already reported a key bool exclusive_input_pressed(int &iptkey, int key, int repeat); + // highlight + void highlight(render_container *container, float x0, float y0, float x1, float y1, rgb_t bgcolor); + render_texture *hilight_main_texture() { return m_global_state->hilight_main_texture(); } + // draw arrow void draw_arrow(render_container *container, float x0, float y0, float x1, float y1, rgb_t fgcolor, UINT32 orientation); - void draw_common_arrow(float origx1, float origy1, float origx2, float origy2, int current, int dmin, int dmax, float title); - void info_arrow(int ub, float origx1, float origx2, float oy1, float line_height, float text_size, float ud_arrow_width); // draw header and footer text void extra_text_render(float top, float bottom, float origx1, float origy1, float origx2, float origy2, const char *header, const char *footer); @@ -279,12 +272,6 @@ protected: int right_visible_lines; // right box lines - static bitmap_ptr snapx_bitmap; - static render_texture *snapx_texture; - - static std::unique_ptr hilight_main_bitmap; - static render_texture *hilight_main_texture; - private: class global_state { @@ -296,7 +283,9 @@ private: void add_cleanup_callback(cleanup_callback &&callback); - render_texture * arrow_texture() { return m_arrow_texture.get(); } + render_texture *hilight_texture() { return m_hilight_texture.get(); } + render_texture *hilight_main_texture() { return m_hilight_main_texture.get(); } + render_texture *arrow_texture() { return m_arrow_texture.get(); } bitmap_argb32 *bgrnd_bitmap() { return m_bgrnd_bitmap.get(); } render_texture * bgrnd_texture() { return m_bgrnd_texture.get(); } @@ -314,15 +303,19 @@ private: private: using cleanup_callback_vector = std::vector; - running_machine &m_machine; - cleanup_callback_vector m_cleanup_callbacks; + running_machine &m_machine; + cleanup_callback_vector m_cleanup_callbacks; - texture_ptr m_arrow_texture; - bitmap_ptr m_bgrnd_bitmap; - texture_ptr m_bgrnd_texture; + bitmap_ptr m_hilight_bitmap; + texture_ptr m_hilight_texture; + bitmap_ptr m_hilight_main_bitmap; + texture_ptr m_hilight_main_texture; + texture_ptr m_arrow_texture; + bitmap_ptr m_bgrnd_bitmap; + texture_ptr m_bgrnd_texture; - std::unique_ptr m_stack; - std::unique_ptr m_free; + std::unique_ptr m_stack; + std::unique_ptr m_free; }; using global_state_ptr = std::shared_ptr; using global_state_map = std::map; diff --git a/src/frontend/mame/ui/selgame.cpp b/src/frontend/mame/ui/selgame.cpp index 6f451a3018e..7ed67a15ed1 100644 --- a/src/frontend/mame/ui/selgame.cpp +++ b/src/frontend/mame/ui/selgame.cpp @@ -1864,7 +1864,7 @@ float menu_select_game::draw_left_panel(float x1, float y1, float x2, float y2) fgcolor = rgb_t(0xff, 0xff, 0xff, 0x00); bgcolor = rgb_t(0xff, 0xff, 0xff, 0xff); ui().draw_textured_box(container, x1, y1, x2, y1 + line_height_max, bgcolor, rgb_t(255, 43, 43, 43), - hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); } float x1t = x1 + text_sign; @@ -2029,7 +2029,7 @@ void menu_select_game::infos_render(void *selectedref, float origx1, float origy if (bgcolor != UI_TEXT_BG_COLOR) ui().draw_textured_box(container, origx1 + ((middle - title_size) * 0.5f), origy1, origx1 + ((middle + title_size) * 0.5f), - origy1 + line_height, bgcolor, rgb_t(255, 43, 43, 43), hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + origy1 + line_height, bgcolor, rgb_t(255, 43, 43, 43), hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); ui().draw_text_full(container, snaptext.c_str(), origx1, origy1, origx2 - origx1, ui::text_layout::CENTER, ui::text_layout::NEVER, mame_ui_manager::NORMAL, fgcolor, bgcolor, nullptr, nullptr, tmp_size); @@ -2093,10 +2093,10 @@ void menu_select_game::infos_render(void *selectedref, float origx1, float origy // up arrow if (r == 0 && m_topline_datsview != 0) - info_arrow(0, origx1, origx2, oy1, line_height, text_size, ud_arrow_width); + draw_info_arrow(0, origx1, origx2, oy1, line_height, text_size, ud_arrow_width); // bottom arrow else if (r == r_visible_lines - 1 && itemline != m_total_lines - 1) - info_arrow(1, origx1, origx2, oy1, line_height, text_size, ud_arrow_width); + draw_info_arrow(1, origx1, origx2, oy1, line_height, text_size, ud_arrow_width); // special case for mamescore else if (ui_globals::curdats_view == UI_STORY_LOAD) { @@ -2203,7 +2203,7 @@ void menu_select_game::infos_render(void *selectedref, float origx1, float origy if (bgcolor != UI_TEXT_BG_COLOR) ui().draw_textured_box(container, origx1 + ((middle - title_size) * 0.5f), origy1, origx1 + ((middle + title_size) * 0.5f), - origy1 + line_height, bgcolor, rgb_t(255, 43, 43, 43), hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + origy1 + line_height, bgcolor, rgb_t(255, 43, 43, 43), hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); ui().draw_text_full(container, t_text[ui_globals::cur_sw_dats_view].c_str(), origx1, origy1, origx2 - origx1, ui::text_layout::CENTER, ui::text_layout::TRUNCATE, mame_ui_manager::NORMAL, fgcolor, bgcolor, nullptr, nullptr); @@ -2251,10 +2251,10 @@ void menu_select_game::infos_render(void *selectedref, float origx1, float origy // up arrow if (r == 0 && m_topline_datsview != 0) - info_arrow(0, origx1, origx2, oy1, line_height, text_size, ud_arrow_width); + draw_info_arrow(0, origx1, origx2, oy1, line_height, text_size, ud_arrow_width); // bottom arrow else if (r == r_visible_lines - 1 && itemline != m_total_lines - 1) - info_arrow(1, origx1, origx2, oy1, line_height, text_size, ud_arrow_width); + draw_info_arrow(1, origx1, origx2, oy1, line_height, text_size, ud_arrow_width); else ui().draw_text_full(container, tempbuf.c_str(), origx1 + gutter_width, oy1, origx2 - origx1, ui::text_layout::LEFT, ui::text_layout::TRUNCATE, mame_ui_manager::NORMAL, UI_TEXT_COLOR, UI_TEXT_BG_COLOR, nullptr, nullptr, text_size); @@ -2314,7 +2314,6 @@ void menu_select_game::draw_right_panel(void *selectedref, float origx1, float o void menu_select_game::arts_render(void *selectedref, float origx1, float origy1, float origx2, float origy2) { - float line_height = ui().get_line_height(); bool is_favorites = ((item[0].flags & FLAG_UI_FAVORITE) != 0); static ui_software_info *oldsoft = nullptr; static const game_driver *olddriver = nullptr; @@ -2347,7 +2346,7 @@ void menu_select_game::arts_render(void *selectedref, float origx1, float origy1 searchstr = arts_render_common(origx1, origy1, origx2, origy2); // loads the image if necessary - if (driver != olddriver || !snapx_bitmap->valid() || ui_globals::switch_image) + if (driver != olddriver || !snapx_valid() || ui_globals::switch_image) { emu_file snapfile(searchstr.c_str(), OPEN_FLAG_READ); snapfile.set_restrict_to_mediapath(true); @@ -2406,16 +2405,7 @@ void menu_select_game::arts_render(void *selectedref, float origx1, float origy1 } // if the image is available, loaded and valid, display it - if (snapx_bitmap->valid()) - { - float x1 = origx1 + 0.01f; - float x2 = origx2 - 0.01f; - float y1 = origy1 + UI_BOX_TB_BORDER + line_height; - float y2 = origy2 - UI_BOX_TB_BORDER - line_height; - - // apply texture - container->add_quad( x1, y1, x2, y2, rgb_t::white, snapx_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA)); - } + draw_snapx(origx1, origy1, origx2, origy2); } else if (soft != nullptr) { @@ -2429,7 +2419,7 @@ void menu_select_game::arts_render(void *selectedref, float origx1, float origy1 searchstr = arts_render_common(origx1, origy1, origx2, origy2); // loads the image if necessary - if (soft != oldsoft || !snapx_bitmap->valid() || ui_globals::switch_image) + if (soft != oldsoft || !snapx_valid() || ui_globals::switch_image) { emu_file snapfile(searchstr.c_str(), OPEN_FLAG_READ); bitmap_argb32 *tmp_bitmap; @@ -2495,16 +2485,7 @@ void menu_select_game::arts_render(void *selectedref, float origx1, float origy1 } // if the image is available, loaded and valid, display it - if (snapx_bitmap->valid()) - { - float x1 = origx1 + 0.01f; - float x2 = origx2 - 0.01f; - float y1 = origy1 + UI_BOX_TB_BORDER + line_height; - float y2 = origy2 - UI_BOX_TB_BORDER - line_height; - - // apply texture - container->add_quad(x1, y1, x2, y2, rgb_t::white, snapx_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA)); - } + draw_snapx(origx1, origy1, origx2, origy2); } } diff --git a/src/frontend/mame/ui/selmenu.cpp b/src/frontend/mame/ui/selmenu.cpp index 3f7b70d5def..f9db29a1a87 100644 --- a/src/frontend/mame/ui/selmenu.cpp +++ b/src/frontend/mame/ui/selmenu.cpp @@ -71,7 +71,9 @@ menu_select_launch::cache_ptr_map menu_select_launch::s_caches; menu_select_launch::cache::cache(running_machine &machine) - : m_no_avail_bitmap(std::make_unique(256, 256)) + : m_snapx_bitmap(std::make_unique(0, 0)) + , m_snapx_texture() + , m_no_avail_bitmap(std::make_unique(256, 256)) , m_star_bitmap(std::make_unique(32, 32)) , m_star_texture() , m_toolbar_bitmap() @@ -82,9 +84,12 @@ menu_select_launch::cache::cache(running_machine &machine) render_manager &render(machine.render()); auto const texture_free([&render](render_texture *texture) { render.texture_free(texture); }); - std::memcpy(&m_no_avail_bitmap->pix32(0), no_avail_bmp, 256 * 256 * sizeof(UINT32)); - std::memcpy(&m_star_bitmap->pix32(0), favorite_star_bmp, 32 * 32 * sizeof(UINT32)); + // create a texture for snapshot + m_snapx_texture = texture_ptr(render.texture_alloc(render_texture::hq_scale), texture_free); + std::memcpy(&m_no_avail_bitmap->pix32(0), no_avail_bmp, 256 * 256 * sizeof(UINT32)); + + std::memcpy(&m_star_bitmap->pix32(0), favorite_star_bmp, 32 * 32 * sizeof(UINT32)); m_star_texture = texture_ptr(render.texture_alloc(), texture_free); m_star_texture->set_bitmap(*m_star_bitmap, m_star_bitmap->cliprect(), TEXFORMAT_ARGB32); @@ -236,7 +241,7 @@ float menu_select_launch::draw_right_box_title(float x1, float y1, float x2, flo fgcolor = rgb_t(0xff, 0xff, 0x00); bgcolor = rgb_t(0xff, 0xff, 0xff); ui().draw_textured_box(container, x1 + UI_LINE_WIDTH, y1 + UI_LINE_WIDTH, x1 + midl - UI_LINE_WIDTH, y1 + line_height, - bgcolor, rgb_t(43, 43, 43), hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + bgcolor, rgb_t(43, 43, 43), hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); } else if (bgcolor == UI_MOUSEOVER_BG_COLOR) container->add_rect(x1 + UI_LINE_WIDTH, y1 + UI_LINE_WIDTH, x1 + midl - UI_LINE_WIDTH, y1 + line_height, @@ -285,7 +290,7 @@ std::string menu_select_launch::arts_render_common(float origx1, float origy1, f if (bgcolor != UI_TEXT_BG_COLOR) ui().draw_textured_box(container, origx1 + ((middle - title_size) * 0.5f), origy1, origx1 + ((middle + title_size) * 0.5f), - origy1 + line_height, bgcolor, rgb_t(43, 43, 43), hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + origy1 + line_height, bgcolor, rgb_t(43, 43, 43), hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); ui().draw_text_full(container, snaptext.c_str(), origx1, origy1, origx2 - origx1, ui::text_layout::CENTER, ui::text_layout::TRUNCATE, mame_ui_manager::NORMAL, fgcolor, bgcolor, nullptr, nullptr, tmp_size); @@ -318,6 +323,7 @@ void menu_select_launch::arts_render_images(bitmap_argb32 *tmp_bitmap, float ori no_available = true; } + bitmap_argb32 &snapx_bitmap(m_cache->snapx_bitmap()); if (tmp_bitmap->valid()) { float panel_width = origx2 - origx1 - 0.02f; @@ -370,21 +376,98 @@ void menu_select_launch::arts_render_images(bitmap_argb32 *tmp_bitmap, float ori else dest_bitmap = tmp_bitmap; - snapx_bitmap->allocate(panel_width_pixel, panel_height_pixel); + snapx_bitmap.allocate(panel_width_pixel, panel_height_pixel); int x1 = (0.5f * panel_width_pixel) - (0.5f * dest_xPixel); int y1 = (0.5f * panel_height_pixel) - (0.5f * dest_yPixel); for (int x = 0; x < dest_xPixel; x++) for (int y = 0; y < dest_yPixel; y++) - snapx_bitmap->pix32(y + y1, x + x1) = dest_bitmap->pix32(y, x); + snapx_bitmap.pix32(y + y1, x + x1) = dest_bitmap->pix32(y, x); auto_free(machine(), dest_bitmap); // apply bitmap - snapx_texture->set_bitmap(*snapx_bitmap, snapx_bitmap->cliprect(), TEXFORMAT_ARGB32); + m_cache->snapx_texture()->set_bitmap(snapx_bitmap, snapx_bitmap.cliprect(), TEXFORMAT_ARGB32); } else - snapx_bitmap->reset(); + { + snapx_bitmap.reset(); + } +} + + +//------------------------------------------------- +// draw common arrows +//------------------------------------------------- + +void menu_select_launch::draw_common_arrow(float origx1, float origy1, float origx2, float origy2, int current, int dmin, int dmax, float title_size) +{ + auto line_height = ui().get_line_height(); + auto lr_arrow_width = 0.4f * line_height * machine().render().ui_aspect(); + auto gutter_width = lr_arrow_width * 1.3f; + + // set left-right arrows dimension + float ar_x0 = 0.5f * (origx2 + origx1) + 0.5f * title_size + gutter_width - lr_arrow_width; + float ar_y0 = origy1 + 0.1f * line_height; + float ar_x1 = 0.5f * (origx2 + origx1) + 0.5f * title_size + gutter_width; + float ar_y1 = origy1 + 0.9f * line_height; + + float al_x0 = 0.5f * (origx2 + origx1) - 0.5f * title_size - gutter_width; + float al_y0 = origy1 + 0.1f * line_height; + float al_x1 = 0.5f * (origx2 + origx1) - 0.5f * title_size - gutter_width + lr_arrow_width; + float al_y1 = origy1 + 0.9f * line_height; + + rgb_t fgcolor_right, fgcolor_left; + fgcolor_right = fgcolor_left = UI_TEXT_COLOR; + + // set hover + if (mouse_hit && ar_x0 <= mouse_x && ar_x1 > mouse_x && ar_y0 <= mouse_y && ar_y1 > mouse_y && current != dmax) + { + ui().draw_textured_box(container, ar_x0 + 0.01f, ar_y0, ar_x1 - 0.01f, ar_y1, UI_MOUSEOVER_BG_COLOR, rgb_t(43, 43, 43), + hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + hover = HOVER_UI_RIGHT; + fgcolor_right = UI_MOUSEOVER_COLOR; + } + else if (mouse_hit && al_x0 <= mouse_x && al_x1 > mouse_x && al_y0 <= mouse_y && al_y1 > mouse_y && current != dmin) + { + ui().draw_textured_box(container, al_x0 + 0.01f, al_y0, al_x1 - 0.01f, al_y1, UI_MOUSEOVER_BG_COLOR, rgb_t(43, 43, 43), + hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + hover = HOVER_UI_LEFT; + fgcolor_left = UI_MOUSEOVER_COLOR; + } + + // apply arrow + if (current == dmin) + draw_arrow(container, ar_x0, ar_y0, ar_x1, ar_y1, fgcolor_right, ROT90); + else if (current == dmax) + draw_arrow(container, al_x0, al_y0, al_x1, al_y1, fgcolor_left, ROT90 ^ ORIENTATION_FLIP_X); + else + { + draw_arrow(container, ar_x0, ar_y0, ar_x1, ar_y1, fgcolor_right, ROT90); + draw_arrow(container, al_x0, al_y0, al_x1, al_y1, fgcolor_left, ROT90 ^ ORIENTATION_FLIP_X); + } +} + + +//------------------------------------------------- +// draw info arrow +//------------------------------------------------- + +void menu_select_launch::draw_info_arrow(int ub, float origx1, float origx2, float oy1, float line_height, float text_size, float ud_arrow_width) +{ + rgb_t fgcolor = UI_TEXT_COLOR; + UINT32 orientation = (!ub) ? ROT0 : ROT0 ^ ORIENTATION_FLIP_Y; + + if (mouse_hit && origx1 <= mouse_x && origx2 > mouse_x && oy1 <= mouse_y && oy1 + (line_height * text_size) > mouse_y) + { + ui().draw_textured_box(container, origx1 + 0.01f, oy1, origx2 - 0.01f, oy1 + (line_height * text_size), UI_MOUSEOVER_BG_COLOR, + rgb_t(43, 43, 43), hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + hover = (!ub) ? HOVER_DAT_UP : HOVER_DAT_DOWN; + fgcolor = UI_MOUSEOVER_COLOR; + } + + draw_arrow(container, 0.5f * (origx1 + origx2) - 0.5f * (ud_arrow_width * text_size), oy1 + 0.25f * (line_height * text_size), + 0.5f * (origx1 + origx2) + 0.5f * (ud_arrow_width * text_size), oy1 + 0.75f * (line_height * text_size), fgcolor, orientation); } @@ -446,6 +529,27 @@ void menu_select_launch::draw_star(float x0, float y0) } +//------------------------------------------------- +// draw snapshot +//------------------------------------------------- + +void menu_select_launch::draw_snapx(float origx1, float origy1, float origx2, float origy2) +{ + // if the image is available, loaded and valid, display it + if (snapx_valid()) + { + float const line_height = ui().get_line_height(); + float const x1 = origx1 + 0.01f; + float const x2 = origx2 - 0.01f; + float const y1 = origy1 + UI_BOX_TB_BORDER + line_height; + float const y2 = origy2 - UI_BOX_TB_BORDER - line_height; + + // apply texture + container->add_quad(x1, y1, x2, y2, rgb_t::white, m_cache->snapx_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA)); + } +} + + void menu_select_launch::set_pressed() { (m_repeat == 0) ? m_repeat = osd_ticks() + osd_ticks_per_second() / 2 : m_repeat = osd_ticks() + osd_ticks_per_second() / 4; @@ -1140,7 +1244,7 @@ void menu_select_launch::draw(UINT32 flags) bgcolor = rgb_t(0xff, 0xff, 0xff); fgcolor3 = rgb_t(0xcc, 0xcc, 0x00); ui().draw_textured_box(container, line_x0 + 0.01f, line_y0, line_x1 - 0.01f, line_y1, bgcolor, rgb_t(43, 43, 43), - hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); } // else if the mouse is over this item, draw with a different background else if (itemnum == hover) @@ -1154,7 +1258,7 @@ void menu_select_launch::draw(UINT32 flags) fgcolor = fgcolor3 = UI_MOUSEOVER_COLOR; bgcolor = UI_MOUSEOVER_BG_COLOR; ui().draw_textured_box(container, line_x0 + 0.01f, line_y0, line_x1 - 0.01f, line_y1, bgcolor, rgb_t(43, 43, 43), - hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); } if (linenum == 0 && top_line != 0) @@ -1230,7 +1334,7 @@ void menu_select_launch::draw(UINT32 flags) fgcolor = rgb_t(0xff, 0xff, 0x00); bgcolor = rgb_t(0xff, 0xff, 0xff); ui().draw_textured_box(container, line_x0 + 0.01f, line_y0, line_x1 - 0.01f, line_y1, bgcolor, rgb_t(43, 43, 43), - hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); } // else if the mouse is over this item, draw with a different background else if (count == hover) diff --git a/src/frontend/mame/ui/selmenu.h b/src/frontend/mame/ui/selmenu.h index 26f1706c2c4..3a9e313c0c3 100644 --- a/src/frontend/mame/ui/selmenu.h +++ b/src/frontend/mame/ui/selmenu.h @@ -51,12 +51,20 @@ protected: std::string arts_render_common(float origx1, float origy1, float origx2, float origy2); void arts_render_images(bitmap_argb32 *bitmap, float origx1, float origy1, float origx2, float origy2); + // draw arrow + void draw_common_arrow(float origx1, float origy1, float origx2, float origy2, int current, int dmin, int dmax, float title); + void draw_info_arrow(int ub, float origx1, float origx2, float oy1, float line_height, float text_size, float ud_arrow_width); + // draw toolbar void draw_toolbar(float x1, float y1, float x2, float y2, bool software = false); // draw star void draw_star(float x0, float y0); + // draw snapshot if valid + void draw_snapx(float origx1, float origy1, float origx2, float origy2); + bool snapx_valid() const { return m_cache->snapx_bitmap().valid(); } + int visible_items; int m_total_lines; int m_topline_datsview; // right box top line @@ -72,6 +80,8 @@ private: cache(running_machine &machine); ~cache(); + bitmap_argb32 &snapx_bitmap() { return *m_snapx_bitmap; } + render_texture *snapx_texture() { return m_snapx_texture.get(); } bitmap_argb32 &no_avail_bitmap() { return *m_no_avail_bitmap; } render_texture *star_texture() { return m_star_texture.get(); } @@ -81,14 +91,16 @@ private: texture_ptr_vector const &sw_toolbar_texture() { return m_sw_toolbar_texture; } private: - bitmap_ptr m_no_avail_bitmap; - bitmap_ptr m_star_bitmap; - texture_ptr m_star_texture; + bitmap_ptr m_snapx_bitmap; + texture_ptr m_snapx_texture; + bitmap_ptr m_no_avail_bitmap; + bitmap_ptr m_star_bitmap; + texture_ptr m_star_texture; - bitmap_ptr_vector m_toolbar_bitmap; - bitmap_ptr_vector m_sw_toolbar_bitmap; - texture_ptr_vector m_toolbar_texture; - texture_ptr_vector m_sw_toolbar_texture; + bitmap_ptr_vector m_toolbar_bitmap; + bitmap_ptr_vector m_sw_toolbar_bitmap; + texture_ptr_vector m_toolbar_texture; + texture_ptr_vector m_sw_toolbar_texture; }; using cache_ptr = std::shared_ptr; using cache_ptr_map = std::map; diff --git a/src/frontend/mame/ui/selsoft.cpp b/src/frontend/mame/ui/selsoft.cpp index bf6763171b2..a28aa465dea 100644 --- a/src/frontend/mame/ui/selsoft.cpp +++ b/src/frontend/mame/ui/selsoft.cpp @@ -1456,7 +1456,7 @@ float menu_select_software::draw_left_panel(float x1, float y1, float x2, float if (bgcolor != UI_TEXT_BG_COLOR) ui().draw_textured_box(container, x1, y1, x2, y1 + line_height, bgcolor, rgb_t(255, 43, 43, 43), - hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); float x1t = x1 + text_sign; if (afilter == UI_SW_CUSTOM) @@ -1583,7 +1583,7 @@ void menu_select_software::infos_render(void *selectedref, float origx1, float o if (bgcolor != UI_TEXT_BG_COLOR) ui().draw_textured_box(container, origx1 + ((middle - title_size) * 0.5f), origy1, origx1 + ((middle + title_size) * 0.5f), - origy1 + line_height, bgcolor, rgb_t(255, 43, 43, 43), hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + origy1 + line_height, bgcolor, rgb_t(255, 43, 43, 43), hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); ui().draw_text_full(container, _("History"), origx1, origy1, origx2 - origx1, ui::text_layout::CENTER, ui::text_layout::NEVER, mame_ui_manager::NORMAL, fgcolor, bgcolor, nullptr, nullptr); @@ -1622,7 +1622,7 @@ void menu_select_software::infos_render(void *selectedref, float origx1, float o if (bgcolor != UI_TEXT_BG_COLOR) ui().draw_textured_box(container, origx1 + ((middle - title_size) * 0.5f), origy1, origx1 + ((middle + title_size) * 0.5f), - origy1 + line_height, bgcolor, rgb_t(255, 43, 43, 43), hilight_main_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); + origy1 + line_height, bgcolor, rgb_t(255, 43, 43, 43), hilight_main_texture(), PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXWRAP(TRUE)); ui().draw_text_full(container, t_text[ui_globals::cur_sw_dats_view].c_str(), origx1, origy1, origx2 - origx1, ui::text_layout::CENTER, ui::text_layout::NEVER, mame_ui_manager::NORMAL, fgcolor, bgcolor, nullptr, nullptr, tmp_size); @@ -1671,10 +1671,10 @@ void menu_select_software::infos_render(void *selectedref, float origx1, float o // up arrow if (r == 0 && m_topline_datsview != 0) - info_arrow(0, origx1, origx2, oy1, line_height, text_size, ud_arrow_width); + draw_info_arrow(0, origx1, origx2, oy1, line_height, text_size, ud_arrow_width); // bottom arrow else if (r == r_visible_lines - 1 && itemline != m_total_lines - 1) - info_arrow(1, origx1, origx2, oy1, line_height, text_size, ud_arrow_width); + draw_info_arrow(1, origx1, origx2, oy1, line_height, text_size, ud_arrow_width); else ui().draw_text_full(container, tempbuf.c_str(), origx1 + gutter_width, oy1, origx2 - origx1, ui::text_layout::LEFT, ui::text_layout::TRUNCATE, mame_ui_manager::NORMAL, UI_TEXT_COLOR, UI_TEXT_BG_COLOR, @@ -1692,7 +1692,6 @@ void menu_select_software::infos_render(void *selectedref, float origx1, float o void menu_select_software::arts_render(void *selectedref, float origx1, float origy1, float origx2, float origy2) { - float line_height = ui().get_line_height(); static ui_software_info *oldsoft = nullptr; static const game_driver *olddriver = nullptr; const game_driver *driver = nullptr; @@ -1715,7 +1714,7 @@ void menu_select_software::arts_render(void *selectedref, float origx1, float or searchstr = arts_render_common(origx1, origy1, origx2, origy2); // loads the image if necessary - if (driver != olddriver || !snapx_bitmap->valid() || ui_globals::switch_image) + if (driver != olddriver || !snapx_valid() || ui_globals::switch_image) { emu_file snapfile(searchstr.c_str(), OPEN_FLAG_READ); snapfile.set_restrict_to_mediapath(true); @@ -1774,16 +1773,7 @@ void menu_select_software::arts_render(void *selectedref, float origx1, float or } // if the image is available, loaded and valid, display it - if (snapx_bitmap->valid()) - { - float x1 = origx1 + 0.01f; - float x2 = origx2 - 0.01f; - float y1 = origy1 + UI_BOX_TB_BORDER + line_height; - float y2 = origy2 - UI_BOX_TB_BORDER - line_height; - - // apply texture - container->add_quad( x1, y1, x2, y2, rgb_t::white, snapx_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA)); - } + draw_snapx(origx1, origy1, origx2, origy2); } else if (soft != nullptr) { @@ -1797,7 +1787,7 @@ void menu_select_software::arts_render(void *selectedref, float origx1, float or searchstr = arts_render_common(origx1, origy1, origx2, origy2); // loads the image if necessary - if (soft != oldsoft || !snapx_bitmap->valid() || ui_globals::switch_image) + if (soft != oldsoft || !snapx_valid() || ui_globals::switch_image) { emu_file snapfile(searchstr.c_str(), OPEN_FLAG_READ); bitmap_argb32 *tmp_bitmap; @@ -1863,16 +1853,7 @@ void menu_select_software::arts_render(void *selectedref, float origx1, float or } // if the image is available, loaded and valid, display it - if (snapx_bitmap->valid()) - { - float x1 = origx1 + 0.01f; - float x2 = origx2 - 0.01f; - float y1 = origy1 + UI_BOX_TB_BORDER + line_height; - float y2 = origy2 - UI_BOX_TB_BORDER - line_height; - - // apply texture - container->add_quad(x1, y1, x2, y2, rgb_t::white, snapx_texture, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA)); - } + draw_snapx(origx1, origy1, origx2, origy2); } }