feat: 项目多标签方案调整
This commit is contained in:
162
src/main/wins/index.ts
Normal file
162
src/main/wins/index.ts
Normal file
@@ -0,0 +1,162 @@
|
||||
import type { BrowserWindow } from 'electron'
|
||||
import { ipcMain } from 'electron';
|
||||
import { WINDOW_NAMES, MAIN_WIN_SIZE, IPC_EVENTS, MENU_IDS, CONVERSATION_ITEM_MENU_IDS, CONVERSATION_LIST_MENU_IDS, MESSAGE_ITEM_MENU_IDS, CONFIG_KEYS } from '@common/constants'
|
||||
import { createProvider } from '../providers'
|
||||
import { windowManager } from '@main/service/window-service'
|
||||
import { menuManager } from '@main/service/menu-service'
|
||||
import { logManager } from '@main/service/logger'
|
||||
import { configManager } from '@main/service/config-service'
|
||||
import { trayManager } from '@main/service/tray-service'
|
||||
import { TabManager } from '@service/tab-manager'
|
||||
|
||||
const handleTray = (minimizeToTray: boolean) => {
|
||||
if (minimizeToTray) {
|
||||
trayManager.create();
|
||||
return;
|
||||
}
|
||||
|
||||
trayManager.destroy();
|
||||
}
|
||||
|
||||
const registerMenus = (window: BrowserWindow) => {
|
||||
|
||||
const conversationItemMenuItemClick = (id: string) => {
|
||||
logManager.logUserOperation(`${IPC_EVENTS.SHOW_CONTEXT_MENU}:${MENU_IDS.CONVERSATION_ITEM}-${id}`)
|
||||
window.webContents.send(`${IPC_EVENTS.SHOW_CONTEXT_MENU}:${MENU_IDS.CONVERSATION_ITEM}`, id);
|
||||
}
|
||||
|
||||
menuManager.register(MENU_IDS.CONVERSATION_ITEM, [
|
||||
{
|
||||
id: CONVERSATION_ITEM_MENU_IDS.PIN,
|
||||
label: 'menu.conversation.pinConversation',
|
||||
click: () => conversationItemMenuItemClick(CONVERSATION_ITEM_MENU_IDS.PIN)
|
||||
},
|
||||
{
|
||||
id: CONVERSATION_ITEM_MENU_IDS.RENAME,
|
||||
label: 'menu.conversation.renameConversation',
|
||||
click: () => conversationItemMenuItemClick(CONVERSATION_ITEM_MENU_IDS.RENAME)
|
||||
},
|
||||
{
|
||||
id: CONVERSATION_ITEM_MENU_IDS.DEL,
|
||||
label: 'menu.conversation.delConversation',
|
||||
click: () => conversationItemMenuItemClick(CONVERSATION_ITEM_MENU_IDS.DEL)
|
||||
},
|
||||
])
|
||||
|
||||
const conversationListMenuItemClick = (id: string) => {
|
||||
logManager.logUserOperation(`${IPC_EVENTS.SHOW_CONTEXT_MENU}:${MENU_IDS.CONVERSATION_LIST}-${id}`)
|
||||
window.webContents.send(`${IPC_EVENTS.SHOW_CONTEXT_MENU}:${MENU_IDS.CONVERSATION_LIST}`, id);
|
||||
}
|
||||
|
||||
menuManager.register(MENU_IDS.CONVERSATION_LIST, [
|
||||
{
|
||||
id: CONVERSATION_LIST_MENU_IDS.NEW_CONVERSATION,
|
||||
label: 'menu.conversation.newConversation',
|
||||
click: () => conversationListMenuItemClick(CONVERSATION_LIST_MENU_IDS.NEW_CONVERSATION)
|
||||
},
|
||||
{ type: 'separator' },
|
||||
{
|
||||
id: CONVERSATION_LIST_MENU_IDS.SORT_BY, label: 'menu.conversation.sortBy', submenu: [
|
||||
{ id: CONVERSATION_LIST_MENU_IDS.SORT_BY_CREATE_TIME, label: 'menu.conversation.sortByCreateTime', type: 'radio', checked: false, click: () => conversationListMenuItemClick(CONVERSATION_LIST_MENU_IDS.SORT_BY_CREATE_TIME) },
|
||||
{ id: CONVERSATION_LIST_MENU_IDS.SORT_BY_UPDATE_TIME, label: 'menu.conversation.sortByUpdateTime', type: 'radio', checked: false, click: () => conversationListMenuItemClick(CONVERSATION_LIST_MENU_IDS.SORT_BY_UPDATE_TIME) },
|
||||
{ id: CONVERSATION_LIST_MENU_IDS.SORT_BY_NAME, label: 'menu.conversation.sortByName', type: 'radio', checked: false, click: () => conversationListMenuItemClick(CONVERSATION_LIST_MENU_IDS.SORT_BY_NAME) },
|
||||
{ id: CONVERSATION_LIST_MENU_IDS.SORT_BY_MODEL, label: 'menu.conversation.sortByModel', type: 'radio', checked: false, click: () => conversationListMenuItemClick(CONVERSATION_LIST_MENU_IDS.SORT_BY_MODEL) },
|
||||
{ type: 'separator' },
|
||||
{ id: CONVERSATION_LIST_MENU_IDS.SORT_ASCENDING, label: 'menu.conversation.sortAscending', type: 'radio', checked: false, click: () => conversationListMenuItemClick(CONVERSATION_LIST_MENU_IDS.SORT_ASCENDING) },
|
||||
{ id: CONVERSATION_LIST_MENU_IDS.SORT_DESCENDING, label: 'menu.conversation.sortDescending', type: 'radio', checked: false, click: () => conversationListMenuItemClick(CONVERSATION_LIST_MENU_IDS.SORT_DESCENDING) },
|
||||
]
|
||||
},
|
||||
{
|
||||
id: CONVERSATION_LIST_MENU_IDS.BATCH_OPERATIONS,
|
||||
label: 'menu.conversation.batchOperations',
|
||||
click: () => conversationListMenuItemClick(CONVERSATION_LIST_MENU_IDS.BATCH_OPERATIONS)
|
||||
}
|
||||
])
|
||||
|
||||
const messageItemMenuItemClick = (id: string) => {
|
||||
logManager.logUserOperation(`${IPC_EVENTS.SHOW_CONTEXT_MENU}:${MENU_IDS.MESSAGE_ITEM}-${id}`)
|
||||
window.webContents.send(`${IPC_EVENTS.SHOW_CONTEXT_MENU}:${MENU_IDS.MESSAGE_ITEM}`, id);
|
||||
}
|
||||
|
||||
menuManager.register(MENU_IDS.MESSAGE_ITEM, [
|
||||
{
|
||||
id: MESSAGE_ITEM_MENU_IDS.COPY,
|
||||
label: 'menu.message.copyMessage',
|
||||
click: () => messageItemMenuItemClick(MESSAGE_ITEM_MENU_IDS.COPY)
|
||||
},
|
||||
{
|
||||
id: MESSAGE_ITEM_MENU_IDS.SELECT,
|
||||
label: 'menu.message.selectMessage',
|
||||
click: () => messageItemMenuItemClick(MESSAGE_ITEM_MENU_IDS.SELECT)
|
||||
},
|
||||
{ type: 'separator' },
|
||||
{
|
||||
id: MESSAGE_ITEM_MENU_IDS.DELETE,
|
||||
label: 'menu.message.deleteMessage',
|
||||
click: () => messageItemMenuItemClick(MESSAGE_ITEM_MENU_IDS.DELETE)
|
||||
},
|
||||
])
|
||||
}
|
||||
|
||||
export function setupMainWindow() {
|
||||
windowManager.onWindowCreate(WINDOW_NAMES.MAIN, (mainWindow) => {
|
||||
let minimizeToTray = configManager.get(CONFIG_KEYS.MINIMIZE_TO_TRAY);
|
||||
|
||||
configManager.onConfigChange((config) => {
|
||||
if (minimizeToTray === config[CONFIG_KEYS.MINIMIZE_TO_TRAY]) return;
|
||||
minimizeToTray = config[CONFIG_KEYS.MINIMIZE_TO_TRAY];
|
||||
handleTray(minimizeToTray);
|
||||
});
|
||||
|
||||
handleTray(minimizeToTray);
|
||||
registerMenus(mainWindow);
|
||||
|
||||
const tabManager = new TabManager(mainWindow)
|
||||
tabManager.enable()
|
||||
|
||||
mainWindow.on('closed', () => {
|
||||
tabManager.destroy()
|
||||
})
|
||||
});
|
||||
|
||||
windowManager.create(WINDOW_NAMES.MAIN, MAIN_WIN_SIZE);
|
||||
|
||||
ipcMain.on(IPC_EVENTS.START_A_DIALOGUE, async (_event, props: CreateDialogueProps) => {
|
||||
const { providerName, messages, messageId, selectedModel } = props;
|
||||
const mainWindow = windowManager.get(WINDOW_NAMES.MAIN);
|
||||
|
||||
if (!mainWindow) {
|
||||
throw new Error('mainWindow not found');
|
||||
}
|
||||
|
||||
try {
|
||||
|
||||
const provider = createProvider(providerName);
|
||||
const chunks = await provider?.chat(messages, selectedModel);
|
||||
|
||||
if (!chunks) {
|
||||
throw new Error('chunks or stream not found');
|
||||
}
|
||||
|
||||
for await (const chunk of chunks) {
|
||||
const chunkContent = {
|
||||
messageId,
|
||||
data: chunk
|
||||
}
|
||||
mainWindow.webContents.send(IPC_EVENTS.START_A_DIALOGUE + 'back' + messageId, chunkContent);
|
||||
}
|
||||
|
||||
} catch (error) {
|
||||
const errorContent = {
|
||||
messageId,
|
||||
data: {
|
||||
isEnd: true,
|
||||
isError: true,
|
||||
result: error instanceof Error ? error.message : String(error),
|
||||
}
|
||||
}
|
||||
|
||||
mainWindow.webContents.send(IPC_EVENTS.START_A_DIALOGUE + 'back' + messageId, errorContent);
|
||||
}
|
||||
})
|
||||
}
|
||||
Reference in New Issue
Block a user