1
1
mirror of https://github.com/neosubhamoy/neodlp.git synced 2026-06-10 04:13:44 +05:30

feat: added quit-on-close option #18 #33

This commit is contained in:
2026-05-26 11:20:05 +05:30
Verified
parent a213a1e8ad
commit eb4cb16bbd
6 changed files with 79 additions and 4 deletions
+2
View File
@@ -13,6 +13,8 @@
"core:window:allow-minimize",
"core:window:allow-maximize",
"core:window:allow-unmaximize",
"core:window:allow-close",
"core:window:allow-destroy",
"core:window:allow-start-dragging",
"opener:default",
"shell:default",
+29 -3
View File
@@ -4,7 +4,7 @@ import { AppContext } from "@/providers/appContextProvider";
import { useEffect, useRef, useState } from "react";
import { arch, exeExtension } from "@tauri-apps/plugin-os";
import { downloadDir, join, resourceDir, tempDir, dataDir } from "@tauri-apps/api/path";
import { useBasePathsStore, useCurrentVideoMetadataStore, useDownloaderPageStatesStore, useDownloadStatesStore, useEnvironmentStore, useKvPairsStatesStore, useSettingsPageStatesStore } from "@/services/store";
import { useBasePathsStore, useCurrentVideoMetadataStore, useDownloadActionStatesStore, useDownloaderPageStatesStore, useDownloadStatesStore, useEnvironmentStore, useKvPairsStatesStore, useSettingsPageStatesStore } from "@/services/store";
import { isObjEmpty} from "@/utils";
import { Command } from "@tauri-apps/plugin-shell";
import { useUpdateDownloadStatus } from "@/services/mutations";
@@ -60,6 +60,7 @@ export default function App({ children }: { children: React.ReactNode }) {
theme: APP_THEME,
color_scheme: APP_COLOR_SCHEME,
use_potoken: USE_POTOKEN,
quit_on_close: QUIT_ON_CLOSE
} = useSettingsPageStatesStore(state => state.settings);
const erroredDownloadIds = useDownloaderPageStatesStore((state) => state.erroredDownloadIds);
@@ -96,6 +97,24 @@ export default function App({ children }: { children: React.ReactNode }) {
const { fetchVideoMetadata, startDownload, pauseDownload, resumeDownload, cancelDownload, processQueuedDownloads } = useDownloader();
const ongoingDownloadsCloseable = globalDownloadStates.filter(state => ['starting', 'downloading', 'queued'].includes(state.download_status));
const setIsPausingDownload = useDownloadActionStatesStore(state => state.setIsPausingDownload);
const stopOngoingDownloads = async () => {
if (ongoingDownloadsCloseable.length > 0) {
for (const state of ongoingDownloadsCloseable) {
setIsPausingDownload(state.download_id, true);
try {
await pauseDownload(state);
} catch (e) {
console.error(e);
} finally {
setIsPausingDownload(state.download_id, false);
}
}
}
}
// Prevent right click context menu in production
if (!import.meta.env.DEV) {
document.oncontextmenu = (event) => {
@@ -105,9 +124,16 @@ export default function App({ children }: { children: React.ReactNode }) {
// Prevent app from closing
useEffect(() => {
const handleCloseRequested = (event: any) => {
const handleCloseRequested = async (event: any) => {
event.preventDefault();
appWindow.hide();
if (QUIT_ON_CLOSE) {
if (ongoingDownloads.length > 0) {
await stopOngoingDownloads()
}
await appWindow.destroy();
} else {
await appWindow.hide();
}
};
appWindow.onCloseRequested(handleCloseRequested);
@@ -130,6 +130,7 @@ function AppGeneralSettings() {
const maxRetries = useSettingsPageStatesStore(state => state.settings.max_retries);
const preferVideoOverPlaylist = useSettingsPageStatesStore(state => state.settings.prefer_video_over_playlist);
const strictDownloadabilityCheck = useSettingsPageStatesStore(state => state.settings.strict_downloadablity_check);
const quitOnClose = useSettingsPageStatesStore(state => state.settings.quit_on_close);
const useAria2 = useSettingsPageStatesStore(state => state.settings.use_aria2);
const useCustomCommands = useSettingsPageStatesStore(state => state.settings.use_custom_commands);
@@ -179,6 +180,15 @@ function AppGeneralSettings() {
/>
<Label htmlFor="max-retries" className="text-xs text-muted-foreground">(Current: {maxRetries}) (Default: 5, Maximum: 100)</Label>
</div>
<div className="quit-on-close">
<h3 className="font-semibold">Quit on Close</h3>
<p className="text-xs text-muted-foreground mb-3">Wheather to quit the app when the main window is closed, if disabled the app will keep running in the background and you can open the main window again from the system tray</p>
<Switch
id="quit-on-close"
checked={quitOnClose}
onCheckedChange={(checked) => saveSettingsKey('quit_on_close', checked)}
/>
</div>
<div className="aria2">
<h3 className="font-semibold">Aria2</h3>
<p className="text-xs text-muted-foreground mb-3">Use aria2c as external downloader (recommended only if you are experiancing too slow download speeds with native downloader, you need to install aria2 via homebrew if you are on macos to use this feature)</p>
+35 -1
View File
@@ -4,10 +4,35 @@ import { MaximizeIcon } from "@/components/icons/maximize";
import { MinimizeIcon } from "@/components/icons/minimize";
import { CloseIcon } from "@/components/icons/close";
import { UnmaximizeIcon } from "@/components/icons/unmaximize";
import { useDownloadActionStatesStore, useDownloadStatesStore, useSettingsPageStatesStore } from "@/services/store";
import { useAppContext } from "@/providers/appContextProvider";
export default function TitleBar() {
const [maximized, setMaximized] = useState<boolean>(false);
const appWindow = getCurrentWebviewWindow();
const quitOnClose = useSettingsPageStatesStore(state => state.settings.quit_on_close);
const downloadStates = useDownloadStatesStore(state => state.downloadStates);
const ongoingDownloads = downloadStates.filter(state =>
['starting', 'downloading', 'queued'].includes(state.download_status)
);
const setIsPausingDownload = useDownloadActionStatesStore(state => state.setIsPausingDownload);
const { pauseDownload } = useAppContext();
const stopOngoingDownloads = async () => {
if (ongoingDownloads.length > 0) {
for (const state of ongoingDownloads) {
setIsPausingDownload(state.download_id, true);
try {
await pauseDownload(state);
} catch (e) {
console.error(e);
} finally {
setIsPausingDownload(state.download_id, false);
}
}
}
}
return (
<div className="titlebar flex items-center justify-between border-b bg-background">
@@ -48,7 +73,16 @@ export default function TitleBar() {
className="px-4 py-3 hover:bg-destructive"
id="titlebar-close"
title="Close"
onClick={() => appWindow.hide()}
onClick={async () => {
if (quitOnClose) {
if (ongoingDownloads.length > 0) {
await stopOngoingDownloads();
}
await appWindow.destroy();
} else {
await appWindow.hide()
}
}}
>
<CloseIcon />
</button>
+2
View File
@@ -223,6 +223,7 @@ export const useSettingsPageStatesStore = create<SettingsPageStatesStore>((set)
pot_server_port: 4416,
windows_filenames: true,
restrict_filenames: true,
quit_on_close: false,
// extension settings
websocket_port: 53511
},
@@ -310,6 +311,7 @@ export const useSettingsPageStatesStore = create<SettingsPageStatesStore>((set)
pot_server_port: 4416,
windows_filenames: true,
restrict_filenames: true,
quit_on_close: false,
// extension settings
websocket_port: 53511
},
+1
View File
@@ -66,6 +66,7 @@ export interface Settings {
pot_server_port: number;
windows_filenames: boolean;
restrict_filenames: boolean;
quit_on_close: boolean;
// extension settings
websocket_port: number;
}