Skip to main content

IAppletManagerV3 Interface

1. Overview​

The IAppletManagerV3 interface is used to manage mini-games, providing functionality for launching, closing games, and handling game events and JsApi calls.

2. Interface Definition​

interface IAppletManagerV3 : public WIUnknown {
// Launch applet
virtual void LaunchApplet(
const char* app_id,
const char* launch_config_pb,
size_t launch_config_pb_length,
LaunchCallback callback
) = 0;

// Close applet
virtual void CloseApplet(const char* app_id) = 0;

// Set JsApi handler
virtual void SetJsApiHandler(JsApiHandler jsapi_handler) = 0;

// Set applet event handler
virtual void SetAppletEventHandler(EventHandler event_handler) = 0;

// Send JsApi or event response
virtual void SendJsApiOrEventResponse(
int task_id,
const char* data,
size_t data_size
) = 0;

// Call applet command
virtual void CallAppletCommand(
const char* command_name,
int32_t task_id,
const char* app_id,
const char* data,
size_t data_size
) = 0;
};

3. Callback Function Types​

3.1 LaunchCallback​

Callback function called when game launch completes.

typedef void (*LaunchCallback)(
const char* app_id,
int result_code,
const char* error_desc
);

Parameter Description

  • app_id (const char*): Game ID
  • result_code (int): Result code
    • 0 (WMPF_ERRCODE_SUCCESS): Launch successful
    • Non-zero: Launch failed
  • error_desc (const char*): Error description (empty on success)

3.2 JsApiHandler​

Handles JsApi calls initiated by games.

typedef bool (*JsApiHandler)(
const char* app_id,
const char* api_name,
const char* data,
size_t data_size,
int task_id
);

Parameter Description

  • app_id (const char*): Game ID
  • api_name (const char*): API name
  • data (const char*): API request data (JSON format)
  • data_size (size_t): Data size
  • task_id (int): Task ID for response

Return Value

  • true: Processing successful
  • false: Processing failed

3.3 EventHandler​

Handles events sent by games.

typedef bool (*EventHandler)(
const char* event_name,
const char* data,
size_t data_size,
int task_id
);

Parameter Description

  • event_name (const char*): Event name
  • data (const char*): Event data (JSON format)
  • data_size (size_t): Data size
  • task_id (int): Task ID for response

Return Value

  • true: Processing successful
  • false: Processing failed

4. Method Details​

4.1 LaunchApplet​

Launches a game instance.

Function Signature

void LaunchApplet(
const char* app_id,
const char* launch_config_pb,
size_t launch_config_pb_length,
LaunchCallback callback
);

Parameter Description

  • app_id (const char*): Game ID (Applet ID), from the id field returned by Game List API
  • launch_config_pb (const char*): Launch configuration JSON string
  • launch_config_pb_length (size_t): Configuration string length
  • callback (LaunchCallback): Launch completion callback function

Key ID Description

ID TypeDescriptionSourceUsage Location
app_id (Game ID)Unique identifier of the gameid field returned by Game List APIFirst parameter of LaunchApplet and CloseApplet
launchKeyGame launch session keylaunchKey field returned by Game List APIlaunchKey field in launch_config_pb JSON

Launch Configuration JSON Format

{
"launchKey": "https://minihost.tuanjie.cn/api/game/start_session?gameId=xxx",
"accessToken": "your-access-token",
"userId": "user-id",
"debug": true,
"mute": false,
"transparent": false
}
FieldTypeRequiredDescription
launchKeyStringYesGame launch URL, from launchKey field returned by Game List API
accessTokenStringYesUser access token for authentication
userIdStringYesUser ID
debugBooleanNoWhether to enable debug mode
muteBooleanNoWhether to mute
transparentBooleanNoWhether the window is transparent

Process to Get app_id and launchKey

  1. Call Game List API to get available game list
  2. Select the game to launch from the returned JSON array
  3. Use that game's id field as the app_id parameter for LaunchApplet
  4. Use that game's launchKey field as the launchKey value in launch_config_pb

