diff --git a/i18n/translation-de.json b/i18n/translation-de.json index 679d88ced..418e56f4a 100644 --- a/i18n/translation-de.json +++ b/i18n/translation-de.json @@ -72,7 +72,7 @@ "markAllRead": "Als Gelesen markieren", "insertPage": "Seite einfügen", "insertBlankPageAbove": "Leere Seite oben einfügen", - "insertBlankPageBelow": "Leere Seite unten einfügen page", + "insertBlankPageBelow": "Leere Seite unten einfügen", "pageManipulation": "Seitenmanipulation", "replace": "Ersetzen", "setDestination": "Festgelegtes Ziel", @@ -88,9 +88,9 @@ "redactPages": "Seiten schwärzen", "playAudio": "Audio abspielen", "pauseAudio": "Audiopause", - "selectAll": "Wählen Sie Alle", + "selectAll": "Alle auswählen", "unselect": "Auswahl aufheben", - "addMark": "Markus hinzufügen", + "addMark": "Markieren", "viewFile": "Datei ansehen", "multiReplyAnnotations": "Auf ausgewählte Anmerkungen antworten ({{count}})", "comparePages": "Seiten vergleichen", @@ -317,8 +317,8 @@ "toolbarGroup-Measure": "Messen", "toolbarGroup-Edit": "Bearbeiten", "toolbarGroup-EditText": "Text bearbeiten", - "toolbarGroup-FillAndSign": "Füllen und unterschreiben", - "toolbarGroup-Forms": "Formen", + "toolbarGroup-FillAndSign": "Formular", + "toolbarGroup-Forms": "Zeichnen", "toolbarGroup-Redact": "Schwärzen" }, "annotationColor": { @@ -584,7 +584,7 @@ "backgroundColor": "Hintergrundfarbe" }, "pageRedactModal": { - "addMark": "Markus hinzufügen", + "addMark": "Markieren", "pageSelection": "Seitenauswahl", "current": "Aktuelle Seite", "specify": "Seiten angeben", @@ -599,18 +599,18 @@ "settings": "Einstellungen", "general": "Allgemein", "keyboardShortcut": "Tastaturkürzel", - "advancedSetting": "Erweiterte Einstellung", + "advancedSetting": "Erweitert", "language": "Sprache", "theme": "Thema", - "darkMode": "Dunkler Modus", - "lightMode": "Lichtmodus", + "darkMode": "Dark-Mode", + "lightMode": "Light-Mode", "viewing": "Anzeigen", - "disableFadePageNavigationComponent": "Deaktivieren Sie die Seitennavigationskomponente ausblenden", + "disableFadePageNavigationComponent": "Seitennavigationskomponente nicht automatisch ausblenden", "disableFadePageNavigationComponentDesc": "Lassen Sie die Seitennavigationskomponente immer auf dem Bildschirm. Das Standardverhalten besteht darin, es nach einer bestimmten Zeit der Inaktivität auszublenden.", "disableNativeScrolling": "Natives Scrollen deaktivieren", "disableNativeScrollingDesc": "Deaktivieren Sie das native Scrollverhalten mobiler Geräte, wenn es zuvor aktiviert wurde. Beachten Sie, dass das native Scrollverhalten mobiler Geräte standardmäßig deaktiviert ist.", "annotations": "Anmerkungen", - "disableToolDefaultStyleUpdateFromAnnotationPopup": "Deaktivieren Sie die Aktualisierung des Werkzeug-Standardstils aus dem Anmerkungs-Popup", + "disableToolDefaultStyleUpdateFromAnnotationPopup": "Aktualisierung des Werkzeug-Standardstils aus dem Anmerkungs-Popup deaktivieren", "disableToolDefaultStyleUpdateFromAnnotationPopupDesc": "Deaktiviert die Synchronisierung von Anmerkungsstilaktualisierungen mit dem zugeordneten Werkzeug, das die Anmerkung erstellt hat. Wenn also der Stil einer Anmerkung geändert wird, werden die Standardstile des Werkzeugs nicht aktualisiert.", "notesPanel": "Notizenbereich", "disableNoteSubmissionWithEnter": "Deaktivieren Sie das Senden von Notizen mit der Eingabetaste", @@ -962,9 +962,9 @@ }, "redactionPanel": { "noMarkedRedactions": "Beginnen Sie mit dem Schwärzen, indem Sie Text, Regionen, Seiten markieren oder eine Suche durchführen.", - "redactionSearchPlaceholder": "Hinzufügen nach Schlüsselwortsuche oder Mustern", + "redactionSearchPlaceholder": "Schlüsselwortsuche oder Muster", "redactionCounter": "Zur Schwärzung markiert", - "clearMarked": "Klar", + "clearMarked": "Abbrechen", "redactAllMarked": "Alle schwärzen", "redactionItem": { "regionRedaction": "Regionsredaktion", diff --git a/src/apis/index.js b/src/apis/index.js index eb90dd03e..24e2513af 100644 --- a/src/apis/index.js +++ b/src/apis/index.js @@ -10,6 +10,7 @@ import Theme from 'constants/theme'; import RedactionSearchPatterns from 'constants/redactionSearchPatterns'; import { languageEnum } from 'constants/languages'; import addSearchListener from './addSearchListener'; +import setSaveAsHandler from './setSaveAsHandler'; import addSortStrategy from './addSortStrategy'; import annotationPopup from './annotationPopup'; import closeDocument from './closeDocument'; @@ -278,6 +279,7 @@ export default (store) => { Theme, RedactionSearchPatterns, addSearchListener, + setSaveAsHandler, addSortStrategy: addSortStrategy(store), annotationPopup: annotationPopup(store), closeDocument: closeDocument(store), diff --git a/src/apis/setSaveAsHandler.js b/src/apis/setSaveAsHandler.js new file mode 100644 index 000000000..b4172a667 --- /dev/null +++ b/src/apis/setSaveAsHandler.js @@ -0,0 +1,26 @@ +/** + * Set save as handler that will be triggered in case of a save action instead of the default method. + * @method UI.setSaveAsHandler + * @param {UI.saveAsHandler} saveAsHandler Callback function that will be triggered when download started + * @example +WebViewer(...) + .then(function(instance) { + function onDownload(data, filename) { + console.log(filename); + }; + + instance.UI.setSaveAsHandler(onDownload); + }); + */ +/** + * Callback that gets passed to {@link UI.setSaveAsHandler setSaveAsHandler}. + * @callback UI.saveAsHandler + * @param {Blob|File} data data + * @param {string} filename filename + */ + +import { setSaveAsHandler as saveAsHandlerHelper } from 'helpers/saveAs'; + +export default function setSaveAsHandler(handler) { + saveAsHandlerHelper(handler); +} diff --git a/src/components/FileAttachmentPanel/FileAttachmentPanel.js b/src/components/FileAttachmentPanel/FileAttachmentPanel.js index be7d1afbd..17f528d71 100644 --- a/src/components/FileAttachmentPanel/FileAttachmentPanel.js +++ b/src/components/FileAttachmentPanel/FileAttachmentPanel.js @@ -2,6 +2,7 @@ import React, { useState, useEffect } from 'react'; import { useTranslation } from 'react-i18next'; import { getFileAttachments } from 'helpers/getFileAttachments'; import { saveAs } from 'file-saver'; +import { getSaveAsHandler } from 'helpers/saveAs'; import Icon from 'components/Icon'; import core from 'core'; import './FileAttachmentPanel.scss'; @@ -53,7 +54,12 @@ const FileAttachmentPanel = () => { {fileAttachments.embeddedFiles.map((file, idx) => renderAttachment( file.filename, () => { - saveAs(file.blob, file.filename); + if (getSaveAsHandler() !== null) { + const handler = getSaveAsHandler(); + handler(file.blob, file.filename); + } else { + saveAs(file.blob, file.filename); + } }, `embeddedFile_${idx}`, ), diff --git a/src/components/ReplyAttachmentList/ReplyAttachmentList.js b/src/components/ReplyAttachmentList/ReplyAttachmentList.js index f98b529f7..d3dc8c12d 100644 --- a/src/components/ReplyAttachmentList/ReplyAttachmentList.js +++ b/src/components/ReplyAttachmentList/ReplyAttachmentList.js @@ -2,6 +2,7 @@ import React, { useState, useEffect } from 'react'; import { useSelector } from 'react-redux'; import selectors from 'selectors'; import { saveAs } from 'file-saver'; +import { getSaveAsHandler } from 'helpers/saveAs'; import Button from 'components/Button'; import Icon from 'components/Icon'; import Tooltip from 'components/Tooltip'; @@ -67,7 +68,12 @@ const ReplyAttachmentList = ({ files, isEditing, fileDeleted }) => { e.stopPropagation(); const fileData = file.url ? file.url : await decompressFileContent(file); - saveAs(fileData, file.name); + if (getSaveAsHandler() !== null) { + const handler = getSaveAsHandler(); + handler(fileData, file.name); + } else { + saveAs(fileData, file.name); + } }; return ( diff --git a/src/event-listeners/onFileAttachmentDataAvailable.js b/src/event-listeners/onFileAttachmentDataAvailable.js index 188366f36..373886e5f 100644 --- a/src/event-listeners/onFileAttachmentDataAvailable.js +++ b/src/event-listeners/onFileAttachmentDataAvailable.js @@ -1,6 +1,12 @@ import { saveAs } from 'file-saver'; +import { getSaveAsHandler } from 'helpers/saveAs'; export default () => (fileMeta) => { const { fileData, fileName } = fileMeta; - saveAs(fileData, fileName); + if (getSaveAsHandler() !== null) { + const handler = getSaveAsHandler(); + handler(fileData, fileName); + } else { + saveAs(fileData, fileName); + } }; diff --git a/src/helpers/downloadPdf.js b/src/helpers/downloadPdf.js index 2b0346946..858c1419f 100644 --- a/src/helpers/downloadPdf.js +++ b/src/helpers/downloadPdf.js @@ -1,4 +1,5 @@ import { saveAs } from 'file-saver'; +import { getSaveAsHandler } from 'helpers/saveAs'; import core from 'core'; import { isIE } from 'helpers/device'; import fireEvent from 'helpers/fireEvent'; @@ -238,7 +239,12 @@ export default async (dispatch, options = {}, documentViewerKey = 1) => { } else { file = new File([arr], downloadName, { type: downloadType }); } - saveAs(file, downloadName); + if (getSaveAsHandler() !== null) { + const handler = getSaveAsHandler(); + handler(file, downloadName); + } else { + saveAs(file, downloadName); + } dispatch(actions.closeElement('loadingModal')); fireEvent(Events.FINISHED_SAVING_PDF); fireEvent(Events.FILE_DOWNLOADED); diff --git a/src/helpers/pageManipulationFunctions.js b/src/helpers/pageManipulationFunctions.js index d716796ab..42fb5774c 100644 --- a/src/helpers/pageManipulationFunctions.js +++ b/src/helpers/pageManipulationFunctions.js @@ -1,6 +1,7 @@ import extractPagesWithAnnotations from 'helpers/extractPagesWithAnnotations'; import core from 'core'; import { saveAs } from 'file-saver'; +import { getSaveAsHandler } from 'helpers/saveAs'; import actions from 'actions'; import i18next from 'i18next'; import { workerTypes } from 'constants/types'; @@ -78,12 +79,22 @@ const extractPages = (pageNumbers, dispatch) => { title, confirmBtnText, onConfirm: () => extractPagesWithAnnotations(pageNumbers).then((file) => { - saveAs(file, 'extractedDocument.pdf'); + if (getSaveAsHandler() !== null) { + const handler = getSaveAsHandler(); + handler(file, 'extractedDocument.pdf'); + } else { + saveAs(file, 'extractedDocument.pdf'); + } }), secondaryBtnText, onSecondary: () => { extractPagesWithAnnotations(pageNumbers).then((file) => { - saveAs(file, 'extractedDocument.pdf'); + if (getSaveAsHandler() !== null) { + const handler = getSaveAsHandler(); + handler(file, 'extractedDocument.pdf'); + } else { + saveAs(file, 'extractedDocument.pdf'); + } core.removePages(pageNumbers).then(() => { dispatch(actions.setSelectedPageThumbnails([])); }); diff --git a/src/helpers/saveAs.js b/src/helpers/saveAs.js new file mode 100644 index 000000000..61683aa16 --- /dev/null +++ b/src/helpers/saveAs.js @@ -0,0 +1,13 @@ +let saveAsHandler = null; + +export function setSaveAsHandler(handler) { + saveAsHandler = handler; +} + +export function clearSaveAsHandler() { + saveAsHandler = null; +} + +export function getSaveAsHandler() { + return saveAsHandler; +} \ No newline at end of file diff --git a/src/redux/actions/internalActions.js b/src/redux/actions/internalActions.js index 7db86b18d..3286e6411 100644 --- a/src/redux/actions/internalActions.js +++ b/src/redux/actions/internalActions.js @@ -493,6 +493,10 @@ export const removeSearchListener = (func) => ({ type: 'REMOVE_SEARCH_LISTENER', payload: { func }, }); +export const setSaveAsHandler = (func) => ({ + type: 'ADD_SAVE_AS_HANDLER', + payload: { func }, +}); export const setSearchValue = (value) => ({ type: 'SET_SEARCH_VALUE', payload: { value },