diff --git a/build-plugin.sh b/build-plugin.sh index ed429a2..b952719 100755 --- a/build-plugin.sh +++ b/build-plugin.sh @@ -2,7 +2,7 @@ set -eu PLUGIN="u-navigator" -VERSION="0.2.9" +VERSION="0.2.10" PKG_DIR="packages" WORK_DIR=".plugin-build" PKG_NAME="${PLUGIN}-${VERSION}.tgz" diff --git a/packages/u-navigator-0.2.10.tgz b/packages/u-navigator-0.2.10.tgz new file mode 100644 index 0000000..e7bbc99 Binary files /dev/null and b/packages/u-navigator-0.2.10.tgz differ diff --git a/packages/u-navigator-0.2.9.tgz b/packages/u-navigator-0.2.9.tgz deleted file mode 100644 index 158aed5..0000000 Binary files a/packages/u-navigator-0.2.9.tgz and /dev/null differ diff --git a/server/public/app.js b/server/public/app.js index 3bb2aea..725cc0d 100644 --- a/server/public/app.js +++ b/server/public/app.js @@ -207,7 +207,7 @@ function renderExplorer(body, win) { dropZone.addEventListener('dragover', (event) => { if (hasDropPayload(event)) { event.preventDefault(); - event.dataTransfer.dropEffect = event.altKey ? 'copy' : 'move'; + setDropEffect(event, event.altKey ? 'copy' : 'move'); data.dragOver = true; dropZone.classList.add('drag-over'); } @@ -242,12 +242,7 @@ function renderExplorer(body, win) { }); row.addEventListener('dragstart', (event) => { state.draggedEntry = { path: entry.path, name: entry.name, sourceWindowId: win.id }; - try { - event.dataTransfer.setData('text/plain', entry.path); - } catch { - // Some WebKit builds reject programmatic drag data. App state is the primary channel. - } - event.dataTransfer.effectAllowed = 'copyMove'; + setEffectAllowed(event); row.classList.add('dragging'); }); row.addEventListener('dragend', () => { @@ -260,7 +255,7 @@ function renderExplorer(body, win) { if (entry.type === 'directory') { event.preventDefault(); event.stopPropagation(); - event.dataTransfer.dropEffect = event.altKey ? 'copy' : 'move'; + setDropEffect(event, event.altKey ? 'copy' : 'move'); } }); row.addEventListener('drop', async (event) => { @@ -362,7 +357,7 @@ async function handleDrop(event, win, targetPath) { return; } - const internalPath = state.draggedEntry?.path || safeGetDragText(event); + const internalPath = state.draggedEntry?.path || ''; if (internalPath) { const name = internalPath.split('/').filter(Boolean).at(-1); const destination = `${targetPath.replace(/\/$/, '')}/${name}`; @@ -374,9 +369,10 @@ async function handleDrop(event, win, targetPath) { return; } - if (event.dataTransfer.files.length) { + const files = getDroppedFiles(event); + if (files.length) { const form = new FormData(); - for (const file of event.dataTransfer.files) { + for (const file of files) { form.append('files', file, file.name); } await fetchChecked(apiUrl(`upload.php?path=${encodeURIComponent(targetPath)}`), { @@ -405,7 +401,7 @@ async function reloadExplorerWindows(ids) { } function hasDropPayload(event) { - return Boolean(state.draggedEntry || event.dataTransfer?.types?.includes('Files') || event.dataTransfer?.types?.includes('text/plain')); + return Boolean(state.draggedEntry || getDroppedFiles(event).length); } function showError(error) { @@ -413,11 +409,25 @@ function showError(error) { alert(message); } -function safeGetDragText(event) { +function getDroppedFiles(event) { try { - return event.dataTransfer.getData('text/plain'); + return [...(event.dataTransfer?.files || [])]; } catch { - return ''; + return []; + } +} + +function setEffectAllowed(event) { + try { + event.dataTransfer.effectAllowed = 'copyMove'; + } catch {} +} + +function setDropEffect(event, effect) { + try { + event.dataTransfer.dropEffect = effect; + } catch { + // Browser rejected the requested cursor hint; the app-state drop still works. } } diff --git a/u-navigator.plg b/u-navigator.plg index 3ab2cc2..780654a 100644 --- a/u-navigator.plg +++ b/u-navigator.plg @@ -1,7 +1,7 @@ - + ]> @@ -14,7 +14,7 @@ https://git.casaderoll.de/michael/Unraid-Navigator/raw/branch/main/packages/&package; -a8f39d867d56be04d8645f0975440b0a +cf0f9388fccc94487173e16cd9075cec