-
Notifications
You must be signed in to change notification settings - Fork 2
/
Copy pathbackground.js
296 lines (280 loc) · 9.11 KB
/
background.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
/*
Copyright 2022. Jefferson "jscher2000" Scher. License: MPL-2.0.
version 0.1 - initial concept
version 1.0 - added toolbar button and keyboard shortcut option
version 1.1 - added option to choose between toolbar button and address bar button
version 1.2 - dark mode icon
version 1.3 - option to decode unicode characters
version 1.4 - simplify icons, add HTML link format
*/
/**** Create and populate data structure ****/
// Default starting values
var oPrefs = {
allpages: true, // Copy the URL of the page even if it's in the top frame
allpagesmenu: false, // Current menu status
contexticon: false, // Option to use context fill color for toolbar icons
contexticonstatus: false, // Whether context-fill icon is in use
clickplain: 'url', // Plain click on browser action copies URL only
clickshift: 'markdown', // Shift+click on browser action copies markdown
clickctrl: 'html', // Shift+click on browser action copies html
pageaction: false, // Button in the address bar
darkmode: false, // Option to use dark icon for Page Action
decode: true // Option to decode Unicode URLs
}
let pagemenu;
let iconpath = 'icons/link-64px-green.svg'; // default path, potentially updated later
// Update oPrefs from storage
let getPrefs = browser.storage.local.get("prefs").then((results) => {
if (results.prefs != undefined){
if (JSON.stringify(results.prefs) != '{}'){
var arrSavedPrefs = Object.keys(results.prefs)
for (var j=0; j<arrSavedPrefs.length; j++){
oPrefs[arrSavedPrefs[j]] = results.prefs[arrSavedPrefs[j]];
}
}
}
}).then(() => {
if (oPrefs.contexticon == true){
iconpath = 'icons/link-64px.svg';
oPrefs.contexticonstatus = true;
// Update toolbar icon (async)
browser.browserAction.setIcon({path: iconpath});
}
if (oPrefs.allpages == true){
pagemenu = browser.menus.create({
id: "copy-page-url",
title: "Copy Page URL",
contexts: ["page", "selection"]
}, function(){ // Optimistic!
oPrefs.allpagesmenu = true;
});
}
if (oPrefs.pageaction){
browser.tabs.onUpdated.addListener(showPageAction);
}
updateButtonTooltips();
}).catch((err) => {console.log('Error retrieving "prefs" from storage: '+err.message);});
/**** Context menu item ****/
let framemenu = browser.menus.create({
id: "copy-frame-url",
title: "Copy Framed Page URL",
contexts: ["frame"]
});
browser.menus.onClicked.addListener((menuInfo, currTab) => {
switch (menuInfo.menuItemId) {
case 'copy-frame-url':
// Copy to clipboard
updateClipboard(deco(menuInfo.frameUrl));
break;
case 'copy-page-url':
// Check for Shift or Ctrl as modifier
var style = oPrefs.clickplain;
if (menuInfo.modifiers){
if (menuInfo.modifiers.includes('Shift')){
style = oPrefs.clickshift;
} else if (menuInfo.modifiers.includes('Ctrl')){
style = oPrefs.clickctrl;
}
}
// Set up text for copying
if (style == 'html'){
var txt = '<a href="' + deco(currTab.url) + '">' + currTab.title + '</a>';
} else if (style == 'markdown'){
var txt = '[' + currTab.title + '](' + deco(currTab.url) + ')';
} else {
txt = deco(menuInfo.pageUrl);
}
updateClipboard(txt);
break;
default:
// WTF?
}
});
function updateClipboard(txt){
// Copy to clipboard
navigator.clipboard.writeText(txt).catch((err) => {
window.alert('Apologies, but there was an error writing to the clipboard: ' + err);
});
}
function deco(urltxt){ // version 1.3
if (oPrefs.decode == true){
try {
return decodeURI(urltxt);
} catch(err) {
console.log(err, urltxt);
return urltxt;
}
} else {
return urltxt;
}
}
/**** Toolbar button and keyboard shortcut ****/
browser.browserAction.onClicked.addListener((tab, clickData) => {
// Check for Shift or Ctrl as modifier
var style = oPrefs.clickplain;
if (clickData && clickData.modifiers){
if (clickData.modifiers.includes('Shift')){
style = oPrefs.clickshift;
} else if (clickData.modifiers.includes('Ctrl')){
style = oPrefs.clickctrl;
}
}
// Set up text for copying
if (style == 'html'){
var txt = '<a href="' + deco(tab.url) + '">' + tab.title + '</a>';
} else if (style == 'markdown'){
var txt = '[' + tab.title + '](' + deco(tab.url) + ')';
} else {
txt = deco(tab.url);
}
updateClipboard(txt);
});
browser.commands.onCommand.addListener((strName) => {
if (strName === 'copy-page-url'){
browser.tabs.query({
active: true,
currentWindow: true
}).then((currTab) => {
updateClipboard(deco(currTab[0].url));
}).catch((err) => {
console.log(err);
});
} else if (strName === 'copy-page-url-as-markdown'){
browser.tabs.query({
active: true,
currentWindow: true
}).then((currTab) => {
updateClipboard('[' + currTab[0].title + '](' + deco(currTab[0].url) + ')');
}).catch((err) => {
console.log(err);
});
} else if (strName === 'copy-page-url-as-html'){ //todo
browser.tabs.query({
active: true,
currentWindow: true
}).then((currTab) => {
updateClipboard('<a href="' + deco(currTab.url) + '">' + currTab.title + '</a>');
}).catch((err) => {
console.log(err);
});
}
});
function showPageAction(tabId){
browser.pageAction.show(tabId);
if (oPrefs.darkmode == true){ // as of v1.4, same icon
browser.pageAction.setIcon({
tabId: tabId,
path: {
64: iconpath
}
});
} else {
browser.pageAction.setIcon({
tabId: tabId,
path: {
64: iconpath
}
});
}
browser.pageAction.setTitle({
tabId: tabId,
title: buttonTitle
});
}
browser.pageAction.onClicked.addListener((tab, clickData) => {
// Check for Shift or Ctrl as modifier
var style = oPrefs.clickplain;
if (clickData && clickData.modifiers){
if (clickData.modifiers.includes('Shift')){
style = oPrefs.clickshift;
} else if (clickData.modifiers.includes('Ctrl')){
style = oPrefs.clickctrl;
}
}
// Set up text for copying
if (style == 'html'){
var txt = '<a href="' + deco(tab.url) + '">' + tab.title + '</a>';
} else if (style == 'markdown'){
var txt = '[' + tab.title + '](' + deco(tab.url) + ')';
} else {
txt = deco(tab.url);
}
updateClipboard(txt);
});
var buttonTitle = '';
function updateButtonTooltips(){
if (oPrefs.clickplain == 'url'){
buttonTitle = 'Copy Current Page URL (Shift => ' + oPrefs.clickshift + ', Ctrl => ' + oPrefs.clickctrl + ')';
}
if (oPrefs.clickplain == 'markdown'){
buttonTitle = 'Copy Title+URL as Markdown (Shift => ' + oPrefs.clickshift + ', Ctrl => ' + oPrefs.clickctrl + ')';
}
if (oPrefs.clickplain == 'html'){
buttonTitle = 'Copy Title+URL as HTML Link (Shift => ' + oPrefs.clickshift + ', Ctrl => ' + oPrefs.clickctrl + ')';
}
if (buttonTitle.length > 0){
browser.browserAction.setTitle({
title: buttonTitle
});
}
}
/**** Handle Requests from Options ****/
function handleMessage(request, sender, sendResponse){
if ("get" in request) {
// Send oPrefs to Options page
sendResponse({
prefs: oPrefs
});
} else if ("update" in request) {
// Receive pref updates from Options page, store to oPrefs, and commit to storage
var oSettings = request["update"];
oPrefs.allpages = oSettings.allpages;
// Icon change
oPrefs.contexticon = oSettings.contexticon;
if (oPrefs.contexticon == true && oPrefs.contexticonstatus == false) {
iconpath = 'icons/link-64px.svg';
oPrefs.contexticonstatus = true;
// Update toolbar icon (async)
browser.browserAction.setIcon({path: iconpath});
// Update menu icon (NOT POSSIBLE FOR TOP LEVEL ITEMS)
} else if (oPrefs.contexticon == false && oPrefs.contexticonstatus == true) {
iconpath = 'icons/link-64px-green.svg';
oPrefs.contexticonstatus = false;
// Update toolbar icon (async)
browser.browserAction.setIcon({path: iconpath});
// Update menu icon (NOT POSSIBLE FOR TOP LEVEL ITEMS)
}
oPrefs.clickplain = oSettings.clickplain;
oPrefs.clickshift = oSettings.clickshift;
oPrefs.clickctrl = oSettings.clickctrl;
oPrefs.decode = oSettings.decode;
// Check for Page Action changes
oPrefs.darkmode = oSettings.darkmode;
if (oSettings.pageaction == true && oPrefs.pageaction == false){
browser.tabs.onUpdated.addListener(showPageAction);
} else if (oSettings.pageaction == false && oPrefs.pageaction == true){
browser.tabs.onUpdated.removeListener(showPageAction);
}
oPrefs.pageaction = oSettings.pageaction;
browser.storage.local.set({prefs: oPrefs})
.catch((err) => {console.log('Error on browser.storage.local.set(): '+err.message);});
// Add or remove menu
if (oPrefs.allpages == true && oPrefs.allpagesmenu == false) {
browser.menus.create({
id: "copy-page-url",
title: "Copy Page URL",
contexts: ["page", "selection"]
}, function(){ // Optimistic!
oPrefs.allpagesmenu = true;
});
} else if (oPrefs.allpages == false && oPrefs.allpagesmenu == true) {
pagemenu = browser.menus.remove("copy-page-url");
pagemenu.then(() => {
oPrefs.allpagesmenu = false;
});
}
// Fix button tooltips
updateButtonTooltips();
}
}
browser.runtime.onMessage.addListener(handleMessage);