Game List API Response Example:

[
{
"id": "691acb162dcfadc65a0fdb77", // Used as app_id parameter
"appId": "691ac9ef2dcfadc65a0fb4a6", // Host App ID
"name": "Example Game",
"launchKey": "691acb162dcfadc65a0fdb77", // Used as launchConfig.launchKey
"gameType": "webgl"
}
]

Code Example

#include "IAppletManagerV3.h"
#include <iostream>

// Launch callback
void OnLaunchComplete(const char* app_id, int result_code, const char* error_desc) {
if (result_code == WMPF_ERRCODE_SUCCESS) {
std::cout << "Game launched successfully: " << app_id << std::endl;
} else {
std::cerr << "Game launch failed: " << error_desc << std::endl;
}
}

// Get IAppletManagerV3 from IBrowsingService
IAppletManagerV3* appletMgr = nullptr;
service->QueryInterface("IAppletManagerV3", (void**)&appletMgr);

// Game ID and Launch Key - these values come from Game List API
// appId: "id" field returned by Game List API
// launchKey: "launchKey" field returned by Game List API
const char* appId = "691acb162dcfadc65a0fdb77"; // From Game List API
const char* launchKey = "691acb162dcfadc65a0fdb77"; // From Game List API

// Build launch config
char launchConfig[2048];
snprintf(launchConfig, sizeof(launchConfig), R"({
"launchKey": "%s",
"accessToken": "your-access-token",
"userId": "developer",
"debug": true,
"mute": false,
"transparent": false
})", launchKey);

// Launch applet
// First parameter appId is from "id" field returned by Game List API
appletMgr->LaunchApplet(
appId,
launchConfig,
strlen(launchConfig),
OnLaunchComplete
);

std::cout << "Launch request sent, waiting for callback..." << std::endl;

4.2 CloseApplet​

Closes a running game instance.

Function Signature

void CloseApplet(const char* app_id);

Parameter Description

  • app_id (const char*): Game ID to close, must be the same as the app_id used in LaunchApplet (from id field returned by Game List API)

Code Example

// Close the game - use the same app_id as in LaunchApplet
// app_id is from "id" field returned by Game List API
appletMgr->CloseApplet("691acb162dcfadc65a0fdb77");
std::cout << "Game closed" << std::endl;

4.3 SetJsApiHandler​

Sets the JsApi call handler. JsApi calls from games will be routed through this handler to the host application.

Function Signature

void SetJsApiHandler(JsApiHandler jsapi_handler);

Parameter Description

  • jsapi_handler (JsApiHandler): JsApi handler function pointer

Code Example

// JsApi handler implementation
bool OnJsApiCall(
const char* app_id,
const char* api_name,
const char* data,
size_t data_size,
int task_id
) {
std::cout << "[JsApi] " << api_name << " from " << app_id << std::endl;
std::cout << "[JsApi] Data: " << std::string(data, data_size) << std::endl;
std::cout << "[JsApi] Task ID: " << task_id << std::endl;

// Process the API call
// ...

// Send response back
const char* response = R"({"code": 0, "message": "success"})";
appletMgr->SendJsApiOrEventResponse(task_id, response, strlen(response));

return true;
}

// Set the handler
appletMgr->SetJsApiHandler(OnJsApiCall);
std::cout << "JsApi handler registered" << std::endl;

4.4 SetAppletEventHandler​

Sets the game event handler. Events from games will be routed through this handler to the host application.

Function Signature

void SetAppletEventHandler(EventHandler event_handler);

Parameter Description

  • event_handler (EventHandler): Event handler function pointer

Code Example

// Event handler implementation
bool OnGameEvent(
const char* event_name,
const char* data,
size_t data_size,
int task_id
) {
std::cout << "[Event] " << event_name << std::endl;
std::cout << "[Event] Data: " << std::string(data, data_size) << std::endl;

// Handle specific events
if (strcmp(event_name, "game_exited") == 0) {
std::cout << "Game exited" << std::endl;
// Handle game exit (cleanup, etc.)
}

return true;
}

