diff --git a/main.py b/main.py index 2e1f739..be5d8b9 100644 --- a/main.py +++ b/main.py @@ -222,12 +222,23 @@ class WhisperApp(QObject): self.settings_root.setVisible(False) # Install Low-Level Window Hook for Transparent Hit Test - # We must keep a reference to 'self.hook' so it isn't GC'd - # scale = self.overlay_root.devicePixelRatio() - # self.hook = WindowHook(int(self.overlay_root.winId()), 500, 300, scale) - # self.hook.install() - - # NOTE: HitTest hook will be installed here later + try: + from src.utils.window_hook import WindowHook + hwnd = self.overlay_root.winId() + # Initial scale from config + scale = float(self.config.get("ui_scale")) + + # Current Overlay Dimensions + win_w = int(460 * scale) + win_h = int(180 * scale) + + self.window_hook = WindowHook(hwnd, win_w, win_h, initial_scale=scale) + self.window_hook.install() + + # Initial state: Disabled because we start inactive + self.window_hook.set_enabled(False) + except Exception as e: + logging.error(f"Failed to install WindowHook: {e}") def center_overlay(self): """Calculates and sets the Overlay position above the taskbar.""" @@ -531,6 +542,25 @@ class WhisperApp(QObject): self.bridge.update_status("Error") logging.error(f"Download Error: {err}") + @Slot(bool) + def on_ui_toggle_request(self, is_recording): + """Called when recording state changes.""" + # Update Window Hook to allow clicking if active + is_active = is_recording or self.bridge.isProcessing + if hasattr(self, 'window_hook'): + self.window_hook.set_enabled(is_active) + + @Slot(bool) + def on_processing_changed(self, is_processing): + is_active = self.bridge.isRecording or is_processing + if hasattr(self, 'window_hook'): + self.window_hook.set_enabled(is_active) + if __name__ == "__main__": + import sys app = WhisperApp() - app.run() + + # Connect extra signal for processing state + app.bridge.isProcessingChanged.connect(app.on_processing_changed) + + sys.exit(app.run()) diff --git a/src/utils/window_hook.py b/src/utils/window_hook.py index ffb06f9..d43f5c0 100644 --- a/src/utils/window_hook.py +++ b/src/utils/window_hook.py @@ -65,6 +65,10 @@ class WindowHook: # (Window 420x140, Pill 380x100) self.logical_rect = [20, 20, 20+380, 20+100] self.current_scale = initial_scale + self.enabled = True # New flag + + def set_enabled(self, enabled): + self.enabled = enabled def install(self): proc_address = ctypes.cast(self.new_wnd_proc, ctypes.c_void_p) @@ -73,6 +77,10 @@ class WindowHook: def wnd_proc_callback(self, hwnd, msg, wParam, lParam): try: if msg == WM_NCHITTEST: + # If disabled (invisible/inactive), let clicks pass through (HTTRANSPARENT) + if not self.enabled: + return HTTRANSPARENT + res = self.on_nchittest(lParam) if res != 0: return res