1130 lines
38 KiB
JavaScript
1130 lines
38 KiB
JavaScript
"use strict";
|
||
|
||
const MAX_INPUT_SIZE = 1048576;
|
||
|
||
if ('serviceWorker' in navigator) {
|
||
console.log("Registering service worker");
|
||
navigator.serviceWorker.register('/sw.js');
|
||
}
|
||
|
||
class QaPage {
|
||
|
||
lang;
|
||
tls;
|
||
domWrapper;
|
||
domUploaderWrapper;
|
||
domUploaderCurrentWrapper;
|
||
domMainWrapper;
|
||
|
||
parser;
|
||
selectedActivity;
|
||
selectedApi;
|
||
|
||
constructor(lang, tls) {
|
||
|
||
this.lang = lang;
|
||
this.tls = Object.freeze(tls);
|
||
|
||
let wrapper = document.createElement("div");
|
||
wrapper.id = "contentWrapper";
|
||
this.domWrapper = wrapper;
|
||
|
||
let domUploaderWrapper = document.createElement("div");
|
||
domUploaderWrapper.id = "uploader";
|
||
domUploaderWrapper.classList.add("uploader");
|
||
this.domUploaderWrapper = domUploaderWrapper;
|
||
|
||
let domUploaderCurrentWrapper = document.createElement("div");
|
||
domUploaderCurrentWrapper.id = "uploaderMenu";
|
||
this.domUploaderCurrentWrapper = domUploaderCurrentWrapper;
|
||
|
||
let domMainWrapper = document.createElement("main");
|
||
this.domMainWrapper = domMainWrapper;
|
||
}
|
||
|
||
goForwardInMenuPages(from) {
|
||
|
||
const app = this;
|
||
|
||
switch (from) {
|
||
case "parserSelection":
|
||
app.drawUpActivitySelection();
|
||
break;
|
||
case "activityTypeSelection":
|
||
app.drawUpApiTypeSelection();
|
||
break;
|
||
case "apiTypeSelection":
|
||
app.drawUpUploadTypeSelection();
|
||
break;
|
||
default:
|
||
console.log("Invalid page to go forward from selected.");
|
||
}
|
||
|
||
}
|
||
|
||
generateDialogueCloseButton() {
|
||
|
||
const cancelB = document.createElement("a");
|
||
cancelB.classList.add("icons");
|
||
cancelB.classList.add("iconsClose");
|
||
cancelB.classList.add("dialogueCloseX");
|
||
cancelB.id = "dialogueClose";
|
||
cancelB.textContent = "X";
|
||
cancelB.title = this.tls.close;
|
||
cancelB.href = "#" + location.href;
|
||
cancelB.addEventListener('click', QaDialogue.closeDialogue);
|
||
return cancelB;
|
||
|
||
}
|
||
|
||
/**
|
||
* Setter for selectedActivity. Checks if the first argument of the API works with the intended
|
||
* activity.
|
||
*/
|
||
setSelectedActivity(selected) {
|
||
|
||
if (['evaluate', 'convert_to_xml'].includes(selected)) {
|
||
this.selectedActivity = selected;
|
||
}
|
||
else {
|
||
window.alert("Invalid activity selected");
|
||
}
|
||
|
||
}
|
||
|
||
/**
|
||
* Setter for selectedApi. Checks if the second argument of the API works with the intended
|
||
* activity.
|
||
*/
|
||
setSelectedApi(selected) {
|
||
|
||
let api_whitelist;
|
||
switch (this.selectedActivity) {
|
||
case "evaluate":
|
||
api_whitelist = ['object', 'count_vocabulary_entries_to_be_added', 'minimaldatensatz'];
|
||
break;
|
||
case "convert_to_xml":
|
||
const allowedXmlConversionTargets = document.documentElement.getAttribute("data-allowed-xml-conversion-targets").split(',');
|
||
api_whitelist = allowedXmlConversionTargets;
|
||
break;
|
||
default:
|
||
window.alert("Invalid activity set: " + this.selectedActivity);
|
||
}
|
||
|
||
if (api_whitelist.includes(selected)) {
|
||
this.selectedApi = selected;
|
||
}
|
||
else {
|
||
window.alert("Invalid activity selected");
|
||
}
|
||
|
||
}
|
||
|
||
downloadFromString(filename, text) {
|
||
|
||
const blob = new Blob([text], { type: "text/plain" });
|
||
const link = document.createElement("a");
|
||
|
||
link.download = filename;
|
||
link.href = window.URL.createObjectURL(blob);
|
||
link.dataset.downloadurl = ["text/plain", link.download, link.href].join(":");
|
||
|
||
const evt = new MouseEvent("click", {
|
||
view: window,
|
||
bubbles: true,
|
||
cancelable: true,
|
||
});
|
||
|
||
link.dispatchEvent(evt);
|
||
link.remove()
|
||
|
||
}
|
||
|
||
generateValidationOutputsForCountNewToVocabs(results) {
|
||
|
||
const validation_overlay_intro = document.getElementById("validation_overlay_intro");
|
||
if (validation_overlay_intro !== undefined && validation_overlay_intro !== null) {
|
||
validation_overlay_intro.parentElement.removeChild(validation_overlay_intro);
|
||
}
|
||
|
||
const resultsSection = document.createElement("div");
|
||
|
||
const h5 = document.createElement("h5");
|
||
h5.textContent = this.tls.count_new_to_vocabs;
|
||
resultsSection.appendChild(h5);
|
||
|
||
const table = document.createElement("table");
|
||
|
||
function createTr(th_value, td_value) {
|
||
|
||
const tr = document.createElement("tr");
|
||
|
||
const th = document.createElement("th");
|
||
th.textContent = th_value;
|
||
tr.appendChild(th);
|
||
|
||
const tdText = document.createElement("td");
|
||
tdText.textContent = td_value;
|
||
tr.appendChild(tdText);
|
||
|
||
return tr;
|
||
|
||
}
|
||
|
||
for (let result of results.count) {
|
||
table.appendChild(createTr(result.category_name, result.count));
|
||
}
|
||
|
||
resultsSection.appendChild(table);
|
||
|
||
const h6 = document.createElement("h6");
|
||
h6.textContent = this.tls.samples;
|
||
resultsSection.appendChild(h6);
|
||
|
||
const tableSamples = document.createElement("table");
|
||
|
||
for (let result of results.samples) {
|
||
tableSamples.appendChild(createTr(result.category_name, result.entries.join(", ")));
|
||
}
|
||
|
||
resultsSection.appendChild(tableSamples);
|
||
|
||
return resultsSection;
|
||
|
||
}
|
||
|
||
generateValidationOutputsForMinimaldatensatz(results) {
|
||
|
||
const resultsSection = document.createElement("div");
|
||
|
||
for (let object of results) {
|
||
|
||
const li = document.createElement("div");
|
||
|
||
const h5 = document.createElement("h5");
|
||
h5.textContent = this.tls.inventory_number + ': ' + object.invno;
|
||
li.appendChild(h5);
|
||
|
||
const table = document.createElement("table");
|
||
for (let field of object.evaluations) {
|
||
|
||
const tr = document.createElement("tr");
|
||
|
||
const td = document.createElement("td");
|
||
td.style.width = "40px";
|
||
if (field.passed === true) {
|
||
td.style.background = "var(--color-green)";
|
||
}
|
||
else td.style.background = "var(--color-red)";
|
||
tr.appendChild(td);
|
||
|
||
const tdText = document.createElement("td");
|
||
tdText.textContent = field.text;
|
||
tr.appendChild(tdText);
|
||
|
||
table.appendChild(tr)
|
||
|
||
}
|
||
li.appendChild(table);
|
||
resultsSection.appendChild(li);
|
||
|
||
}
|
||
|
||
return resultsSection;
|
||
|
||
}
|
||
|
||
generateRegularValidationOutputs(results) {
|
||
|
||
const resultsSection = document.createElement("div");
|
||
|
||
function createTr(thText, tdChild) {
|
||
|
||
const tr = document.createElement("tr");
|
||
|
||
const th = document.createElement("th");
|
||
th.textContent = thText;
|
||
tr.appendChild(th);
|
||
|
||
const td = document.createElement("td");
|
||
td.appendChild(tdChild);
|
||
tr.appendChild(td);
|
||
|
||
return tr;
|
||
|
||
}
|
||
|
||
for (let object of results) {
|
||
|
||
const li = document.createElement("div");
|
||
|
||
const h5 = document.createElement("h5");
|
||
h5.textContent = this.tls.inventory_number + ': ' + object.invno;
|
||
li.appendChild(h5);
|
||
|
||
const liContent = document.createElement("div");
|
||
|
||
const table = document.createElement("table");
|
||
|
||
const score = document.createElement("span");
|
||
score.textContent = object.puqi.score;
|
||
table.appendChild(createTr(this.tls.puqi_score, score));
|
||
|
||
const plausiStatus = document.createElement("span");
|
||
if (object.plausi.warn === false) {
|
||
plausiStatus.textContent = this.tls.check_passed;
|
||
}
|
||
else plausiStatus.textContent = this.tls.warning;
|
||
table.appendChild(createTr(this.tls.plausi + ': ' + this.tls.status, plausiStatus));
|
||
|
||
const plausiLegalStatus = document.createElement("span");
|
||
if (object.plausi_legal.warn === false) {
|
||
plausiLegalStatus.textContent = this.tls.check_passed;
|
||
}
|
||
else plausiLegalStatus.textContent = this.tls.warning;
|
||
table.appendChild(createTr(this.tls.plausi_legal + ': ' + this.tls.status, plausiLegalStatus));
|
||
|
||
liContent.appendChild(table);
|
||
|
||
// Generate section for plausi warnings
|
||
if (object.plausi.msg.length !== 0) {
|
||
|
||
const h6plausi = document.createElement("h6");
|
||
h6plausi.textContent = this.tls.plausibility_warnings;
|
||
liContent.appendChild(h6plausi);
|
||
|
||
const plausiMsgUl = document.createElement("ul");
|
||
for (let msg of object.plausi.msg) {
|
||
|
||
const plausiMsgLi = document.createElement("li");
|
||
plausiMsgLi.textContent = msg;
|
||
plausiMsgUl.appendChild(plausiMsgLi);
|
||
|
||
}
|
||
liContent.appendChild(plausiMsgUl);
|
||
|
||
}
|
||
|
||
// Generate section for plausiLegal warnings
|
||
if (object.plausi_legal.warn === true) {
|
||
|
||
const h6plausiLegal = document.createElement("h6");
|
||
h6plausiLegal.textContent = this.tls.plausibility_warnings_licenses;
|
||
liContent.appendChild(h6plausiLegal);
|
||
|
||
const plausiLegalMsgUl = document.createElement("ul");
|
||
for (let msg of object.plausi_legal.msg) {
|
||
|
||
const plausiLegalMsgLi = document.createElement("li");
|
||
|
||
if (msg.link !== '') {
|
||
const plausiLegalA = document.createElement("a");
|
||
plausiLegalA.href = msg.link;
|
||
plausiLegalA.textContent = msg.text;
|
||
plausiLegalMsgLi.appendChild(plausiLegalA);
|
||
}
|
||
else plausiLegalMsgLi.textContent = msg.text;
|
||
|
||
plausiLegalMsgUl.appendChild(plausiLegalMsgLi);
|
||
|
||
}
|
||
liContent.appendChild(plausiLegalMsgUl);
|
||
|
||
}
|
||
|
||
const h6puq = document.createElement("h6");
|
||
h6puq.textContent = this.tls.puqi_notices;
|
||
liContent.appendChild(h6puq);
|
||
|
||
const puqiMsgUl = document.createElement("ul");
|
||
|
||
for (let msg of object.puqi.msg) {
|
||
|
||
const puqiMsgLi = document.createElement("li");
|
||
puqiMsgLi.textContent = msg.message;
|
||
puqiMsgUl.appendChild(puqiMsgLi);
|
||
|
||
}
|
||
|
||
liContent.appendChild(puqiMsgUl);
|
||
|
||
li.appendChild(liContent);
|
||
|
||
resultsSection.appendChild(li);
|
||
|
||
}
|
||
|
||
return resultsSection;
|
||
|
||
}
|
||
|
||
listValidationOutputs(elements) {
|
||
|
||
console.log("Listing validation errors");
|
||
|
||
const dialogueContent = document.createElement("div");
|
||
|
||
const headline = document.createElement("h3");
|
||
headline.textContent = this.tls.validation_errors;
|
||
headline.appendChild(this.generateDialogueCloseButton());
|
||
dialogueContent.appendChild(headline);
|
||
|
||
const intro = document.createElement("p");
|
||
intro.id = "validation_overlay_intro";
|
||
intro.textContent = this.tls.objects_identified.replace("[placeholder_for_count]", elements.results.length);
|
||
dialogueContent.appendChild(intro);
|
||
|
||
const resultsSection = document.createElement("section");
|
||
dialogueContent.appendChild(resultsSection);
|
||
|
||
const resultsSectionH4 = document.createElement("h4");
|
||
resultsSectionH4.textContent = this.tls.results;
|
||
resultsSection.appendChild(resultsSectionH4);
|
||
|
||
switch (this.selectedApi) {
|
||
case "count_vocabulary_entries_to_be_added":
|
||
resultsSection.appendChild(this.generateValidationOutputsForCountNewToVocabs(elements.results));
|
||
break;
|
||
case "minimaldatensatz":
|
||
resultsSection.appendChild(this.generateValidationOutputsForMinimaldatensatz(elements.results));
|
||
break;
|
||
default:
|
||
resultsSection.appendChild(this.generateRegularValidationOutputs(elements.results));
|
||
break;
|
||
}
|
||
|
||
dialogue = QaDialogue.drawDialogue(dialogueContent);
|
||
|
||
}
|
||
|
||
async runApiQuery(data) {
|
||
|
||
if (navigator.onLine === false) {
|
||
window.alert(this.tls.currently_offline_msg);
|
||
document.body.classList.remove("loading");
|
||
return false;
|
||
}
|
||
|
||
let app = this;
|
||
|
||
(async function() {
|
||
const result = data;
|
||
if (result.includes('<27>')) {
|
||
window.alert('The file encoding appears to not be UTF-8-encoded!');
|
||
}
|
||
})();
|
||
|
||
let bodyParams = {
|
||
parser: app.parser,
|
||
lang: app.lang,
|
||
data: data,
|
||
};
|
||
|
||
if (app.selectedActivity === 'convert_to_xml') {
|
||
bodyParams.institution_name = window.prompt("The institution's name cannot automatically be reused from what may be stated in the uploaded data. If you would like to have one in the output data, please enter it here.");
|
||
bodyParams.institution_identifier = window.prompt("The institution's identifier (e.g. an ISIL ID) cannot automatically be reused from what may be stated in the uploaded data. If you would like to have one in the output data, please enter it here.");
|
||
}
|
||
|
||
try {
|
||
|
||
let requestBody = [];
|
||
for (let param in bodyParams) {
|
||
requestBody.push(param + '=' + encodeURIComponent(bodyParams[param]));
|
||
}
|
||
const response = await window.fetch('/api/' + app.selectedActivity + '/' + app.selectedApi, {
|
||
method: 'POST', cache: 'no-cache',
|
||
headers: {'Content-Type': 'application/x-www-form-urlencoded'},
|
||
body: requestBody.join("&"),
|
||
});
|
||
|
||
document.body.classList.remove("loading");
|
||
if (response.status === 200) {
|
||
|
||
switch (app.selectedActivity) {
|
||
case "evaluate":
|
||
try {
|
||
const elements = await response.json();
|
||
app.listValidationOutputs(elements);
|
||
}
|
||
catch (error) {
|
||
console.log(error);
|
||
}
|
||
break;
|
||
case "convert_to_xml":
|
||
const text = await response.text();
|
||
app.downloadFromString('converted-' + app.selectedActivity + '.xml', text);
|
||
break;
|
||
default:
|
||
window.alert("Invalid activity selected");
|
||
}
|
||
}
|
||
else {
|
||
const text = await response.text();
|
||
window.alert(text);
|
||
}
|
||
}
|
||
catch(error) {
|
||
console.log(error);
|
||
};
|
||
|
||
app.drawUpParserSelection();
|
||
|
||
}
|
||
|
||
uploadFileForValidation(file) {
|
||
|
||
let app = this;
|
||
|
||
if (file.size >= MAX_INPUT_SIZE) {
|
||
window.alert(this.tls.filesize_too_big.replace("[placeholder]", MAX_INPUT_SIZE));
|
||
return false;
|
||
}
|
||
|
||
const reader = new FileReader();
|
||
reader.readAsText(file, 'UTF-8');
|
||
|
||
document.body.classList.add("loading");
|
||
|
||
reader.onload = function() {
|
||
|
||
function handleValidation() {
|
||
app.runApiQuery(reader.result);
|
||
|
||
}
|
||
|
||
handleValidation();
|
||
|
||
};
|
||
reader.onerror = function() {
|
||
alert(reader.error);
|
||
};
|
||
|
||
}
|
||
|
||
renderGenHeader() {
|
||
|
||
const header = document.createElement("header");
|
||
header.id = "mainHeader";
|
||
|
||
const logoArea = document.createElement("a");
|
||
logoArea.id = "logoArea";
|
||
logoArea.href = "https://www.museum-digital.org/";
|
||
|
||
const logoImg = document.createElement("img");
|
||
logoImg.src = "/static/img/mdlogo-code.svg";
|
||
logoImg.alt = "Logo of museum-digital";
|
||
logoArea.appendChild(logoImg);
|
||
|
||
const h2 = document.createElement("h2");
|
||
h2.textContent = "museum-digital";
|
||
logoArea.appendChild(h2);
|
||
|
||
header.appendChild(logoArea);
|
||
|
||
// Right side of the header
|
||
const nav = document.createElement("nav");
|
||
|
||
const lAbout = document.createElement("a");
|
||
lAbout.href = "https://en.about.museum-digital.org/about";
|
||
lAbout.textContent = this.tls.about;
|
||
nav.appendChild(lAbout);
|
||
|
||
const lContactList = document.createElement("div");
|
||
|
||
const lContact = document.createElement("a");
|
||
lContact.textContent = this.tls.contact;
|
||
lContact.href = "https://en.about.museum-digital.org/contact/";
|
||
lContactList.appendChild(lContact);
|
||
|
||
const lContactDiv = document.createElement("div");
|
||
|
||
const lImprint = document.createElement("a");
|
||
lImprint.textContent = this.tls.imprint;
|
||
lImprint.href = "https://en.about.museum-digital.org/impressum";
|
||
lContactDiv.appendChild(lImprint);
|
||
|
||
const lPrivacy = document.createElement("a");
|
||
lPrivacy.textContent = this.tls.privacy_policy;
|
||
lPrivacy.href = "https://en.about.museum-digital.org/privacy/";
|
||
lContactDiv.appendChild(lPrivacy);
|
||
|
||
lContactList.appendChild(lContactDiv);
|
||
nav.appendChild(lContactList);
|
||
|
||
const lNews = document.createElement("a")
|
||
lNews.textContent = this.tls.news;
|
||
lNews.href = "https://blog.museum-digital.org/";
|
||
nav.appendChild(lNews);
|
||
|
||
header.appendChild(nav);
|
||
document.body.appendChild(header);
|
||
|
||
}
|
||
|
||
renderHeader() {
|
||
|
||
const appHeader = document.createElement("header");
|
||
appHeader.id = "appHeader";
|
||
|
||
const h1 = document.createElement("h1");
|
||
|
||
const img = document.createElement("img");
|
||
img.width = "70";
|
||
img.height = "70";
|
||
img.src = "/static/img/mdlogo-code.svg";
|
||
img.alt = "";
|
||
h1.appendChild(img);
|
||
|
||
const h1Span = document.createElement("span");
|
||
h1Span.textContent = "museum-digital:qa";
|
||
h1.appendChild(h1Span);
|
||
|
||
appHeader.appendChild(h1);
|
||
|
||
document.body.appendChild(appHeader);
|
||
|
||
}
|
||
|
||
createP(text) {
|
||
const output = document.createElement("p");
|
||
output.textContent = text;
|
||
return output;
|
||
}
|
||
|
||
createPlainTextElem(type, text) {
|
||
const output = document.createElement(type);
|
||
output.textContent = text;
|
||
return output;
|
||
}
|
||
|
||
renderText() {
|
||
|
||
const domH2 = document.createElement("h2");
|
||
domH2.textContent = this.tls.quality_assessment_tools;
|
||
this.domMainWrapper.appendChild(domH2);
|
||
|
||
this.domMainWrapper.appendChild(this.createP(this.tls.intro_text));
|
||
|
||
this.domWrapper.appendChild(this.domMainWrapper);
|
||
|
||
}
|
||
|
||
// Setup
|
||
renderUploader() {
|
||
|
||
const textarea = document.createElement("textarea");
|
||
this.domUploaderWrapper.appendChild(textarea);
|
||
|
||
const submitB = document.createElement("button");
|
||
submitB.textContent = "Submittt";
|
||
this.domUploaderWrapper.appendChild(submitB);
|
||
|
||
this.domWrapper.appendChild(this.domUploaderWrapper);
|
||
|
||
}
|
||
|
||
renderStartpageSectionTechBackground() {
|
||
|
||
const app = this;
|
||
|
||
function toggleAccordionBox(elem) {
|
||
|
||
elem.classList.toggle("active");
|
||
const panel = elem;
|
||
if (panel.style.maxHeight) {
|
||
panel.style.maxHeight = null
|
||
} else {
|
||
panel.style.maxHeight = panel.scrollHeight + "px"
|
||
}
|
||
|
||
}
|
||
|
||
function appendTypesOfEvaluations(section) {
|
||
|
||
section.appendChild(app.createPlainTextElem("h3", app.tls.types_of_evaluations));
|
||
|
||
const threeColumnDiv = document.createElement("div");
|
||
threeColumnDiv.classList.add("threeCol");
|
||
|
||
function generatePuqiDiv() {
|
||
|
||
const puqiDiv = document.createElement("div");
|
||
puqiDiv.id = "puqi_ex";
|
||
puqiDiv.appendChild(app.createPlainTextElem("h4", app.tls.puqi));
|
||
puqiDiv.appendChild(app.createP(app.tls.puqi_explica));
|
||
puqiDiv.appendChild(app.createPlainTextElem("h5", app.tls.see));
|
||
|
||
const puqiCitUl = document.createElement("ul");
|
||
|
||
const puqiCit3 = document.createElement("li");
|
||
puqiCit3.innerHTML = 'Rohde-Enslin, S. (2014). "PuQi - Eine Versuchung." Paper presented at the Autumn Seminar of the Working Group Documentation of the German Museum Association, 2014 (Herbsttagung der FG Dokumentation des Deutschen Museumsbunds). <a href="https://files.museum-digital.org/de/Praesentationen/2014-10-06_PuQI-Eine-Versuchung_SRE.pdf">https://files.museum-digital.org/de/Praesentationen/2014-10-06_PuQI-Eine-Versuchung_SRE.pdf</a>';
|
||
puqiCitUl.appendChild(puqiCit3);;
|
||
|
||
const puqiCit1 = document.createElement("li");
|
||
puqiCit1.innerHTML = 'Rohde-Enslin, S. (2015). "PuQI – A Smart Way to Create Better Data." <i>Uncommon Culture</i>, 6 (2), 122-129. <a href="https://uncommonculture.org/ojs/index.php/UC/article/view/6218">https://uncommonculture.org/ojs/index.php/UC/article/view/6218</a>';
|
||
puqiCitUl.appendChild(puqiCit1);
|
||
|
||
const puqiCit2 = document.createElement("li");
|
||
puqiCit2.innerHTML = 'Rohde-Enslin, S. (2021). "PuQi – Verführung zu Qualität." <i>museum-digital:blog</i>, <a href="https://blog.museum-digital.org/de/2021/01/22/ein-publikations-qualitaets-index-fuer-museumsobjektinformationen/">https://blog.museum-digital.org/de/2021/01/22/ein-publikations-qualitaets-index-fuer-museumsobjektinformationen/</a>';
|
||
puqiCitUl.appendChild(puqiCit2);;
|
||
puqiDiv.appendChild(puqiCitUl);
|
||
|
||
puqiDiv.addEventListener('click', function() { toggleAccordionBox(puqiDiv); }, {passive: true})
|
||
|
||
return puqiDiv;
|
||
|
||
}
|
||
function generatePlausiDiv() {
|
||
|
||
const plausiDiv = document.createElement("div");
|
||
plausiDiv.id = "plausi_ex";
|
||
plausiDiv.appendChild(app.createPlainTextElem("h4", app.tls.plausi));
|
||
plausiDiv.appendChild(app.createP(app.tls.plausi_explica));
|
||
plausiDiv.appendChild(app.createP(app.tls.plausi_explica_2));
|
||
plausiDiv.appendChild(app.createPlainTextElem("h5", app.tls.see));
|
||
|
||
const plausiCitUl = document.createElement("ul");
|
||
const plausiCit1 = document.createElement("li");
|
||
plausiCit1.innerHTML = 'Rohde-Enslin, S. (2017). "Plausi - PuQI hat einen Freund bekommen." Paper presented at the Autumn Seminar of the Working Group Documentation of the German Museum Association, 2017 (Herbsttagung der FG Dokumentation des Deutschen Museumsbunds). <a href="https://files.museum-digital.org/de/Praesentationen/2017-11_Plausi-FG-Doku-Berlin_SRE.pdf">https://files.museum-digital.org/de/Praesentationen/2017-11_Plausi-FG-Doku-Berlin_SRE.pdf</a>';
|
||
plausiCitUl.appendChild(plausiCit1);;
|
||
plausiDiv.appendChild(plausiCitUl);
|
||
|
||
plausiDiv.addEventListener('click', function() { toggleAccordionBox(plausiDiv); }, {passive: true})
|
||
return plausiDiv;
|
||
|
||
}
|
||
function generatePlausiLegalDiv() {
|
||
|
||
const plausiLegalDiv = document.createElement("div");
|
||
plausiLegalDiv.id = "plausi_legal_ex";
|
||
plausiLegalDiv.appendChild(app.createPlainTextElem("h4", app.tls.plausi_legal));
|
||
plausiLegalDiv.appendChild(app.createP(app.tls.plausi_legal_explica));
|
||
plausiLegalDiv.appendChild(app.createP(app.tls.plausi_legal_explica_2));
|
||
|
||
plausiLegalDiv.addEventListener('click', function() { toggleAccordionBox(plausiLegalDiv); }, {passive: true})
|
||
return plausiLegalDiv;
|
||
|
||
}
|
||
function generateCountNewToVocabsDiv() {
|
||
|
||
const div = document.createElement("div");
|
||
div.id = "minimaldatensatz_ex";
|
||
div.appendChild(app.createPlainTextElem("h4", app.tls.count_new_to_vocabs));
|
||
div.appendChild(app.createP(app.tls.count_new_to_vocabs_explica_1));
|
||
// div.appendChild(app.createPlainTextElem("h5", app.tls.see));
|
||
|
||
div.addEventListener('click', function() { toggleAccordionBox(div); }, {passive: true})
|
||
return div;
|
||
|
||
}
|
||
function generateMinimaldatensatzDiv() {
|
||
|
||
const div = document.createElement("div");
|
||
div.id = "minimaldatensatz_ex";
|
||
div.appendChild(app.createPlainTextElem("h4", "AG Minimaldatensatz"));
|
||
div.appendChild(app.createP(app.tls.minimaldatensatz_explica_1));
|
||
div.appendChild(app.createP(app.tls.minimaldatensatz_explica_2));
|
||
div.appendChild(app.createPlainTextElem("h5", app.tls.see));
|
||
|
||
const citUl = document.createElement("ul");
|
||
const cit1 = document.createElement("li");
|
||
cit1.innerHTML = 'AG Minimaldatensatz. (2023). "Minimaldatensatz-Empfehlung." <a href="http://minimaldatensatz.de">http://minimaldatensatz.de</a>';
|
||
citUl.appendChild(cit1);;
|
||
|
||
const cit2 = document.createElement("li");
|
||
cit2.innerHTML = 'Marchini C. & Greisinger S. (2023). "Ein Fuß in der Tür: Die Minimaldatensatz-Empfehlung für Museen und Sammlungen." Paper presented at the Autumn Seminar of the Working Group Documentation of the German Museum Association, 2023 (Herbsttagung der FG Dokumentation des Deutschen Museumsbunds).';
|
||
citUl.appendChild(cit2);;
|
||
div.appendChild(citUl);
|
||
|
||
div.addEventListener('click', function() { toggleAccordionBox(div); }, {passive: true})
|
||
return div;
|
||
|
||
}
|
||
|
||
threeColumnDiv.appendChild(generatePuqiDiv());
|
||
threeColumnDiv.appendChild(generatePlausiDiv());
|
||
threeColumnDiv.appendChild(generatePlausiLegalDiv());
|
||
threeColumnDiv.appendChild(generateCountNewToVocabsDiv());
|
||
threeColumnDiv.appendChild(generateMinimaldatensatzDiv());
|
||
|
||
section.appendChild(threeColumnDiv);
|
||
|
||
}
|
||
|
||
function appendOtherFeatures(section) {
|
||
|
||
section.appendChild(app.createPlainTextElem("h3", app.tls.other_features));
|
||
|
||
const threeColumnDiv = document.createElement("div");
|
||
threeColumnDiv.classList.add("threeCol");
|
||
|
||
function generateXmlConversionExp() {
|
||
|
||
const xmlCDiv = document.createElement("div");
|
||
xmlCDiv.id = "xmlC_ex";
|
||
xmlCDiv.appendChild(app.createPlainTextElem("h4", app.tls.convert_to_xml));
|
||
xmlCDiv.appendChild(app.createP(app.tls.convert_to_xml_explica));
|
||
|
||
xmlCDiv.appendChild(app.createPlainTextElem("h5", app.tls.see));
|
||
const citUl = document.createElement("ul");
|
||
const citLi = document.createElement("li");
|
||
|
||
const eodemA = document.createElement("a");
|
||
eodemA.textContent = "EODEM";
|
||
eodemA.href = "https://cidoc.mini.icom.museum/working-groups/documentation-standards/eodem-home/";
|
||
citLi.appendChild(eodemA);
|
||
|
||
citUl.appendChild(citLi);
|
||
xmlCDiv.appendChild(citUl);
|
||
|
||
xmlCDiv.addEventListener('click', function() { toggleAccordionBox(xmlCDiv); }, {passive: true})
|
||
|
||
return xmlCDiv;
|
||
|
||
}
|
||
|
||
threeColumnDiv.appendChild(generateXmlConversionExp());
|
||
|
||
section.appendChild(threeColumnDiv);
|
||
|
||
}
|
||
|
||
const section = document.createElement("div");
|
||
section.appendChild(this.createPlainTextElem("h2", this.tls.tech_background_hl));
|
||
|
||
const summaryDiv = document.createElement("div");
|
||
summaryDiv.classList.add("summary");
|
||
summaryDiv.appendChild(this.createPlainTextElem("h3", this.tls.summary));
|
||
summaryDiv.appendChild(this.createP(this.tls.tech_background_summary));
|
||
summaryDiv.appendChild(this.createP(this.tls.click_read_more));
|
||
section.appendChild(summaryDiv);
|
||
|
||
const techBackgroundDetails = this.createP(this.tls.tech_background_text);
|
||
techBackgroundDetails.classList.add("accordion");
|
||
section.appendChild(techBackgroundDetails);
|
||
|
||
summaryDiv.addEventListener('click', function() { toggleAccordionBox(techBackgroundDetails); }, {passive: true})
|
||
|
||
appendTypesOfEvaluations(section);
|
||
appendOtherFeatures(section);
|
||
|
||
return section;
|
||
|
||
}
|
||
|
||
renderStartpageSectionFuture() {
|
||
|
||
const section = document.createElement("div");
|
||
section.appendChild(this.createPlainTextElem("h2", this.tls.outlook));
|
||
section.appendChild(this.createP(this.tls.outlook_text));
|
||
return section;
|
||
|
||
}
|
||
|
||
renderStartpageSectionFaq() {
|
||
|
||
function toggleAccordionBox(elem) {
|
||
|
||
elem.classList.toggle("active");
|
||
const panel = elem;
|
||
if (panel.style.maxHeight) {
|
||
panel.style.maxHeight = null
|
||
} else {
|
||
panel.style.maxHeight = panel.scrollHeight + "px"
|
||
}
|
||
|
||
}
|
||
|
||
function buildFaqEntry(question, answer) {
|
||
|
||
const entry = document.createElement("div");
|
||
entry.id = "faqEntry";
|
||
|
||
const q = document.createElement("p");
|
||
q.classList.add("faq_question");
|
||
q.textContent = question;
|
||
entry.appendChild(q);
|
||
|
||
const a = document.createElement("div");
|
||
a.classList.add("faq_answer", "accordion");
|
||
a.textContent = answer;
|
||
entry.appendChild(a);
|
||
|
||
q.addEventListener('click', function() { toggleAccordionBox(a); }, {passive: true})
|
||
|
||
return entry;
|
||
|
||
}
|
||
|
||
const section = document.createElement("div");
|
||
section.id = "faq";
|
||
section.appendChild(this.createPlainTextElem("h2", "FAQ"));
|
||
|
||
section.appendChild(buildFaqEntry(this.tls.faq_q_1, this.tls.faq_a_1));
|
||
section.appendChild(buildFaqEntry(this.tls.faq_q_2, this.tls.faq_a_2));
|
||
|
||
return section;
|
||
|
||
}
|
||
|
||
renderStartpageSectionMore() {
|
||
|
||
// More / Links to further content
|
||
|
||
const moreSec = document.createElement("div");
|
||
moreSec.id = "more";
|
||
|
||
moreSec.appendChild(this.createPlainTextElem("h2", this.tls.more));
|
||
|
||
const moreTiles = document.createElement("div");
|
||
moreTiles.classList.add("moreTiles");
|
||
moreTiles.setAttribute("property", "itemListElement");
|
||
moreTiles.setAttribute("typeof", "http://schema.org/ListItem");
|
||
|
||
let counter = 1;
|
||
function createMoreTile(url, title, subtitle, img_url_webp, img_url_fallback, img_alt) {
|
||
|
||
const tile = document.createElement("a");
|
||
tile.href = url;
|
||
tile.setAttribute("property", "position");
|
||
tile.setAttribute("content", counter);
|
||
counter++;
|
||
|
||
const pic = document.createElement("picture");
|
||
pic.loading = "lazy";
|
||
|
||
const source_webp = document.createElement("source");
|
||
source_webp.type = "image/webp";
|
||
source_webp.srcset = img_url_webp;
|
||
pic.appendChild(source_webp);
|
||
|
||
const source_fallback = document.createElement("source");
|
||
source_fallback.type = "image/png";
|
||
source_fallback.srcset = img_url_fallback;
|
||
pic.appendChild(source_fallback);
|
||
|
||
const img = document.createElement("img");
|
||
img.loading = "lazy";
|
||
img.src = img_url_fallback;
|
||
img.alt = img_alt;
|
||
img.width = "400";
|
||
img.height = "225";
|
||
img.setAttribute("property", "image");
|
||
pic.appendChild(img);
|
||
|
||
tile.appendChild(pic);
|
||
|
||
const meta = document.createElement("div");
|
||
meta.classList.add("moreTilesMeta");
|
||
|
||
const e_title = document.createElement("p");
|
||
e_title.textContent = title;
|
||
e_title.setAttribute("property", "name");
|
||
e_title.classList.add("moreTilesTitle");
|
||
meta.appendChild(e_title);
|
||
|
||
const e_subtitle = document.createElement("p");
|
||
e_subtitle.textContent = subtitle;
|
||
e_subtitle.classList.add("moreTilesSubtitle");
|
||
meta.appendChild(e_subtitle);
|
||
|
||
tile.appendChild(meta);
|
||
|
||
return tile;
|
||
|
||
}
|
||
|
||
moreTiles.appendChild(createMoreTile(
|
||
"https://files.museum-digital.org/",
|
||
"Vortragsfolien",
|
||
"Vortrag auf der Herbsttagung der Fachgruppe Dokumentation des DMB, 10.10.2023.", "CC BY 4.0 @ Joshua Ramon Enslin, Freies Deutsches Hochstift",
|
||
"/static/img/more/20231010-Presentation.webp",
|
||
"/static/img/more/20231010-Presentation.png",
|
||
"Folie zur Nachnutzbarkeit von vorliegendem Code im Vortrag auf der Herbsttagung der FG Doku.",
|
||
)
|
||
);
|
||
|
||
moreSec.appendChild(moreTiles);
|
||
|
||
// Log
|
||
|
||
moreSec.appendChild(this.createPlainTextElem("h3", this.tls.log));
|
||
|
||
const logUl = document.createElement("ul");
|
||
|
||
const app = this;
|
||
function generateLogEntry(date, text) {
|
||
const logLi1 = document.createElement("li");
|
||
logLi1.textContent = new Intl.DateTimeFormat([app.lang, 'de']).format(date) + ': ' + text;
|
||
return logLi1;
|
||
}
|
||
|
||
logUl.appendChild(generateLogEntry(
|
||
new Date(Date.UTC(2023, 11, 16, 3, 45, 0, 738)), "Add options to convert input data to XML formats"
|
||
));
|
||
|
||
logUl.appendChild(generateLogEntry(
|
||
new Date(Date.UTC(2023, 9, 10, 3, 45, 0, 738)), this.tls.launch // 9 = October
|
||
));
|
||
|
||
moreSec.appendChild(logUl);
|
||
|
||
|
||
// Say thanks
|
||
moreSec.appendChild(this.createPlainTextElem("h3", this.tls.thanks));
|
||
|
||
const thanksP = document.createElement("p");
|
||
|
||
moreSec.appendChild(thanksP);
|
||
|
||
return moreSec;
|
||
|
||
}
|
||
|
||
renderFooter() {
|
||
|
||
const footer = document.createElement("footer");
|
||
|
||
/*
|
||
|
||
const licenseStatement = document.createElement("p");
|
||
licenseStatement.textContent = "This work is licensed under the GNU Affero Public License Version 3.";
|
||
footer.appendChild(licenseStatement);
|
||
|
||
*/
|
||
|
||
const footerOptions = document.createElement("div");
|
||
|
||
/*
|
||
const codeLink = document.createElement("a");
|
||
codeLink.textContent = "Source code";
|
||
codeLink.href = "https://gitea.armuli.eu/museum-digital/csvxml";
|
||
footerOptions.appendChild(codeLink);
|
||
*/
|
||
|
||
const codeLink = document.createElement("a");
|
||
codeLink.textContent = "API"; // TODO
|
||
codeLink.href = "/swagger";
|
||
footerOptions.appendChild(codeLink);
|
||
|
||
if ('serviceWorker' in navigator) {
|
||
const refreshB = document.createElement("span");
|
||
refreshB.textContent = this.tls.reload_application;
|
||
refreshB.setAttribute("tabindex", 1);
|
||
refreshB.addEventListener('click', function(e) {
|
||
|
||
Promise.all(['qa-cache-v1'].map(function(cache) {
|
||
caches.has(cache).then(function(hasCache) {
|
||
if (hasCache === true) {
|
||
caches.delete(cache).then(function(deletionStatus) {});
|
||
}
|
||
})
|
||
}))
|
||
location.reload()
|
||
|
||
}, {passive: true, once: true});
|
||
footerOptions.appendChild(refreshB);
|
||
}
|
||
|
||
const allowedLangs = document.documentElement.getAttribute("data-allowed-langs").split(',');
|
||
const langSel = document.createElement("div");
|
||
for (let lang of allowedLangs) {
|
||
const l = document.createElement("a");
|
||
l.href = "#" + lang;
|
||
l.textContent = lang;
|
||
l.style.textTranform = "uppercase";
|
||
l.addEventListener('click', function(e) {
|
||
e.preventDefault();
|
||
sessionStorage.setItem("lang", lang);
|
||
location.reload();
|
||
});
|
||
langSel.appendChild(l);
|
||
}
|
||
footerOptions.appendChild(langSel);
|
||
|
||
footer.appendChild(footerOptions);
|
||
|
||
const licenseLine = document.createElement("p");
|
||
|
||
const license = document.createElement("a");
|
||
license.textContent = "CC BY 4.0";
|
||
license.href = "https://creativecommons.org/licenses/by/4.0/";
|
||
licenseLine.appendChild(license);
|
||
|
||
licenseLine.appendChild(this.createPlainTextElem("span", " @ "));
|
||
|
||
const author = document.createElement("a");
|
||
author.textContent = "Joshua Ramon Enslin";
|
||
author.href = "https://www.jrenslin.de";
|
||
author.setAttribute("rel", "author");
|
||
licenseLine.appendChild(author);
|
||
|
||
licenseLine.appendChild(this.createPlainTextElem("span", ", "));
|
||
|
||
const attributionYear = document.createElement("span");
|
||
attributionYear.textContent = "2023";
|
||
licenseLine.appendChild(attributionYear);
|
||
|
||
footer.appendChild(licenseLine);
|
||
|
||
document.body.appendChild(footer);
|
||
|
||
}
|
||
|
||
}
|
||
|
||
(async function() {
|
||
|
||
function getLang() {
|
||
|
||
const allowedLangs = document.documentElement.getAttribute("data-allowed-langs").split(',');
|
||
|
||
const langFromSession = sessionStorage.getItem("lang");
|
||
if (langFromSession !== undefined && allowedLangs.includes(langFromSession)) {
|
||
return langFromSession;
|
||
}
|
||
|
||
if (navigator.language === undefined) return 'en';
|
||
|
||
const browserLang = navigator.language.toLowerCase().substr(0, 2);
|
||
console.log(browserLang);
|
||
|
||
if (allowedLangs.includes(browserLang)) return browserLang;
|
||
else return 'en';
|
||
|
||
}
|
||
|
||
const lang = getLang();
|
||
document.documentElement.setAttribute("lang", lang);
|
||
|
||
document.body.classList.add("loading");
|
||
|
||
let loaded = 0;
|
||
|
||
let tls;
|
||
|
||
function loadPage() {
|
||
|
||
document.body.classList.remove("loading");
|
||
|
||
const page = new QaPage(lang, tls);
|
||
page.renderGenHeader();
|
||
page.renderHeader();
|
||
page.renderUploader();
|
||
page.renderText();
|
||
document.body.appendChild(page.domWrapper);
|
||
page.renderFooter();
|
||
|
||
}
|
||
|
||
window.fetch('/static/json/tls.' + lang + '.json', {
|
||
method: 'GET', cache: 'no-cache', credentials: 'same-origin',
|
||
}).then(function(response) {
|
||
return response.json();
|
||
}).then(function(elements) {
|
||
tls = elements;
|
||
loadPage();
|
||
});
|
||
|
||
})();
|