mirror of
https://github.com/nuttylmao/nutty.gg.git
synced 2026-09-19 04:00:59 -04:00
Updated to new Settings page
This commit is contained in:
@@ -2,49 +2,51 @@
|
|||||||
<html lang="en">
|
<html lang="en">
|
||||||
|
|
||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8">
|
<meta charset="UTF-8">
|
||||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||||
<link rel="icon" href="../../.resources/logo.png" type="image/png">
|
<title>Settings</title>
|
||||||
<title>Settings</title>
|
<link rel="stylesheet" href="style.css">
|
||||||
<link rel="stylesheet" href="style.css">
|
<script type="text/javascript" src="https://unpkg.com/@streamerbot/client/dist/streamerbot-client.js"></script>
|
||||||
<script type="text/javascript" src="https://unpkg.com/@streamerbot/client/dist/streamerbot-client.js"></script>
|
|
||||||
</head>
|
</head>
|
||||||
|
|
||||||
<body>
|
<body>
|
||||||
|
<!-- Header -->
|
||||||
<div id="pinned-header">
|
<div id="header">
|
||||||
<div style="display: flex; align-items: center; padding-bottom: 20px;">
|
<img src="../../.resources/logo.png" style="height: 40px;" />
|
||||||
<img src="../../.resources/logo.png" style="height: 40px;"/>
|
<button id="membershipsButton" onclick="OpenMembershipPage()">Check out my member exclusive widgets!</button>
|
||||||
<button style="display: flex; width: auto; margin-left: auto; background: var(--accent-color);" onclick="OpenMembershipPage()">Check out my premium widgets</button>
|
<div id="widgetUrlInputWrapper">
|
||||||
</div>
|
<span id="urlLabel">Click to copy URL</span>
|
||||||
<h2>Widget URL</h2>
|
<input id="widgetUrlInput" type="text" readonly onclick="CopyURLToClipboard()">
|
||||||
<input id="widget-url" type="text" readonly onfocus="this.select();">
|
</div>
|
||||||
<div style="display: flex; gap: 10px;">
|
<button id="loadSettingsButton" onclick="OpenLoadSettingsPopup()">Load Settings</button>
|
||||||
<button id="save-settings">Click to copy URL</button>
|
|
||||||
<button onclick="OpenLoadSettingsPopup()">Load Settings</button>
|
|
||||||
</div>
|
|
||||||
<!-- <button onclick="OpenMembershipPage()">💎 Member Exclusive Widgets</button> -->
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div id="settings-container">
|
|
||||||
<div id="settings-content"></div>
|
|
||||||
</div>
|
|
||||||
<script src="script.js"></script>
|
|
||||||
|
|
||||||
<div id="mommy-milkers">
|
|
||||||
<div id="load-settings-container">
|
|
||||||
<h2>Load Settings</h2>
|
|
||||||
<label style="font-size: 0.8em;">Paste in your existing widget URL</label>
|
|
||||||
<input id="load-url" type="text">
|
|
||||||
<div style="display: flex;">
|
|
||||||
<button id="cancel-settings" onclick="CloseSettings()">Cancel</button>
|
|
||||||
<span style="width: 20px;"></span>
|
|
||||||
<button id="load-settings" onclick="LoadSettings()">Load Settings</button>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
</div>
|
<!-- Main Content Area -->
|
||||||
|
<div id="contentArea">
|
||||||
|
|
||||||
|
<!-- Settings Panel -->
|
||||||
|
<div id="settingsPanel">
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<!-- Widget Preview Panel -->
|
||||||
|
<iframe id="widgetPreview">
|
||||||
|
</iframe>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<!-- Load Settings Popup -->
|
||||||
|
<div id="loadSettingsWrapper">
|
||||||
|
<div id="loadSettingsContainer">
|
||||||
|
<h2>Load Settings</h2>
|
||||||
|
<label style="font-size: 0.8em;">Paste in your existing widget URL</label>
|
||||||
|
<input id="loadUrlBox" type="text" style="width: 100%;">
|
||||||
|
<div style="display: flex; gap: 20px">
|
||||||
|
<button id="cancelSettingsButton" onclick="CloseSettings()">Cancel</button>
|
||||||
|
<button style="background-color: var(--accent-color);" onclick="LoadSettings()">Load Settings</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</body>
|
</body>
|
||||||
|
|
||||||
</html>
|
</html>
|
||||||
|
|
||||||
|
<script src="script.js"></script>
|
||||||
@@ -2,6 +2,231 @@
|
|||||||
const queryString = window.location.search;
|
const queryString = window.location.search;
|
||||||
const urlParams = new URLSearchParams(queryString);
|
const urlParams = new URLSearchParams(queryString);
|
||||||
const settingsJson = urlParams.get("settingsJson") || "";
|
const settingsJson = urlParams.get("settingsJson") || "";
|
||||||
|
const widgetURL = urlParams.get("widgetURL") || "";
|
||||||
|
|
||||||
|
// Page elements
|
||||||
|
const widgetUrlInputWrapper = document.getElementById('widgetUrlInputWrapper');
|
||||||
|
const widgetUrlInput = document.getElementById('widgetUrlInput');
|
||||||
|
const urlLabel = document.getElementById('urlLabel');
|
||||||
|
const settingsPanel = document.getElementById('settingsPanel');
|
||||||
|
const widgetPreview = document.getElementById('widgetPreview');
|
||||||
|
const loadURLBox = document.getElementById('loadUrlBox');
|
||||||
|
const cancelSettingsButton = document.getElementById('cancelSettingsButton');
|
||||||
|
const loadSettingsBox = document.getElementById('loadSettingsWrapper');
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
/////////////////////////////
|
||||||
|
// LOAD FROM SETTINGS.JSON //
|
||||||
|
/////////////////////////////
|
||||||
|
|
||||||
|
fetch(settingsJson)
|
||||||
|
.then(response => response.json())
|
||||||
|
.then(data => {
|
||||||
|
const groupedSettings = {};
|
||||||
|
|
||||||
|
// Group settings by their 'group' property
|
||||||
|
data.settings.forEach(setting => {
|
||||||
|
if (!groupedSettings[setting.group]) {
|
||||||
|
groupedSettings[setting.group] = [];
|
||||||
|
}
|
||||||
|
groupedSettings[setting.group].push(setting);
|
||||||
|
});
|
||||||
|
|
||||||
|
// Render settings for each group
|
||||||
|
for (const groupName in groupedSettings) {
|
||||||
|
const groupDiv = document.createElement('div');
|
||||||
|
groupDiv.classList.add('setting-group');
|
||||||
|
|
||||||
|
const groupHeader = document.createElement('h2');
|
||||||
|
groupHeader.textContent = groupName;
|
||||||
|
groupDiv.appendChild(groupHeader);
|
||||||
|
|
||||||
|
groupedSettings[groupName].forEach(setting => {
|
||||||
|
const settingItem = document.createElement('div');
|
||||||
|
settingItem.classList.add('setting-item');
|
||||||
|
settingItem.id = `item-${setting.id}`;
|
||||||
|
|
||||||
|
const labelDescriptionDiv = document.createElement('div');
|
||||||
|
|
||||||
|
if (setting.label) {
|
||||||
|
const label = document.createElement('label');
|
||||||
|
label.textContent = setting.label;
|
||||||
|
labelDescriptionDiv.appendChild(label);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (setting.description) {
|
||||||
|
const description = document.createElement('p');
|
||||||
|
description.innerHTML = setting.description;
|
||||||
|
labelDescriptionDiv.appendChild(description);
|
||||||
|
}
|
||||||
|
|
||||||
|
const settingItemContent = document.createElement('div');
|
||||||
|
settingItemContent.classList.add('setting-item-content');
|
||||||
|
|
||||||
|
let inputElement;
|
||||||
|
switch (setting.type) {
|
||||||
|
case 'text':
|
||||||
|
inputElement = document.createElement('input');
|
||||||
|
inputElement.type = 'text';
|
||||||
|
inputElement.id = setting.id; //Added setting ID
|
||||||
|
inputElement.value = setting.defaultValue;
|
||||||
|
break;
|
||||||
|
case 'checkbox':
|
||||||
|
const labelDiv = document.createElement('label');
|
||||||
|
labelDiv.classList.add('switch');
|
||||||
|
checkBoxElement = document.createElement('input');
|
||||||
|
checkBoxElement.type = 'checkbox';
|
||||||
|
checkBoxElement.id = setting.id;
|
||||||
|
checkBoxElement.checked = setting.defaultValue;
|
||||||
|
labelDiv.appendChild(checkBoxElement);
|
||||||
|
|
||||||
|
const slider = document.createElement('span');
|
||||||
|
slider.classList.add('slider');
|
||||||
|
slider.classList.add('round');
|
||||||
|
labelDiv.appendChild(slider);
|
||||||
|
|
||||||
|
// Add event listener to the switchDiv
|
||||||
|
labelDiv.addEventListener('click', () => {
|
||||||
|
checkBoxElement.checked = !checkBoxElement.checked;
|
||||||
|
UpdateSettingItemVisibility();
|
||||||
|
});
|
||||||
|
inputElement = labelDiv;
|
||||||
|
break;
|
||||||
|
case 'select':
|
||||||
|
inputElement = document.createElement('select');
|
||||||
|
inputElement.id = setting.id; //Added setting ID
|
||||||
|
setting.options.forEach(option => {
|
||||||
|
const optionElement = document.createElement('option');
|
||||||
|
optionElement.value = option.value;
|
||||||
|
optionElement.textContent = option.label;
|
||||||
|
if (option === setting.defaultValue) {
|
||||||
|
optionElement.selected = true;
|
||||||
|
}
|
||||||
|
inputElement.appendChild(optionElement);
|
||||||
|
});
|
||||||
|
inputElement.value = setting.defaultValue;
|
||||||
|
break;
|
||||||
|
case 'color':
|
||||||
|
inputElement = document.createElement('input');
|
||||||
|
inputElement.type = 'color';
|
||||||
|
inputElement.id = setting.id; //Added setting ID
|
||||||
|
inputElement.value = setting.defaultValue;
|
||||||
|
break;
|
||||||
|
case 'number':
|
||||||
|
inputElement = document.createElement('input');
|
||||||
|
inputElement.type = 'number';
|
||||||
|
inputElement.id = setting.id; //Added setting ID
|
||||||
|
inputElement.value = setting.defaultValue;
|
||||||
|
inputElement.min = setting.min;
|
||||||
|
inputElement.max = setting.max;
|
||||||
|
inputElement.step = setting.step;
|
||||||
|
break;
|
||||||
|
case 'sb-actions':
|
||||||
|
inputElement = document.createElement('input');
|
||||||
|
inputElement.type = 'text';
|
||||||
|
inputElement.placeholder = 'Type to search...';
|
||||||
|
inputElement.id = setting.id; //Added setting ID
|
||||||
|
inputElement.value = setting.defaultValue;
|
||||||
|
inputElement.setAttribute('list', 'streamer-bot-actions');
|
||||||
|
inputElement.autocomplete = 'off';
|
||||||
|
break;
|
||||||
|
case 'button':
|
||||||
|
inputElement = document.createElement('button');
|
||||||
|
inputElement.id = setting.id; //Added setting ID
|
||||||
|
inputElement.textContent = setting.label;
|
||||||
|
|
||||||
|
inputElement.addEventListener('click', () => {
|
||||||
|
widgetPreview.contentWindow.callFunction(setting.callFunction);
|
||||||
|
|
||||||
|
const defaultBackgroundColor = "#2e2e2e";
|
||||||
|
const defaultTextColor = "white";
|
||||||
|
|
||||||
|
inputElement.style.transitionDuration = '0s'
|
||||||
|
inputElement.style.backgroundColor = "#2196f3"
|
||||||
|
inputElement.style.color = "#ffffff";
|
||||||
|
|
||||||
|
setTimeout(() => {
|
||||||
|
inputElement.style.transitionDuration = '0.2s'
|
||||||
|
inputElement.style.backgroundColor = defaultBackgroundColor;
|
||||||
|
inputElement.style.color = defaultTextColor;
|
||||||
|
}, 100);
|
||||||
|
});
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
inputElement = document.createElement('input');
|
||||||
|
inputElement.type = 'text';
|
||||||
|
inputElement.id = setting.id; //Added setting ID
|
||||||
|
inputElement.value = setting.defaultValue;
|
||||||
|
}
|
||||||
|
|
||||||
|
inputElement.addEventListener('input', function (event) {
|
||||||
|
RefreshWidgetPreview(data);
|
||||||
|
});
|
||||||
|
|
||||||
|
settingItemContent.appendChild(inputElement);
|
||||||
|
|
||||||
|
if (setting.type == 'button') {
|
||||||
|
settingItem.style.display = 'block'
|
||||||
|
settingItem.appendChild(settingItemContent);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
settingItem.appendChild(labelDescriptionDiv);
|
||||||
|
settingItem.appendChild(settingItemContent);
|
||||||
|
}
|
||||||
|
|
||||||
|
groupDiv.appendChild(settingItem);
|
||||||
|
});
|
||||||
|
|
||||||
|
settingsPanel.appendChild(groupDiv);
|
||||||
|
}
|
||||||
|
|
||||||
|
function UpdateSettingItemVisibility() {
|
||||||
|
data.settings.forEach(setting => {
|
||||||
|
if (setting.showIf) {
|
||||||
|
if (!document.getElementById(setting.showIf).checked)
|
||||||
|
document.getElementById(`item-${setting.id}`).style.display = 'none'
|
||||||
|
else
|
||||||
|
document.getElementById(`item-${setting.id}`).style.display = 'flex'
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
UpdateSettingItemVisibility();
|
||||||
|
RefreshWidgetPreview(data);
|
||||||
|
})
|
||||||
|
.catch(error => console.error('Error loading settings:', error));
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
function RefreshWidgetPreview(data) {
|
||||||
|
const settings = {};
|
||||||
|
data.settings.forEach(setting => {
|
||||||
|
let inputElement = document.getElementById(setting.id);
|
||||||
|
|
||||||
|
if (setting.type === 'checkbox') {
|
||||||
|
settings[setting.id] = inputElement.checked;
|
||||||
|
} else {
|
||||||
|
settings[setting.id] = inputElement.value;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// Generate parameter string
|
||||||
|
const paramString = Object.entries(settings)
|
||||||
|
.map(([key, value]) => `${encodeURIComponent(key)}=${encodeURIComponent(value)}`)
|
||||||
|
.join('&');
|
||||||
|
|
||||||
|
console.debug('Parameter String:', paramString);
|
||||||
|
|
||||||
|
widgetUrlInput.value = widgetURL + "?" + paramString;
|
||||||
|
widgetPreview.src = widgetUrlInput.value;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
//////////////////
|
||||||
|
// STREAMER.BOT //
|
||||||
|
//////////////////
|
||||||
|
|
||||||
// Connect to Streamer.bot and get list of actions
|
// Connect to Streamer.bot and get list of actions
|
||||||
const sbServerAddress = '127.0.0.1';
|
const sbServerAddress = '127.0.0.1';
|
||||||
@@ -14,8 +239,8 @@ const client = new StreamerbotClient({
|
|||||||
console.log(`Streamer.bot successfully connected to ${sbServerAddress}:${sbServerPort}`)
|
console.log(`Streamer.bot successfully connected to ${sbServerAddress}:${sbServerPort}`)
|
||||||
console.debug(data);
|
console.debug(data);
|
||||||
|
|
||||||
// Get list of actions
|
// Get list of actions
|
||||||
GetSBActions();
|
GetSBActions();
|
||||||
},
|
},
|
||||||
|
|
||||||
onDisconnect: () => {
|
onDisconnect: () => {
|
||||||
@@ -24,310 +249,96 @@ const client = new StreamerbotClient({
|
|||||||
});
|
});
|
||||||
|
|
||||||
async function GetSBActions() {
|
async function GetSBActions() {
|
||||||
const response = await client.getActions();
|
const response = await client.getActions();
|
||||||
|
|
||||||
console.debug(response);
|
console.debug(response);
|
||||||
|
|
||||||
const datalistElement = document.createElement('datalist');
|
const datalistElement = document.createElement('datalist');
|
||||||
datalistElement.id = 'streamer-bot-actions';
|
datalistElement.id = 'streamer-bot-actions';
|
||||||
|
|
||||||
for (const action of response.actions)
|
for (const action of response.actions) {
|
||||||
{
|
const option = document.createElement('option');
|
||||||
const option = document.createElement('option');
|
option.value = action.name;
|
||||||
option.value = action.name;
|
datalistElement.appendChild(option);
|
||||||
datalistElement.appendChild(option);
|
}
|
||||||
}
|
|
||||||
|
|
||||||
document.body.appendChild(datalistElement);
|
document.body.appendChild(datalistElement);
|
||||||
}
|
|
||||||
|
|
||||||
document.addEventListener('DOMContentLoaded', () => {
|
|
||||||
|
|
||||||
const settingsContent = document.getElementById('settings-content');
|
|
||||||
const saveButton = document.getElementById('save-settings');
|
|
||||||
|
|
||||||
fetch(settingsJson)
|
|
||||||
.then(response => response.json())
|
|
||||||
.then(data => {
|
|
||||||
const groupedSettings = {};
|
|
||||||
|
|
||||||
// Group settings by their 'group' property
|
|
||||||
data.settings.forEach(setting => {
|
|
||||||
if (!groupedSettings[setting.group]) {
|
|
||||||
groupedSettings[setting.group] = [];
|
|
||||||
}
|
|
||||||
groupedSettings[setting.group].push(setting);
|
|
||||||
});
|
|
||||||
|
|
||||||
// Render settings for each group
|
|
||||||
for (const groupName in groupedSettings) {
|
|
||||||
const groupDiv = document.createElement('div');
|
|
||||||
groupDiv.classList.add('setting-group');
|
|
||||||
|
|
||||||
const groupHeader = document.createElement('h2');
|
|
||||||
groupHeader.textContent = groupName;
|
|
||||||
groupDiv.appendChild(groupHeader);
|
|
||||||
|
|
||||||
groupedSettings[groupName].forEach(setting => {
|
|
||||||
const settingItem = document.createElement('div');
|
|
||||||
settingItem.classList.add('setting-item');
|
|
||||||
settingItem.id = `item-${setting.id}`;
|
|
||||||
|
|
||||||
const labelDescriptionDiv = document.createElement('div');
|
|
||||||
|
|
||||||
if (setting.label) {
|
|
||||||
const label = document.createElement('label');
|
|
||||||
label.textContent = setting.label;
|
|
||||||
labelDescriptionDiv.appendChild(label);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (setting.description) {
|
|
||||||
const description = document.createElement('p');
|
|
||||||
description.innerHTML = setting.description;
|
|
||||||
labelDescriptionDiv.appendChild(description);
|
|
||||||
}
|
|
||||||
|
|
||||||
const settingItemContent = document.createElement('div');
|
|
||||||
settingItemContent.classList.add('setting-item-content');
|
|
||||||
|
|
||||||
let inputElement;
|
|
||||||
switch (setting.type) {
|
|
||||||
case 'text':
|
|
||||||
inputElement = document.createElement('input');
|
|
||||||
inputElement.type = 'text';
|
|
||||||
inputElement.id = setting.id; //Added setting ID
|
|
||||||
inputElement.value = setting.defaultValue;
|
|
||||||
break;
|
|
||||||
case 'checkbox':
|
|
||||||
const labelDiv = document.createElement('label');
|
|
||||||
labelDiv.classList.add('switch');
|
|
||||||
checkBoxElement = document.createElement('input');
|
|
||||||
checkBoxElement.type = 'checkbox';
|
|
||||||
checkBoxElement.id = setting.id;
|
|
||||||
checkBoxElement.checked = setting.defaultValue;
|
|
||||||
labelDiv.appendChild(checkBoxElement);
|
|
||||||
|
|
||||||
const slider = document.createElement('span');
|
|
||||||
slider.classList.add('slider');
|
|
||||||
slider.classList.add('round');
|
|
||||||
labelDiv.appendChild(slider);
|
|
||||||
|
|
||||||
// Add event listener to the switchDiv
|
|
||||||
labelDiv.addEventListener('click', () => {
|
|
||||||
checkBoxElement.checked = !checkBoxElement.checked;
|
|
||||||
UpdateSettingItemVisibility();
|
|
||||||
});
|
|
||||||
inputElement = labelDiv;
|
|
||||||
break;
|
|
||||||
case 'select':
|
|
||||||
inputElement = document.createElement('select');
|
|
||||||
inputElement.id = setting.id; //Added setting ID
|
|
||||||
setting.options.forEach(option => {
|
|
||||||
const optionElement = document.createElement('option');
|
|
||||||
optionElement.value = option.value;
|
|
||||||
optionElement.textContent = option.label;
|
|
||||||
if (option === setting.defaultValue) {
|
|
||||||
optionElement.selected = true;
|
|
||||||
}
|
|
||||||
inputElement.appendChild(optionElement);
|
|
||||||
});
|
|
||||||
inputElement.value = setting.defaultValue;
|
|
||||||
break;
|
|
||||||
case 'color':
|
|
||||||
inputElement = document.createElement('input');
|
|
||||||
inputElement.type = 'color';
|
|
||||||
inputElement.id = setting.id; //Added setting ID
|
|
||||||
inputElement.value = setting.defaultValue;
|
|
||||||
break;
|
|
||||||
case 'number':
|
|
||||||
inputElement = document.createElement('input');
|
|
||||||
inputElement.type = 'number';
|
|
||||||
inputElement.id = setting.id; //Added setting ID
|
|
||||||
inputElement.value = setting.defaultValue;
|
|
||||||
inputElement.min = setting.min;
|
|
||||||
inputElement.max = setting.max;
|
|
||||||
inputElement.step = setting.step;
|
|
||||||
break;
|
|
||||||
case 'sb-actions':
|
|
||||||
inputElement = document.createElement('input');
|
|
||||||
inputElement.type = 'text';
|
|
||||||
inputElement.placeholder = 'Type to search...';
|
|
||||||
inputElement.id = setting.id; //Added setting ID
|
|
||||||
inputElement.value = setting.defaultValue;
|
|
||||||
inputElement.setAttribute('list', 'streamer-bot-actions');
|
|
||||||
inputElement.autocomplete = 'off';
|
|
||||||
break;
|
|
||||||
case 'button':
|
|
||||||
inputElement = document.createElement('button');
|
|
||||||
inputElement.id = setting.id; //Added setting ID
|
|
||||||
inputElement.textContent = setting.label;
|
|
||||||
|
|
||||||
inputElement.addEventListener('click', () => {
|
|
||||||
window.parent.callFunction(setting.callFunction);
|
|
||||||
|
|
||||||
const defaultBackgroundColor = "#2e2e2e";
|
|
||||||
const defaultTextColor = "white";
|
|
||||||
|
|
||||||
inputElement.style.transitionDuration = '0s'
|
|
||||||
inputElement.style.backgroundColor = "#2196f3"
|
|
||||||
inputElement.style.color = "#ffffff";
|
|
||||||
|
|
||||||
setTimeout(() => {
|
|
||||||
inputElement.style.transitionDuration = '0.2s'
|
|
||||||
inputElement.style.backgroundColor = defaultBackgroundColor;
|
|
||||||
inputElement.style.color = defaultTextColor;
|
|
||||||
}, 100);
|
|
||||||
});
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
inputElement = document.createElement('input');
|
|
||||||
inputElement.type = 'text';
|
|
||||||
inputElement.id = setting.id; //Added setting ID
|
|
||||||
inputElement.value = setting.defaultValue;
|
|
||||||
}
|
|
||||||
|
|
||||||
inputElement.addEventListener('input', function (event) {
|
|
||||||
SendDataToParent(data);
|
|
||||||
});
|
|
||||||
|
|
||||||
settingItemContent.appendChild(inputElement);
|
|
||||||
|
|
||||||
if (setting.type == 'button')
|
|
||||||
{
|
|
||||||
settingItem.style.display = 'block'
|
|
||||||
settingItem.appendChild(settingItemContent);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
settingItem.appendChild(labelDescriptionDiv);
|
|
||||||
settingItem.appendChild(settingItemContent);
|
|
||||||
}
|
|
||||||
|
|
||||||
groupDiv.appendChild(settingItem);
|
|
||||||
});
|
|
||||||
|
|
||||||
settingsContent.appendChild(groupDiv);
|
|
||||||
}
|
|
||||||
|
|
||||||
function UpdateSettingItemVisibility() {
|
|
||||||
data.settings.forEach(setting => {
|
|
||||||
if (setting.showIf)
|
|
||||||
{
|
|
||||||
if (!document.getElementById(setting.showIf).checked)
|
|
||||||
document.getElementById(`item-${setting.id}`).style.display = 'none'
|
|
||||||
else
|
|
||||||
document.getElementById(`item-${setting.id}`).style.display = 'flex'
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
UpdateSettingItemVisibility();
|
|
||||||
|
|
||||||
// saveButton.addEventListener('click', () => {
|
|
||||||
// SendDataToParent(data);
|
|
||||||
// });
|
|
||||||
SendDataToParent(data);
|
|
||||||
})
|
|
||||||
.catch(error => console.error('Error loading settings:', error));
|
|
||||||
});
|
|
||||||
|
|
||||||
|
|
||||||
// In the iframe's JavaScript:
|
|
||||||
function SendDataToParent(data) {
|
|
||||||
const settings = {};
|
|
||||||
data.settings.forEach(setting => {
|
|
||||||
let inputElement = document.getElementById(setting.id);
|
|
||||||
|
|
||||||
if (setting.type === 'checkbox') {
|
|
||||||
settings[setting.id] = inputElement.checked;
|
|
||||||
} else {
|
|
||||||
settings[setting.id] = inputElement.value;
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
// Generate parameter string
|
|
||||||
const paramString = Object.entries(settings)
|
|
||||||
.map(([key, value]) => `${encodeURIComponent(key)}=${encodeURIComponent(value)}`)
|
|
||||||
.join('&');
|
|
||||||
|
|
||||||
console.log('Parameter String:', paramString);
|
|
||||||
|
|
||||||
let widgetURLBox = document.getElementById('widget-url');
|
|
||||||
widgetURLBox.value = GetWidgetURL() + "?" + paramString;
|
|
||||||
window.parent.reloadWidget(paramString);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
let saveButton = document.getElementById('save-settings');
|
|
||||||
let widgetURLBox = document.getElementById('widget-url');
|
|
||||||
let cancelSettingsButton = document.getElementById('cancel-settings');
|
|
||||||
|
|
||||||
saveButton.addEventListener('click', () => {
|
/////////////////////////
|
||||||
navigator.clipboard.writeText(widgetURLBox.value);
|
// BUTTON CLICK EVENTS //
|
||||||
|
/////////////////////////
|
||||||
|
|
||||||
const defaultBackgroundColor = "#2e2e2e";
|
function CopyURLToClipboard() {
|
||||||
const defaultTextColor = "white";
|
// Copy to clipboard
|
||||||
|
navigator.clipboard.writeText(widgetUrlInput.value);
|
||||||
|
|
||||||
saveButton.innerText = "Copied to clipboard";
|
// Create the "Copied!" message
|
||||||
saveButton.style.backgroundColor = "#00dd63"
|
const copiedMessage = document.createElement('span');
|
||||||
saveButton.style.color = "#ffffff";
|
copiedMessage.textContent = 'Copied to clipboard!';
|
||||||
|
copiedMessage.style.textAlign = 'center';
|
||||||
|
copiedMessage.style.fontWeight = 'absolute';
|
||||||
|
copiedMessage.style.position = 'absolute';
|
||||||
|
copiedMessage.style.top = '50%';
|
||||||
|
copiedMessage.style.left = '50%';
|
||||||
|
copiedMessage.style.transform = 'translate(-50%, -50%)';
|
||||||
|
copiedMessage.style.backgroundColor = '#00dd63'; // Green with some transparency
|
||||||
|
copiedMessage.style.color = 'white';
|
||||||
|
copiedMessage.style.padding = '5px 10px';
|
||||||
|
copiedMessage.style.borderRadius = '5px';
|
||||||
|
copiedMessage.style.zIndex = '2'; // Ensure it's above the input and label
|
||||||
|
copiedMessage.style.opacity = '0'; // Start with opacity 0 for fade-in
|
||||||
|
copiedMessage.style.transition = 'opacity 0.2s ease-in-out';
|
||||||
|
|
||||||
setTimeout(() => {
|
widgetUrlInputWrapper.appendChild(copiedMessage);
|
||||||
saveButton.innerText = "Click to copy URL";
|
|
||||||
saveButton.style.backgroundColor = defaultBackgroundColor;
|
// Force a reflow to trigger the transition
|
||||||
saveButton.style.color = defaultTextColor;
|
void copiedMessage.offsetWidth;
|
||||||
}, 3000);
|
|
||||||
});
|
// Fade in the message
|
||||||
|
copiedMessage.style.opacity = '1';
|
||||||
|
|
||||||
|
// Fade out and remove the message after 3 seconds
|
||||||
|
setTimeout(() => {
|
||||||
|
copiedMessage.style.opacity = '0';
|
||||||
|
setTimeout(() => {
|
||||||
|
widgetUrlInputWrapper.removeChild(copiedMessage);
|
||||||
|
}, 500); // Wait for the fade-out
|
||||||
|
}, 5000);
|
||||||
|
}
|
||||||
|
|
||||||
function CloseSettings() {
|
function CloseSettings() {
|
||||||
let loadSettingsBox = document.getElementById('mommy-milkers');
|
loadSettingsBox.style.visibility = 'hidden';
|
||||||
loadSettingsBox.style.visibility = 'hidden';
|
loadSettingsBox.style.opacity = 0;
|
||||||
loadSettingsBox.style.opacity = 0;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
function LoadSettings() {
|
function LoadSettings() {
|
||||||
let loadURLBox = document.getElementById('load-url');
|
const url = new URL(loadURLBox.value);
|
||||||
const url = new URL(loadURLBox.value);
|
|
||||||
|
|
||||||
url.searchParams.forEach((value, key) => {
|
url.searchParams.forEach((value, key) => {
|
||||||
|
|
||||||
const inputElement = document.getElementById(key);
|
const inputElement = document.getElementById(key);
|
||||||
if (inputElement != null) {
|
if (inputElement != null) {
|
||||||
if (inputElement.type == 'checkbox')
|
if (inputElement.type == 'checkbox')
|
||||||
inputElement.checked = value.toLocaleLowerCase() == 'true';
|
inputElement.checked = value.toLocaleLowerCase() == 'true';
|
||||||
else
|
else
|
||||||
inputElement.value = value;
|
inputElement.value = value;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
loadURLBox.value = '';
|
loadURLBox.value = '';
|
||||||
|
|
||||||
let loadSettingsBox = document.getElementById('mommy-milkers');
|
loadSettingsBox.style.visibility = 'hidden';
|
||||||
loadSettingsBox.style.visibility = 'hidden';
|
loadSettingsBox.style.opacity = 0;
|
||||||
loadSettingsBox.style.opacity = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
function GetWidgetURL() {
|
|
||||||
const parsedUrl = new URL(settingsJson);
|
|
||||||
|
|
||||||
let result = parsedUrl.origin; // Base domain (protocol + hostname + port)
|
|
||||||
|
|
||||||
const pathSegments = parsedUrl.pathname.split('/').filter(segment => segment); // Split and remove empty segments
|
|
||||||
|
|
||||||
if (pathSegments.length > 0) {
|
|
||||||
result += '/' + pathSegments[0]; // Add the first path segment
|
|
||||||
}
|
|
||||||
|
|
||||||
return result;
|
|
||||||
//return 'D:/Projects/GitHub Projects/nutty.gg/multistream-alerts/index.html'
|
|
||||||
}
|
}
|
||||||
|
|
||||||
function OpenMembershipPage() {
|
function OpenMembershipPage() {
|
||||||
window.open("https://nutty.gg/supporters/sign_in", '_blank').focus();
|
window.open("https://nutty.gg/collections/member-exclusive-widgets", '_blank').focus();
|
||||||
}
|
}
|
||||||
|
|
||||||
function OpenLoadSettingsPopup() {
|
function OpenLoadSettingsPopup() {
|
||||||
let loadSettingsBox = document.getElementById('mommy-milkers');
|
loadSettingsBox.style.visibility = 'visible';
|
||||||
loadSettingsBox.style.visibility = 'visible';
|
loadSettingsBox.style.opacity = 1;
|
||||||
loadSettingsBox.style.opacity = 1;
|
|
||||||
}
|
}
|
||||||
@@ -1,273 +1,346 @@
|
|||||||
* {
|
* {
|
||||||
font-family: -apple-system, BlinkMacSystemFont, Segoe UI, Roboto, Helvetica, Arial, sans-serif;
|
font-family: -apple-system, BlinkMacSystemFont, Segoe UI, Roboto, Helvetica, Arial, sans-serif;
|
||||||
font-size: 16px;
|
font-size: 16px;
|
||||||
color: white;
|
font-weight: 500;
|
||||||
--accent-color: #2196f3;
|
color: white;
|
||||||
|
--accent-color: #2196f3;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
html,
|
||||||
body {
|
body {
|
||||||
background-color: #181818;
|
background-color: #181818;
|
||||||
margin: 0px 20px;
|
margin: 0px 0px;
|
||||||
|
display: flex;
|
||||||
|
flex-flow: column;
|
||||||
|
height: 100%;
|
||||||
|
overflow: hidden;
|
||||||
|
/* Prevent overall page scroll */
|
||||||
}
|
}
|
||||||
|
|
||||||
body::-webkit-scrollbar {
|
#header {
|
||||||
width: 8px;
|
display: flex;
|
||||||
/* Width of the entire scrollbar */
|
flex-direction: row;
|
||||||
|
gap: 10px;
|
||||||
|
align-items: center;
|
||||||
|
padding: 0px 20px;
|
||||||
|
box-shadow: 0px 0px 10px rgba(0, 0, 0, 1);
|
||||||
|
/* Add the shadow */
|
||||||
|
z-index: 1;
|
||||||
|
/* Ensure the shadow isn't hidden by content */
|
||||||
}
|
}
|
||||||
|
|
||||||
body::-webkit-scrollbar-track {
|
#contentArea {
|
||||||
background: #2c2c2c;
|
display: flex;
|
||||||
/* Color of the tracking area */
|
flex-direction: row;
|
||||||
|
flex-grow: 1;
|
||||||
|
overflow: hidden;
|
||||||
|
/* Prevent overall page scroll */
|
||||||
}
|
}
|
||||||
|
|
||||||
body::-webkit-scrollbar-thumb {
|
#header > button {
|
||||||
background-color: #9f9f9f;
|
width: auto;
|
||||||
/* Color of the scroll thumb */
|
/* Allow buttons to size based on content */
|
||||||
border-radius: 4px;
|
flex-shrink: 0;
|
||||||
/* Roundness of the scroll thumb */
|
/* Prevent buttons from shrinking */
|
||||||
border: none;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
body::-webkit-scrollbar-thumb:hover {
|
#membershipsButton {
|
||||||
background-color: #d1d1d1;
|
background: var(--accent-color);
|
||||||
/* Color of the scroll thumb on hover */
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#pinned-header {
|
#settingsPanel {
|
||||||
position: sticky;
|
width: 600px;
|
||||||
top: 0;
|
overflow-y: auto;
|
||||||
margin: 40px auto;
|
height: 100%;
|
||||||
padding: 10px 0;
|
padding: 0px 20px;
|
||||||
z-index: 100;
|
box-shadow: 0px 0px 10px rgba(0, 0, 0, 1);
|
||||||
background: #181818af;
|
|
||||||
backdrop-filter: blur(10px);
|
|
||||||
-webkit-backdrop-filter: blur(10px);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#widget-url {
|
#settingsPanel::-webkit-scrollbar {
|
||||||
font-size: 1em;
|
width: 8px;
|
||||||
width: 100%;
|
/* Width of the entire scrollbar */
|
||||||
margin: 10px 0px;
|
|
||||||
padding: 10px 10px;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#settings-container {
|
#settingsPanel::-webkit-scrollbar-track {
|
||||||
margin: 0px auto;
|
background: #2c2c2c;
|
||||||
/* border: 1px solid #ddd; */
|
/* Color of the tracking area */
|
||||||
border-radius: 5px;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#settings-container h1 {
|
#settingsPanel::-webkit-scrollbar-thumb {
|
||||||
text-align: center;
|
background-color: #9f9f9f;
|
||||||
margin-bottom: 20px;
|
/* Color of the scroll thumb */
|
||||||
|
border-radius: 4px;
|
||||||
|
/* Roundness of the scroll thumb */
|
||||||
|
border: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
#settingsPanel::-webkit-scrollbar-thumb:hover {
|
||||||
|
background-color: #d1d1d1;
|
||||||
|
/* Color of the scroll thumb on hover */
|
||||||
|
}
|
||||||
|
|
||||||
|
#widgetPreview {
|
||||||
|
flex-grow: 1;
|
||||||
|
overflow: hidden;
|
||||||
|
border: transparent;
|
||||||
|
}
|
||||||
|
|
||||||
|
#widgetUrlInputWrapper {
|
||||||
|
position: relative;
|
||||||
|
/* Make the wrapper a positioning context */
|
||||||
|
display: inline-block;
|
||||||
|
/* Or block, depending on your layout */
|
||||||
|
width: 100%;
|
||||||
|
/* Match the input width */
|
||||||
|
flex-grow: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
#widgetUrlInputWrapper:hover #urlLabel {
|
||||||
|
opacity: 0;
|
||||||
|
/* Fade out the label on hover of the wrapper */
|
||||||
|
}
|
||||||
|
|
||||||
|
#widgetUrlInput {
|
||||||
|
font-size: 1em;
|
||||||
|
width: 100%;
|
||||||
|
padding: 10px 10px;
|
||||||
|
filter: blur(4px) brightness(0.4);
|
||||||
|
/* Apply a blur effect */
|
||||||
|
transition: filter 0.1s ease-in-out;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
#urlLabel {
|
||||||
|
border-radius: 0.5em;
|
||||||
|
padding: 5px 20px;
|
||||||
|
z-index: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
#urlLabel,
|
||||||
|
#copiedToClipboard {
|
||||||
|
position: absolute;
|
||||||
|
top: 50%;
|
||||||
|
left: 50%;
|
||||||
|
transform: translate(-50%, -50%);
|
||||||
|
color: white;
|
||||||
|
pointer-events: none;
|
||||||
|
opacity: 1;
|
||||||
|
transition: opacity 0.2s ease-in-out;
|
||||||
|
}
|
||||||
|
|
||||||
|
#widgetUrlInput:hover {
|
||||||
|
filter: none;
|
||||||
|
/* Remove blur when the input is focused */
|
||||||
|
outline: none;
|
||||||
|
/* Remove default focus outline */
|
||||||
}
|
}
|
||||||
|
|
||||||
.setting-group {
|
.setting-group {
|
||||||
margin-bottom: 20px;
|
margin-bottom: 20px;
|
||||||
/* border: 1px solid #ddd; */
|
/* border: 1px solid #ddd; */
|
||||||
padding-bottom: 15px;
|
padding-bottom: 15px;
|
||||||
border-radius: 5px;
|
border-radius: 5px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.setting-group:last-child {
|
||||||
|
padding-bottom: 0px;
|
||||||
}
|
}
|
||||||
|
|
||||||
h2 {
|
h2 {
|
||||||
font-size: 0.9em;
|
font-size: 0.9em;
|
||||||
font-weight: 500;
|
font-weight: 500;
|
||||||
color: #93cdfd;
|
color: #93cdfd;
|
||||||
}
|
}
|
||||||
|
|
||||||
.setting-item {
|
.setting-item {
|
||||||
display: flex;
|
display: flex;
|
||||||
justify-content: space-between;
|
justify-content: space-between;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
padding: 10px 0;
|
padding: 10px 0;
|
||||||
/* border-bottom: 1px solid #eee; */
|
/* border-bottom: 1px solid #eee; */
|
||||||
}
|
}
|
||||||
|
|
||||||
.setting-item:last-child {
|
.setting-item:last-child {
|
||||||
border-bottom: none;
|
padding-bottom: 0px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.setting-item label {
|
.setting-item label {
|
||||||
font-weight: 500;
|
font-weight: 500;
|
||||||
margin-bottom: 5px;
|
margin-bottom: 5px;
|
||||||
display: block;
|
display: block;
|
||||||
}
|
}
|
||||||
|
|
||||||
.setting-item p,
|
.setting-item p,
|
||||||
.setting-item a {
|
.setting-item a {
|
||||||
font-size: 0.9em;
|
font-size: 0.9em;
|
||||||
font-weight: 300;
|
font-weight: 300;
|
||||||
/* color: #666; */
|
/* color: #666; */
|
||||||
opacity: 0.6;
|
opacity: 0.6;
|
||||||
margin: 0;
|
margin: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
a {
|
a {
|
||||||
font-weight: 500 !important;
|
font-weight: 500 !important;
|
||||||
}
|
}
|
||||||
|
|
||||||
.setting-item-content {
|
.setting-item-content {
|
||||||
display: flex;
|
display: flex;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
}
|
}
|
||||||
|
|
||||||
input[type="text"],
|
input[type="text"],
|
||||||
select,
|
select,
|
||||||
input[type="number"] {
|
input[type="number"] {
|
||||||
width: 250px;
|
width: 250px;
|
||||||
padding: 5px;
|
padding: 5px;
|
||||||
|
|
||||||
margin: 10px 0px;
|
margin: 10px 0px;
|
||||||
padding: 10px 10px;
|
padding: 10px 10px;
|
||||||
background-color: #ffffff05;
|
background-color: #ffffff05;
|
||||||
border-width: 0px;
|
border-width: 0px;
|
||||||
color: white;
|
color: white;
|
||||||
border-radius: 0.5em;
|
border-radius: 0.5em;
|
||||||
|
|
||||||
-webkit-box-sizing: border-box;
|
-webkit-box-sizing: border-box;
|
||||||
-moz-box-sizing: border-box;
|
-moz-box-sizing: border-box;
|
||||||
box-sizing: border-box;
|
box-sizing: border-box;
|
||||||
}
|
}
|
||||||
|
|
||||||
.setting-item-content option {
|
.setting-item-content option {
|
||||||
color: black;
|
color: black;
|
||||||
}
|
}
|
||||||
|
|
||||||
textarea:focus,
|
textarea:focus,
|
||||||
input:focus {
|
input:focus {
|
||||||
outline: none;
|
outline: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
.setting-item-content input[type="color"] {
|
.setting-item-content input[type="color"] {
|
||||||
width: 40px;
|
width: 40px;
|
||||||
height: 40px;
|
height: 40px;
|
||||||
margin-left: 10px;
|
margin-left: 10px;
|
||||||
/* padding: 2px; */
|
/* padding: 2px; */
|
||||||
/* border: 1px solid #ccc; */
|
/* border: 1px solid #ccc; */
|
||||||
/* border-radius: 4px; */
|
/* border-radius: 4px; */
|
||||||
|
|
||||||
appearance: none;
|
appearance: none;
|
||||||
-moz-appearance: none;
|
-moz-appearance: none;
|
||||||
-webkit-appearance: none;
|
-webkit-appearance: none;
|
||||||
background: none;
|
background: none;
|
||||||
border: 0;
|
border: 0;
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
padding: 0;
|
padding: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Switch styling */
|
/* Switch styling */
|
||||||
.switch {
|
.switch {
|
||||||
position: relative;
|
position: relative;
|
||||||
display: inline-block;
|
display: inline-block;
|
||||||
width: 60px;
|
width: 60px;
|
||||||
height: 34px;
|
height: 34px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.switch input {
|
.switch input {
|
||||||
opacity: 0;
|
opacity: 0;
|
||||||
width: 0;
|
width: 0;
|
||||||
height: 0;
|
height: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
.slider {
|
.slider {
|
||||||
position: absolute;
|
position: absolute;
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
top: 0;
|
top: 0;
|
||||||
left: 0;
|
left: 0;
|
||||||
right: 0;
|
right: 0;
|
||||||
bottom: 0;
|
bottom: 0;
|
||||||
background-color: #ccc;
|
background-color: #ccc;
|
||||||
-webkit-transition: .4s;
|
-webkit-transition: .4s;
|
||||||
transition: .4s;
|
transition: .4s;
|
||||||
}
|
}
|
||||||
|
|
||||||
.slider:before {
|
.slider:before {
|
||||||
position: absolute;
|
position: absolute;
|
||||||
content: "";
|
content: "";
|
||||||
height: 26px;
|
height: 26px;
|
||||||
width: 26px;
|
width: 26px;
|
||||||
left: 4px;
|
left: 4px;
|
||||||
bottom: 4px;
|
bottom: 4px;
|
||||||
background-color: white;
|
background-color: white;
|
||||||
-webkit-transition: .4s;
|
-webkit-transition: .4s;
|
||||||
transition: .4s;
|
transition: .4s;
|
||||||
}
|
}
|
||||||
|
|
||||||
input:checked+.slider {
|
input:checked+.slider {
|
||||||
background-color: var(--accent-color);
|
background-color: var(--accent-color);
|
||||||
}
|
}
|
||||||
|
|
||||||
input:focus+.slider {
|
input:focus+.slider {
|
||||||
box-shadow: 0 0 1px var(--accent-color);
|
box-shadow: 0 0 1px var(--accent-color);
|
||||||
}
|
}
|
||||||
|
|
||||||
input:checked+.slider:before {
|
input:checked+.slider:before {
|
||||||
-webkit-transform: translateX(26px);
|
-webkit-transform: translateX(26px);
|
||||||
-ms-transform: translateX(26px);
|
-ms-transform: translateX(26px);
|
||||||
transform: translateX(26px);
|
transform: translateX(26px);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Rounded sliders */
|
/* Rounded sliders */
|
||||||
.slider.round {
|
.slider.round {
|
||||||
border-radius: 34px;
|
border-radius: 34px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.slider.round:before {
|
.slider.round:before {
|
||||||
border-radius: 50%;
|
border-radius: 50%;
|
||||||
}
|
}
|
||||||
|
|
||||||
button {
|
button {
|
||||||
font-weight: 500;
|
font-weight: 500;
|
||||||
background-color: #2e2e2e;
|
background-color: #2e2e2e;
|
||||||
color: white;
|
color: white;
|
||||||
opacity: 0.8;
|
opacity: 0.8;
|
||||||
margin: 5px 0px;
|
margin: 5px 0px;
|
||||||
border-width: 0;
|
border-width: 0;
|
||||||
border-radius: 0.5em;
|
border-radius: 0.5em;
|
||||||
padding: 10px 20px;
|
padding: 10px 20px;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
transition: all 0.2s ease-in-out;
|
transition: all 0.2s ease-in-out;
|
||||||
}
|
}
|
||||||
|
|
||||||
button:hover {
|
button:hover {
|
||||||
opacity: 1;
|
opacity: 1;
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
}
|
}
|
||||||
|
|
||||||
#mommy-milkers {
|
#loadSettingsWrapper {
|
||||||
visibility: hidden;
|
visibility: hidden;
|
||||||
position: fixed;
|
position: absolute;
|
||||||
top: 0;
|
top: 0;
|
||||||
left: 0;
|
left: 0;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
height: 100%;
|
height: 100%;
|
||||||
background: #181818af;
|
background: #181818af;
|
||||||
backdrop-filter: blur(10px); /* Adjust blur radius as needed */
|
backdrop-filter: blur(20px) grayscale(50%) brightness(200%);
|
||||||
z-index: 9999; /* Ensure it's on top */
|
/* Adjust blur radius as needed */
|
||||||
/* Add any other styles for the overlay content */
|
z-index: 9999;
|
||||||
transition: all 0.2s ease-in-out;
|
/* Ensure it's on top */
|
||||||
opacity: 0;
|
/* Add any other styles for the overlay content */
|
||||||
|
transition: all 0.2s ease-in-out;
|
||||||
|
opacity: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
#load-url {
|
#loadSettingsContainer {
|
||||||
width: 100%;
|
position: absolute;
|
||||||
}
|
left: 50%;
|
||||||
|
top: 50%;
|
||||||
#load-settings-container {
|
max-width: 1000px;
|
||||||
position: fixed;
|
width: calc(100% - 75px);
|
||||||
left: 50%;
|
border-radius: 1em;
|
||||||
top: 50%;
|
border: 1px rgba(255, 255, 255, 0.24) solid ;
|
||||||
width: calc(100% - 75px);
|
padding: 1em;
|
||||||
border-radius: 0.5em;
|
box-shadow: 5px 5px 10px rgba(0, 0, 0, 0.5);
|
||||||
padding: 1em;
|
background: #181818af;
|
||||||
box-shadow: 5px 5px 10px rgba(0, 0, 0, 0.5);
|
/* background: rgba(255, 0, 0, 0.637); */
|
||||||
background: #181818af;
|
backdrop-filter: blur(10px);
|
||||||
/* background: rgba(255, 0, 0, 0.637); */
|
-webkit-backdrop-filter: blur(10px);
|
||||||
backdrop-filter: blur(10px);
|
transform: translate(-50%, -50%);
|
||||||
-webkit-backdrop-filter: blur(10px);
|
|
||||||
transform: translate(-50%, -50%);
|
|
||||||
}
|
|
||||||
|
|
||||||
#load-settings {
|
|
||||||
background-color: var(--accent-color);
|
|
||||||
}
|
}
|
||||||
@@ -4,61 +4,26 @@
|
|||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8">
|
<meta charset="UTF-8">
|
||||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||||
<title>Settings</title>
|
<link rel="icon" href="../../.resources/logo.png" type="image/png">
|
||||||
|
<title>nutty</title>
|
||||||
<style>
|
<style>
|
||||||
body {
|
body {
|
||||||
margin: 0;
|
margin: 0;
|
||||||
/* Remove default body margin */
|
|
||||||
display: flex;
|
display: flex;
|
||||||
/* Use flexbox for layout */
|
|
||||||
background: #181818;
|
background: #181818;
|
||||||
}
|
}
|
||||||
|
|
||||||
#settings-container {
|
#widgetContainer {
|
||||||
width: 600px;
|
width: 100vw;
|
||||||
/* 50% of viewport width */
|
|
||||||
min-width: 600px;
|
|
||||||
/* 50% of viewport width */
|
|
||||||
height: 100vh;
|
height: 100vh;
|
||||||
/* 100% of viewport height */
|
border-width: 0px;
|
||||||
border: none;
|
|
||||||
/* Remove default iframe border */
|
|
||||||
}
|
|
||||||
|
|
||||||
#widget-container {
|
|
||||||
flex-grow: 1;
|
|
||||||
/* Allow the content-container to take up remaining space */
|
|
||||||
height: 100vh;
|
|
||||||
}
|
|
||||||
|
|
||||||
iframe {
|
|
||||||
width: 100%;
|
|
||||||
height: 100%;
|
|
||||||
border: none;
|
|
||||||
}
|
|
||||||
|
|
||||||
.content-container {
|
|
||||||
width: 50vw;
|
|
||||||
height: 100vh;
|
|
||||||
background-color: #f0f0f0;
|
|
||||||
/* Example background for right side */
|
|
||||||
padding: 20px;
|
|
||||||
box-sizing: border-box;
|
|
||||||
/* Include padding in width/height */
|
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
</head>
|
</head>
|
||||||
|
|
||||||
<body>
|
<body>
|
||||||
|
<iframe id="widgetContainer"></iframe>
|
||||||
<iframe id="settings-container"></iframe>
|
|
||||||
|
|
||||||
<div id="widget-container">
|
|
||||||
<iframe id="widget"></iframe>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<script src="script.js"></script>
|
<script src="script.js"></script>
|
||||||
|
|
||||||
</body>
|
</body>
|
||||||
|
|
||||||
</html>
|
</html>
|
||||||
@@ -1,29 +1,29 @@
|
|||||||
let settingsContainer = document.getElementById('settings-container');
|
const widgetContainer = document.getElementById('widgetContainer');
|
||||||
settingsContainer.src = `../../.utilities/settings-page-builder?settingsJson=${window.location.href}/settings.json`
|
|
||||||
console.log(settingsContainer.src);
|
|
||||||
|
|
||||||
function reloadWidget(data) {
|
const settingsPageURL = '../../.utilities/settings-page-builder';
|
||||||
|
|
||||||
|
const currentURL = window.location.href;
|
||||||
|
|
||||||
|
let settingsJSON;
|
||||||
|
let baseURL = currentURL;
|
||||||
|
|
||||||
|
if (baseURL.endsWith("index.html"))
|
||||||
|
baseURL = baseURL.replace("index.html", "");
|
||||||
|
|
||||||
|
settingsJSON = "?settingsJson=" + baseURL + "settings.json";
|
||||||
|
|
||||||
|
const lastSlashIndex = baseURL.lastIndexOf("/");
|
||||||
|
let widgetURL = "&widgetURL=" + baseURL.replace("/settings", "");
|
||||||
|
|
||||||
|
console.debug("Window Ref: " + window.location.href);
|
||||||
|
console.debug("Base URL: " + baseURL);
|
||||||
|
console.debug("Settings JSON: " + settingsJSON);
|
||||||
|
console.debug("Widget URL: " + widgetURL);
|
||||||
|
|
||||||
|
widgetContainer.src = settingsPageURL + settingsJSON + widgetURL;
|
||||||
|
|
||||||
|
function callFunction(functionName) {
|
||||||
|
console.debug(`Calling ${functionName}`);
|
||||||
let widget = document.getElementById("widget");
|
let widget = document.getElementById("widget");
|
||||||
widget.src = `${getParentUrl()}?${data}`;
|
widget.contentWindow[functionName]();
|
||||||
}
|
|
||||||
|
|
||||||
function getParentUrl() {
|
|
||||||
const currentUrl = window.location.href;
|
|
||||||
const urlParts = currentUrl.split('/');
|
|
||||||
|
|
||||||
// Remove the last part of the URL (the current page/file)
|
|
||||||
urlParts.pop();
|
|
||||||
|
|
||||||
// Remove the last part again to go one directory up
|
|
||||||
urlParts.pop();
|
|
||||||
|
|
||||||
// Reconstruct the URL
|
|
||||||
const parentUrl = urlParts.join('/');
|
|
||||||
|
|
||||||
// Ensure there's a trailing slash if necessary (if it was a directory)
|
|
||||||
if (urlParts.length > 2 && !parentUrl.endsWith('/')) {
|
|
||||||
return parentUrl + '/';
|
|
||||||
}
|
|
||||||
|
|
||||||
return parentUrl;
|
|
||||||
}
|
}
|
||||||
-51
@@ -1,51 +0,0 @@
|
|||||||
<!DOCTYPE html>
|
|
||||||
<html lang="en">
|
|
||||||
<head>
|
|
||||||
<meta charset="UTF-8">
|
|
||||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
||||||
<title>My Simple Page</title>
|
|
||||||
<style>
|
|
||||||
/* Optional: Basic CSS Styling */
|
|
||||||
body {
|
|
||||||
font-family: sans-serif;
|
|
||||||
margin: 0;
|
|
||||||
padding: 0;
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
min-height: 100vh;
|
|
||||||
}
|
|
||||||
|
|
||||||
header {
|
|
||||||
background-color: #f0f0f0;
|
|
||||||
padding: 20px;
|
|
||||||
text-align: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
main {
|
|
||||||
flex-grow: 1;
|
|
||||||
padding: 20px;
|
|
||||||
}
|
|
||||||
|
|
||||||
footer {
|
|
||||||
background-color: #e0e0e0;
|
|
||||||
padding: 10px;
|
|
||||||
text-align: center;
|
|
||||||
}
|
|
||||||
</style>
|
|
||||||
</head>
|
|
||||||
<body>
|
|
||||||
|
|
||||||
<header>
|
|
||||||
<h1>Welcome to My Page</h1>
|
|
||||||
</header>
|
|
||||||
|
|
||||||
<main>
|
|
||||||
<p>This is the main content area.</p>
|
|
||||||
</main>
|
|
||||||
|
|
||||||
<footer>
|
|
||||||
<p>© 2024 My Website</p>
|
|
||||||
</footer>
|
|
||||||
|
|
||||||
</body>
|
|
||||||
</html>
|
|
||||||
@@ -4,61 +4,26 @@
|
|||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8">
|
<meta charset="UTF-8">
|
||||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||||
<title>Settings</title>
|
<link rel="icon" href="../../.resources/logo.png" type="image/png">
|
||||||
|
<title>nutty</title>
|
||||||
<style>
|
<style>
|
||||||
body {
|
body {
|
||||||
margin: 0;
|
margin: 0;
|
||||||
/* Remove default body margin */
|
|
||||||
display: flex;
|
display: flex;
|
||||||
/* Use flexbox for layout */
|
|
||||||
background: #181818;
|
background: #181818;
|
||||||
}
|
}
|
||||||
|
|
||||||
#settings-container {
|
#widgetContainer {
|
||||||
width: 600px;
|
width: 100vw;
|
||||||
/* 50% of viewport width */
|
|
||||||
min-width: 600px;
|
|
||||||
/* 50% of viewport width */
|
|
||||||
height: 100vh;
|
height: 100vh;
|
||||||
/* 100% of viewport height */
|
border-width: 0px;
|
||||||
border: none;
|
|
||||||
/* Remove default iframe border */
|
|
||||||
}
|
|
||||||
|
|
||||||
#widget-container {
|
|
||||||
flex-grow: 1;
|
|
||||||
/* Allow the content-container to take up remaining space */
|
|
||||||
height: 100vh;
|
|
||||||
}
|
|
||||||
|
|
||||||
iframe {
|
|
||||||
width: 100%;
|
|
||||||
height: 100%;
|
|
||||||
border: none;
|
|
||||||
}
|
|
||||||
|
|
||||||
.content-container {
|
|
||||||
width: 50vw;
|
|
||||||
height: 100vh;
|
|
||||||
background-color: #f0f0f0;
|
|
||||||
/* Example background for right side */
|
|
||||||
padding: 20px;
|
|
||||||
box-sizing: border-box;
|
|
||||||
/* Include padding in width/height */
|
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
</head>
|
</head>
|
||||||
|
|
||||||
<body>
|
<body>
|
||||||
|
<iframe id="widgetContainer"></iframe>
|
||||||
<iframe id="settings-container"></iframe>
|
|
||||||
|
|
||||||
<div id="widget-container">
|
|
||||||
<iframe id="widget"></iframe>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<script src="script.js"></script>
|
<script src="script.js"></script>
|
||||||
|
|
||||||
</body>
|
</body>
|
||||||
|
|
||||||
</html>
|
</html>
|
||||||
@@ -1,29 +1,29 @@
|
|||||||
let settingsContainer = document.getElementById('settings-container');
|
const widgetContainer = document.getElementById('widgetContainer');
|
||||||
settingsContainer.src = `../../.utilities/settings-page-builder?settingsJson=${window.location.href}/settings.json`
|
|
||||||
console.log(settingsContainer.src);
|
|
||||||
|
|
||||||
function reloadWidget(data) {
|
const settingsPageURL = '../../.utilities/settings-page-builder';
|
||||||
|
|
||||||
|
const currentURL = window.location.href;
|
||||||
|
|
||||||
|
let settingsJSON;
|
||||||
|
let baseURL = currentURL;
|
||||||
|
|
||||||
|
if (baseURL.endsWith("index.html"))
|
||||||
|
baseURL = baseURL.replace("index.html", "");
|
||||||
|
|
||||||
|
settingsJSON = "?settingsJson=" + baseURL + "settings.json";
|
||||||
|
|
||||||
|
const lastSlashIndex = baseURL.lastIndexOf("/");
|
||||||
|
let widgetURL = "&widgetURL=" + baseURL.replace("/settings", "");
|
||||||
|
|
||||||
|
console.debug("Window Ref: " + window.location.href);
|
||||||
|
console.debug("Base URL: " + baseURL);
|
||||||
|
console.debug("Settings JSON: " + settingsJSON);
|
||||||
|
console.debug("Widget URL: " + widgetURL);
|
||||||
|
|
||||||
|
widgetContainer.src = settingsPageURL + settingsJSON + widgetURL;
|
||||||
|
|
||||||
|
function callFunction(functionName) {
|
||||||
|
console.debug(`Calling ${functionName}`);
|
||||||
let widget = document.getElementById("widget");
|
let widget = document.getElementById("widget");
|
||||||
widget.src = `${getParentUrl()}?${data}`;
|
widget.contentWindow[functionName]();
|
||||||
}
|
|
||||||
|
|
||||||
function getParentUrl() {
|
|
||||||
const currentUrl = window.location.href;
|
|
||||||
const urlParts = currentUrl.split('/');
|
|
||||||
|
|
||||||
// Remove the last part of the URL (the current page/file)
|
|
||||||
urlParts.pop();
|
|
||||||
|
|
||||||
// Remove the last part again to go one directory up
|
|
||||||
urlParts.pop();
|
|
||||||
|
|
||||||
// Reconstruct the URL
|
|
||||||
const parentUrl = urlParts.join('/');
|
|
||||||
|
|
||||||
// Ensure there's a trailing slash if necessary (if it was a directory)
|
|
||||||
if (urlParts.length > 2 && !parentUrl.endsWith('/')) {
|
|
||||||
return parentUrl + '/';
|
|
||||||
}
|
|
||||||
|
|
||||||
return parentUrl;
|
|
||||||
}
|
}
|
||||||
@@ -1,58 +1,29 @@
|
|||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
|
<html lang="en">
|
||||||
|
|
||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8">
|
<meta charset="UTF-8">
|
||||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||||
<title>Settings</title>
|
<link rel="icon" href="../../.resources/logo.png" type="image/png">
|
||||||
|
<title>nutty</title>
|
||||||
<style>
|
<style>
|
||||||
body {
|
body {
|
||||||
margin: 0;
|
margin: 0;
|
||||||
/* Remove default body margin */
|
|
||||||
display: flex;
|
display: flex;
|
||||||
/* Use flexbox for layout */
|
|
||||||
background: #181818;
|
background: #181818;
|
||||||
}
|
}
|
||||||
|
|
||||||
#settings-container {
|
#widgetContainer {
|
||||||
width: 600px;
|
width: 100vw;
|
||||||
/* 50% of viewport width */
|
|
||||||
min-width: 600px;
|
|
||||||
/* 50% of viewport width */
|
|
||||||
height: 100vh;
|
height: 100vh;
|
||||||
/* 100% of viewport height */
|
border-width: 0px;
|
||||||
border: none;
|
|
||||||
/* Remove default iframe border */
|
|
||||||
}
|
|
||||||
|
|
||||||
#widget-container {
|
|
||||||
flex-grow: 1;
|
|
||||||
/* Allow the content-container to take up remaining space */
|
|
||||||
height: 100vh;
|
|
||||||
}
|
|
||||||
|
|
||||||
iframe {
|
|
||||||
width: 100%;
|
|
||||||
height: 100%;
|
|
||||||
border: none;
|
|
||||||
}
|
|
||||||
|
|
||||||
.content-container {
|
|
||||||
width: 50vw;
|
|
||||||
height: 100vh;
|
|
||||||
background-color: #f0f0f0;
|
|
||||||
/* Example background for right side */
|
|
||||||
padding: 20px;
|
|
||||||
box-sizing: border-box;
|
|
||||||
/* Include padding in width/height */
|
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
</head>
|
</head>
|
||||||
|
|
||||||
<body>
|
<body>
|
||||||
<iframe id="settings-container"></iframe>
|
<iframe id="widgetContainer"></iframe>
|
||||||
<div id="widget-container">
|
<script src="script.js"></script>
|
||||||
<iframe id="widget"></iframe>
|
|
||||||
</div>
|
|
||||||
</body>
|
</body>
|
||||||
|
|
||||||
<script src="./script.js"></script>
|
</html>
|
||||||
@@ -1,33 +1,26 @@
|
|||||||
let settingsContainer = document.getElementById('settings-container');
|
const widgetContainer = document.getElementById('widgetContainer');
|
||||||
settingsContainer.src = `../../.utilities/settings-page-builder?settingsJson=${window.location.href}/settings.json`
|
|
||||||
//settingsContainer.src = `../../.utilities/settings-page-builder?settingsJson=../../multistream-alerts/settings/settings.json`
|
|
||||||
console.log(settingsContainer.src);
|
|
||||||
|
|
||||||
function reloadWidget(data) {
|
const settingsPageURL = '../../.utilities/settings-page-builder';
|
||||||
let widget = document.getElementById("widget");
|
|
||||||
widget.src = `${getParentUrl()}?${data}`;
|
|
||||||
}
|
|
||||||
|
|
||||||
function getParentUrl() {
|
const currentURL = window.location.href;
|
||||||
const currentUrl = window.location.href;
|
|
||||||
const urlParts = currentUrl.split('/');
|
|
||||||
|
|
||||||
// Remove the last part of the URL (the current page/file)
|
let settingsJSON;
|
||||||
urlParts.pop();
|
let baseURL = currentURL;
|
||||||
|
|
||||||
// Remove the last part again to go one directory up
|
if (baseURL.endsWith("index.html"))
|
||||||
urlParts.pop();
|
baseURL = baseURL.replace("index.html", "");
|
||||||
|
|
||||||
// Reconstruct the URL
|
settingsJSON = "?settingsJson=" + baseURL + "settings.json";
|
||||||
const parentUrl = urlParts.join('/');
|
|
||||||
|
|
||||||
// Ensure there's a trailing slash if necessary (if it was a directory)
|
const lastSlashIndex = baseURL.lastIndexOf("/");
|
||||||
if (urlParts.length > 2 && !parentUrl.endsWith('/')) {
|
let widgetURL = "&widgetURL=" + baseURL.replace("/settings", "");
|
||||||
return parentUrl + '/';
|
|
||||||
}
|
|
||||||
|
|
||||||
return parentUrl;
|
console.debug("Window Ref: " + window.location.href);
|
||||||
}
|
console.debug("Base URL: " + baseURL);
|
||||||
|
console.debug("Settings JSON: " + settingsJSON);
|
||||||
|
console.debug("Widget URL: " + widgetURL);
|
||||||
|
|
||||||
|
widgetContainer.src = settingsPageURL + settingsJSON + widgetURL;
|
||||||
|
|
||||||
function callFunction(functionName) {
|
function callFunction(functionName) {
|
||||||
console.debug(`Calling ${functionName}`);
|
console.debug(`Calling ${functionName}`);
|
||||||
|
|||||||
Reference in New Issue
Block a user