diff --git a/BUILD.md b/BUILD.md index 6a8008d..d02db27 100644 --- a/BUILD.md +++ b/BUILD.md @@ -22,7 +22,8 @@ The ZIP root should contain the project files directly. Do not wrap them inside an extra nested `Parroty` directory. Required source/runtime files include `app/`, `tools/`, `requirements.txt`, the -tracked launcher helpers, `parroty.ico`, documentation, and `LICENSE`. +tracked launcher helpers, `parroty.ico`, `app/static/parroty.ico`, documentation, +and `LICENSE`. The voice package must include all eight `builtin_*.wav` files and `app/assets/voices/ATTRIBUTION.md`. @@ -57,11 +58,13 @@ py -3.12 -m py_compile launch_parroty.pyw app/server.py app/tts.py app/narrate_w py -3.12 -c "from app.tts import ENGINE_CATALOG; v=ENGINE_CATALOG['chatterbox']['builtin_voices']; assert len(v)==8; print(list(v))" ``` -After installation, verify the monitor identifies CUDA/NVIDIA, the app opens in -a dedicated maximized window without a visible console, and closing that app -window with X stops the Flask listener and releases port 5000. Also verify the -desktop shortcut uses `parroty.ico`, all eight voices appear, previews work, and -`stop.bat` still shuts down port 5000 as a fallback. +After installation, verify the monitor identifies CUDA/NVIDIA and the app opens in +a dedicated maximized window without a visible console. Confirm the desktop +shortcut, native app window, and taskbar button all use `parroty.ico`. Start a +short narration, close the app window with X, and verify the Flask listener and +every `app.narrate_worker` process exit. Also verify the generated `stop.bat` can +find and stop Parroty workers even when port 5000 is no longer listening. Finally, +confirm all eight voices appear and previews work. Before publishing, review `README.md`, `Quick Start Readme.txt`, `BUILD.md`, `RELEASE_NOTES.md`, and the voice attribution. No version bump or GitHub Release diff --git a/Quick Start Readme.txt b/Quick Start Readme.txt index 07cc6d6..4c754d3 100644 --- a/Quick Start Readme.txt +++ b/Quick Start Readme.txt @@ -16,8 +16,9 @@ launch_parroty.pyw, and the app folder: 5. Save with the exact .bat filename shown. The eight bundled Chatterbox voices already live under app\assets\voices. -No API key or separate voice download is required. Closing the dedicated -Parroty Chrome/Edge app window with X automatically stops the hidden backend. +No API key or separate voice download is required. The dedicated Parroty +Chrome/Edge app window uses the bird icon in its title bar and taskbar. Closing +it with X stops Flask and any active narration workers. ======================================================================== FILE: install_all.bat @@ -98,13 +99,27 @@ exit /b 0 ======================================================================== @echo off -setlocal enabledelayedexpansion -set "FOUND=0" -for /f "tokens=5" %%P in ('netstat -ano ^| findstr ":5000" ^| findstr LISTENING') do ( - taskkill /F /PID %%P >nul 2>&1 - set "FOUND=1" -) -if "!FOUND!"=="0" (echo Parroty was not running.) else (echo Parroty stopped.) +setlocal +cd /d "%~dp0" +title Stop Parroty + +powershell.exe -NoLogo -NoProfile -ExecutionPolicy Bypass -Command ^ + "$root=[IO.Path]::GetFullPath('%CD%');" ^ + "$targets=New-Object 'System.Collections.Generic.HashSet[int]';" ^ + "try { Get-NetTCPConnection -LocalPort 5000 -State Listen -ErrorAction Stop | ForEach-Object { if ($_.OwningProcess -gt 0) { [void]$targets.Add([int]$_.OwningProcess) } } } catch {};" ^ + "Get-CimInstance Win32_Process | Where-Object {" ^ + " $_.Name -match '^pythonw?\.exe$' -and $_.CommandLine -and (" ^ + " ($_.CommandLine -like ('*' + $root + '*launch_parroty.pyw*')) -or" ^ + " ($_.CommandLine -like ('*' + $root + '*-m app.narrate_worker*')) -or" ^ + " ($_.CommandLine -like ('*' + $root + '*-m app.server*'))" ^ + " )" ^ + "} | ForEach-Object { [void]$targets.Add([int]$_.ProcessId) };" ^ + "if ($targets.Count -eq 0) { Write-Host 'Parroty was not running.'; exit 0 };" ^ + "$ordered=@($targets) | Sort-Object -Descending;" ^ + "foreach ($id in $ordered) { & taskkill.exe /PID $id /T /F 2>$null | Out-Null };" ^ + "Remove-Item -LiteralPath (Join-Path $root '.parroty.browser.pid') -Force -ErrorAction SilentlyContinue;" ^ + "Write-Host 'Parroty stopped, including active narration workers.'" + timeout /t 2 >nul exit /b 0 @@ -141,8 +156,8 @@ exit /b 0 1. Run install_all.bat once. 2. Start Parroty with run.bat or the desktop shortcut. -3. Close the Parroty app window with X to stop the hidden backend automatically. -4. Use stop.bat only if the window is already gone or a forced stop is needed. +3. Close the Parroty app window with X to stop Flask and active narration workers. +4. Use stop.bat if the window is already gone or a forced full stop is needed. 5. Use run_debug.bat only for troubleshooting. Do not commit the generated BAT files. They are local/package conveniences. diff --git a/README.md b/README.md index 1a308fd..93852cb 100644 --- a/README.md +++ b/README.md @@ -52,6 +52,8 @@ timestamps. Everything runs on your own machine and opens in Chrome. off — finishing 100+ chapter books on a 16 GB machine without crashes. - **Runs entirely on your own machine** — your files and (for the local engine) your audio never leave your computer. +- **Windows desktop-app behavior:** opens maximized with the Parroty bird icon in + the window and taskbar; closing X stops Flask and active narration workers. ## Screenshots @@ -417,12 +419,13 @@ installed). Press **Ctrl+C** to stop. **Optional Windows launchers:** create the local `.bat` files from `Quick Start Readme.txt`, or use a packaged Windows ZIP that already includes them. `run.bat` starts the backend windowlessly through `pythonw.exe`, opens -Parroty in a dedicated maximized Chrome/Edge app window, and silently creates or -refreshes the desktop shortcut. Closing that Parroty app window with **X** now -automatically stops the hidden Flask backend, the same result as running -`stop.bat`. Output goes to `parroty.log`; `stop.bat` remains available as a -fallback if the window is already gone or the backend needs to be forced closed. -These `.bat` files are deliberately ignored by Git. +Parroty in a dedicated maximized Chrome/Edge app window, applies the Parroty bird +icon to the native window and taskbar button, and silently creates or refreshes +the desktop shortcut. Closing that app window with **X** terminates the complete +Parroty process tree—including an active `app.narrate_worker`—rather than only +closing the port-5000 Flask parent. Output goes to `parroty.log`; `stop.bat` uses +the same full-tree behavior and can also find orphaned Parroty workers if the +listener is already gone. These `.bat` files are deliberately ignored by Git. Starting again later needs no reinstall — setup is one-time. Open a terminal, `cd` into the Parroty folder, activate the venv, and run the server: diff --git a/RELEASE_NOTES.md b/RELEASE_NOTES.md index 7a7eb7e..331d6d3 100644 --- a/RELEASE_NOTES.md +++ b/RELEASE_NOTES.md @@ -12,11 +12,13 @@ No version number is assigned to this update. - Added the bottom-left CPU/GPU/VRAM system monitor. - Added hidden background launching with persistent `parroty.log` diagnostics. - Added a dedicated maximized Chrome/Edge app window using its own browser profile. -- Closing the dedicated Parroty app window now automatically stops the hidden - Flask backend, matching `stop.bat` behavior without affecting normal browser windows. -- Corrected that shutdown detection to monitor the exact native Parroty window - handle rather than waiting for the Chromium process, which may remain alive - after its app window is closed. +- Closing the dedicated Parroty app window now monitors the exact native window + handle and terminates the complete Parroty process tree, including active + `app.narrate_worker` children that Windows would otherwise leave orphaned. +- Updated the local `stop.bat` template to detect both the port-5000 listener and + Parroty launcher/server/narration workers, preventing false “not running” reports. +- Added the Parroty bird favicon and applies `parroty.ico` directly to the native + Chrome/Edge app window so the title bar and Windows taskbar show the app icon. - Added desktop-shortcut creation using the Parroty icon. - Corrected hidden-launch template/static resolution. - Kept narration workers GPU-enabled when the app window is hidden or inactive. diff --git a/app/static/parroty.ico b/app/static/parroty.ico new file mode 100644 index 0000000..5d82775 Binary files /dev/null and b/app/static/parroty.ico differ diff --git a/app/templates/index.html b/app/templates/index.html index c12f649..dac98c3 100644 --- a/app/templates/index.html +++ b/app/templates/index.html @@ -4,6 +4,9 @@