From e0791aa2b0f53dd31f2ddebd23284609cbbc5204 Mon Sep 17 00:00:00 2001 From: Aaron Meese Date: Tue, 9 Aug 2022 20:02:26 -0400 Subject: [PATCH 1/4] Multiselect support (#22) --- index.js | 167 +++++++++++++++++++++++++++++++++++-------------------- 1 file changed, 107 insertions(+), 60 deletions(-) diff --git a/index.js b/index.js index b10c181..32f4398 100644 --- a/index.js +++ b/index.js @@ -125,23 +125,26 @@ const createInitialPaths = (core, proc) => { return {homePath, initialPath}; }; -/** - * Formats file status message - */ -const formatFileMessage = file => `${file.filename} (${file.size} bytes)`; +const getDirectoryCount = files => + files.filter(file => file.isDirectory).length; +const getFileCount = files => + files.filter(file => !file.isDirectory).length; +const getTotalSize = files => + files.reduce((total, file) => total + (file.size || 0), 0); /** * Formats directory status message */ -const formatStatusMessage = (core) => { +const formatStatusMessage = (core, files) => { const {translatable} = core.make('osjs/locale'); const __ = translatable(translations); return (path, files) => { - const directoryCount = files.filter(f => f.isDirectory).length; - const fileCount = files.filter(f => !f.isDirectory).length; - const totalSize = files.reduce((t, f) => t + (f.size || 0), 0); + const directoryCount = getDirectoryCount(files); + const fileCount = getFileCount(files); + const totalSize = getTotalSize(files); + // TODO: Copy over new label messages with translation return __('LBL_STATUS', directoryCount, fileCount, totalSize); }; }; @@ -318,6 +321,8 @@ const vfsActionFactory = (core, proc, win, dialog, state) => { const readdir = async (dir, history, selectFile) => { if (win.getState('loading')) { return; + } else if (Array.isArray(dir)) { + dir = dir[0]; } try { @@ -347,7 +352,7 @@ const vfsActionFactory = (core, proc, win, dialog, state) => { } catch (error) { dialog('error', error, __('MSG_READDIR_ERROR', dir.path)); } finally { - state.currentFile = undefined; + state.currentFile = []; win.setState('loading', false); } }; @@ -359,25 +364,32 @@ const vfsActionFactory = (core, proc, win, dialog, state) => { }); const paste = (move, currentPath) => ({item, callback}) => { - const dest = {path: pathJoin(currentPath.path, item.filename)}; + const promises = items.map(item => { + const dest = { + path: pathJoin(currentPath.path, item.filename) + }; - const fn = move - ? vfs.move(item, dest, {pid: proc.pid}) - : vfs.copy(item, dest, {pid: proc.pid}); + return move + ? vfs.move(item, dest, {pid: proc.pid}) + : vfs.copy(item, dest, {pid: proc.pid}); + }); - return fn - .then(() => { + return Promise + .all(promises) + .then(results => { refresh(true); if (typeof callback === 'function') { callback(); } + + return results; }) .catch(error => dialog('error', error, __('MSG_PASTE_ERROR'))); }; return { - download: file => vfs.download(file), + download: files => files.forEach(file => vfs.download(file)), upload, refresh, action, @@ -430,23 +442,34 @@ const dialogFactory = (core, proc, win) => { value: __('DIALOG_MKDIR_PLACEHOLDER') }, usingPositiveButton(value => { const newPath = pathJoin(currentPath.path, value); - action(() => vfs.mkdir({path: newPath}, {pid: proc.pid}), value, __('MSG_MKDIR_ERROR')); + action( + () => vfs.mkdir({path: newPath}, {pid: proc.pid}), + value, + __('MSG_MKDIR_ERROR') + ); })); - const renameDialog = (action, file) => dialog('prompt', { - message: __('DIALOG_RENAME_MESSAGE', file.filename), - value: file.filename - }, usingPositiveButton(value => { - const idx = file.path.lastIndexOf(file.filename); - const newPath = file.path.substr(0, idx) + value; + const renameDialog = (action, files) => files.forEach(file => + dialog('prompt', { + message: __('DIALOG_RENAME_MESSAGE', file.filename), + value: file.filename + }, usingPositiveButton(value => { + const idx = file.path.lastIndexOf(file.filename); + const newPath = file.path.substr(0, idx) + value; - action(() => vfs.rename(file, {path: newPath}), value, __('MSG_RENAME_ERROR')); - })); + action(() => vfs.rename(file, {path: newPath}), value, __('MSG_RENAME_ERROR')); + }))); - const deleteDialog = (action, file) => dialog('confirm', { + const deleteDialog = (action, files) => dialog('confirm', { message: __('DIALOG_DELETE_MESSAGE', file.filename), }, usingPositiveButton(() => { - action(() => vfs.unlink(file, {pid: proc.pid}), true, __('MSG_DELETE_ERROR')); + action( + () => Promise.all( + files.map(file => vfs.unlink(file, {pid: proc.pid})) + ), + true, + __('MSG_DELETE_ERROR') + ); })); const progressDialog = (file) => dialog('progress', { @@ -512,40 +535,44 @@ const menuFactory = (core, proc, win) => { {label: _('LBL_QUIT'), onclick: () => win.emit('filemanager:menu:quit')} ]); - const createEditMenu = async (item, isContextMenu) => { - const emitter = name => win.emit(name, item); + const createEditMenu = async (items, isContextMenu) => { + const emitter = name => win.emit(name, items); + const item = items[items.length - 1]; - if (item && isSpecialFile(item.filename)) { - return [{ + if (items.length === 1 && item && isSpecialFile(item.filename)) { + return [{ label: _('LBL_GO'), - onclick: () => emitter('filemanager:navigate') - }]; - } + onclick: () => emitter('filemanager:navigate'), + }]; + } - const isValidFile = item && !isSpecialFile(item.filename); - const isDirectory = item && item.isDirectory; + const canDownload = items.some( + item => !item.isDirectory && !isSpecialFile(item.filename) + ); + const hasValidFile = items.some(item => !isSpecialFile(item.filename)); + const isDirectory = items.length === 1 && item.isDirectory; const openMenu = isDirectory ? [{ label: _('LBL_GO'), - disabled: !item, + disabled: !items.length, onclick: () => emitter('filemanager:navigate') }] : [{ label: _('LBL_OPEN'), - disabled: !item, + disabled: !items.length, onclick: () => emitter('filemanager:open') }, { label: __('LBL_OPEN_WITH'), - disabled: !item, + disabled: !items.length, onclick: () => emitter('filemanager:openWith') }]; const clipboardMenu = [{ label: _('LBL_COPY'), - disabled: !isValidFile, + disabled: !hasValidFile, onclick: () => emitter('filemanager:menu:copy') }, { label: _('LBL_CUT'), - disabled: !isValidFile, + disabled: !hasValidFile, onclick: () => emitter('filemanager:menu:cut') }]; @@ -563,7 +590,7 @@ const menuFactory = (core, proc, win) => { if (core.config('filemanager.disableDownload', false) !== true) { configuredItems.push({ label: _('LBL_DOWNLOAD'), - disabled: !item || isDirectory || !isValidFile, + disabled: !canDownload, onclick: () => emitter('filemanager:menu:download') }); } @@ -572,12 +599,12 @@ const menuFactory = (core, proc, win) => { ...openMenu, { label: _('LBL_RENAME'), - disabled: !isValidFile, + disabled: !hasValidFile, onclick: () => emitter('filemanager:menu:rename') }, { label: _('LBL_DELETE'), - disabled: !isValidFile, + disabled: !hasValidFile, onclick: () => emitter('filemanager:menu:delete') }, ...clipboardMenu, @@ -685,7 +712,6 @@ const createApplication = (core, proc) => { const createRows = listViewRowFactory(core, proc); const createMounts = mountViewRowsFactory(core); const {draggable} = core.make('osjs/dnd'); - const statusMessage = formatStatusMessage(core); const initialState = { path: '', @@ -705,7 +731,9 @@ const createApplication = (core, proc) => { }), fileview: listView.state({ - columns: [] + columns: [], + multiselect: true, + previousSelectedIndex: 0 }) }; @@ -742,18 +770,18 @@ const createApplication = (core, proc) => { setStatus: status => ({status}), setMinimalistic: minimalistic => ({minimalistic}), setList: ({list, path, selectFile}) => ({fileview, mountview}) => { - let selectedIndex; + let selectedIndex = []; if (selectFile) { const foundIndex = list.findIndex(file => file.filename === selectFile); if (foundIndex !== -1) { - selectedIndex = foundIndex; + selectedIndex = [foundIndex]; } } return { path, - status: statusMessage(path, list), + status: formatStatusMessage(list), mountview: Object.assign({}, mountview, { rows: createMounts() }), @@ -771,7 +799,10 @@ const createApplication = (core, proc) => { fileview: listView.actions({ select: ({data}) => win.emit('filemanager:select', data), - activate: ({data}) => win.emit(`filemanager:${data.isFile ? 'open' : 'navigate'}`, data), + activate: ({data}) => + data.forEach(item => + win.emit(`filemanager:${item.isFile ? 'open' : 'navigate'}`, item) + ), contextmenu: args => win.emit('filemanager:contextmenu', args), created: ({el, data}) => { if (data.isFile) { @@ -793,7 +824,7 @@ const createApplication = (core, proc) => { */ const createWindow = (core, proc) => { let wired; - const state = {currentFile: undefined, currentPath: undefined}; + const state = {currentFile: [], currentPath: undefined}; const {homePath, initialPath} = createInitialPaths(core, proc); const title = core.make('osjs/locale').translatableFlat(proc.metadata.title); @@ -812,13 +843,29 @@ const createWindow = (core, proc) => { const onDrop = (...args) => vfs.drop(...args); const onHome = () => vfs.readdir(homePath, 'clear'); const onNavigate = (...args) => vfs.readdir(...args); - const onSelectItem = file => (state.currentFile = file); - const onSelectStatus = file => win.emit('filemanager:status', formatFileMessage(file)); + const onSelectItem = files => (state.currentFile = files); + const onSelectStatus = files => win.emit('filemanager:status', formatStatusMessage(files)); const onContextMenu = ({ev, data}) => createMenu({ev, name: 'edit'}, data, true); const onReaddirRender = args => wired.setList(args); const onRefresh = (...args) => vfs.refresh(...args); - const onOpen = file => core.open(file, {useDefault: true}); - const onOpenWith = file => core.open(file, {useDefault: true, forceDialog: true}); + const onOpen = files => { + if (!Array.isArray(files)) { + files = [files]; + } + + return files.forEach( + file => core.open(file, {useDefault: true}) + ); + }; + const onOpenWith = files => { + if (!Array.isArray(files)) { + files = [files]; + } + + return files.forEach( + file => core.open(file, {useDefault: true, forceDialog: true}) + ); + }; const onHistoryPush = file => wired.history.push(file); const onHistoryClear = () => wired.history.clear(); const onMenu = (props, args) => createMenu(props, args || state.currentFile); @@ -829,11 +876,11 @@ const createWindow = (core, proc) => { const onMenuToggleMinimalistic = () => wired.toggleMinimalistic(); const onMenuShowDate = () => setSetting('showDate', !proc.settings.showDate); const onMenuShowHidden = () => setSetting('showHiddenFiles', !proc.settings.showHiddenFiles); - const onMenuRename = file => dialog('rename', vfs.action, file); - const onMenuDelete = file => dialog('delete', vfs.action, file); - const onMenuDownload = (...args) => vfs.download(...args); - const onMenuCopy = item => clipboard.set(item); - const onMenuCut = item => clipboard.cut(item); + const onMenuRename = files => dialog('rename', vfs.action, files); + const onMenuDelete = files => dialog('delete', vfs.action, files); + const onMenuDownload = (files) => vfs.download(files); + const onMenuCopy = items => clipboard.set(items); + const onMenuCut = items => clipboard.cut(items); const onMenuPaste = () => clipboard.paste(); return win From 4b677b97ecf49ee5f6d181a4bf4be8591d82a9e0 Mon Sep 17 00:00:00 2001 From: Aaron Meese Date: Wed, 10 Aug 2022 20:07:54 -0400 Subject: [PATCH 2/4] More accurate selection status messages --- index.js | 17 ++++++++++++----- locales.js | 49 ++++++++++++++++++++++++++++++++++++++++++------- 2 files changed, 54 insertions(+), 12 deletions(-) diff --git a/index.js b/index.js index 32f4398..435a92f 100644 --- a/index.js +++ b/index.js @@ -141,11 +141,18 @@ const formatStatusMessage = (core, files) => { return (path, files) => { const directoryCount = getDirectoryCount(files); - const fileCount = getFileCount(files); - const totalSize = getTotalSize(files); - - // TODO: Copy over new label messages with translation - return __('LBL_STATUS', directoryCount, fileCount, totalSize); + const fileCount = getFileCount(files); + const totalSize = getTotalSize(files); + const directoryCountMessage = `${directoryCount} ${__(directoryCount === 1 ? 'SINGLE_DIR' : 'MULTI_DIR')}`; + const fileCountMessage = `${fileCount} ${__(fileCount === 1 ? 'SINGLE_FILE' : 'MULTI_FILE')}`; + + if (directoryCount > 0 && fileCount > 0) { + return __('LBL_DIR_AND_FILE_STATUS', directoryCountMessage, fileCountMessage, totalSize); + } else if (directoryCount > 0) { + return __('LBL_DIR_OR_FILE_STATUS', directoryCountMessage, totalSize); + } else { + return __('LBL_DIR_OR_FILE_STATUS', fileCountMessage, totalSize); + } }; }; diff --git a/locales.js b/locales.js index 5a92aa1..741cae7 100644 --- a/locales.js +++ b/locales.js @@ -3,7 +3,12 @@ export const en_EN = { LBL_MINIMALISTIC: 'Minimalistic', LBL_OPEN_WITH: 'Open with...', LBL_SHOW_DATE: 'Show date column', - LBL_STATUS: '{0} directories, {1} files, {2} bytes total', + LBL_DIR_AND_FILE_STATUS: '{0}, {1}, {2} bytes total', + LBL_DIR_OR_FILE_STATUS: '{0}, {1} bytes total', + SINGLE_DIR: 'directory', + MULTI_DIR: 'directories', + SINGLE_FILE: 'file', + MULTI_FILE: 'files', LBL_DATE: 'Date', // FIXME: Move to client LBL_LOADING: 'Loading {0}', DIALOG_MKDIR_MESSAGE: 'Create new directory', @@ -25,7 +30,12 @@ export const sv_SE = { LBL_MINIMALISTIC: 'Minimalistic', LBL_OPEN_WITH: 'Öppna med...', LBL_SHOW_DATE: 'Visa datumkolumn', - LBL_STATUS: '{0} kataloger, {1} filer, {2} byte totalt', + LBL_DIR_AND_FILE_STATUS: '{0}, {1}, {2} byte totalt', + LBL_DIR_OR_FILE_STATUS: '{0}, {1} byte totalt', + SINGLE_DIR: 'katalog', + MULTI_DIR: 'kataloger', + SINGLE_FILE: 'fil', + MULTI_FILE: 'filer', LBL_DATE: 'Datum', // FIXME: Move to client LBL_LOADING: 'Laddar {0}', DIALOG_MKDIR_MESSAGE: 'Skapa ny katalog', @@ -46,7 +56,12 @@ export const nb_NO = { LBL_MINIMALISTIC: 'Minimalistisk', LBL_OPEN_WITH: 'Åpne med...', LBL_SHOW_DATE: 'Vis dato kolonne', - LBL_STATUS: '{0} mapper, {1} filer, {2} bytes totalt', + LBL_DIR_AND_FILE_STATUS: '{0}, {1}, {2} bytes totalt', + LBL_DIR_OR_FILE_STATUS: '{0}, {1} bytes totalt', + SINGLE_DIR: 'mappe', + MULTI_DIR: 'mapper', + SINGLE_FILE: 'fil', + MULTI_FILE: 'filer', LBL_DATE: 'Dato', LBL_LOADING: 'Laster {0}', DIALOG_MKDIR_MESSAGE: 'Lag ny mappe', @@ -67,7 +82,12 @@ export const vi_VN = { LBL_MINIMALISTIC: 'Tối giản', LBL_OPEN_WITH: 'Mở bằng...', LBL_SHOW_DATE: 'Hiện cột thời gian', - LBL_STATUS: '{0} thư mục, {1} tập tin, tổng dung lượng {2} bytes', + LBL_DIR_AND_FILE_STATUS: '{0}, {1}, tổng dung lượng {2} bytes', + LBL_DIR_OR_FILE_STATUS: '{0}, tổng dung lượng {1} bytes', + SINGLE_DIR: 'thư mục', + MULTI_DIR: 'thư mục', + SINGLE_FILE: 'tập tin', + MULTI_FILE: 'các tập tin', LBL_DATE: 'Thời gian', LBL_LOADING: 'Đang tải {0}', DIALOG_MKDIR_MESSAGE: 'Tạo thư mục mới', @@ -88,7 +108,12 @@ export const pt_BR = { LBL_MINIMALISTIC: 'Minimalista', LBL_OPEN_WITH: 'Abrir com...', LBL_SHOW_DATE: 'Mostrar coluna Data', - LBL_STATUS: '{0} diretórios, {1} arquivos, {2} bytes no total', + LBL_DIR_AND_FILE_STATUS: '{0}, {1}, {2} bytes no total', + LBL_DIR_OR_FILE_STATUS: '{0}, {1} bytes no total', + SINGLE_DIR: 'diretório', + MULTI_DIR: 'diretórios', + SINGLE_FILE: 'arquivo', + MULTI_FILE: 'arquivos', LBL_DATE: 'Data', // FIXME: Move to client LBL_LOADING: 'Carregando {0}', DIALOG_MKDIR_MESSAGE: 'Criar novo diretório', @@ -109,7 +134,12 @@ export const fr_FR = { LBL_MINIMALISTIC: 'Minimaliste', LBL_OPEN_WITH: 'Ouvrir avec...', LBL_SHOW_DATE: 'Affichier la colonne date', - LBL_STATUS: '{0} dossiers, {1} fichiers, {2} bytes au total', + LBL_DIR_AND_FILE_STATUS: '{0}, {1}, {2} bytes au total', + LBL_DIR_OR_FILE_STATUS: '{0}, {1} bytes au total', + SINGLE_DIR: 'dossier', + MULTI_DIR: 'dossiers', + SINGLE_FILE: 'dossier', + MULTI_FILE: 'des dossiers', LBL_DATE: 'Date', // FIXME: Move to client LBL_LOADING: 'Chargement en cours {0}', DIALOG_MKDIR_MESSAGE: 'Créer nouveau dossier', @@ -130,7 +160,12 @@ export const tr_TR = { LBL_MINIMALISTIC: 'Minimalist', LBL_OPEN_WITH: 'Şununla aç:', LBL_SHOW_DATE: 'Tarih sütununu göster', - LBL_STATUS: 'toplamda {0} dizin, {1} dosya, {2} byte var', + LBL_DIR_AND_FILE_STATUS: 'toplamda {0}, {1}, {2} byte var', + LBL_DIR_OR_FILE_STATUS: 'toplamda {0}, {1} byte var', + SINGLE_DIR: 'dizin', + MULTI_DIR: 'dizinler', + SINGLE_FILE: 'dosya', + MULTI_FILE: 'dosyalar', LBL_DATE: 'Tarih', // FIXME: Move to client LBL_LOADING: 'Yükleniyor {0}', DIALOG_MKDIR_MESSAGE: 'Yeni dizin oluştur', From 7b2b4dfba510e67da1fc9296e753f4932496c524 Mon Sep 17 00:00:00 2001 From: Aaron Meese Date: Wed, 10 Aug 2022 20:10:33 -0400 Subject: [PATCH 3/4] Resolved eslint errors --- index.js | 50 +++++++++++++++++++++++++------------------------- 1 file changed, 25 insertions(+), 25 deletions(-) diff --git a/index.js b/index.js index 435a92f..091df5f 100644 --- a/index.js +++ b/index.js @@ -126,11 +126,11 @@ const createInitialPaths = (core, proc) => { }; const getDirectoryCount = files => - files.filter(file => file.isDirectory).length; + files.filter(file => file.isDirectory).length; const getFileCount = files => - files.filter(file => !file.isDirectory).length; + files.filter(file => !file.isDirectory).length; const getTotalSize = files => - files.reduce((total, file) => total + (file.size || 0), 0); + files.reduce((total, file) => total + (file.size || 0), 0); /** * Formats directory status message @@ -547,17 +547,17 @@ const menuFactory = (core, proc, win) => { const item = items[items.length - 1]; if (items.length === 1 && item && isSpecialFile(item.filename)) { - return [{ + return [{ label: _('LBL_GO'), onclick: () => emitter('filemanager:navigate'), - }]; - } + }]; + } const canDownload = items.some( - item => !item.isDirectory && !isSpecialFile(item.filename) - ); - const hasValidFile = items.some(item => !isSpecialFile(item.filename)); - const isDirectory = items.length === 1 && item.isDirectory; + item => !item.isDirectory && !isSpecialFile(item.filename) + ); + const hasValidFile = items.some(item => !isSpecialFile(item.filename)); + const isDirectory = items.length === 1 && item.isDirectory; const openMenu = isDirectory ? [{ label: _('LBL_GO'), @@ -740,7 +740,7 @@ const createApplication = (core, proc) => { fileview: listView.state({ columns: [], multiselect: true, - previousSelectedIndex: 0 + previousSelectedIndex: 0 }) }; @@ -807,9 +807,9 @@ const createApplication = (core, proc) => { fileview: listView.actions({ select: ({data}) => win.emit('filemanager:select', data), activate: ({data}) => - data.forEach(item => - win.emit(`filemanager:${item.isFile ? 'open' : 'navigate'}`, item) - ), + data.forEach(item => + win.emit(`filemanager:${item.isFile ? 'open' : 'navigate'}`, item) + ), contextmenu: args => win.emit('filemanager:contextmenu', args), created: ({el, data}) => { if (data.isFile) { @@ -856,23 +856,23 @@ const createWindow = (core, proc) => { const onReaddirRender = args => wired.setList(args); const onRefresh = (...args) => vfs.refresh(...args); const onOpen = files => { - if (!Array.isArray(files)) { + if (!Array.isArray(files)) { files = [files]; } - return files.forEach( - file => core.open(file, {useDefault: true}) - ); - }; - const onOpenWith = files => { - if (!Array.isArray(files)) { + return files.forEach( + file => core.open(file, {useDefault: true}) + ); + }; + const onOpenWith = files => { + if (!Array.isArray(files)) { files = [files]; } - return files.forEach( - file => core.open(file, {useDefault: true, forceDialog: true}) - ); - }; + return files.forEach( + file => core.open(file, {useDefault: true, forceDialog: true}) + ); + }; const onHistoryPush = file => wired.history.push(file); const onHistoryClear = () => wired.history.clear(); const onMenu = (props, args) => createMenu(props, args || state.currentFile); From 8df52d07ddc4c35328c7f9ef46d712b9a130085f Mon Sep 17 00:00:00 2001 From: Aaron Meese Date: Wed, 10 Aug 2022 20:16:49 -0400 Subject: [PATCH 4/4] Improved dialog messages --- index.js | 4 ++-- locales.js | 26 +++++++++++++------------- 2 files changed, 15 insertions(+), 15 deletions(-) diff --git a/index.js b/index.js index 091df5f..760662d 100644 --- a/index.js +++ b/index.js @@ -370,7 +370,7 @@ const vfsActionFactory = (core, proc, win, dialog, state) => { .catch(error => dialog('error', error, __('MSG_UPLOAD_ERROR'))); }); - const paste = (move, currentPath) => ({item, callback}) => { + const paste = (move, currentPath) => ({items, callback}) => { const promises = items.map(item => { const dest = { path: pathJoin(currentPath.path, item.filename) @@ -468,7 +468,7 @@ const dialogFactory = (core, proc, win) => { }))); const deleteDialog = (action, files) => dialog('confirm', { - message: __('DIALOG_DELETE_MESSAGE', file.filename), + message: __('DIALOG_DELETE_MESSAGE', files.length), }, usingPositiveButton(() => { action( () => Promise.all( diff --git a/locales.js b/locales.js index 741cae7..7070914 100644 --- a/locales.js +++ b/locales.js @@ -13,8 +13,8 @@ export const en_EN = { LBL_LOADING: 'Loading {0}', DIALOG_MKDIR_MESSAGE: 'Create new directory', DIALOG_MKDIR_PLACEHOLDER: 'New directory', - DIALOG_RENAME_MESSAGE: 'Rename {0} ?', - DIALOG_DELETE_MESSAGE: 'Delete {0} ?', + DIALOG_RENAME_MESSAGE: 'Rename {0}?', + DIALOG_DELETE_MESSAGE: 'Delete {0} file(s)?', DIALOG_PROGRESS_MESSAGE: 'Uploading {0}...', MSG_ERROR: 'An error occurred', MSG_UPLOAD_ERROR: 'Failed to upload file(s)', @@ -40,8 +40,8 @@ export const sv_SE = { LBL_LOADING: 'Laddar {0}', DIALOG_MKDIR_MESSAGE: 'Skapa ny katalog', DIALOG_MKDIR_PLACEHOLDER: 'Ny katalog', - DIALOG_RENAME_MESSAGE: 'Döp om {0} ?', - DIALOG_DELETE_MESSAGE: 'Radera {0} ?', + DIALOG_RENAME_MESSAGE: 'Döp om {0}?', + DIALOG_DELETE_MESSAGE: 'Radera {0} fil(er)?', MSG_ERROR: 'Ett fel uppstod', MSG_UPLOAD_ERROR: 'Det gick inte att ladda upp filer(na)', MSG_READDIR_ERROR: 'Ett fel uppstod när katalogen lästes: {0}', @@ -66,8 +66,8 @@ export const nb_NO = { LBL_LOADING: 'Laster {0}', DIALOG_MKDIR_MESSAGE: 'Lag ny mappe', DIALOG_MKDIR_PLACEHOLDER: 'Ny mappe', - DIALOG_RENAME_MESSAGE: 'Omdøpe {0} ?', - DIALOG_DELETE_MESSAGE: 'Slette {0} ?', + DIALOG_RENAME_MESSAGE: 'Omdøpe {0}?', + DIALOG_DELETE_MESSAGE: 'Slette {0} fil(er)?', MSG_ERROR: 'En feil oppstod', MSG_UPLOAD_ERROR: 'Feil under opplasting av fil(er)', MSG_READDIR_ERROR: 'En feil oppstod under lesing av mappe: {0}', @@ -92,8 +92,8 @@ export const vi_VN = { LBL_LOADING: 'Đang tải {0}', DIALOG_MKDIR_MESSAGE: 'Tạo thư mục mới', DIALOG_MKDIR_PLACEHOLDER: 'Thư mục mới', - DIALOG_RENAME_MESSAGE: 'Đổi tên {0} ?', - DIALOG_DELETE_MESSAGE: 'Xoá {0} ?', + DIALOG_RENAME_MESSAGE: 'Đổi tên {0}?', + DIALOG_DELETE_MESSAGE: 'Xoá {0} (các) tập tin?', MSG_ERROR: 'Đã xảy ra lỗi', MSG_UPLOAD_ERROR: 'Không thể tải lên tập tin', MSG_READDIR_ERROR: 'Đã xảy ra lỗi trong khi đọc thư mục: {0}', @@ -118,8 +118,8 @@ export const pt_BR = { LBL_LOADING: 'Carregando {0}', DIALOG_MKDIR_MESSAGE: 'Criar novo diretório', DIALOG_MKDIR_PLACEHOLDER: 'Novo diretório', - DIALOG_RENAME_MESSAGE: 'Renomear {0} ?', - DIALOG_DELETE_MESSAGE: 'Deletar {0} ?', + DIALOG_RENAME_MESSAGE: 'Renomear {0}?', + DIALOG_DELETE_MESSAGE: 'Deletar {0} arquivo(s)?', MSG_ERROR: 'Um erro ocorreu', MSG_UPLOAD_ERROR: 'Falha ao fazer upload do(s) arquivo(s)', MSG_READDIR_ERROR: 'Um erro ocorreu ao ler o diretório: {0}', @@ -144,8 +144,8 @@ export const fr_FR = { LBL_LOADING: 'Chargement en cours {0}', DIALOG_MKDIR_MESSAGE: 'Créer nouveau dossier', DIALOG_MKDIR_PLACEHOLDER: 'Nouveau dossier', - DIALOG_RENAME_MESSAGE: 'Renommer {0} ?', - DIALOG_DELETE_MESSAGE: 'Supprimer {0} ?', + DIALOG_RENAME_MESSAGE: 'Renommer {0}?', + DIALOG_DELETE_MESSAGE: 'Supprimer {0} (des) dossiers?', MSG_ERROR: 'Une erreur est survenue', MSG_UPLOAD_ERROR: 'Echec du chargement du(des) fichier(s)', MSG_READDIR_ERROR: 'Une erreur est survenue lors de la lecture du répertoire : {0}', @@ -171,7 +171,7 @@ export const tr_TR = { DIALOG_MKDIR_MESSAGE: 'Yeni dizin oluştur', DIALOG_MKDIR_PLACEHOLDER: 'Yeni dizin', DIALOG_RENAME_MESSAGE: '{0} ismi değişsin mi?', - DIALOG_DELETE_MESSAGE: '{0} silinsin mi?', + DIALOG_DELETE_MESSAGE: '{0} dosya(lar) silinsin mi?', MSG_ERROR: 'Bir hata oldu', MSG_UPLOAD_ERROR: 'Dosya(lar)ın yüklenmesi işlemi başarısız', MSG_READDIR_ERROR: 'Belirtilen dizin okunurken bir hata oluştu: {0}',