You've already forked joplin
mirror of
https://github.com/laurent22/joplin.git
synced 2025-12-08 23:07:32 +02:00
Desktop: Add friendly default filenames to export options (#2749)
* Add friendly default filenames to export options * remove extension from safefilename call * Load parent folder for all exports * convert foldername and filename to friendly versions separatly * Add null guards to the filename export
This commit is contained in:
@@ -2,6 +2,9 @@ const { _ } = require('lib/locale');
|
|||||||
const { bridge } = require('electron').remote.require('./bridge');
|
const { bridge } = require('electron').remote.require('./bridge');
|
||||||
const InteropService = require('lib/services/InteropService');
|
const InteropService = require('lib/services/InteropService');
|
||||||
const Setting = require('lib/models/Setting');
|
const Setting = require('lib/models/Setting');
|
||||||
|
const Note = require('lib/models/Note.js');
|
||||||
|
const Folder = require('lib/models/Folder.js');
|
||||||
|
const { friendlySafeFilename } = require('lib/path-utils');
|
||||||
const md5 = require('md5');
|
const md5 = require('md5');
|
||||||
const url = require('url');
|
const url = require('url');
|
||||||
const { shim } = require('lib/shim');
|
const { shim } = require('lib/shim');
|
||||||
@@ -92,6 +95,29 @@ class InteropServiceHelper {
|
|||||||
return this.exportNoteTo_('printer', noteId, options);
|
return this.exportNoteTo_('printer', noteId, options);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static async defaultFilename(noteIds, fileExtension) {
|
||||||
|
const note = await Note.load(noteIds[0]);
|
||||||
|
// In a rare case the passed not will be null, use the id for filename
|
||||||
|
if (note === null) {
|
||||||
|
const filename = friendlySafeFilename(noteIds[0], 100);
|
||||||
|
|
||||||
|
return `${filename}.${fileExtension}`;
|
||||||
|
}
|
||||||
|
const folder = await Folder.load(note.parent_id);
|
||||||
|
|
||||||
|
const filename = friendlySafeFilename(note.title, 100);
|
||||||
|
|
||||||
|
// In a less rare case the folder will be null, just ignore it
|
||||||
|
if (folder === null) {
|
||||||
|
return `${filename}.${fileExtension}`;
|
||||||
|
}
|
||||||
|
|
||||||
|
const foldername = friendlySafeFilename(folder.title, 100);
|
||||||
|
|
||||||
|
// friendlySafeFilename assumes that the file extension is added after
|
||||||
|
return `${foldername} - ${filename}.${fileExtension}`;
|
||||||
|
}
|
||||||
|
|
||||||
static async export(dispatch, module, options = null) {
|
static async export(dispatch, module, options = null) {
|
||||||
if (!options) options = {};
|
if (!options) options = {};
|
||||||
|
|
||||||
@@ -100,6 +126,7 @@ class InteropServiceHelper {
|
|||||||
if (module.target === 'file') {
|
if (module.target === 'file') {
|
||||||
path = bridge().showSaveDialog({
|
path = bridge().showSaveDialog({
|
||||||
filters: [{ name: module.description, extensions: module.fileExtensions }],
|
filters: [{ name: module.description, extensions: module.fileExtensions }],
|
||||||
|
defaultPath: await this.defaultFilename(options.sourceNoteIds, module.fileExtensions[0]),
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
path = bridge().showOpenDialog({
|
path = bridge().showOpenDialog({
|
||||||
|
|||||||
@@ -34,7 +34,7 @@ const NoteSearchBar = require('./NoteSearchBar.min.js');
|
|||||||
const markdownUtils = require('lib/markdownUtils');
|
const markdownUtils = require('lib/markdownUtils');
|
||||||
const ExternalEditWatcher = require('lib/services/ExternalEditWatcher');
|
const ExternalEditWatcher = require('lib/services/ExternalEditWatcher');
|
||||||
const ResourceFetcher = require('lib/services/ResourceFetcher');
|
const ResourceFetcher = require('lib/services/ResourceFetcher');
|
||||||
const { toSystemSlashes, safeFilename } = require('lib/path-utils');
|
const { toSystemSlashes } = require('lib/path-utils');
|
||||||
const { clipboard } = require('electron');
|
const { clipboard } = require('electron');
|
||||||
const SearchEngine = require('lib/services/SearchEngine');
|
const SearchEngine = require('lib/services/SearchEngine');
|
||||||
const NoteTextViewer = require('./NoteTextViewer.min');
|
const NoteTextViewer = require('./NoteTextViewer.min');
|
||||||
@@ -1303,10 +1303,6 @@ class NoteTextComponent extends React.Component {
|
|||||||
this.isPrinting_ = false;
|
this.isPrinting_ = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
pdfFileName_(note, folder) {
|
|
||||||
return safeFilename(`${note.title} - ${folder.title}.pdf`, 255, true);
|
|
||||||
}
|
|
||||||
|
|
||||||
async commandSavePdf(args) {
|
async commandSavePdf(args) {
|
||||||
try {
|
try {
|
||||||
if (!this.state.note && !args.noteIds) throw new Error('No notes selected for pdf export');
|
if (!this.state.note && !args.noteIds) throw new Error('No notes selected for pdf export');
|
||||||
@@ -1315,12 +1311,9 @@ class NoteTextComponent extends React.Component {
|
|||||||
|
|
||||||
let path = null;
|
let path = null;
|
||||||
if (noteIds.length === 1) {
|
if (noteIds.length === 1) {
|
||||||
const note = await Note.load(noteIds[0]);
|
|
||||||
const folder = Folder.byId(this.props.folders, note.parent_id);
|
|
||||||
|
|
||||||
path = bridge().showSaveDialog({
|
path = bridge().showSaveDialog({
|
||||||
filters: [{ name: _('PDF File'), extensions: ['pdf'] }],
|
filters: [{ name: _('PDF File'), extensions: ['pdf'] }],
|
||||||
defaultPath: this.pdfFileName_(note, folder),
|
defaultPath: await InteropServiceHelper.defaultFilename(noteIds, 'pdf'),
|
||||||
});
|
});
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
|
|||||||
Reference in New Issue
Block a user