175 lines
6.2 KiB
Plaintext
175 lines
6.2 KiB
Plaintext
(function() {
|
|
'use strict';
|
|
|
|
window.utils = window.utils || {};
|
|
|
|
window.utils.modal = function(modal) {
|
|
var overlay = document.createElement('div');
|
|
var closer = document.createElement('div');
|
|
var trigger = document.querySelector('#' + modal.dataset.trigger);
|
|
// var origParent = modal.parentNode;
|
|
|
|
function open(event) {
|
|
// disable modals for narrow screens
|
|
if (event) {
|
|
event.preventDefault();
|
|
}
|
|
modal.classList.add('modal--open');
|
|
overlay.classList.add('modal__overlay');
|
|
// document.body.insertBefore(modal, null);
|
|
document.body.insertBefore(overlay, modal);
|
|
overlay.classList.add('modal__overlay--open');
|
|
|
|
if ('closeable' in modal.dataset) {
|
|
closer.classList.add('modal__closer');
|
|
modal.insertBefore(closer, null);
|
|
closer.addEventListener('click', close, false);
|
|
overlay.addEventListener('click', close, false);
|
|
}
|
|
}
|
|
|
|
// you can open this modal via event
|
|
// example: document.dispatchEvent(new CustomEvent('modal-open', { details: { for: 'modal-[id]' }}))
|
|
function openOnEvent(event) {
|
|
if (event.detail.for === modal.getAttribute('id')) {
|
|
open();
|
|
}
|
|
}
|
|
|
|
function close(event) {
|
|
if (typeof event === 'undefined' || event.target === closer || event.target === overlay) {
|
|
overlay.remove();
|
|
// origParent.insertBefore(modal, null);
|
|
modal.classList.remove('modal--open');
|
|
closer.removeEventListener('click', close, false);
|
|
}
|
|
};
|
|
|
|
function setup() {
|
|
document.body.insertBefore(modal, null);
|
|
|
|
// every modal can be openend via document-wide event, see openOnEvent
|
|
document.addEventListener('modal-open', openOnEvent, false);
|
|
// if modal has trigger assigned to it open modal on click
|
|
if (trigger) {
|
|
trigger.classList.add('modal__trigger');
|
|
trigger.addEventListener('click', open, false);
|
|
}
|
|
|
|
if ('dynamic' in modal.dataset) {
|
|
var dynamicContentURL = trigger.getAttribute('href');
|
|
|
|
var i = dynamicContentURL.indexOf('?');
|
|
if (i === -1) {
|
|
dynamicContentURL = dynamicContentURL + "?" + #{String modalParameter};
|
|
} else {
|
|
dynamicContentURL = dynamicContentURL.slice(0,i) + "?" + #{String modalParameter} + "&" + dynamicContentURL.slice(i + 1);
|
|
}
|
|
console.log(dynamicContentURL);
|
|
|
|
if (dynamicContentURL.length > 0) {
|
|
fetch(dynamicContentURL, {
|
|
credentials: 'same-origin',
|
|
}).then(function(response) {
|
|
return response.text();
|
|
}).then(function(body) {
|
|
var modalContent = document.createElement('div');
|
|
modalContent.classList.add('modal__content');
|
|
modalContent.innerHTML = body;
|
|
|
|
var contentBody = modalContent.querySelector('.main__content-body');
|
|
var scriptTags = [];
|
|
if (contentBody) {
|
|
modalContent.querySelectorAll('script').forEach(function(scriptTag) {
|
|
if (Array.from(document.body.querySelectorAll('script')).some(function(haystack) {
|
|
if (haystack.text === scriptTag.text && haystack.getAttribute('src') === scriptTag.getAttribute('src')) {
|
|
return true;
|
|
}
|
|
return false;
|
|
})) { return }
|
|
|
|
console.log(scriptTag);
|
|
var scriptClone = document.createElement('script');
|
|
if (scriptTag.text)
|
|
scriptClone.text = striptTag.text;
|
|
if (scriptTag.hasAttributes()) {
|
|
var attrs = scriptTag.attributes;
|
|
for (var i = attrs.length - 1; i >= 0; i--) {
|
|
scriptClone.setAttribute(attrs[i].name, attrs[i].value);
|
|
}
|
|
}
|
|
|
|
document.body.insertBefore(scriptClone, null);
|
|
scriptTags.push(scriptClone);
|
|
});
|
|
|
|
modalContent.querySelectorAll('style').forEach(function(styleTag) {
|
|
if (Array.from(document.head.querySelectorAll('style')).some(function(haystack) {
|
|
return haystack.innerText === styleTag.innerText;
|
|
})) { return }
|
|
|
|
document.head.insertBefore(styleTag, null);
|
|
});
|
|
|
|
modalContent.querySelectorAll('link').forEach(function(linkTag) {
|
|
if (linkTag.getAttribute('rel') !== 'stylesheet')
|
|
return;
|
|
|
|
if (Array.from(document.head.querySelectorAll('link')).some(function(haystack) {
|
|
return haystack.getAttribute('href') === linkTag.getAttribute('href');
|
|
})) { return }
|
|
|
|
|
|
document.head.insertBefore(linkTag, null);
|
|
});
|
|
|
|
modalContent = contentBody;
|
|
}
|
|
|
|
var nudgeAttr = function(attr, x) {
|
|
var oldVal = x.getAttribute(attr);
|
|
var newVal = modal.getAttribute('id') + '__' + oldVal;
|
|
|
|
// console.log(oldVal, newVal);
|
|
x.setAttribute(attr, newVal);
|
|
};
|
|
|
|
var idAttrs = ['id', 'for', 'data-conditional-id'];
|
|
idAttrs.map(function(attr) {
|
|
modalContent.querySelectorAll('[' + attr + ']').forEach(function(x) { nudgeAttr(attr, x); });
|
|
});
|
|
|
|
modal.appendChild(modalContent);
|
|
|
|
var triggerContentLoad = function() {
|
|
document.dispatchEvent(new CustomEvent('setup', {
|
|
detail: { scope: modalContent },
|
|
bubbles: true,
|
|
cancelable: true
|
|
}));
|
|
}
|
|
|
|
if (scriptTags.length !== 0) {
|
|
scriptTags.forEach(function(t) { t.onload = triggerContentLoad; });
|
|
}
|
|
|
|
triggerContentLoad();
|
|
});
|
|
}
|
|
}
|
|
// tell further modals, that this one already got initialized
|
|
modal.classList.add('js-modal-initialized');
|
|
}
|
|
setup();
|
|
};
|
|
})();
|
|
|
|
document.addEventListener('setup', function(e) {
|
|
|
|
Array.from(e.detail.scope.querySelectorAll('.js-modal:not(.js-modal-initialized)')).map(function(modal) {
|
|
new utils.modal(modal);
|
|
});
|
|
|
|
}, false);
|
|
|