Skip to content

Commit

Permalink
feat: will check has recording item when close window
Browse files Browse the repository at this point in the history
  • Loading branch information
chenfan0 committed Jun 29, 2024
1 parent 7a47749 commit 938b43b
Show file tree
Hide file tree
Showing 9 changed files with 129 additions and 51 deletions.
3 changes: 3 additions & 0 deletions src/const.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,4 +13,7 @@ export const MINIMIZE_WINDOW = 'MINIMIZE_WINDOW'
export const MAXIMIZE_RESTORE_WINDOW = 'MAXIMIZE_RESTORE_WINDOW'
export const CLOSE_WINDOW = 'CLOSE_WINDOW'

export const USER_CLOSE_WINDOW = 'USER_CLOSE_WINDOW'
export const FORCE_CLOSE_WINDOW = 'FORCE_CLOSE_WINDOW'

export const RECORD_DUMMY_PROCESS = { kill: () => {} }
22 changes: 20 additions & 2 deletions src/main/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import { electronApp, optimizer, is } from '@electron-toolkit/utils'
import {
CLOSE_WINDOW,
FFMPEG_PROGRESS_INFO,
FORCE_CLOSE_WINDOW,
GET_LIVE_URLS,
MAXIMIZE_RESTORE_WINDOW,
MINIMIZE_WINDOW,
Expand All @@ -13,7 +14,8 @@ import {
SHOW_NOTIFICATION,
START_STREAM_RECORD,
STOP_STREAM_RECORD,
STREAM_RECORD_END
STREAM_RECORD_END,
USER_CLOSE_WINDOW
} from '../const'
import { getLiveUrls } from './crawler/index'
import { FFMPEG_ERROR_CODE, SUCCESS_CODE } from '../code'
Expand Down Expand Up @@ -81,6 +83,11 @@ function createWindow(): void {
return { action: 'deny' }
})

mainWindow.on('close', (e) => {
e.preventDefault()
mainWindow.webContents.send(USER_CLOSE_WINDOW)
})

