diff --git a/config.def.h b/config.def.h index 97194edb2e..060fd76109 100644 --- a/config.def.h +++ b/config.def.h @@ -92,6 +92,9 @@ enum CAMERA_IOS, CAMERA_NULL, + LOCATION_ANDROID, + LOCATION_APPLE, + OSK_PS3, OSK_NULL, }; @@ -206,6 +209,12 @@ enum #define CAMERA_DEFAULT_DRIVER CAMERA_NULL #endif +#if defined(ANDROID) +#define LOCATION_DEFAULT_DRIVER LOCATION_ANDROID +#elif defined(IOS) || defined(OSX) +#define LOCATION_DEFAULT_DRIVER LOCATION_APPLE +#endif + #if defined(__CELLOS_LV2__) #define OSK_DEFAULT_DRIVER OSK_PS3 #else diff --git a/driver.c b/driver.c index 6048bd8299..c432d18619 100644 --- a/driver.c +++ b/driver.c @@ -298,6 +298,60 @@ void find_next_camera_driver(void) } #endif +#ifdef HAVE_LOCATION +static const location_driver_t *location_drivers[] = { +#ifdef ANDROID +#endif +#ifdef IOS +#endif + NULL, +}; + +static int find_location_driver_index(const char *driver) +{ + unsigned i; + for (i = 0; location_drivers[i]; i++) + if (strcasecmp(driver, location_drivers[i]->ident) == 0) + return i; + return -1; +} + +static void find_location_driver(void) +{ + int i = find_location_driver_index(g_settings.location.driver); + if (i >= 0) + driver.location = location_drivers[i]; + else + { + unsigned d; + RARCH_ERR("Couldn't find any location driver named \"%s\"\n", g_settings.location.driver); + RARCH_LOG_OUTPUT("Available location drivers are:\n"); + for (d = 0; location_drivers[d]; d++) + RARCH_LOG_OUTPUT("\t%s\n", location_drivers[d]->ident); + + rarch_fail(1, "find_location_driver()"); + } +} + +void find_prev_location_driver(void) +{ + int i = find_location_driver_index(g_settings.location.driver); + if (i > 0) + strlcpy(g_settings.location.driver, location_drivers[i - 1]->ident, sizeof(g_settings.location.driver)); + else + RARCH_WARN("Couldn't find any previous location driver (current one: \"%s\").\n", g_settings.location.driver); +} + +void find_next_location_driver(void) +{ + int i = find_location_driver_index(g_settings.location.driver); + if (i >= 0 && location_drivers[i + 1]) + strlcpy(g_settings.location.driver, location_drivers[i + 1]->ident, sizeof(g_settings.location.driver)); + else + RARCH_WARN("Couldn't find any next location driver (current one: \"%s\").\n", g_settings.location.driver); +} +#endif + static int find_audio_driver_index(const char *driver) { unsigned i; @@ -449,6 +503,9 @@ void init_drivers_pre(void) #ifdef HAVE_CAMERA find_camera_driver(); #endif +#ifdef HAVE_LOCATION + find_location_driver(); +#endif #ifdef HAVE_OSK find_osk_driver(); #endif @@ -568,6 +625,22 @@ void driver_camera_poll(void) } #endif +#ifdef HAVE_LOCATION +bool driver_location_start(void) +{ + if (driver.location && driver.location_data) + return driver.location->start(driver.location_data); + else + return false; +} + +void driver_location_stop(void) +{ + if (driver.location && driver.location_data) + driver.location->stop(driver.location_data); +} +#endif + uintptr_t driver_get_current_framebuffer(void) { #ifdef HAVE_FBO @@ -630,6 +703,14 @@ void global_uninit_drivers(void) } #endif +#ifdef HAVE_LOCATION + if (driver.location && driver.location_data) + { + driver.location->free(driver.camera_data); + driver.location_data = NULL; + } +#endif + #ifdef HAVE_OSK if (driver.osk && driver.osk_data) { @@ -665,6 +746,25 @@ void init_camera(void) } #endif +#ifdef HAVE_LOCATION +void init_location(void) +{ + // Resource leaks will follow if location interface is initialized twice. + if (driver.camera_data) + return; + + find_location_driver(); + + driver.location_data = location_init_func(g_settings.location.update_interval_ms, g_settings.location.update_interval_distance); + + if (!driver.location_data) + { + RARCH_ERR("Failed to initialize location driver. Will continue without location.\n"); + g_extern.location_active = false; + } +} +#endif + #ifdef HAVE_OSK void init_osk(void) { @@ -693,6 +793,9 @@ void init_drivers(void) #ifdef HAVE_CAMERA driver.camera_data_own = !driver.camera_data; #endif +#ifdef HAVE_LOCATION + driver.location_data_own = !driver.location_data; +#endif #ifdef HAVE_OSK driver.osk_data_own = !driver.osk_data; #endif @@ -714,6 +817,13 @@ void init_drivers(void) init_camera(); #endif +#ifdef HAVE_LOCATION + // FIXME + // Only init location driver if we're ever going to use it. + //if (g_extern.system.camera_callback.caps) + init_location(); +#endif + #ifdef HAVE_OSK init_osk(); #endif @@ -737,6 +847,14 @@ void uninit_camera(void) } #endif +#ifdef HAVE_LOCATION +void uninit_location(void) +{ + if (driver.location_data && driver.location) + driver.location->free(driver.location_data); +} +#endif + #ifdef HAVE_OSK void uninit_osk(void) { @@ -760,6 +878,14 @@ void uninit_drivers(void) if (driver.camera_data_own) driver.camera_data = NULL; #endif + +#ifdef HAVE_LOCATION + uninit_location(); + + if (driver.location_data_own) + driver.location_data = NULL; +#endif + #ifdef HAVE_OSK uninit_osk(); @@ -776,6 +902,9 @@ void uninit_drivers(void) #ifdef HAVE_CAMERA driver.camera_data_own = false; #endif +#ifdef HAVE_LOCATION + driver.location_data_own = false; +#endif #ifdef HAVE_OSK driver.osk_data_own = false; #endif diff --git a/driver.h b/driver.h index 2ab7eacd15..63e68dc73b 100644 --- a/driver.h +++ b/driver.h @@ -367,6 +367,19 @@ typedef struct camera_driver const char *ident; } camera_driver_t; +typedef struct location_driver +{ + void *(*init)(int interval_msecs, int interval_distance); + void (*free)(void *data); + + bool (*start)(void *data); + void (*stop)(void *data); + + double (*get_longitude)(void *data); + double (*get_latitude)(void *data); + const char *ident; +} location_driver_t; + struct rarch_viewport; #ifdef HAVE_OVERLAY @@ -459,6 +472,10 @@ typedef struct driver #ifdef HAVE_CAMERA const camera_driver_t *camera; void *camera_data; +#endif +#ifdef HAVE_LOCATION + const location_driver_t *location; + void *location_data; #endif void *audio_data; void *video_data; @@ -484,6 +501,9 @@ typedef struct driver #ifdef HAVE_CAMERA bool camera_data_own; #endif +#ifdef HAVE_LOCATION + bool location_data_own; +#endif #ifdef HAVE_OSK bool osk_data_own; #endif @@ -552,6 +572,13 @@ void find_prev_camera_driver(void); void find_next_camera_driver(void); #endif +#ifdef HAVE_LOCATION +void init_location(void); +void uninit_location(void); +void find_prev_location_driver(void); +void find_next_location_driver(void); +#endif + void driver_set_monitor_refresh_rate(float hz); bool driver_monitor_fps_statistics(double *refresh_rate, double *deviation, unsigned *sample_points); void driver_set_nonblock_state(bool nonblock); @@ -572,6 +599,12 @@ void driver_camera_stop(void); void driver_camera_poll(void); #endif +// Used by RETRO_ENVIRONMENT_GET_LOCATION_INTERFACE +#ifdef HAVE_LOCATION +bool driver_location_start(void); +void driver_location_stop(void); +#endif + extern driver_t driver; //////////////////////////////////////////////// Backends diff --git a/driver_funcs.h b/driver_funcs.h index 3d8ea016fe..0235ccdc3e 100644 --- a/driver_funcs.h +++ b/driver_funcs.h @@ -20,6 +20,8 @@ #define camera_init_func(device, caps, width, height) driver.camera->init(device, caps, width, height) +#define location_init_func(interval_msecs, interval_distance) driver.location->init(interval_msecs, interval_distance) + #define osk_init_func(unknown) driver.osk->init(unknown) #define audio_init_func(device, rate, latency) driver.audio->init(device, rate, latency) diff --git a/dynamic.c b/dynamic.c index cffeaf44df..18896a923f 100644 --- a/dynamic.c +++ b/dynamic.c @@ -835,6 +835,14 @@ bool rarch_environment_cb(unsigned cmd, void *data) break; } #endif +#ifdef HAVE_LOCATION + case RETRO_ENVIRONMENT_GET_LOCATION_INTERFACE: + { + RARCH_LOG("Environ GET_LOCATION_INTERFACE.\n"); + struct retro_location_interface *cb = (struct retro_location_interface*)data; + break; + } +#endif case RETRO_ENVIRONMENT_GET_LOG_INTERFACE: { diff --git a/frontend/frontend.c b/frontend/frontend.c index 907602f13b..0c3fe8bfc9 100644 --- a/frontend/frontend.c +++ b/frontend/frontend.c @@ -367,7 +367,7 @@ returntype main_entry(signature()) global_uninit_drivers(); #ifdef PERF_TEST - rarch_perf_logs(); + rarch_perf_log(); #endif #if defined(HAVE_LOGGER) && !defined(ANDROID) diff --git a/frontend/frontend_emscripten.c b/frontend/frontend_emscripten.c index 0282fb60a4..5c2a044180 100644 --- a/frontend/frontend_emscripten.c +++ b/frontend/frontend_emscripten.c @@ -41,7 +41,7 @@ static void endloop(void) rarch_deinit_msg_queue(); #ifdef PERF_TEST - rarch_perf_logs(); + rarch_perf_log(); #endif rarch_main_clear_state(); diff --git a/frontend/menu/menu_common.c b/frontend/menu/menu_common.c index ea36082395..0f7d87601a 100644 --- a/frontend/menu/menu_common.c +++ b/frontend/menu/menu_common.c @@ -1998,6 +1998,9 @@ void menu_populate_entries(void *data, unsigned menu_type) file_list_push(rgui->selection_buf, "Input driver", RGUI_SETTINGS_DRIVER_INPUT, 0); #ifdef HAVE_CAMERA file_list_push(rgui->selection_buf, "Camera driver", RGUI_SETTINGS_DRIVER_CAMERA, 0); +#endif +#ifdef HAVE_LOCATION + file_list_push(rgui->selection_buf, "Location driver", RGUI_SETTINGS_DRIVER_LOCATION, 0); #endif break; case RGUI_SETTINGS: diff --git a/frontend/menu/menu_common.h b/frontend/menu/menu_common.h index fcda08fe10..91a8f14b7e 100644 --- a/frontend/menu/menu_common.h +++ b/frontend/menu/menu_common.h @@ -124,6 +124,7 @@ typedef enum RGUI_SETTINGS_DRIVER_AUDIO, RGUI_SETTINGS_DRIVER_INPUT, RGUI_SETTINGS_DRIVER_CAMERA, + RGUI_SETTINGS_DRIVER_LOCATION, RGUI_SETTINGS_SCREENSHOT, RGUI_SETTINGS_GPU_SCREENSHOT, RGUI_SCREENSHOT_DIR_PATH, diff --git a/frontend/menu/menu_settings.c b/frontend/menu/menu_settings.c index 029317772f..f30f5a9b7c 100644 --- a/frontend/menu/menu_settings.c +++ b/frontend/menu/menu_settings.c @@ -998,6 +998,14 @@ int menu_set_settings(void *data, unsigned setting, unsigned action) else if (action == RGUI_ACTION_RIGHT) find_next_camera_driver(); break; +#endif +#ifdef HAVE_LOCATION + case RGUI_SETTINGS_DRIVER_LOCATION: + if (action == RGUI_ACTION_LEFT) + find_prev_location_driver(); + else if (action == RGUI_ACTION_RIGHT) + find_next_location_driver(); + break; #endif case RGUI_SETTINGS_VIDEO_GAMMA: if (action == RGUI_ACTION_START) @@ -1625,6 +1633,11 @@ void menu_set_settings_label(char *type_str, size_t type_str_size, unsigned *w, case RGUI_SETTINGS_DRIVER_CAMERA: strlcpy(type_str, g_settings.camera.driver, type_str_size); break; +#endif +#ifdef HAVE_LOCATION + case RGUI_SETTINGS_DRIVER_LOCATION: + strlcpy(type_str, g_settings.location.driver, type_str_size); + break; #endif case RGUI_SETTINGS_VIDEO_REFRESH_RATE_AUTO: { diff --git a/general.h b/general.h index 9e9bcde0fe..fc47d96302 100644 --- a/general.h +++ b/general.h @@ -190,6 +190,15 @@ struct settings } camera; #endif +#ifdef HAVE_LOCATION + struct + { + char driver[32]; + int update_interval_ms; + int update_interval_distance; + } location; +#endif + #ifdef HAVE_OSK struct { @@ -328,6 +337,9 @@ struct global #ifdef HAVE_CAMERA bool camera_active; #endif +#ifdef HAVE_LOCATION + bool location_active; +#endif #ifdef HAVE_OSK bool osk_active; #endif @@ -655,6 +667,9 @@ void config_set_defaults(void); #ifdef HAVE_CAMERA const char *config_get_default_camera(void); #endif +#ifdef HAVE_LOCATION +const char *config_get_default_location(void); +#endif #ifdef HAVE_OSK const char *config_get_default_osk(void); #endif diff --git a/griffin/griffin.c b/griffin/griffin.c index 9dfbaf74a8..12d15444a4 100644 --- a/griffin/griffin.c +++ b/griffin/griffin.c @@ -369,6 +369,12 @@ CAMERA #endif +/*============================================================ +LOCATION +============================================================ */ +#ifdef HAVE_LOCATION +#endif + /*============================================================ RSOUND ============================================================ */ diff --git a/libretro_private.h b/libretro_private.h index a393412911..be1b824aa3 100644 --- a/libretro_private.h +++ b/libretro_private.h @@ -40,6 +40,44 @@ // Requests that this core is deinitialized, and a new core is loaded. It also escapes the main loop the core is currently // bound to. // The libretro core used is set with SET_LIBRETRO_PATH, and path to game is passed in _EXEC. NULL means no game. +#define RETRO_ENVIRONMENT_GET_LOCATION_INTERFACE (RETRO_ENVIRONMENT_PRIVATE | 3) + // struct retro_location_interface * -- + // Gets access to the location interface. + // The purpose of this interface is to be able to retrieve location-based information from the host device, + // such as current latitude / longitude. + // + +//Sets the interval of time and/or distance at which to update/poll location-based data. +//To ensure compatibility with all location-based implementations, values for both +//interval_ms and interval_distance should be provided. +//interval_ms is the interval expressed in milliseconds +//interval_distance is the distance interval expressed in meters. +typedef void (*retro_location_set_interval_t)(int interval_ms, int interval_distance); + +//Start location services. The device will start listening for changes to the +//current location at regular intervals (which are defined with retro_location_set_interval_t). +typedef void (*retro_location_start_t)(void); + +//Stop location services. The device will stop listening for changes to the current +//location. +typedef void (*retro_location_stop_t)(void); + +//Get the latitude of the current location. +typedef double (*retro_location_get_latitude_t)(void); + +//Get the longitude of the current location. +typedef double (*retro_location_get_longitude_t)(void); + +struct retro_location_interface +{ + int interval_in_ms; + int interval_distance_in_meters; + retro_location_start_t start; + retro_location_stop_t stop; + retro_location_get_latitude_t get_latitude; + retro_location_get_longitude_t get_longitude; + retro_location_set_interval_t set_interval; +}; #endif diff --git a/settings.c b/settings.c index 4054faecb1..ae972a203e 100644 --- a/settings.c +++ b/settings.c @@ -184,6 +184,23 @@ const char *config_get_default_camera(void) } #endif +#ifdef HAVE_LOCATION +const char *config_get_default_location(void) +{ + switch (LOCATION_DEFAULT_DRIVER) + { +#if 0 + case LOCATION_ANDROID: + return "android"; + case LOCATION_APPLE: + return "apple"; +#endif + default: + return NULL; + } +} +#endif + void config_set_defaults(void) { @@ -197,6 +214,14 @@ void config_set_defaults(void) if (def_camera) strlcpy(g_settings.camera.driver, def_camera, sizeof(g_settings.camera.driver)); #endif + +#ifdef HAVE_LOCATION + const char *def_location = config_get_default_location(); + + if (def_location) + strlcpy(g_settings.location.driver, def_location, sizeof(g_settings.location.driver)); +#endif + #ifdef HAVE_OSK const char *def_osk = config_get_default_osk();