// Set the handler
appletMgr->SetAppletEventHandler(OnGameEvent);
std::cout << "Event handler registered" << std::endl;

4.5 SendJsApiOrEventResponse​

Sends a response to a JsApi call or event.

Function Signature

void SendJsApiOrEventResponse(
int task_id,
const char* data,
size_t data_size
);

Parameter Description

  • task_id (int): Task ID (received from JsApiHandler or EventHandler)
  • data (const char*): Response data (JSON format)
  • data_size (size_t): Data size

Code Example

// In JsApi handler
bool OnJsApiCall(
const char* app_id,
const char* api_name,
const char* data,
size_t data_size,
int task_id
) {
// Process API call
// ...

// Build response
const char* response = R"({
"code": 0,
"message": "success",
"data": {
"result": "operation completed"
}
})";

// Send response
appletMgr->SendJsApiOrEventResponse(task_id, response, strlen(response));

return true;
}

4.6 CallAppletCommand​

Calls a game command (for extended functionality).

Function Signature

void CallAppletCommand(
const char* command_name,
int32_t task_id,
const char* app_id,
const char* data,
size_t data_size
);

Parameter Description

  • command_name (const char*): Command name
  • task_id (int32_t): Task ID
  • app_id (const char*): Game ID
  • data (const char*): Command data (JSON format)
  • data_size (size_t): Data size

Supported Commands

Command NameDescriptionData Format
runCustomScriptInject and execute JavaScript code in the game{"script": "JS code"}

Code Example - Inject JavaScript

Use the runCustomScript command to inject custom JavaScript code while the game is running:

// Build JavaScript code to inject
std::string jsCode = R"(
(function() {
console.log('Custom script injected!');
// Your custom logic here
return true;
})()
)";

// Escape the script for JSON
std::string escapedScript = EscapeForJson(jsCode);

