Skip to content

Commit

Permalink
Add a context menu to save item with selection as note
Browse files Browse the repository at this point in the history
Addresses zotero#166. Safari does not get this yet, because improved
Safari popover menus are blocked by PR zotero#193.
  • Loading branch information
adomasven committed Apr 5, 2018
1 parent 9cef1a8 commit e26abdf
Show file tree
Hide file tree
Showing 4 changed files with 81 additions and 27 deletions.
32 changes: 27 additions & 5 deletions src/browserExt/background.js
Expand Up @@ -451,6 +451,9 @@ Zotero.Connector_Browser = new function() {
if (translators && translators.length) {
_showTranslatorIcon(tab, translators[0]);
_showTranslatorContextMenuItem(translators, saveMenuID);
if (translators[0].itemType != "multiple") {
_showNoteContextMenuItems(saveMenuID);
}
} else if (isPDF) {
Zotero.Connector_Browser._showPDFIcon(tab);
} else {
Expand Down Expand Up @@ -604,6 +607,18 @@ Zotero.Connector_Browser = new function() {
}
}

function _showNoteContextMenuItems(parentID) {
browser.contextMenus.create({
id: "zotero-context-menu-translator-save-with-selection-note",
title: "Create Zotero Item and Note from Selection",
onclick: function (info, tab) {
Zotero.Connector_Browser.saveWithTranslator(tab, 0, {note: info.selectionText});
},
parentId: parentID,
contexts: ['selection']
});
}

function _showWebpageContextMenuItem(parentID) {
var fns = [];
fns.push(() => browser.contextMenus.create({
Expand Down Expand Up @@ -694,7 +709,7 @@ Zotero.Connector_Browser = new function() {
});
}
else if(_tabInfo[tab.id] && _tabInfo[tab.id].translators && _tabInfo[tab.id].translators.length) {
Zotero.Connector_Browser.saveWithTranslator(tab, 0, true);
Zotero.Connector_Browser.saveWithTranslator(tab, 0, {fallbackOnFailure: true});
} else {
if (_tabInfo[tab.id] && _tabInfo[tab.id].isPDF) {
Zotero.Connector_Browser.saveAsWebpage(tab, _tabInfo[tab.id].frameId, true);
Expand All @@ -705,8 +720,16 @@ Zotero.Connector_Browser = new function() {
}
}
}

this.saveWithTranslator = function(tab, i, fallbackOnFailure = false) {

/**
* @param tab <Tab>
* @param i <Integer> the index of translator to save with
* @param options <Object>
* - fallbackOnFailure <Boolean> if translation fails, attempt to save with lower priority translators
* - note <String> add string as a note to the saved item
* @returns {Promise<*>}
*/
this.saveWithTranslator = function(tab, i, options) {
var translator = _tabInfo[tab.id].translators[i];

// Set frameId to null - send message to all frames
Expand All @@ -716,8 +739,7 @@ Zotero.Connector_Browser = new function() {
[
_tabInfo[tab.id].instanceID,
translator.translatorID,
translator.itemType,
fallbackOnFailure
options
],
tab,
null
Expand Down
53 changes: 36 additions & 17 deletions src/common/inject/inject.jsx
Expand Up @@ -52,7 +52,7 @@ if (isTopWindow) {
*/
Zotero.Inject = new function() {
var _translate;
var _lastSessionDetails;
this.sessionDetails = {};
this.translators = [];

/**
Expand All @@ -65,6 +65,10 @@ Zotero.Inject = new function() {
} else if (document.location.href.substr(0, ZOTERO_CONFIG.OAUTH.ZOTERO.CALLBACK_URL.length+1) === ZOTERO_CONFIG.OAUTH.GOOGLE_DOCS.CALLBACK_URL+"#") {
Zotero.GoogleDocs_API.onAuthComplete(document.location.href);
}

const noteImgSrc = Zotero.isSafari
? safari.extension.baseURI+"images/treeitem-note.png"
: browser.extension.getURL('images/treeitem-note.png');

// wrap this in try/catch so that errors will reach logError
try {
Expand Down Expand Up @@ -139,6 +143,17 @@ Zotero.Inject = new function() {
]
);
}
if (item.notes) {
for (let note of item.notes) {
Zotero.Messaging.sendMessage('progressWindow.itemProgress', [
null,
noteImgSrc,
note.note,
item.id,
100
])
}
}
});
_translate.setHandler("attachmentProgress", function(obj, attachment, progress, err) {
if(progress === 0) return;
Expand Down Expand Up @@ -357,46 +372,50 @@ Zotero.Inject = new function() {
}
};

this.translate = async function(translatorID, itemType, fallbackOnFailure = false) {
this.translate = async function(translatorID, options={}) {
let result = await Zotero.Inject.checkActionToServer();
if (!result) return;
var translator = this.translators.find((t) => t.translatorID == translatorID);

// If the URL hasn't changed (from a history push) and the user triggered the same
// non-multiple translator as the last successful save, use the same session ID to reopen
// the popup.
if (_lastSessionDetails
&& document.location.href == _lastSessionDetails.url
&& translatorID == _lastSessionDetails.translatorID
&& itemType != 'multiple') {
let sessionID = _lastSessionDetails.id;
if (Zotero.Inject.sessionDetails.id
&& document.location.href == Zotero.Inject.sessionDetails.url
&& translatorID == Zotero.Inject.sessionDetails.translatorID
&& translator.itemType != 'multiple') {
let sessionID = Zotero.Inject.sessionDetails.id;
Zotero.Messaging.sendMessage("progressWindow.show", [sessionID]);
return;
}

var sessionID = Zotero.Utilities.randomString();
Zotero.Messaging.sendMessage("progressWindow.show", [sessionID]);

Zotero.Inject.sessionDetails = {saveOptions: options};

var translators = Array.from(this.translators);
while (translators[0].translatorID != translatorID) {
translators.shift();
}
while (true) {
var translator = translators.shift();
translator = translators.shift();
_translate.setTranslator(translator);
try {
let items = await _translate.translate({ sessionID });
Zotero.Messaging.sendMessage("progressWindow.done", [true]);
// Record details for the last successful save. We're storing the translator
// chosen by the user, regardless of whether there was a fallback to another
// translator.
_lastSessionDetails = {
Object.assign(Zotero.Inject.sessionDetails, {
id: sessionID,
url: document.location.href,
translatorID
};
});
return items;
} catch (e) {
if (fallbackOnFailure && translators.length) {
// Should we fallback if translator.itemType == "multiple"?
if (options.fallbackOnFailure && translators.length) {
Zotero.Messaging.sendMessage("progressWindow.error", ['fallback', translator.label, translators[0].label]);
} else {
Zotero.Messaging.sendMessage("progressWindow.done", [false]);
Expand All @@ -413,10 +432,10 @@ Zotero.Inject = new function() {
if (!result) return;

var translatorID = 'webpage' + (withSnapshot ? 'WithSnapshot' : '');
if (_lastSessionDetails
&& document.location.href == _lastSessionDetails.url
&& translatorID == _lastSessionDetails.translatorID) {
let sessionID = _lastSessionDetails.id;
if (Zotero.Inject.sessionDetails.id
&& document.location.href == Zotero.Inject.sessionDetails.url
&& translatorID == Zotero.Inject.sessionDetails.translatorID) {
let sessionID = Zotero.Inject.sessionDetails.id;
Zotero.Messaging.sendMessage("progressWindow.show", [sessionID]);
return;
}
Expand Down Expand Up @@ -461,11 +480,11 @@ Zotero.Inject = new function() {
]
);
Zotero.Messaging.sendMessage("progressWindow.done", [true]);
_lastSessionDetails = {
Object.assign(Zotero.Inject.sessionDetails, {
id: sessionID,
url: document.location.href,
translatorID
};
});
return result;
} catch (e) {
// Client unavailable
Expand Down
16 changes: 15 additions & 1 deletion src/common/translate_item.js
Expand Up @@ -90,7 +90,9 @@ Zotero.Translate.ItemSaver.prototype = {
* save progress. The callback will be called as attachmentCallback(attachment, false, error)
* on failure or attachmentCallback(attachment, progressPercent) periodically during saving.
*/
saveItems: function (items, attachmentCallback) {
saveItems: async function (items, attachmentCallback) {
items = await this._processItems(items);

// first try to save items via connector
var payload = {
items,
Expand Down Expand Up @@ -130,6 +132,18 @@ Zotero.Translate.ItemSaver.prototype = {
}.bind(this));
},

_processItems: function(items) {
var saveOptions = Zotero.Inject.sessionDetails.saveOptions;
if (saveOptions.note && items.length == 1) {
if (items[0].notes) {
items[0].notes.push({note: saveOptions.note})
} else {
items[0].notes = {note: saveOptions.note};
}
}
return items;
},

/**
* Polls for updates to attachment progress
* @param items Items in Zotero.Item.toArray() format
Expand Down
7 changes: 3 additions & 4 deletions src/safari/global.js
Expand Up @@ -112,7 +112,7 @@ Zotero.Connector_Browser = new function() {
var tab = safari.application.activeBrowserWindow.activeTab;
if (command === "zotero-button") {
if(tab.translators && tab.translators.length) {
Zotero.Connector_Browser.saveWithTranslator(tab, 0, true);
Zotero.Connector_Browser.saveWithTranslator(tab, 0, {fallbackOnFailure: true});
} else {
var withSnapshot = Zotero.Connector.isOnline ? Zotero.Connector.automaticSnapshots :
Zotero.Prefs.get('automaticSnapshots');
Expand Down Expand Up @@ -164,15 +164,14 @@ Zotero.Connector_Browser = new function() {
return tab.private;
}

this.saveWithTranslator = function(tab, i, fallbackOnFailure=false) {
this.saveWithTranslator = function(tab, i, options) {
var translator = tab.translators[i];
return Zotero.Messaging.sendMessage(
"translate",
[
tab.instanceID,
translator.translatorID,
translator.itemType,
fallbackOnFailure
options
],
tab
);
Expand Down

0 comments on commit e26abdf

Please sign in to comment.