From e72c67bf8745ae8da79381629264b9e19078e739 Mon Sep 17 00:00:00 2001 From: jdgleaver Date: Tue, 19 Mar 2019 11:48:22 +0000 Subject: [PATCH 1/4] (RGUI) Add widescreen support --- config.def.h | 1 + configuration.c | 1 + configuration.h | 1 + cores/dynamic_dummy.c | 51 +++- intl/msg_hash_lbl.h | 2 + intl/msg_hash_us.h | 20 ++ menu/cbs/menu_cbs_sublabel.c | 4 + menu/drivers/rgui.c | 494 +++++++++++++++++++++++------------ menu/menu_defines.h | 8 + menu/menu_displaylist.c | 4 + menu/menu_setting.c | 48 ++++ msg_hash.h | 5 + 12 files changed, 466 insertions(+), 173 deletions(-) diff --git a/config.def.h b/config.def.h index 5164432321..451964cb52 100644 --- a/config.def.h +++ b/config.def.h @@ -388,6 +388,7 @@ static unsigned rgui_thumbnail_downscaler = RGUI_THUMB_SCALE_POINT; static bool rgui_lock_aspect = false; static unsigned rgui_internal_upscale_level = RGUI_UPSCALE_NONE; static bool rgui_full_width_layout = true; +static unsigned rgui_aspect = RGUI_ASPECT_RATIO_4_3; #else static bool default_block_config_read = false; diff --git a/configuration.c b/configuration.c index e779600a69..5ff9b1b3f2 100644 --- a/configuration.c +++ b/configuration.c @@ -1694,6 +1694,7 @@ static struct config_uint_setting *populate_settings_uint(settings_t *settings, SETTING_UINT("rgui_menu_color_theme", &settings->uints.menu_rgui_color_theme, true, rgui_color_theme, false); SETTING_UINT("rgui_thumbnail_downscaler", &settings->uints.menu_rgui_thumbnail_downscaler, true, rgui_thumbnail_downscaler, false); SETTING_UINT("rgui_internal_upscale_level", &settings->uints.menu_rgui_internal_upscale_level, true, rgui_internal_upscale_level, false); + SETTING_UINT("rgui_aspect_ratio", &settings->uints.menu_rgui_aspect_ratio, true, rgui_aspect, false); #endif #ifdef HAVE_LIBNX SETTING_UINT("split_joycon_p1", &settings->uints.input_split_joycon[0], true, 0, false); diff --git a/configuration.h b/configuration.h index 6e8cd1ad2c..82e3729aa4 100644 --- a/configuration.h +++ b/configuration.h @@ -443,6 +443,7 @@ typedef struct settings unsigned menu_font_color_green; unsigned menu_font_color_blue; unsigned menu_rgui_internal_upscale_level; + unsigned menu_rgui_aspect_ratio; unsigned menu_ticker_type; unsigned playlist_show_inline_core_name; diff --git a/cores/dynamic_dummy.c b/cores/dynamic_dummy.c index d456c4ed01..6b5db0bff1 100644 --- a/cores/dynamic_dummy.c +++ b/cores/dynamic_dummy.c @@ -21,10 +21,19 @@ #include +#if defined(HAVE_MENU) && defined(HAVE_RGUI) +#include +#include "../configuration.h" +#include "../menu/menu_defines.h" +#endif + #include "internal_cores.h" static uint16_t *dummy_frame_buf; +static uint16_t frame_buf_width; +static uint16_t frame_buf_height; + #if defined(HAVE_LIBNX) && defined(HAVE_STATIC_DUMMY) void retro_init(void) { libretro_dummy_retro_init(); } void retro_deinit(void) { libretro_dummy_retro_deinit(); } @@ -55,10 +64,36 @@ void retro_cheat_set(unsigned idx, bool enabled, const char *code) { libretro_du void libretro_dummy_retro_init(void) { +#if defined(HAVE_MENU) && defined(HAVE_RGUI) + settings_t *settings = config_get_ptr(); +#endif unsigned i; - dummy_frame_buf = (uint16_t*)calloc(320 * 240, sizeof(uint16_t)); - for (i = 0; i < 320 * 240; i++) + /* Sensible defaults */ + frame_buf_width = 320; + frame_buf_height = 240; + +#if defined(HAVE_MENU) && defined(HAVE_RGUI) + if (string_is_equal(settings->arrays.menu_driver, "rgui")) + { + switch (settings->uints.menu_rgui_aspect_ratio) + { + case RGUI_ASPECT_RATIO_16_9: + frame_buf_width = 426; + break; + case RGUI_ASPECT_RATIO_16_10: + frame_buf_width = 384; + break; + default: + /* 4:3 */ + frame_buf_width = 320; + break; + } + } +#endif + + dummy_frame_buf = (uint16_t*)calloc(frame_buf_width * frame_buf_height, sizeof(uint16_t)); + for (i = 0; i < frame_buf_width * frame_buf_height; i++) dummy_frame_buf[i] = 4 << 5; } @@ -109,11 +144,11 @@ void libretro_dummy_retro_get_system_av_info( info->timing.fps = refresh_rate; info->timing.sample_rate = 30000.0; - info->geometry.base_width = 320; - info->geometry.base_height = 240; - info->geometry.max_width = 320; - info->geometry.max_height = 240; - info->geometry.aspect_ratio = 4.0 / 3.0; + info->geometry.base_width = frame_buf_width; + info->geometry.base_height = frame_buf_height; + info->geometry.max_width = frame_buf_width; + info->geometry.max_height = frame_buf_height; + info->geometry.aspect_ratio = (float)frame_buf_width / (float)frame_buf_height; } void libretro_dummy_retro_set_environment(retro_environment_t cb) @@ -158,7 +193,7 @@ void libretro_dummy_retro_reset(void) void libretro_dummy_retro_run(void) { dummy_input_poll_cb(); - dummy_video_cb(dummy_frame_buf, 320, 240, 640); + dummy_video_cb(dummy_frame_buf, frame_buf_width, frame_buf_height, 2 * frame_buf_width); } /* This should never be called, it's only used as a placeholder. */ diff --git a/intl/msg_hash_lbl.h b/intl/msg_hash_lbl.h index 4ff5531de8..aa62858979 100644 --- a/intl/msg_hash_lbl.h +++ b/intl/msg_hash_lbl.h @@ -1609,6 +1609,8 @@ MSG_HASH(MENU_ENUM_LABEL_MENU_RGUI_LOCK_ASPECT, "menu_rgui_lock_aspect") MSG_HASH(MENU_ENUM_LABEL_MENU_RGUI_INTERNAL_UPSCALE_LEVEL, "rgui_internal_upscale_level") +MSG_HASH(MENU_ENUM_LABEL_MENU_RGUI_ASPECT_RATIO, + "rgui_aspect_ratio") MSG_HASH(MENU_ENUM_LABEL_MENU_RGUI_FULL_WIDTH_LAYOUT, "menu_rgui_full_width_layout") MSG_HASH(MENU_ENUM_LABEL_CONTENT_SHOW_REWIND, diff --git a/intl/msg_hash_us.h b/intl/msg_hash_us.h index ec89eef333..461965bb9e 100644 --- a/intl/msg_hash_us.h +++ b/intl/msg_hash_us.h @@ -3022,6 +3022,18 @@ MSG_HASH( MENU_ENUM_LABEL_VALUE_RGUI_UPSCALE_X9, "x9" ) +MSG_HASH( + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_4_3, + "4:3" + ) +MSG_HASH( + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_9, + "16:9" + ) +MSG_HASH( + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_10, + "16:10" + ) MSG_HASH( MENU_ENUM_LABEL_VALUE_THUMBNAILS_DIRECTORY, "Thumbnails" @@ -6808,6 +6820,14 @@ MSG_HASH( MENU_ENUM_SUBLABEL_MENU_RGUI_INTERNAL_UPSCALE_LEVEL, "Upscale menu interface before drawing to screen. When used with 'Menu Linear Filter' enabled, removes scaling artefacts (uneven pixels) while maintaining a sharp image. Has a significant performance impact that increases with upscaling level." ) +MSG_HASH( + MENU_ENUM_LABEL_VALUE_MENU_RGUI_ASPECT_RATIO, + "Menu Aspect Ratio" + ) +MSG_HASH( + MENU_ENUM_SUBLABEL_MENU_RGUI_ASPECT_RATIO, + "Select menu aspect ratio. Widescreen ratios increase the horizontal resolution of the menu interface. (May require a restart if 'Lock Menu Aspect Ratio' is disabled)" + ) MSG_HASH( MENU_ENUM_LABEL_VALUE_MENU_RGUI_FULL_WIDTH_LAYOUT, "Use Full-Width Layout" diff --git a/menu/cbs/menu_cbs_sublabel.c b/menu/cbs/menu_cbs_sublabel.c index 108446b63c..48d73cc31c 100644 --- a/menu/cbs/menu_cbs_sublabel.c +++ b/menu/cbs/menu_cbs_sublabel.c @@ -528,6 +528,7 @@ default_sublabel_macro(action_bind_sublabel_content_runtime_log, default_sublabel_macro(action_bind_sublabel_content_runtime_log_aggregate, MENU_ENUM_SUBLABEL_CONTENT_RUNTIME_LOG_AGGREGATE) default_sublabel_macro(action_bind_sublabel_playlist_sublabel_runtime_type, MENU_ENUM_SUBLABEL_PLAYLIST_SUBLABEL_RUNTIME_TYPE) default_sublabel_macro(action_bind_sublabel_menu_rgui_internal_upscale_level, MENU_ENUM_SUBLABEL_MENU_RGUI_INTERNAL_UPSCALE_LEVEL) +default_sublabel_macro(action_bind_sublabel_menu_rgui_aspect_ratio, MENU_ENUM_SUBLABEL_MENU_RGUI_ASPECT_RATIO) default_sublabel_macro(action_bind_sublabel_menu_ticker_type, MENU_ENUM_SUBLABEL_MENU_TICKER_TYPE) default_sublabel_macro(action_bind_sublabel_menu_ticker_speed, MENU_ENUM_SUBLABEL_MENU_TICKER_SPEED) default_sublabel_macro(action_bind_sublabel_playlist_show_inline_core_name, MENU_ENUM_SUBLABEL_PLAYLIST_SHOW_INLINE_CORE_NAME) @@ -2410,6 +2411,9 @@ int menu_cbs_init_bind_sublabel(menu_file_list_cbs_t *cbs, case MENU_ENUM_LABEL_MENU_RGUI_INTERNAL_UPSCALE_LEVEL: BIND_ACTION_SUBLABEL(cbs, action_bind_sublabel_menu_rgui_internal_upscale_level); break; + case MENU_ENUM_LABEL_MENU_RGUI_ASPECT_RATIO: + BIND_ACTION_SUBLABEL(cbs, action_bind_sublabel_menu_rgui_aspect_ratio); + break; case MENU_ENUM_LABEL_MENU_TICKER_TYPE: BIND_ACTION_SUBLABEL(cbs, action_bind_sublabel_menu_ticker_type); break; diff --git a/menu/drivers/rgui.c b/menu/drivers/rgui.c index 032e3aab5f..7ab929ed11 100644 --- a/menu/drivers/rgui.c +++ b/menu/drivers/rgui.c @@ -58,15 +58,33 @@ #include "../../tasks/tasks_internal.h" #include -#define RGUI_TERM_START_X(width) (width / 21) -#define RGUI_TERM_START_Y(height) (height / 9) -#define RGUI_TERM_WIDTH(width) (((width - RGUI_TERM_START_X(width) - RGUI_TERM_START_X(width)) / (FONT_WIDTH_STRIDE))) -#define RGUI_TERM_HEIGHT(width, height) (((height - RGUI_TERM_START_Y(height) - RGUI_TERM_START_X(width)) / (FONT_HEIGHT_STRIDE)) - 1) +#if defined(GEKKO) +#define RGUI_TERM_START_X(fb_width) (width / 21) +#define RGUI_TERM_START_Y(fb_height) (height / 9) +#define RGUI_TERM_WIDTH(fb_width) (((width - RGUI_TERM_START_X(width) - RGUI_TERM_START_X(width)) / (FONT_WIDTH_STRIDE))) +#define RGUI_TERM_HEIGHT(fb_height) (((height - RGUI_TERM_START_Y(height) - RGUI_TERM_START_Y(height)) / (FONT_HEIGHT_STRIDE))) +#else +#define RGUI_TERM_START_X(fb_width) rgui_term_layout.start_x +#define RGUI_TERM_START_Y(fb_height) rgui_term_layout.start_y +#define RGUI_TERM_WIDTH(fb_width) rgui_term_layout.width +#define RGUI_TERM_HEIGHT(fb_height) rgui_term_layout.height +#endif #define RGUI_ENTRY_VALUE_MAXLEN 19 #define RGUI_TICKER_SPACER " | " +typedef struct +{ + unsigned start_x; + unsigned start_y; + unsigned width; + unsigned height; + unsigned value_maxlen; +} rgui_term_layout_t; + +static rgui_term_layout_t rgui_term_layout = {0}; + typedef struct { uint32_t hover_color; @@ -431,20 +449,19 @@ typedef struct char theme_preset_path[PATH_MAX_LENGTH]; /* Must be a fixed length array... */ char menu_title[255]; /* Must be a fixed length array... */ char menu_sublabel[255]; /* Must be a fixed length array... */ - unsigned content_aspect_ratio; + unsigned menu_aspect_ratio; + unsigned menu_aspect_ratio_idx; + unsigned content_aspect_ratio_idx; struct scaler_ctx image_scaler; } rgui_t; -#define THUMB_MAX_WIDTH 320 -#define THUMB_MAX_HEIGHT 240 - typedef struct { unsigned width; unsigned height; bool is_valid; char *path; - uint16_t data[THUMB_MAX_WIDTH * THUMB_MAX_HEIGHT]; + uint16_t *data; } thumbnail_t; static thumbnail_t thumbnail = { @@ -452,25 +469,20 @@ static thumbnail_t thumbnail = { 0, false, NULL, - {0} + NULL }; -/* Identical to thumbnail max width/height, but cannot - * assume this will always be the case... */ -#define WALLPAPER_WIDTH 320 -#define WALLPAPER_HEIGHT 240 - typedef struct { bool is_valid; char *path; - uint16_t data[WALLPAPER_WIDTH * WALLPAPER_HEIGHT]; + uint16_t *data; } wallpaper_t; static wallpaper_t wallpaper = { false, NULL, - {0} + NULL }; typedef struct @@ -478,15 +490,19 @@ typedef struct unsigned width; unsigned height; uint16_t *data; -} upscale_buf_t; +} frame_buf_t; -static upscale_buf_t upscale_buf = { +static frame_buf_t rgui_frame_buf = { 0, 0, NULL }; -static uint16_t *rgui_framebuf_data = NULL; +static frame_buf_t rgui_upscale_buf = { + 0, + 0, + NULL +}; #if defined(PS2) @@ -635,16 +651,16 @@ static void process_wallpaper(rgui_t *rgui, struct texture_image *image) unsigned x, y; /* Sanity check */ - if (!image->pixels || (image->width != WALLPAPER_WIDTH) || (image->height != WALLPAPER_HEIGHT)) + if (!image->pixels || (image->width != rgui_frame_buf.width) || (image->height != rgui_frame_buf.height) || !wallpaper.data) return; /* Copy image to wallpaper buffer, performing pixel format conversion */ - for (x = 0; x < WALLPAPER_WIDTH; x++) + for (x = 0; x < rgui_frame_buf.width; x++) { - for (y = 0; y < WALLPAPER_HEIGHT; y++) + for (y = 0; y < rgui_frame_buf.height; y++) { - wallpaper.data[x + (y * WALLPAPER_WIDTH)] = - argb32_to_pixel_platform_format(image->pixels[x + (y * WALLPAPER_WIDTH)]); + wallpaper.data[x + (y * rgui_frame_buf.width)] = + argb32_to_pixel_platform_format(image->pixels[x + (y * rgui_frame_buf.width)]); } } @@ -694,23 +710,23 @@ static bool downscale_thumbnail(rgui_t *rgui, struct texture_image *image_src, s settings_t *settings = config_get_ptr(); /* Determine output dimensions */ - static const float display_aspect_ratio = (float)THUMB_MAX_WIDTH / (float)THUMB_MAX_HEIGHT; + float display_aspect_ratio = (float)rgui_frame_buf.width / (float)rgui_frame_buf.height; float aspect_ratio = (float)image_src->width / (float)image_src->height; if (aspect_ratio > display_aspect_ratio) { - image_dst->width = THUMB_MAX_WIDTH; - image_dst->height = image_src->height * THUMB_MAX_WIDTH / image_src->width; + image_dst->width = rgui_frame_buf.width; + image_dst->height = image_src->height * rgui_frame_buf.width / image_src->width; /* Account for any possible rounding errors... */ image_dst->height = (image_dst->height < 1) ? 1 : image_dst->height; - image_dst->height = (image_dst->height > THUMB_MAX_HEIGHT) ? THUMB_MAX_HEIGHT : image_dst->height; + image_dst->height = (image_dst->height > rgui_frame_buf.height) ? rgui_frame_buf.height : image_dst->height; } else { - image_dst->height = THUMB_MAX_HEIGHT; - image_dst->width = image_src->width * THUMB_MAX_HEIGHT / image_src->height; + image_dst->height = rgui_frame_buf.height; + image_dst->width = image_src->width * rgui_frame_buf.height / image_src->height; /* Account for any possible rounding errors... */ image_dst->width = (image_dst->width < 1) ? 1 : image_dst->width; - image_dst->width = (image_dst->width > THUMB_MAX_WIDTH) ? THUMB_MAX_WIDTH : image_dst->width; + image_dst->width = (image_dst->width > rgui_frame_buf.width) ? rgui_frame_buf.width : image_dst->width; } /* Allocate pixel buffer */ @@ -806,11 +822,11 @@ static void process_thumbnail(rgui_t *rgui, struct texture_image *image_src) return; /* Sanity check */ - if (!image_src->pixels || (image_src->width < 1) || (image_src->height < 1)) + if (!image_src->pixels || (image_src->width < 1) || (image_src->height < 1) || !thumbnail.data) return; /* Downscale thumbnail if it exceeds maximum size limits */ - if ((image_src->width > THUMB_MAX_WIDTH) || (image_src->height > THUMB_MAX_HEIGHT)) + if ((image_src->width > rgui_frame_buf.width) || (image_src->height > rgui_frame_buf.height)) { if (!downscale_thumbnail(rgui, image_src, &image_resampled)) return; @@ -879,16 +895,16 @@ static bool rgui_render_wallpaper(void) size_t fb_pitch; unsigned fb_width, fb_height; - if (wallpaper.is_valid && rgui_framebuf_data) + if (wallpaper.is_valid && rgui_frame_buf.data && wallpaper.data) { menu_display_get_fb_size(&fb_width, &fb_height, &fb_pitch); /* Sanity check */ - if ((fb_width != WALLPAPER_WIDTH) || (fb_height != WALLPAPER_HEIGHT) || (fb_pitch != WALLPAPER_WIDTH << 1)) + if ((fb_width != rgui_frame_buf.width) || (fb_height != rgui_frame_buf.height) || (fb_pitch != rgui_frame_buf.width << 1)) return false; /* Copy wallpaper to framebuffer */ - memcpy(rgui_framebuf_data, wallpaper.data, WALLPAPER_WIDTH * WALLPAPER_HEIGHT * sizeof(uint16_t)); + memcpy(rgui_frame_buf.data, wallpaper.data, rgui_frame_buf.width * rgui_frame_buf.height * sizeof(uint16_t)); return true; } @@ -905,7 +921,7 @@ static void rgui_render_thumbnail(void) unsigned thumb_x_offset, thumb_y_offset; unsigned width, height; - if (thumbnail.is_valid && rgui_framebuf_data) + if (thumbnail.is_valid && rgui_frame_buf.data && thumbnail.data) { menu_display_get_fb_size(&fb_width, &fb_height, &fb_pitch); @@ -944,7 +960,7 @@ static void rgui_render_thumbnail(void) { for (x = 0; x < width; x++) { - rgui_framebuf_data[(y + fb_y_offset) * (fb_pitch >> 1) + (x + fb_x_offset)] = + rgui_frame_buf.data[(y + fb_y_offset) * (fb_pitch >> 1) + (x + fb_x_offset)] = thumbnail.data[(x + thumb_x_offset) + ((y + thumb_y_offset) * thumbnail.width)]; } } @@ -1028,13 +1044,30 @@ static const rgui_theme_t *get_theme(rgui_t *rgui) static void load_custom_theme(rgui_t *rgui, rgui_theme_t *theme_colors, const char *theme_path) { + settings_t *settings = config_get_ptr(); config_file_t *conf = NULL; + char *wallpaper_key = NULL; unsigned normal_color, hover_color, title_color, bg_dark_color, bg_light_color, border_dark_color, border_light_color; char wallpaper_file[PATH_MAX_LENGTH]; bool success = false; + /* Determine which type of wallpaper to load */ + switch (settings->uints.menu_rgui_aspect_ratio) + { + case RGUI_ASPECT_RATIO_16_9: + wallpaper_key = "rgui_wallpaper_16_9"; + break; + case RGUI_ASPECT_RATIO_16_10: + wallpaper_key = "rgui_wallpaper_16_10"; + break; + default: + /* 4:3 */ + wallpaper_key = "rgui_wallpaper"; + break; + } + wallpaper_file[0] = '\0'; /* Sanity check */ @@ -1070,7 +1103,7 @@ static void load_custom_theme(rgui_t *rgui, rgui_theme_t *theme_colors, const ch if(!config_get_hex(conf, "rgui_border_light_color", &border_light_color)) goto end; - config_get_array(conf, "rgui_wallpaper", wallpaper_file, sizeof(wallpaper_file)); + config_get_array(conf, wallpaper_key, wallpaper_file, sizeof(wallpaper_file)); success = true; @@ -1214,7 +1247,7 @@ static void blit_line(int x, int y, bool col = (font_fb[FONT_OFFSET(symbol) + offset] & rem); if (col) - rgui_framebuf_data[(y + j) * (pitch >> 1) + (x + i)] = color; + rgui_frame_buf.data[(y + j) * (pitch >> 1) + (x + i)] = color; } } @@ -1307,8 +1340,8 @@ static void rgui_render_background(rgui_t *rgui) pitch_in_pixels = fb_pitch >> 1; size = fb_pitch * 4; - src = rgui_framebuf_data + pitch_in_pixels * fb_height; - dst = rgui_framebuf_data; + src = rgui_frame_buf.data + pitch_in_pixels * fb_height; + dst = rgui_frame_buf.data; while (dst < src) { @@ -1319,16 +1352,16 @@ static void rgui_render_background(rgui_t *rgui) /* Skip drawing border if we are currently showing a thumbnail */ if (!(rgui->show_thumbnail && rgui->entry_has_thumbnail && (thumbnail.is_valid || (rgui->thumbnail_queue_size > 0)))) { - if (rgui_framebuf_data) + if (rgui_frame_buf.data) { settings_t *settings = config_get_ptr(); if (settings->bools.menu_rgui_border_filler_enable) { - rgui_fill_rect(rgui, rgui_framebuf_data, fb_pitch, 5, 5, fb_width - 10, 5, rgui_border_filler); - rgui_fill_rect(rgui, rgui_framebuf_data, fb_pitch, 5, fb_height - 10, fb_width - 10, 5, rgui_border_filler); - rgui_fill_rect(rgui, rgui_framebuf_data, fb_pitch, 5, 5, 5, fb_height - 10, rgui_border_filler); - rgui_fill_rect(rgui, rgui_framebuf_data, fb_pitch, fb_width - 10, 5, 5, fb_height - 10, rgui_border_filler); + rgui_fill_rect(rgui, rgui_frame_buf.data, fb_pitch, 5, 5, fb_width - 10, 5, rgui_border_filler); + rgui_fill_rect(rgui, rgui_frame_buf.data, fb_pitch, 5, fb_height - 10, fb_width - 10, 5, rgui_border_filler); + rgui_fill_rect(rgui, rgui_frame_buf.data, fb_pitch, 5, 5, 5, fb_height - 10, rgui_border_filler); + rgui_fill_rect(rgui, rgui_frame_buf.data, fb_pitch, fb_width - 10, 5, 5, fb_height - 10, rgui_border_filler); } } } @@ -1397,16 +1430,16 @@ static void rgui_render_messagebox(rgui_t *rgui, const char *message) x = (fb_width - width) / 2; y = (fb_height - height) / 2; - if (rgui_framebuf_data) + if (rgui_frame_buf.data) { - rgui_fill_rect(rgui, rgui_framebuf_data, fb_pitch, x + 5, y + 5, width - 10, height - 10, rgui_bg_filler); + rgui_fill_rect(rgui, rgui_frame_buf.data, fb_pitch, x + 5, y + 5, width - 10, height - 10, rgui_bg_filler); if (settings->bools.menu_rgui_border_filler_enable) { - rgui_fill_rect(rgui, rgui_framebuf_data, fb_pitch, x, y, width - 5, 5, rgui_border_filler); - rgui_fill_rect(rgui, rgui_framebuf_data, fb_pitch, x + width - 5, y, 5, height - 5, rgui_border_filler); - rgui_fill_rect(rgui, rgui_framebuf_data, fb_pitch, x + 5, y + height - 5, width - 5, 5, rgui_border_filler); - rgui_fill_rect(rgui, rgui_framebuf_data, fb_pitch, x, y + 5, 5, height - 5, rgui_border_filler); + rgui_fill_rect(rgui, rgui_frame_buf.data, fb_pitch, x, y, width - 5, 5, rgui_border_filler); + rgui_fill_rect(rgui, rgui_frame_buf.data, fb_pitch, x + width - 5, y, 5, height - 5, rgui_border_filler); + rgui_fill_rect(rgui, rgui_frame_buf.data, fb_pitch, x + 5, y + height - 5, width - 5, 5, rgui_border_filler); + rgui_fill_rect(rgui, rgui_frame_buf.data, fb_pitch, x, y + 5, 5, height - 5, rgui_border_filler); } } @@ -1416,7 +1449,7 @@ static void rgui_render_messagebox(rgui_t *rgui, const char *message) int offset_x = (int)(FONT_WIDTH_STRIDE * (glyphs_width - utf8len(msg)) / 2); int offset_y = (int)(FONT_HEIGHT_STRIDE * i); - if (rgui_framebuf_data) + if (rgui_frame_buf.data) blit_line(x + 8 + offset_x, y + 8 + offset_y, msg, rgui->colors.normal_color); } @@ -1434,36 +1467,10 @@ static void rgui_blit_cursor(void) menu_display_get_fb_size(&fb_width, &fb_height, &fb_pitch); - if (rgui_framebuf_data) + if (rgui_frame_buf.data) { - rgui_color_rect(rgui_framebuf_data, fb_pitch, fb_width, fb_height, x, y - 5, 1, 11, 0xFFFF); - rgui_color_rect(rgui_framebuf_data, fb_pitch, fb_width, fb_height, x - 5, y, 11, 1, 0xFFFF); - } -} - -static void rgui_frame(void *data, video_frame_info_t *video_info) -{ - rgui_t *rgui = (rgui_t*)data; - settings_t *settings = config_get_ptr(); - - if ((settings->bools.menu_rgui_background_filler_thickness_enable != rgui->bg_thickness) || - (settings->bools.menu_rgui_border_filler_thickness_enable != rgui->border_thickness) - ) - rgui->bg_modified = true; - - rgui->bg_thickness = settings->bools.menu_rgui_background_filler_thickness_enable; - rgui->border_thickness = settings->bools.menu_rgui_border_filler_thickness_enable; - - if (settings->uints.menu_rgui_color_theme != rgui->color_theme) - { - prepare_rgui_colors(rgui, settings); - } - else if (settings->uints.menu_rgui_color_theme == RGUI_THEME_CUSTOM) - { - if (string_is_not_equal_fast(settings->paths.path_rgui_theme_preset, rgui->theme_preset_path, sizeof(rgui->theme_preset_path))) - { - prepare_rgui_colors(rgui, settings); - } + rgui_color_rect(rgui_frame_buf.data, fb_pitch, fb_width, fb_height, x, y - 5, 1, 11, 0xFFFF); + rgui_color_rect(rgui_frame_buf.data, fb_pitch, fb_width, fb_height, x - 5, y, 11, 1, 0xFFFF); } } @@ -1505,9 +1512,9 @@ static void rgui_render(void *data, bool is_idle) /* if the framebuffer changed size, recache the background */ if (rgui->bg_modified || rgui->last_width != fb_width || rgui->last_height != fb_height) { - if (rgui_framebuf_data) + if (rgui_frame_buf.data) { - rgui_fill_rect(rgui, rgui_framebuf_data, fb_pitch, 0, fb_height, fb_width, 4, rgui_bg_filler); + rgui_fill_rect(rgui, rgui_frame_buf.data, fb_pitch, 0, fb_height, fb_width, 4, rgui_bg_filler); } rgui->last_width = fb_width; rgui->last_height = fb_height; @@ -1560,13 +1567,13 @@ static void rgui_render(void *data, bool is_idle) } /* Do not scroll if all items are visible. */ - if (menu_entries_get_size() <= RGUI_TERM_HEIGHT(fb_width, fb_height)) + if (menu_entries_get_size() <= RGUI_TERM_HEIGHT(fb_height)) { size_t start = 0; menu_entries_ctl(MENU_ENTRIES_CTL_SET_START, &start); } - bottom = (int)(menu_entries_get_size() - RGUI_TERM_HEIGHT(fb_width, fb_height)); + bottom = (int)(menu_entries_get_size() - RGUI_TERM_HEIGHT(fb_height)); menu_entries_ctl(MENU_ENTRIES_CTL_START_GET, &old_start); if (old_start > (unsigned)bottom) @@ -1576,8 +1583,8 @@ static void rgui_render(void *data, bool is_idle) entries_end = menu_entries_get_size(); - end = ((old_start + RGUI_TERM_HEIGHT(fb_width, fb_height)) <= (entries_end)) ? - old_start + RGUI_TERM_HEIGHT(fb_width, fb_height) : entries_end; + end = ((old_start + RGUI_TERM_HEIGHT(fb_height)) <= (entries_end)) ? + old_start + RGUI_TERM_HEIGHT(fb_height) : entries_end; /* Render wallpaper or 'normal' background */ if (rgui->show_wallpaper && wallpaper.is_valid) @@ -1628,10 +1635,10 @@ static void rgui_render(void *data, bool is_idle) title_width = utf8len(thumbnail_title_buf) * FONT_WIDTH_STRIDE; title_x = RGUI_TERM_START_X(fb_width) + ((RGUI_TERM_WIDTH(fb_width) * FONT_WIDTH_STRIDE) - title_width) / 2; - if (rgui_framebuf_data) + if (rgui_frame_buf.data) { /* Draw thumbnail title background */ - rgui_fill_rect(rgui, rgui_framebuf_data, fb_pitch, + rgui_fill_rect(rgui, rgui_frame_buf.data, fb_pitch, title_x - 5, 0, title_width + 10, FONT_HEIGHT_STRIDE, rgui_bg_filler); /* Draw thumbnail title */ @@ -1643,7 +1650,8 @@ static void rgui_render(void *data, bool is_idle) { /* No thumbnail - render usual text */ char title_buf[255]; - unsigned timedate_x = RGUI_TERM_WIDTH(fb_width) * FONT_WIDTH_STRIDE - RGUI_TERM_START_X(fb_width); + unsigned timedate_x = (RGUI_TERM_START_X(fb_width) + (RGUI_TERM_WIDTH(fb_width) * FONT_WIDTH_STRIDE)) - + (5 * FONT_WIDTH_STRIDE); unsigned core_name_len = ((timedate_x - RGUI_TERM_START_X(fb_width)) / FONT_WIDTH_STRIDE) - 3; /* Print title */ @@ -1658,11 +1666,11 @@ static void rgui_render(void *data, bool is_idle) string_to_upper(title_buf); - if (rgui_framebuf_data) + if (rgui_frame_buf.data) blit_line( (int)(RGUI_TERM_START_X(fb_width) + (RGUI_TERM_WIDTH(fb_width) - utf8len(title_buf)) * FONT_WIDTH_STRIDE / 2), - RGUI_TERM_START_X(fb_width), + RGUI_TERM_START_Y(fb_height) - FONT_HEIGHT_STRIDE, title_buf, rgui->colors.title_color); /* Print menu entries */ @@ -1712,7 +1720,8 @@ static void rgui_render(void *data, bool is_idle) { /* Resize fields according to actual length of value string */ entry_value_len = strlen(entry_value); - entry_value_len = entry_value_len > RGUI_ENTRY_VALUE_MAXLEN ? RGUI_ENTRY_VALUE_MAXLEN : entry_value_len; + entry_value_len = entry_value_len > rgui_term_layout.value_maxlen ? + rgui_term_layout.value_maxlen : entry_value_len; } else { @@ -1765,7 +1774,7 @@ static void rgui_render(void *data, bool is_idle) entry_title_buf); } - if (rgui_framebuf_data) + if (rgui_frame_buf.data) blit_line(x, y, message, entry_selected ? rgui->colors.hover_color : rgui->colors.normal_color); @@ -1786,10 +1795,10 @@ static void rgui_render(void *data, bool is_idle) menu_animation_ticker(&ticker); - if (rgui_framebuf_data) + if (rgui_frame_buf.data) blit_line( RGUI_TERM_START_X(fb_width) + FONT_WIDTH_STRIDE, - (RGUI_TERM_HEIGHT(fb_width, fb_height) * FONT_HEIGHT_STRIDE) + + (RGUI_TERM_HEIGHT(fb_height) * FONT_HEIGHT_STRIDE) + RGUI_TERM_START_Y(fb_height) + 2, sublabel_buf, rgui->colors.hover_color); } else if (settings->bools.menu_core_enable) @@ -1807,10 +1816,10 @@ static void rgui_render(void *data, bool is_idle) menu_animation_ticker(&ticker); - if (rgui_framebuf_data) + if (rgui_frame_buf.data) blit_line( RGUI_TERM_START_X(fb_width) + FONT_WIDTH_STRIDE, - (RGUI_TERM_HEIGHT(fb_width, fb_height) * FONT_HEIGHT_STRIDE) + + (RGUI_TERM_HEIGHT(fb_height) * FONT_HEIGHT_STRIDE) + RGUI_TERM_START_Y(fb_height) + 2, core_title_buf, rgui->colors.hover_color); } } @@ -1829,10 +1838,10 @@ static void rgui_render(void *data, bool is_idle) menu_display_timedate(&datetime); - if (rgui_framebuf_data) + if (rgui_frame_buf.data) blit_line( timedate_x, - (RGUI_TERM_HEIGHT(fb_width, fb_height) * FONT_HEIGHT_STRIDE) + + (RGUI_TERM_HEIGHT(fb_height) * FONT_HEIGHT_STRIDE) + RGUI_TERM_START_Y(fb_height) + 2, timedate, rgui->colors.hover_color); } } @@ -1868,9 +1877,144 @@ static void rgui_render(void *data, bool is_idle) static void rgui_framebuffer_free(void) { - if (rgui_framebuf_data) - free(rgui_framebuf_data); - rgui_framebuf_data = NULL; + if (rgui_frame_buf.data) + free(rgui_frame_buf.data); + rgui_frame_buf.data = NULL; +} + +static void rgui_thumbnail_free(void) +{ + thumbnail.width = 0; + thumbnail.height = 0; + thumbnail.is_valid = false; + + if (!string_is_empty(thumbnail.path)) + free(thumbnail.path); + thumbnail.path = NULL; + + if (thumbnail.data) + free(thumbnail.data); + thumbnail.data = NULL; +} + +static void rgui_wallpaper_free(void) +{ + wallpaper.is_valid = false; + + if (!string_is_empty(wallpaper.path)) + free(wallpaper.path); + wallpaper.path = NULL; + + if (wallpaper.data) + free(wallpaper.data); + wallpaper.data = NULL; +} + +static bool rgui_set_aspect_ratio(rgui_t *rgui) +{ +#if !defined(GEKKO) + settings_t *settings = config_get_ptr(); +#endif + + rgui_framebuffer_free(); + rgui_thumbnail_free(); + rgui_wallpaper_free(); + + /* Cache new aspect ratio */ + rgui->menu_aspect_ratio = settings->uints.menu_rgui_aspect_ratio; + +#if defined(GEKKO) + + /* Set frame buffer dimensions + * and update menu aspect index */ + rgui_frame_buf.height = 240; + rgui_frame_buf.width = 320; + rgui->menu_aspect_ratio_idx = ASPECT_RATIO_4_3; + + /* Allocate frame buffer + * (4 extra lines to cache the chequered background) */ + rgui_frame_buf.data = (uint16_t*)calloc( + 400 * (rgui_frame_buf.height + 4), sizeof(uint16_t)); + +#else + + /* Set frame buffer dimensions + * and update menu aspect index */ + rgui_frame_buf.height = 240; + switch (settings->uints.menu_rgui_aspect_ratio) + { + case RGUI_ASPECT_RATIO_16_9: + rgui_frame_buf.width = 426; + rgui->menu_aspect_ratio_idx = ASPECT_RATIO_16_9; + break; + case RGUI_ASPECT_RATIO_16_10: + rgui_frame_buf.width = 384; + rgui->menu_aspect_ratio_idx = ASPECT_RATIO_16_10; + break; + default: + /* 4:3 */ + rgui_frame_buf.width = 320; + rgui->menu_aspect_ratio_idx = ASPECT_RATIO_4_3; + break; + } + + /* Allocate frame buffer + * (4 extra lines to cache the chequered background) */ + rgui_frame_buf.data = (uint16_t*)calloc( + rgui_frame_buf.width * (rgui_frame_buf.height + 4), sizeof(uint16_t)); + +#endif + + if (!rgui_frame_buf.data) + return false; + + /* Configure 'menu display' settings */ + menu_display_set_width(rgui_frame_buf.width); + menu_display_set_height(rgui_frame_buf.height); + menu_display_set_framebuffer_pitch(rgui_frame_buf.width * sizeof(uint16_t)); + + /* Determine terminal layout */ + rgui_term_layout.start_x = (3 * 5) + 1; + rgui_term_layout.start_y = (3 * 5) + FONT_HEIGHT_STRIDE; + rgui_term_layout.width = (rgui_frame_buf.width - (2 * rgui_term_layout.start_x)) / FONT_WIDTH_STRIDE; + rgui_term_layout.height = (rgui_frame_buf.height - (2 * rgui_term_layout.start_y)) / FONT_HEIGHT_STRIDE; + rgui_term_layout.value_maxlen = (unsigned)(((float)RGUI_ENTRY_VALUE_MAXLEN * (float)rgui_frame_buf.width / 320.0f) + 0.5); + + /* > 'Start X/Y' adjustments */ + rgui_term_layout.start_x = (rgui_frame_buf.width - (rgui_term_layout.width * FONT_WIDTH_STRIDE)) / 2; + rgui_term_layout.start_y = (rgui_frame_buf.height - (rgui_term_layout.height * FONT_HEIGHT_STRIDE)) / 2; + + /* Allocate thumbnail buffer */ + thumbnail.data = (uint16_t*)calloc( + rgui_frame_buf.width * rgui_frame_buf.height, sizeof(uint16_t)); + if (!thumbnail.data) + return false; + + /* Allocate wallpaper buffer */ + wallpaper.data = (uint16_t*)calloc( + rgui_frame_buf.width * rgui_frame_buf.height, sizeof(uint16_t)); + if (!wallpaper.data) + return false; + + /* Trigger background/display update */ + rgui->theme_preset_path[0] = '\0'; + rgui->bg_modified = true; + rgui->force_redraw = true; + + /* If aspect ratio lock is enabled, notify + * video driver of change */ + if (settings->bools.menu_rgui_lock_aspect) + { + unsigned aspect_ratio_idx = settings->uints.video_aspect_ratio_idx; + if (aspect_ratio_idx != rgui->menu_aspect_ratio_idx) + { + settings->uints.video_aspect_ratio_idx = rgui->menu_aspect_ratio_idx; + video_driver_set_aspect_ratio(); + settings->uints.video_aspect_ratio_idx = aspect_ratio_idx; + } + } + + return true; } static void *rgui_init(void **userdata, bool video_is_threaded) @@ -1895,27 +2039,20 @@ static void *rgui_init(void **userdata, bool video_is_threaded) rgui->menu_title[0] = '\0'; rgui->menu_sublabel[0] = '\0'; + /* Set aspect ratio + * - Allocates frame buffer + * - Configures variable 'menu display' settings */ + if (!rgui_set_aspect_ratio(rgui)) + goto error; + + /* Fixed 'menu display' settings */ + new_font_height = FONT_HEIGHT_STRIDE * 2; + menu_display_set_header_height(new_font_height); + /* Prepare RGUI colors, to improve performance */ rgui->theme_preset_path[0] = '\0'; prepare_rgui_colors(rgui, settings); - /* 4 extra lines to cache the checked background */ - rgui_framebuf_data = (uint16_t*) - calloc(400 * (240 + 4), sizeof(uint16_t)); - - if (!rgui_framebuf_data) - goto error; - - fb_width = 320; - fb_height = 240; - fb_pitch = fb_width * sizeof(uint16_t); - new_font_height = FONT_HEIGHT_STRIDE * 2; - - menu_display_set_width(fb_width); - menu_display_set_height(fb_height); - menu_display_set_header_height(new_font_height); - menu_display_set_framebuffer_pitch(fb_pitch); - start = 0; menu_entries_ctl(MENU_ENTRIES_CTL_SET_START, &start); @@ -1928,8 +2065,8 @@ static void *rgui_init(void **userdata, bool video_is_threaded) rgui->border_thickness = settings->bools.menu_rgui_border_filler_thickness_enable; rgui->bg_modified = true; - rgui->last_width = fb_width; - rgui->last_height = fb_height; + rgui->last_width = rgui_frame_buf.width; + rgui->last_height = rgui_frame_buf.height; rgui->thumbnail_path_data = menu_thumbnail_path_init(); if (!rgui->thumbnail_path_data) @@ -1943,6 +2080,8 @@ static void *rgui_init(void **userdata, bool video_is_threaded) error: rgui_framebuffer_free(); + rgui_thumbnail_free(); + rgui_wallpaper_free(); if (menu) free(menu); return NULL; @@ -1970,20 +2109,45 @@ static void rgui_free(void *data) menu_display_set_font_data_init(fb_font_inited); rgui_framebuffer_free(); + rgui_thumbnail_free(); + rgui_wallpaper_free(); - if (!string_is_empty(thumbnail.path)) - free(thumbnail.path); - - if (!string_is_empty(wallpaper.path)) - free(wallpaper.path); - - if (upscale_buf.data) + if (rgui_upscale_buf.data) { - free(upscale_buf.data); - upscale_buf.data = NULL; + free(rgui_upscale_buf.data); + rgui_upscale_buf.data = NULL; } } +static void rgui_frame(void *data, video_frame_info_t *video_info) +{ + rgui_t *rgui = (rgui_t*)data; + settings_t *settings = config_get_ptr(); + + if ((settings->bools.menu_rgui_background_filler_thickness_enable != rgui->bg_thickness) || + (settings->bools.menu_rgui_border_filler_thickness_enable != rgui->border_thickness) + ) + rgui->bg_modified = true; + + rgui->bg_thickness = settings->bools.menu_rgui_background_filler_thickness_enable; + rgui->border_thickness = settings->bools.menu_rgui_border_filler_thickness_enable; + + if (settings->uints.menu_rgui_color_theme != rgui->color_theme) + { + prepare_rgui_colors(rgui, settings); + } + else if (settings->uints.menu_rgui_color_theme == RGUI_THEME_CUSTOM) + { + if (string_is_not_equal_fast(settings->paths.path_rgui_theme_preset, rgui->theme_preset_path, sizeof(rgui->theme_preset_path))) + { + prepare_rgui_colors(rgui, settings); + } + } + + if (settings->uints.menu_rgui_aspect_ratio != rgui->menu_aspect_ratio) + rgui_set_aspect_ratio(rgui); +} + static void rgui_set_texture(void) { size_t fb_pitch; @@ -2000,7 +2164,7 @@ static void rgui_set_texture(void) if (settings->uints.menu_rgui_internal_upscale_level == RGUI_UPSCALE_NONE) { - video_driver_set_texture_frame(rgui_framebuf_data, + video_driver_set_texture_frame(rgui_frame_buf.data, false, fb_width, fb_height, 1.0f); } else @@ -2013,7 +2177,7 @@ static void rgui_set_texture(void) * than the menu framebuffer, no scaling is required */ if ((vp.width <= fb_width) && (vp.height <= fb_height)) { - video_driver_set_texture_frame(rgui_framebuf_data, + video_driver_set_texture_frame(rgui_frame_buf.data, false, fb_width, fb_height, 1.0f); } else @@ -2037,25 +2201,25 @@ static void rgui_set_texture(void) } /* Allocate upscaling buffer, if required */ - if ((upscale_buf.width != out_width) || (upscale_buf.height != out_height) || !upscale_buf.data) + if ((rgui_upscale_buf.width != out_width) || (rgui_upscale_buf.height != out_height) || !rgui_upscale_buf.data) { - upscale_buf.width = out_width; - upscale_buf.height = out_height; + rgui_upscale_buf.width = out_width; + rgui_upscale_buf.height = out_height; - if (upscale_buf.data) + if (rgui_upscale_buf.data) { - free(upscale_buf.data); - upscale_buf.data = NULL; + free(rgui_upscale_buf.data); + rgui_upscale_buf.data = NULL; } - upscale_buf.data = (uint16_t*)calloc(out_width * out_height, sizeof(uint16_t)); - if (!upscale_buf.data) + rgui_upscale_buf.data = (uint16_t*)calloc(out_width * out_height, sizeof(uint16_t)); + if (!rgui_upscale_buf.data) { /* Uh oh... This could mean we don't have enough * memory, so disable upscaling and draw the usual * framebuffer... */ settings->uints.menu_rgui_internal_upscale_level = RGUI_UPSCALE_NONE; - video_driver_set_texture_frame(rgui_framebuf_data, + video_driver_set_texture_frame(rgui_frame_buf.data, false, fb_width, fb_height, 1.0f); return; } @@ -2073,12 +2237,12 @@ static void rgui_set_texture(void) for (x_dst = 0; x_dst < out_width; x_dst++) { x_src = (x_dst * x_ratio) >> 16; - upscale_buf.data[(y_dst * out_width) + x_dst] = rgui_framebuf_data[(y_src * fb_width) + x_src]; + rgui_upscale_buf.data[(y_dst * out_width) + x_dst] = rgui_frame_buf.data[(y_src * fb_width) + x_src]; } } /* Draw upscaled texture */ - video_driver_set_texture_frame(upscale_buf.data, + video_driver_set_texture_frame(rgui_upscale_buf.data, false, out_width, out_height, 1.0f); } } @@ -2205,20 +2369,20 @@ static void rgui_navigation_set(void *data, bool scroll) menu_display_get_fb_size(&fb_width, &fb_height, &fb_pitch); - if (selection < RGUI_TERM_HEIGHT(fb_width, fb_height) /2) + if (selection < RGUI_TERM_HEIGHT(fb_height) /2) { start = 0; do_set_start = true; } - else if (selection >= (RGUI_TERM_HEIGHT(fb_width, fb_height) /2) - && selection < (end - RGUI_TERM_HEIGHT(fb_width, fb_height) /2)) + else if (selection >= (RGUI_TERM_HEIGHT(fb_height) /2) + && selection < (end - RGUI_TERM_HEIGHT(fb_height) /2)) { - start = selection - RGUI_TERM_HEIGHT(fb_width, fb_height) /2; + start = selection - RGUI_TERM_HEIGHT(fb_height) /2; do_set_start = true; } - else if (selection >= (end - RGUI_TERM_HEIGHT(fb_width, fb_height) /2)) + else if (selection >= (end - RGUI_TERM_HEIGHT(fb_height) /2)) { - start = end - RGUI_TERM_HEIGHT(fb_width, fb_height); + start = end - RGUI_TERM_HEIGHT(fb_height); do_set_start = true; } @@ -2332,30 +2496,30 @@ static void rgui_toggle(void *userdata, bool menu_on) if (menu_on) { /* Cache last used content aspect ratio */ - rgui->content_aspect_ratio = settings->uints.video_aspect_ratio_idx; + rgui->content_aspect_ratio_idx = settings->uints.video_aspect_ratio_idx; /* Check if aspect ratio needs to change */ - if (rgui->content_aspect_ratio != ASPECT_RATIO_4_3) + if (rgui->content_aspect_ratio_idx != rgui->menu_aspect_ratio_idx) { - settings->uints.video_aspect_ratio_idx = ASPECT_RATIO_4_3; + settings->uints.video_aspect_ratio_idx = rgui->menu_aspect_ratio_idx; video_driver_set_aspect_ratio(); /* If content is using a custom aspect ratio, we * have to stop here - otherwise, restore content * aspect ratio setting */ - if (rgui->content_aspect_ratio != ASPECT_RATIO_CUSTOM) - settings->uints.video_aspect_ratio_idx = rgui->content_aspect_ratio; + if (rgui->content_aspect_ratio_idx != ASPECT_RATIO_CUSTOM) + settings->uints.video_aspect_ratio_idx = rgui->content_aspect_ratio_idx; } } else { /* If content is using a custom aspect ratio, this * must be restored */ - if (rgui->content_aspect_ratio == ASPECT_RATIO_CUSTOM - && settings->uints.video_aspect_ratio_idx == ASPECT_RATIO_4_3) - settings->uints.video_aspect_ratio_idx = rgui->content_aspect_ratio; + if (rgui->content_aspect_ratio_idx == ASPECT_RATIO_CUSTOM + && settings->uints.video_aspect_ratio_idx == rgui->menu_aspect_ratio_idx) + settings->uints.video_aspect_ratio_idx = rgui->content_aspect_ratio_idx; - if (settings->uints.video_aspect_ratio_idx != ASPECT_RATIO_4_3) + if (settings->uints.video_aspect_ratio_idx != rgui->menu_aspect_ratio_idx) video_driver_set_aspect_ratio(); } } @@ -2363,10 +2527,10 @@ static void rgui_toggle(void *userdata, bool menu_on) /* Upscaling buffer is only required while menu is on. Save * memory by freeing it whenever we switch back to the current * content */ - if (!menu_on && upscale_buf.data) + if (!menu_on && rgui_upscale_buf.data) { - free(upscale_buf.data); - upscale_buf.data = NULL; + free(rgui_upscale_buf.data); + rgui_upscale_buf.data = NULL; } } diff --git a/menu/menu_defines.h b/menu/menu_defines.h index 91a0ad3f16..5d0d26e8ed 100644 --- a/menu/menu_defines.h +++ b/menu/menu_defines.h @@ -249,6 +249,14 @@ enum rgui_upscale_level RGUI_UPSCALE_LAST }; +enum rgui_aspect_ratio +{ + RGUI_ASPECT_RATIO_4_3 = 0, + RGUI_ASPECT_RATIO_16_9, + RGUI_ASPECT_RATIO_16_10, + RGUI_ASPECT_RATIO_LAST +}; + enum menu_action { MENU_ACTION_NOOP = 0, diff --git a/menu/menu_displaylist.c b/menu/menu_displaylist.c index abd882be63..7fde7b8ec1 100644 --- a/menu/menu_displaylist.c +++ b/menu/menu_displaylist.c @@ -6114,6 +6114,10 @@ bool menu_displaylist_ctl(enum menu_displaylist_ctl_state type, menu_displaylist MENU_ENUM_LABEL_MENU_RGUI_INTERNAL_UPSCALE_LEVEL, PARSE_ONLY_UINT, false) == 0) count++; + if (menu_displaylist_parse_settings_enum(menu, info, + MENU_ENUM_LABEL_MENU_RGUI_ASPECT_RATIO, + PARSE_ONLY_UINT, false) == 0) + count++; if (menu_displaylist_parse_settings_enum(menu, info, MENU_ENUM_LABEL_MENU_RGUI_LOCK_ASPECT, PARSE_ONLY_BOOL, false) == 0) diff --git a/menu/menu_setting.c b/menu/menu_setting.c index 2bad35bb7d..0d5980c118 100644 --- a/menu/menu_setting.c +++ b/menu/menu_setting.c @@ -891,6 +891,36 @@ static void setting_get_string_representation_uint_rgui_internal_upscale_level( } } +static void setting_get_string_representation_uint_rgui_aspect_ratio( + rarch_setting_t *setting, + char *s, size_t len) +{ + if (!setting) + return; + + switch (*setting->value.target.unsigned_integer) + { + case RGUI_ASPECT_RATIO_4_3: + strlcpy(s, + msg_hash_to_str( + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_4_3), + len); + break; + case RGUI_ASPECT_RATIO_16_9: + strlcpy(s, + msg_hash_to_str( + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_9), + len); + break; + case RGUI_ASPECT_RATIO_16_10: + strlcpy(s, + msg_hash_to_str( + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_10), + len); + break; + } +} + static void setting_get_string_representation_uint_menu_ticker_type( rarch_setting_t *setting, char *s, size_t len) @@ -8293,6 +8323,24 @@ static bool setting_append_list( settings_data_list_current_add_flags(list, list_info, SD_FLAG_ADVANCED); } +#if !defined(GEKKO) + CONFIG_UINT( + list, list_info, + &settings->uints.menu_rgui_aspect_ratio, + MENU_ENUM_LABEL_MENU_RGUI_ASPECT_RATIO, + MENU_ENUM_LABEL_VALUE_MENU_RGUI_ASPECT_RATIO, + rgui_aspect, + &group_info, + &subgroup_info, + parent_group, + general_write_handler, + general_read_handler); + (*list)[list_info->index - 1].action_ok = &setting_action_ok_uint; + (*list)[list_info->index - 1].get_string_representation = + &setting_get_string_representation_uint_rgui_aspect_ratio; + menu_settings_list_current_add_range(list, list_info, 0, RGUI_ASPECT_RATIO_LAST-1, 1, true, true); +#endif + CONFIG_BOOL( list, list_info, &settings->bools.menu_rgui_lock_aspect, diff --git a/msg_hash.h b/msg_hash.h index 25e7b53a64..2600d05f47 100644 --- a/msg_hash.h +++ b/msg_hash.h @@ -867,6 +867,7 @@ enum msg_hash_enums MENU_LABEL(MENU_RGUI_BORDER_FILLER_THICKNESS_ENABLE), MENU_LABEL(MENU_RGUI_LOCK_ASPECT), MENU_LABEL(MENU_RGUI_INTERNAL_UPSCALE_LEVEL), + MENU_LABEL(MENU_RGUI_ASPECT_RATIO), MENU_LABEL(MENU_RGUI_FULL_WIDTH_LAYOUT), MENU_LABEL(MENU_LINEAR_FILTER), MENU_LABEL(MENU_HORIZONTAL_ANIMATION), @@ -1985,6 +1986,10 @@ enum msg_hash_enums MENU_ENUM_LABEL_VALUE_RGUI_UPSCALE_X8, MENU_ENUM_LABEL_VALUE_RGUI_UPSCALE_X9, + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_4_3, + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_9, + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_10, + /* Callback strings */ MENU_ENUM_LABEL_CB_CORE_CONTENT_DIRS_LIST, MENU_ENUM_LABEL_CB_CORE_CONTENT_DOWNLOAD, From a17f0e2136f4b30faa8d66dde91a8bac9eac387e Mon Sep 17 00:00:00 2001 From: jdgleaver Date: Tue, 19 Mar 2019 13:11:00 +0000 Subject: [PATCH 2/4] (RGUI) Allow text to be centred when selecting widescreen layouts --- cores/dynamic_dummy.c | 2 ++ intl/msg_hash_us.h | 8 ++++++++ menu/drivers/rgui.c | 21 +++++++++++++++++++-- menu/menu_defines.h | 2 ++ menu/menu_setting.c | 12 ++++++++++++ msg_hash.h | 2 ++ 6 files changed, 45 insertions(+), 2 deletions(-) diff --git a/cores/dynamic_dummy.c b/cores/dynamic_dummy.c index 6b5db0bff1..d02b2846b7 100644 --- a/cores/dynamic_dummy.c +++ b/cores/dynamic_dummy.c @@ -79,9 +79,11 @@ void libretro_dummy_retro_init(void) switch (settings->uints.menu_rgui_aspect_ratio) { case RGUI_ASPECT_RATIO_16_9: + case RGUI_ASPECT_RATIO_16_9_CENTRE: frame_buf_width = 426; break; case RGUI_ASPECT_RATIO_16_10: + case RGUI_ASPECT_RATIO_16_10_CENTRE: frame_buf_width = 384; break; default: diff --git a/intl/msg_hash_us.h b/intl/msg_hash_us.h index 461965bb9e..8564c7aa7e 100644 --- a/intl/msg_hash_us.h +++ b/intl/msg_hash_us.h @@ -3030,10 +3030,18 @@ MSG_HASH( MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_9, "16:9" ) +MSG_HASH( + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_9_CENTRE, + "16:9 (Centered)" + ) MSG_HASH( MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_10, "16:10" ) +MSG_HASH( + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_10_CENTRE, + "16:10 (Centered)" + ) MSG_HASH( MENU_ENUM_LABEL_VALUE_THUMBNAILS_DIRECTORY, "Thumbnails" diff --git a/menu/drivers/rgui.c b/menu/drivers/rgui.c index 7ab929ed11..0f62f75a4d 100644 --- a/menu/drivers/rgui.c +++ b/menu/drivers/rgui.c @@ -1057,9 +1057,11 @@ static void load_custom_theme(rgui_t *rgui, rgui_theme_t *theme_colors, const ch switch (settings->uints.menu_rgui_aspect_ratio) { case RGUI_ASPECT_RATIO_16_9: + case RGUI_ASPECT_RATIO_16_9_CENTRE: wallpaper_key = "rgui_wallpaper_16_9"; break; case RGUI_ASPECT_RATIO_16_10: + case RGUI_ASPECT_RATIO_16_10_CENTRE: wallpaper_key = "rgui_wallpaper_16_10"; break; default: @@ -1915,6 +1917,7 @@ static bool rgui_set_aspect_ratio(rgui_t *rgui) #if !defined(GEKKO) settings_t *settings = config_get_ptr(); #endif + unsigned base_term_width; rgui_framebuffer_free(); rgui_thumbnail_free(); @@ -1929,6 +1932,7 @@ static bool rgui_set_aspect_ratio(rgui_t *rgui) * and update menu aspect index */ rgui_frame_buf.height = 240; rgui_frame_buf.width = 320; + base_term_width = rgui_frame_buf.width; rgui->menu_aspect_ratio_idx = ASPECT_RATIO_4_3; /* Allocate frame buffer @@ -1945,15 +1949,28 @@ static bool rgui_set_aspect_ratio(rgui_t *rgui) { case RGUI_ASPECT_RATIO_16_9: rgui_frame_buf.width = 426; + base_term_width = rgui_frame_buf.width; + rgui->menu_aspect_ratio_idx = ASPECT_RATIO_16_9; + break; + case RGUI_ASPECT_RATIO_16_9_CENTRE: + rgui_frame_buf.width = 426; + base_term_width = 320; rgui->menu_aspect_ratio_idx = ASPECT_RATIO_16_9; break; case RGUI_ASPECT_RATIO_16_10: rgui_frame_buf.width = 384; + base_term_width = rgui_frame_buf.width; + rgui->menu_aspect_ratio_idx = ASPECT_RATIO_16_10; + break; + case RGUI_ASPECT_RATIO_16_10_CENTRE: + rgui_frame_buf.width = 384; + base_term_width = 320; rgui->menu_aspect_ratio_idx = ASPECT_RATIO_16_10; break; default: /* 4:3 */ rgui_frame_buf.width = 320; + base_term_width = rgui_frame_buf.width; rgui->menu_aspect_ratio_idx = ASPECT_RATIO_4_3; break; } @@ -1976,9 +1993,9 @@ static bool rgui_set_aspect_ratio(rgui_t *rgui) /* Determine terminal layout */ rgui_term_layout.start_x = (3 * 5) + 1; rgui_term_layout.start_y = (3 * 5) + FONT_HEIGHT_STRIDE; - rgui_term_layout.width = (rgui_frame_buf.width - (2 * rgui_term_layout.start_x)) / FONT_WIDTH_STRIDE; + rgui_term_layout.width = (base_term_width - (2 * rgui_term_layout.start_x)) / FONT_WIDTH_STRIDE; rgui_term_layout.height = (rgui_frame_buf.height - (2 * rgui_term_layout.start_y)) / FONT_HEIGHT_STRIDE; - rgui_term_layout.value_maxlen = (unsigned)(((float)RGUI_ENTRY_VALUE_MAXLEN * (float)rgui_frame_buf.width / 320.0f) + 0.5); + rgui_term_layout.value_maxlen = (unsigned)(((float)RGUI_ENTRY_VALUE_MAXLEN * (float)base_term_width / 320.0f) + 0.5); /* > 'Start X/Y' adjustments */ rgui_term_layout.start_x = (rgui_frame_buf.width - (rgui_term_layout.width * FONT_WIDTH_STRIDE)) / 2; diff --git a/menu/menu_defines.h b/menu/menu_defines.h index 5d0d26e8ed..95d3ff04b3 100644 --- a/menu/menu_defines.h +++ b/menu/menu_defines.h @@ -253,7 +253,9 @@ enum rgui_aspect_ratio { RGUI_ASPECT_RATIO_4_3 = 0, RGUI_ASPECT_RATIO_16_9, + RGUI_ASPECT_RATIO_16_9_CENTRE, RGUI_ASPECT_RATIO_16_10, + RGUI_ASPECT_RATIO_16_10_CENTRE, RGUI_ASPECT_RATIO_LAST }; diff --git a/menu/menu_setting.c b/menu/menu_setting.c index 0d5980c118..984712fdbd 100644 --- a/menu/menu_setting.c +++ b/menu/menu_setting.c @@ -912,12 +912,24 @@ static void setting_get_string_representation_uint_rgui_aspect_ratio( MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_9), len); break; + case RGUI_ASPECT_RATIO_16_9_CENTRE: + strlcpy(s, + msg_hash_to_str( + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_9_CENTRE), + len); + break; case RGUI_ASPECT_RATIO_16_10: strlcpy(s, msg_hash_to_str( MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_10), len); break; + case RGUI_ASPECT_RATIO_16_10_CENTRE: + strlcpy(s, + msg_hash_to_str( + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_10_CENTRE), + len); + break; } } diff --git a/msg_hash.h b/msg_hash.h index 2600d05f47..2bf42c3415 100644 --- a/msg_hash.h +++ b/msg_hash.h @@ -1988,7 +1988,9 @@ enum msg_hash_enums MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_4_3, MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_9, + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_9_CENTRE, MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_10, + MENU_ENUM_LABEL_VALUE_RGUI_ASPECT_RATIO_16_10_CENTRE, /* Callback strings */ MENU_ENUM_LABEL_CB_CORE_CONTENT_DIRS_LIST, From b10901e6b9f0d537c6895da4294ffbe46b6d9385 Mon Sep 17 00:00:00 2001 From: jdgleaver Date: Tue, 19 Mar 2019 14:42:52 +0000 Subject: [PATCH 3/4] Fix 'Multiplication result converted to larger type' alert --- cores/dynamic_dummy.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cores/dynamic_dummy.c b/cores/dynamic_dummy.c index d02b2846b7..65d76a4c7b 100644 --- a/cores/dynamic_dummy.c +++ b/cores/dynamic_dummy.c @@ -67,7 +67,7 @@ void libretro_dummy_retro_init(void) #if defined(HAVE_MENU) && defined(HAVE_RGUI) settings_t *settings = config_get_ptr(); #endif - unsigned i; + uint32_t i; /* Sensible defaults */ frame_buf_width = 320; From 8336163112efcc5005799284eec1474d608dc3e3 Mon Sep 17 00:00:00 2001 From: jdgleaver Date: Tue, 19 Mar 2019 15:10:14 +0000 Subject: [PATCH 4/4] (RGUI) Ensure update is immediate when changing 'Menu Aspect Ratio' --- menu/drivers/rgui.c | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/menu/drivers/rgui.c b/menu/drivers/rgui.c index 0f62f75a4d..418bb10e9a 100644 --- a/menu/drivers/rgui.c +++ b/menu/drivers/rgui.c @@ -2023,12 +2023,9 @@ static bool rgui_set_aspect_ratio(rgui_t *rgui) if (settings->bools.menu_rgui_lock_aspect) { unsigned aspect_ratio_idx = settings->uints.video_aspect_ratio_idx; - if (aspect_ratio_idx != rgui->menu_aspect_ratio_idx) - { - settings->uints.video_aspect_ratio_idx = rgui->menu_aspect_ratio_idx; - video_driver_set_aspect_ratio(); - settings->uints.video_aspect_ratio_idx = aspect_ratio_idx; - } + settings->uints.video_aspect_ratio_idx = rgui->menu_aspect_ratio_idx; + video_driver_set_aspect_ratio(); + settings->uints.video_aspect_ratio_idx = aspect_ratio_idx; } return true;