MarseyWorld/files/assets/js/core.js

775 lines
20 KiB
JavaScript
Raw Normal View History

const SITE_FULL_IMAGES = document.getElementById('SITE_FULL_IMAGES').value
function getMessageFromJsonData(success, json) {
2023-11-10 14:15:37 +00:00
let message = success ? "Success!" : "Error, please refresh the page and try again";
let key = success ? "message" : "error";
if (!json || !json[key]) return message;
message = json[key];
if (!success && json["details"]) {
message = json["details"];
}
return message;
}
2023-08-11 21:50:23 +00:00
function showToast(success, message) {
const oldToast = bootstrap.Toast.getOrCreateInstance(document.getElementById('toast-post-' + (success ? 'error': 'success'))); // intentionally reversed here: this is the old toast
oldToast.hide();
let element = success ? "toast-post-success" : "toast-post-error";
2022-10-14 12:33:36 +00:00
let textElement = element + "-text";
2022-10-14 09:49:58 +00:00
if (!message) {
2023-11-10 14:15:37 +00:00
message = success ? "Action successful!" : "Error, please refresh the page and try again";
2022-10-14 09:49:58 +00:00
}
document.getElementById(textElement).textContent = message;
2022-10-14 09:49:58 +00:00
bootstrap.Toast.getOrCreateInstance(document.getElementById(element)).show();
2022-10-14 08:19:09 +00:00
}
function createXhrWithFormKey(url, form=new FormData(), method='POST') {
2022-10-14 12:33:36 +00:00
const xhr = new XMLHttpRequest();
xhr.open(method, url);
2022-10-14 12:33:36 +00:00
xhr.setRequestHeader('xhr', 'xhr');
if (!form) form = new FormData();
2022-10-14 12:33:36 +00:00
form.append("formkey", formkey());
return [xhr, form]; // hacky but less stupid than what we were doing before
}
function postToast(t, url, data, extraActionsOnSuccess, extraActionsOnFailure) {
2023-10-10 18:23:14 +00:00
const is_shop = t.id && t.id.startsWith('buy-')
if (!is_shop) {
t.disabled = true;
t.classList.add("disabled");
}
2023-08-12 12:48:40 +00:00
2022-10-14 12:33:36 +00:00
let form = new FormData();
2023-08-06 03:33:34 +00:00
if (typeof data === 'object' && data !== null) {
for(let k of Object.keys(data)) {
form.append(k, data[k]);
}
}
2023-08-12 10:35:59 +00:00
const xhr = createXhrWithFormKey(url, form);
xhr[0].onload = function() {
2023-08-11 21:50:23 +00:00
const success = xhr[0].status >= 200 && xhr[0].status < 300;
2023-10-10 18:23:14 +00:00
if (!(extraActionsOnSuccess == reload && success && !is_shop)) {
2023-08-11 21:50:23 +00:00
t.disabled = false;
t.classList.remove("disabled");
}
let result
2022-10-14 12:33:36 +00:00
let message;
if (typeof result == "string") {
message = result;
} else {
message = getMessageFromJsonData(success, JSON.parse(xhr[0].response));
}
showToast(success, message);
2023-08-12 10:49:37 +00:00
if (success && extraActionsOnSuccess) extraActionsOnSuccess(xhr[0]);
if (!success && extraActionsOnFailure) extraActionsOnFailure(xhr[0]);
2022-10-14 12:33:36 +00:00
return success;
};
xhr[0].send(xhr[1]);
2022-11-03 19:07:08 +00:00
}
function handle_disabled(t) {
btn = t.parentElement.getElementsByClassName('handle_disabled')[0]
2023-09-17 19:14:07 +00:00
if (!btn) return
if (t.value) {
btn.disabled = false;
btn.classList.remove('disabled')
}
else {
btn.disabled = true;
btn.classList.add('disabled')
}
}
2023-08-12 10:35:59 +00:00
function postToastReload(t, url) {
postToast(t, url, {}, reload);
2022-11-04 21:44:37 +00:00
}
2023-08-12 10:35:59 +00:00
function postToastSwitch(t, url, button1, button2, cls, extraActionsOnSuccess) {
postToast(t, url,
2022-11-03 19:07:08 +00:00
{
},
(xhr) => {
2022-11-04 18:45:52 +00:00
if (button1)
{
2023-08-23 00:31:20 +00:00
if (typeof button1 == 'boolean') {
2022-11-04 18:45:52 +00:00
location.reload()
} else {
2022-12-16 20:00:42 +00:00
try {
document.getElementById(button1).classList.toggle(cls);
2022-12-16 20:17:23 +00:00
}
catch (e) {}
try {
document.getElementById(button2).classList.toggle(cls);
2022-12-16 20:00:42 +00:00
}
catch (e) {}
2022-11-04 18:45:52 +00:00
}
}
2023-01-24 10:40:25 +00:00
if (typeof extraActionsOnSuccess == 'function')
2023-08-12 10:35:59 +00:00
extraActionsOnSuccess(xhr);
});
}
if (!location.pathname.endsWith('/submit') && !location.pathname.endsWith('/chat'))
{
document.addEventListener('keydown', (e) => {
2023-08-06 03:33:34 +00:00
if (!((e.ctrlKey || e.metaKey) && e.key === "Enter")) return;
const targetDOM = document.activeElement;
2023-08-06 03:33:34 +00:00
if (!(targetDOM instanceof HTMLTextAreaElement || targetDOM instanceof HTMLInputElement)) return;
const formDOM = targetDOM.parentElement;
2023-07-22 17:43:32 +00:00
if (formDOM.id == 'note_section') {
2023-10-10 16:53:46 +00:00
document.querySelector('.awardbtn:not(.d-none)').click();
2023-07-22 17:43:32 +00:00
return
}
2023-10-13 15:56:12 +00:00
if (location.pathname == '/admin/orgies') {
2023-08-16 19:18:05 +00:00
document.getElementById('start-orgy').click();
return
}
const submitButtonDOMs = formDOM.querySelectorAll('input[type=submit], .btn-primary');
2023-10-02 06:04:05 +00:00
if (submitButtonDOMs.length === 0)
throw new TypeError("I am unable to find the submit button :(. Contact the head custodian immediately.")
const btn = submitButtonDOMs[0]
btn.click();
});
}
2022-11-08 04:09:55 +00:00
function autoExpand(field) {
xpos = window.scrollX;
ypos = window.scrollY;
field.style.height = 'inherit';
let computed = window.getComputedStyle(field);
2022-12-04 15:40:32 +00:00
let height = parseInt(computed.getPropertyValue('border-top-width'), 10)
+ parseInt(computed.getPropertyValue('padding-top'), 10)
+ field.scrollHeight
+ parseInt(computed.getPropertyValue('padding-bottom'), 10)
+ parseInt(computed.getPropertyValue('border-bottom-width'), 10);
field.style.height = height + 'px';
if (Math.abs(window.scrollX - xpos) < 1 && Math.abs(window.scrollY - ypos) < 1) return;
window.scrollTo(xpos,ypos);
};
function smoothScrollTop()
{
window.scrollTo({ top: 0, behavior: 'smooth' });
}
// Click navbar to scroll back to top
2022-11-26 05:34:50 +00:00
const nav = document.getElementsByTagName('nav')
2022-12-04 15:40:32 +00:00
if (nav.length) {
2022-11-26 05:34:50 +00:00
nav[0].addEventListener('click', (e) => {
if (e.target.id === "navbar" ||
e.target.classList.contains("container-fluid") ||
e.target.id == "navbarResponsive" ||
e.target.id == "logo-container" ||
e.target.classList.contains("srd"))
smoothScrollTop();
}, false);
}
function formkey() {
let formkey = document.getElementById("formkey")
if (formkey) return formkey.innerHTML;
else return null;
}
function bs_trigger(e) {
let tooltipTriggerList = [].slice.call(e.querySelectorAll('[data-bs-toggle="tooltip"]'));
tooltipTriggerList.map(function(element){
return bootstrap.Tooltip.getOrCreateInstance(element);
});
2024-01-12 05:18:24 +00:00
if (typeof update_inline_emoji_modal == 'function') {
2023-08-12 18:57:59 +00:00
insertGhostDivs(e)
}
}
function escapeHTML(unsafe) {
return unsafe.replace(/&/g, "&amp;").replace(/</g, "&lt;").replace(/>/g, "&gt;").replace(/"/g, "&quot;").replace(/'/g, "&#039;");
}
2023-01-01 12:31:40 +00:00
function showmore(t) {
2023-03-10 21:10:46 +00:00
div = t.parentElement.parentElement.parentElement
2023-02-24 07:31:12 +00:00
let text = div.getElementsByTagName('d')[0]
if (!text) text = div.getElementsByClassName('showmore-text')[0]
2023-03-10 23:30:42 +00:00
if (!text) text = div.querySelector('div.d-none')
2023-02-24 07:31:12 +00:00
text.classList.remove('d-none')
t.remove()
}
function formatDate(d) {
const options = {year: 'numeric', month: 'short', day: 'numeric', hour: '2-digit', minute: '2-digit', timeZoneName: 'short'};
return d.toLocaleTimeString([], options)
}
const timestamps = document.querySelectorAll('[data-time]');
for (const e of timestamps) {
2022-11-25 23:25:15 +00:00
e.innerHTML = formatDate(new Date(e.dataset.time*1000));
};
function timestamp(t, ti) {
2022-11-25 23:25:15 +00:00
const date = formatDate(new Date(ti*1000));
t.setAttribute("data-bs-original-title", date);
};
function areyousure(t) {
2024-02-12 07:18:43 +00:00
if (t.dataset.nonce != nonce) { //to stop the oldhtml attribute from being used as a vector for html injections
console.error("Nonce check failed!")
return
}
if (t.value) {
t.dataset.oldvalue = t.value
t.value = 'Are you sure?'
}
else {
t.dataset.oldhtml = t.innerHTML
t.innerHTML = t.innerHTML.replace(t.textContent, 'Are you sure?')
}
2022-12-30 12:14:18 +00:00
t.setAttribute("data-onclick", t.dataset.areyousure);
if (t.dataset.dismiss)
2022-10-14 09:49:58 +00:00
t.setAttribute("data-bs-dismiss", t.dataset.dismiss);
t.classList.add('areyousure')
2022-10-14 18:20:23 +00:00
}
2022-10-24 22:36:51 +00:00
function prepare_to_pause(audio) {
for (const e of document.querySelectorAll('video,audio'))
{
if (e == audio) continue
2022-10-24 22:36:51 +00:00
e.addEventListener('play', () => {
if (!audio.paused) audio.pause();
});
}
document.addEventListener('click', (e) => {
if ((e.target.tagName.toLowerCase() == "lite-youtube" || e.target.classList.contains('lty-playbtn')) && !audio.paused) {
audio.pause();
}
});
2022-10-24 22:36:51 +00:00
}
2023-10-19 18:58:44 +00:00
function handle_playing_music(audio) {
audio.addEventListener('play', () => {
localStorage.setItem("playing_music", Date.now());
2023-10-19 19:08:32 +00:00
addEventListener('beforeunload', () => {
2023-10-19 18:58:44 +00:00
localStorage.setItem("playing_music", 0);
})
})
audio.addEventListener('pause', () => {
localStorage.setItem("playing_music", 0);
})
}
function playing_music() {
2023-10-19 19:23:06 +00:00
return (Date.now() - localStorage.getItem("playing_music", 0) < 300000)
2023-10-19 18:58:44 +00:00
}
2023-08-11 21:50:23 +00:00
function reload() {
location.reload();
}
2022-12-30 12:52:59 +00:00
function sendFormXHR(form, extraActionsOnSuccess) {
2024-01-12 05:18:24 +00:00
if (typeof close_inline_emoji_modal === "function") {
close_inline_emoji_modal();
2023-10-17 20:35:47 +00:00
}
2023-08-11 21:50:23 +00:00
const t = form.querySelector('[type="submit"]')
t.disabled = true;
t.classList.add("disabled");
const xhr = new XMLHttpRequest();
formData = new FormData(form);
formData.append("formkey", formkey());
actionPath = form.getAttribute("action");
xhr.open("POST", actionPath);
xhr.setRequestHeader('xhr', 'xhr');
xhr.onload = function() {
2023-08-11 21:50:23 +00:00
const success = xhr.status >= 200 && xhr.status < 300;
if (!(extraActionsOnSuccess == reload && success)) {
t.disabled = false;
t.classList.remove("disabled");
}
2023-10-10 19:34:38 +00:00
try {
2023-08-11 21:50:23 +00:00
const data = JSON.parse(xhr.response);
showToast(success, getMessageFromJsonData(success, data));
}
2023-10-10 19:34:38 +00:00
catch {}
2023-08-11 21:50:23 +00:00
if (success && extraActionsOnSuccess) extraActionsOnSuccess(xhr);
};
xhr.send(formData);
}
function sendFormXHRSwitch(form) {
2022-12-30 12:52:59 +00:00
sendFormXHR(form,
() => {
2023-09-20 14:57:31 +00:00
form.nextElementSibling.classList.remove('d-none');
const days = form.querySelector("input[name=days]")
if (!days || !days.value)
form.classList.add('d-none');
}
)
}
2022-12-10 10:40:34 +00:00
2023-07-14 17:07:58 +00:00
function sendFormXHRReload(form) {
2023-08-11 21:50:23 +00:00
sendFormXHR(form, reload)
2023-07-14 17:07:58 +00:00
}
2022-12-10 10:40:34 +00:00
let sortAscending = {};
function sort_table(t) {
const n = Array.prototype.indexOf.call(t.parentElement.children, t);
const table = this.event.target.parentElement.parentElement.parentElement
const rows = table.rows;
let items = [];
for (let i = 1; i < rows.length; i++) {
const ele = rows[i];
let x = rows[i].getElementsByTagName("TD")[n];
if (!('sortKey' in x.dataset)) {
x = x.getElementsByTagName('a')[0] || x;
}
let attr;
if ('sortKey' in x.dataset) {
attr = x.dataset.sortKey;
2023-03-07 05:38:55 +00:00
if (/^[\d-,]+$/.test(attr)) {
2023-03-07 05:37:14 +00:00
attr = parseInt(attr.replace(/,/g, ''))
}
2022-12-10 10:40:34 +00:00
} else if ('time' in x.dataset) {
attr = parseInt(x.dataset.time);
} else {
attr = x.textContent
2022-12-10 11:57:23 +00:00
if (/^[\d-,]+$/.test(x.innerHTML)) {
2022-12-10 10:40:34 +00:00
attr = parseInt(attr.replace(/,/g, ''))
}
}
items.push({ele, attr});
}
if (sortAscending[n]) {
items.sort((a, b) => a.attr > b.attr ? 1 : -1);
sortAscending[n] = false;
} else {
items.sort((a, b) => a.attr < b.attr ? 1 : -1);
sortAscending[n] = true;
}
for (let i = items.length - 1; i--;) {
items[i].ele.parentNode.insertBefore(items[i].ele, items[i + 1].ele);
}
}
const is_pwa = window.matchMedia('(display-mode: standalone)')['matches'] || window.matchMedia('(display-mode: minimal-ui)')['matches']
if (is_pwa) {
const links = document.querySelectorAll('a[data-target="t"]');
for (const link of links) {
link.removeAttribute("target");
}
}
const gbrowser = document.getElementById('gbrowser').value
2023-09-24 22:12:42 +00:00
if (location.pathname != '/chat' && (gbrowser == 'iphone' || gbrowser == 'mac')) {
const videos = document.querySelectorAll('video')
for (const video of videos) {
const link = video.src
const htmlString = `
<a rel="noopener" href="${link}" target="_blank">
<div class="d-flex justify-content-between align-items-center border rounded p-2 mb-3 download-video">
<span>${link}</span>
<i class="fas fa-external-link-alt text-small"></i>
</div>
</a>`
const div = document.createElement('div');
div.innerHTML = htmlString;
video.after(div)
}
}
2023-01-24 10:02:08 +00:00
2023-09-29 06:11:18 +00:00
const screen_width = (innerWidth > 0) ? innerWidth : screen.width;
function focusSearchBar(element)
{
if (screen_width >= 768) {
element.focus();
}
}
2023-02-27 15:02:35 +00:00
let MINFLIES;
let MAXFLIES;
2023-07-14 11:24:53 +00:00
let ACTUALMAXFILES;
2023-02-27 15:02:35 +00:00
if (screen_width < 768) {
MINFLIES = 5;
MAXFLIES = 10;
2023-07-14 11:24:53 +00:00
ACTUALMAXFILES = 50;
}
else {
MINFLIES = 10;
MAXFLIES = 20;
2023-07-14 11:24:53 +00:00
ACTUALMAXFILES = 150;
}
2023-02-27 15:02:35 +00:00
2023-03-18 14:27:12 +00:00
function insertText(input, text) {
if (input.value) text = ` ${text}`
2023-03-18 14:27:12 +00:00
const newPos = input.selectionStart + text.length;
input.setRangeText(text);
if (window.chrome !== undefined)
2023-03-18 14:27:12 +00:00
setTimeout(function(){
input.focus();
for(let i = 0; i < 2; i++)
input.setSelectionRange(newPos, newPos);
input.focus();
for(let i = 0; i < 2; i++)
input.setSelectionRange(newPos, newPos);
}, 1);
else
input.setSelectionRange(newPos, newPos);
2023-07-22 16:29:19 +00:00
input.selectionStart = newPos;
handle_disabled(input)
if (typeof checkForRequired === "function") checkForRequired();
setTimeout(() => {
2023-10-29 14:12:29 +00:00
if (document.activeElement !== input)
input.focus();
2023-10-29 14:09:35 +00:00
}, 200);
2023-03-18 14:27:12 +00:00
}
2023-02-27 15:02:35 +00:00
//FILE SHIT
let oldfiles = {};
2023-10-02 15:02:39 +00:00
let MAX_IMAGE_AUDIO_SIZE_MB
let MAX_IMAGE_AUDIO_SIZE_MB_PATRON
let MAX_VIDEO_SIZE_MB
let MAX_VIDEO_SIZE_MB_PATRON
let vpatron
if (document.getElementById("MAX_IMAGE_AUDIO_SIZE_MB")) {
MAX_IMAGE_AUDIO_SIZE_MB = parseInt(document.getElementById("MAX_IMAGE_AUDIO_SIZE_MB").value)
MAX_IMAGE_AUDIO_SIZE_MB_PATRON = parseInt(document.getElementById("MAX_IMAGE_AUDIO_SIZE_MB_PATRON").value)
MAX_VIDEO_SIZE_MB = parseInt(document.getElementById("MAX_VIDEO_SIZE_MB").value)
MAX_VIDEO_SIZE_MB_PATRON = parseInt(document.getElementById("MAX_VIDEO_SIZE_MB_PATRON").value)
vpatron = parseInt(document.getElementById("vpatron").value)
}
let patron
if (location.host == 'rdrama.net') patron = 'paypig'
else patron = 'patron'
2023-02-27 15:02:35 +00:00
function handle_files(input, newfiles) {
if (!newfiles) return;
2023-05-05 21:45:25 +00:00
for (const file of newfiles) {
if (file.type.startsWith('image/'))
continue
let max_size
let max_size_patron
let type
if (file.type.startsWith('video/')) {
max_size = MAX_VIDEO_SIZE_MB
max_size_patron = MAX_VIDEO_SIZE_MB_PATRON
type = 'video'
}
else {
max_size = MAX_IMAGE_AUDIO_SIZE_MB
max_size_patron = MAX_IMAGE_AUDIO_SIZE_MB_PATRON
type = 'image/audio'
}
if (file.size > max_size_patron * 1024 * 1024 || (!vpatron && file.size > max_size * 1024 * 1024)) {
const msg = `Max ${type} size is ${max_size} MB (${max_size_patron} MB for ${patron}s)`
showToast(false, msg);
input.value = null;
return
}
}
2023-02-27 15:02:35 +00:00
const ta = input.parentElement.parentElement.parentElement.parentElement.querySelector('textarea.file-ta');
2023-08-18 02:11:21 +00:00
if (!oldfiles[ta.id]) {
oldfiles[ta.id] = new DataTransfer();
2023-02-27 15:02:35 +00:00
}
2023-09-07 15:26:31 +00:00
const oldtext = ta.value;
for (let file of newfiles) {
if (file.name == 'image.png') {
const blob = file.slice(0, file.size, 'image/png');
const new_name = Math.random().toString(32).substring(2,10) + '.png'
file = new File([blob], new_name, {type: 'image/png'});
}
2023-08-18 02:11:21 +00:00
oldfiles[ta.id].items.add(file);
insertText(ta, `[${file.name}]`);
2023-08-18 02:11:21 +00:00
}
2023-02-27 15:02:35 +00:00
input.files = oldfiles[ta.id].files;
2023-09-07 15:26:31 +00:00
if (input.files.length > 20)
2023-02-27 15:02:35 +00:00
{
window.alert("You can't upload more than 20 files at one time!")
2023-02-27 15:02:35 +00:00
input.value = null
ta.value = oldtext
oldfiles[ta.id] = new DataTransfer();
2023-02-27 15:02:35 +00:00
return
}
2023-08-22 23:21:49 +00:00
markdown(ta)
2023-02-27 15:02:35 +00:00
autoExpand(ta)
2023-09-07 15:26:31 +00:00
if (typeof checkForRequired === "function")
checkForRequired();
2023-09-07 15:26:31 +00:00
if (typeof savetext === "function")
savetext();
2023-08-08 12:26:32 +00:00
if (typeof submit_save_files === "function") {
const array = []
for (const x of input.files) {
array.push(x)
}
submit_save_files("textarea", array);
}
2023-02-27 15:02:35 +00:00
}
file_upload = document.getElementById('file-upload');
if (file_upload) {
function display_url_image() {
if (file_upload.files)
{
2023-08-07 13:27:04 +00:00
const file = file_upload.files[0]
const char_limit = screen_width >= 768 ? 50 : 10;
file_upload.previousElementSibling.textContent = file.name.substr(0, char_limit);
2023-08-07 13:27:04 +00:00
if (file.type.startsWith('image/')) {
const fileReader = new FileReader();
fileReader.readAsDataURL(file_upload.files[0]);
fileReader.onload = function () {
document.getElementById('image-preview').setAttribute('src', this.result);
document.getElementById('image-preview').classList.remove('d-none');
document.getElementById('image-preview').classList.add('mr-2');
};
}
else {
document.getElementById('image-preview').classList.add('d-none');
document.getElementById('image-preview').classList.remove('mr-2');
}
if (typeof checkForRequired === "function") {
document.getElementById('urlblock').classList.add('d-none');
document.getElementById('remove-attachment').classList.remove('d-none');
checkForRequired();
}
else {
document.getElementById('submit-btn').disabled = false;
}
}
}
file_upload.onchange = () => {
display_url_image()
if (typeof submit_save_files === "function") {
const array = []
for (const x of file_upload.files) {
array.push(x)
}
submit_save_files("attachment", array);
}
}
}
2023-02-27 15:02:35 +00:00
document.onpaste = function(event) {
const files = structuredClone(event.clipboardData.files);
if (!files.length) return
const focused = document.activeElement;
let input;
if (file_upload) {
if (location.pathname.endsWith('/submit') && focused && focused.id == 'post-text') {
2023-02-27 15:02:35 +00:00
input = document.getElementById('file-upload-submit')
}
else {
file_upload.files = files;
display_url_image();
if (typeof submit_save_files === "function") {
const array = []
for (const x of file_upload.files) {
array.push(x)
}
submit_save_files("attachment", array);
}
2023-02-27 15:02:35 +00:00
return;
}
}
else if (focused) {
input = focused.parentElement.querySelector('input[type="file"]')
}
else {
input = document.querySelector('input[type="file"]')
}
event.preventDefault();
2023-02-27 15:02:35 +00:00
handle_files(input, files);
}
2023-02-27 17:25:38 +00:00
function handleUploadProgress(e, upload_prog) {
const bar = upload_prog.firstElementChild;
const percentIndicator = upload_prog.lastElementChild;
2023-05-05 21:45:25 +00:00
2023-02-27 17:25:38 +00:00
upload_prog.classList.remove("d-none")
if (e.lengthComputable) {
const progressPercent = Math.floor((e.loaded / e.total) * 100);
bar.value = progressPercent;
percentIndicator.textContent = progressPercent + '%';
}
}
2023-10-02 06:04:05 +00:00
2023-10-14 19:29:33 +00:00
if (screen_width < 768) {
2023-10-02 06:04:05 +00:00
let object
2024-02-18 20:39:01 +00:00
const expandImageModal = document.getElementById('expandImageModal')
2023-10-02 06:04:05 +00:00
if (gbrowser == 'iphone' && expandImageModal)
object = expandImageModal
2024-02-18 20:39:01 +00:00
2023-10-02 06:04:05 +00:00
if (gbrowser != 'iphone')
object = document
if (object) {
object.addEventListener('shown.bs.modal', function (e) {
const new_href = `${location.href.split('#')[0]}#m-${e.target.id}`
history.pushState({}, '', new_href)
});
object.addEventListener('hide.bs.modal', function (e) {
if (location.hash == `#m-${e.target.id}`) {
history.back();
}
});
addEventListener('hashchange', function () {
if (!location.hash.startsWith("#m-")) {
const curr_modal = bootstrap.Modal.getInstance(document.getElementsByClassName('show')[0])
if (curr_modal) curr_modal.hide()
}
});
}
}
document.addEventListener('show.bs.modal', () => {
2024-01-12 05:18:24 +00:00
if (typeof close_inline_emoji_modal === "function") {
close_inline_emoji_modal();
}
});
2023-10-17 20:35:47 +00:00
document.addEventListener('hide.bs.modal', () => {
2024-01-12 05:18:24 +00:00
if (typeof close_inline_emoji_modal === "function") {
close_inline_emoji_modal();
2023-10-17 20:35:47 +00:00
}
});
2023-03-21 19:03:28 +00:00
document.querySelectorAll('form').forEach(form => {
2023-03-21 18:56:05 +00:00
form.addEventListener('submit', (e) => {
if (form.classList.contains('is-submitting')) {
e.preventDefault();
}
2023-05-05 21:45:25 +00:00
2023-03-21 18:56:05 +00:00
form.classList.add('is-submitting');
});
});
function urlB64ToUint8Array(base64String) {
const padding = '='.repeat((4 - base64String.length % 4) % 4);
const base64 = (base64String + padding)
.replace(/\-/g, '+')
.replace(/_/g, '/');
const rawData = window.atob(base64);
const outputArray = new Uint8Array(rawData.length);
for (let i = 0; i < rawData.length; ++i) {
outputArray[i] = rawData.charCodeAt(i);
}
return outputArray;
}
function updateSubscriptionOnServer(subscription, apiEndpoint) {
const formData = new FormData();
formData.append("subscription_json", JSON.stringify(subscription));
const xhr = createXhrWithFormKey(
apiEndpoint,
formData
);
xhr[0].send(xhr[1]);
}
function enablePushNotifications() {
if (!('serviceWorker' in navigator && 'PushManager' in window)) return;
let publicKeyElement = document.getElementById('VAPID_PUBLIC_KEY');
if (!publicKeyElement) return;
let publicKey = urlB64ToUint8Array(publicKeyElement.value);
navigator.serviceWorker.getRegistration("/assets/js/service_worker.js").then((reg) => {
return reg.pushManager.subscribe({
userVisibleOnly: true,
applicationServerKey: publicKey,
})
}).then((subscription) => {
updateSubscriptionOnServer(subscription, "/push_subscribe")
window.alert("Push notifications are enabled!")
}).catch((e) => {
window.alert("Please give the site access to notifications!")
2023-07-22 23:44:00 +00:00
console.error(e)
})
}
2024-01-31 21:14:20 +00:00
function delReport(t, url) {
postToast(t, url,
{
},
() => {
t.parentElement.remove()
}
);
}
2024-02-14 09:57:05 +00:00
for (const el of document.getElementsByClassName('autofocus')) {
el.focus()
}