新增: 添加工作目录设置相关函数

📝 修改: 实现工作目录设置及自动工作目录的逻辑
📝 修改: 更新菜单和命令行输入设置涉及的逻辑
🔧 修复: 修改自启动相关的注册表键名生成逻辑
main
机械师 2025-09-12 17:51:05 +08:00
parent eb3a5aa939
commit 286bd74835
4 changed files with 59 additions and 17 deletions

View File

@ -44,8 +44,9 @@ public:
void SetStopCommand(const std::string& command, int timeout_ms = 5000);
void SetEnvironmentVariables(const std::map<std::string, std::string>& env_vars);
void SetOutputEncoding(OutputEncoding encoding);
void SetAutoWorkingDir(bool auto_dir);
// 新增:工作目录设置
// 工作目录设置
void SetWorkingDirectory(const std::string& working_dir);
std::string GetWorkingDirectory() const;

View File

@ -26,38 +26,40 @@ CLIProcess::CLIProcess() {
max_log_lines_ = 1000;
stop_timeout_ms_ = 5000;
output_encoding_ = OutputEncoding::AUTO_DETECT;
use_auto_working_dir_ = false; // 自动工作目录
use_auto_working_dir_ = true; // 自动工作目录
}
CLIProcess::~CLIProcess() {
Stop();
CleanupResources();
}
// 新增:设置工作目录
void CLIProcess::SetAutoWorkingDir(const bool auto_dir) {
use_auto_working_dir_ = auto_dir;
}
// 设置工作目录
void CLIProcess::SetWorkingDirectory(const std::string& working_dir) {
std::lock_guard<std::mutex> lock(working_dir_mutex_);
if (working_dir.empty()) {
use_auto_working_dir_ = true;
// use_auto_working_dir_ = true;
working_directory_.clear();
} else {
if (DirectoryExists(working_dir)) {
working_directory_ = GetAbsolutePath(working_dir);
use_auto_working_dir_ = false;
AddLog("工作目录已设置为: " + working_directory_);
// AddLog("工作目录已设置为: " + working_directory_);
} else {
AddLog("警告: 指定的工作目录不存在: " + working_dir);
}
}
}
// 新增:获取当前工作目录设置
// 获取当前工作目录设置
std::string CLIProcess::GetWorkingDirectory() const {
std::lock_guard<std::mutex> lock(working_dir_mutex_);
return working_directory_;
}
// 新增:从命令中提取目录路径
// 从命令中提取目录路径
std::string CLIProcess::ExtractDirectoryFromCommand(const std::string& command) {
if (command.empty()) return "";
@ -470,7 +472,7 @@ void CLIProcess::Start(const std::string& command) {
// AddLog("环境变量设置完成,数量: " + std::to_string(environment_variables_.size()));
} else {
AddLog("未设置自定义环境变量,使用默认环境 PWD:" + WideToString(working_dir));
// AddLog("未设置自定义环境变量,使用默认环境 PWD:" + WideToString(working_dir));
}
BOOL result = CreateProcess(

View File

@ -111,6 +111,7 @@ bool Manager::Initialize() {
m_app_state.LoadSettings();
m_app_state.auto_start = IsAutoStartEnabled();
m_app_state.ApplySettings();
m_app_state.SaveSettings();
#ifdef _WIN32
m_tray->UpdateWebUrl(StringToWide(m_app_state.web_url));
@ -122,6 +123,8 @@ bool Manager::Initialize() {
// 如果开启了开机自启动且有启动命令,则自动启动子进程
if (m_app_state.auto_start && strlen(m_app_state.command_input) > 0) {
m_app_state.cli_process.Start(m_app_state.command_input);
m_app_state.show_main_window = false;
HideMainWindow();
}
m_tray->UpdateStatus(m_app_state.cli_process.IsRunning() ? L"运行中" : L"已停止", m_app_state.cli_process.GetPid());
m_initialized = true;
@ -235,9 +238,11 @@ void Manager::RenderUI() {
// 设置默认布局(仅在第一次运行时)
SetupDefaultDockingLayout(m_dockspace_id);
ImGuiWindowClass window_class;
window_class.DockNodeFlagsOverrideSet = ImGuiDockNodeFlags_NoWindowMenuButton;
ImGui::SetNextWindowClass(&window_class);
RenderMainContent();
ImGui::End();
@ -541,7 +546,11 @@ void Manager::RenderSettingsMenu() {
SetAutoStart(m_app_state.auto_start);
m_app_state.settings_dirty = true;
}
if (ImGui::MenuItem("自动工作路径", nullptr, m_app_state.auto_working_dir)) {
m_app_state.auto_working_dir = !m_app_state.auto_working_dir;
m_app_state.cli_process.SetAutoWorkingDir(m_app_state.auto_working_dir);
m_app_state.settings_dirty = true;
}
ImGui::Separator();
ImGui::Text("日志设置");
if (ImGui::InputInt("最大日志行数", &m_app_state.max_log_lines, 100, 500)) {
@ -732,7 +741,7 @@ void Manager::RenderOutputEncodingSettings() {
void Manager::RenderControlPanel(float buttonWidth, float buttonHeight, float inputWidth) {
// 启动命令输入区域
ImGui::SeparatorText("启动命令");
ImGui::SeparatorText("CLI程序");
// 命令输入框和历史记录按钮
ImGui::SetNextItemWidth(inputWidth);
@ -749,7 +758,11 @@ void Manager::RenderControlPanel(float buttonWidth, float buttonHeight, float in
if (show_command_history_) {
RenderCommandHistory();
}
ImGui::SeparatorText("工作路径(留空且开启自动路径为文件父路径、不然为管理器路径)");
if (ImGui::InputText("##工作路径", m_app_state.working_directory, IM_ARRAYSIZE(m_app_state.working_directory))) {
m_app_state.cli_process.SetWorkingDirectory(m_app_state.working_directory);
m_app_state.settings_dirty = true;
}
ImGui::Spacing();
// 控制按钮组
@ -758,6 +771,11 @@ void Manager::RenderControlPanel(float buttonWidth, float buttonHeight, float in
if (strlen(m_app_state.command_input) > 0) {
m_app_state.cli_process.Start(m_app_state.command_input);
m_app_state.AddCommandToHistory(m_app_state.command_input);
if (strlen(m_app_state.working_directory) > 0) {
m_app_state.cli_process.SetWorkingDirectory(m_app_state.working_directory);
}else {
strncpy_s(m_app_state.working_directory,m_app_state.cli_process.GetWorkingDirectory().c_str(),sizeof(m_app_state.working_directory)-1);
}
m_tray->UpdateStatus(m_app_state.cli_process.IsRunning() ? L"运行中" : L"已停止",
m_app_state.cli_process.GetPid());
}
@ -1133,7 +1151,6 @@ void Manager::ContentScaleCallback(GLFWwindow *window, float xscale, float yscal
}
}
#ifdef USE_WIN32_BACKEND
bool Manager::InitializeWin32() {
m_wc = {};
@ -1478,7 +1495,6 @@ void Manager::ReloadFonts() const {
#endif
}
#ifdef __APPLE__
// macOS 特定的辅助函数声明
extern "C" {

View File

@ -32,12 +32,22 @@ void SetAutoStart(bool enable) {
WCHAR exePath[MAX_PATH];
GetModuleFileName(NULL, exePath, MAX_PATH);
// 计算路径的简单哈希值
size_t hash = 0;
for (size_t i = 0; i < wcslen(exePath); i++) {
hash = (hash * 31) + exePath[i];
}
// 创建包含哈希的键名
WCHAR keyName[32];
swprintf(keyName, 32, L"CLIManager_%08X", static_cast<unsigned int>(hash));
if (enable) {
RegSetValueEx(hKey, L"CLIManager", 0, REG_SZ,
RegSetValueEx(hKey, keyName, 0, REG_SZ,
(BYTE*)exePath, (wcslen(exePath) + 1) * sizeof(WCHAR));
}
else {
RegDeleteValue(hKey, L"CLIManager");
RegDeleteValue(hKey, keyName);
}
RegCloseKey(hKey);
}
@ -49,8 +59,21 @@ bool IsAutoStartEnabled() {
if (RegOpenKeyEx(HKEY_CURRENT_USER, path, 0, KEY_READ, &hKey) != ERROR_SUCCESS)
return false;
WCHAR exePath[MAX_PATH];
GetModuleFileName(NULL, exePath, MAX_PATH);
// 计算相同的哈希值
size_t hash = 0;
for (size_t i = 0; i < wcslen(exePath); i++) {
hash = (hash * 31) + exePath[i];
}
// 创建相同的键名用于查询
WCHAR keyName[32];
swprintf(keyName, 32, L"CLIManager_%08X", static_cast<unsigned int>(hash));
DWORD type, size = 0;
bool exists = (RegQueryValueEx(hKey, L"CLIManager", NULL, &type, NULL, &size) == ERROR_SUCCESS);
bool exists = (RegQueryValueEx(hKey, keyName, NULL, &type, NULL, &size) == ERROR_SUCCESS);
RegCloseKey(hKey);
return exists;