#include "embodied_ai_agent.h" #include #include #include #include namespace hhb { namespace core { EmbodiedAIAgent::EmbodiedAIAgent() : llmClient_(LLMClient::getInstance()), toolRegistry_(ToolRegistry::getInstance()), state_(EmbodiedAIState::Idle), processing_(false) { } EmbodiedAIAgent::~EmbodiedAIAgent() { if (pendingFuture_.valid()) { pendingFuture_.wait(); } } void EmbodiedAIAgent::initialize(const std::string& endpoint, const std::string& api_key, const std::string& model, GeometryAPI* geometry_api) { llmClient_.setEndpoint(endpoint); llmClient_.setApiKey(api_key); llmClient_.setModel(model); llmClient_.setTimeout(60000); // 初始化工具注册表,将几何分析能力暴露给 LLM toolRegistry_.initialize(geometry_api); // 清除旧工具并注册所有工具到 LLMClient llmClient_.clearTools(); toolRegistry_.registerAllToLLM(llmClient_); std::cout << "[EmbodiedAIAgent] Initialized with endpoint: " << endpoint << " model: " << model << std::endl; std::cout << "[EmbodiedAIAgent] Registered tools: "; for (const auto& name : llmClient_.getRegisteredToolNames()) { std::cout << name << " "; } std::cout << std::endl; } void EmbodiedAIAgent::processInputAsync(const std::string& user_input) { if (processing_) { std::cout << "[EmbodiedAIAgent] Still processing previous request" << std::endl; return; } processing_ = true; setState(EmbodiedAIState::Processing); // 添加用户消息到历史 { std::lock_guard lock(historyMutex_); auto now = std::chrono::system_clock::now(); auto time_t = std::chrono::system_clock::to_time_t(now); std::stringstream ss; ss << std::put_time(std::localtime(&time_t), "%H:%M:%S"); chatHistory_.push_back({user_input, true, ss.str()}); } // 异步执行具身智能闭环 pendingFuture_ = std::async(std::launch::async, [this, user_input]() -> std::string { std::cout << "[EmbodiedAIAgent] Starting embodied query for: " << user_input << std::endl; setState(EmbodiedAIState::Processing); // 调用 LLMClient 的 embodiedQuery 方法 // 该方法实现了完整的闭环:用户输入 -> LLM 解析 -> 工具执行 -> 结果反馈 -> LLM 总结 std::string response = llmClient_.embodiedQuery(user_input, 3); // 检查工具执行结果,更新高亮 if (toolRegistry_.hasNewResult()) { auto indices = toolRegistry_.getHighlightIndices(); auto type = toolRegistry_.getHighlightType(); auto desc = toolRegistry_.getLastAnalysisDesc(); std::cout << "[EmbodiedAIAgent] Tool result: " << indices.size() << " indices, type=" << static_cast(type) << std::endl; // 通知渲染层更新高亮 if (resultCallback_) { resultCallback_(indices, type, desc); } toolRegistry_.clearNewResult(); } return response; }); } std::string EmbodiedAIAgent::processInput(const std::string& user_input) { // 添加用户消息到历史 { std::lock_guard lock(historyMutex_); auto now = std::chrono::system_clock::now(); auto time_t = std::chrono::system_clock::to_time_t(now); std::stringstream ss; ss << std::put_time(std::localtime(&time_t), "%H:%M:%S"); chatHistory_.push_back({user_input, true, ss.str()}); } setState(EmbodiedAIState::Processing); std::string response = llmClient_.embodiedQuery(user_input, 3); // 检查工具执行结果 if (toolRegistry_.hasNewResult()) { auto indices = toolRegistry_.getHighlightIndices(); auto type = toolRegistry_.getHighlightType(); auto desc = toolRegistry_.getLastAnalysisDesc(); if (resultCallback_) { resultCallback_(indices, type, desc); } toolRegistry_.clearNewResult(); } // 添加 AI 回复到历史 { std::lock_guard lock(historyMutex_); auto now = std::chrono::system_clock::now(); auto time_t = std::chrono::system_clock::to_time_t(now); std::stringstream ss; ss << std::put_time(std::localtime(&time_t), "%H:%M:%S"); chatHistory_.push_back({response, false, ss.str()}); } lastResponse_ = response; if (response.find("[Error]") != std::string::npos) { lastError_ = response; setState(EmbodiedAIState::Error); } else { setState(EmbodiedAIState::Idle); } return response; } EmbodiedAIState EmbodiedAIAgent::getState() const { return state_.load(); } std::string EmbodiedAIAgent::getStateString() const { switch (state_.load()) { case EmbodiedAIState::Idle: return "Idle"; case EmbodiedAIState::Processing: return "Processing..."; case EmbodiedAIState::ToolExecuting: return "Executing Tool..."; case EmbodiedAIState::Responding: return "Generating Response..."; case EmbodiedAIState::Error: return "Error"; default: return "Unknown"; } } std::vector EmbodiedAIAgent::getChatHistory() const { std::lock_guard lock(historyMutex_); return chatHistory_; } std::string EmbodiedAIAgent::getLastResponse() const { return lastResponse_; } std::string EmbodiedAIAgent::getLastError() const { return lastError_; } bool EmbodiedAIAgent::isProcessing() const { return processing_.load(); } void EmbodiedAIAgent::clearHistory() { std::lock_guard lock(historyMutex_); chatHistory_.clear(); } void EmbodiedAIAgent::setStateCallback(StateCallback callback) { stateCallback_ = callback; } void EmbodiedAIAgent::setResultCallback(ResultCallback callback) { resultCallback_ = callback; } void EmbodiedAIAgent::setState(EmbodiedAIState state) { state_.store(state); if (stateCallback_) { stateCallback_(state); } } void EmbodiedAIAgent::checkPendingResult() { if (!pendingFuture_.valid()) return; auto status = pendingFuture_.wait_for(std::chrono::seconds(0)); if (status == std::future_status::ready) { std::string response = pendingFuture_.get(); // 添加 AI 回复到历史 { std::lock_guard lock(historyMutex_); auto now = std::chrono::system_clock::now(); auto time_t = std::chrono::system_clock::to_time_t(now); std::stringstream ss; ss << std::put_time(std::localtime(&time_t), "%H:%M:%S"); chatHistory_.push_back({response, false, ss.str()}); } lastResponse_ = response; processing_ = false; if (response.find("[Error]") != std::string::npos) { lastError_ = response; setState(EmbodiedAIState::Error); } else { setState(EmbodiedAIState::Idle); } } } } // namespace core } // namespace hhb