Updated html element creation to single function for smaller code base when creating elements

This commit is contained in:
2022-09-04 00:04:27 +03:00
parent 35d5f2cab3
commit b9dd04c63a

View File

@@ -1,223 +1,254 @@
(function runTwitchNotes() { (function runTwitchNotes() {
let mousePosition = { x: 0, y: 0 }; const Notes = {
let lastMousePosition = { x: 0, y: 0 }; getSavedUserList: () => {
let openContainers = {}; return JSON.parse(localStorage.getItem(LS_UserList) || "[]");
let isMouseDown = false; },
let activeContainer = null; addUserToSavedList: (username) => {
let settingsWindowOpen = false; let userList = Notes.getSavedUserList();
let LS_UserList = "twitch-note-all-users-list"; if (!userList.includes(username)) {
let LS_Prefix = "twitch-note-"; userList.push(username);
localStorage.setItem(LS_UserList, JSON.stringify(userList));
document.addEventListener("mousemove", handleMouseMove); }
document.addEventListener("mouseup", handleMouseUp); },
saveNote: (username, note) => {
function createSettingsButton(buttonContainer) { Notes.addUserToSavedList(username);
const c1 = document.createElement("div"); localStorage.setItem(LS_Prefix + username, note);
c1.style.marginLeft = "0.5rem !important"; },
const c2 = document.createElement("div"); getNote: (username) => {
c2.style.display = "inline-flex !important"; return localStorage.getItem(LS_Prefix + username) || "";
}
const settingsButton = document.createElement("button");
settingsButton.classList.add("twitch-notes-settings-button");
settingsButton.innerHTML = "Notes";
settingsButton.addEventListener("click", () => {
console.log("TN Settings");
});
c2.appendChild(settingsButton);
c1.appendChild(c2);
buttonContainer.lastChild.insertBefore(
c1,
buttonContainer.lastChild.lastChild
);
}
function getSavedUserList() {
return JSON.parse(localStorage.getItem(LS_UserList) || "[]");
}
function addUserToSavedList(username) {
let userList = getSavedUserList();
if (!userList.includes(username)) {
userList.push(username);
localStorage.setItem(LS_UserList, JSON.stringify(userList));
} }
}
function saveNote(username, note) { const Mouse = {
addUserToSavedList(username); mousePosition: {x: 0, y: 0},
localStorage.setItem(LS_Prefix + username, note); lastMousePosition: {x: 0, y: 0},
} handleMouseMove: (event) => {
function getNote(username) { if (isMouseDown) {
return localStorage.getItem(LS_Prefix + username) || ""; if (activeContainer) {
} const dx = Mouse.mousePosition.x - Mouse.lastMousePosition.x;
const dy = Mouse.mousePosition.y - Mouse.lastMousePosition.y;
function handleMouseMove(event) { openContainers[activeContainer].style.top =
event = event || window.event; parseInt(openContainers[activeContainer].style.top) + dy + "px";
if (isMouseDown) { openContainers[activeContainer].style.left =
if (activeContainer) { parseInt(openContainers[activeContainer].style.left) + dx + "px";
const dx = mousePosition.x - lastMousePosition.x; }
const dy = mousePosition.y - lastMousePosition.y; }
openContainers[activeContainer].style.top = Mouse.updateMousePosition(event.clientX, event.clientY);
parseInt(openContainers[activeContainer].style.top) + dy + "px"; },
openContainers[activeContainer].style.left = handleMouseUp: () => {
parseInt(openContainers[activeContainer].style.left) + dx + "px"; activeContainer = null;
} isMouseDown = false;
},
updateMousePosition: (x, y) => {
Mouse.lastMousePosition = {...Mouse.mousePosition};
Mouse.mousePosition = {x, y};
}
} }
updateMousePosition(event.clientX, event.clientY);
}
function handleMouseUp(event) { function createElement(tag, body, classes, styles, attributes) {
activeContainer = null; const element = document.createElement(tag);
isMouseDown = false;
}
function updateMousePosition(x, y) { if (body) {
lastMousePosition = { ...mousePosition }; element.innerHTML = body;
mousePosition.x = x; }
mousePosition.y = y;
}
function removeContainer(username) { if (classes) {
if (!openContainers[username]) return; if (typeof classes === 'object') {
openContainers[username].remove(); for (let className of classes) {
delete openContainers[username]; element.classList.add((className));
} }
} else {
element.classList.add(classes);
}
}
function addContainer(username, container) { if (styles) {
if (openContainers[username]) return; if (typeof styles === 'object') {
openContainers[username] = container; for (let style in styles) {
document.body.appendChild(container); element.style[style] = styles[style];
} }
}
}
function openTwitchNote(username) { if (attributes) {
// CONTAINER if (typeof attributes === 'object') {
const container = document.createElement("div"); for (let attribute in attributes) {
container.style.left = mousePosition.x + "px"; element.setAttribute(attribute, attributes[attribute]);
container.style.top = mousePosition.y + 10 + "px"; }
container.classList.add("twitch-note-container"); }
}
// HEADER return element;
const header = document.createElement("div"); }
header.classList.add("twitch-note-header");
header.addEventListener("mousedown", function close() {
activeContainer = username;
isMouseDown = true;
});
const closeButton = document.createElement("span");
closeButton.classList.add("twitch-note-close-button");
closeButton.innerText = "X";
closeButton.addEventListener("click", function close() {
removeContainer(username);
});
header.appendChild(closeButton);
const title = document.createElement("span");
title.classList.add("twitch-note-title");
title.innerHTML = username;
header.appendChild(title);
container.appendChild(header);
// BODY function createSettingsButton(buttonContainer) {
const content = document.createElement("div");
content.classList.add("twitch-note-content");
content.setAttribute("contentEditable", true);
content.innerHTML = getNote(username);
container.appendChild(content); const c1 = createElement('div', null, null, {marginLeft: "0.5rem !important"});
const c2 = createElement('div', null, null, {display: "inline-flex !important"});
const settingsButton = createElement('button', 'Notes', 'twitch-notes-settings-button');
const saveButton = document.createElement("div"); settingsButton.addEventListener("click", toggleSettings);
saveButton.classList.add("twitch-note-save-button");
saveButton.innerText = "SAVE";
saveButton.addEventListener("click", function () {
saveNote(username, content.innerHTML);
removeContainer(username);
});
container.appendChild(saveButton); c2.appendChild(settingsButton);
c1.appendChild(c2);
addContainer(username, container); buttonContainer.lastChild.insertBefore(
} c1,
buttonContainer.lastChild.lastChild
);
}
let giveUpAt = Date.now() + 20000; function removeContainer(username) {
if (!openContainers[username]) return;
openContainers[username].remove();
delete openContainers[username];
}
let changeInProgress = false; function addContainer(username, container) {
if (openContainers[username]) return;
openContainers[username] = container;
document.body.appendChild(container);
}
let targetNode; function openTwitchNote(username) {
let buttonContainer;
do { const container = createElement('div', null, 'twitch-note-container', {
targetNode = document.getElementsByClassName( left: Mouse.mousePosition.x + 'px',
"chat-scrollable-area__message-container" top: Mouse.mousePosition.y + 10 + 'px'
)[0]; });
} while (!targetNode || giveUpAt < Date.now());
do { const header = createElement('div', null, 'twitch-note-header');
buttonContainer = document.getElementsByClassName( header.addEventListener("mousedown", function close() {
"chat-input__buttons-container" activeContainer = username;
)[0]; isMouseDown = true;
} while (!buttonContainer || giveUpAt < Date.now()); });
createSettingsButton(buttonContainer); const closeButton = createElement('span', "X", 'twitch-note-close-button')
closeButton.addEventListener("click", function close() {
removeContainer(username);
});
// Options for the observer (which mutations to observe) const title = createElement('span', username, 'twitch-note-title');
const config = { attributes: true, childList: true, subtree: true }; const content = createElement('div', Notes.getNote(username), 'twitch-note-content', [], {
contentEditable: 'true'
});
// Callback function to execute when mutations are observed const saveButton = createElement('div', 'SAVE', 'twitch-note-save-button')
const callback = (mutationList, observer) => { saveButton.addEventListener("click", function () {
if (!changeInProgress) { Notes.saveNote(username, content.innerHTML);
for (const mutation of mutationList) { removeContainer(username);
if (mutation.type === "childList") { });
changeInProgress = true;
let nodes = document.getElementsByClassName("chat-line__message"); header.appendChild(closeButton);
let users = []; header.appendChild(title);
for (let node of nodes) { container.appendChild(header);
container.appendChild(content);
container.appendChild(saveButton);
addContainer(username, container);
}
function addNoteBadges() {
let nodes = document.getElementsByClassName("chat-line__message");
let users = [];
for (let node of nodes) {
const n = node.querySelector(".chat-author__display-name"); const n = node.querySelector(".chat-author__display-name");
if (!n) continue; if (!n) continue;
const usernameContainer = node.querySelector( const usernameContainer = node.querySelector(
".chat-line__username-container" ".chat-line__username-container"
); );
const username = n.attributes["data-a-user"].value; const username = n.attributes["data-a-user"].value;
if (username) { if (username) {
let noteButton = usernameContainer.querySelector(".twitch-note"); let noteButton = usernameContainer.querySelector(".twitch-note");
if (!noteButton) { if (!noteButton) {
const twitchNote = document.createElement("span");
twitchNote.classList.add("twitch-note");
twitchNote.style.cursor = "pointer";
twitchNote.addEventListener("click", () => {
openTwitchNote(username);
});
const img = document.createElement("img"); const twitchNote = createElement('span', null, 'twitch-note', {
img.src = "https://cdn.rdarius.lt/icons/32-id-card.png"; cursor: 'pointer',
img.style.height = "18px"; })
img.style.paddingRight = "4px"; twitchNote.addEventListener("click", () => {
twitchNote.appendChild(img); openTwitchNote(username);
});
usernameContainer.insertBefore( const img = createElement('img', null, null, {
twitchNote, height: '18px',
usernameContainer.firstChild paddingRight: '4px'
); }, {
} src: "https://cdn.rdarius.lt/icons/32-id-card.png"
if (!users[username]) { })
users[username] = 0;
} twitchNote.appendChild(img);
users[username]++;
usernameContainer.insertBefore(
twitchNote,
usernameContainer.firstChild
);
}
if (!users[username]) {
users[username] = 0;
}
users[username]++;
} }
}
changeInProgress = false;
} }
}
} }
};
// Create an observer instance linked to the callback function function toggleSettings() {
const observer = new MutationObserver(callback); console.log('toggle settings');
}
// Start observing the target node for configured mutations let openContainers = {};
observer.observe(targetNode, config); let isMouseDown = false;
let activeContainer = null;
// let settingsWindowOpen = false;
let LS_UserList = "twitch-note-all-users-list";
let LS_Prefix = "twitch-note-";
document.addEventListener("mousemove", Mouse.handleMouseMove);
document.addEventListener("mouseup", Mouse.handleMouseUp);
let giveUpAt = Date.now() + 20000;
let changeInProgress = false;
let targetNode;
let buttonContainer;
do {
targetNode = document.getElementsByClassName(
"chat-scrollable-area__message-container"
)[0];
} while (!targetNode || giveUpAt < Date.now());
do {
buttonContainer = document.getElementsByClassName(
"chat-input__buttons-container"
)[0];
} while (!buttonContainer || giveUpAt < Date.now());
createSettingsButton(buttonContainer);
// Options for the observer (which mutations to observe)
const config = {attributes: true, childList: true, subtree: true};
// Callback function to execute when mutations are observed
const callback = (mutationList) => {
if (!changeInProgress) {
for (const mutation of mutationList) {
if (mutation.type === "childList") {
changeInProgress = true;
addNoteBadges();
changeInProgress = false;
}
}
}
};
// Create an observer instance linked to the callback function
const observer = new MutationObserver(callback);
// Start observing the target node for configured mutations
observer.observe(targetNode, config);
})(); })();