Add clickable menu and prompt settings
This commit is contained in:
265
wezterm.lua
265
wezterm.lua
@@ -96,12 +96,14 @@ local pane_start_times = {}
|
|||||||
|
|
||||||
wezterm.on("update-right-status", function(window, pane)
|
wezterm.on("update-right-status", function(window, pane)
|
||||||
window:set_left_status(wezterm.format({
|
window:set_left_status(wezterm.format({
|
||||||
|
{ Hyperlink = { uri = "wezterm://main-menu" } },
|
||||||
{ Background = { Color = "#89b4fa" } },
|
{ Background = { Color = "#89b4fa" } },
|
||||||
{ Foreground = { Color = "#1e1e2e" } },
|
{ Foreground = { Color = "#1e1e2e" } },
|
||||||
{ Text = " ☰ " },
|
{ Text = " ☰ Menu " },
|
||||||
|
{ Hyperlink = { uri = "" } },
|
||||||
{ Background = { Color = "#313244" } },
|
{ Background = { Color = "#313244" } },
|
||||||
{ Foreground = { Color = "#cdd6f4" } },
|
{ Foreground = { Color = "#cdd6f4" } },
|
||||||
{ Text = " Menu: Ctrl+a m " },
|
{ Text = " Ctrl+a m " },
|
||||||
}))
|
}))
|
||||||
|
|
||||||
local pane_id = pane:pane_id()
|
local pane_id = pane:pane_id()
|
||||||
@@ -150,41 +152,225 @@ config.unix_domains = {
|
|||||||
local is_windows = wezterm.target_triple:find("windows") ~= nil
|
local is_windows = wezterm.target_triple:find("windows") ~= nil
|
||||||
local config_file = is_windows and (wezterm.home_dir .. "\\.wezterm.lua") or "/mnt/storage/wezterm.lua"
|
local config_file = is_windows and (wezterm.home_dir .. "\\.wezterm.lua") or "/mnt/storage/wezterm.lua"
|
||||||
|
|
||||||
local function open_config_section(window, pane, line)
|
local function notify(window, message)
|
||||||
local args
|
if window.toast_notification then
|
||||||
if is_windows then
|
window:toast_notification("WezTerm", message, nil, 4000)
|
||||||
args = {
|
|
||||||
"powershell.exe",
|
|
||||||
"-NoLogo",
|
|
||||||
"-NoExit",
|
|
||||||
"-Command",
|
|
||||||
string.format(
|
|
||||||
'$file = %q; $line = %d; '
|
|
||||||
.. '$code = Get-Command code.cmd,code -ErrorAction SilentlyContinue | Select-Object -First 1; '
|
|
||||||
.. 'if ($code) { & $code.Source -g "${file}:${line}" } '
|
|
||||||
.. 'else { Write-Host "VS Code not found. Opening Notepad without line jump."; notepad.exe $file }',
|
|
||||||
config_file,
|
|
||||||
line
|
|
||||||
),
|
|
||||||
}
|
|
||||||
else
|
else
|
||||||
args = {
|
wezterm.log_info(message)
|
||||||
"sh",
|
end
|
||||||
"-lc",
|
end
|
||||||
string.format(
|
|
||||||
'file=%q; line=%d; editor="${VISUAL:-${EDITOR:-}}"; '
|
local function read_config_text()
|
||||||
.. 'if [ -z "$editor" ]; then for candidate in nvim vim vi nano; do command -v "$candidate" >/dev/null 2>&1 && editor="$candidate" && break; done; fi; '
|
local file = io.open(config_file, "r")
|
||||||
.. 'if [ -z "$editor" ]; then echo "No terminal editor found. Set EDITOR or install vim/nano."; exec "${SHELL:-sh}"; fi; '
|
if not file then
|
||||||
.. '"$editor" +"$line" "$file"; status=$?; '
|
return nil, "설정 파일을 열 수 없습니다: " .. config_file
|
||||||
.. 'if [ $status -ne 0 ]; then echo; echo "Editor exited with status $status. Press Enter to close, or type commands below."; exec "${SHELL:-sh}"; fi',
|
end
|
||||||
config_file,
|
local text = file:read("*a")
|
||||||
line
|
file:close()
|
||||||
),
|
return text
|
||||||
}
|
end
|
||||||
|
|
||||||
|
local function write_config_text(text)
|
||||||
|
local file = io.open(config_file, "w")
|
||||||
|
if not file then
|
||||||
|
return false, "설정 파일에 쓸 수 없습니다: " .. config_file
|
||||||
|
end
|
||||||
|
file:write(text)
|
||||||
|
file:close()
|
||||||
|
return true
|
||||||
|
end
|
||||||
|
|
||||||
|
local function set_config_value(window, pane, key, value)
|
||||||
|
local text, err = read_config_text()
|
||||||
|
if not text then
|
||||||
|
notify(window, err)
|
||||||
|
return
|
||||||
end
|
end
|
||||||
|
|
||||||
|
local pattern = "(config%." .. key .. "%s*=%s*)[^\n]+"
|
||||||
|
local updated, count = text:gsub(pattern, function(prefix)
|
||||||
|
return prefix .. value
|
||||||
|
end, 1)
|
||||||
|
|
||||||
|
if count == 0 then
|
||||||
|
notify(window, "설정 항목을 찾지 못했습니다: config." .. key)
|
||||||
|
return
|
||||||
|
end
|
||||||
|
|
||||||
|
local ok, write_err = write_config_text(updated)
|
||||||
|
if not ok then
|
||||||
|
notify(window, write_err)
|
||||||
|
return
|
||||||
|
end
|
||||||
|
|
||||||
|
notify(window, "저장됨: config." .. key .. " = " .. value)
|
||||||
|
window:perform_action(act.ReloadConfiguration, pane)
|
||||||
|
end
|
||||||
|
|
||||||
|
local function prompt_config_value(window, pane, title, key, initial_value, quote_string)
|
||||||
window:perform_action(
|
window:perform_action(
|
||||||
act.SpawnCommandInNewTab({ args = args }),
|
act.PromptInputLine({
|
||||||
|
description = title,
|
||||||
|
initial_value = tostring(initial_value),
|
||||||
|
action = wezterm.action_callback(function(inner_window, inner_pane, line)
|
||||||
|
if not line or line == "" then
|
||||||
|
return
|
||||||
|
end
|
||||||
|
local value = quote_string and string.format("%q", line) or line
|
||||||
|
set_config_value(inner_window, inner_pane, key, value)
|
||||||
|
end),
|
||||||
|
}),
|
||||||
|
pane
|
||||||
|
)
|
||||||
|
end
|
||||||
|
|
||||||
|
local function show_font_settings(window, pane)
|
||||||
|
window:perform_action(
|
||||||
|
act.InputSelector({
|
||||||
|
title = "폰트 설정",
|
||||||
|
fuzzy = true,
|
||||||
|
choices = {
|
||||||
|
{ label = "폰트 크기", id = "font_size" },
|
||||||
|
{ label = "줄 높이", id = "line_height" },
|
||||||
|
{ label = "색상 테마", id = "color_scheme" },
|
||||||
|
{ label = "창 투명도", id = "opacity" },
|
||||||
|
},
|
||||||
|
action = wezterm.action_callback(function(inner_window, inner_pane, id)
|
||||||
|
if id == "font_size" then
|
||||||
|
prompt_config_value(inner_window, inner_pane, "폰트 크기", "font_size", config.font_size, false)
|
||||||
|
elseif id == "line_height" then
|
||||||
|
prompt_config_value(inner_window, inner_pane, "줄 높이", "line_height", config.line_height, false)
|
||||||
|
elseif id == "color_scheme" then
|
||||||
|
prompt_config_value(inner_window, inner_pane, "색상 테마", "color_scheme", config.color_scheme, true)
|
||||||
|
elseif id == "opacity" then
|
||||||
|
prompt_config_value(inner_window, inner_pane, "창 투명도", "window_background_opacity", config.window_background_opacity, false)
|
||||||
|
end
|
||||||
|
end),
|
||||||
|
}),
|
||||||
|
pane
|
||||||
|
)
|
||||||
|
end
|
||||||
|
|
||||||
|
local function append_ssh_domain(window, pane, name, remote_address, username)
|
||||||
|
local text, err = read_config_text()
|
||||||
|
if not text then
|
||||||
|
notify(window, err)
|
||||||
|
return
|
||||||
|
end
|
||||||
|
|
||||||
|
local entry = string.format('\t{\n\t\tname = %q,\n\t\tremote_address = %q,\n\t\tusername = %q,\n\t},\n', name, remote_address, username)
|
||||||
|
local updated, count = text:gsub("(config%.ssh_domains%s*=%s*{%s*\n)", function(prefix)
|
||||||
|
return prefix .. entry
|
||||||
|
end, 1)
|
||||||
|
|
||||||
|
if count == 0 then
|
||||||
|
notify(window, "config.ssh_domains 블록을 찾지 못했습니다")
|
||||||
|
return
|
||||||
|
end
|
||||||
|
|
||||||
|
local ok, write_err = write_config_text(updated)
|
||||||
|
if not ok then
|
||||||
|
notify(window, write_err)
|
||||||
|
return
|
||||||
|
end
|
||||||
|
|
||||||
|
notify(window, "SSH 도메인 추가됨: " .. name)
|
||||||
|
window:perform_action(act.ReloadConfiguration, pane)
|
||||||
|
end
|
||||||
|
|
||||||
|
local function prompt_ssh_domain(window, pane)
|
||||||
|
local draft = {}
|
||||||
|
window:perform_action(
|
||||||
|
act.PromptInputLine({
|
||||||
|
description = "SSH 이름",
|
||||||
|
action = wezterm.action_callback(function(w1, p1, name)
|
||||||
|
if not name or name == "" then
|
||||||
|
return
|
||||||
|
end
|
||||||
|
draft.name = name
|
||||||
|
w1:perform_action(
|
||||||
|
act.PromptInputLine({
|
||||||
|
description = "SSH 주소",
|
||||||
|
action = wezterm.action_callback(function(w2, p2, address)
|
||||||
|
if not address or address == "" then
|
||||||
|
return
|
||||||
|
end
|
||||||
|
draft.remote_address = address
|
||||||
|
w2:perform_action(
|
||||||
|
act.PromptInputLine({
|
||||||
|
description = "SSH 사용자명",
|
||||||
|
action = wezterm.action_callback(function(w3, p3, username)
|
||||||
|
if not username or username == "" then
|
||||||
|
return
|
||||||
|
end
|
||||||
|
append_ssh_domain(w3, p3, draft.name, draft.remote_address, username)
|
||||||
|
end),
|
||||||
|
}),
|
||||||
|
p2
|
||||||
|
)
|
||||||
|
end),
|
||||||
|
}),
|
||||||
|
p1
|
||||||
|
)
|
||||||
|
end),
|
||||||
|
}),
|
||||||
|
pane
|
||||||
|
)
|
||||||
|
end
|
||||||
|
|
||||||
|
local function show_connection_settings(window, pane)
|
||||||
|
window:perform_action(
|
||||||
|
act.InputSelector({
|
||||||
|
title = "연결 설정",
|
||||||
|
fuzzy = true,
|
||||||
|
choices = {
|
||||||
|
{ label = "SSH 도메인 추가", id = "add_ssh" },
|
||||||
|
{ label = "SSH 도메인 목록", id = "domains" },
|
||||||
|
{ label = "통합 런처", id = "launcher" },
|
||||||
|
},
|
||||||
|
action = wezterm.action_callback(function(inner_window, inner_pane, id)
|
||||||
|
if id == "add_ssh" then
|
||||||
|
prompt_ssh_domain(inner_window, inner_pane)
|
||||||
|
elseif id == "domains" then
|
||||||
|
inner_window:perform_action(act.ShowLauncherArgs({ flags = "DOMAINS" }), inner_pane)
|
||||||
|
elseif id == "launcher" then
|
||||||
|
inner_window:perform_action(act.ShowLauncherArgs({ flags = "FUZZY|TABS|DOMAINS|WORKSPACES|LAUNCH_MENU_ITEMS" }), inner_pane)
|
||||||
|
end
|
||||||
|
end),
|
||||||
|
}),
|
||||||
|
pane
|
||||||
|
)
|
||||||
|
end
|
||||||
|
|
||||||
|
local function show_other_settings(window, pane)
|
||||||
|
window:perform_action(
|
||||||
|
act.InputSelector({
|
||||||
|
title = "기타 설정",
|
||||||
|
fuzzy = true,
|
||||||
|
choices = {
|
||||||
|
{ label = "스크롤백 줄 수", id = "scrollback" },
|
||||||
|
{ label = "최대 FPS", id = "max_fps" },
|
||||||
|
{ label = "탭바 위치: 상단", id = "tab_top" },
|
||||||
|
{ label = "탭바 위치: 하단", id = "tab_bottom" },
|
||||||
|
{ label = "창 닫기 확인 켜기", id = "close_prompt" },
|
||||||
|
{ label = "창 닫기 확인 끄기", id = "close_no_prompt" },
|
||||||
|
},
|
||||||
|
action = wezterm.action_callback(function(inner_window, inner_pane, id)
|
||||||
|
if id == "scrollback" then
|
||||||
|
prompt_config_value(inner_window, inner_pane, "스크롤백 줄 수", "scrollback_lines", config.scrollback_lines, false)
|
||||||
|
elseif id == "max_fps" then
|
||||||
|
prompt_config_value(inner_window, inner_pane, "최대 FPS", "max_fps", config.max_fps, false)
|
||||||
|
elseif id == "tab_top" then
|
||||||
|
set_config_value(inner_window, inner_pane, "tab_bar_at_bottom", "false")
|
||||||
|
elseif id == "tab_bottom" then
|
||||||
|
set_config_value(inner_window, inner_pane, "tab_bar_at_bottom", "true")
|
||||||
|
elseif id == "close_prompt" then
|
||||||
|
set_config_value(inner_window, inner_pane, "window_close_confirmation", string.format("%q", "AlwaysPrompt"))
|
||||||
|
elseif id == "close_no_prompt" then
|
||||||
|
set_config_value(inner_window, inner_pane, "window_close_confirmation", string.format("%q", "NeverPrompt"))
|
||||||
|
end
|
||||||
|
end),
|
||||||
|
}),
|
||||||
pane
|
pane
|
||||||
)
|
)
|
||||||
end
|
end
|
||||||
@@ -207,11 +393,11 @@ local function show_main_menu(window, pane)
|
|||||||
end
|
end
|
||||||
|
|
||||||
if id == "font" then
|
if id == "font" then
|
||||||
open_config_section(inner_window, inner_pane, 6)
|
show_font_settings(inner_window, inner_pane)
|
||||||
elseif id == "connection" then
|
elseif id == "connection" then
|
||||||
open_config_section(inner_window, inner_pane, 123)
|
show_connection_settings(inner_window, inner_pane)
|
||||||
elseif id == "other" then
|
elseif id == "other" then
|
||||||
open_config_section(inner_window, inner_pane, 339)
|
show_other_settings(inner_window, inner_pane)
|
||||||
elseif id == "launcher" then
|
elseif id == "launcher" then
|
||||||
inner_window:perform_action(
|
inner_window:perform_action(
|
||||||
act.ShowLauncherArgs({ flags = "FUZZY|TABS|DOMAINS|WORKSPACES|LAUNCH_MENU_ITEMS" }),
|
act.ShowLauncherArgs({ flags = "FUZZY|TABS|DOMAINS|WORKSPACES|LAUNCH_MENU_ITEMS" }),
|
||||||
@@ -230,6 +416,13 @@ wezterm.on("show-main-menu", function(window, pane)
|
|||||||
show_main_menu(window, pane)
|
show_main_menu(window, pane)
|
||||||
end)
|
end)
|
||||||
|
|
||||||
|
wezterm.on("open-uri", function(window, pane, uri)
|
||||||
|
if uri == "wezterm://main-menu" then
|
||||||
|
show_main_menu(window, pane)
|
||||||
|
return false
|
||||||
|
end
|
||||||
|
end)
|
||||||
|
|
||||||
-- 시작 시 첫 화면으로 메인 메뉴를 띄워 설정과 연결 메뉴에 바로 접근합니다.
|
-- 시작 시 첫 화면으로 메인 메뉴를 띄워 설정과 연결 메뉴에 바로 접근합니다.
|
||||||
wezterm.on("gui-startup", function(cmd)
|
wezterm.on("gui-startup", function(cmd)
|
||||||
local tab, pane, window = wezterm.mux.spawn_window(cmd or {})
|
local tab, pane, window = wezterm.mux.spawn_window(cmd or {})
|
||||||
|
|||||||
Reference in New Issue
Block a user