Merge branch 'master' into gblues/hid

This commit is contained in:
gblues 2018-04-03 20:30:06 -07:00
commit 46dad14d5f
27 changed files with 887 additions and 459 deletions

View File

@ -292,6 +292,7 @@ bool core_load_game(retro_ctx_load_content_info_t *load_info)
#ifdef HAVE_RUNAHEAD #ifdef HAVE_RUNAHEAD
set_load_content_info(load_info); set_load_content_info(load_info);
clear_controller_port_map();
#endif #endif
content_get_status(&contentless, &is_inited); content_get_status(&contentless, &is_inited);

View File

@ -68,6 +68,7 @@
#ifdef HAVE_RUNAHEAD #ifdef HAVE_RUNAHEAD
#include "runahead/secondary_core.h" #include "runahead/secondary_core.h"
#include "runahead/run_ahead.h"
#endif #endif
#ifdef HAVE_DYNAMIC #ifdef HAVE_DYNAMIC
@ -1763,6 +1764,16 @@ bool rarch_environment_cb(unsigned cmd, void *data)
{ {
result |= 1; result |= 1;
} }
#ifdef HAVE_RUNAHEAD
if (want_fast_savestate())
{
result |= 4;
}
if (get_hard_disable_audio())
{
result |= 8;
}
#endif
if (data != NULL) if (data != NULL)
{ {
int* result_p = (int*)data; int* result_p = (int*)data;

View File

@ -424,9 +424,10 @@ static int win32_drag_query_file(HWND hwnd, WPARAM wparam)
static LRESULT win32_handle_keyboard_event(HWND hwnd, UINT message, static LRESULT win32_handle_keyboard_event(HWND hwnd, UINT message,
WPARAM wparam, LPARAM lparam) WPARAM wparam, LPARAM lparam)
{ {
unsigned keycode; unsigned keycode = 0;
uint16_t mod = 0; uint16_t mod = 0;
bool keydown = true; bool keydown = true;
settings_t *settings = NULL;
if (GetKeyState(VK_SHIFT) & 0x80) if (GetKeyState(VK_SHIFT) & 0x80)
mod |= RETROKMOD_SHIFT; mod |= RETROKMOD_SHIFT;
@ -460,7 +461,8 @@ static LRESULT win32_handle_keyboard_event(HWND hwnd, UINT message,
keydown = false; keydown = false;
#if _WIN32_WINNT >= 0x0501 /* XP */ #if _WIN32_WINNT >= 0x0501 /* XP */
if (string_is_equal(config_get_ptr()->arrays.input_driver, "raw")) settings = config_get_ptr();
if (settings && string_is_equal(settings->arrays.input_driver, "raw"))
keycode = input_keymaps_translate_keysym_to_rk((unsigned)(wparam)); keycode = input_keymaps_translate_keysym_to_rk((unsigned)(wparam));
else else
#endif #endif

View File

@ -107,47 +107,6 @@ void x11_show_mouse(Display *dpy, Window win, bool state)
x11_hide_mouse(dpy, win); x11_hide_mouse(dpy, win);
} }
static bool x11_check_atom_supported(Display *dpy, Atom atom)
{
Atom XA_NET_SUPPORTED = XInternAtom(dpy, "_NET_SUPPORTED", True);
Atom type;
int format;
unsigned long nitems;
unsigned long bytes_after;
Atom *prop;
int i;
if (XA_NET_SUPPORTED == None)
return false;
XGetWindowProperty(dpy, DefaultRootWindow(dpy), XA_NET_SUPPORTED, 0, UINT_MAX, False, XA_ATOM, &type, &format,&nitems, &bytes_after, (unsigned char **) &prop);
if (!prop || type != XA_ATOM)
{
return false;
}
for (i = 0; i < nitems; i++)
{
if (prop[i] == atom)
{
XFree(prop);
return true;
}
}
XFree(prop);
return false;
}
bool x11_has_net_wm_fullscreen(Display *dpy)
{
XA_NET_WM_STATE_FULLSCREEN = XInternAtom(dpy, "_NET_WM_STATE_FULLSCREEN", False);
return x11_check_atom_supported(dpy, XA_NET_WM_STATE_FULLSCREEN);
}
void x11_set_net_wm_fullscreen(Display *dpy, Window win) void x11_set_net_wm_fullscreen(Display *dpy, Window win)
{ {
XEvent xev = {0}; XEvent xev = {0};
@ -726,3 +685,106 @@ void x11_event_queue_check(XEvent *event)
XIfEvent(g_x11_dpy, event, x11_wait_notify, NULL); XIfEvent(g_x11_dpy, event, x11_wait_notify, NULL);
} }
static bool x11_check_atom_supported(Display *dpy, Atom atom)
{
Atom XA_NET_SUPPORTED = XInternAtom(dpy, "_NET_SUPPORTED", True);
Atom type;
int format;
unsigned long nitems;
unsigned long bytes_after;
Atom *prop;
int i;
if (XA_NET_SUPPORTED == None)
return false;
XGetWindowProperty(dpy, DefaultRootWindow(dpy), XA_NET_SUPPORTED, 0, UINT_MAX, False, XA_ATOM, &type, &format,&nitems, &bytes_after, (unsigned char **) &prop);
if (!prop || type != XA_ATOM)
{
return false;
}
for (i = 0; i < nitems; i++)
{
if (prop[i] == atom)
{
XFree(prop);
return true;
}
}
XFree(prop);
return false;
}
bool x11_has_net_wm_fullscreen(Display *dpy)
{
XA_NET_WM_STATE_FULLSCREEN = XInternAtom(dpy, "_NET_WM_STATE_FULLSCREEN", False);
return x11_check_atom_supported(dpy, XA_NET_WM_STATE_FULLSCREEN);
}
char *x11_get_wm_name(Display *dpy)
{
Atom XA_NET_SUPPORTING_WM_CHECK = XInternAtom(g_x11_dpy, "_NET_SUPPORTING_WM_CHECK", False);
Atom XA_NET_WM_NAME = XInternAtom(g_x11_dpy, "_NET_WM_NAME", False);
Atom XA_UTF8_STRING = XInternAtom(g_x11_dpy, "UTF8_STRING", False);
int status;
Atom type;
int format;
unsigned long nitems;
unsigned long bytes_after;
unsigned char *propdata;
char *title;
Window window;
if (!XA_NET_SUPPORTING_WM_CHECK || !XA_NET_WM_NAME)
return NULL;
status = XGetWindowProperty(dpy,
DefaultRootWindow(dpy),
XA_NET_SUPPORTING_WM_CHECK,
0,
1,
False,
XA_WINDOW,
&type,
&format,
&nitems,
&bytes_after,
&propdata);
if (status == Success && propdata)
window = ((Window *) propdata)[0];
else
return NULL;
XFree(propdata);
status = XGetWindowProperty(dpy,
window,
XA_NET_WM_NAME,
0,
8192,
False,
XA_UTF8_STRING,
&type,
&format,
&nitems,
&bytes_after,
&propdata);
if (status == Success && propdata)
{
title = strdup((char *) propdata);
}
else
return NULL;
XFree(propdata);
return title;
}

View File

@ -29,7 +29,6 @@ extern Colormap g_x11_cmap;
extern unsigned g_x11_screen; extern unsigned g_x11_screen;
void x11_show_mouse(Display *dpy, Window win, bool state); void x11_show_mouse(Display *dpy, Window win, bool state);
bool x11_has_net_wm_fullscreen(Display *dpy);
void x11_set_net_wm_fullscreen(Display *dpy, Window win); void x11_set_net_wm_fullscreen(Display *dpy, Window win);
void x11_suspend_screensaver(Window win, bool enable); void x11_suspend_screensaver(Window win, bool enable);
bool x11_enter_fullscreen(video_frame_info_t *video_info, bool x11_enter_fullscreen(video_frame_info_t *video_info,
@ -76,5 +75,9 @@ void x11_install_quit_atom(void);
void x11_event_queue_check(XEvent *event); void x11_event_queue_check(XEvent *event);
char *x11_get_wm_name(Display *dpy);
bool x11_has_net_wm_fullscreen(Display *dpy);
#endif #endif

View File

@ -500,21 +500,28 @@ static void d3d10_set_menu_texture_frame(
void* data, const void* frame, bool rgb32, unsigned width, unsigned height, float alpha) void* data, const void* frame, bool rgb32, unsigned width, unsigned height, float alpha)
{ {
d3d10_video_t* d3d10 = (d3d10_video_t*)data; d3d10_video_t* d3d10 = (d3d10_video_t*)data;
int pitch = width * (rgb32 ? sizeof(uint32_t) : sizeof(uint16_t)); settings_t* settings = config_get_ptr();
DXGI_FORMAT format = rgb32 ? DXGI_FORMAT_B8G8R8A8_UNORM : (DXGI_FORMAT)DXGI_FORMAT_EX_A4R4G4B4_UNORM; int pitch = width * (rgb32 ? sizeof(uint32_t)
: sizeof(uint16_t));
DXGI_FORMAT format = rgb32 ? DXGI_FORMAT_B8G8R8A8_UNORM
: (DXGI_FORMAT)DXGI_FORMAT_EX_A4R4G4B4_UNORM;
if (d3d10->menu.texture.desc.Width != width || d3d10->menu.texture.desc.Height != height) if ( d3d10->menu.texture.desc.Width != width ||
d3d10->menu.texture.desc.Height != height)
{ {
d3d10->menu.texture.desc.Format = d3d10_get_closest_match_texture2D(d3d10->device, format); d3d10->menu.texture.desc.Format = d3d10_get_closest_match_texture2D(
d3d10->device, format);
d3d10->menu.texture.desc.Width = width; d3d10->menu.texture.desc.Width = width;
d3d10->menu.texture.desc.Height = height; d3d10->menu.texture.desc.Height = height;
d3d10_init_texture(d3d10->device, &d3d10->menu.texture); d3d10_init_texture(d3d10->device, &d3d10->menu.texture);
} }
d3d10_update_texture(width, height, pitch, format, frame, &d3d10->menu.texture); d3d10_update_texture(width, height, pitch, format,
d3d10->menu.sampler = config_get_ptr()->bools.menu_linear_filter ? d3d10->sampler_linear frame, &d3d10->menu.texture);
: d3d10->sampler_nearest; d3d10->menu.sampler = settings->bools.menu_linear_filter
? d3d10->sampler_linear : d3d10->sampler_nearest;
} }
static void d3d10_set_menu_texture_enable(void* data, bool state, bool full_screen) static void d3d10_set_menu_texture_enable(void* data, bool state, bool full_screen)
{ {
d3d10_video_t* d3d10 = (d3d10_video_t*)data; d3d10_video_t* d3d10 = (d3d10_video_t*)data;

View File

@ -574,9 +574,9 @@ static void*
d3d11_gfx_init(const video_info_t* video, const input_driver_t** input, void** input_data) d3d11_gfx_init(const video_info_t* video, const input_driver_t** input, void** input_data)
{ {
unsigned i; unsigned i;
WNDCLASSEX wndclass = { 0 };
MONITORINFOEX current_mon; MONITORINFOEX current_mon;
HMONITOR hm_to_use; HMONITOR hm_to_use;
WNDCLASSEX wndclass = { 0 };
settings_t* settings = config_get_ptr(); settings_t* settings = config_get_ptr();
d3d11_video_t* d3d11 = (d3d11_video_t*)calloc(1, sizeof(*d3d11)); d3d11_video_t* d3d11 = (d3d11_video_t*)calloc(1, sizeof(*d3d11));
@ -1447,10 +1447,13 @@ static void d3d11_set_menu_texture_frame(
void* data, const void* frame, bool rgb32, unsigned width, unsigned height, float alpha) void* data, const void* frame, bool rgb32, unsigned width, unsigned height, float alpha)
{ {
d3d11_video_t* d3d11 = (d3d11_video_t*)data; d3d11_video_t* d3d11 = (d3d11_video_t*)data;
DXGI_FORMAT format = settings_t* settings = config_get_ptr();
rgb32 ? DXGI_FORMAT_B8G8R8A8_UNORM : (DXGI_FORMAT)DXGI_FORMAT_EX_A4R4G4B4_UNORM; DXGI_FORMAT format = rgb32 ? DXGI_FORMAT_B8G8R8A8_UNORM :
(DXGI_FORMAT)DXGI_FORMAT_EX_A4R4G4B4_UNORM;
if (d3d11->menu.texture.desc.Width != width || d3d11->menu.texture.desc.Height != height) if (
d3d11->menu.texture.desc.Width != width ||
d3d11->menu.texture.desc.Height != height)
{ {
d3d11->menu.texture.desc.Format = format; d3d11->menu.texture.desc.Format = format;
d3d11->menu.texture.desc.Width = width; d3d11->menu.texture.desc.Width = width;
@ -1458,9 +1461,10 @@ static void d3d11_set_menu_texture_frame(
d3d11_init_texture(d3d11->device, &d3d11->menu.texture); d3d11_init_texture(d3d11->device, &d3d11->menu.texture);
} }
d3d11_update_texture(d3d11->context, width, height, 0, format, frame, &d3d11->menu.texture); d3d11_update_texture(d3d11->context, width, height, 0,
format, frame, &d3d11->menu.texture);
d3d11->menu.texture.sampler = d3d11->samplers d3d11->menu.texture.sampler = d3d11->samplers
[config_get_ptr()->bools.menu_linear_filter [settings->bools.menu_linear_filter
? RARCH_FILTER_LINEAR ? RARCH_FILTER_LINEAR
: RARCH_FILTER_NEAREST][RARCH_WRAP_DEFAULT]; : RARCH_FILTER_NEAREST][RARCH_WRAP_DEFAULT];
} }

View File

@ -871,9 +871,9 @@ static void d3d12_gfx_free(void* data)
static void* static void*
d3d12_gfx_init(const video_info_t* video, const input_driver_t** input, void** input_data) d3d12_gfx_init(const video_info_t* video, const input_driver_t** input, void** input_data)
{ {
WNDCLASSEX wndclass = { 0 };
MONITORINFOEX current_mon; MONITORINFOEX current_mon;
HMONITOR hm_to_use; HMONITOR hm_to_use;
WNDCLASSEX wndclass = { 0 };
settings_t* settings = config_get_ptr(); settings_t* settings = config_get_ptr();
d3d12_video_t* d3d12 = (d3d12_video_t*)calloc(1, sizeof(*d3d12)); d3d12_video_t* d3d12 = (d3d12_video_t*)calloc(1, sizeof(*d3d12));
@ -1597,14 +1597,19 @@ static bool d3d12_gfx_read_viewport(void* data, uint8_t* buffer, bool is_idle)
} }
static void d3d12_set_menu_texture_frame( static void d3d12_set_menu_texture_frame(
void* data, const void* frame, bool rgb32, unsigned width, unsigned height, float alpha) void* data, const void* frame, bool rgb32,
unsigned width, unsigned height, float alpha)
{ {
d3d12_video_t* d3d12 = (d3d12_video_t*)data; d3d12_video_t* d3d12 = (d3d12_video_t*)data;
int pitch = width * (rgb32 ? sizeof(uint32_t) : sizeof(uint16_t)); settings_t* settings = config_get_ptr();
DXGI_FORMAT format = int pitch = width *
rgb32 ? DXGI_FORMAT_B8G8R8A8_UNORM : (DXGI_FORMAT)DXGI_FORMAT_EX_A4R4G4B4_UNORM; (rgb32 ? sizeof(uint32_t) : sizeof(uint16_t));
DXGI_FORMAT format = rgb32 ? DXGI_FORMAT_B8G8R8A8_UNORM
: (DXGI_FORMAT)DXGI_FORMAT_EX_A4R4G4B4_UNORM;
if (d3d12->menu.texture.desc.Width != width || d3d12->menu.texture.desc.Height != height) if (
d3d12->menu.texture.desc.Width != width ||
d3d12->menu.texture.desc.Height != height)
{ {
d3d12->menu.texture.desc.Width = width; d3d12->menu.texture.desc.Width = width;
d3d12->menu.texture.desc.Height = height; d3d12->menu.texture.desc.Height = height;
@ -1613,13 +1618,14 @@ static void d3d12_set_menu_texture_frame(
d3d12_init_texture(d3d12->device, &d3d12->menu.texture); d3d12_init_texture(d3d12->device, &d3d12->menu.texture);
} }
d3d12_update_texture(width, height, pitch, format, frame, &d3d12->menu.texture); d3d12_update_texture(width, height, pitch,
format, frame, &d3d12->menu.texture);
d3d12->menu.alpha = alpha; d3d12->menu.alpha = alpha;
{ {
D3D12_RANGE read_range = { 0, 0 }; D3D12_RANGE read_range = { 0, 0 };
d3d12_vertex_t* v; d3d12_vertex_t* v = NULL;
D3D12Map(d3d12->menu.vbo, 0, &read_range, (void**)&v); D3D12Map(d3d12->menu.vbo, 0, &read_range, (void**)&v);
v[0].color[3] = alpha; v[0].color[3] = alpha;
@ -1629,19 +1635,27 @@ static void d3d12_set_menu_texture_frame(
D3D12Unmap(d3d12->menu.vbo, 0, NULL); D3D12Unmap(d3d12->menu.vbo, 0, NULL);
} }
d3d12->menu.texture.sampler = config_get_ptr()->bools.menu_linear_filter d3d12->menu.texture.sampler = settings->bools.menu_linear_filter
? d3d12->samplers[RARCH_FILTER_LINEAR][RARCH_WRAP_DEFAULT] ? d3d12->samplers[RARCH_FILTER_LINEAR][RARCH_WRAP_DEFAULT]
: d3d12->samplers[RARCH_FILTER_NEAREST][RARCH_WRAP_DEFAULT]; : d3d12->samplers[RARCH_FILTER_NEAREST][RARCH_WRAP_DEFAULT];
} }
static void d3d12_set_menu_texture_enable(void* data, bool state, bool full_screen)
static void d3d12_set_menu_texture_enable(void* data,
bool state, bool full_screen)
{ {
d3d12_video_t* d3d12 = (d3d12_video_t*)data; d3d12_video_t* d3d12 = (d3d12_video_t*)data;
if (!d3d12)
return;
d3d12->menu.enabled = state; d3d12->menu.enabled = state;
d3d12->menu.fullscreen = full_screen; d3d12->menu.fullscreen = full_screen;
} }
static void d3d12_gfx_show_mouse(void* data, bool state) { win32_show_cursor(state); } static void d3d12_gfx_show_mouse(void* data, bool state)
{
win32_show_cursor(state);
}
static void d3d12_gfx_set_aspect_ratio(void* data, unsigned aspect_ratio_idx) static void d3d12_gfx_set_aspect_ratio(void* data, unsigned aspect_ratio_idx)
{ {
@ -1663,21 +1677,21 @@ static void d3d12_gfx_apply_state_changes(void* data)
} }
static void d3d12_gfx_set_osd_msg( static void d3d12_gfx_set_osd_msg(
void* data, video_frame_info_t* video_info, const char* msg, const void* params, void* font) void* data, video_frame_info_t* video_info,
const char* msg, const void* params, void* font)
{ {
d3d12_video_t* d3d12 = (d3d12_video_t*)data; d3d12_video_t* d3d12 = (d3d12_video_t*)data;
if (d3d12) if (!d3d12 || !d3d12->sprites.enabled)
{ return;
if (d3d12->sprites.enabled)
font_driver_render_msg(video_info, font, msg, (const struct font_params*)params); font_driver_render_msg(video_info, font, msg,
else (const struct font_params*)params);
printf("OSD msg: %s\n", msg);
}
} }
static uintptr_t d3d12_gfx_load_texture( static uintptr_t d3d12_gfx_load_texture(
void* video_data, void* data, bool threaded, enum texture_filter_type filter_type) void* video_data, void* data, bool threaded,
enum texture_filter_type filter_type)
{ {
d3d12_texture_t* texture = NULL; d3d12_texture_t* texture = NULL;
d3d12_video_t* d3d12 = (d3d12_video_t*)video_data; d3d12_video_t* d3d12 = (d3d12_video_t*)video_data;
@ -1696,12 +1710,14 @@ static uintptr_t d3d12_gfx_load_texture(
case TEXTURE_FILTER_MIPMAP_LINEAR: case TEXTURE_FILTER_MIPMAP_LINEAR:
texture->desc.MipLevels = UINT16_MAX; texture->desc.MipLevels = UINT16_MAX;
case TEXTURE_FILTER_LINEAR: case TEXTURE_FILTER_LINEAR:
texture->sampler = d3d12->samplers[RARCH_FILTER_LINEAR][RARCH_WRAP_EDGE]; texture->sampler = d3d12->samplers[
RARCH_FILTER_LINEAR][RARCH_WRAP_EDGE];
break; break;
case TEXTURE_FILTER_MIPMAP_NEAREST: case TEXTURE_FILTER_MIPMAP_NEAREST:
texture->desc.MipLevels = UINT16_MAX; texture->desc.MipLevels = UINT16_MAX;
case TEXTURE_FILTER_NEAREST: case TEXTURE_FILTER_NEAREST:
texture->sampler = d3d12->samplers[RARCH_FILTER_NEAREST][RARCH_WRAP_EDGE]; texture->sampler = d3d12->samplers[
RARCH_FILTER_NEAREST][RARCH_WRAP_EDGE];
break; break;
} }
@ -1713,7 +1729,8 @@ static uintptr_t d3d12_gfx_load_texture(
d3d12_init_texture(d3d12->device, texture); d3d12_init_texture(d3d12->device, texture);
d3d12_update_texture( d3d12_update_texture(
image->width, image->height, 0, DXGI_FORMAT_B8G8R8A8_UNORM, image->pixels, texture); image->width, image->height, 0,
DXGI_FORMAT_B8G8R8A8_UNORM, image->pixels, texture);
return (uintptr_t)texture; return (uintptr_t)texture;
} }

View File

@ -632,6 +632,7 @@ static bool gfx_ctx_x_set_video_mode(void *data,
int y_off = 0; int y_off = 0;
XVisualInfo *vi = NULL; XVisualInfo *vi = NULL;
XSetWindowAttributes swa = {0}; XSetWindowAttributes swa = {0};
char *wm_name = NULL;
int (*old_handler)(Display*, XErrorEvent*) = NULL; int (*old_handler)(Display*, XErrorEvent*) = NULL;
gfx_ctx_x_data_t *x = (gfx_ctx_x_data_t*)data; gfx_ctx_x_data_t *x = (gfx_ctx_x_data_t*)data;
Atom net_wm_icon = XInternAtom(g_x11_dpy, "_NET_WM_ICON", False); Atom net_wm_icon = XInternAtom(g_x11_dpy, "_NET_WM_ICON", False);
@ -679,6 +680,7 @@ static bool gfx_ctx_x_set_video_mode(void *data,
swa.event_mask = StructureNotifyMask | KeyPressMask | KeyReleaseMask | swa.event_mask = StructureNotifyMask | KeyPressMask | KeyReleaseMask |
LeaveWindowMask | EnterWindowMask | LeaveWindowMask | EnterWindowMask |
ButtonReleaseMask | ButtonPressMask; ButtonReleaseMask | ButtonPressMask;
swa.override_redirect = False;
if (fullscreen && !windowed_full) if (fullscreen && !windowed_full)
{ {
@ -691,7 +693,20 @@ static bool gfx_ctx_x_set_video_mode(void *data,
RARCH_ERR("[GLX]: Entering true fullscreen failed. Will attempt windowed mode.\n"); RARCH_ERR("[GLX]: Entering true fullscreen failed. Will attempt windowed mode.\n");
} }
swa.override_redirect = (!x11_has_net_wm_fullscreen(g_x11_dpy) && true_full) ? True : False; wm_name = x11_get_wm_name(g_x11_dpy);
if (wm_name)
{
RARCH_LOG("[GLX]: Window manager is %s.\n", wm_name);
if (true_full && strcasestr(wm_name, "xfwm"))
{
RARCH_LOG("[GLX]: Using override-redirect workaround.\n");
swa.override_redirect = True;
}
free(wm_name);
}
if (!x11_has_net_wm_fullscreen(g_x11_dpy) && true_full)
swa.override_redirect = True;
if (video_info->monitor_index) if (video_info->monitor_index)
g_x11_screen = video_info->monitor_index - 1; g_x11_screen = video_info->monitor_index - 1;
@ -722,8 +737,8 @@ static bool gfx_ctx_x_set_video_mode(void *data,
g_x11_win = XCreateWindow(g_x11_dpy, RootWindow(g_x11_dpy, vi->screen), g_x11_win = XCreateWindow(g_x11_dpy, RootWindow(g_x11_dpy, vi->screen),
x_off, y_off, width, height, 0, x_off, y_off, width, height, 0,
vi->depth, InputOutput, vi->visual, vi->depth, InputOutput, vi->visual,
CWBorderPixel | CWColormap | CWEventMask | CWBorderPixel | CWColormap | CWEventMask | CWOverrideRedirect,
CWOverrideRedirect, &swa); &swa);
XSetWindowBackground(g_x11_dpy, g_x11_win, 0); XSetWindowBackground(g_x11_dpy, g_x11_win, 0);
XChangeProperty(g_x11_dpy, g_x11_win, net_wm_icon, cardinal, 32, PropModeReplace, (const unsigned char*)retroarch_icon_data, sizeof(retroarch_icon_data) / sizeof(*retroarch_icon_data)); XChangeProperty(g_x11_dpy, g_x11_win, net_wm_icon, cardinal, 32, PropModeReplace, (const unsigned char*)retroarch_icon_data, sizeof(retroarch_icon_data) / sizeof(*retroarch_icon_data));
@ -780,7 +795,6 @@ static bool gfx_ctx_x_set_video_mode(void *data,
{ {
RARCH_LOG("[GLX]: Using true fullscreen.\n"); RARCH_LOG("[GLX]: Using true fullscreen.\n");
XMapRaised(g_x11_dpy, g_x11_win); XMapRaised(g_x11_dpy, g_x11_win);
if (swa.override_redirect == False)
x11_set_net_wm_fullscreen(g_x11_dpy, g_x11_win); x11_set_net_wm_fullscreen(g_x11_dpy, g_x11_win);
} }
else if (fullscreen) else if (fullscreen)

View File

@ -272,7 +272,9 @@ static bool gfx_ctx_xegl_set_video_mode(void *data,
XVisualInfo temp = {0}; XVisualInfo temp = {0};
XSetWindowAttributes swa = {0}; XSetWindowAttributes swa = {0};
XVisualInfo *vi = NULL; XVisualInfo *vi = NULL;
char *wm_name = NULL;
xegl_ctx_data_t *xegl = (xegl_ctx_data_t*)data; xegl_ctx_data_t *xegl = (xegl_ctx_data_t*)data;
settings_t *settings = config_get_ptr();
int (*old_handler)(Display*, XErrorEvent*) = NULL; int (*old_handler)(Display*, XErrorEvent*) = NULL;
@ -297,6 +299,7 @@ static bool gfx_ctx_xegl_set_video_mode(void *data,
vi->visual, AllocNone); vi->visual, AllocNone);
swa.event_mask = StructureNotifyMask | KeyPressMask | swa.event_mask = StructureNotifyMask | KeyPressMask |
ButtonPressMask | ButtonReleaseMask | KeyReleaseMask; ButtonPressMask | ButtonReleaseMask | KeyReleaseMask;
swa.override_redirect = False;
if (fullscreen && !video_info->windowed_fullscreen) if (fullscreen && !video_info->windowed_fullscreen)
{ {
@ -309,7 +312,20 @@ static bool gfx_ctx_xegl_set_video_mode(void *data,
RARCH_ERR("[X/EGL]: Entering true fullscreen failed. Will attempt windowed mode.\n"); RARCH_ERR("[X/EGL]: Entering true fullscreen failed. Will attempt windowed mode.\n");
} }
swa.override_redirect = (!x11_has_net_wm_fullscreen(g_x11_dpy) && true_full) ? True : False; wm_name = x11_get_wm_name(g_x11_dpy);
if (wm_name)
{
RARCH_LOG("[X/EGL]: Window manager is %s.\n", wm_name);
if (true_full && strcasestr(wm_name, "xfwm"))
{
RARCH_LOG("[X/EGL]: Using override-redirect workaround.\n");
swa.override_redirect = True;
}
free(wm_name);
}
if (!x11_has_net_wm_fullscreen(g_x11_dpy) && true_full)
swa.override_redirect = True;
if (video_info->monitor_index) if (video_info->monitor_index)
g_x11_screen = video_info->monitor_index - 1; g_x11_screen = video_info->monitor_index - 1;
@ -340,11 +356,11 @@ static bool gfx_ctx_xegl_set_video_mode(void *data,
g_x11_win = XCreateWindow(g_x11_dpy, RootWindow(g_x11_dpy, vi->screen), g_x11_win = XCreateWindow(g_x11_dpy, RootWindow(g_x11_dpy, vi->screen),
x_off, y_off, width, height, 0, x_off, y_off, width, height, 0,
vi->depth, InputOutput, vi->visual, vi->depth, InputOutput, vi->visual,
CWBorderPixel | CWColormap | CWEventMask | CWBorderPixel | CWColormap | CWEventMask | CWOverrideRedirect,
CWOverrideRedirect, &swa); &swa);
XSetWindowBackground(g_x11_dpy, g_x11_win, 0); XSetWindowBackground(g_x11_dpy, g_x11_win, 0);
if (fullscreen && config_get_ptr()->bools.video_disable_composition) if (fullscreen && settings && settings->bools.video_disable_composition)
{ {
uint32_t value = 1; uint32_t value = 1;
Atom cardinal = XInternAtom(g_x11_dpy, "CARDINAL", False); Atom cardinal = XInternAtom(g_x11_dpy, "CARDINAL", False);
@ -373,7 +389,6 @@ static bool gfx_ctx_xegl_set_video_mode(void *data,
{ {
RARCH_LOG("[X/EGL]: Using true fullscreen.\n"); RARCH_LOG("[X/EGL]: Using true fullscreen.\n");
XMapRaised(g_x11_dpy, g_x11_win); XMapRaised(g_x11_dpy, g_x11_win);
if (swa.override_redirect == False)
x11_set_net_wm_fullscreen(g_x11_dpy, g_x11_win); x11_set_net_wm_fullscreen(g_x11_dpy, g_x11_win);
} }
else if (fullscreen) else if (fullscreen)

View File

@ -70,7 +70,7 @@ CFComparisonResult iohidmanager_sort_elements(const void *val1, const void *val2
if (page1 != page2) if (page1 != page2)
return (CFComparisonResult)(page1 > page2); return (CFComparisonResult)(page1 > page2);
if(use1 != use2) if (use1 != use2)
return (CFComparisonResult)(use1 > use2); return (CFComparisonResult)(use1 > use2);
return (CFComparisonResult)(cookie1 > cookie2); return (CFComparisonResult)(cookie1 > cookie2);
@ -78,9 +78,9 @@ CFComparisonResult iohidmanager_sort_elements(const void *val1, const void *val2
static bool iohidmanager_check_for_id(apple_input_rec_t *rec, uint32_t id) static bool iohidmanager_check_for_id(apple_input_rec_t *rec, uint32_t id)
{ {
while(rec) while (rec)
{ {
if(rec->id == id) if (rec->id == id)
return true; return true;
rec = rec->next; rec = rec->next;
} }
@ -90,7 +90,7 @@ static bool iohidmanager_check_for_id(apple_input_rec_t *rec, uint32_t id)
static void iohidmanager_append_record(apple_input_rec_t *rec, apple_input_rec_t *b) static void iohidmanager_append_record(apple_input_rec_t *rec, apple_input_rec_t *b)
{ {
apple_input_rec_t *tmp = rec; apple_input_rec_t *tmp = rec;
while(tmp->next) while (tmp->next)
tmp = tmp->next; tmp = tmp->next;
tmp->next = b; tmp->next = b;
} }
@ -110,7 +110,8 @@ static void iohidmanager_append_record(apple_input_rec_t *rec, apple_input_rec_t
static void iohidmanager_append_record_ordered(apple_input_rec_t **p_rec, apple_input_rec_t *b) static void iohidmanager_append_record_ordered(apple_input_rec_t **p_rec, apple_input_rec_t *b)
{ {
apple_input_rec_t *tmp = *p_rec; apple_input_rec_t *tmp = *p_rec;
while(tmp && (tmp->id <= b->id)) { while (tmp && (tmp->id <= b->id))
{
p_rec = &tmp->next; p_rec = &tmp->next;
tmp = tmp->next; tmp = tmp->next;
} }
@ -154,7 +155,7 @@ static bool iohidmanager_hid_joypad_button(void *data,
if (hat_dir) if (hat_dir)
{ {
unsigned h = GET_HAT(joykey); unsigned h = GET_HAT(joykey);
if(h >= 1) if (h >= 1)
return false; return false;
switch(hat_dir) switch(hat_dir)
@ -207,7 +208,7 @@ static int16_t iohidmanager_hid_joypad_axis(void *data,
if (val >= 0) if (val >= 0)
val = 0; val = 0;
} }
else if(AXIS_POS_GET(joyaxis) < 6) else if (AXIS_POS_GET(joyaxis) < 6)
{ {
val += hid->axes[port][AXIS_POS_GET(joyaxis)]; val += hid->axes[port][AXIS_POS_GET(joyaxis)];
val += pad_connection_get_axis(&hid->slots[port], val += pad_connection_get_axis(&hid->slots[port],
@ -282,15 +283,15 @@ static void iohidmanager_hid_device_input_callback(void *data, IOReturn result,
{ {
tmp = adapter->hats; tmp = adapter->hats;
while(tmp && tmp->cookie != (IOHIDElementCookie)cookie) while (tmp && tmp->cookie != (IOHIDElementCookie)cookie)
tmp = tmp->next; tmp = tmp->next;
if(tmp->cookie == (IOHIDElementCookie)cookie) if (tmp->cookie == (IOHIDElementCookie)cookie)
{ {
CFIndex range = IOHIDElementGetLogicalMax(element) - IOHIDElementGetLogicalMin(element); CFIndex range = IOHIDElementGetLogicalMax(element) - IOHIDElementGetLogicalMin(element);
CFIndex val = IOHIDValueGetIntegerValue(value); CFIndex val = IOHIDValueGetIntegerValue(value);
if(range == 3) if (range == 3)
val *= 2; val *= 2;
switch(val) switch(val)
@ -347,12 +348,12 @@ static void iohidmanager_hid_device_input_callback(void *data, IOReturn result,
default: default:
tmp = adapter->axes; tmp = adapter->axes;
while(tmp && tmp->cookie != (IOHIDElementCookie)cookie) while (tmp && tmp->cookie != (IOHIDElementCookie)cookie)
tmp = tmp->next; tmp = tmp->next;
if (tmp) if (tmp)
{ {
if(tmp->cookie == (IOHIDElementCookie)cookie) if (tmp->cookie == (IOHIDElementCookie)cookie)
{ {
CFIndex min = IOHIDElementGetPhysicalMin(element); CFIndex min = IOHIDElementGetPhysicalMin(element);
CFIndex state = IOHIDValueGetIntegerValue(value) - min; CFIndex state = IOHIDValueGetIntegerValue(value) - min;
@ -384,16 +385,17 @@ static void iohidmanager_hid_device_input_callback(void *data, IOReturn result,
if (pushed_button) if (pushed_button)
{ {
uint8_t bit = 0;
tmp = adapter->buttons; tmp = adapter->buttons;
uint8_t bit = 0; while (tmp && tmp->cookie != (IOHIDElementCookie)cookie)
while(tmp && tmp->cookie != (IOHIDElementCookie)cookie)
{ {
bit++; bit++;
tmp = tmp->next; tmp = tmp->next;
} }
if(tmp && tmp->cookie == (IOHIDElementCookie)cookie) if (tmp && tmp->cookie == (IOHIDElementCookie)cookie)
{ {
CFIndex state = IOHIDValueGetIntegerValue(value); CFIndex state = IOHIDValueGetIntegerValue(value);
if (state) if (state)
@ -425,19 +427,21 @@ static void iohidmanager_hid_device_remove(void *data,
if (adapter) if (adapter)
{ {
apple_input_rec_t* tmp = NULL; apple_input_rec_t* tmp = NULL;
while(adapter->hats != NULL) while (adapter->hats != NULL)
{ {
tmp = adapter->hats; tmp = adapter->hats;
adapter->hats = adapter->hats->next; adapter->hats = adapter->hats->next;
free(tmp); free(tmp);
} }
while(adapter->axes != NULL)
while (adapter->axes != NULL)
{ {
tmp = adapter->axes; tmp = adapter->axes;
adapter->axes = adapter->axes->next; adapter->axes = adapter->axes->next;
free(tmp); free(tmp);
} }
while(adapter->buttons != NULL)
while (adapter->buttons != NULL)
{ {
tmp = adapter->buttons; tmp = adapter->buttons;
adapter->buttons = adapter->buttons->next; adapter->buttons = adapter->buttons->next;
@ -450,11 +454,11 @@ static void iohidmanager_hid_device_remove(void *data,
static int32_t iohidmanager_hid_device_get_int_property( static int32_t iohidmanager_hid_device_get_int_property(
IOHIDDeviceRef device, CFStringRef key) IOHIDDeviceRef device, CFStringRef key)
{ {
int32_t value;
CFNumberRef ref = (CFNumberRef)IOHIDDeviceGetProperty(device, key); CFNumberRef ref = (CFNumberRef)IOHIDDeviceGetProperty(device, key);
if (ref && (CFGetTypeID(ref) == CFNumberGetTypeID())) if (ref && (CFGetTypeID(ref) == CFNumberGetTypeID()))
{ {
int32_t value = 0;
CFNumberGetValue((CFNumberRef)ref, kCFNumberIntType, &value); CFNumberGetValue((CFNumberRef)ref, kCFNumberIntType, &value);
return value; return value;
} }
@ -474,6 +478,12 @@ static uint16_t iohidmanager_hid_device_get_product_id(IOHIDDeviceRef device)
CFSTR(kIOHIDProductIDKey)); CFSTR(kIOHIDProductIDKey));
} }
static uint32_t iohidmanager_hid_device_get_location_id(IOHIDDeviceRef device)
{
return iohidmanager_hid_device_get_int_property(device,
CFSTR(kIOHIDLocationIDKey));
}
static void iohidmanager_hid_device_get_product_string( static void iohidmanager_hid_device_get_product_string(
IOHIDDeviceRef device, char *buf, size_t len) IOHIDDeviceRef device, char *buf, size_t len)
{ {
@ -501,8 +511,8 @@ static void iohidmanager_hid_device_add_autodetect(unsigned idx,
RARCH_LOG("Port %d: %s.\n", idx, device_name); RARCH_LOG("Port %d: %s.\n", idx, device_name);
} }
static void iohidmanager_hid_device_add(void *data, IOReturn result, static void iohidmanager_hid_device_add(IOHIDDeviceRef device, iohidmanager_hid_t* hid)
void* sender, IOHIDDeviceRef device)
{ {
int i; int i;
IOReturn ret; IOReturn ret;
@ -516,8 +526,6 @@ static void iohidmanager_hid_device_add(void *data, IOReturn result,
apple_input_rec_t *tmp = NULL; apple_input_rec_t *tmp = NULL;
apple_input_rec_t *tmpButtons = NULL; apple_input_rec_t *tmpButtons = NULL;
apple_input_rec_t *tmpAxes = NULL; apple_input_rec_t *tmpAxes = NULL;
iohidmanager_hid_t *hid = (iohidmanager_hid_t*)
hid_driver_get_data();
struct iohidmanager_hid_adapter *adapter = (struct iohidmanager_hid_adapter*) struct iohidmanager_hid_adapter *adapter = (struct iohidmanager_hid_adapter*)
calloc(1, sizeof(*adapter)); calloc(1, sizeof(*adapter));
@ -577,17 +585,18 @@ static void iohidmanager_hid_device_add(void *data, IOReturn result,
for (i = 0; i < count; i++) for (i = 0; i < count; i++)
{ {
IOHIDElementType type;
uint32_t page, use, cookie;
int detected_button = 0;
IOHIDElementRef element = (IOHIDElementRef)CFArrayGetValueAtIndex(elements, i); IOHIDElementRef element = (IOHIDElementRef)CFArrayGetValueAtIndex(elements, i);
if (!element) if (!element)
continue; continue;
IOHIDElementType type = IOHIDElementGetType(element); type = IOHIDElementGetType(element);
uint32_t page = (uint32_t)IOHIDElementGetUsagePage(element); page = (uint32_t)IOHIDElementGetUsagePage(element);
uint32_t use = (uint32_t)IOHIDElementGetUsage(element); use = (uint32_t)IOHIDElementGetUsage(element);
uint32_t cookie = (uint32_t)IOHIDElementGetCookie(element); cookie = (uint32_t)IOHIDElementGetCookie(element);
int detected_button = 0;
switch (page) switch (page)
{ {
@ -632,10 +641,10 @@ static void iohidmanager_hid_device_add(void *data, IOReturn result,
axis->cookie = (IOHIDElementCookie)cookie; axis->cookie = (IOHIDElementCookie)cookie;
axis->next = NULL; axis->next = NULL;
if(iohidmanager_check_for_id(adapter->axes,i)) if (iohidmanager_check_for_id(adapter->axes,i))
{ {
/* axis ID already exists, save to tmp for appending later */ /* axis ID already exists, save to tmp for appending later */
if(tmpAxes) if (tmpAxes)
iohidmanager_append_record(tmpAxes, axis); iohidmanager_append_record(tmpAxes, axis);
else else
tmpAxes = axis; tmpAxes = axis;
@ -643,7 +652,7 @@ static void iohidmanager_hid_device_add(void *data, IOReturn result,
else else
{ {
found_axis[axis->id] = true; found_axis[axis->id] = true;
if(adapter->axes) if (adapter->axes)
iohidmanager_append_record(adapter->axes, axis); iohidmanager_append_record(adapter->axes, axis);
else else
adapter->axes = axis; adapter->axes = axis;
@ -683,16 +692,16 @@ static void iohidmanager_hid_device_add(void *data, IOReturn result,
btn->cookie = (IOHIDElementCookie)cookie; btn->cookie = (IOHIDElementCookie)cookie;
btn->next = NULL; btn->next = NULL;
if(iohidmanager_check_for_id(adapter->buttons,btn->id)) if (iohidmanager_check_for_id(adapter->buttons,btn->id))
{ {
if(tmpButtons) if (tmpButtons)
iohidmanager_append_record_ordered(&tmpButtons, btn); iohidmanager_append_record_ordered(&tmpButtons, btn);
else else
tmpButtons = btn; tmpButtons = btn;
} }
else else
{ {
if(adapter->buttons) if (adapter->buttons)
iohidmanager_append_record_ordered(&adapter->buttons, btn); iohidmanager_append_record_ordered(&adapter->buttons, btn);
else else
adapter->buttons = btn; adapter->buttons = btn;
@ -703,7 +712,7 @@ static void iohidmanager_hid_device_add(void *data, IOReturn result,
/* take care of buttons/axes with duplicate 'use' values */ /* take care of buttons/axes with duplicate 'use' values */
for (i = 0; i < 6; i++) for (i = 0; i < 6; i++)
{ {
if(found_axis[i] == false && tmpAxes) if (found_axis[i] == false && tmpAxes)
{ {
apple_input_rec_t *next = tmpAxes->next; apple_input_rec_t *next = tmpAxes->next;
tmpAxes->id = i; tmpAxes->id = i;
@ -717,11 +726,11 @@ static void iohidmanager_hid_device_add(void *data, IOReturn result,
if (tmp) if (tmp)
{ {
while(tmp->next) while (tmp->next)
tmp = tmp->next; tmp = tmp->next;
} }
while(tmpButtons) while (tmpButtons)
{ {
apple_input_rec_t *next = tmpButtons->next; apple_input_rec_t *next = tmpButtons->next;
@ -742,31 +751,31 @@ static void iohidmanager_hid_device_add(void *data, IOReturn result,
error: error:
{ {
apple_input_rec_t *tmp = NULL; apple_input_rec_t *tmp = NULL;
while(adapter->hats != NULL) while (adapter->hats != NULL)
{ {
tmp = adapter->hats; tmp = adapter->hats;
adapter->hats = adapter->hats->next; adapter->hats = adapter->hats->next;
free(tmp); free(tmp);
} }
while(adapter->axes != NULL) while (adapter->axes != NULL)
{ {
tmp = adapter->axes; tmp = adapter->axes;
adapter->axes = adapter->axes->next; adapter->axes = adapter->axes->next;
free(tmp); free(tmp);
} }
while(adapter->buttons != NULL) while (adapter->buttons != NULL)
{ {
tmp = adapter->buttons; tmp = adapter->buttons;
adapter->buttons = adapter->buttons->next; adapter->buttons = adapter->buttons->next;
free(tmp); free(tmp);
} }
while(tmpAxes != NULL) while (tmpAxes != NULL)
{ {
tmp = tmpAxes; tmp = tmpAxes;
tmpAxes = tmpAxes->next; tmpAxes = tmpAxes->next;
free(tmp); free(tmp);
} }
while(tmpButtons != NULL) while (tmpButtons != NULL)
{ {
tmp = tmpButtons; tmp = tmpButtons;
tmpButtons = tmpButtons->next; tmpButtons = tmpButtons->next;
@ -829,27 +838,81 @@ static int iohidmanager_hid_manager_free(iohidmanager_hid_t *hid)
return 0; return 0;
} }
/* re order device by location id */
typedef struct hid_list
{
IOHIDDeviceRef device;
uint32_t lid;
struct hid_list *next;
} hid_list_t;
static int iohidmanager_hid_manager_set_device_matching( static int iohidmanager_hid_manager_set_device_matching(
iohidmanager_hid_t *hid) iohidmanager_hid_t *hid)
{ {
CFMutableArrayRef matcher = CFArrayCreateMutable(kCFAllocatorDefault, 0, unsigned i;
&kCFTypeArrayCallBacks); hid_list_t* devList = NULL;
CFSetRef set = IOHIDManagerCopyDevices(hid->ptr);
CFIndex num_devices = CFSetGetCount(set);
IOHIDDeviceRef *device_array = (IOHIDDeviceRef*)calloc(num_devices, sizeof(IOHIDDeviceRef));
if (!matcher) CFSetGetValues(set, (const void **) device_array);
return -1;
iohidmanager_hid_append_matching_dictionary(matcher, for (i = 0; i < num_devices; i++)
kHIDPage_GenericDesktop, {
kHIDUsage_GD_Joystick); IOHIDDeviceRef dev = device_array[i];
iohidmanager_hid_append_matching_dictionary(matcher,
kHIDPage_GenericDesktop,
kHIDUsage_GD_GamePad);
IOHIDManagerSetDeviceMatchingMultiple(hid->ptr, matcher); /* filter gamepad/joystick devices */
IOHIDManagerRegisterDeviceMatchingCallback(hid->ptr, if ( IOHIDDeviceConformsTo(dev, kHIDPage_GenericDesktop, kHIDUsage_GD_Joystick)
iohidmanager_hid_device_add, 0); || IOHIDDeviceConformsTo(dev, kHIDPage_GenericDesktop, kHIDUsage_GD_GamePad)
)
{
if (!devList)
{
devList = (hid_list_t *)malloc(sizeof(hid_list_t));
devList->device = dev;
devList->lid = iohidmanager_hid_device_get_location_id(dev);
devList->next = NULL;
}
else
{
hid_list_t *ptr = NULL;
hid_list_t *new = (hid_list_t *)malloc(sizeof(hid_list_t));
new->device = dev;
new->lid = iohidmanager_hid_device_get_location_id(dev);
new->next = NULL;
CFRelease(matcher); ptr = devList;
if ( new->lid < ptr->lid )
{
new->next = ptr;
devList = new;
}
else
{
while ((ptr->lid < new->lid ) && ptr->next)
ptr = ptr->next;
new->next = ptr->next;
ptr->next = new;
}
}
}
}
{
/* register devices */
hid_list_t * ptr = devList;
while (ptr)
{
iohidmanager_hid_device_add(ptr->device, hid);
ptr = ptr->next;
free(devList);
devList = ptr;
}
}
free(device_array);
return 0; return 0;
} }
@ -860,7 +923,7 @@ static void *iohidmanager_hid_init(void)
calloc(1, sizeof(*hid_apple)); calloc(1, sizeof(*hid_apple));
if (!hid_apple) if (!hid_apple)
goto error; return NULL;
hid_apple->slots = pad_connection_init(MAX_USERS); hid_apple->slots = pad_connection_init(MAX_USERS);

View File

@ -72,8 +72,121 @@ struct input_overlay
input_overlay_t *overlay_ptr = NULL; input_overlay_t *overlay_ptr = NULL;
/**
* input_overlay_add_inputs:
* @ol : pointer to overlay
* @port : the user to show the inputs of
*
* Adds inputs from current_input to the overlay, so it's displayed
* returns true if an input that is pressed will change the overlay
*/
static bool input_overlay_add_inputs_inner(overlay_desc_t *desc,
unsigned port, unsigned analog_dpad_mode)
{
switch(desc->type)
{
case OVERLAY_TYPE_BUTTONS:
{
unsigned i;
bool all_buttons_pressed = false;
/*Check each bank of the mask*/
for (i = 0; i < ARRAY_SIZE(desc->button_mask.data); ++i)
{
/*Get bank*/
uint32_t bank_mask = BITS_GET_ELEM(desc->button_mask,i);
unsigned id = i * 32;
/*Worth pursuing? Have we got any bits left in here?*/
while (bank_mask)
{
/*If this bit is set then we need to query the pad
*The button must be pressed.*/
if (bank_mask & 1)
{
/* Light up the button if pressed */
if (input_state(port, RETRO_DEVICE_JOYPAD, 0, id))
{
all_buttons_pressed = true;
desc->updated = true;
}
else
{
/*we need ALL of the inputs to be active*/
all_buttons_pressed = false;
desc->updated = false;
/*abort*/
return false;
}
}
bank_mask >>= 1;
++id;
}
}
return all_buttons_pressed;
}
case OVERLAY_TYPE_ANALOG_LEFT:
case OVERLAY_TYPE_ANALOG_RIGHT:
{
unsigned int index = (desc->type == OVERLAY_TYPE_ANALOG_RIGHT) ?
RETRO_DEVICE_INDEX_ANALOG_RIGHT : RETRO_DEVICE_INDEX_ANALOG_LEFT;
float analog_x = input_state(port, RETRO_DEVICE_ANALOG,
index, RETRO_DEVICE_ID_ANALOG_X);
float analog_y = input_state(port, RETRO_DEVICE_ANALOG,
index, RETRO_DEVICE_ID_ANALOG_Y);
float dx = (analog_x/0x8000)*(desc->range_x/2);
float dy = (analog_y/0x8000)*(desc->range_y/2);
desc->delta_x = dx;
desc->delta_y = dy;
/*Maybe use some option here instead of 0, only display
changes greater than some magnitude.
*/
if ((dx * dx) > 0 || (dy*dy) > 0)
return true;
}
break;
case OVERLAY_TYPE_KEYBOARD:
if (input_state(port, RETRO_DEVICE_KEYBOARD, 0, desc->retro_key_idx))
{
desc->updated = true;
return true;
}
break;
default:
break;
}
return false;
}
static bool input_overlay_add_inputs(input_overlay_t *ol, static bool input_overlay_add_inputs(input_overlay_t *ol,
unsigned port, unsigned analog_dpad_mode); unsigned port, unsigned analog_dpad_mode)
{
unsigned i;
bool button_pressed = false;
input_overlay_state_t *ol_state = &ol->overlay_state;
if (!ol_state)
return false;
for (i = 0; i < ol->active->size; i++)
{
overlay_desc_t *desc = &(ol->active->descs[i]);
button_pressed |= input_overlay_add_inputs_inner(desc,
port, analog_dpad_mode);
}
return button_pressed;
}
/** /**
* input_overlay_scale: * input_overlay_scale:
* @ol : Overlay handle. * @ol : Overlay handle.
@ -234,7 +347,8 @@ static void input_overlay_enable(input_overlay_t *ol, bool enable)
* Check whether the given @x and @y coordinates of the overlay * Check whether the given @x and @y coordinates of the overlay
* descriptor @desc is inside the overlay descriptor's hitbox. * descriptor @desc is inside the overlay descriptor's hitbox.
* *
* Returns: true (1) if X, Y coordinates are inside a hitbox, otherwise false (0). * Returns: true (1) if X, Y coordinates are inside a hitbox,
* otherwise false (0).
**/ **/
static bool inside_hitbox(const struct overlay_desc *desc, float x, float y) static bool inside_hitbox(const struct overlay_desc *desc, float x, float y)
{ {
@ -305,7 +419,9 @@ static void input_overlay_poll(
{ {
case OVERLAY_TYPE_BUTTONS: case OVERLAY_TYPE_BUTTONS:
{ {
bits_or_bits(out->buttons.data, desc->button_mask.data, ARRAY_SIZE(desc->button_mask.data)); bits_or_bits(out->buttons.data,
desc->button_mask.data,
ARRAY_SIZE(desc->button_mask.data));
if (BIT256_GET(desc->button_mask, RARCH_OVERLAY_NEXT)) if (BIT256_GET(desc->button_mask, RARCH_OVERLAY_NEXT))
ol->next_index = desc->next_index; ol->next_index = desc->next_index;
@ -322,10 +438,14 @@ static void input_overlay_poll(
float x_val_sat = x_val / desc->analog_saturate_pct; float x_val_sat = x_val / desc->analog_saturate_pct;
float y_val_sat = y_val / desc->analog_saturate_pct; float y_val_sat = y_val / desc->analog_saturate_pct;
unsigned int base = (desc->type == OVERLAY_TYPE_ANALOG_RIGHT) ? 2 : 0; unsigned int base =
(desc->type == OVERLAY_TYPE_ANALOG_RIGHT)
? 2 : 0;
out->analog[base + 0] = clamp_float(x_val_sat, -1.0f, 1.0f) * 32767.0f; out->analog[base + 0] = clamp_float(x_val_sat, -1.0f, 1.0f)
out->analog[base + 1] = clamp_float(y_val_sat, -1.0f, 1.0f) * 32767.0f; * 32767.0f;
out->analog[base + 1] = clamp_float(y_val_sat, -1.0f, 1.0f)
* 32767.0f;
} }
break; break;
} }
@ -498,9 +618,12 @@ void input_overlay_loaded(void *task_data, void *user_data, const char *err)
} }
#endif #endif
if (!data->overlay_enable || !video_driver_overlay_interface(&iface) || !iface) if ( !data->overlay_enable ||
!video_driver_overlay_interface(&iface) ||
!iface)
{ {
RARCH_ERR("Overlay interface is not present in video driver, or not enabled.\n"); RARCH_ERR("Overlay interface is not present in video driver,"
" or not enabled.\n");
goto abort_load; goto abort_load;
} }
@ -532,14 +655,16 @@ abort_load:
free(data); free(data);
} }
void input_overlay_set_visibility(int overlay_idx,enum overlay_visibility vis) void input_overlay_set_visibility(int overlay_idx,
enum overlay_visibility vis)
{ {
int i;
input_overlay_t *ol = overlay_ptr; input_overlay_t *ol = overlay_ptr;
if (!visibility) if (!visibility)
{ {
visibility = (enum overlay_visibility *)calloc(MAX_VISIBILITY,sizeof(enum overlay_visibility)); unsigned i;
visibility = (enum overlay_visibility *)calloc(
MAX_VISIBILITY, sizeof(enum overlay_visibility));
for (i = 0; i < MAX_VISIBILITY; i++) for (i = 0; i < MAX_VISIBILITY; i++)
visibility[i] = OVERLAY_VISIBILITY_DEFAULT; visibility[i] = OVERLAY_VISIBILITY_DEFAULT;
@ -612,7 +737,8 @@ bool input_overlay_key_pressed(input_overlay_t *ol, unsigned key)
* *
* Poll pressed buttons/keys on currently active overlay. * Poll pressed buttons/keys on currently active overlay.
**/ **/
void input_poll_overlay(input_overlay_t *ol, float opacity, unsigned analog_dpad_mode, void input_poll_overlay(input_overlay_t *ol, float opacity,
unsigned analog_dpad_mode,
float axis_threshold) float axis_threshold)
{ {
rarch_joypad_info_t joypad_info; rarch_joypad_info_t joypad_info;
@ -661,7 +787,9 @@ void input_poll_overlay(input_overlay_t *ol, float opacity, unsigned analog_dpad
else else
ol->blocked = false; ol->blocked = false;
bits_or_bits(ol_state->buttons.data, polled_data.buttons.data, ARRAY_SIZE(polled_data.buttons.data)); bits_or_bits(ol_state->buttons.data,
polled_data.buttons.data,
ARRAY_SIZE(polled_data.buttons.data));
for (j = 0; j < ARRAY_SIZE(ol_state->keys); j++) for (j = 0; j < ARRAY_SIZE(ol_state->keys); j++)
ol_state->keys[j] |= polled_data.keys[j]; ol_state->keys[j] |= polled_data.keys[j];
@ -753,7 +881,9 @@ void input_poll_overlay(input_overlay_t *ol, float opacity, unsigned analog_dpad
} }
if (settings->bools.input_overlay_show_physical_inputs) if (settings->bools.input_overlay_show_physical_inputs)
button_pressed = input_overlay_add_inputs(ol, settings->uints.input_overlay_show_physical_inputs_port, analog_dpad_mode); button_pressed = input_overlay_add_inputs(ol,
settings->uints.input_overlay_show_physical_inputs_port,
analog_dpad_mode);
if (button_pressed || polled) if (button_pressed || polled)
input_overlay_post_poll(ol, opacity); input_overlay_post_poll(ol, opacity);
@ -779,12 +909,14 @@ void input_state_overlay(input_overlay_t *ol, int16_t *ret,
case RETRO_DEVICE_KEYBOARD: case RETRO_DEVICE_KEYBOARD:
if (id < RETROK_LAST) if (id < RETROK_LAST)
{ {
/*RARCH_LOG("UDLR %u %u %u %u\n", #if 0
RARCH_LOG("UDLR %u %u %u %u\n",
OVERLAY_GET_KEY(ol_state, RETROK_UP), OVERLAY_GET_KEY(ol_state, RETROK_UP),
OVERLAY_GET_KEY(ol_state, RETROK_DOWN), OVERLAY_GET_KEY(ol_state, RETROK_DOWN),
OVERLAY_GET_KEY(ol_state, RETROK_LEFT), OVERLAY_GET_KEY(ol_state, RETROK_LEFT),
OVERLAY_GET_KEY(ol_state, RETROK_RIGHT) OVERLAY_GET_KEY(ol_state, RETROK_RIGHT)
);*/ );
#endif
if (OVERLAY_GET_KEY(ol_state, id)) if (OVERLAY_GET_KEY(ol_state, id))
*ret |= 1; *ret |= 1;
} }
@ -803,117 +935,3 @@ void input_state_overlay(input_overlay_t *ol, int16_t *ret,
break; break;
} }
} }
/**
* input_overlay_add_inputs:
* @ol : pointer to overlay
* @port : the user to show the inputs of
*
* Adds inputs from current_input to the overlay, so it's displayed
* returns true if an input that is pressed will change the overlay
*/
static bool input_overlay_add_inputs_inner(overlay_desc_t *desc,
unsigned port, unsigned analog_dpad_mode)
{
switch(desc->type)
{
case OVERLAY_TYPE_BUTTONS:
{
unsigned i;
unsigned id;
uint32_t bank_mask;
bool all_buttons_pressed = false;
/*Check each bank of the mask*/
for (i=0; i<ARRAY_SIZE(desc->button_mask.data); ++i)
{
/*Get bank*/
bank_mask = BITS_GET_ELEM(desc->button_mask,i);
id = i*32;
/*Worth pursuing? Have we got any bits left in here?*/
while (bank_mask)
{
/*If this bit is set then we need to query the pad
*The button must be pressed.*/
if (bank_mask & 1)
{
/* Light up the button if pressed */
if (input_state(port, RETRO_DEVICE_JOYPAD, 0, id))
{
all_buttons_pressed = true;
desc->updated = true;
}
else
{
/*we need ALL of the inputs to be active*/
all_buttons_pressed = false;
desc->updated = false;
/*abort*/
return false;
}
}
bank_mask >>= 1;
++id;
}
}
return all_buttons_pressed;
}
case OVERLAY_TYPE_ANALOG_LEFT:
case OVERLAY_TYPE_ANALOG_RIGHT:
{
unsigned int index = (desc->type == OVERLAY_TYPE_ANALOG_RIGHT) ?
RETRO_DEVICE_INDEX_ANALOG_RIGHT : RETRO_DEVICE_INDEX_ANALOG_LEFT;
float analog_x = input_state(port, RETRO_DEVICE_ANALOG, index, RETRO_DEVICE_ID_ANALOG_X);
float analog_y = input_state(port, RETRO_DEVICE_ANALOG, index, RETRO_DEVICE_ID_ANALOG_Y);
float dx = (analog_x/0x8000)*(desc->range_x/2);
float dy = (analog_y/0x8000)*(desc->range_y/2);
desc->delta_x = dx;
desc->delta_y = dy;
/*Maybe use some option here instead of 0, only display
changes greater than some magnitude.
*/
if ((dx * dx) > 0 || (dy*dy) > 0)
return true;
}
break;
case OVERLAY_TYPE_KEYBOARD:
if (input_state(port, RETRO_DEVICE_KEYBOARD, 0, desc->retro_key_idx))
{
desc->updated = true;
return true;
}
break;
default:
break;
}
return false;
}
static bool input_overlay_add_inputs(input_overlay_t *ol,
unsigned port, unsigned analog_dpad_mode)
{
unsigned i;
bool button_pressed = false;
input_overlay_state_t *ol_state = &ol->overlay_state;
if (!ol_state)
return false;
for (i = 0; i < ol->active->size; i++)
{
overlay_desc_t *desc = &(ol->active->descs[i]);
button_pressed |= input_overlay_add_inputs_inner(desc, port, analog_dpad_mode);
}
return button_pressed;
}

View File

@ -1119,12 +1119,44 @@ struct retro_led_interface
#define RETRO_ENVIRONMENT_GET_AUDIO_VIDEO_ENABLE (47 | RETRO_ENVIRONMENT_EXPERIMENTAL) #define RETRO_ENVIRONMENT_GET_AUDIO_VIDEO_ENABLE (47 | RETRO_ENVIRONMENT_EXPERIMENTAL)
/* int * -- /* int * --
* Queries the frontend if audio and video are enabled or not. * Tells the core if the frontend wants audio or video.
* If not enabled, the frontend will discard the audio or video, * If disabled, the frontend will discard the audio or video,
* so the core may decide to skip producing audio or video. * so the core may decide to skip generating a frame or generating audio.
* Bit 0 (value 1) is set if Video is enabled, * This is mainly used for increasing performance.
* Bit 1 (value 2) is set if Audio is enabled. * Bit 0 (value 1): Enable Video
* Other bits are reserved for future use. * Bit 1 (value 2): Enable Audio
* Bit 2 (value 4): Use Fast Savestates.
* Bit 3 (value 8): Hard Disable Audio
* Other bits are reserved for future use and will default to zero.
* If video is disabled:
* * The frontend wants the core to not generate any video,
* including presenting frames via hardware acceleration.
* * The frontend's video frame callback will do nothing.
* * After running the frame, the video output of the next frame should be
* no different than if video was enabled, and saving and loading state
* should have no issues.
* If audio is disabled:
* * The frontend wants the core to not generate any audio.
* * The frontend's audio callbacks will do nothing.
* * After running the frame, the audio output of the next frame should be
* no different than if audio was enabled, and saving and loading state
* should have no issues.
* Fast Savestates:
* * Guaranteed to be created by the same binary that will load them.
* * Will not be written to or read from the disk.
* * Suggest that the core assumes loading state will succeed.
* * Suggest that the core updates its memory buffers in-place if possible.
* * Suggest that the core skips clearing memory.
* * Suggest that the core skips resetting the system.
* * Suggest that the core may skip validation steps.
* Hard Disable Audio:
* * Used for a secondary core when running ahead.
* * Indicates that the frontend will never need audio from the core.
* * Suggests that the core may stop synthesizing audio, but this should not
* compromise emulation accuracy.
* * Audio output for the next frame does not matter, and the frontend will
* never need an accurate audio state in the future.
* * State will never be saved when using Hard Disable Audio.
*/ */
#define RETRO_ENVIRONMENT_GET_HW_RENDER_INTERFACE (41 | RETRO_ENVIRONMENT_EXPERIMENTAL) #define RETRO_ENVIRONMENT_GET_HW_RENDER_INTERFACE (41 | RETRO_ENVIRONMENT_EXPERIMENTAL)

View File

@ -138,6 +138,7 @@ void net_http_urlencode_full(char *dest,
char *tmp = NULL; char *tmp = NULL;
char url_domain[PATH_MAX_LENGTH] = {0}; char url_domain[PATH_MAX_LENGTH] = {0};
char url_path[PATH_MAX_LENGTH] = {0}; char url_path[PATH_MAX_LENGTH] = {0};
char url_encoded[PATH_MAX_LENGTH] = {0};
int count = 0; int count = 0;
strlcpy (url_path, source, sizeof(url_path)); strlcpy (url_path, source, sizeof(url_path));

View File

@ -279,27 +279,8 @@ typedef struct xmb_handle
video_font_raster_block_t raster_block2; video_font_raster_block_t raster_block2;
} xmb_handle_t; } xmb_handle_t;
/* scaling multiplier resulting from equations using values below */
/* applied in xmb_init */
/* values for xmb_scale 50 = {2.5, 2.5, 2, 1.7, 2.5, 4, 2.4, 2.5} */
/* values for xmb_scale 75 = {2, 1.6, 1.6, 1.4, 1.5, 2.3, 1.9, 1.3} */
float scale_mod[8] = { float scale_mod[8] = {
/* text length & word wrap (base 35 apply to file browser, 1st column) */ 1, 1, 1, 1, 1, 1, 1, 1
1,
/* playlist text length when thumbnail is ON (small, base 40) */
1,
/* playlist text length when thumbnail is OFF (large, base 70) */
1,
/* sub-label length & word wrap */
1,
/* thumbnail size & vertical margin from top */
1,
/* thumbnail horizontal left margin (horizontal positioning) */
1,
/* margin before 2nd column start (shaders parameters, cheats...) */
1,
/* text length & word wrap (base 35 apply to 2nd column in cheats, shaders...) */
1
}; };
static float coord_shadow[] = { static float coord_shadow[] = {
@ -513,7 +494,7 @@ static xmb_node_t *xmb_copy_node(const xmb_node_t *old_node)
static const char *xmb_thumbnails_ident(char pos) static const char *xmb_thumbnails_ident(char pos)
{ {
char folder; char folder = 0;
settings_t *settings = config_get_ptr(); settings_t *settings = config_get_ptr();
if (pos == 'R') if (pos == 'R')
@ -598,7 +579,8 @@ static size_t xmb_list_get_size(void *data, enum menu_list_type type)
return 0; return 0;
} }
static void *xmb_list_get_entry(void *data, enum menu_list_type type, unsigned i) static void *xmb_list_get_entry(void *data,
enum menu_list_type type, unsigned i)
{ {
size_t list_size = 0; size_t list_size = 0;
xmb_handle_t *xmb = (xmb_handle_t*)data; xmb_handle_t *xmb = (xmb_handle_t*)data;
@ -1571,7 +1553,8 @@ static void xmb_list_open_new(xmb_handle_t *xmb,
xmb->old_depth = xmb->depth; xmb->old_depth = xmb->depth;
menu_entries_ctl(MENU_ENTRIES_CTL_SET_START, &skip); menu_entries_ctl(MENU_ENTRIES_CTL_SET_START, &skip);
xmb_system_tab = xmb_get_system_tab(xmb, (unsigned)xmb->categories_selection_ptr); xmb_system_tab = xmb_get_system_tab(xmb,
(unsigned)xmb->categories_selection_ptr);
if (xmb_system_tab <= XMB_SYSTEM_TAB_SETTINGS) if (xmb_system_tab <= XMB_SYSTEM_TAB_SETTINGS)
{ {
@ -1584,10 +1567,11 @@ static void xmb_list_open_new(xmb_handle_t *xmb,
} }
} }
static xmb_node_t *xmb_node_allocate_userdata(xmb_handle_t *xmb, unsigned i) static xmb_node_t *xmb_node_allocate_userdata(
xmb_handle_t *xmb, unsigned i)
{ {
xmb_node_t *tmp = NULL;
xmb_node_t *node = xmb_alloc_node(); xmb_node_t *node = xmb_alloc_node();
xmb_node_t *tmp;
if (!node) if (!node)
{ {
@ -1604,7 +1588,8 @@ static xmb_node_t *xmb_node_allocate_userdata(xmb_handle_t *xmb, unsigned i)
node->zoom = xmb->categories_active_zoom; node->zoom = xmb->categories_active_zoom;
} }
tmp = (xmb_node_t*)file_list_get_userdata_at_offset(xmb->horizontal_list, i); tmp = (xmb_node_t*)file_list_get_userdata_at_offset(
xmb->horizontal_list, i);
xmb_free_node(tmp); xmb_free_node(tmp);
file_list_set_userdata(xmb->horizontal_list, i, node); file_list_set_userdata(xmb->horizontal_list, i, node);
@ -1619,7 +1604,8 @@ static xmb_node_t* xmb_get_userdata_from_horizontal_list(
file_list_get_userdata_at_offset(xmb->horizontal_list, i); file_list_get_userdata_at_offset(xmb->horizontal_list, i);
} }
static void xmb_push_animations(xmb_node_t *node, uintptr_t tag, float ia, float ix) static void xmb_push_animations(xmb_node_t *node,
uintptr_t tag, float ia, float ix)
{ {
menu_animation_ctx_entry_t anim_entry; menu_animation_ctx_entry_t anim_entry;
@ -1654,7 +1640,8 @@ static void xmb_list_switch_old(xmb_handle_t *xmb,
last = end > 0 ? end - 1 : 0; last = end > 0 ? end - 1 : 0;
video_driver_get_size(NULL, &height); video_driver_get_size(NULL, &height);
xmb_calculate_visible_range(xmb, height, end, current, &first, &last); xmb_calculate_visible_range(xmb, height, end,
current, &first, &last);
for (i = 0; i < end; i++) for (i = 0; i < end; i++)
{ {
@ -1773,7 +1760,8 @@ static void xmb_set_title(xmb_handle_t *xmb)
if (!path) if (!path)
return; return;
fill_pathname_base_noext(xmb->title_name, path, sizeof(xmb->title_name)); fill_pathname_base_noext(
xmb->title_name, path, sizeof(xmb->title_name));
} }
} }
@ -1867,7 +1855,8 @@ static void xmb_list_switch(xmb_handle_t *xmb)
xmb_list_switch_horizontal_list(xmb); xmb_list_switch_horizontal_list(xmb);
anim_entry.duration = XMB_DELAY; anim_entry.duration = XMB_DELAY;
anim_entry.target_value = xmb->icon_spacing_horizontal * -(float)xmb->categories_selection_ptr; anim_entry.target_value = xmb->icon_spacing_horizontal
* -(float)xmb->categories_selection_ptr;
anim_entry.subject = &xmb->categories_x_pos; anim_entry.subject = &xmb->categories_x_pos;
anim_entry.easing_enum = EASING_OUT_QUAD; anim_entry.easing_enum = EASING_OUT_QUAD;
/* TODO/FIXME - integer conversion resulted in change of sign */ /* TODO/FIXME - integer conversion resulted in change of sign */
@ -2045,7 +2034,8 @@ static void xmb_context_reset_horizontal_list(
size_t list_size = size_t list_size =
xmb_list_get_size(xmb, MENU_LIST_HORIZONTAL); xmb_list_get_size(xmb, MENU_LIST_HORIZONTAL);
xmb->categories_x_pos = xmb->icon_spacing_horizontal * xmb->categories_x_pos =
xmb->icon_spacing_horizontal *
-(float)xmb->categories_selection_ptr; -(float)xmb->categories_selection_ptr;
depth = (xmb->depth > 1) ? 2 : 1; depth = (xmb->depth > 1) ? 2 : 1;
@ -2077,9 +2067,12 @@ static void xmb_context_reset_horizontal_list(
{ {
struct texture_image ti; struct texture_image ti;
char sysname[256]; char sysname[256];
char *iconpath = (char*)malloc(PATH_MAX_LENGTH * sizeof(char)); char *iconpath = (char*)
char *texturepath = (char*)malloc(PATH_MAX_LENGTH * sizeof(char)); malloc(PATH_MAX_LENGTH * sizeof(char));
char *content_texturepath = (char*)malloc(PATH_MAX_LENGTH * sizeof(char)); char *texturepath = (char*)
malloc(PATH_MAX_LENGTH * sizeof(char));
char *content_texturepath = (char*)
malloc(PATH_MAX_LENGTH * sizeof(char));
iconpath[0] = sysname[0] = iconpath[0] = sysname[0] =
texturepath[0] = content_texturepath[0] = '\0'; texturepath[0] = content_texturepath[0] = '\0';
@ -2149,7 +2142,8 @@ static void xmb_refresh_horizontal_list(xmb_handle_t *xmb)
menu_driver_ctl(RARCH_MENU_CTL_SET_PREVENT_POPULATE, NULL); menu_driver_ctl(RARCH_MENU_CTL_SET_PREVENT_POPULATE, NULL);
xmb->horizontal_list = (file_list_t*)calloc(1, sizeof(file_list_t)); xmb->horizontal_list = (file_list_t*)
calloc(1, sizeof(file_list_t));
if (xmb->horizontal_list) if (xmb->horizontal_list)
xmb_init_horizontal_list(xmb); xmb_init_horizontal_list(xmb);
@ -2338,7 +2332,8 @@ static uintptr_t xmb_icon_get_id(xmb_handle_t *xmb,
if (core_node) if (core_node)
return core_node->content_icon; return core_node->content_icon;
switch (xmb_get_system_tab(xmb, (unsigned)xmb->categories_selection_ptr)) switch (xmb_get_system_tab(xmb,
(unsigned)xmb->categories_selection_ptr))
{ {
case XMB_SYSTEM_TAB_FAVORITES: case XMB_SYSTEM_TAB_FAVORITES:
return xmb->textures.list[XMB_TEXTURE_FAVORITE]; return xmb->textures.list[XMB_TEXTURE_FAVORITE];
@ -2413,11 +2408,13 @@ static uintptr_t xmb_icon_get_id(xmb_handle_t *xmb,
#ifdef HAVE_NETWORKING #ifdef HAVE_NETWORKING
case MENU_ROOM: case MENU_ROOM:
return xmb->textures.list[XMB_TEXTURE_ROOM]; return xmb->textures.list[XMB_TEXTURE_ROOM];
/* stub these out until we have the icons #if 0
/* stub these out until we have the icons */
case MENU_ROOM_LAN: case MENU_ROOM_LAN:
return xmb->textures.list[XMB_TEXTURE_ROOM_LAN]; return xmb->textures.list[XMB_TEXTURE_ROOM_LAN];
case MENU_ROOM_MITM: case MENU_ROOM_MITM:
return xmb->textures.list[XMB_TEXTURE_ROOM_MITM]; */ return xmb->textures.list[XMB_TEXTURE_ROOM_MITM];
#endif
#endif #endif
} }
@ -2452,7 +2449,8 @@ static void xmb_calculate_visible_range(const xmb_handle_t *xmb,
{ {
for (j = current; j-- > 0; ) for (j = current; j-- > 0; )
{ {
float bottom = xmb_item_y(xmb, j, current) + base_y + xmb->icon_size; float bottom = xmb_item_y(xmb, j, current)
+ base_y + xmb->icon_size;
if (bottom < 0) if (bottom < 0)
break; break;
@ -2538,16 +2536,20 @@ static int xmb_draw_item(
} }
} }
if (string_is_equal(entry->value, msg_hash_to_str(MENU_ENUM_LABEL_DISABLED)) || if (string_is_equal(entry->value,
(string_is_equal(entry->value, msg_hash_to_str(MENU_ENUM_LABEL_VALUE_OFF)))) msg_hash_to_str(MENU_ENUM_LABEL_DISABLED)) ||
(string_is_equal(entry->value,
msg_hash_to_str(MENU_ENUM_LABEL_VALUE_OFF))))
{ {
if (xmb->textures.list[XMB_TEXTURE_SWITCH_OFF]) if (xmb->textures.list[XMB_TEXTURE_SWITCH_OFF])
texture_switch = xmb->textures.list[XMB_TEXTURE_SWITCH_OFF]; texture_switch = xmb->textures.list[XMB_TEXTURE_SWITCH_OFF];
else else
do_draw_text = true; do_draw_text = true;
} }
else if (string_is_equal(entry->value, msg_hash_to_str(MENU_ENUM_LABEL_ENABLED)) || else if (string_is_equal(entry->value,
(string_is_equal(entry->value, msg_hash_to_str(MENU_ENUM_LABEL_VALUE_ON)))) msg_hash_to_str(MENU_ENUM_LABEL_ENABLED)) ||
(string_is_equal(entry->value,
msg_hash_to_str(MENU_ENUM_LABEL_VALUE_ON))))
{ {
if (xmb->textures.list[XMB_TEXTURE_SWITCH_ON]) if (xmb->textures.list[XMB_TEXTURE_SWITCH_ON])
texture_switch = xmb->textures.list[XMB_TEXTURE_SWITCH_ON]; texture_switch = xmb->textures.list[XMB_TEXTURE_SWITCH_ON];
@ -2834,7 +2836,8 @@ static void xmb_render(void *data, bool is_idle)
video_driver_get_size(NULL, &height); video_driver_get_size(NULL, &height);
if (height) if (height)
xmb_calculate_visible_range(xmb, height, end, selection, &first, &last); xmb_calculate_visible_range(xmb, height,
end, selection, &first, &last);
for (i = first; i <= last; i++) for (i = first; i <= last; i++)
{ {
@ -3022,29 +3025,32 @@ static void xmb_draw_dark_layer(
static void xmb_frame(void *data, video_frame_info_t *video_info) static void xmb_frame(void *data, video_frame_info_t *video_info)
{ {
size_t selection;
size_t percent_width = 0;
math_matrix_4x4 mymat; math_matrix_4x4 mymat;
unsigned i; unsigned i;
float thumb_width, thumb_height, left_thumb_width, left_thumb_height;
menu_display_ctx_rotate_draw_t rotate_draw; menu_display_ctx_rotate_draw_t rotate_draw;
char msg[1024]; char msg[1024];
char title_msg[255]; char title_msg[255];
char title_truncated[255]; char title_truncated[255];
size_t selection = 0;
size_t percent_width = 0;
const int min_thumb_size = 50; const int min_thumb_size = 50;
settings_t *settings = config_get_ptr();
unsigned width = video_info->width;
unsigned height = video_info->height;
bool render_background = false; bool render_background = false;
file_list_t *selection_buf = NULL; file_list_t *selection_buf = NULL;
unsigned width = video_info->width;
unsigned height = video_info->height;
const float under_thumb_margin = 0.96;
float scale_factor = 0.0f;
float pseudo_font_length = 0.0f;
xmb_handle_t *xmb = (xmb_handle_t*)data; xmb_handle_t *xmb = (xmb_handle_t*)data;
float window_width = video_info->width; settings_t *settings = config_get_ptr();
float window_height = video_info->height;
const float around_thumb_margin = 0.96;
if (!xmb) if (!xmb)
return; return;
scale_factor = (settings->uints.menu_xmb_scale_factor * (float)width) / (1920.0 * 100);
pseudo_font_length = xmb->icon_spacing_horizontal
* 4 - xmb->icon_size / 4;
xmb->frame_count++; xmb->frame_count++;
msg[0] = '\0'; msg[0] = '\0';
@ -3073,12 +3079,13 @@ static void xmb_frame(void *data, video_frame_info_t *video_info)
selection = menu_navigation_get_selection(); selection = menu_navigation_get_selection();
strlcpy(title_truncated, xmb->title_name, sizeof(title_truncated)); strlcpy(title_truncated,
xmb->title_name, sizeof(title_truncated));
if (selection > 1) if (selection > 1)
{ {
/* skip 25 utf8 multi-byte chars */ /* skip 25 utf8 multi-byte chars */
char* end = title_truncated; char *end = title_truncated;
for(i = 0; i < 25 && *end; i++) for(i = 0; i < 25 && *end; i++)
{ {
@ -3115,71 +3122,83 @@ static void xmb_frame(void *data, video_frame_info_t *video_info)
/* Do not draw the right thumbnail if there is no space available */ /* Do not draw the right thumbnail if there is no space available */
if (((xmb->margins_screen_top + xmb->icon_size + min_thumb_size) <= height) && if (((xmb->margins_screen_top +
((xmb->margins_screen_left * scale_mod[5] + xmb->icon_spacing_horizontal + xmb->icon_size + min_thumb_size) <= height) &&
xmb->icon_spacing_horizontal * 4 - xmb->icon_size / 4 + min_thumb_size) <= width)) ((xmb->margins_screen_left * scale_mod[5] +
xmb->icon_spacing_horizontal +
pseudo_font_length + min_thumb_size) <= width))
{ {
if (xmb->savestate_thumbnail) if (xmb->savestate_thumbnail)
xmb_draw_thumbnail(video_info, xmb_draw_thumbnail(video_info,
xmb, &coord_white[0], width, height, xmb, &coord_white[0], width, height,
xmb->margins_screen_left * scale_mod[5] xmb->margins_screen_left * scale_mod[5]
+ xmb->icon_spacing_horizontal + + xmb->icon_spacing_horizontal + pseudo_font_length,
xmb->icon_spacing_horizontal * 4 - xmb->icon_size / 4, xmb->margins_screen_top + xmb->icon_size
xmb->margins_screen_top + xmb->icon_size + xmb->savestate_thumbnail_height * scale_mod[4], + xmb->savestate_thumbnail_height * scale_mod[4],
xmb->savestate_thumbnail_width, xmb->savestate_thumbnail_height * scale_mod[4], xmb->savestate_thumbnail_width * scale_mod[4],
xmb->savestate_thumbnail_height * scale_mod[4],
xmb->savestate_thumbnail); xmb->savestate_thumbnail);
else if (xmb->thumbnail else if (xmb->thumbnail
&& !string_is_equal(xmb_thumbnails_ident('R'), && !string_is_equal(xmb_thumbnails_ident('R'),
msg_hash_to_str(MENU_ENUM_LABEL_VALUE_OFF))) msg_hash_to_str(MENU_ENUM_LABEL_VALUE_OFF)))
{ {
#ifdef XMB_DEBUG
RARCH_LOG("[XMB thumbnail] width: %.2f, height: %.2f\n", xmb->thumbnail_width, xmb->thumbnail_height); /* Limit thumbnail width */
float thumb_width = 0.0f;
float thumb_height = 0.0f;
float thumb_max_width = (float)width - (xmb->icon_size / 6)
- (xmb->margins_screen_left * scale_mod[5]) -
xmb->icon_spacing_horizontal - pseudo_font_length;
#ifdef XMB_DEBUG
RARCH_LOG("[XMB thumbnail] width: %.2f, height: %.2f\n",
xmb->thumbnail_width, xmb->thumbnail_height);
RARCH_LOG("[XMB thumbnail] w: %.2f, h: %.2f\n", width, height); RARCH_LOG("[XMB thumbnail] w: %.2f, h: %.2f\n", width, height);
#endif #endif
if (xmb->thumbnail_width * scale_mod[4] > thumb_max_width)
{
thumb_width = (xmb->thumbnail_width * scale_mod[4]) *
(thumb_max_width / (xmb->thumbnail_width * scale_mod[4]));
thumb_height = (xmb->thumbnail_height * scale_mod[4]) *
(thumb_max_width / (xmb->thumbnail_width * scale_mod[4]));
}
else
{
thumb_width = xmb->thumbnail_width * scale_mod[4];
thumb_height = xmb->thumbnail_height * scale_mod[4];
}
/* Limit thumbnail height to screen height + margin. */ /* Limit thumbnail height to screen height + margin. */
thumb_width = xmb->thumbnail_width; if (xmb->margins_screen_top + xmb->icon_size + thumb_height >=
thumb_height = xmb->thumbnail_height; ((float)height * under_thumb_margin))
if (xmb->margins_screen_top + xmb->icon_size + xmb->thumbnail_height * scale_mod[4] >=
(window_height * around_thumb_margin))
{ {
thumb_width = thumb_width * thumb_width = thumb_width *
(((window_height * around_thumb_margin) - xmb->margins_screen_top - xmb->icon_size) / ((((float)height * under_thumb_margin) -
(thumb_height * scale_mod[4])); xmb->margins_screen_top - xmb->icon_size) /
thumb_height);
thumb_height = thumb_height * thumb_height = thumb_height *
(((window_height * around_thumb_margin) - xmb->margins_screen_top - xmb->icon_size) / ((((float)height * under_thumb_margin) -
(thumb_height * scale_mod[4])); xmb->margins_screen_top - xmb->icon_size) /
} thumb_height);
/* Limit thumbnail width */
if (xmb->margins_screen_left * scale_mod[5] + xmb->icon_spacing_horizontal +
xmb->icon_spacing_horizontal*4 - xmb->icon_size / 4 + thumb_width * scale_mod[4] >=
(window_width * around_thumb_margin))
{
thumb_height = thumb_height *
(((window_width * around_thumb_margin) - xmb->margins_screen_left * scale_mod[5] - xmb->icon_spacing_horizontal -
xmb->icon_spacing_horizontal * 4 + xmb->icon_size / 4) / (thumb_width * scale_mod[4]));
thumb_width = thumb_width *
(((window_width * around_thumb_margin) - xmb->margins_screen_left * scale_mod[5] - xmb->icon_spacing_horizontal -
xmb->icon_spacing_horizontal * 4 + xmb->icon_size / 4) / (thumb_width * scale_mod[4]));
} }
xmb_draw_thumbnail(video_info, xmb_draw_thumbnail(video_info,
xmb, &coord_white[0], width, height, xmb, &coord_white[0], width, height,
xmb->margins_screen_left * scale_mod[5] + xmb->icon_spacing_horizontal + (float)width - (xmb->icon_size / 6) - thumb_max_width +
xmb->icon_spacing_horizontal*4 - xmb->icon_size / 4, ((thumb_max_width - thumb_width) / 2),
xmb->margins_screen_top + xmb->icon_size + thumb_height * scale_mod[4], xmb->margins_screen_top + xmb->icon_size + thumb_height,
thumb_width * scale_mod[4], thumb_height * scale_mod[4], thumb_width, thumb_height,
xmb->thumbnail); xmb->thumbnail);
} }
} }
/* Do not draw the left thumbnail if there is no space available */ /* Do not draw the left thumbnail if there is no space available */
if ((xmb->margins_screen_top + xmb->icon_size * (!(xmb->depth == 1)? 2.1 : 1) + min_thumb_size) <= window_height) if ((xmb->margins_screen_top + xmb->icon_size *
(!(xmb->depth == 1)? 2.1 : 1) + min_thumb_size)
<= (float)height)
{ {
/* Left Thumbnail */ /* Left Thumbnail */
@ -3187,19 +3206,24 @@ static void xmb_frame(void *data, video_frame_info_t *video_info)
&& !string_is_equal(xmb_thumbnails_ident('L'), && !string_is_equal(xmb_thumbnails_ident('L'),
msg_hash_to_str(MENU_ENUM_LABEL_VALUE_OFF))) msg_hash_to_str(MENU_ENUM_LABEL_VALUE_OFF)))
{ {
float scale_factor = (settings->uints.menu_xmb_scale_factor * width) / (1920.0 * 100); float left_thumb_width = 0.0f;
float left_thumb_height = 0.0f;
/* Limit left thumbnail height to screen height + margin. */ /* Limit left thumbnail height to screen height + margin. */
if (xmb->margins_screen_top + xmb->icon_size * (!(xmb->depth == 1)? 2.1 : 1) + if (xmb->margins_screen_top + xmb->icon_size *
xmb->left_thumbnail_height >= (float)(height - (96.0 * scale_factor))) (!(xmb->depth == 1)? 2.1 : 1) +
xmb->left_thumbnail_height >=
((float)height - (96.0 * scale_factor)))
{ {
left_thumb_width = xmb->left_thumbnail_width * left_thumb_width = xmb->left_thumbnail_width *
(((float)(height - (96.0 * scale_factor)) - xmb->margins_screen_top - ((((float)height - (96.0 * scale_factor))
- xmb->margins_screen_top -
(xmb->icon_size * (!(xmb->depth == 1)? 2.1 : 1))) / (xmb->icon_size * (!(xmb->depth == 1)? 2.1 : 1))) /
xmb->left_thumbnail_height); xmb->left_thumbnail_height);
left_thumb_height = xmb->left_thumbnail_height * left_thumb_height = xmb->left_thumbnail_height *
(((float)(height - (96.0 * scale_factor)) - xmb->margins_screen_top - ((((float)height - (96.0 * scale_factor))
- xmb->margins_screen_top -
(xmb->icon_size * (!(xmb->depth == 1)? 2.1 : 1))) / (xmb->icon_size * (!(xmb->depth == 1)? 2.1 : 1))) /
xmb->left_thumbnail_height); xmb->left_thumbnail_height);
} }
@ -3211,12 +3235,15 @@ static void xmb_frame(void *data, video_frame_info_t *video_info)
xmb_draw_thumbnail(video_info, xmb_draw_thumbnail(video_info,
xmb, &coord_white[0], width, height, xmb, &coord_white[0], width, height,
20 * scale_factor + ((xmb->left_thumbnail_width - left_thumb_width) / 2), (xmb->icon_size / 6) +
xmb->margins_screen_top + xmb->icon_size * (!(xmb->depth == 1)? 2.1 : 1) + left_thumb_height, ((xmb->left_thumbnail_width - left_thumb_width) / 2),
xmb->margins_screen_top + xmb->icon_size *
(!(xmb->depth == 1)? 2.1 : 1) + left_thumb_height,
left_thumb_width, left_thumb_height, left_thumb_width, left_thumb_height,
xmb->left_thumbnail); xmb->left_thumbnail);
} }
} }
/* Clock image */ /* Clock image */
menu_display_set_alpha(coord_white, MIN(xmb->alpha, 1.00f)); menu_display_set_alpha(coord_white, MIN(xmb->alpha, 1.00f));
@ -3263,7 +3290,9 @@ static void xmb_frame(void *data, video_frame_info_t *video_info)
snprintf(msg, sizeof(msg), "%d%%", percent); snprintf(msg, sizeof(msg), "%d%%", percent);
percent_width = (unsigned)font_driver_get_message_width(xmb->font, msg, (unsigned)strlen(msg), 1); percent_width = (unsigned)
font_driver_get_message_width(
xmb->font, msg, (unsigned)strlen(msg), 1);
xmb_draw_text(video_info, xmb, msg, xmb_draw_text(video_info, xmb, msg,
width - xmb->margins_title_left - x_pos, width - xmb->margins_title_left - x_pos,
@ -3318,7 +3347,8 @@ static void xmb_frame(void *data, video_frame_info_t *video_info)
} }
/* Arrow image */ /* Arrow image */
menu_display_set_alpha(coord_white, MIN(xmb->textures_arrow_alpha, xmb->alpha)); menu_display_set_alpha(coord_white,
MIN(xmb->textures_arrow_alpha, xmb->alpha));
if (coord_white[3] != 0) if (coord_white[3] != 0)
xmb_draw_icon(video_info, xmb_draw_icon(video_info,
@ -3326,7 +3356,8 @@ static void xmb_frame(void *data, video_frame_info_t *video_info)
&mymat, &mymat,
xmb->textures.list[XMB_TEXTURE_ARROW], xmb->textures.list[XMB_TEXTURE_ARROW],
xmb->x + xmb->margins_screen_left + xmb->x + xmb->margins_screen_left +
xmb->icon_spacing_horizontal - xmb->icon_size / 2.0 + xmb->icon_size, xmb->icon_spacing_horizontal -
xmb->icon_size / 2.0 + xmb->icon_size,
xmb->margins_screen_top + xmb->margins_screen_top +
xmb->icon_size / 2.0 + xmb->icon_spacing_vertical xmb->icon_size / 2.0 + xmb->icon_spacing_vertical
* xmb->active_item_factor, * xmb->active_item_factor,
@ -3358,8 +3389,10 @@ static void xmb_frame(void *data, video_frame_info_t *video_info)
uintptr_t texture = node->icon; uintptr_t texture = node->icon;
float x = xmb->x + xmb->categories_x_pos + float x = xmb->x + xmb->categories_x_pos +
xmb->margins_screen_left + xmb->margins_screen_left +
xmb->icon_spacing_horizontal * (i + 1) - xmb->icon_size / 2.0; xmb->icon_spacing_horizontal
float y = xmb->margins_screen_top + xmb->icon_size / 2.0; * (i + 1) - xmb->icon_size / 2.0;
float y = xmb->margins_screen_top
+ xmb->icon_size / 2.0;
float rotation = 0; float rotation = 0;
float scale_factor = node->zoom; float scale_factor = node->zoom;
@ -3398,7 +3431,8 @@ static void xmb_frame(void *data, video_frame_info_t *video_info)
xmb->selection_buf_old, xmb->selection_buf_old,
xmb->selection_ptr_old, xmb->selection_ptr_old,
(xmb_list_get_size(xmb, MENU_LIST_PLAIN) > 1) (xmb_list_get_size(xmb, MENU_LIST_PLAIN) > 1)
? xmb->categories_selection_ptr : xmb->categories_selection_ptr_old, ? xmb->categories_selection_ptr :
xmb->categories_selection_ptr_old,
&item_color[0], &item_color[0],
width, width,
height); height);
@ -3497,7 +3531,7 @@ static void xmb_layout_ps3(xmb_handle_t *xmb, int width)
new_header_height = 128.0 * scale_factor; new_header_height = 128.0 * scale_factor;
xmb->thumbnail_width = 460.0 * scale_factor; xmb->thumbnail_width = 1024.0 * scale_factor;
xmb->left_thumbnail_width = 430.0 * scale_factor; xmb->left_thumbnail_width = 430.0 * scale_factor;
xmb->savestate_thumbnail_width= 460.0 * scale_factor; xmb->savestate_thumbnail_width= 460.0 * scale_factor;
xmb->cursor_size = 64.0 * scale_factor; xmb->cursor_size = 64.0 * scale_factor;
@ -3546,9 +3580,9 @@ static void xmb_layout_psp(xmb_handle_t *xmb, int width)
settings_t *settings = config_get_ptr(); settings_t *settings = config_get_ptr();
float scale_factor = float scale_factor =
((settings->uints.menu_xmb_scale_factor * width) / (1920.0 * 100)) * 1.5; ((settings->uints.menu_xmb_scale_factor * width) / (1920.0 * 100)) * 1.5;
#ifdef _3DS #ifdef _3DS
scale_factor = settings->uints.menu_xmb_scale_factor / 400.0; scale_factor =
settings->uints.menu_xmb_scale_factor / 400.0;
#endif #endif
xmb->above_subitem_offset = 1.5; xmb->above_subitem_offset = 1.5;
@ -3731,16 +3765,27 @@ static void *xmb_init(void **userdata, bool video_is_threaded)
menu_handle_t *menu = (menu_handle_t*)calloc(1, sizeof(*menu)); menu_handle_t *menu = (menu_handle_t*)calloc(1, sizeof(*menu));
float scale_value = settings->uints.menu_xmb_scale_factor; float scale_value = settings->uints.menu_xmb_scale_factor;
/* scaling multiplier formulas made from these values: */
/* xmb_scale 50 = {2.5, 2.5, 2, 1.7, 2.5, 4, 2.4, 2.5} */
/* xmb_scale 75 = { 2, 1.6, 1.6, 1.4, 1.5, 2.3, 1.9, 1.3} */
if (scale_value < 100) if (scale_value < 100)
{ {
scale_mod[0] = -0.03 * scale_value + 4.083333; /* text length & word wrap (base 35 apply to file browser, 1st column) */
scale_mod[0] = -0.03 * scale_value + 4.083;
/* playlist text length when thumbnail is ON (small, base 40) */
scale_mod[1] = -0.03 * scale_value + 3.95; scale_mod[1] = -0.03 * scale_value + 3.95;
scale_mod[2] = -0.02 * scale_value + 3.033333; /* playlist text length when thumbnail is OFF (large, base 70) */
scale_mod[3] = -0.014 * scale_value + 2.416667; scale_mod[2] = -0.02 * scale_value + 3.033;
scale_mod[4] = -0.03 * scale_value + 3.916667; /* sub-label length & word wrap */
scale_mod[5] = -0.06 * scale_value + 6.933333; scale_mod[3] = -0.014 * scale_value + 2.416;
scale_mod[6] = -0.028 * scale_value + 3.866667; /* thumbnail size & vertical margin from top */
scale_mod[7] = 134.179 * pow(scale_value, -1.077852); scale_mod[4] = -0.03 * scale_value + 3.916;
/* thumbnail horizontal left margin (horizontal positioning) */
scale_mod[5] = -0.06 * scale_value + 6.933;
/* margin before 2nd column start (shaders parameters, cheats...) */
scale_mod[6] = -0.028 * scale_value + 3.866;
/* text length & word wrap (base 35 apply to 2nd column in cheats, shaders, etc) */
scale_mod[7] = 134.179 * pow(scale_value, -1.0778);
for (i = 0; i < 8; i++) for (i = 0; i < 8; i++)
if (scale_mod[i] < 1) if (scale_mod[i] < 1)

View File

@ -3282,12 +3282,15 @@ static int menu_displaylist_parse_options_remappings(
{ {
for (retro_id = 0; retro_id < RARCH_FIRST_CUSTOM_BIND; retro_id++) for (retro_id = 0; retro_id < RARCH_FIRST_CUSTOM_BIND; retro_id++)
{ {
unsigned user = settings->uints.keymapper_port + 1;
unsigned desc_offset = retro_id;
char descriptor[255]; char descriptor[255];
const struct retro_keybind *keybind = &input_config_binds[settings->uints.keymapper_port][retro_id]; const struct retro_keybind *auto_bind = NULL;
const struct retro_keybind *auto_bind = (const struct retro_keybind*) const struct retro_keybind *keybind = NULL;
input_config_get_bind_auto(settings->uints.keymapper_port, retro_id);
descriptor[0] = '\0'; keybind = &input_config_binds[settings->uints.keymapper_port][retro_id];
auto_bind = (const struct retro_keybind*)
input_config_get_bind_auto(settings->uints.keymapper_port, retro_id);
input_config_get_bind_string(descriptor, input_config_get_bind_string(descriptor,
keybind, auto_bind, sizeof(descriptor)); keybind, auto_bind, sizeof(descriptor));

View File

@ -542,16 +542,23 @@ void menu_display_unset_framebuffer_dirty_flag(void)
* RGUI or XMB use this. */ * RGUI or XMB use this. */
float menu_display_get_dpi(void) float menu_display_get_dpi(void)
{ {
settings_t *settings = config_get_ptr();
float dpi;
unsigned width, height; unsigned width, height;
settings_t *settings = config_get_ptr();
float dpi = 0.0f;
float diagonal = 6.5f;
video_driver_get_size(&width, &height); video_driver_get_size(&width, &height);
if (!settings) if (!settings)
return true; return true;
dpi = sqrt((width * width) + (height * height)) / 6.5; #ifdef RARCH_MOBILE
diagonal = 5.0f;
#endif
/* Generic dpi calculation formula,
* the divider is the screen diagonal in inches */
dpi = sqrt((width * width) + (height * height)) / diagonal;
if (settings->bools.menu_dpi_override_enable) if (settings->bools.menu_dpi_override_enable)
return settings->uints.menu_dpi_override_value; return settings->uints.menu_dpi_override_value;

View File

@ -67,7 +67,7 @@ else
DEFINES += -DHAVE_OPENGLES2 DEFINES += -DHAVE_OPENGLES2
endif endif
DEFINES += -DRARCH_MOBILE -DHAVE_GRIFFIN -DHAVE_STB_VORBIS -DHAVE_LANGEXTRA -DANDROID -DHAVE_DYNAMIC -DHAVE_OPENGL -DHAVE_OVERLAY -DHAVE_OPENGLES -DGLSL_DEBUG -DHAVE_DYLIB -DHAVE_EGL -DHAVE_GLSL -DHAVE_MENU -DHAVE_RGUI -DHAVE_ZLIB -DHAVE_RPNG -DHAVE_RJPEG -DHAVE_RBMP -DHAVE_RTGA -DINLINE=inline -DHAVE_THREADS -D__LIBRETRO__ -DHAVE_RSOUND -DHAVE_NETWORKGAMEPAD -DHAVE_NETWORKING -DRARCH_INTERNAL -DHAVE_FILTERS_BUILTIN -DHAVE_MATERIALUI -DHAVE_XMB -DHAVE_SHADERPIPELINE -DHAVE_LIBRETRODB -DHAVE_STB_FONT -DHAVE_IMAGEVIEWER -DHAVE_UPDATE_ASSETS -DHAVE_CC_RESAMPLER -DHAVE_MINIUPNPC -DHAVE_BUILTINMINIUPNPC -DMINIUPNPC_SET_SOCKET_TIMEOUT -DMINIUPNPC_GET_SRC_ADDR -DHAVE_KEYMAPPER -DHAVE_NETWORKGAMEPAD -DHAVE_FLAC -DHAVE_CHD DEFINES += -DRARCH_MOBILE -DHAVE_GRIFFIN -DHAVE_STB_VORBIS -DHAVE_LANGEXTRA -DANDROID -DHAVE_DYNAMIC -DHAVE_OPENGL -DHAVE_OVERLAY -DHAVE_OPENGLES -DGLSL_DEBUG -DHAVE_DYLIB -DHAVE_EGL -DHAVE_GLSL -DHAVE_MENU -DHAVE_RGUI -DHAVE_ZLIB -DHAVE_RPNG -DHAVE_RJPEG -DHAVE_RBMP -DHAVE_RTGA -DINLINE=inline -DHAVE_THREADS -D__LIBRETRO__ -DHAVE_RSOUND -DHAVE_NETWORKGAMEPAD -DHAVE_NETWORKING -DRARCH_INTERNAL -DHAVE_FILTERS_BUILTIN -DHAVE_MATERIALUI -DHAVE_XMB -DHAVE_SHADERPIPELINE -DHAVE_LIBRETRODB -DHAVE_STB_FONT -DHAVE_IMAGEVIEWER -DHAVE_UPDATE_ASSETS -DHAVE_CC_RESAMPLER -DHAVE_MINIUPNPC -DHAVE_BUILTINMINIUPNPC -DMINIUPNPC_SET_SOCKET_TIMEOUT -DMINIUPNPC_GET_SRC_ADDR -DHAVE_KEYMAPPER -DHAVE_NETWORKGAMEPAD -DHAVE_FLAC -DHAVE_CHD -DHAVE_RUNAHEAD
DEFINES += -DWANT_IFADDRS DEFINES += -DWANT_IFADDRS
ifeq ($(HAVE_VULKAN),1) ifeq ($(HAVE_VULKAN),1)

View File

@ -332,6 +332,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -417,6 +418,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -469,6 +471,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -555,6 +558,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -625,6 +629,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",

View File

@ -332,6 +332,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -418,6 +419,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -471,6 +473,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -558,6 +561,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -628,6 +632,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",

View File

@ -344,6 +344,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -425,6 +426,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -473,6 +475,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -554,6 +557,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -623,6 +627,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",

View File

@ -347,6 +347,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -416,6 +417,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -490,6 +492,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -574,6 +577,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -625,6 +629,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",

View File

@ -362,6 +362,7 @@
"-DHAVE_CORETEXT", "-DHAVE_CORETEXT",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -445,6 +446,7 @@
"-DHAVE_CORETEXT", "-DHAVE_CORETEXT",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -495,6 +497,7 @@
"-DHAVE_CORETEXT", "-DHAVE_CORETEXT",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -580,6 +583,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",
@ -649,6 +653,7 @@
"-DHAVE_HID", "-DHAVE_HID",
"-DHAVE_NETWORKING", "-DHAVE_NETWORKING",
"-DHAVE_AVFOUNDATION", "-DHAVE_AVFOUNDATION",
"-DHAVE_RUNAHEAD",
"-DHAVE_GRIFFIN", "-DHAVE_GRIFFIN",
"-DHAVE_STB_VORBIS", "-DHAVE_STB_VORBIS",
"-DHAVE_MINIUPNPC", "-DHAVE_MINIUPNPC",

View File

@ -23,6 +23,10 @@ static void runahead_suspend_audio(void);
static void runahead_resume_audio(void); static void runahead_resume_audio(void);
static void runahead_suspend_video(void); static void runahead_suspend_video(void);
static void runahead_resume_video(void); static void runahead_resume_video(void);
static void set_fast_savestate(void);
static void unset_fast_savestate(void);
static void set_hard_disable_audio(void);
static void unset_hard_disable_audio(void);
static size_t runahead_save_state_size = -1; static size_t runahead_save_state_size = -1;
@ -92,8 +96,7 @@ static void runahead_save_state_list_rotate(void)
static function_t originalRetroDeinit = NULL; static function_t originalRetroDeinit = NULL;
static function_t originalRetroUnload = NULL; static function_t originalRetroUnload = NULL;
typedef struct retro_core_t _retro_core_t; extern struct retro_core_t current_core;
extern _retro_core_t current_core;
extern struct retro_callbacks retro_ctx; extern struct retro_callbacks retro_ctx;
static void remove_hooks(void) static void remove_hooks(void)
@ -109,6 +112,7 @@ static void remove_hooks(void)
current_core.retro_unload_game = originalRetroUnload; current_core.retro_unload_game = originalRetroUnload;
originalRetroUnload = NULL; originalRetroUnload = NULL;
} }
current_core.retro_set_environment(rarch_environment_cb);
remove_input_state_hook(); remove_input_state_hook();
} }
@ -131,6 +135,18 @@ static void deinit_hook(void)
current_core.retro_deinit(); current_core.retro_deinit();
} }
static bool env_hook(unsigned cmd, void *data)
{
bool result = rarch_environment_cb(cmd, data);
if (cmd == RETRO_ENVIRONMENT_GET_VARIABLE_UPDATE && result)
{
bool *bool_p = (bool*)data;
if (*bool_p == true)
secondary_core_set_variable_update();
}
return result;
}
static void add_hooks(void) static void add_hooks(void)
{ {
if (!originalRetroDeinit) if (!originalRetroDeinit)
@ -144,7 +160,7 @@ static void add_hooks(void)
originalRetroUnload = current_core.retro_unload_game; originalRetroUnload = current_core.retro_unload_game;
current_core.retro_unload_game = unload_hook; current_core.retro_unload_game = unload_hook;
} }
current_core.retro_set_environment(env_hook);
add_input_state_hook(); add_input_state_hook();
} }
@ -274,7 +290,9 @@ void run_ahead(int runAheadCount, bool useSecondary)
{ {
runahead_suspend_video(); runahead_suspend_video();
runahead_suspend_audio(); runahead_suspend_audio();
set_hard_disable_audio();
okay = runahead_run_secondary(); okay = runahead_run_secondary();
unset_hard_disable_audio();
runahead_resume_audio(); runahead_resume_audio();
runahead_resume_video(); runahead_resume_video();
@ -285,7 +303,9 @@ void run_ahead(int runAheadCount, bool useSecondary)
} }
} }
runahead_suspend_audio(); runahead_suspend_audio();
set_hard_disable_audio();
okay = runahead_run_secondary(); okay = runahead_run_secondary();
unset_hard_disable_audio();
runahead_resume_audio(); runahead_resume_audio();
/* Could not create a secondary core. RunAhead /* Could not create a secondary core. RunAhead
@ -330,8 +350,10 @@ static bool runahead_save_state(void)
{ {
retro_ctx_serialize_info_t *serialize_info = retro_ctx_serialize_info_t *serialize_info =
(retro_ctx_serialize_info_t*)runahead_save_state_list->data[0]; (retro_ctx_serialize_info_t*)runahead_save_state_list->data[0];
bool okay = core_serialize(serialize_info); bool okay;
set_fast_savestate();
okay = core_serialize(serialize_info);
unset_fast_savestate();
if (!okay) if (!okay)
runahead_error(); runahead_error();
return okay; return okay;
@ -342,7 +364,12 @@ static bool runahead_load_state(void)
retro_ctx_serialize_info_t *serialize_info = (retro_ctx_serialize_info_t*) retro_ctx_serialize_info_t *serialize_info = (retro_ctx_serialize_info_t*)
runahead_save_state_list->data[0]; runahead_save_state_list->data[0];
bool lastDirty = input_is_dirty; bool lastDirty = input_is_dirty;
bool okay = core_unserialize(serialize_info); bool okay;
set_fast_savestate();
/* calling core_unserialize has side effects with netplay (it triggers transmitting your save state)
call retro_unserialize directly from the core instead */
okay = current_core.retro_unserialize(serialize_info->data_const, serialize_info->size);
unset_fast_savestate();
input_is_dirty = lastDirty; input_is_dirty = lastDirty;
if (!okay) if (!okay)
@ -355,7 +382,10 @@ static bool runahead_load_state_secondary(void)
{ {
retro_ctx_serialize_info_t *serialize_info = retro_ctx_serialize_info_t *serialize_info =
(retro_ctx_serialize_info_t*)runahead_save_state_list->data[0]; (retro_ctx_serialize_info_t*)runahead_save_state_list->data[0];
bool okay = secondary_core_deserialize(serialize_info->data_const, serialize_info->size); bool okay;
set_fast_savestate();
okay = secondary_core_deserialize(serialize_info->data_const, serialize_info->size);
unset_fast_savestate();
if (!okay) if (!okay)
runahead_secondary_core_available = false; runahead_secondary_core_available = false;
@ -400,3 +430,37 @@ void runahead_destroy(void)
remove_hooks(); remove_hooks();
runahead_clear_variables(); runahead_clear_variables();
} }
static bool request_fast_savestate;
static bool hard_disable_audio;
bool want_fast_savestate(void)
{
return request_fast_savestate;
}
static void set_fast_savestate(void)
{
request_fast_savestate = true;
}
static void unset_fast_savestate(void)
{
request_fast_savestate = false;
}
bool get_hard_disable_audio(void)
{
return hard_disable_audio;
}
static void set_hard_disable_audio(void)
{
hard_disable_audio = true;
}
static void unset_hard_disable_audio(void)
{
hard_disable_audio = false;
}

View File

@ -10,6 +10,9 @@ void runahead_destroy(void);
void run_ahead(int runAheadCount, bool useSecondary); void run_ahead(int runAheadCount, bool useSecondary);
bool want_fast_savestate(void);
bool get_hard_disable_audio(void);
RETRO_END_DECLS RETRO_END_DECLS
#endif #endif

View File

@ -22,6 +22,8 @@
#include "../paths.h" #include "../paths.h"
#include "../content.h" #include "../content.h"
#include "secondary_core.h"
static int port_map[16]; static int port_map[16];
static char *secondary_library_path; static char *secondary_library_path;
@ -46,6 +48,8 @@ bool secondary_core_run_no_input_polling(void);
bool secondary_core_deserialize(const void *buffer, int size); bool secondary_core_deserialize(const void *buffer, int size);
static bool rarch_environment_secondary_core_hook(unsigned cmd, void *data);
void secondary_core_destroy(void); void secondary_core_destroy(void);
void set_last_core_type(enum rarch_core_type type); void set_last_core_type(enum rarch_core_type type);
@ -205,7 +209,8 @@ bool secondary_core_create(void)
secondary_core.retro_set_audio_sample_batch(secondary_callbacks.sample_batch_cb); secondary_core.retro_set_audio_sample_batch(secondary_callbacks.sample_batch_cb);
secondary_core.retro_set_input_state(secondary_callbacks.state_cb); secondary_core.retro_set_input_state(secondary_callbacks.state_cb);
secondary_core.retro_set_input_poll(secondary_callbacks.poll_cb); secondary_core.retro_set_input_poll(secondary_callbacks.poll_cb);
secondary_core.retro_set_environment(rarch_environment_cb); secondary_core.retro_set_environment(rarch_environment_secondary_core_hook);
secondary_core_set_variable_update();
secondary_core.retro_init(); secondary_core.retro_init();
@ -269,6 +274,26 @@ bool secondary_core_create(void)
return true; return true;
} }
static bool has_variable_update;
static bool rarch_environment_secondary_core_hook(unsigned cmd, void *data)
{
bool result = rarch_environment_cb(cmd, data);
if (cmd == RETRO_ENVIRONMENT_GET_VARIABLE_UPDATE && has_variable_update)
{
bool *bool_p = (bool*)data;
*bool_p = true;
has_variable_update = false;
return true;
}
return result;
}
void secondary_core_set_variable_update(void)
{
has_variable_update = true;
}
bool secondary_core_run_no_input_polling(void) bool secondary_core_run_no_input_polling(void)
{ {
if (!secondary_module) if (!secondary_module)
@ -350,5 +375,10 @@ void remember_controller_port_device(long port, long device)
{ {
/* do nothing */ /* do nothing */
} }
void secondary_core_set_variable_update(void)
{
/* do nothing */
}
#endif #endif

View File

@ -14,6 +14,7 @@ void secondary_core_destroy(void);
void set_last_core_type(enum rarch_core_type type); void set_last_core_type(enum rarch_core_type type);
void remember_controller_port_device(long port, long device); void remember_controller_port_device(long port, long device);
void clear_controller_port_map(void); void clear_controller_port_map(void);
void secondary_core_set_variable_update(void);
RETRO_END_DECLS RETRO_END_DECLS