keeweb-plugins/docs/plugins/external-selection-menu/plugin.js

116 lines
3.9 KiB
JavaScript

/**
* KeeWeb plugin: external-selection-menu
* @author Benjamin
* @license MIT
*/
const Logger = require('util/logger');
const logger = new Logger.Logger('external-selection-menu');
const launcher = require('comp/launcher');
const Launcher = launcher.Launcher;
const autoType = require('auto-type/index.js')
const originalProcessEventWithFilter = autoType.AutoType.processEventWithFilter; /* Preserve original method for uninstall */
const selectView = require('views/auto-type/auto-type-select-view.js');
const AutoTypeSelectView = selectView.AutoTypeSelectView;
// Function to pad number with leading zeroes
function pad(n, width, z) {
z = z || '0';
n = n + '';
return n.length >= width ? n : new Array(width - n.length + 1).join(z) + n;
}
// Command to execute
let cmd = 'dmenu';
let args = ['-c'];
// Overwrite processEventWithFilter function
autoType.AutoType.processEventWithFilter = function (evt) {
// Default code for when a matching entry can be found without having to select one
//
const initEntries = evt.filter.getEntries(); if (initEntries.length === 1 && AppSettingsModel.directAutotype) {
this.hideWindow(() => {
autoType.AutoType.runAndHandleResult({ entry: initEntries[0] }, evt.windowInfo.id);
});
return;
}
// Custom code replacing the selection menu
//
evt.filter.ignoreWindowInfo = true; /* Set filter to ignore windowInfo */
this.selectEntryView = new AutoTypeSelectView({ filter: evt.filter }); /* Create new AutoTypeSelectView to gain access to entries */
const entries = this.selectEntryView.model.filter.getEntries(); /* Get all entries from selectEntryView */
this.selectEntryView = null; /* Remove selectEntryView */
this.data = ""; /* Init data string, will be used as stdin for the command */
// Loop over all entries and add information from that entry to the data string
for (var i = 0, len = entries.length; i < len; i++) {
this.data += pad([i], 3) + ": " + entries[i].title + " - " + entries[i].user + " - " + entries[i].url + " - " + entries[i].tags + "\n";
}
// Spawn a new command (dmenu)
Launcher.spawn({
cmd: cmd,
args: args,
data: this.data,
complete: (err, stdout, code) => {
if (err) {
delete entries; /* Remove entries */
return;
}
// Callback function
const cb = function () {
let i = parseInt(stdout.split(":")[0], 10); /* From selection, get everything up to the first : (This will be the index of the entry) and parse it to an int to remove leading zeroes */
autoType.AutoType.runAndHandleResult({ entry: entries[i] }, evt.windowInfo.id); /* runAndHandleResult with the selected entry */
delete entries; /* Remove entries */
};
cb(err, stdout, code);
}
});
return;
};
module.exports.getSettings = function() {
return [
{
name: 'External menu command',
label: 'Command to be run every time the selection menu comes up',
type: 'text',
maxlength: 50,
placeholder: '',
value: 'dmenu'
},
{
name: 'External menu command arguments',
label: 'Arguments to give to the command',
type: 'text',
maxlength: 50,
placeholder: '',
value: '-c'
}
];
};
module.exports.setSettings = function(changes) {
if (changes['External menu command'])
{
cmd = changes['External menu command'];
}
if (changes['External menu command arguments'])
{
args = changes['External menu command arguments'].split(" ");
}
logger.info('Menu command changed to: ' + cmd + ' ' + args);
};
module.exports.uninstall = function() {
delete autoType.AutoType.processEventWithFilter;
autoType.AutoType.processEventWithFilter = originalProcessEventWithFilter;
};