[Python] 纯文本查看 复制代码
# -*- coding: utf-8 -*-
import os
import sys
import ctypes
import json
import queue
import threading
import traceback
import time
import functools
import subprocess
from datetime import datetime
import winreg
def global_exception_handler(exc_type, exc_value, exc_tb):
error_msg = f"程序崩溃异常:\n类型: {exc_type}\n值: {exc_value}\n堆栈: {''.join(traceback.format_tb(exc_tb))}"
error_log_file = os.path.join(os.path.dirname(os.path.abspath(__file__)), "crash_log.txt")
try:
with open(error_log_file, 'a', encoding='utf-8') as f:
f.write(f"\n{'='*60}\n")
f.write(f"时间: {datetime.now().strftime('%Y-%m-%d %H:%M:%S')}\n")
f.write(error_msg)
f.write(f"\n{'='*60}\n")
except:
pass
sys.__excepthook__(exc_type, exc_value, exc_tb)
sys.excepthook = global_exception_handler
if sys.platform == "win32":
try:
ctypes.windll.kernel32.FreeConsole()
except:
pass
def install_dependencies():
required_packages = {
'keyboard': 'keyboard',
'pygetwindow': 'pygetwindow',
'pywin32': 'win32gui',
'tkinter': 'tkinter'
}
missing_packages = []
for package, import_name in required_packages.items():
try:
if package == 'tkinter':
import tkinter
else:
__import__(import_name if import_name != 'win32gui' else 'win32gui')
except ImportError:
if package not in ['tkinter']:
missing_packages.append(package)
if missing_packages:
try:
import subprocess
for package in missing_packages:
subprocess.check_call([
sys.executable, "-m", "pip", "install",
"-i", "https://pypi.tuna.tsinghua.edu.cn/simple",
package
])
try:
import tkinter.messagebox as msgbox
msgbox.showinfo("依赖安装完成", "依赖安装完成,请重新运行程序")
except:
pass
sys.exit(0)
except Exception as e:
print(f"依赖安装失败: {e}")
sys.exit(1)
try:
install_dependencies()
except:
pass
try:
import tkinter as tk
from tkinter import ttk, messagebox, filedialog
import keyboard
import pygetwindow as gw
import win32gui
import win32con
import win32event
import win32api
import winerror
except Exception as e:
print(f"导入依赖库失败: {e}")
sys.exit(1)
CONFIG_FILE = "bosskey_config.json"
def safe_is_window(hwnd):
if hwnd is None:
return False
try:
return win32gui.IsWindow(hwnd)
except:
return False
def safe_get_window_text(hwnd):
try:
if safe_is_window(hwnd):
return win32gui.GetWindowText(hwnd)
except:
pass
return ""
def safe_show_window(hwnd, show_cmd):
try:
if safe_is_window(hwnd):
win32gui.ShowWindow(hwnd, show_cmd)
return True
except:
pass
return False
def safe_get_foreground_window():
try:
hwnd = win32gui.GetForegroundWindow()
if safe_is_window(hwnd):
return hwnd
except:
pass
return None
def get_all_visible_windows():
windows = []
try:
def callback(hwnd, extra):
if win32gui.IsWindowVisible(hwnd):
title = win32gui.GetWindowText(hwnd)
if title and not title.startswith('Default'):
windows.append((hwnd, title))
return True
win32gui.EnumWindows(callback, None)
except:
pass
return windows
def hide_all_except_target(target_path, exclude_hwnds=None):
if exclude_hwnds is None:
exclude_hwnds = []
hidden = []
try:
windows = get_all_visible_windows()
for hwnd, title in windows:
try:
if hwnd in exclude_hwnds:
continue
if '任务栏' in title or 'Start' in title or 'Taskbar' in title:
continue
if 'Program Manager' in title or '桌面' in title:
continue
if target_path:
target_name = os.path.basename(target_path)
if target_name and target_name in title:
continue
win32gui.ShowWindow(hwnd, win32con.SW_HIDE)
hidden.append((hwnd, title))
except:
pass
except:
pass
return hidden
def restore_all_windows(hidden_windows):
restored = 0
for hwnd, title in hidden_windows:
try:
if safe_is_window(hwnd):
win32gui.ShowWindow(hwnd, win32con.SW_SHOW)
restored += 1
except:
pass
return restored
def open_target_path(path):
try:
if os.path.exists(path):
os.startfile(path)
return True, f"已打开: {os.path.basename(path)}"
else:
return False, f"路径不存在: {path}"
except Exception as e:
return False, f"打开失败: {str(e)}"
def set_auto_start():
try:
key = winreg.OpenKey(winreg.HKEY_CURRENT_USER,
r"Software\Microsoft\Windows\CurrentVersion\Run",
0, winreg.KEY_SET_VALUE)
exe_path = sys.executable if getattr(sys, 'frozen', False) else sys.argv[0]
winreg.SetValueEx(key, "BossKey", 0, winreg.REG_SZ, f'"{exe_path}" --elevated')
winreg.CloseKey(key)
return True
except:
return False
def remove_auto_start():
try:
key = winreg.OpenKey(winreg.HKEY_CURRENT_USER,
r"Software\Microsoft\Windows\CurrentVersion\Run",
0, winreg.KEY_SET_VALUE)
winreg.DeleteValue(key, "BossKey")
winreg.CloseKey(key)
return True
except:
return False
def check_auto_start():
try:
key = winreg.OpenKey(winreg.HKEY_CURRENT_USER,
r"Software\Microsoft\Windows\CurrentVersion\Run",
0, winreg.KEY_READ)
value, _ = winreg.QueryValueEx(key, "BossKey")
winreg.CloseKey(key)
return True
except:
return False
try:
MUTEX_NAME = "Global\\BossKeyAppMutex"
mutex = win32event.CreateMutex(None, False, MUTEX_NAME)
if win32api.GetLastError() == winerror.ERROR_ALREADY_EXISTS:
sys.exit(0)
except:
pass
class HideConfigItem:
HIDE_ALL = "hideall"
OPEN_TARGET = "opentarget"
TYPE_MAP = {
HIDE_ALL: "专注模式(隐藏所有,打开目标)",
OPEN_TARGET: "仅打开目标"
}
REVERSE_MAP = {v: k for k, v in TYPE_MAP.items()}
def __init__(self, enable=True, hide_type=HIDE_ALL, hotkey="", target_path=""):
try:
self.enable = tk.BooleanVar(value=enable)
self.hide_type = tk.StringVar(value=hide_type)
self.hotkey = tk.StringVar(value=hotkey)
self.target_path = tk.StringVar(value=target_path)
self.type_display = tk.StringVar(value=self.TYPE_MAP.get(hide_type, "专注模式"))
self.type_display.trace("w", self._sync_hide_type)
self.hidden_windows = []
self.is_hidden = False
self.target_opened = False
self.lock = threading.Lock()
except:
pass
def _sync_hide_type(self, *args):
try:
eng = self.REVERSE_MAP.get(self.type_display.get(), self.HIDE_ALL)
if self.hide_type.get() != eng:
self.hide_type.set(eng)
except:
pass
def to_dict(self):
try:
return {
"enable": self.enable.get(),
"type": self.hide_type.get(),
"hotkey": self.hotkey.get(),
"target_path": self.target_path.get()
}
except:
return {}
@classmethod
def from_dict(cls, data):
try:
return cls(
enable=data.get("enable", True),
hide_type=data.get("type", cls.HIDE_ALL),
hotkey=data.get("hotkey", ""),
target_path=data.get("target_path", "")
)
except:
return cls()
class BossKeyApp:
def __init__(self, root, auto_start=False):
try:
self.root = root
self.root.title("老板键 V26.06.16 制作:洪强盛15980027880")
self.root.geometry("700x450")
self.root.resizable(True, True)
self.root.protocol("WM_DELETE_WINDOW", self.safe_close)
self._closing = False
self._root_exists = True
self.auto_start = auto_start
self.config_items = []
self.config_frames = []
self.active = False
self.action_queue = queue.Queue()
self.registered_hotkeys = {}
self.running = True
self.all_hidden_windows = []
self.self_hidden = False
self.auto_start_enabled = check_auto_start()
self.load_config()
self.build_ui()
if self.auto_start:
self.root.after(500, self.auto_elevated_start)
self.process_queue()
except:
pass
def safe_close(self):
if self._closing:
return
self._closing = True
try:
self.running = False
if self.active:
self._stop_hotkeys()
self.restore_all_global_windows()
try:
if self.self_hidden:
self.root.deiconify()
self.self_hidden = False
except:
pass
self._root_exists = False
try:
self.root.destroy()
except:
pass
except:
pass
finally:
sys.exit(0)
def restore_all_global_windows(self):
try:
restored = 0
for hwnd, title in self.all_hidden_windows:
if safe_show_window(hwnd, win32con.SW_SHOW):
restored += 1
self.all_hidden_windows.clear()
except:
pass
def build_ui(self):
try:
title_frame = ttk.Frame(self.root)
title_frame.pack(fill="x", padx=20, pady=(10, 5))
ttk.Label(title_frame, text="老板键",
font=("微软雅黑", 14, "bold")).pack(side="left")
ttk.Label(title_frame, text="一键隐藏所有窗口,只留目标文件/文件夹",
font=("微软雅黑", 9), foreground="gray").pack(side="left", padx=10)
container = ttk.Frame(self.root)
container.pack(fill="both", expand=True, padx=20, pady=4)
canvas = tk.Canvas(container, borderwidth=0, highlightthickness=0)
scrollbar = ttk.Scrollbar(container, orient="vertical", command=canvas.yview)
self.config_list_frame = ttk.Frame(canvas)
self.config_list_frame.bind("<Configure>",
lambda e: canvas.configure(scrollregion=canvas.bbox("all")))
canvas.create_window((0, 0), window=self.config_list_frame, anchor="nw")
canvas.configure(yscrollcommand=scrollbar.set)
canvas.pack(side="left", fill="both", expand=True)
scrollbar.pack(side="right", fill="y")
for item in self.config_items:
self._add_config_row(item)
if not self.config_items:
default_item = HideConfigItem(
hide_type=HideConfigItem.HIDE_ALL,
hotkey="ctrl+enter",
target_path=""
)
self.config_items.append(default_item)
self._add_config_row(default_item)
bottom_frame = ttk.Frame(self.root)
bottom_frame.pack(pady=(8, 5), fill="x", padx=20)
btn_frame = ttk.Frame(bottom_frame)
btn_frame.pack()
ttk.Button(btn_frame, text="添加配置", command=self.add_config_item).pack(side="left", padx=3)
self.start_btn = ttk.Button(btn_frame, text="启动老板键", command=self.start)
self.start_btn.pack(side="left", padx=3)
self.stop_btn = ttk.Button(btn_frame, text="停止老板键", command=self.stop, state="disabled")
self.stop_btn.pack(side="left", padx=3)
ttk.Button(btn_frame, text="恢复所有窗口", command=self.restore_all_windows_ui).pack(side="left", padx=3)
self.auto_start_btn = ttk.Button(btn_frame, text="开机自启", command=self.toggle_auto_start)
self.auto_start_btn.pack(side="left", padx=3)
self.update_auto_start_btn()
status_frame = ttk.Frame(self.root)
status_frame.pack(fill="x", padx=20, pady=(5, 10))
self.status_label = ttk.Label(status_frame, text="状态:未启动", foreground="gray")
self.status_label.pack(side="left")
except:
pass
def update_auto_start_btn(self):
try:
if self.auto_start_enabled:
self.auto_start_btn.config(text="✓ 开机自启", foreground="green")
else:
self.auto_start_btn.config(text="开机自启", foreground="black")
except:
pass
def toggle_auto_start(self):
try:
if self.auto_start_enabled:
if remove_auto_start():
self.auto_start_enabled = False
self.update_auto_start_btn()
self.update_status("已取消开机自启")
messagebox.showinfo("提示", "已取消开机自启")
else:
messagebox.showerror("错误", "取消开机自启失败,请以管理员身份运行")
else:
if set_auto_start():
self.auto_start_enabled = True
self.update_auto_start_btn()
self.update_status("已设置开机自启")
messagebox.showinfo("提示", "已设置开机自启")
else:
messagebox.showerror("错误", "设置开机自启失败,请以管理员身份运行")
except:
pass
def restore_all_windows_ui(self):
try:
for item in self.config_items:
item.is_hidden = False
item.hidden_windows.clear()
item.target_opened = False
self.restore_all_global_windows()
if self.self_hidden:
try:
self.root.deiconify()
self.self_hidden = False
except:
pass
self.update_status("已恢复所有窗口")
except:
pass
def _add_config_row(self, item):
try:
if not self._root_exists:
return
frame = ttk.Frame(self.config_list_frame, relief="ridge", borderwidth=1)
frame.pack(fill="x", pady=3, padx=2)
row1 = ttk.Frame(frame)
row1.pack(fill="x", pady=2)
ttk.Checkbutton(row1, variable=item.enable).pack(side="left", padx=(5, 2))
type_combo = ttk.Combobox(row1, textvariable=item.type_display,
values=["专注模式(隐藏所有,打开目标)", "仅打开目标"],
state="readonly", width=28)
type_combo.pack(side="left", padx=2)
ttk.Label(row1, text="快捷键:").pack(side="left", padx=(5, 2))
hotkey_entry = ttk.Entry(row1, textvariable=item.hotkey, width=18, font=("Consolas", 10))
hotkey_entry.pack(side="left", padx=2)
ttk.Button(row1, text="捕获",
command=lambda it=item: self.capture_hotkey(it.hotkey)).pack(side="left", padx=2)
status_label = ttk.Label(row1, text="○", foreground="gray")
status_label.pack(side="left", padx=5)
item._status_label = status_label
ttk.Button(row1, text="删除",
command=lambda f=frame, it=item: self.delete_config_item(f, it)).pack(side="right", padx=5)
row2 = ttk.Frame(frame)
row2.pack(fill="x", pady=2)
path_label = ttk.Label(row2, text="目标路径:")
path_label.pack(side="left", padx=(10, 2))
path_entry = ttk.Entry(row2, textvariable=item.target_path, width=45)
path_entry.pack(side="left", padx=2)
ttk.Button(row2, text="浏览文件",
command=lambda it=item: self.browse_file(it)).pack(side="left", padx=2)
ttk.Button(row2, text="浏览文件夹",
command=lambda it=item: self.browse_folder(it)).pack(side="left", padx=2)
self.config_frames.append(frame)
except:
pass
def browse_file(self, item):
try:
file_path = filedialog.askopenfilename(
title="选择文件",
filetypes=[("所有文件", "*.*"), ("可执行文件", "*.exe")]
)
if file_path:
item.target_path.set(file_path)
except:
pass
def browse_folder(self, item):
try:
folder_path = filedialog.askdirectory(title="选择文件夹")
if folder_path:
item.target_path.set(folder_path)
except:
pass
def add_config_item(self):
try:
if not self._root_exists:
return
new_item = HideConfigItem(hide_type=HideConfigItem.HIDE_ALL, hotkey="")
self.config_items.append(new_item)
self._add_config_row(new_item)
except:
pass
def delete_config_item(self, frame, item):
try:
if len(self.config_items) <= 1:
messagebox.showinfo("提示", "至少保留一个配置项")
return
if self.active:
messagebox.showwarning("提示", "请先停止老板键")
return
self.config_items.remove(item)
frame.destroy()
self.config_frames.remove(frame)
except:
pass
def update_status(self, text):
try:
if self._root_exists:
self.status_label.config(text=f"状态:{text}")
except:
pass
def start(self):
if self.active:
return
valid = any(item.enable.get() and item.hotkey.get().strip() for item in self.config_items)
if not valid:
messagebox.showwarning("提示", "请至少启用一个配置项并设置快捷键!")
return
if self._start_hotkeys():
self.active = True
self.start_btn.config(state="disabled")
self.stop_btn.config(state="normal")
self.update_status("已启动")
self.save_config()
hk_list = "\n".join([f" {hk} -> {item.type_display.get()}"
for hk, item in self.registered_hotkeys.items()])
messagebox.showinfo("启动成功", f"老板键已启动!\n\n已注册热键:\n{hk_list}")
else:
messagebox.showerror("错误", "热键注册失败!")
def stop(self):
try:
self.action_queue.put(("stop",))
self.update_status("已停止")
except:
pass
def _start_hotkeys(self):
try:
registered = {}
success_count = 0
for item in self.config_items:
if not item.enable.get():
continue
hk = item.hotkey.get().strip()
if not hk:
continue
try:
try:
keyboard.remove_hotkey(hk)
except:
pass
keyboard.add_hotkey(hk, functools.partial(self._hotkey_callback, item))
registered[hk] = item
success_count += 1
except:
pass
self.registered_hotkeys = registered
return success_count > 0
except:
return False
def _hotkey_callback(self, item):
try:
if self.running and self.active:
self.action_queue.put(("toggle_item", item))
except:
pass
def _stop_hotkeys(self):
try:
for hk in list(self.registered_hotkeys.keys()):
try:
keyboard.remove_hotkey(hk)
except:
pass
self.registered_hotkeys.clear()
self.restore_all_global_windows()
for item in self.config_items:
item.is_hidden = False
item.hidden_windows.clear()
item.target_opened = False
self.active = False
self.start_btn.config(state="normal")
self.stop_btn.config(state="disabled")
except:
pass
def toggle_by_item(self, item):
try:
if not self.running or not self.active:
return
t = item.hide_type.get()
if t == HideConfigItem.HIDE_ALL:
self._focus_mode(item)
elif t == HideConfigItem.OPEN_TARGET:
self._open_target_only(item)
except:
pass
def _focus_mode(self, item):
try:
with item.lock:
if item.is_hidden:
restored = restore_all_windows(item.hidden_windows)
item.hidden_windows.clear()
item.is_hidden = False
item.target_opened = False
if self.self_hidden:
try:
self.root.deiconify()
self.self_hidden = False
except:
pass
self.update_status(f"已恢复 {restored} 个窗口")
if hasattr(item, '_status_label'):
item._status_label.config(text="○", foreground="gray")
else:
target_path = item.target_path.get().strip()
if not target_path:
self.update_status("请设置目标路径")
messagebox.showwarning("提示", "请先设置要打开的目标路径!")
return
if not os.path.exists(target_path):
self.update_status("目标路径不存在")
messagebox.showerror("错误", f"目标路径不存在:\n{target_path}")
return
if not self.self_hidden:
try:
self.root.withdraw()
self.self_hidden = True
except:
pass
exclude_hwnds = []
try:
exclude_hwnds.append(int(self.root.winfo_id()))
except:
pass
if not item.target_opened:
success, msg = open_target_path(target_path)
if success:
item.target_opened = True
time.sleep(0.3)
hidden = hide_all_except_target(target_path, exclude_hwnds)
item.hidden_windows = hidden
item.is_hidden = True
self.all_hidden_windows.extend(hidden)
if item.target_opened:
target_name = os.path.basename(target_path)
self.update_status(f"已隐藏 {len(hidden)} 个窗口,已打开 {target_name}")
else:
self.update_status(f"已隐藏 {len(hidden)} 个窗口")
if hasattr(item, '_status_label'):
item._status_label.config(text="●", foreground="red")
except:
pass
def _open_target_only(self, item):
try:
target_path = item.target_path.get().strip()
if not target_path:
self.update_status("请设置目标路径")
messagebox.showwarning("提示", "请先设置要打开的目标路径!")
return
if not os.path.exists(target_path):
self.update_status("目标路径不存在")
messagebox.showerror("错误", f"目标路径不存在:\n{target_path}")
return
success, msg = open_target_path(target_path)
self.update_status(msg)
if success:
messagebox.showinfo("成功", msg)
else:
messagebox.showerror("错误", msg)
except:
pass
def capture_hotkey(self, var):
def _capture():
try:
self.update_status("请按下组合键...")
hotkey_str = keyboard.read_hotkey(suppress=False)
if self.running:
var.set(hotkey_str)
self.update_status(f"已捕获: {hotkey_str}")
except:
pass
threading.Thread(target=_capture, daemon=True).start()
def process_queue(self):
try:
while True:
try:
cmd = self.action_queue.get_nowait()
if not self.running:
continue
if cmd[0] == "status":
self.update_status(cmd[1])
elif cmd[0] == "update_hotkey":
_, var, value = cmd
var.set(value)
elif cmd[0] == "toggle_item":
self.toggle_by_item(cmd[1])
elif cmd[0] == "stop":
self._stop_hotkeys()
except queue.Empty:
break
except:
pass
except:
pass
if self.running:
try:
self.root.after(100, self.process_queue)
except:
pass
def save_config(self):
try:
data = [item.to_dict() for item in self.config_items]
with open(CONFIG_FILE, "w", encoding="utf-8") as f:
json.dump(data, f, ensure_ascii=False, indent=2)
except:
pass
def load_config(self):
try:
if os.path.exists(CONFIG_FILE):
with open(CONFIG_FILE, "r", encoding="utf-8") as f:
data = json.load(f)
if isinstance(data, list):
for item_data in data:
try:
self.config_items.append(HideConfigItem.from_dict(item_data))
except:
pass
except:
pass
@staticmethod
def is_admin():
try:
return ctypes.windll.shell32.IsUserAnAdmin()
except:
return False
@staticmethod
def run_as_admin():
try:
script = sys.argv[0]
ctypes.windll.shell32.ShellExecuteW(None, "runas", sys.executable, f'"{script}" --elevated', None, 1)
except:
pass
def auto_elevated_start(self):
try:
self.start()
if self.active:
self.root.withdraw()
self.self_hidden = True
except:
pass
if __name__ == "__main__":
try:
auto_mode = "--elevated" in sys.argv
root = tk.Tk()
app = BossKeyApp(root, auto_start=auto_mode)
root.mainloop()
except Exception as e:
try:
root = tk.Tk()
root.withdraw()
messagebox.showerror("启动错误", f"程序启动失败:\n{str(e)}")
root.destroy()
except:
pass
sys.exit(1)