Added support for IAppletCommonFunctions. Added appletReadThemeStorage, appletWriteThemeStorage, appletGetDisplayLogicalResolution, appletSetDisplayMagnification, appletSetHomeButtonDoubleClickEnabled, and appletGetHomeButtonDoubleClickEnabled. Minor other changes.

This commit is contained in:
yellows8 2019-08-02 14:16:48 -04:00
parent 98fbadc778
commit 1bb777afe7
No known key found for this signature in database
GPG Key ID: 0AF90DA3F1E60E43
2 changed files with 264 additions and 36 deletions

View File

@ -1204,6 +1204,62 @@ Result appletBeginToWatchShortHomeButtonMessage(void);
*/ */
Result appletEndToWatchShortHomeButtonMessage(void); Result appletEndToWatchShortHomeButtonMessage(void);
// IAppletCommonFunctions
/**
* @brief Reads the ThemeStorage for the current applet.
* @note Only available with AppletType_SystemApplet, AppletType_LibraryApplet, or AppletType_OverlayApplet, on [7.0.0+].
* @note offset(+size) must be <=0x400.
* @param[out] buffer Output buffer data.
* @param[in] size Size to read.
* @param[in] offset Offset within the ThemeStorage.
* @param[out] transfer_size Actual read size.
*/
Result appletReadThemeStorage(void* buffer, size_t size, u64 offset, size_t *transfer_size);
/**
* @brief Writes the ThemeStorage for the current applet.
* @note Only available with AppletType_SystemApplet, AppletType_LibraryApplet, or AppletType_OverlayApplet, on [7.0.0+].
* @note offset(+size) must be <=0x400.
* @param[in] buffer Input buffer data.
* @param[in] size Size to write.
* @param[in] offset Offset within the ThemeStorage.
*/
Result appletWriteThemeStorage(const void* buffer, size_t size, u64 offset);
/**
* @brief Gets the DisplayLogicalResolution.
* @note Only available with AppletType_SystemApplet, AppletType_LibraryApplet, or AppletType_OverlayApplet, on [8.0.0+].
* @param[out] width Output width.
* @param[out] height Output height.
*/
Result appletGetDisplayLogicalResolution(s32 *width, s32 *height);
/**
* @brief Sets the DisplayMagnification. This is essentially layer image crop, for everything non-Overlay.
* @note Only available with AppletType_SystemApplet, AppletType_LibraryApplet, or AppletType_OverlayApplet, on [8.0.0+].
* @note x and width are multiplied with the same width value returned by \ref appletGetDisplayLogicalResolution, so these should be in the range 0.0f-1.0f. Likewise for y and height, except those are multipled with the height value.
* @param[in] x X position.
* @param[in] y Y position.
* @param[in] width Width.
* @param[in] height Height.
*/
Result appletSetDisplayMagnification(float x, float y, float width, float height);
/**
* @brief Sets whether HomeButtonDoubleClick is enabled.
* @note Only available with AppletType_SystemApplet, AppletType_LibraryApplet, or AppletType_OverlayApplet, on [8.0.0+].
* @param[in] flag Flag
*/
Result appletSetHomeButtonDoubleClickEnabled(bool flag);
/**
* @brief Gets whether HomeButtonDoubleClick is enabled.
* @note Only available with AppletType_SystemApplet, AppletType_LibraryApplet, or AppletType_OverlayApplet, on [8.0.0+].
* @param[out] out Output flag.
*/
Result appletGetHomeButtonDoubleClickEnabled(bool *out);
// State / other // State / other
/** /**

View File

@ -29,6 +29,8 @@ static u64 g_refCnt;
static bool g_appletExitProcessFlag; static bool g_appletExitProcessFlag;
// From Get*Functions. // From Get*Functions.
static Service g_appletIAppletCommonFunctions;
static Service g_appletIFunctions; static Service g_appletIFunctions;
static Service g_appletIGlobalStateController; static Service g_appletIGlobalStateController;
@ -45,6 +47,7 @@ static Service g_appletIAudioController;
static Service g_appletIDisplayController; static Service g_appletIDisplayController;
static Service g_appletIDebugFunctions; static Service g_appletIDebugFunctions;
static size_t g_appletIAppletCommonFunctions_ptrbufsize;
static size_t g_appletISelfController_ptrbufsize; static size_t g_appletISelfController_ptrbufsize;
static Event g_appletMessageEvent; static Event g_appletMessageEvent;
@ -163,6 +166,14 @@ Result appletInitialize(void)
} while (rc == AM_BUSY_ERROR); } while (rc == AM_BUSY_ERROR);
} }
// [7.0.0+] GetAppletCommonFunctions
if (R_SUCCEEDED(rc) && hosversionAtLeast(7,0,0)) {
if (__nx_applet_type == AppletType_SystemApplet || __nx_applet_type == AppletType_LibraryApplet || __nx_applet_type == AppletType_OverlayApplet) {
rc = _appletGetSession(&g_appletProxySession, &g_appletIAppletCommonFunctions, __nx_applet_type == AppletType_SystemApplet ? 23 : 21);
if (R_SUCCEEDED(rc)) rc = ipcQueryPointerBufferSize(g_appletIAppletCommonFunctions.handle, &g_appletIAppletCommonFunctions_ptrbufsize);
}
}
// Get*Functions // Get*Functions
if (R_SUCCEEDED(rc) && __nx_applet_type != AppletType_LibraryApplet) if (R_SUCCEEDED(rc) && __nx_applet_type != AppletType_LibraryApplet)
rc = _appletGetSession(&g_appletProxySession, &g_appletIFunctions, 20); rc = _appletGetSession(&g_appletProxySession, &g_appletIFunctions, 20);
@ -375,6 +386,8 @@ void appletExit(void)
serviceClose(&g_appletILibraryAppletSelfAccessor); serviceClose(&g_appletILibraryAppletSelfAccessor);
} }
serviceClose(&g_appletIAppletCommonFunctions);
serviceClose(&g_appletProxySession); serviceClose(&g_appletProxySession);
serviceClose(&g_appletSrv); serviceClose(&g_appletSrv);
g_appletResourceUserId = 0; g_appletResourceUserId = 0;
@ -1060,6 +1073,45 @@ static Result _appletGetIdentityInfo(Service* srv, AppletIdentityInfo *info, u64
return rc; return rc;
} }
static Result _appletGetResolution(Service* srv, s32 *width, s32 *height, u64 cmd_id) {
IpcCommand c;
ipcInitialize(&c);
struct {
u64 magic;
u64 cmd_id;
} *raw;
raw = serviceIpcPrepareHeader(srv, &c, sizeof(*raw));
raw->magic = SFCI_MAGIC;
raw->cmd_id = cmd_id;
Result rc = serviceIpcDispatch(srv);
if (R_SUCCEEDED(rc)) {
IpcParsedCommand r;
struct {
u64 magic;
u64 result;
s32 width;
s32 height;
} *resp;
serviceIpcParse(srv, &r, sizeof(*resp));
resp = r.Raw;
rc = resp->result;
if (R_SUCCEEDED(rc)) {
if (width) *width = resp->width;
if (height) *height = resp->height;
}
}
return rc;
}
// ICommonStateGetter // ICommonStateGetter
static Result _appletReceiveMessage(u32 *out) { static Result _appletReceiveMessage(u32 *out) {
@ -1316,42 +1368,7 @@ Result appletGetDefaultDisplayResolution(s32 *width, s32 *height) {
if (hosversionBefore(3,0,0)) if (hosversionBefore(3,0,0))
return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer); return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
IpcCommand c; return _appletGetResolution(&g_appletICommonStateGetter, width, height, 60);
ipcInitialize(&c);
struct {
u64 magic;
u64 cmd_id;
} *raw;
raw = serviceIpcPrepareHeader(&g_appletICommonStateGetter, &c, sizeof(*raw));
raw->magic = SFCI_MAGIC;
raw->cmd_id = 60;
Result rc = serviceIpcDispatch(&g_appletICommonStateGetter);
if (R_SUCCEEDED(rc)) {
IpcParsedCommand r;
struct {
u64 magic;
u64 result;
s32 width;
s32 height;
} *resp;
serviceIpcParse(&g_appletICommonStateGetter, &r, sizeof(*resp));
resp = r.Raw;
rc = resp->result;
if (R_SUCCEEDED(rc)) {
if (width) *width = resp->width;
if (height) *height = resp->height;
}
}
return rc;
} }
Result appletGetDefaultDisplayResolutionChangeEvent(Event *out_event) { Result appletGetDefaultDisplayResolutionChangeEvent(Event *out_event) {
@ -3832,6 +3849,161 @@ Result appletEndToWatchShortHomeButtonMessage(void) {
return _appletCmdNoIO(&g_appletIFunctions, 1); return _appletCmdNoIO(&g_appletIFunctions, 1);
} }
// IAppletCommonFunctions
Result appletReadThemeStorage(void* buffer, size_t size, u64 offset, size_t *transfer_size) {
if (!serviceIsActive(&g_appletIAppletCommonFunctions))
return MAKERESULT(Module_Libnx, LibnxError_NotInitialized);
IpcCommand c;
ipcInitialize(&c);
ipcAddRecvSmart(&c, g_appletIAppletCommonFunctions_ptrbufsize, buffer, size, 0);
struct {
u64 magic;
u64 cmd_id;
u64 offset;
} *raw;
raw = serviceIpcPrepareHeader(&g_appletIAppletCommonFunctions, &c, sizeof(*raw));
raw->magic = SFCI_MAGIC;
raw->cmd_id = 10;
raw->offset = offset;
Result rc = serviceIpcDispatch(&g_appletIAppletCommonFunctions);
if (R_SUCCEEDED(rc)) {
IpcParsedCommand r;
struct {
u64 magic;
u64 result;
u64 transfer_size;
} *resp;
serviceIpcParse(&g_appletIAppletCommonFunctions, &r, sizeof(*resp));
resp = r.Raw;
rc = resp->result;
if (R_SUCCEEDED(rc) && transfer_size) *transfer_size = resp->transfer_size;
}
return rc;
}
Result appletWriteThemeStorage(const void* buffer, size_t size, u64 offset) {
if (!serviceIsActive(&g_appletIAppletCommonFunctions))
return MAKERESULT(Module_Libnx, LibnxError_NotInitialized);
IpcCommand c;
ipcInitialize(&c);
ipcAddSendSmart(&c, g_appletIAppletCommonFunctions_ptrbufsize, buffer, size, 0);
struct {
u64 magic;
u64 cmd_id;
u64 offset;
} *raw;
raw = serviceIpcPrepareHeader(&g_appletIAppletCommonFunctions, &c, sizeof(*raw));
raw->magic = SFCI_MAGIC;
raw->cmd_id = 11;
raw->offset = offset;
Result rc = serviceIpcDispatch(&g_appletIAppletCommonFunctions);
if (R_SUCCEEDED(rc)) {
IpcParsedCommand r;
struct {
u64 magic;
u64 result;
} *resp;
serviceIpcParse(&g_appletIAppletCommonFunctions, &r, sizeof(*resp));
resp = r.Raw;
rc = resp->result;
}
return rc;
}
Result appletGetDisplayLogicalResolution(s32 *width, s32 *height) {
if (!serviceIsActive(&g_appletIAppletCommonFunctions))
return MAKERESULT(Module_Libnx, LibnxError_NotInitialized);
if (hosversionBefore(8,0,0))
return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
return _appletGetResolution(&g_appletIAppletCommonFunctions, width, height, 40);
}
Result appletSetDisplayMagnification(float x, float y, float width, float height) {
if (!serviceIsActive(&g_appletIAppletCommonFunctions))
return MAKERESULT(Module_Libnx, LibnxError_NotInitialized);
if (hosversionBefore(8,0,0))
return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
IpcCommand c;
ipcInitialize(&c);
struct {
u64 magic;
u64 cmd_id;
float x;
float y;
float width;
float height;
} *raw;
raw = serviceIpcPrepareHeader(&g_appletIAppletCommonFunctions, &c, sizeof(*raw));
raw->magic = SFCI_MAGIC;
raw->cmd_id = 42;
raw->x = x;
raw->y = y;
raw->width = width;
raw->height = height;
Result rc = serviceIpcDispatch(&g_appletIAppletCommonFunctions);
if (R_SUCCEEDED(rc)) {
IpcParsedCommand r;
struct {
u64 magic;
u64 result;
} *resp;
serviceIpcParse(&g_appletIAppletCommonFunctions, &r, sizeof(*resp));
resp = r.Raw;
rc = resp->result;
}
return rc;
}
Result appletSetHomeButtonDoubleClickEnabled(bool flag) {
if (!serviceIsActive(&g_appletIAppletCommonFunctions))
return MAKERESULT(Module_Libnx, LibnxError_NotInitialized);
if (hosversionBefore(8,0,0))
return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
return _appletCmdInBool(&g_appletIAppletCommonFunctions, flag, 50);
}
Result appletGetHomeButtonDoubleClickEnabled(bool *out) {
if (!serviceIsActive(&g_appletIAppletCommonFunctions))
return MAKERESULT(Module_Libnx, LibnxError_NotInitialized);
if (hosversionBefore(8,0,0))
return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
return _appletCmdNoInOutBool(&g_appletIAppletCommonFunctions, out, 51);
}
// State / other // State / other
u8 appletGetOperationMode(void) { u8 appletGetOperationMode(void) {