// Build command data
std::ostringstream oss;
oss << R"({"script":")" << escapedScript << R"("})";
std::string scriptData = oss.str();

// Inject script into the game
appletMgr->CallAppletCommand(
"runCustomScript",
task_id,
app_id,
scriptData.c_str(),
scriptData.length()
);
Use Cases

runCustomScript is commonly used for:

  • Dynamically injecting UI elements (such as ad display)
  • Calling game internal APIs
  • Debugging and testing

Code Example - General Command

const char* commandData = R"({"param": "value"})";
appletMgr->CallAppletCommand(
"customCommand",
12345,
"684aa7ed8efdfe29f316a960",
commandData,
strlen(commandData)
);

5. Complete Usage Example​

#include <iostream>
#include <thread>
#include <chrono>
#include <atomic>
#include "IBrowsingService.h"
#include "IAppletManagerV3.h"
#include "ICoreServiceHandler.h"

// Global state
std::atomic<bool> g_launchCompleted{false};
std::atomic<bool> g_shouldExit{false};
IAppletManagerV3* g_appletMgr = nullptr;

// Launch callback
void OnLaunchComplete(const char* app_id, int result_code, const char* error_desc) {
std::cout << "\n[Launch Callback]" << std::endl;
std::cout << "App ID: " << app_id << std::endl;
std::cout << "Result: " << result_code << std::endl;

if (result_code == WMPF_ERRCODE_SUCCESS) {
std::cout << "Game launched successfully!" << std::endl;
} else {
std::cerr << "Launch failed: " << error_desc << std::endl;
}

g_launchCompleted = true;
}

// JsApi handler
bool OnJsApiCall(
const char* app_id,
const char* api_name,
const char* data,
size_t data_size,
int task_id
) {
std::cout << "\n[JsApi Call]" << std::endl;
std::cout << "API: " << api_name << std::endl;
std::cout << "App ID: " << app_id << std::endl;
std::cout << "Task ID: " << task_id << std::endl;
std::cout << "Data: " << std::string(data, data_size) << std::endl;

// Send response
const char* response = R"({"code": 0, "message": "success"})";
g_appletMgr->SendJsApiOrEventResponse(task_id, response, strlen(response));

return true;
}

// Event handler
bool OnGameEvent(
const char* event_name,
const char* data,
size_t data_size,
int task_id
) {
std::cout << "\n[Game Event]" << std::endl;
std::cout << "Event: " << event_name << std::endl;
std::cout << "Data: " << std::string(data, data_size) << std::endl;

return true;
}

int main() {
// 1. Initialize service (see init.md and browsing-service.md)
// ...
IBrowsingService* service = GetBrowsingService();
service->InitializeBrowsingCore(config, "", nullptr);

// 2. Get IAppletManagerV3
service->QueryInterface("IAppletManagerV3", (void**)&g_appletMgr);

if (!g_appletMgr) {
std::cerr << "Failed to get IAppletManagerV3" << std::endl;
return 1;
}

std::cout << "Got IAppletManagerV3 interface" << std::endl;

// 3. Set handlers
g_appletMgr->SetJsApiHandler(OnJsApiCall);
g_appletMgr->SetAppletEventHandler(OnGameEvent);
std::cout << "Handlers registered" << std::endl;

// 4. Launch game
// appId and launchKey come from Game List API
// appId: "id" field returned by Game List API
// launchKey: "launchKey" field returned by Game List API
const char* appId = "691acb162dcfadc65a0fdb77";
const char* launchKey = "691acb162dcfadc65a0fdb77";

char launchConfig[2048];
snprintf(launchConfig, sizeof(launchConfig), R"({
"launchKey": "%s",
"accessToken": "your-access-token",
"userId": "developer",
"debug": true
})", launchKey);

std::cout << "\nLaunching game..." << std::endl;
g_appletMgr->LaunchApplet(
appId,
launchConfig,
strlen(launchConfig),
OnLaunchComplete
);

// 5. Wait for launch to complete
while (!g_launchCompleted && !g_shouldExit) {
std::this_thread::sleep_for(std::chrono::milliseconds(100));
}

if (!g_shouldExit) {
std::cout << "\nGame is running. Press Ctrl+C to exit..." << std::endl;

// Keep running for demo (in real app, use proper event loop)
std::this_thread::sleep_for(std::chrono::seconds(30));

// 6. Close game
std::cout << "\nClosing game..." << std::endl;
g_appletMgr->CloseApplet(appId);
}

// 7. Cleanup
g_appletMgr->Release();
service->UninitializeBrowsingCore();
service->Release();

std::cout << "Done!" << std::endl;
return 0;
}

6. Common Usage Patterns​

6.1 Pattern 1: Launch Game and Wait for Completion​

std::atomic<bool> launchDone{false};

void OnLaunch(const char* app_id, int result_code, const char* error_desc) {
launchDone = true;
}

appletMgr->LaunchApplet(appId, config, strlen(config), OnLaunch);

while (!launchDone) {
std::this_thread::sleep_for(std::chrono::milliseconds(100));
}

6.2 Pattern 2: Handle JsApi and Return Result​

bool OnJsApi(const char* app_id, const char* api_name,
const char* data, size_t data_size, int task_id) {
// Parse request
// Do some work

// Build response
std::string response = BuildResponse();

// Send back
appletMgr->SendJsApiOrEventResponse(
task_id,
response.c_str(),
response.length()
);

return true;
}

6.3 Pattern 3: Listen for Game Events​

bool OnEvent(const char* event_name, const char* data,
size_t data_size, int task_id) {
if (strcmp(event_name, "game_exited") == 0) {
// Game has exited, perform cleanup
std::cout << "Game exited" << std::endl;
}
return true;
}

7. Important Notes​

  1. Callback Function Threading: Callback functions may execute in different threads; ensure thread safety
  2. Lifecycle Management: Ensure IAppletManagerV3 object remains valid while the game is running
  3. Response Timeliness: JsApi and event handlers should return quickly; avoid blocking
  4. Memory Management: String parameters are managed internally by the SDK; do not use them after the callback returns
  5. Error Handling: Always check the result_code in launch callbacks