#include "ohos_init.h"
#include "memory_adapter.h"
#include <cstdio>
+#include <sstream>
+#include <vector>
#include "service_id_define.h"
#include "bundle_install_msg.h"
#include "graphic_service.h"
}
void HandTaskCharacterConfigNotify(Request *request)
{
- WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandTaskCharacterConfigNotify msg_id = %d",request->msgId);
- int status = *(int *)request->data;
+ WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandTaskCharacterConfigNotify msg_id = %d", request->msgId);
+
+ if (request->data == nullptr || request->len <= 0) {
+ WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandTaskCharacterConfigNotify: invalid data");
+ return;
+ }
+
+ // 解析接收到的数据:角色配置信息(以'|'分隔)
+ // 格式: "characterId|characterName|eyesShape|hairColor|eyesColor|hairStyle|screenImageAsEmoji"
+ std::string payload(static_cast<char*>(request->data), request->len);
+ WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandTaskCharacterConfigNotify payload = %s", payload.c_str());
+
+ // 解析各个字段
+ std::vector<std::string> fields;
+ std::stringstream ss(payload);
+ std::string field;
+ while (std::getline(ss, field, '|')) {
+ fields.push_back(field);
+ }
+
+ if (fields.size() < 7) {
+ WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandTaskCharacterConfigNotify: invalid payload format, expected 7 fields, got %zu", fields.size());
+ return;
+ }
+
+ std::string characterId = fields[0];
+ std::string characterName = fields[1];
+ std::string eyesShape = fields[2];
+ std::string hairColor = fields[3];
+ std::string eyesColor = fields[4];
+ std::string hairStyle = fields[5];
+ int screenImageAsEmoji = std::stoi(fields[6]);
+
+ WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandTaskCharacterConfigNotify characterId = %s", characterId.c_str());
+ WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandTaskCharacterConfigNotify characterName = %s", characterName.c_str());
+ WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandTaskCharacterConfigNotify eyesShape = %s", eyesShape.c_str());
+ WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandTaskCharacterConfigNotify hairColor = %s", hairColor.c_str());
+ WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandTaskCharacterConfigNotify eyesColor = %s", eyesColor.c_str());
+ WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandTaskCharacterConfigNotify hairStyle = %s", hairStyle.c_str());
+ WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandTaskCharacterConfigNotify screenImageAsEmoji = %d", screenImageAsEmoji);
+
+ // 通过图形服务调用 ThunderBirdModel 的处理函数
+ GraphicService::GetInstance()->PostGraphicEvent(
+ [characterId, characterName, eyesShape, hairColor, eyesColor, hairStyle, screenImageAsEmoji]() {
+ if (OHOS::ThunderBirdModel::GetInstance()) {
+ OHOS::ThunderBirdModel::GetInstance()->HandleCharacterConfigChange(
+ characterId.c_str(), characterName.c_str(), eyesShape.c_str(),
+ hairColor.c_str(), eyesColor.c_str(), hairStyle.c_str(), screenImageAsEmoji);
+ }
+ });
}
// 哄睡模式开始通知
WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandSleepModeStartNotify msg_id = %d", request->msgId);
std::string theme(static_cast<char*>(request->data), request->len);
WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandSleepModeStartNotify storyTheme = %s", theme.c_str());
+ //跳转到哄睡模式
+ GraphicService::GetInstance()->PostGraphicEvent(
+ std::bind(&OHOS::ThunderBirdModel::HandleSleepModeStart,OHOS::ThunderBirdModel::GetInstance(),theme.c_str()));
}
// 哄睡模式结束通知
void HandSleepModeEndNotify(Request *request)
{
WEARABLE_LOGE(WEARABLE_LOG_MODULE_UI_SERVICE, "HandSleepModeEndNotify msg_id = %d",request->msgId);
+ GraphicService::GetInstance()->PostGraphicEvent(
+ std::bind(&OHOS::ThunderBirdModel::HandleSleepModeEnd,OHOS::ThunderBirdModel::GetInstance()));
+
}
// 下载表情通知
static uint32_t ln_memory_info_at(uint8_t *para, uint32_t paraLen, char *strCommonCmd);
static uint32_t ln_folder_size_at(uint8_t *para, uint32_t paraLen, char *strCommonCmd);
+//表情切换相关AT命令函数声明
+static uint32_t ln_switch_expression_at(uint8_t *para, uint32_t paraLen, char *strCommonCmd);
+
//帧率控制相关AT命令函数声明
static uint32_t ln_set_fps_at(uint8_t *para, uint32_t paraLen, char *strCommonCmd);
static uint32_t ln_get_fps_at(uint8_t *para, uint32_t paraLen, char *strCommonCmd);
printf("[LN][CHAT_STAMINA_DEMO] chatLeft=%d, flowLeft=%d\n", chatLeft, flowLeft);
return ERRCODE_SUCC;
}
+/**
+ * @brief AT^LN_SWITCH_EXPRESSION=<video_path> - 切换表情视频
+ * @param para 参数字符串(视频文件路径)
+ * @param paraLen 参数长度
+ * @param strCommonCmd 命令字符串(未使用)
+ * @return uint32_t 错误码
+ *
+ * 功能:切换表情视频
+ * 用法:AT^LN_SWITCH_EXPRESSION=/user/res/video/Angry.mp4
+ * AT^LN_SWITCH_EXPRESSION=/user/res/video/Happy.mp4
+ */
+static uint32_t ln_switch_expression_at(uint8_t *para, uint32_t paraLen, char *strCommonCmd)
+{
+ VAD_UNUSED(strCommonCmd);
+
+ uint8_t argv[LN_MAX_ARGC][LN_MAX_ARGV_LEN] = {0};
+ uint32_t argc = 0;
+
+ // 解析参数
+ if (ConvertCmdToParam(para, paraLen, argv, &argc) != VAD_SUCCESS) {
+ printf("ERROR: Failed to parse parameters\n");
+ return ERRCODE_FAIL;
+ }
+
+ if (argc < 1) {
+ printf("ERROR: Missing video path parameter\n");
+ printf("Usage: AT^LN_SWITCH_EXPRESSION=<video_path>\n");
+ printf("Example: AT^LN_SWITCH_EXPRESSION=/user/res/video/Angry.mp4\n");
+ return ERRCODE_FAIL;
+ }
+
+ const char *video_path = (char*)argv[0];
+ if (video_path == NULL || strlen(video_path) == 0) {
+ printf("ERROR: Empty video path parameter\n");
+ return ERRCODE_FAIL;
+ }
+
+ // 检查路径长度限制
+ if (strlen(video_path) > 256) {
+ printf("ERROR: Video path too long (max 256 characters)\n");
+ return ERRCODE_FAIL;
+ }
+
+ printf("[LN][SWITCH_EXPRESSION] Switching to video: %s\n", video_path);
+
+ // 调用C接口切换表情视频
+ bool result = switch_expression_video(video_path);
+
+ if (result) {
+ printf("+LN_SWITCH_EXPRESSION: OK\n");
+ printf("Expression video switched successfully: %s\n", video_path);
+ return ERRCODE_SUCC;
+ } else {
+ printf("+LN_SWITCH_EXPRESSION: FAIL\n");
+ printf("Failed to switch expression video: %s\n", video_path);
+ return ERRCODE_FAIL;
+ }
+}
static const at_cmd_table_t g_ln_api_cmd[] = {
/* ----------------------------------- VAD ---------------------------------- */
{(char *)"AT^LN_SLEEP_MODE_END", ln_sleep_mode_end_at, (char *)"哄睡模式结束: AT^LN_SLEEP_MODE_END"},
{(char *)"AT^LN_DOWNLOAD_EMOJI", ln_download_emoji_at, (char *)"下载表情: AT^LN_DOWNLOAD_EMOJI[=characterId,eyesColor,eyesShape]"},
{(char *)"AT^LN_CHAT_STAMINA_DEMO", ln_chat_stamina_demo_at, (char *)"演示对话体力/流量UI: AT^LN_CHAT_STAMINA_DEMO=member|enough|low|empty 或自定义"},
+ {(char *)"AT^LN_SWITCH_EXPRESSION", ln_switch_expression_at, (char *)"切换表情视频: AT^LN_SWITCH_EXPRESSION=<video_path>"},
/* 内存查看相关AT命令 */
{(char *)"AT^LN_MEMORY_INFO", ln_memory_info_at, (char *)"查看系统内存信息: AT^LN_MEMORY_INFO"},
{(char *)"AT^LN_FOLDER_SIZE", ln_folder_size_at, (char *)"查看文件夹大小: AT^LN_FOLDER_SIZE[=/path/to/folder]"},
/* 推送角色配置更改通知 */
push_character_config_change_notification(g_ln_character_config.character_id,
g_ln_character_config.character_name,
+ g_ln_character_config.avatar_eyes_shape,
g_ln_character_config.avatar_hair_color,
g_ln_character_config.avatar_eyes_color,
g_ln_character_config.avatar_hair_style,
- g_ln_character_config.avatar_eyes_shape,
g_ln_character_config.avatar_screen_image_as_emoji);
cJSON_Delete(root);
const char *ec = eyesColor ? eyesColor : "";
const char *hs = hairStyle ? hairStyle : "";
(void)snprintf(payload, sizeof(payload) - 1, "%s|%s|%s|%s|%s|%s|%d", id,n, es, hc, ec, hs, screenImageAsEmoji ? 1 : 0);
+ printf("push_character_config_change_notification: characterId=%s, characterName=%s, eyesShape=%s, hairColor=%s, eyesColor=%s, hairStyle=%s, screenImageAsEmoji=%d\r\n", id, n, es, hc, ec, hs, screenImageAsEmoji ? 1 : 0);
SendMsgToUIService(HAND_CHARACTER_CONFIG_CHANGE_NOTIFY, 0, (void *)payload, (int32_t)strlen(payload));
}
(void)snprintf(payload, sizeof(payload) - 1, "%d|%s|%d|%s|%s", chatLeft, cd, flowLeft, fd, qr);
SendMsgToUIService(HAND_CHAT_STAMINA_NOTIFY, 0, (void *)payload, (int32_t)strlen(payload));
}
+// 切换表情视频
+bool switch_expression_video(const char *video_path)
+{
+ if (video_path == nullptr) {
+ printf("[LN][SWITCH_VIDEO] Error: video_path is null\n");
+ return false;
+ }
+
+ OHOS::ThunderBirdModel* mainView = OHOS::ThunderBirdModel::GetInstance();
+ if (mainView == nullptr) {
+ printf("[LN][SWITCH_VIDEO] Error: ThunderBirdModel instance is null\n");
+ return false;
+ }
+
+ bool result = mainView->SwitchExpressionVideo(video_path);
+ printf("[LN][SWITCH_VIDEO] Switching to video: %s, result: %s\n",
+ video_path, result ? "success" : "failed");
+
+ return result;
+}
#ifdef __cplusplus
};
#endif
\ No newline at end of file
int flowLeft,
const char *flowDesc,
const char *qrcodeUrl);
+// 切换表情视频
+bool switch_expression_video(const char *video_path);
+
#ifdef __cplusplus
}
#endif