// HMR for renderer base on electron-vite cli.
// Load the remote URL for development or the local html file for production.
if (is.dev && process.env['ELECTRON_RENDERER_URL']) {
Expand Down Expand Up @@ -203,6 +210,17 @@ app.whenReady().then(() => {
win?.close()
})

ipcMain.handle(FORCE_CLOSE_WINDOW, () => {
const stillRecordStreamKeys = Object.keys(recordStreamFfmpegProcessMap)

stillRecordStreamKeys.forEach((key) => {
resetRecordStreamFfmpeg(key)
})
clearTimerWhenAllFfmpegProcessEnd()

win?.destroy()
})

createWindow()

app.on('activate', function () {
Expand All @@ -216,7 +234,7 @@ app.whenReady().then(() => {
// for applications and their menu bar to stay active until the user quits
// explicitly with Cmd + Q.
app.on('window-all-closed', () => {
if (process.platform !== 'darwin') {
if (process.platform !== 'darwin' || is.dev) {
app.quit()
}
})
Expand Down
2 changes: 2 additions & 0 deletions src/preload/index.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,9 +18,11 @@ declare global {
minimizeWindow: () => void
maxRestoreWindow: () => void
closeWindow: () => void
forceCloseWindow: () => void

onStreamRecordEnd: (callback: (title: string, code: number) => void) => void
onFFmpegProgressInfo: (callback: (info: IFfmpegProgressInfo) => void) => void
onUserCloseWindow: (callback: () => void) => void
}
}
}
10 changes: 9 additions & 1 deletion src/preload/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,14 +3,16 @@ import { electronAPI } from '@electron-toolkit/preload'
import {
CLOSE_WINDOW,
FFMPEG_PROGRESS_INFO,
FORCE_CLOSE_WINDOW,
MAXIMIZE_RESTORE_WINDOW,
MINIMIZE_WINDOW,
NAV_BY_DEFAULT_BROWSER,
SELECT_DIR,
SHOW_NOTIFICATION,
START_STREAM_RECORD,
STOP_STREAM_RECORD,
STREAM_RECORD_END
STREAM_RECORD_END,
USER_CLOSE_WINDOW
} from '../const'

// Custom APIs for renderer
Expand All @@ -29,6 +31,7 @@ const api = {
minimizeWindow: () => ipcRenderer.invoke(MINIMIZE_WINDOW),
maxRestoreWindow: () => ipcRenderer.invoke(MAXIMIZE_RESTORE_WINDOW),
closeWindow: () => ipcRenderer.invoke(CLOSE_WINDOW),
forceCloseWindow: () => ipcRenderer.invoke(FORCE_CLOSE_WINDOW),

onStreamRecordEnd: (callback: (title: string, code: number) => void) => {
ipcRenderer.on(STREAM_RECORD_END, (_, title, code) => {
Expand All @@ -39,6 +42,11 @@ const api = {
ipcRenderer.on(FFMPEG_PROGRESS_INFO, (_, info) => {
callback(info)
})
},
onUserCloseWindow: (callback: () => void) => {
ipcRenderer.on(USER_CLOSE_WINDOW, () => {
callback()
})
}
}

Expand Down
43 changes: 43 additions & 0 deletions src/renderer/src/components/Dialog.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
import {
Dialog as ShadcnDialog,
DialogContent as ShadcnDialogContent,
DialogHeader as ShadcnDialogHeader,
DialogTitle as ShadcnDialogTitle,
DialogFooter as ShadcnDialogFooter
} from '@/shadcn/ui/dialog'
import { Button } from '@renderer/shadcn/ui/button'

interface DialogProps {
title: string
btnText: string
dialogOpen: boolean
onOpenChange: (open: boolean) => void
handleBtnClick: () => void
variant?:
| 'link'
| 'default'
| 'destructive'
| 'outline'
| 'secondary'
| 'ghost'
| null
| undefined
}

export default function Dialog(props: DialogProps) {
const { title, dialogOpen, btnText, variant, onOpenChange, handleBtnClick } = props
return (
<ShadcnDialog open={dialogOpen} onOpenChange={onOpenChange}>
<ShadcnDialogContent>
<ShadcnDialogHeader>
<ShadcnDialogTitle className="mt-[20px]">{title}</ShadcnDialogTitle>
</ShadcnDialogHeader>
<ShadcnDialogFooter>
<Button className="mt-[20px]" variant={variant} onClick={handleBtnClick}>
{btnText}
</Button>
</ShadcnDialogFooter>
</ShadcnDialogContent>
</ShadcnDialog>
)
}
46 changes: 41 additions & 5 deletions src/renderer/src/components/StreamConfigList/StreamConfigList.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,8 @@
import { useState } from 'react'
import { useMount } from 'react-use'
import { useTranslation } from 'react-i18next'

import Dialog from '@/components/Dialog'
import StreamConfigCard from './components/StreamConfigCard'

import { SUCCESS_CODE, FFMPEG_ERROR_CODE, errorCodeToI18nMessage } from '../../../../code'
Expand All @@ -7,25 +11,37 @@ import { useStreamConfigStore } from '@/store/useStreamConfigStore'
import { useFfmpegProgressInfoStore } from '@/store/useFfmpegProgressInfoStore'
import { StreamStatus } from '@renderer/lib/utils'
import { useToast } from '@renderer/hooks/useToast'
import { useTranslation } from 'react-i18next'

export default function StreamConfigList() {
const { streamConfigList } = useStreamConfigStore((state) => state)
const [closeWindowDialogOpen, setCloseWindowDialogOpen] = useState(false)
const { streamConfigList, updateStreamConfig } = useStreamConfigStore((state) => state)
const { updateFfmpegProgressInfo } = useFfmpegProgressInfoStore((state) => state)
const { toast } = useToast()
const { t } = useTranslation()

const handleForceCloseWindow = () => {
setCloseWindowDialogOpen(false)

streamConfigList.forEach((streamConfig, index) => {
if (streamConfig.status !== StreamStatus.NOT_STARTED) {
updateStreamConfig({ ...streamConfig, status: StreamStatus.NOT_STARTED }, index)
}
})

setTimeout(() => {
window.api.forceCloseWindow()
})
}

useMount(() => {
window.api.onFFmpegProgressInfo((progressInfo) => {
console.log('onFFmpegProgressInfo', progressInfo)
updateFfmpegProgressInfo(progressInfo)
})

window.api.onStreamRecordEnd(async (title, code) => {
const { streamConfigList, updateStreamConfig } = useStreamConfigStore.getState()
const index = streamConfigList.findIndex((streamConfig) => streamConfig.title === title)

console.log('onStreamRecordEnd', title, code)
if (index === -1) {
return
}
Expand All @@ -36,7 +52,6 @@ export default function StreamConfigList() {
const isStopByUser = code === FFMPEG_ERROR_CODE.USER_KILL_PROCESS
const isStopByStreamEnd = code === SUCCESS_CODE

console.log('status:', streamConfig.status)
if (streamConfig.status === StreamStatus.RECORDING) {
updateStreamConfig({ ...streamConfig, status: StreamStatus.VIDEO_FORMAT_CONVERSION }, index)
return
Expand Down Expand Up @@ -80,6 +95,19 @@ export default function StreamConfigList() {

updateStreamConfig({ ...streamConfig, status: StreamStatus.NOT_STARTED }, index)
})

window.api.onUserCloseWindow(() => {
const { streamConfigList } = useStreamConfigStore.getState()

const stillWorkStream = streamConfigList.find(
(streamConfig) => streamConfig.status !== StreamStatus.NOT_STARTED
)
if (!stillWorkStream) {
window.api.forceCloseWindow()
return
}
setCloseWindowDialogOpen(true)
})
})

return (
Expand All @@ -91,6 +119,14 @@ export default function StreamConfigList() {
))}
</div>
}
<Dialog
title={t('stream_config.confirm_force_close_window')}
btnText={t('stream_config.confirm')}
dialogOpen={closeWindowDialogOpen}
onOpenChange={setCloseWindowDialogOpen}
variant="default"
handleBtnClick={handleForceCloseWindow}
/>
</>
)
}

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import { useRef, useState } from 'react'
import { useTranslation } from 'react-i18next'

import UseThemeIcon from '@/components/UseThemeIcon'
import Dialog from '@/components/Dialog'
import { useStreamConfigStore } from '@/store/useStreamConfigStore'

// import darkPreviewIcon from '@/assets/images/dark/preview.svg'
Expand All @@ -16,9 +17,9 @@ import darkDeleteIcon from '@/assets/images/dark/close.svg'
import lightDeleteIcon from '@/assets/images/light/close.svg'
import { StreamStatus } from '@renderer/lib/utils'
import StreamConfigSheet from '@renderer/components/StreamConfigSheet'
import DeleteRecordDialog from './DeleteRecordDialog'
import { CRAWLER_ERROR_CODE, SUCCESS_CODE, errorCodeToI18nMessage } from '../../../../../code'

import { useToast } from '@renderer/hooks/useToast'
import { CRAWLER_ERROR_CODE, SUCCESS_CODE, errorCodeToI18nMessage } from '../../../../../code'

interface OperationBarProps {
index: number
Expand Down Expand Up @@ -84,13 +85,6 @@ export default function OperationBar(props: OperationBarProps) {
description: errMessage,
variant: 'destructive'
})

// updateStreamConfig({ ...streamConfig, status: StreamStatus.NOT_STARTED }, index)
// toast({
// title: streamConfig.title,
// description: t('record.start_failed'),
// variant: 'destructive'
// })
}

const handlePlayClick = () => {
Expand Down Expand Up @@ -150,11 +144,13 @@ export default function OperationBar(props: OperationBarProps) {
type="edit"
/>

<DeleteRecordDialog
title={streamConfig.title}
<Dialog
title={t('stream_config.confirm_delete', { title: streamConfig.title })}
btnText={t('stream_config.delete')}
dialogOpen={deleteDialogOpen}
onOpenChange={setDeleteDialogOpen}
handleConfirmDelete={handleConfirmDelete}
handleBtnClick={handleConfirmDelete}
variant="destructive"
/>
</>
)
Expand Down
3 changes: 3 additions & 0 deletions src/renderer/src/locales/locales.js
Original file line number Diff line number Diff line change
Expand Up @@ -82,6 +82,9 @@ export default {
},
stream_config: {
confirm: '确认',
confirm_delete: '确定删除该录制项? ({{title}})',
delete: '删除',
confirm_force_close_window: '当前有录制任务正在进行, 是否强制关闭窗口?',
create: '新建录制项',
edit: '编辑录制项',
title: '标题',
Expand Down

0 comments on commit 938b43b

Please sign in to comment.