2020-10-09 19:35:46 +02:00
|
|
|
// This is the API that JS files loaded from the webview can see
|
|
|
|
// eslint-disable-next-line no-unused-vars, @typescript-eslint/no-unused-vars
|
|
|
|
const webviewApi = {
|
|
|
|
postMessage: function(message) {
|
|
|
|
window.postMessage({ target: 'plugin', message: message }, '*');
|
|
|
|
},
|
|
|
|
};
|
|
|
|
|
|
|
|
(function() {
|
|
|
|
function docReady(fn) {
|
|
|
|
if (document.readyState === 'complete' || document.readyState === 'interactive') {
|
|
|
|
setTimeout(fn, 1);
|
|
|
|
} else {
|
|
|
|
document.addEventListener('DOMContentLoaded', fn);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
function fileExtension(path) {
|
|
|
|
if (!path) throw new Error('Path is empty');
|
|
|
|
|
|
|
|
const output = path.split('.');
|
|
|
|
if (output.length <= 1) return '';
|
|
|
|
return output[output.length - 1];
|
|
|
|
}
|
|
|
|
|
|
|
|
docReady(() => {
|
|
|
|
const rootElement = document.createElement('div');
|
|
|
|
document.getElementsByTagName('body')[0].appendChild(rootElement);
|
|
|
|
|
|
|
|
const contentElement = document.createElement('div');
|
|
|
|
contentElement.setAttribute('id', 'joplin-plugin-content');
|
|
|
|
rootElement.appendChild(contentElement);
|
|
|
|
|
|
|
|
const headElement = document.getElementsByTagName('head')[0];
|
|
|
|
|
|
|
|
const addedScripts = {};
|
|
|
|
|
|
|
|
function addScript(scriptPath, id = null) {
|
|
|
|
const ext = fileExtension(scriptPath).toLowerCase();
|
|
|
|
|
|
|
|
if (ext === 'js') {
|
|
|
|
const script = document.createElement('script');
|
|
|
|
script.src = scriptPath;
|
|
|
|
if (id) script.id = id;
|
|
|
|
headElement.appendChild(script);
|
|
|
|
} else if (ext === 'css') {
|
|
|
|
const link = document.createElement('link');
|
|
|
|
link.rel = 'stylesheet';
|
|
|
|
link.href = scriptPath;
|
|
|
|
if (id) link.id = id;
|
|
|
|
headElement.appendChild(link);
|
|
|
|
} else {
|
|
|
|
throw new Error(`Unsupported script: ${scriptPath}`);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
const ipc = {
|
|
|
|
setHtml: (args) => {
|
|
|
|
contentElement.innerHTML = args.html;
|
2020-11-16 18:14:26 +02:00
|
|
|
|
2020-11-27 01:31:31 +02:00
|
|
|
// console.debug('UserWebviewIndex: setting html to', args.html);
|
2020-11-16 18:14:26 +02:00
|
|
|
|
|
|
|
window.requestAnimationFrame(() => {
|
2020-11-27 01:31:31 +02:00
|
|
|
console.debug('UserWebviewIndex: setting html callback', args.hash);
|
2020-11-16 18:14:26 +02:00
|
|
|
window.postMessage({ target: 'UserWebview', message: 'htmlIsSet', hash: args.hash }, '*');
|
|
|
|
});
|
2020-10-09 19:35:46 +02:00
|
|
|
},
|
|
|
|
|
|
|
|
setScript: (args) => {
|
|
|
|
const { script, key } = args;
|
|
|
|
|
|
|
|
const scriptPath = `file://${script}`;
|
|
|
|
const elementId = `joplin-script-${key}`;
|
|
|
|
|
|
|
|
if (addedScripts[elementId]) {
|
|
|
|
document.getElementById(elementId).remove();
|
|
|
|
delete addedScripts[elementId];
|
|
|
|
}
|
|
|
|
|
|
|
|
addScript(scriptPath, elementId);
|
|
|
|
},
|
|
|
|
|
|
|
|
setScripts: (args) => {
|
|
|
|
const scripts = args.scripts;
|
|
|
|
|
|
|
|
if (!scripts) return;
|
|
|
|
|
|
|
|
for (let i = 0; i < scripts.length; i++) {
|
|
|
|
const scriptPath = `file://${scripts[i]}`;
|
|
|
|
|
|
|
|
if (addedScripts[scriptPath]) continue;
|
|
|
|
addedScripts[scriptPath] = true;
|
|
|
|
|
|
|
|
addScript(scriptPath);
|
|
|
|
}
|
|
|
|
},
|
|
|
|
};
|
|
|
|
|
|
|
|
window.addEventListener('message', ((event) => {
|
|
|
|
if (!event.data || event.data.target !== 'webview') return;
|
|
|
|
|
|
|
|
const callName = event.data.name;
|
|
|
|
const args = event.data.args;
|
|
|
|
|
|
|
|
if (!ipc[callName]) {
|
|
|
|
console.warn('Missing IPC function:', event.data);
|
|
|
|
} else {
|
2020-11-27 01:31:31 +02:00
|
|
|
console.debug('UserWebviewIndex: Got message', callName, args);
|
2020-10-09 19:35:46 +02:00
|
|
|
ipc[callName](args);
|
|
|
|
}
|
|
|
|
}));
|
|
|
|
|
2020-11-16 18:14:26 +02:00
|
|
|
// Send a message to the containing component to notify it that the
|
|
|
|
// view content is fully ready.
|
|
|
|
//
|
|
|
|
// Need to send it with a delay to make sure all listeners are
|
|
|
|
// ready when the message is sent.
|
|
|
|
window.requestAnimationFrame(() => {
|
2020-11-27 01:31:31 +02:00
|
|
|
console.debug('UserWebViewIndex: calling isReady');
|
2020-11-16 18:14:26 +02:00
|
|
|
window.postMessage({ target: 'UserWebview', message: 'ready' }, '*');
|
|
|
|
});
|
2020-10-09 19:35:46 +02:00
|
|
|
});
|
|
|
|
})();
|