diff --git a/CHANGELOG.md b/CHANGELOG.md index c569906e..a150ea93 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,15 @@ ### Features +- The configuration is now checked when you enter the compilation page, giving you any tips if your configuration is wrong. + +- Button to open compilation logs now changes color at the end of a compilation + + Green: when all scripts compile successfully + Red: when a script gone wrong + +- Recent files: option to show the script full path (#130) + - New documentation released: access the documentation via NexusMods or with the new button at the bottom left ![docs/changelog/Unreleased/documentation.png](docs/changelog/Unreleased/documentation.png) diff --git a/src/renderer/components/dialog/dialog-recent-files.tsx b/src/renderer/components/dialog/dialog-recent-files.tsx index 348b6bb9..f8ff649f 100644 --- a/src/renderer/components/dialog/dialog-recent-files.tsx +++ b/src/renderer/components/dialog/dialog-recent-files.tsx @@ -7,6 +7,7 @@ import CheckBoxIcon from '@mui/icons-material/CheckBox' import CheckBoxOutlineBlankIcon from '@mui/icons-material/CheckBoxOutlineBlank' import DeleteOutlinedIcon from '@mui/icons-material/DeleteOutlined' +import { Checkbox, FormControlLabel, FormGroup } from '@mui/material' import cx from 'classnames' import React, { memo, useCallback, useEffect, useMemo, useState } from 'react' import { useTranslation } from 'react-i18next' @@ -19,6 +20,7 @@ import bridge from '../../bridge' import { useApp } from '../../hooks/use-app' import { useCompilation } from '../../hooks/use-compilation' import { useIpc } from '../../hooks/use-ipc' +import { usePlatform } from '../../hooks/use-platform' import { useRecentFiles } from '../../hooks/use-recent-files' import { useTelemetry } from '../../hooks/use-telemetry' import { scriptsToRenderer } from '../../utils/scripts/scripts-to-renderer' @@ -37,15 +39,18 @@ const DialogRecentFiles = ({ isOpen, onClose }: Props) => { const { send } = useTelemetry() const { setScripts, scripts: loadedScripts } = useCompilation() const { config } = useApp() - const { clearRecentFiles, removeRecentFile, recentFiles } = useRecentFiles() + const platform = usePlatform() + const { + clearRecentFiles, + removeRecentFile, + recentFiles, + showFullPath: [isShowFullPath, setShowFullPath], + } = useRecentFiles() const [selectedRecentFiles, setSelectedRecentFiles] = useState( new Map(), ) const [isFirstRender, setFirstRender] = useState(true) - const isValid = useCallback( - () => selectedRecentFiles.size > 0, - [selectedRecentFiles.size], - ) + const isValid = selectedRecentFiles.size > 0 useEffect(() => { if (!isFirstRender) { @@ -103,13 +108,13 @@ const DialogRecentFiles = ({ isOpen, onClose }: Props) => { setSelectedRecentFiles(new Map()) }) - const onClickClose = useCallback(() => { + const onClickClose = () => { setSelectedRecentFiles(new Map()) onClose() - }, [onClose]) + } - const onClickLoad = useCallback(() => { - if (!isValid()) { + const onClickLoad = () => { + if (!isValid) { return } @@ -121,67 +126,55 @@ const DialogRecentFiles = ({ isOpen, onClose }: Props) => { ) setSelectedRecentFiles(new Map()) onClose() - }, [isValid, onClose, selectedRecentFiles, send, setScripts]) + } - const onDialogClose = useCallback( - (reason: CloseReason) => { - if (reason === CloseReason.enter && isValid()) { - send(TelemetryEvent.recentFilesCloseWithEnter, {}) - onClickLoad() - } else { - onClickClose() - } - }, - [isValid, send, onClickLoad, onClickClose], - ) + const onDialogClose = (reason: CloseReason) => { + if (reason === CloseReason.enter && isValid) { + send(TelemetryEvent.recentFilesCloseWithEnter, {}) + onClickLoad() + } else { + onClickClose() + } + } - const onClickFile = useCallback( - (script: Script) => { - return (e: React.MouseEvent) => { - e.currentTarget.blur() + const onClickFile = (script: Script) => { + return (e: React.MouseEvent) => { + e.currentTarget.blur() - if (selectedRecentFiles.has(script.path)) { - setSelectedRecentFiles(list => { - list.delete(script.path) + if (selectedRecentFiles.has(script.path)) { + setSelectedRecentFiles(list => { + list.delete(script.path) - return new Map(list) - }) - } else { - setSelectedRecentFiles(list => { - list.set(script.path, script) + return new Map(list) + }) + } else { + setSelectedRecentFiles(list => { + list.set(script.path, script) - return new Map(list) - }) - } + return new Map(list) + }) } - }, - [selectedRecentFiles], - ) + } + } - const onClickDeleteFile = useCallback( - (script: Script) => { - return (e: React.MouseEvent) => { - e.currentTarget.blur() + const onClickDeleteFile = (script: Script) => { + return (e: React.MouseEvent) => { + e.currentTarget.blur() - removeRecentFile(script).then(() => { - send(TelemetryEvent.recentFileRemove, {}) - setSelectedRecentFiles(srf => { - srf.delete(script.path) + removeRecentFile(script).then(() => { + send(TelemetryEvent.recentFileRemove, {}) + setSelectedRecentFiles(srf => { + srf.delete(script.path) - return new Map(srf) - }) + return new Map(srf) }) - } - }, - [removeRecentFile, send], - ) + }) + } + } - const isAlreadyLoaded = useCallback( - (script: Script) => { - return !!loadedScripts.find(s => s.path === script.path) - }, - [loadedScripts], - ) + const isAlreadyLoaded = (script: Script) => { + return !!loadedScripts.find(s => s.path === script.path) + } const Line = useCallback( ({ @@ -197,11 +190,44 @@ const DialogRecentFiles = ({ isOpen, onClose }: Props) => { disabled?: boolean script: Script }) => { - const shortenedPath = shorten(script.path, { - length: 20, - home: true, - homedir: config.game?.path ?? '', - }) + console.log('si', script.path, script.name) + + const dirname = (path: string) => { + if (path.length === 0) return '.' + let code = path.charCodeAt(0) + const hasRoot = code === 47 + let end = -1 + let matchedSlash = true + for (let i = path.length - 1; i >= 1; --i) { + code = path.charCodeAt(i) + if (code === 47 /*/*/) { + if (!matchedSlash) { + end = i + break + } + } else { + // We saw the first non-path separator + matchedSlash = false + } + } + + if (end === -1) return hasRoot ? '/' : '.' + if (hasRoot && end === 1) return '//' + return path.slice(0, end) + } + + const shortenedPath = isShowFullPath + ? { + path: `${dirname(script.path)}${ + platform === 'windows' ? '\\' : '/' + }`, + filename: script.name, + } + : shorten(script.path, { + length: 20, + home: true, + homedir: config.game?.path ?? '', + }) return ( <> @@ -223,8 +249,13 @@ const DialogRecentFiles = ({ isOpen, onClose }: Props) => { )} -
- {shortenedPath.path} +
+ {shortenedPath.path}