aboutsummaryrefslogtreecommitdiff
path: root/html/item_preview.js
diff options
context:
space:
mode:
Diffstat (limited to 'html/item_preview.js')
-rw-r--r--html/item_preview.js151
1 files changed, 151 insertions, 0 deletions
diff --git a/html/item_preview.js b/html/item_preview.js
new file mode 100644
index 0000000..f59e30e
--- /dev/null
+++ b/html/item_preview.js
@@ -0,0 +1,151 @@
+/**
+ * This file is part of Haketilo.
+ *
+ * Function: Showing resource/mapping details in a browser.
+ *
+ * Copyright (C) 2022 Wojtek Kosior
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * As additional permission under GNU GPL version 3 section 7, you
+ * may distribute forms of that code without the copy of the GNU
+ * GPL normally required by section 4, provided you include this
+ * license notice and, in case of non-source distribution, a URL
+ * through which recipients can access the Corresponding Source.
+ * If you modify file(s) with this exception, you may extend this
+ * exception to your version of the file(s), but you are not
+ * obligated to do so. If you do not wish to do so, delete this
+ * exception statement from your version.
+ *
+ * As a special exception to the GPL, any HTML file which merely
+ * makes function calls to this code, and for that purpose
+ * includes it by reference shall be deemed a separate work for
+ * copyright law purposes. If you modify this code, you may extend
+ * this exception to your version of the code, but you are not
+ * obligated to do so. If you do not wish to do so, delete this
+ * exception statement from your version.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <https://www.gnu.org/licenses/>.
+ *
+ * I, Wojtek Kosior, thereby promise not to sue for violation of this file's
+ * license. Although I request that you do not make use of this code in a
+ * proprietary program, I am not going to enforce this in court.
+ */
+
+#IMPORT common/indexeddb.js AS haketilodb
+#IMPORT html/dialog.js
+
+#FROM html/DOM_helpers.js IMPORT clone_template
+
+function populate_list(ul, items)
+{
+ for (const item of items) {
+ const li = document.createElement("li");
+ li.append(item);
+ ul.append(li);
+ }
+}
+
+async function file_link_clicked(preview_object, file_ref, event)
+{
+ event.preventDefault();
+
+ const db = await haketilodb.get();
+ const file = await haketilodb.idb_get(db.transaction("files"),
+ "files", file_ref.hash_key);
+ if (file === undefined) {
+ dialog.error(preview_object.dialog_context,
+ "File missing from Haketilo's inernal database :(");
+ } else {
+ const encoded_file = encodeURIComponent(file.contents);
+ open(`data:text/plain;charset=utf8,${encoded_file}`, '_blank');
+ }
+}
+
+function make_file_link(preview_object, file_ref)
+{
+ const a = document.createElement("a");
+ a.href = "javascript:void(0)";
+ a.innerText = file_ref.file;
+ a.addEventListener("click",
+ e => file_link_clicked(preview_object, file_ref, e));
+
+ return a;
+}
+
+function resource_preview(resource, preview_object, dialog_context)
+{
+ if (preview_object === undefined)
+ preview_object = clone_template("resource_preview_div");
+
+ preview_object.identifier.innerText = resource.identifier;
+ preview_object.long_name.innerText = resource.long_name;
+ preview_object.uuid.innerText = resource.uuid;
+ preview_object.version.innerText =
+ `${resource.version.join(".")}-${resource.revision}`;
+ preview_object.description.innerText = resource.description;
+ preview_object.source_name.innerText = resource.source_name;
+
+ [...preview_object.dependencies.childNodes].forEach(n => n.remove());
+ populate_list(preview_object.dependencies, resource.dependencies);
+
+ const link_maker = file_ref => make_file_link(preview_object, file_ref);
+
+ [...preview_object.scripts.childNodes].forEach(n => n.remove());
+ populate_list(preview_object.scripts, resource.scripts.map(link_maker));
+
+ [...preview_object.copyright.childNodes].forEach(n => n.remove());
+ populate_list(preview_object.copyright,
+ resource.source_copyright.map(link_maker));
+
+ preview_object.dialog_context = dialog_context;
+
+ return preview_object;
+}
+#EXPORT resource_preview
+
+function mapping_preview(mapping, preview_object, dialog_context)
+{
+ if (preview_object === undefined)
+ preview_object = clone_template("mapping_preview_div");
+
+ preview_object.identifier.innerText = mapping.identifier;
+ preview_object.long_name.innerText = mapping.long_name;
+ preview_object.uuid.innerText = mapping.uuid;
+ preview_object.version.innerText = mapping.version.join(".");
+ preview_object.description.innerText = mapping.description;
+ preview_object.source_name.innerText = mapping.source_name;
+
+ [...preview_object.payloads.childNodes].forEach(n => n.remove());
+ for (const [pattern, payload] of Object.entries(mapping.payloads).sort()) {
+ /* We use a non-breaking space because normal space would be ignored. */
+ const [nbsp, rarrow] = [160, 0x2192].map(n => String.fromCodePoint(n));
+ const texts = [`${pattern}${nbsp}`, `${rarrow} ${payload.identifier}`];
+ for (let i = 0; i < texts.length; i++) {
+ const span = document.createElement("span");
+ span.innerText = texts[i];
+ span.classList.add(`grid_col_${i + 1}`);
+ preview_object.payloads.append(span);
+ }
+ }
+
+ const link_maker = file_ref => make_file_link(preview_object, file_ref);
+
+ [...preview_object.copyright.childNodes].forEach(n => n.remove());
+ populate_list(preview_object.copyright,
+ mapping.source_copyright.map(link_maker));
+
+ preview_object.dialog_context = dialog_context;
+
+ return preview_object;
+}
+#EXPORT mapping_preview