Initial commit to new repository

This commit is contained in:
2026-04-03 18:22:19 +09:00
commit 4458bb0f52
7672 changed files with 452440 additions and 0 deletions

View File

@@ -0,0 +1,943 @@
using System;
using System.CodeDom.Compiler;
using System.Collections.Generic;
using System.Diagnostics;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Threading;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Forms;
using System.Windows.Threading;
using AxCopilot.Core;
using AxCopilot.Handlers;
using AxCopilot.Models;
using AxCopilot.Security;
using AxCopilot.Services;
using AxCopilot.ViewModels;
using AxCopilot.Views;
using Microsoft.Win32;
namespace AxCopilot;
public class App : System.Windows.Application
{
private static class NativeMethods
{
public struct INPUT
{
public uint type;
public InputUnion u;
}
[StructLayout(LayoutKind.Explicit)]
public struct InputUnion
{
[FieldOffset(0)]
public KEYBDINPUT ki;
}
public struct KEYBDINPUT
{
public ushort wVk;
public ushort wScan;
public uint dwFlags;
public uint time;
public nint dwExtraInfo;
}
[DllImport("user32.dll")]
public static extern uint SendInput(uint nInputs, INPUT[] pInputs, int cbSize);
}
[Serializable]
[CompilerGenerated]
private sealed class _003C_003Ec
{
public static readonly _003C_003Ec _003C_003E9 = new _003C_003Ec();
public static DispatcherUnhandledExceptionEventHandler _003C_003E9__24_0;
public static Action _003C_003E9__31_10;
public static Action _003C_003E9__31_17;
public static Action _003C_003E9__31_18;
public static Action<bool> _003C_003E9__31_13;
public static Action _003C_003E9__31_19;
internal void _003COnStartup_003Eb__24_0(object _, DispatcherUnhandledExceptionEventArgs ex)
{
LogService.Error($"미처리 예외: {ex.Exception}");
CustomMessageBox.Show("오류가 발생했습니다:\n" + ex.Exception.Message + "\n\n로그 폴더를 확인하세요.", "AX Copilot 오류", MessageBoxButton.OK, MessageBoxImage.Hand);
ex.Handled = true;
}
internal void _003CSetupTrayIcon_003Eb__31_10()
{
string arguments = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData), "AxCopilot", "logs");
Process.Start(new ProcessStartInfo("explorer.exe", arguments)
{
UseShellExecute = true
});
}
internal void _003CSetupTrayIcon_003Eb__31_17()
{
new StatisticsWindow().Show();
}
internal void _003CSetupTrayIcon_003Eb__31_18()
{
new GuideViewerWindow().Show();
}
internal void _003CSetupTrayIcon_003Eb__31_13(bool isChecked)
{
SetAutoStart(isChecked);
}
internal void _003CSetupTrayIcon_003Eb__31_19()
{
new AboutWindow().Show();
}
}
private Mutex? _singleInstanceMutex;
private InputListener? _inputListener;
private LauncherWindow? _launcher;
private NotifyIcon? _trayIcon;
private TrayMenuWindow? _trayMenu;
private SettingsService? _settings;
private SettingsWindow? _settingsWindow;
private PluginHost? _pluginHost;
private ClipboardHistoryService? _clipboardHistory;
private DockBarWindow? _dockBar;
private FileDialogWatcher? _fileDialogWatcher;
private volatile IndexService? _indexService;
private SessionTrackingService? _sessionTracking;
private WorktimeReminderService? _worktimeReminder;
private ScreenCaptureHandler? _captureHandler;
private AgentMemoryService? _memoryService;
private ChatWindow? _chatWindow;
private const string AutoRunKey = "Software\\Microsoft\\Windows\\CurrentVersion\\Run";
private const string AutoRunName = "AxCopilot";
private bool _contentLoaded;
public IndexService? IndexService => _indexService;
public SettingsService? SettingsService => _settings;
public ClipboardHistoryService? ClipboardHistoryService => _clipboardHistory;
public AgentMemoryService? MemoryService => _memoryService;
protected override void OnStartup(StartupEventArgs e)
{
//IL_0031: Unknown result type (might be due to invalid IL or missing references)
//IL_0036: Unknown result type (might be due to invalid IL or missing references)
//IL_003c: Expected O, but got Unknown
base.OnStartup(e);
AntiTamper.Check();
object obj = _003C_003Ec._003C_003E9__24_0;
if (obj == null)
{
DispatcherUnhandledExceptionEventHandler val = delegate(object _, DispatcherUnhandledExceptionEventArgs ex)
{
LogService.Error($"미처리 예외: {ex.Exception}");
CustomMessageBox.Show("오류가 발생했습니다:\n" + ex.Exception.Message + "\n\n로그 폴더를 확인하세요.", "AX Copilot 오류", MessageBoxButton.OK, MessageBoxImage.Hand);
ex.Handled = true;
};
_003C_003Ec._003C_003E9__24_0 = val;
obj = (object)val;
}
base.DispatcherUnhandledException += (DispatcherUnhandledExceptionEventHandler)obj;
_singleInstanceMutex = new Mutex(initiallyOwned: true, "Global\\AXCopilot_SingleInstance", out var createdNew);
if (!createdNew)
{
_singleInstanceMutex.Dispose();
_singleInstanceMutex = null;
CustomMessageBox.Show("AX Copilot가 이미 실행 중입니다.\n트레이 아이콘을 확인하세요.", "AX Copilot", MessageBoxButton.OK, MessageBoxImage.Asterisk);
Shutdown();
return;
}
LogService.Info("=== AX Copilot 시작 ===");
_settings = new SettingsService();
SettingsService settings = _settings;
settings.Load();
if (settings.MigrationSummary != null)
{
((DispatcherObject)this).Dispatcher.BeginInvoke((Delegate)(Action)delegate
{
CustomMessageBox.Show(settings.MigrationSummary, "AX Copilot — 설정 업데이트", MessageBoxButton.OK, MessageBoxImage.Asterisk);
}, (DispatcherPriority)6, Array.Empty<object>());
}
L10n.SetLanguage(settings.Settings.Launcher.Language);
if (!IsAutoStartEnabled())
{
SetAutoStart(enable: true);
}
_memoryService = new AgentMemoryService();
_memoryService.Load(settings.Settings.Llm.WorkFolder);
_indexService = new IndexService(settings);
IndexService indexService = _indexService;
FuzzyEngine fuzzy = new FuzzyEngine(indexService);
CommandResolver commandResolver = new CommandResolver(fuzzy, settings);
ContextManager context = new ContextManager(settings);
_sessionTracking = new SessionTrackingService();
_worktimeReminder = new WorktimeReminderService(settings, ((DispatcherObject)this).Dispatcher);
_clipboardHistory = new ClipboardHistoryService(settings);
commandResolver.RegisterHandler(new CalculatorHandler());
commandResolver.RegisterHandler(new SystemCommandHandler(settings));
commandResolver.RegisterHandler(new SnippetHandler(settings));
commandResolver.RegisterHandler(new ClipboardHistoryHandler(_clipboardHistory));
commandResolver.RegisterHandler(new WorkspaceHandler(context, settings));
commandResolver.RegisterHandler(new UrlAliasHandler(settings));
commandResolver.RegisterHandler(new FolderAliasHandler(settings));
commandResolver.RegisterHandler(new BatchHandler(settings));
commandResolver.RegisterHandler(new ClipboardHandler(settings));
commandResolver.RegisterHandler(new BookmarkHandler());
commandResolver.RegisterHandler(new WebSearchHandler(settings));
commandResolver.RegisterHandler(new ProcessHandler());
commandResolver.RegisterHandler(new MediaHandler());
commandResolver.RegisterHandler(new SystemInfoHandler());
commandResolver.RegisterHandler(new StarInfoHandler());
commandResolver.RegisterHandler(new EmojiHandler());
commandResolver.RegisterHandler(new ColorHandler());
commandResolver.RegisterHandler(new RecentFilesHandler());
commandResolver.RegisterHandler(new NoteHandler());
commandResolver.RegisterHandler(new UninstallHandler());
commandResolver.RegisterHandler(new PortHandler());
commandResolver.RegisterHandler(new EnvHandler());
commandResolver.RegisterHandler(new JsonHandler());
commandResolver.RegisterHandler(new EncodeHandler());
commandResolver.RegisterHandler(new SnapHandler());
_captureHandler = new ScreenCaptureHandler(settings);
commandResolver.RegisterHandler(_captureHandler);
commandResolver.RegisterHandler(new ColorPickHandler());
commandResolver.RegisterHandler(new DateCalcHandler());
commandResolver.RegisterHandler(new ServiceHandler(_clipboardHistory));
commandResolver.RegisterHandler(new ClipboardPipeHandler());
commandResolver.RegisterHandler(new JournalHandler());
commandResolver.RegisterHandler(new RoutineHandler());
commandResolver.RegisterHandler(new BatchTextHandler());
commandResolver.RegisterHandler(new DiffHandler(_clipboardHistory));
commandResolver.RegisterHandler(new WindowSwitchHandler());
commandResolver.RegisterHandler(new RunHandler());
commandResolver.RegisterHandler(new TextStatsHandler());
commandResolver.RegisterHandler(new FavoriteHandler());
commandResolver.RegisterHandler(new RenameHandler());
commandResolver.RegisterHandler(new MonitorHandler());
commandResolver.RegisterHandler(new ScaffoldHandler());
commandResolver.RegisterHandler(new EverythingHandler());
commandResolver.RegisterHandler(new HelpHandler(settings));
commandResolver.RegisterHandler(new ChatHandler(settings));
PluginHost pluginHost = new PluginHost(settings, commandResolver);
pluginHost.LoadAll();
_pluginHost = pluginHost;
LauncherViewModel vm = new LauncherViewModel(commandResolver, settings);
_launcher = new LauncherWindow(vm)
{
OpenSettingsAction = OpenSettings
};
((DispatcherObject)this).Dispatcher.BeginInvoke((Delegate)(Action)delegate
{
_clipboardHistory?.Initialize();
}, (DispatcherPriority)2, Array.Empty<object>());
((DispatcherObject)this).Dispatcher.BeginInvoke((Delegate)(Action)delegate
{
PrewarmChatWindow();
}, (DispatcherPriority)1, Array.Empty<object>());
indexService.BuildAsync().ContinueWith(delegate
{
indexService.StartWatchers();
});
_inputListener = new InputListener();
_inputListener.HotkeyTriggered += OnHotkeyTriggered;
_inputListener.CaptureHotkeyTriggered += OnCaptureHotkeyTriggered;
_inputListener.HookFailed += OnHookFailed;
_inputListener.UpdateHotkey(settings.Settings.Hotkey);
_inputListener.UpdateCaptureHotkey(settings.Settings.ScreenCapture.GlobalHotkey, settings.Settings.ScreenCapture.GlobalHotkeyEnabled);
SnippetExpander snippetExpander = new SnippetExpander(settings);
_inputListener.KeyFilter = snippetExpander.HandleKey;
_inputListener.Start();
SetupTrayIcon(pluginHost, settings);
_fileDialogWatcher = new FileDialogWatcher();
_fileDialogWatcher.FileDialogOpened += delegate
{
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
if (_launcher != null && !_launcher.IsVisible)
{
SettingsService? settings2 = _settings;
if (settings2 != null && settings2.Settings.Launcher.EnableFileDialogIntegration)
{
WindowTracker.Capture();
_launcher.Show();
((DispatcherObject)this).Dispatcher.BeginInvoke((DispatcherPriority)5, (Delegate)(Action)delegate
{
_launcher.SetInputText("cd ");
});
}
}
});
};
_fileDialogWatcher.Start();
if (settings.Settings.Launcher.DockBarAutoShow)
{
((DispatcherObject)this).Dispatcher.BeginInvoke((DispatcherPriority)6, (Delegate)(Action)delegate
{
ToggleDockBar();
});
}
LogService.Info("초기화 완료. " + settings.Settings.Hotkey + "로 실행하세요.");
}
private void OnHotkeyTriggered(object? sender, EventArgs e)
{
WindowTracker.Capture();
LauncherSettings launcherSettings = _settings?.Settings.Launcher;
bool flag = launcherSettings?.EnableTextAction ?? false;
bool isVisible = false;
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
isVisible = _launcher?.IsVisible ?? false;
});
if (isVisible)
{
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
_launcher?.Hide();
});
return;
}
if (!flag)
{
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
if (_launcher != null)
{
UsageStatisticsService.RecordLauncherOpen();
_launcher.Show();
}
});
return;
}
string selectedText = TryGetSelectedText();
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
if (_launcher != null)
{
if (!string.IsNullOrWhiteSpace(selectedText))
{
List<string> enabledCmds = launcherSettings?.TextActionCommands ?? new List<string>();
if (enabledCmds.Count == 1 && !string.IsNullOrEmpty(TextActionPopup.AvailableCommands.FirstOrDefault<(string, string)>(((string Key, string Label) c) => c.Key == enabledCmds[0]).Item1))
{
string text = enabledCmds[0];
if (1 == 0)
{
}
TextActionPopup.ActionResult actionResult = text switch
{
"translate" => TextActionPopup.ActionResult.Translate,
"summarize" => TextActionPopup.ActionResult.Summarize,
"grammar" => TextActionPopup.ActionResult.GrammarFix,
"explain" => TextActionPopup.ActionResult.Explain,
"rewrite" => TextActionPopup.ActionResult.Rewrite,
_ => TextActionPopup.ActionResult.None,
};
if (1 == 0)
{
}
TextActionPopup.ActionResult actionResult2 = actionResult;
if (actionResult2 != TextActionPopup.ActionResult.None)
{
ExecuteTextAction(actionResult2, selectedText);
return;
}
}
TextActionPopup popup = new TextActionPopup(selectedText, enabledCmds);
popup.Closed += delegate
{
switch (popup.SelectedAction)
{
case TextActionPopup.ActionResult.OpenLauncher:
UsageStatisticsService.RecordLauncherOpen();
_launcher.Show();
break;
case TextActionPopup.ActionResult.None:
break;
default:
ExecuteTextAction(popup.SelectedAction, popup.SelectedText);
break;
}
};
popup.Show();
}
else
{
UsageStatisticsService.RecordLauncherOpen();
_launcher.Show();
}
}
});
}
private string? TryGetSelectedText()
{
try
{
string prevText = null;
bool hadText = false;
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
hadText = System.Windows.Clipboard.ContainsText();
prevText = (hadText ? System.Windows.Clipboard.GetText() : null);
System.Windows.Clipboard.Clear();
});
Thread.Sleep(30);
NativeMethods.INPUT[] array = new NativeMethods.INPUT[4]
{
new NativeMethods.INPUT
{
type = 1u,
u = new NativeMethods.InputUnion
{
ki = new NativeMethods.KEYBDINPUT
{
wVk = 17
}
}
},
new NativeMethods.INPUT
{
type = 1u,
u = new NativeMethods.InputUnion
{
ki = new NativeMethods.KEYBDINPUT
{
wVk = 67
}
}
},
new NativeMethods.INPUT
{
type = 1u,
u = new NativeMethods.InputUnion
{
ki = new NativeMethods.KEYBDINPUT
{
wVk = 67,
dwFlags = 2u
}
}
},
new NativeMethods.INPUT
{
type = 1u,
u = new NativeMethods.InputUnion
{
ki = new NativeMethods.KEYBDINPUT
{
wVk = 17,
dwFlags = 2u
}
}
}
};
NativeMethods.SendInput((uint)array.Length, array, Marshal.SizeOf<NativeMethods.INPUT>());
Thread.Sleep(80);
string selected = null;
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
if (System.Windows.Clipboard.ContainsText())
{
string text = System.Windows.Clipboard.GetText();
if (text != prevText && !string.IsNullOrWhiteSpace(text))
{
selected = text;
}
}
if (selected != null && prevText != null)
{
System.Windows.Clipboard.SetText(prevText);
}
else if (selected != null && !hadText)
{
System.Windows.Clipboard.Clear();
}
});
return selected;
}
catch
{
return null;
}
}
private void ExecuteTextAction(TextActionPopup.ActionResult action, string text)
{
if (1 == 0)
{
}
string text2 = action switch
{
TextActionPopup.ActionResult.Translate => "다음 텍스트를 번역해줘:\n\n" + text,
TextActionPopup.ActionResult.Summarize => "다음 텍스트를 요약해줘:\n\n" + text,
TextActionPopup.ActionResult.GrammarFix => "다음 텍스트의 문법을 교정해줘:\n\n" + text,
TextActionPopup.ActionResult.Explain => "다음 텍스트를 쉽게 설명해줘:\n\n" + text,
TextActionPopup.ActionResult.Rewrite => "다음 텍스트를 다시 작성해줘:\n\n" + text,
_ => text,
};
if (1 == 0)
{
}
string text3 = text2;
_launcher?.Show();
_launcher?.SetInputText("! " + text3);
}
private void OnCaptureHotkeyTriggered(object? sender, EventArgs e)
{
WindowTracker.Capture();
string mode = _settings?.Settings.ScreenCapture.GlobalHotkeyMode ?? "screen";
((DispatcherObject)this).Dispatcher.Invoke<Task>((Func<Task>)async delegate
{
if (_captureHandler == null)
{
return;
}
try
{
await _captureHandler.CaptureDirectAsync(mode);
}
catch (Exception ex)
{
LogService.Error("글로벌 캡처 실패: " + ex.Message);
}
});
}
private void OnHookFailed(object? sender, EventArgs e)
{
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
_trayIcon?.ShowBalloonTip(3000, "AX Copilot", "글로벌 단축키 등록에 실패했습니다.\n다른 앱과 " + (_settings?.Settings.Hotkey ?? "단축키") + "가 충돌하고 있을 수 있습니다.", ToolTipIcon.Warning);
});
}
private void SetupTrayIcon(PluginHost pluginHost, SettingsService settings)
{
_trayIcon = new NotifyIcon
{
Text = "AX Copilot",
Visible = true,
Icon = LoadAppIcon()
};
_trayMenu = new TrayMenuWindow();
_trayMenu.AddItem("\ue7c5", "AX Commander 호출하기", delegate
{
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
_launcher?.Show();
});
}).AddItem("\ue8bd", "AX Agent 대화하기", delegate
{
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
OpenAiChat();
});
}, out Border aiTrayItem).AddItem("\ue8a7", "독 바 표시", delegate
{
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
ToggleDockBar();
});
})
.AddSeparator()
.AddItem("\ue72c", "플러그인 재로드", delegate
{
pluginHost.Reload();
_trayIcon.ShowBalloonTip(2000, "AX Copilot", "플러그인이 재로드되었습니다.", ToolTipIcon.None);
})
.AddItem("\ue838", "로그 폴더 열기", delegate
{
string arguments = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData), "AxCopilot", "logs");
Process.Start(new ProcessStartInfo("explorer.exe", arguments)
{
UseShellExecute = true
});
})
.AddItem("\ue9d9", "사용 통계", delegate
{
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
new StatisticsWindow().Show();
});
})
.AddItem("\ue736", "사용 가이드 문서보기", delegate
{
try
{
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
new GuideViewerWindow().Show();
});
}
catch (Exception ex)
{
LogService.Error("사용 가이드 열기 실패: " + ex.Message);
}
})
.AddSeparator()
.AddToggleItem("\ue82f", "Windows 시작 시 자동 실행", IsAutoStartEnabled(), delegate(bool isChecked)
{
SetAutoStart(isChecked);
}, out Func<bool> _, out Action<string> _)
.AddSeparator()
.AddItem("\ue713", "설정", delegate
{
((DispatcherObject)this).Dispatcher.Invoke((Action)OpenSettings);
})
.AddItem("\ue946", "개발 정보", delegate
{
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
new AboutWindow().Show();
});
})
.AddItem("\ue711", "종료", delegate
{
_inputListener?.Dispose();
_trayIcon?.Dispose();
Shutdown();
});
_trayMenu.Opening += delegate
{
aiTrayItem.Visibility = ((!settings.Settings.AiEnabled) ? Visibility.Collapsed : Visibility.Visible);
};
_trayIcon.MouseClick += delegate(object? _, MouseEventArgs e)
{
if (e.Button == MouseButtons.Left)
{
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
_launcher?.Show();
});
}
else if (e.Button == MouseButtons.Right)
{
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
_trayMenu?.ShowWithUpdate();
});
}
};
NotificationService.Initialize(delegate(string title, string msg)
{
((DispatcherObject)this).Dispatcher.Invoke((Action)delegate
{
_trayIcon?.ShowBalloonTip(4000, title, msg, ToolTipIcon.None);
});
});
}
public void OpenSettingsFromChat()
{
((DispatcherObject)this).Dispatcher.Invoke((Action)OpenSettings);
}
internal void PrewarmChatWindow()
{
if (_chatWindow == null && _settings != null)
{
_chatWindow = new ChatWindow(_settings);
}
}
private void OpenAiChat()
{
if (_settings != null)
{
if (_chatWindow == null)
{
_chatWindow = new ChatWindow(_settings);
}
_chatWindow.Show();
_chatWindow.Activate();
}
}
public void ToggleDockBar()
{
if (_dockBar != null && _dockBar.IsVisible)
{
_dockBar.Hide();
return;
}
if (_dockBar == null)
{
_dockBar = new DockBarWindow();
_dockBar.OnQuickSearch = delegate(string query)
{
if (_launcher != null)
{
_launcher.Show();
_launcher.Activate();
if (!string.IsNullOrEmpty(query))
{
((DispatcherObject)this).Dispatcher.BeginInvoke((DispatcherPriority)5, (Delegate)(Action)delegate
{
_launcher.SetInputText(query);
});
}
}
};
_dockBar.OnCapture = async delegate
{
WindowTracker.Capture();
if (_captureHandler != null)
{
await _captureHandler.CaptureDirectAsync("region");
}
};
_dockBar.OnOpenAgent = delegate
{
if (_launcher != null)
{
_launcher.Show();
((DispatcherObject)this).Dispatcher.BeginInvoke((DispatcherPriority)5, (Delegate)(Action)delegate
{
_launcher.SetInputText("!");
});
}
};
}
LauncherSettings launcherSettings = _settings?.Settings.Launcher;
List<string> itemKeys = launcherSettings?.DockBarItems ?? new List<string> { "launcher", "clipboard", "capture", "agent", "clock", "cpu" };
_dockBar.BuildFromSettings(itemKeys);
_dockBar.OnPositionChanged = delegate(double left, double top)
{
if (_settings != null)
{
_settings.Settings.Launcher.DockBarLeft = left;
_settings.Settings.Launcher.DockBarTop = top;
_settings.Save();
}
};
_dockBar.Show();
_dockBar.ApplySettings(launcherSettings?.DockBarOpacity ?? 0.92, launcherSettings?.DockBarLeft ?? (-1.0), launcherSettings?.DockBarTop ?? (-1.0), launcherSettings?.DockBarRainbowGlow ?? false);
}
public void RefreshDockBar()
{
if (_dockBar != null && _dockBar.IsVisible)
{
LauncherSettings launcherSettings = _settings?.Settings.Launcher;
List<string> itemKeys = launcherSettings?.DockBarItems ?? new List<string> { "launcher", "clipboard", "capture", "agent", "clock", "cpu" };
_dockBar.BuildFromSettings(itemKeys);
_dockBar.ApplySettings(launcherSettings?.DockBarOpacity ?? 0.92, launcherSettings?.DockBarLeft ?? (-1.0), launcherSettings?.DockBarTop ?? (-1.0), launcherSettings?.DockBarRainbowGlow ?? false);
}
}
private void OpenSettings()
{
SettingsViewModel vm;
if (_settingsWindow != null && _settingsWindow.IsVisible)
{
_settingsWindow.Activate();
}
else
{
if (_settings == null || _launcher == null)
{
return;
}
vm = new SettingsViewModel(_settings);
_settingsWindow = new SettingsWindow(vm, PreviewCallback, RevertCallback)
{
SuspendHotkeyCallback = delegate(bool suspend)
{
if (_inputListener != null)
{
_inputListener.SuspendHotkey = suspend;
}
}
};
vm.SaveCompleted += delegate
{
if (_inputListener != null && _settings != null)
{
_inputListener.UpdateHotkey(_settings.Settings.Hotkey);
_inputListener.UpdateCaptureHotkey(_settings.Settings.ScreenCapture.GlobalHotkey, _settings.Settings.ScreenCapture.GlobalHotkeyEnabled);
}
_worktimeReminder?.RestartTimer();
};
_settingsWindow.Show();
}
void PreviewCallback(string themeKey)
{
if (themeKey == "custom")
{
CustomThemeColors customThemeColors = new CustomThemeColors();
foreach (ColorRowModel colorRow in vm.ColorRows)
{
typeof(CustomThemeColors).GetProperty(colorRow.Property)?.SetValue(customThemeColors, colorRow.Hex);
}
_launcher.ApplyTheme(themeKey, customThemeColors);
}
else
{
_launcher.ApplyTheme(themeKey, _settings.Settings.Launcher.CustomTheme);
}
}
void RevertCallback()
{
_launcher.ApplyTheme(_settings.Settings.Launcher.Theme ?? "system", _settings.Settings.Launcher.CustomTheme);
}
}
private static Icon LoadAppIcon()
{
Size smallIconSize = SystemInformation.SmallIconSize;
try
{
string path = Path.GetDirectoryName(Environment.ProcessPath) ?? AppContext.BaseDirectory;
string text = Path.Combine(path, "Assets", "icon.ico");
if (File.Exists(text))
{
return new Icon(text, smallIconSize);
}
}
catch
{
}
try
{
Uri uriResource = new Uri("pack://application:,,,/Assets/icon.ico");
Stream stream = System.Windows.Application.GetResourceStream(uriResource)?.Stream;
if (stream != null)
{
return new Icon(stream, smallIconSize);
}
}
catch
{
}
return SystemIcons.Application;
}
private static bool IsAutoStartEnabled()
{
try
{
using RegistryKey registryKey = Registry.CurrentUser.OpenSubKey("Software\\Microsoft\\Windows\\CurrentVersion\\Run", writable: false);
return registryKey?.GetValue("AxCopilot") != null;
}
catch
{
return false;
}
}
private static void SetAutoStart(bool enable)
{
try
{
using RegistryKey registryKey = Registry.CurrentUser.OpenSubKey("Software\\Microsoft\\Windows\\CurrentVersion\\Run", writable: true);
if (registryKey == null)
{
return;
}
if (enable)
{
string text = Environment.ProcessPath ?? Process.GetCurrentProcess().MainModule?.FileName ?? string.Empty;
if (!string.IsNullOrEmpty(text))
{
registryKey.SetValue("AxCopilot", "\"" + text + "\"");
}
}
else
{
registryKey.DeleteValue("AxCopilot", throwOnMissingValue: false);
}
}
catch (Exception ex)
{
LogService.Warn("자동 시작 레지스트리 설정 실패: " + ex.Message);
}
}
protected override void OnExit(ExitEventArgs e)
{
_chatWindow?.ForceClose();
_inputListener?.Dispose();
_clipboardHistory?.Dispose();
_indexService?.Dispose();
_sessionTracking?.Dispose();
_worktimeReminder?.Dispose();
_trayIcon?.Dispose();
try
{
_singleInstanceMutex?.ReleaseMutex();
}
catch
{
}
_singleInstanceMutex?.Dispose();
LogService.Info("=== AX Copilot 종료 ===");
base.OnExit(e);
}
[DebuggerNonUserCode]
[GeneratedCode("PresentationBuildTasks", "10.0.5.0")]
public void InitializeComponent()
{
if (!_contentLoaded)
{
_contentLoaded = true;
Uri resourceLocator = new Uri("/AxCopilot;component/app.xaml", UriKind.Relative);
System.Windows.Application.LoadComponent(this, resourceLocator);
}
}
[STAThread]
[DebuggerNonUserCode]
[GeneratedCode("PresentationBuildTasks", "10.0.5.0")]
public static void Main()
{
App app = new App();
app.InitializeComponent();
app.Run();
}
}