794 lines
25 KiB
C++
794 lines
25 KiB
C++
#include "ConfigManager.h"
|
||
#include "VrError.h"
|
||
#include "VrLog.h"
|
||
#include "PathManager.h"
|
||
#include <QtCore/QJsonDocument>
|
||
#include <QtCore/QJsonObject>
|
||
#include <QtCore/QJsonArray>
|
||
#include <cstring>
|
||
#include <algorithm>
|
||
#include <fstream>
|
||
|
||
// SystemConfig 实现
|
||
CameraUIParam* SystemConfig::GetCameraUIParam(int cameraIndex)
|
||
{
|
||
for (auto& param : cameraUIParams) {
|
||
if (param.cameraIndex == cameraIndex) {
|
||
return ¶m;
|
||
}
|
||
}
|
||
return nullptr;
|
||
}
|
||
|
||
const CameraUIParam* SystemConfig::GetCameraUIParam(int cameraIndex) const
|
||
{
|
||
for (const auto& param : cameraUIParams) {
|
||
if (param.cameraIndex == cameraIndex) {
|
||
return ¶m;
|
||
}
|
||
}
|
||
return nullptr;
|
||
}
|
||
|
||
void SystemConfig::SetCameraUIParam(const CameraUIParam& param)
|
||
{
|
||
for (auto& existingParam : cameraUIParams) {
|
||
if (existingParam.cameraIndex == param.cameraIndex) {
|
||
existingParam = param;
|
||
return;
|
||
}
|
||
}
|
||
// 如果不存在,则添加新的
|
||
cameraUIParams.push_back(param);
|
||
}
|
||
|
||
void SystemConfig::EnsureCameraUIParam(int cameraIndex)
|
||
{
|
||
for (const auto& param : cameraUIParams) {
|
||
if (param.cameraIndex == cameraIndex) {
|
||
return; // 已存在
|
||
}
|
||
}
|
||
|
||
// 不存在,创建默认参数
|
||
CameraUIParam defaultParam;
|
||
defaultParam.cameraIndex = cameraIndex;
|
||
cameraUIParams.push_back(defaultParam);
|
||
}
|
||
|
||
// ConfigManager 实现
|
||
ConfigManager::ConfigManager()
|
||
: m_pVrConfig(nullptr)
|
||
, m_pConfigCmdShareMem(nullptr)
|
||
, m_bSharedMemMonitorRunning(false)
|
||
{
|
||
}
|
||
|
||
ConfigManager::~ConfigManager()
|
||
{
|
||
Shutdown();
|
||
}
|
||
|
||
bool ConfigManager::Initialize(const std::string& configFilePath)
|
||
{
|
||
LOG_INFO("ConfigManager initializing...\n");
|
||
|
||
// 保存配置文件路径
|
||
if (configFilePath.empty()) {
|
||
m_configFilePath = PathManager::GetConfigFilePath().toStdString();
|
||
} else {
|
||
m_configFilePath = configFilePath;
|
||
}
|
||
|
||
// 创建VrConfig实例
|
||
if (!IVrConfig::CreateInstance(&m_pVrConfig) || !m_pVrConfig) {
|
||
LOG_ERROR("Failed to create VrConfig instance\n");
|
||
return false;
|
||
}
|
||
|
||
// 加载配置文件
|
||
if (!LoadConfigFromFile(m_configFilePath)) {
|
||
LOG_WARNING("Failed to load config file, using default config\n");
|
||
_InitializeDefaultConfig();
|
||
}
|
||
|
||
LOG_INFO("ConfigManager initialized successfully\n");
|
||
return true;
|
||
}
|
||
|
||
void ConfigManager::Shutdown()
|
||
{
|
||
LOG_INFO("ConfigManager shutting down...\n");
|
||
|
||
// 停止共享内存监听
|
||
StopSharedMemoryMonitor();
|
||
|
||
// 清理监听器
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_listenersMutex);
|
||
m_listeners.clear();
|
||
}
|
||
|
||
// 释放VrConfig实例
|
||
if (m_pVrConfig) {
|
||
delete m_pVrConfig;
|
||
m_pVrConfig = nullptr;
|
||
}
|
||
|
||
LOG_INFO("ConfigManager shutdown completed\n");
|
||
}
|
||
|
||
SystemConfig ConfigManager::GetConfig() const
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
return m_systemConfig;
|
||
}
|
||
|
||
CameraUIParam ConfigManager::GetCameraUIParam(int cameraIndex) const
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
const CameraUIParam* param = m_systemConfig.GetCameraUIParam(cameraIndex);
|
||
if (param) {
|
||
return *param;
|
||
}
|
||
|
||
// 返回默认参数
|
||
CameraUIParam defaultParam;
|
||
defaultParam.cameraIndex = cameraIndex;
|
||
return defaultParam;
|
||
}
|
||
|
||
VrAlgorithmParams ConfigManager::GetAlgorithmParams() const
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
return m_systemConfig.configResult.algorithmParams;
|
||
}
|
||
|
||
ConfigResult ConfigManager::GetConfigResult() const
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
return m_systemConfig.configResult;
|
||
}
|
||
|
||
bool ConfigManager::UpdateCameraUIParam(int cameraIndex, const CameraUIParam& param)
|
||
{
|
||
bool changed = false;
|
||
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
|
||
CameraUIParam* existingParam = m_systemConfig.GetCameraUIParam(cameraIndex);
|
||
if (!existingParam || memcmp(existingParam, ¶m, sizeof(CameraUIParam)) != 0) {
|
||
m_systemConfig.SetCameraUIParam(param);
|
||
changed = true;
|
||
}
|
||
}
|
||
|
||
if (changed) {
|
||
_NotifyCameraParamChanged(cameraIndex);
|
||
LOG_INFO("Camera %d UI parameters updated\n", cameraIndex);
|
||
}
|
||
|
||
return true;
|
||
}
|
||
|
||
bool ConfigManager::UpdateAlgorithmParams(const VrAlgorithmParams& params)
|
||
{
|
||
bool changed = false;
|
||
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
|
||
if (memcmp(&m_systemConfig.configResult.algorithmParams, ¶ms, sizeof(VrAlgorithmParams)) != 0) {
|
||
m_systemConfig.configResult.algorithmParams = params;
|
||
changed = true;
|
||
}
|
||
}
|
||
|
||
if (changed) {
|
||
_NotifyAlgorithmParamChanged();
|
||
LOG_INFO("Algorithm parameters updated\n");
|
||
}
|
||
|
||
return true;
|
||
}
|
||
|
||
bool ConfigManager::UpdateFullConfig(const SystemConfig& config)
|
||
{
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
m_systemConfig = config;
|
||
}
|
||
|
||
_NotifyConfigChanged();
|
||
LOG_INFO("Full configuration updated\n");
|
||
|
||
return true;
|
||
}
|
||
|
||
bool ConfigManager::LoadConfigFromFile(const std::string& filePath)
|
||
{
|
||
if (!m_pVrConfig) {
|
||
LOG_ERROR("VrConfig instance not available\n");
|
||
return false;
|
||
}
|
||
|
||
try {
|
||
// 首先检查文件是否存在
|
||
std::ifstream fileCheck(filePath);
|
||
if (!fileCheck.good()) {
|
||
LOG_ERROR("Configuration file not found or cannot be read: %s\n", filePath.c_str());
|
||
return false;
|
||
}
|
||
fileCheck.close();
|
||
|
||
LOG_DEBUG("%d %s\n", __LINE__, filePath.c_str());
|
||
|
||
// 加载配置文件
|
||
int ret = m_pVrConfig->LoadConfig(filePath, m_systemConfig.configResult);
|
||
if (ret != LOAD_CONFIG_SUCCESS) {
|
||
LOG_ERROR("Failed to load config file directly, error code: %d\n", ret);
|
||
return false;
|
||
}
|
||
LOG_DEBUG("ConfigResult loaded successfully\n");
|
||
return true;
|
||
|
||
} catch (const std::exception& e) {
|
||
LOG_ERROR("Failed to load configuration from file %s: %s\n", filePath.c_str(), e.what());
|
||
return false;
|
||
} catch (...) {
|
||
LOG_ERROR("Unknown exception while loading configuration from file %s\n", filePath.c_str());
|
||
return false;
|
||
}
|
||
}
|
||
|
||
bool ConfigManager::SaveConfigToFile(const std::string& filePath)
|
||
{
|
||
if (!m_pVrConfig) {
|
||
LOG_ERROR("VrConfig instance not available\n");
|
||
return false;
|
||
}
|
||
|
||
try {
|
||
ConfigResult configResult;
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
configResult = m_systemConfig.configResult;
|
||
}
|
||
|
||
bool result = m_pVrConfig->SaveConfig(filePath, configResult);
|
||
if (result) {
|
||
LOG_INFO("Configuration saved to file: %s\n", filePath.c_str());
|
||
} else {
|
||
LOG_ERROR("Failed to save configuration to file: %s\n", filePath.c_str());
|
||
}
|
||
|
||
return result;
|
||
|
||
} catch (const std::exception& e) {
|
||
LOG_ERROR("Exception while saving configuration to file %s: %s\n", filePath.c_str(), e.what());
|
||
return false;
|
||
}
|
||
}
|
||
|
||
void ConfigManager::AddConfigChangeListener(std::shared_ptr<IConfigChangeListener> listener)
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_listenersMutex);
|
||
m_listeners.push_back(listener);
|
||
|
||
LOG_DEBUG("Config change listener added, total listeners: %zu\n", m_listeners.size());
|
||
}
|
||
|
||
void ConfigManager::RemoveConfigChangeListener(std::shared_ptr<IConfigChangeListener> listener)
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_listenersMutex);
|
||
|
||
auto it = std::find_if(m_listeners.begin(), m_listeners.end(),
|
||
[&listener](const std::weak_ptr<IConfigChangeListener>& weak_listener) {
|
||
return weak_listener.lock() == listener;
|
||
});
|
||
|
||
if (it != m_listeners.end()) {
|
||
m_listeners.erase(it);
|
||
LOG_DEBUG("Config change listener removed, remaining listeners: %zu\n", m_listeners.size());
|
||
}
|
||
}
|
||
|
||
bool ConfigManager::StartSharedMemoryMonitor()
|
||
{
|
||
if (m_bSharedMemMonitorRunning) {
|
||
LOG_WARNING("Shared memory monitor is already running\n");
|
||
return true;
|
||
}
|
||
|
||
if (!_InitializeSharedMemory()) {
|
||
LOG_ERROR("Failed to initialize shared memory for config monitor\n");
|
||
return false;
|
||
}
|
||
|
||
// 启动监听线程
|
||
m_bSharedMemMonitorRunning = true;
|
||
m_sharedMemMonitorThread = std::thread(&ConfigManager::_SharedMemoryMonitorThread, this);
|
||
|
||
LOG_INFO("Shared memory monitor started\n");
|
||
return true;
|
||
}
|
||
|
||
void ConfigManager::StopSharedMemoryMonitor()
|
||
{
|
||
if (!m_bSharedMemMonitorRunning) {
|
||
return;
|
||
}
|
||
|
||
m_bSharedMemMonitorRunning = false;
|
||
|
||
// 等待线程结束
|
||
if (m_sharedMemMonitorThread.joinable()) {
|
||
m_sharedMemMonitorThread.join();
|
||
}
|
||
|
||
// 清理共享内存
|
||
_CleanupSharedMemory();
|
||
|
||
LOG_INFO("Shared memory monitor stopped\n");
|
||
}
|
||
|
||
void ConfigManager::_SharedMemoryMonitorThread()
|
||
{
|
||
LOG_INFO("Shared memory monitor thread started\n");
|
||
|
||
ConfigCmdSharedData lastData;
|
||
memset(&lastData, 0, sizeof(ConfigCmdSharedData));
|
||
|
||
while (m_bSharedMemMonitorRunning) {
|
||
try {
|
||
// 锁定共享内存并读取数据
|
||
int ret = m_pConfigCmdShareMem->Lock(1000); // 1秒超时
|
||
if (ret != SUCCESS) {
|
||
if (ret != SHAREMEM_ERR_TIMEOUT) {
|
||
LOG_ERROR("Failed to lock shared memory for config monitor, error: %d\n", ret);
|
||
}
|
||
std::this_thread::sleep_for(std::chrono::milliseconds(100));
|
||
continue;
|
||
}
|
||
|
||
ConfigCmdSharedData currentData;
|
||
ret = m_pConfigCmdShareMem->ReadData(0, ¤tData, sizeof(ConfigCmdSharedData));
|
||
m_pConfigCmdShareMem->Unlock();
|
||
|
||
if (ret < 0) {
|
||
LOG_ERROR("Failed to read shared memory for config monitor, error: %d\n", ret);
|
||
std::this_thread::sleep_for(std::chrono::milliseconds(100));
|
||
continue;
|
||
}
|
||
|
||
// 检查魔数和版本
|
||
if (strcmp(currentData.header.magic, "VRCFG001") != 0 || currentData.header.version != 1) {
|
||
std::this_thread::sleep_for(std::chrono::milliseconds(100));
|
||
continue;
|
||
}
|
||
|
||
// 检查是否有新数据
|
||
if (!currentData.header.hasNewData) {
|
||
std::this_thread::sleep_for(std::chrono::milliseconds(100));
|
||
continue;
|
||
}
|
||
|
||
// 验证校验和
|
||
if (!currentData.ValidateChecksum()) {
|
||
LOG_ERROR("Config command data checksum validation failed\n");
|
||
std::this_thread::sleep_for(std::chrono::milliseconds(100));
|
||
continue;
|
||
}
|
||
|
||
// 检查是否是新的命令(与上次不同)
|
||
if (memcmp(&lastData.data, ¤tData.data, sizeof(ConfigCmdData)) == 0) {
|
||
std::this_thread::sleep_for(std::chrono::milliseconds(100));
|
||
continue;
|
||
}
|
||
|
||
// 应用配置命令
|
||
LOG_INFO("Received new config command, type: %d, timestamp: %s\n",
|
||
currentData.data.cmdType, currentData.data.timestamp);
|
||
|
||
if (_ApplyConfigCommand(currentData.data)) {
|
||
LOG_INFO("Config command applied successfully\n");
|
||
} else {
|
||
LOG_ERROR("Failed to apply config command\n");
|
||
}
|
||
|
||
// 更新最后处理的数据
|
||
lastData = currentData;
|
||
|
||
// 标记数据已处理(清除新数据标志)
|
||
ret = m_pConfigCmdShareMem->Lock(1000);
|
||
if (ret == SUCCESS) {
|
||
ConfigCmdSharedData clearData = currentData;
|
||
clearData.header.hasNewData = false;
|
||
m_pConfigCmdShareMem->WriteData(0, &clearData, sizeof(ConfigCmdSharedData));
|
||
m_pConfigCmdShareMem->Unlock();
|
||
}
|
||
|
||
} catch (const std::exception& e) {
|
||
LOG_ERROR("Exception in config monitor thread: %s\n", e.what());
|
||
}
|
||
|
||
std::this_thread::sleep_for(std::chrono::milliseconds(100));
|
||
}
|
||
|
||
LOG_INFO("Shared memory monitor thread stopped\n");
|
||
}
|
||
|
||
bool ConfigManager::_ApplyConfigCommand(const ConfigCmdData& configData)
|
||
{
|
||
switch (configData.cmdType) {
|
||
case CONFIG_CMD_CAMERA_EXPOSE:
|
||
return _ApplyCameraExpose(configData.cameraParam);
|
||
|
||
case CONFIG_CMD_CAMERA_GAIN:
|
||
return _ApplyCameraGain(configData.cameraParam);
|
||
|
||
case CONFIG_CMD_CAMERA_FRAMERATE:
|
||
return _ApplyCameraFrameRate(configData.cameraParam);
|
||
|
||
case CONFIG_CMD_CAMERA_SWING:
|
||
return _ApplyCameraSwing(configData.swingParam);
|
||
|
||
case CONFIG_CMD_ALGO_PARAM:
|
||
return _ApplyAlgoParam(configData.algoParam);
|
||
|
||
case CONFIG_CMD_CALIB_PARAM:
|
||
return _ApplyCalibParam(configData.calibParam);
|
||
|
||
case CONFIG_CMD_FULL_CONFIG:
|
||
return _ApplyFullConfig(configData.fullConfigParam);
|
||
|
||
default:
|
||
LOG_ERROR("Unknown config command type: %d\n", configData.cmdType);
|
||
return false;
|
||
}
|
||
}
|
||
|
||
bool ConfigManager::_ApplyCameraExpose(const CameraConfigParam& param)
|
||
{
|
||
LOG_INFO("Applying camera expose setting: camera %d, expose time: %.2f\n",
|
||
param.cameraIndex, param.exposeTime);
|
||
|
||
if (param.cameraIndex == -1) {
|
||
// 应用到所有相机
|
||
bool changed = false;
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
for (auto& cameraParam : m_systemConfig.cameraUIParams) {
|
||
if (cameraParam.exposeTime != param.exposeTime) {
|
||
cameraParam.exposeTime = param.exposeTime;
|
||
changed = true;
|
||
}
|
||
}
|
||
}
|
||
if (changed) {
|
||
_NotifyConfigChanged();
|
||
}
|
||
} else {
|
||
// 应用到指定相机
|
||
bool changed = false;
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
m_systemConfig.EnsureCameraUIParam(param.cameraIndex);
|
||
CameraUIParam* cameraParam = m_systemConfig.GetCameraUIParam(param.cameraIndex);
|
||
if (cameraParam && cameraParam->exposeTime != param.exposeTime) {
|
||
cameraParam->exposeTime = param.exposeTime;
|
||
changed = true;
|
||
}
|
||
}
|
||
if (changed) {
|
||
_NotifyCameraParamChanged(param.cameraIndex);
|
||
}
|
||
}
|
||
|
||
return true;
|
||
}
|
||
|
||
bool ConfigManager::_ApplyCameraGain(const CameraConfigParam& param)
|
||
{
|
||
LOG_INFO("Applying camera gain setting: camera %d, gain: %.2f\n",
|
||
param.cameraIndex, param.gain);
|
||
|
||
if (param.cameraIndex == -1) {
|
||
// 应用到所有相机
|
||
bool changed = false;
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
for (auto& cameraParam : m_systemConfig.cameraUIParams) {
|
||
if (cameraParam.gain != param.gain) {
|
||
cameraParam.gain = param.gain;
|
||
changed = true;
|
||
}
|
||
}
|
||
}
|
||
if (changed) {
|
||
_NotifyConfigChanged();
|
||
}
|
||
} else {
|
||
// 应用到指定相机
|
||
bool changed = false;
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
m_systemConfig.EnsureCameraUIParam(param.cameraIndex);
|
||
CameraUIParam* cameraParam = m_systemConfig.GetCameraUIParam(param.cameraIndex);
|
||
if (cameraParam && cameraParam->gain != param.gain) {
|
||
cameraParam->gain = param.gain;
|
||
changed = true;
|
||
}
|
||
}
|
||
if (changed) {
|
||
_NotifyCameraParamChanged(param.cameraIndex);
|
||
}
|
||
}
|
||
|
||
return true;
|
||
}
|
||
|
||
bool ConfigManager::_ApplyCameraFrameRate(const CameraConfigParam& param)
|
||
{
|
||
LOG_INFO("Applying camera frame rate setting: camera %d, frame rate: %.2f\n",
|
||
param.cameraIndex, param.frameRate);
|
||
|
||
if (param.cameraIndex == -1) {
|
||
// 应用到所有相机
|
||
bool changed = false;
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
for (auto& cameraParam : m_systemConfig.cameraUIParams) {
|
||
if (cameraParam.frameRate != param.frameRate) {
|
||
cameraParam.frameRate = param.frameRate;
|
||
changed = true;
|
||
}
|
||
}
|
||
}
|
||
if (changed) {
|
||
_NotifyConfigChanged();
|
||
}
|
||
} else {
|
||
// 应用到指定相机
|
||
bool changed = false;
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
m_systemConfig.EnsureCameraUIParam(param.cameraIndex);
|
||
CameraUIParam* cameraParam = m_systemConfig.GetCameraUIParam(param.cameraIndex);
|
||
if (cameraParam && cameraParam->frameRate != param.frameRate) {
|
||
cameraParam->frameRate = param.frameRate;
|
||
changed = true;
|
||
}
|
||
}
|
||
if (changed) {
|
||
_NotifyCameraParamChanged(param.cameraIndex);
|
||
}
|
||
}
|
||
|
||
return true;
|
||
}
|
||
|
||
bool ConfigManager::_ApplyCameraSwing(const SwingConfigParam& param)
|
||
{
|
||
LOG_INFO("Applying camera swing setting: camera %d, speed: %.2f, angles: %.2f-%.2f\n",
|
||
param.cameraIndex, param.swingSpeed, param.startAngle, param.stopAngle);
|
||
|
||
if (param.cameraIndex == -1) {
|
||
// 应用到所有相机
|
||
bool changed = false;
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
for (auto& cameraParam : m_systemConfig.cameraUIParams) {
|
||
if (cameraParam.swingSpeed != param.swingSpeed ||
|
||
cameraParam.swingStartAngle != param.startAngle ||
|
||
cameraParam.swingStopAngle != param.stopAngle) {
|
||
cameraParam.swingSpeed = param.swingSpeed;
|
||
cameraParam.swingStartAngle = param.startAngle;
|
||
cameraParam.swingStopAngle = param.stopAngle;
|
||
changed = true;
|
||
}
|
||
}
|
||
}
|
||
if (changed) {
|
||
_NotifyConfigChanged();
|
||
}
|
||
} else {
|
||
// 应用到指定相机
|
||
bool changed = false;
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
m_systemConfig.EnsureCameraUIParam(param.cameraIndex);
|
||
CameraUIParam* cameraParam = m_systemConfig.GetCameraUIParam(param.cameraIndex);
|
||
if (cameraParam && (cameraParam->swingSpeed != param.swingSpeed ||
|
||
cameraParam->swingStartAngle != param.startAngle ||
|
||
cameraParam->swingStopAngle != param.stopAngle)) {
|
||
cameraParam->swingSpeed = param.swingSpeed;
|
||
cameraParam->swingStartAngle = param.startAngle;
|
||
cameraParam->swingStopAngle = param.stopAngle;
|
||
changed = true;
|
||
}
|
||
}
|
||
if (changed) {
|
||
_NotifyCameraParamChanged(param.cameraIndex);
|
||
}
|
||
}
|
||
|
||
return true;
|
||
}
|
||
|
||
bool ConfigManager::_ApplyAlgoParam(const AlgoConfigParam& param)
|
||
{
|
||
LOG_INFO("Applying algorithm parameter: %s = %.3f\n", param.paramName, param.paramValue);
|
||
|
||
// 算法参数设置暂时只记录日志,具体实现可以根据需要扩展
|
||
return true;
|
||
}
|
||
|
||
bool ConfigManager::_ApplyCalibParam(const CalibConfigParam& param)
|
||
{
|
||
LOG_INFO("Applying calibration parameter for camera %d\n", param.cameraIndex);
|
||
|
||
// 标定参数设置暂时只记录日志,具体实现可以根据需要扩展
|
||
return true;
|
||
}
|
||
|
||
bool ConfigManager::_ApplyFullConfig(const FullConfigParam& param)
|
||
{
|
||
LOG_INFO("Applying full configuration update\n");
|
||
|
||
// JSON反序列化和应用完整配置
|
||
SystemConfig newConfig;
|
||
if (_DeserializeConfigFromJson(param.configJson, newConfig)) {
|
||
UpdateFullConfig(newConfig);
|
||
return true;
|
||
}
|
||
|
||
LOG_ERROR("Failed to deserialize full configuration from JSON\n");
|
||
return false;
|
||
}
|
||
|
||
void ConfigManager::_NotifyConfigChanged()
|
||
{
|
||
SystemConfig currentConfig = GetConfig();
|
||
|
||
std::lock_guard<std::mutex> lock(m_listenersMutex);
|
||
_CleanupExpiredListeners();
|
||
|
||
for (auto& weakListener : m_listeners) {
|
||
if (auto listener = weakListener.lock()) {
|
||
try {
|
||
listener->OnSystemConfigChanged(currentConfig);
|
||
} catch (const std::exception& e) {
|
||
LOG_ERROR("Exception in config change listener: %s\n", e.what());
|
||
}
|
||
}
|
||
}
|
||
}
|
||
|
||
void ConfigManager::_NotifyCameraParamChanged(int cameraIndex)
|
||
{
|
||
CameraUIParam cameraParam = GetCameraUIParam(cameraIndex);
|
||
|
||
std::lock_guard<std::mutex> lock(m_listenersMutex);
|
||
_CleanupExpiredListeners();
|
||
|
||
for (auto& weakListener : m_listeners) {
|
||
if (auto listener = weakListener.lock()) {
|
||
try {
|
||
listener->OnCameraParamChanged(cameraIndex, cameraParam);
|
||
} catch (const std::exception& e) {
|
||
LOG_ERROR("Exception in camera param change listener: %s\n", e.what());
|
||
}
|
||
}
|
||
}
|
||
}
|
||
|
||
void ConfigManager::_NotifyAlgorithmParamChanged()
|
||
{
|
||
VrAlgorithmParams algorithmParams = GetAlgorithmParams();
|
||
|
||
std::lock_guard<std::mutex> lock(m_listenersMutex);
|
||
_CleanupExpiredListeners();
|
||
|
||
for (auto& weakListener : m_listeners) {
|
||
if (auto listener = weakListener.lock()) {
|
||
try {
|
||
listener->OnAlgorithmParamChanged(algorithmParams);
|
||
} catch (const std::exception& e) {
|
||
LOG_ERROR("Exception in algorithm param change listener: %s\n", e.what());
|
||
}
|
||
}
|
||
}
|
||
}
|
||
|
||
void ConfigManager::_CleanupExpiredListeners()
|
||
{
|
||
// 移除已过期的weak_ptr
|
||
m_listeners.erase(
|
||
std::remove_if(m_listeners.begin(), m_listeners.end(),
|
||
[](const std::weak_ptr<IConfigChangeListener>& weak_listener) {
|
||
return weak_listener.expired();
|
||
}),
|
||
m_listeners.end());
|
||
}
|
||
|
||
bool ConfigManager::_InitializeSharedMemory()
|
||
{
|
||
if (m_pConfigCmdShareMem) {
|
||
return true; // 已经初始化
|
||
}
|
||
|
||
m_pConfigCmdShareMem = CreateShareMemInstance();
|
||
if (!m_pConfigCmdShareMem) {
|
||
return false;
|
||
}
|
||
|
||
// 尝试打开已存在的共享内存,如果不存在则创建
|
||
int ret = m_pConfigCmdShareMem->CreateOrOpen(CONFIG_CMD_SHARED_MEM_NAME, CONFIG_CMD_SHARED_MEM_SIZE, false);
|
||
if (ret != SUCCESS) {
|
||
// 如果打开失败,尝试创建新的
|
||
ret = m_pConfigCmdShareMem->CreateOrOpen(CONFIG_CMD_SHARED_MEM_NAME, CONFIG_CMD_SHARED_MEM_SIZE, true);
|
||
if (ret != SUCCESS) {
|
||
_CleanupSharedMemory();
|
||
return false;
|
||
}
|
||
}
|
||
|
||
// 映射内存
|
||
void* mappedAddr = m_pConfigCmdShareMem->MapView();
|
||
if (!mappedAddr) {
|
||
_CleanupSharedMemory();
|
||
return false;
|
||
}
|
||
|
||
return true;
|
||
}
|
||
|
||
void ConfigManager::_CleanupSharedMemory()
|
||
{
|
||
if (m_pConfigCmdShareMem) {
|
||
m_pConfigCmdShareMem->UnmapView();
|
||
m_pConfigCmdShareMem->Close();
|
||
DestroyShareMemInstance(m_pConfigCmdShareMem);
|
||
m_pConfigCmdShareMem = nullptr;
|
||
}
|
||
}
|
||
|
||
bool ConfigManager::_InitializeDefaultConfig()
|
||
{
|
||
std::lock_guard<std::mutex> lock(m_configMutex);
|
||
|
||
// 初始化默认ConfigResult(所有字段自动使用IVrConfig.h中定义的默认值)
|
||
m_systemConfig.configResult = ConfigResult();
|
||
|
||
// 添加默认相机配置
|
||
DeviceInfo defaultCamera;
|
||
defaultCamera.name = "Camera1";
|
||
defaultCamera.ip = "192.168.1.100";
|
||
m_systemConfig.configResult.cameraList.push_back(defaultCamera);
|
||
|
||
// 初始化默认的相机UI参数
|
||
m_systemConfig.cameraUIParams.clear();
|
||
CameraUIParam defaultCameraUI;
|
||
defaultCameraUI.cameraIndex = 1;
|
||
m_systemConfig.cameraUIParams.push_back(defaultCameraUI);
|
||
|
||
LOG_INFO("Default configuration initialized\n");
|
||
return true;
|
||
}
|
||
|
||
std::string ConfigManager::_SerializeConfigToJson(const SystemConfig& config)
|
||
{
|
||
// 简化的JSON序列化实现
|
||
// 在实际项目中,建议使用完整的JSON库
|
||
return "{}"; // 暂时返回空JSON
|
||
}
|
||
|
||
bool ConfigManager::_DeserializeConfigFromJson(const std::string& json, SystemConfig& config)
|
||
{
|
||
// 简化的JSON反序列化实现
|
||
// 在实际项目中,建议使用完整的JSON库
|
||
return false; // 暂时返回失败
|
||
}
|