large js refactor

This commit is contained in:
Vladimir Mandic
2023-07-12 10:58:32 -04:00
parent c3a4293f22
commit de2c239c26
25 changed files with 538 additions and 568 deletions
-1
View File
@@ -88,7 +88,6 @@ svg.feather.feather-image, .feather .feather-image { display: none }
#txt2img_prompt > label > textarea, #txt2img_neg_prompt > label > textarea, #img2img_prompt > label > textarea, #img2img_neg_prompt > label > textarea { font-size: 1.1rem; }
#img2img_settings { min-width: calc(2 * var(--left-column)); max-width: calc(2 * var(--left-column)); background-color: #111111; padding-top: 16px; }
#interrogate, #deepbooru { margin: 0 0px 10px 0px; max-width: 80px; max-height: 80px; font-weight: normal; font-size: 0.95em; }
#lightboxModal { background-color: rgba(20, 20, 20, 0.8) }
#quicksettings .gr-button-tool { font-size: 1.6rem; box-shadow: none; margin-left: -20px; margin-top: -2px; height: 2.4em; }
#quicksettings > div, #quicksettings > fieldset { min-width: 24em; max-width: 26em; line-height: 2em; }
#open_folder_extras, #footer, #style_pos_col, #style_neg_col, #roll_col, #extras_upscaler_2, #extras_upscaler_2_visibility, #txt2img_seed_resize_from_w, #txt2img_seed_resize_from_h { display: none; }
+15 -23
View File
@@ -52,18 +52,19 @@ const contextMenuInit = () => {
return newItem.id;
}
function removeContextMenuOption(uid) {
function removeContextMenuOption(id) {
menuSpecs.forEach((v, k) => {
let index = -1;
v.forEach((e, ei) => { if (e.id === uid) { index = ei; } });
if (index >= 0) {
v.splice(index, 1);
}
v.forEach((e, ei) => {
if (e.id === id) { index = ei; }
});
if (index >= 0) v.splice(index, 1);
});
}
function addContextMenuEventListener() {
if (eventListenerApplied) return;
console.log('initContextMenu');
gradioApp().addEventListener('click', (e) => {
if (!e.isTrusted) return;
const oldMenu = gradioApp().querySelector('#context-menu');
@@ -89,34 +90,25 @@ const appendContextMenuOption = initResponse[0];
const removeContextMenuOption = initResponse[1];
const addContextMenuEventListener = initResponse[2];
(function () {
(function () { // eslint-disable-line
// Start example Context Menu Items
const generateOnRepeat = function (genbuttonid, interruptbuttonid) {
const generateOnRepeat = (genbuttonid, interruptbuttonid) => {
const genbutton = gradioApp().querySelector(genbuttonid);
const busy = document.getElementById('progressbar')?.style.display === 'block';
if (!busy) {
genbutton.click();
}
if (!busy) genbutton.click();
clearInterval(window.generateOnRepeatInterval);
window.generateOnRepeatInterval = setInterval(
() => {
const busy = document.getElementById('progressbar')?.style.display === 'block';
if (!busy) genbutton.click();
const pbBusy = document.getElementById('progressbar')?.style.display === 'block';
if (!pbBusy) genbutton.click();
},
500,
);
};
appendContextMenuOption('#txt2img_generate', 'Generate forever', () => {
generateOnRepeat('#txt2img_generate', '#txt2img_interrupt');
});
appendContextMenuOption('#img2img_generate', 'Generate forever', () => {
generateOnRepeat('#img2img_generate', '#img2img_interrupt');
});
const cancelGenerateForever = function () {
clearInterval(window.generateOnRepeatInterval);
};
appendContextMenuOption('#txt2img_generate', 'Generate forever', () => generateOnRepeat('#txt2img_generate', '#txt2img_interrupt'));
appendContextMenuOption('#img2img_generate', 'Generate forever', () => generateOnRepeat('#img2img_generate', '#img2img_interrupt'));
const cancelGenerateForever = () => clearInterval(window.generateOnRepeatInterval);
appendContextMenuOption('#txt2img_interrupt', 'Cancel generate forever', cancelGenerateForever);
appendContextMenuOption('#txt2img_generate', 'Cancel generate forever', cancelGenerateForever);
@@ -126,7 +118,7 @@ const addContextMenuEventListener = initResponse[2];
'#roll',
'Roll three',
() => {
const rollbutton = get_uiCurrentTabContent().querySelector('#roll');
const rollbutton = getUICurrentTabContent().querySelector('#roll');
setTimeout(() => { rollbutton.click(); }, 100);
setTimeout(() => { rollbutton.click(); }, 200);
setTimeout(() => { rollbutton.click(); }, 300);
+1 -6
View File
@@ -70,28 +70,23 @@ function keyupEditAttention(event) {
selectionStart += 1;
selectionEnd += 1;
}
const end = text.slice(selectionEnd + 1).indexOf(closeCharacter) + 1;
let weight = parseFloat(text.slice(selectionEnd + 1, selectionEnd + 1 + end));
if (Number.isNaN(weight)) return;
weight += isPlus ? delta : -delta;
weight = parseFloat(weight.toPrecision(12));
if (String(weight).length === 1) weight += '.0';
if (closeCharacter == ')' && weight == 1) {
if (closeCharacter === ')' && weight === 1) {
text = text.slice(0, selectionStart - 1) + text.slice(selectionStart, selectionEnd) + text.slice(selectionEnd + 5);
selectionStart--;
selectionEnd--;
} else {
text = text.slice(0, selectionEnd + 1) + weight + text.slice(selectionEnd + 1 + end - 1);
}
target.focus();
target.value = text;
target.selectionStart = selectionStart;
target.selectionEnd = selectionEnd;
updateInput(target);
}
+69 -69
View File
@@ -2,7 +2,30 @@ let globalPopup = null;
let globalPopupInner = null;
const activePromptTextarea = {};
const getENActiveTab = () => gradioApp().getElementById('tab_txt2img').style.display == 'block' ? 'txt2img' : 'img2img';
const getENActiveTab = () => gradioApp().getElementById('tab_txt2img').style.display === 'block' ? 'txt2img' : 'img2img';
function requestGet(url, data, handler, errorHandler) {
const xhr = new XMLHttpRequest();
const args = Object.keys(data).map((k) => `${encodeURIComponent(k)}=${encodeURIComponent(data[k])}`).join('&');
xhr.open('GET', `${url}?${args}`, true);
xhr.onreadystatechange = () => {
if (xhr.readyState === 4) {
if (xhr.status === 200) {
try {
const js = JSON.parse(xhr.responseText);
handler(js);
} catch (error) {
console.error(error);
errorHandler();
}
} else {
errorHandler();
}
}
};
const js = JSON.stringify(data);
xhr.send(js);
}
function setupExtraNetworksForTab(tabname) {
gradioApp().querySelector(`#${tabname}_extra_tabs`).classList.add('extra-networks');
@@ -16,23 +39,23 @@ function setupExtraNetworksForTab(tabname) {
description.classList.add('description');
tabs.appendChild(refresh);
tabs.appendChild(close);
div = document.createElement('div');
const div = document.createElement('div');
div.classList.add('second-line');
tabs.appendChild(div);
div.appendChild(search);
div.appendChild(description);
search.addEventListener('input', (evt) => {
searchTerm = search.value.toLowerCase();
const searchTerm = search.value.toLowerCase();
gradioApp().querySelectorAll(`#${tabname}_extra_tabs div.card`).forEach((elem) => {
text = `${elem.querySelector('.name').textContent.toLowerCase()} ${elem.querySelector('.search_term').textContent.toLowerCase()}`;
text = text.replace('models--', 'Diffusers')
elem.style.display = text.indexOf(searchTerm) == -1 ? 'none' : '';
let text = `${elem.querySelector('.name').textContent.toLowerCase()} ${elem.querySelector('.search_term').textContent.toLowerCase()}`;
text = text.replace('models--', 'Diffusers');
elem.style.display = text.indexOf(searchTerm) === -1 ? 'none' : '';
});
});
intersectionObserver = new IntersectionObserver((entries) => {
if (!en) return
for (el of Array.from(gradioApp().querySelectorAll('.extra-networks-page'))) el.style.height = window.opts.extra_networks_height + 'vh';
const intersectionObserver = new IntersectionObserver((entries) => {
if (!en) return;
for (const el of Array.from(gradioApp().querySelectorAll('.extra-networks-page'))) el.style.height = `${window.opts.extra_networks_height}vh`;
if (entries[0].intersectionRatio > 0) {
if (window.opts.extra_networks_card_cover === 'cover') {
en.style.transition = '';
@@ -41,15 +64,15 @@ function setupExtraNetworksForTab(tabname) {
en.style.right = 'unset';
en.style.width = 'unset';
en.style.height = 'unset';
gradioApp().getElementById(`${tabname}_settings`).parentNode.style.width = 'unset'
gradioApp().getElementById(`${tabname}_settings`).parentNode.style.width = 'unset';
} else if (window.opts.extra_networks_card_cover === 'sidebar') {
en.style.transition = 'width 0.2s ease';
en.style.zIndex = 0;
en.style.position = 'absolute';
en.style.right = '0';
en.style.width = window.opts.extra_networks_sidebar_width + 'vw';
en.style.height = '-webkit-fill-available'
gradioApp().getElementById(`${tabname}_settings`).parentNode.style.width = 100 - 2 - window.opts.extra_networks_sidebar_width + 'vw';
en.style.width = `${window.opts.extra_networks_sidebar_width}vw`;
en.style.height = '-webkit-fill-available';
gradioApp().getElementById(`${tabname}_settings`).parentNode.style.width = `${100 - 2 - window.opts.extra_networks_sidebar_width}vw`;
} else {
en.style.transition = '';
en.style.zIndex = 0;
@@ -57,20 +80,20 @@ function setupExtraNetworksForTab(tabname) {
en.style.right = 'unset';
en.style.width = 'unset';
en.style.height = 'unset';
gradioApp().getElementById(`${tabname}_settings`).parentNode.style.width = 'unset'
gradioApp().getElementById(`${tabname}_settings`).parentNode.style.width = 'unset';
}
} else {
en.style.width = 0;
gradioApp().getElementById(`${tabname}_settings`).parentNode.style.width = 'unset'
gradioApp().getElementById(`${tabname}_settings`).parentNode.style.width = 'unset';
}
});
intersectionObserver.observe(en); // monitor visibility of
intersectionObserver.observe(en); // monitor visibility of
}
function setupExtraNetworks() {
setupExtraNetworksForTab('txt2img');
setupExtraNetworksForTab('img2img');
function registerPrompt(tabname, id) {
const textarea = gradioApp().querySelector(`#${id} > label > textarea`);
if (!activePromptTextarea[tabname]) activePromptTextarea[tabname] = textarea;
@@ -90,27 +113,27 @@ const re_extranet = /<([^:]+:[^:]+):[\d\.]+>/;
const re_extranet_g = /\s+<([^:]+:[^:]+):[\d\.]+>/g;
function tryToRemoveExtraNetworkFromPrompt(textarea, text) {
var m = text.match(re_extranet);
var replaced = false;
var newTextareaText;
let m = text.match(re_extranet);
let replaced = false;
let newTextareaText;
if (m) {
var partToSearch = m[1];
newTextareaText = textarea.value.replaceAll(re_extranet_g, function(found) {
m = found.match(re_extranet);
if (m[1] == partToSearch) {
replaced = true;
return "";
}
return found;
});
const partToSearch = m[1];
newTextareaText = textarea.value.replaceAll(re_extranet_g, (found) => {
m = found.match(re_extranet);
if (m[1] === partToSearch) {
replaced = true;
return '';
}
return found;
});
} else {
newTextareaText = textarea.value.replaceAll(new RegExp(text, "g"), function(found) {
if (found == text) {
replaced = true;
return "";
}
return found;
});
newTextareaText = textarea.value.replaceAll(new RegExp(text, 'g'), (found) => {
if (found === text) {
replaced = true;
return '';
}
return found;
});
}
if (replaced) {
textarea.value = newTextareaText;
@@ -170,9 +193,9 @@ function readCardDescription(event, filename, descript, extraPage, cardName) {
function extraNetworksSearchButton(event) {
const tabname = getENActiveTab();
searchTextarea = gradioApp().querySelector(`#${tabname}_extra_tabs > div > div > textarea`);
button = event.target;
text = button.classList.contains('search-all') ? '' : `/${button.textContent.trim()}/`;
const searchTextarea = gradioApp().querySelector(`#${tabname}_extra_tabs > div > div > textarea`);
const button = event.target;
const text = button.classList.contains('search-all') ? '' : `/${button.textContent.trim()}/`;
searchTextarea.value = text;
updateInput(searchTextarea);
}
@@ -180,15 +203,15 @@ function extraNetworksSearchButton(event) {
function popup(contents) {
if (!globalPopup) {
globalPopup = document.createElement('div');
globalPopup.onclick = function () { globalPopup.style.display = 'none'; };
globalPopup.onclick = () => { globalPopup.style.display = 'none'; };
globalPopup.classList.add('global-popup');
const close = document.createElement('div');
close.classList.add('global-popup-close');
close.onclick = function () { globalPopup.style.display = 'none'; };
close.onclick = () => { globalPopup.style.display = 'none'; };
close.title = 'Close';
globalPopup.appendChild(close);
globalPopupInner = document.createElement('div');
globalPopupInner.onclick = function (event) { event.stopPropagation(); return false; };
globalPopupInner.onclick = (event) => { event.stopPropagation(); return false; };
globalPopupInner.classList.add('global-popup-inner');
globalPopup.appendChild(globalPopupInner);
gradioApp().appendChild(globalPopup);
@@ -200,8 +223,8 @@ function popup(contents) {
function readCardMetadata(event, extraPage, cardName) {
requestGet('./sd_extra_networks/metadata', { page: extraPage, item: cardName }, (data) => {
if (data?.metadata && (typeof(data?.metadata) === 'string')) {
elem = document.createElement('pre');
if (data?.metadata && (typeof (data?.metadata) === 'string')) {
const elem = document.createElement('pre');
elem.classList.add('popup-metadata');
elem.textContent = data.metadata;
popup(elem);
@@ -213,8 +236,8 @@ function readCardMetadata(event, extraPage, cardName) {
function readCardInformation(event, extraPage, cardName) {
requestGet('./sd_extra_networks/info', { page: extraPage, item: cardName }, (data) => {
if (data?.info && (typeof(data?.info) === 'string')) {
elem = document.createElement('pre');
if (data?.info && (typeof (data?.info) === 'string')) {
const elem = document.createElement('pre');
elem.classList.add('popup-metadata');
elem.textContent = data.info;
popup(elem);
@@ -223,26 +246,3 @@ function readCardInformation(event, extraPage, cardName) {
event.stopPropagation();
event.preventDefault();
}
function requestGet(url, data, handler, errorHandler) {
const xhr = new XMLHttpRequest();
const args = Object.keys(data).map((k) => `${encodeURIComponent(k)}=${encodeURIComponent(data[k])}`).join('&');
xhr.open('GET', `${url}?${args}`, true);
xhr.onreadystatechange = function () {
if (xhr.readyState === 4) {
if (xhr.status === 200) {
try {
const js = JSON.parse(xhr.responseText);
handler(js);
} catch (error) {
console.error(error);
errorHandler();
}
} else {
errorHandler();
}
}
};
const js = JSON.stringify(data);
xhr.send(js);
}
+21 -22
View File
@@ -3,16 +3,10 @@
function attachGalleryListeners(tab_name) {
const gallery = gradioApp().querySelector(`#${tab_name}_gallery`);
gallery?.addEventListener('click', () => setTimeout(() => {
gradioApp()
.getElementById(`${tab_name}_generation_info_button`)
?.click();
gradioApp().getElementById(`${tab_name}_generation_info_button`)?.click();
}, 500));
gallery?.addEventListener('keydown', (e) => {
if (e.keyCode == 37 || e.keyCode == 39) { // left or right arrow
gradioApp()
.getElementById(`${tab_name}_generation_info_button`)
.click();
}
if (e.keyCode === 37 || e.keyCode === 39) gradioApp().getElementById(`${tab_name}_generation_info_button`).click(); // left or right arrow
});
return gallery;
}
@@ -20,21 +14,26 @@ function attachGalleryListeners(tab_name) {
let txt2img_gallery;
let img2img_gallery;
let modal;
let generationParamsInitialized = false;
function initiGenerationParams() {
if (generationParamsInitialized) return;
if (!modal) modal = gradioApp().getElementById('lightboxModal');
if (!modal) return;
generationParamsInitialized = true;
const modalObserver = new MutationObserver((mutations) => {
mutations.forEach((mutationRecord) => {
let selectedTab = gradioApp().querySelector('#tabs div button.selected')?.innerText;
if (!selectedTab) selectedTab = gradioApp().querySelector('#tabs div button')?.innerText;
if (mutationRecord.target.style.display === 'none' && (selectedTab === 'txt2img' || selectedTab === 'img2img')) { gradioApp().getElementById(`${selectedTab}_generation_info_button`)?.click(); }
});
});
onAfterUiUpdate(() => {
if (!txt2img_gallery) txt2img_gallery = attachGalleryListeners('txt2img');
if (!img2img_gallery) img2img_gallery = attachGalleryListeners('img2img');
if (!modal) {
modal = gradioApp().getElementById('lightboxModal');
modalObserver.observe(modal, { attributes: true, attributeFilter: ['style'] });
}
});
let modalObserver = new MutationObserver((mutations) => {
mutations.forEach((mutationRecord) => {
let selectedTab = gradioApp().querySelector('#tabs div button.selected')?.innerText;
if (!selectedTab) selectedTab = gradioApp().querySelector('#tabs div button')?.innerText;
if (mutationRecord.target.style.display === 'none' && (selectedTab === 'txt2img' || selectedTab === 'img2img')) { gradioApp().getElementById(`${selectedTab}_generation_info_button`)?.click(); }
});
});
modalObserver.observe(modal, { attributes: true, attributeFilter: ['style'] });
console.log('initGenerationParams');
}
onAfterUiUpdate(initiGenerationParams);
+3 -5
View File
@@ -1,13 +1,11 @@
function onCalcResolutionHires(enable_hr, width, height, hr_scale, hr_resize_x, hr_resize_y) {
function setInactive(elem, inactive) {
elem.classList.toggle('inactive', !!inactive);
}
const setInactive = (elem, inactive) => elem.classList.toggle('inactive', !!inactive);
const hrUpscaleBy = gradioApp().getElementById('txt2img_hr_scale');
const hrResizeX = gradioApp().getElementById('txt2img_hr_resize_x');
const hrResizeY = gradioApp().getElementById('txt2img_hr_resize_y');
gradioApp().getElementById('txt2img_hires_fix_row3').style.display = opts.use_old_hires_fix_width_height ? 'none' : '';
setInactive(hrUpscaleBy, opts.use_old_hires_fix_width_height || hr_resize_x > 0 || hr_resize_y > 0);
setInactive(hrResizeX, opts.use_old_hires_fix_width_height || hr_resize_x == 0);
setInactive(hrResizeY, opts.use_old_hires_fix_width_height || hr_resize_y == 0);
setInactive(hrResizeX, opts.use_old_hires_fix_width_height || hr_resize_x === 0);
setInactive(hrResizeY, opts.use_old_hires_fix_width_height || hr_resize_y === 0);
return [enable_hr, width, height, hr_scale, hr_resize_x, hr_resize_y];
}
-6
View File
@@ -8,29 +8,23 @@ function imageMaskResize() {
window.removeEventListener('resize', imageMaskResize);
return;
}
const wrapper = canvases[0].closest('.touch-none');
const previewImage = wrapper.previousElementSibling;
if (!previewImage.complete) {
previewImage.addEventListener('load', imageMaskResize);
return;
}
const w = previewImage.width;
const h = previewImage.height;
const nw = previewImage.naturalWidth;
const nh = previewImage.naturalHeight;
const portrait = nh > nw;
const wW = Math.min(w, portrait ? h / nh * nw : w / nw * nw);
const wH = Math.min(h, portrait ? h / nh * nh : w / nw * nh);
wrapper.style.width = `${wW}px`;
wrapper.style.height = `${wH}px`;
wrapper.style.left = '0px';
wrapper.style.top = '0px';
canvases.forEach((c) => {
c.style.width = '';
c.style.height = '';
+7 -5
View File
@@ -1,17 +1,19 @@
window.onload = (function () {
window.onload = () => {
window.addEventListener('drop', (e) => {
const target = e.composedPath()[0];
if (!target.placeholder) return;
if (target.placeholder.indexOf('Prompt') == -1) return;
const prompt_target = get_tab_index('tabs') == 1 ? 'img2img_prompt_image' : 'txt2img_prompt_image';
if (target.placeholder.indexOf('Prompt') === -1) return;
const promptTarget = get_tab_index('tabs') === 1 ? 'img2img_prompt_image' : 'txt2img_prompt_image';
e.stopPropagation();
e.preventDefault();
const imgParent = gradioApp().getElementById(prompt_target);
const imgParent = gradioApp().getElementById(promptTarget);
if (!imgParent) return;
const { files } = e.dataTransfer;
const fileInput = imgParent.querySelector('input[type="file"]');
if (fileInput) {
fileInput.files = files;
fileInput.dispatchEvent(new Event('change'));
console.log('dropEvent');
}
});
});
};
+75 -96
View File
@@ -1,67 +1,77 @@
// A full size 'lightbox' preview modal shown when left clicking on gallery previews
let previewTimestamp = Date.now();
let previewDrag = false;
let modalPreviewZone;
function closeModal(force = false) {
if (force) gradioApp().getElementById('lightboxModal').style.display = 'none';
if (previewDrag) return;
if ((Date.now() - previewTimestamp) < 250) return
if ((Date.now() - previewTimestamp) < 250) return;
gradioApp().getElementById('lightboxModal').style.display = 'none';
}
function showModal(event) {
const source = event.target || event.srcElement;
const modalImage = gradioApp().getElementById('modalImage');
const lb = gradioApp().getElementById('lightboxModal');
modalImage.src = source.src;
if (modalImage.style.display === 'none') lb.style.setProperty('background-image', `url(${source.src})`);
lb.style.display = 'flex';
lb.focus();
previewTimestamp = Date.now()
event.stopPropagation();
}
function updateOnBackgroundChange() {
const modalImage = gradioApp().getElementById('modalImage');
if (modalImage && modalImage.offsetParent) {
const currentButton = selected_gallery_button();
if (currentButton?.children?.length > 0 && modalImage.src != currentButton.children[0].src) {
modalImage.src = currentButton.children[0].src;
if (modalImage.style.display === 'none') modal.style.setProperty('background-image', `url(${modalImage.src})`);
}
}
}
function modalImageSwitch(offset) {
const galleryButtons = all_gallery_buttons();
if (galleryButtons.length > 1) {
const currentButton = selected_gallery_button();
let result = -1;
galleryButtons.forEach((v, i) => {
if (v == currentButton) result = i;
if (v === currentButton) result = i;
});
const negmod = (n, m) => ((n % m) + m) % m;
if (result != -1) {
nextButton = galleryButtons[negmod((result + offset), galleryButtons.length)];
if (result !== -1) {
const nextButton = galleryButtons[negmod((result + offset), galleryButtons.length)];
nextButton.click();
const modalImage = gradioApp().getElementById('modalImage');
const modal = gradioApp().getElementById('lightboxModal');
modalImage.onload = () => modalPreviewZone.focus();
modalImage.src = nextButton.children[0].src;
if (modalImage.style.display === 'none') modal.style.setProperty('background-image', `url(${modalImage.src})`);
setTimeout(() => modal.focus(), 10);
}
}
}
function saveImage() {
if (gradioApp().getElementById('tab_txt2img').style.display != 'none') gradioApp().getElementById('save_txt2img').click();
else if (gradioApp().getElementById('tab_img2img').style.display != 'none') gradioApp().getElementById('save_img2img').click();
else if (gradioApp().getElementById('tab_process').style.display != 'none') gradioApp().getElementById('save_extras').click();
function modalSaveImage(event) {
if (gradioApp().getElementById('tab_txt2img').style.display !== 'none') gradioApp().getElementById('save_txt2img').click();
else if (gradioApp().getElementById('tab_img2img').style.display !== 'none') gradioApp().getElementById('save_img2img').click();
else if (gradioApp().getElementById('tab_process').style.display !== 'none') gradioApp().getElementById('save_extras').click();
}
function modalKeyHandler(event) {
console.log('HERE2', event.key);
switch (event.key) {
case 's':
modalSaveImage();
break;
case 'ArrowLeft':
modalImageSwitch(-1);
break;
case 'ArrowRight':
modalImageSwitch(1);
break;
case 'Escape':
closeModal(true);
break;
}
event.stopPropagation();
}
function showModal(event) {
const source = event.target || event.srcElement;
const modalImage = gradioApp().getElementById('modalImage');
const lb = gradioApp().getElementById('lightboxModal');
modalImage.onload = () => modalPreviewZone.focus();
modalImage.src = source.src;
if (modalImage.style.display === 'none') lb.style.setProperty('background-image', `url(${source.src})`);
lb.style.display = 'flex';
lb.onkeydown = modalKeyHandler;
previewTimestamp = Date.now();
event.stopPropagation();
}
function modalDownloadImage() {
const link = document.createElement("a");
link.style.display = "none";
const link = document.createElement('a');
link.style.display = 'none';
link.href = gradioApp().getElementById('modalImage').src;
link.download = 'image';
document.body.appendChild(link);
@@ -72,52 +82,19 @@ function modalDownloadImage() {
}, 0);
}
function modalSaveImage(event) {
saveImage();
event.stopPropagation();
}
function modalNextImage(event) {
modalImageSwitch(1);
event.stopPropagation();
}
function modalPrevImage(event) {
modalImageSwitch(-1);
event.stopPropagation();
}
function modalKeyHandler(event) {
switch (event.key) {
case 's':
saveImage();
break;
case 'ArrowLeft':
modalPrevImage(event);
break;
case 'ArrowRight':
modalNextImage(event);
break;
case 'Escape':
closeModal(true);
break;
}
}
function modalZoomSet(modalImage, enable) {
localStorage.setItem('modalZoom', enable ? 'yes' : 'no');
if (modalImage) modalImage.classList.toggle('modalImageFullscreen', !!enable);
}
function setupImageForLightbox(e) {
if (e.dataset.modded) return;
if (e.dataset.modded) return;
e.dataset.modded = true;
e.style.cursor = 'pointer';
e.style.userSelect = 'none';
e.addEventListener('mousedown', (evt) => {
if (evt.button != 0) return;
const initialZoom = (localStorage.getItem('modalZoom') || true) == 'yes';
if (evt.button !== 0) return;
const initialZoom = (localStorage.getItem('modalZoom') || true) === 'yes';
modalZoomSet(gradioApp().getElementById('modalImage'), initialZoom);
evt.preventDefault();
showModal(evt);
@@ -144,30 +121,29 @@ function modalTileToggle(event) {
event.stopPropagation();
}
function galleryImageHandler(e) {
e.onclick = showGalleryImage;
}
let imageViewerInitialized = false;
onAfterUiUpdate(() => {
fullImg_preview = gradioApp().querySelectorAll('.gradio-gallery > div > img');
if (fullImg_preview != null) fullImg_preview.forEach(setupImageForLightbox);
updateOnBackgroundChange();
});
function initImageViewer() {
const fullImgPreview = gradioApp().querySelectorAll('.gradio-gallery > div > img');
if (fullImgPreview.length > 0) fullImgPreview.forEach(setupImageForLightbox);
if (imageViewerInitialized) return;
imageViewerInitialized = true;
document.addEventListener('DOMContentLoaded', () => {
// main elements
const modal = document.createElement('div');
modal.id = 'lightboxModal';
modal.addEventListener('keydown', modalKeyHandler, true);
// modal.addEventListener('keydown', modalKeyHandler, true);
const modalPreviewZone = document.createElement('div');
modalPreviewZone.className = 'lightboxModalPreviewZone'
modalPreviewZone = document.createElement('div');
modalPreviewZone.className = 'lightboxModalPreviewZone';
const modalImage = document.createElement('img');
modalImage.id = 'modalImage';
modalImage.addEventListener('keydown', modalKeyHandler, true);
// modalImage.addEventListener('keydown', modalKeyHandler, true);
modalPreviewZone.appendChild(modalImage);
modalImage.onload = () => panzoom(modalImage, { zoomSpeed: 0.05, minZoom: 0.25, maxZoom: 4.0 });
panzoom(modalImage, {
zoomSpeed: 0.05, minZoom: 0.25, maxZoom: 4.0, filterKey: (/* e, dx, dy, dz */) => true,
});
// toolbar
const modalZoom = document.createElement('span');
@@ -206,25 +182,25 @@ document.addEventListener('DOMContentLoaded', () => {
modalClose.addEventListener('click', closeModal, true);
// handlers
modalPreviewZone.addEventListener('mousedown', () => previewDrag = false);
modalPreviewZone.addEventListener('touchstart', () => { previewDrag = false }, { passive: true });
modalPreviewZone.addEventListener('mousemove', () => previewDrag = true);
modalPreviewZone.addEventListener('touchmove', () => { previewDrag = true }, { passive: true });
modalPreviewZone.addEventListener('scroll', () => previewDrag = true);
modalPreviewZone.addEventListener('mousedown', () => { previewDrag = false; });
modalPreviewZone.addEventListener('touchstart', () => { previewDrag = false; }, { passive: true });
modalPreviewZone.addEventListener('mousemove', () => { previewDrag = true; });
modalPreviewZone.addEventListener('touchmove', () => { previewDrag = true; }, { passive: true });
modalPreviewZone.addEventListener('scroll', () => { previewDrag = true; });
modalPreviewZone.addEventListener('mouseup', () => closeModal());
modalPreviewZone.addEventListener('touchend', () => closeModal());
const modalPrev = document.createElement('a');
modalPrev.className = 'modalPrev';
modalPrev.innerHTML = '&#10094;';
modalPrev.addEventListener('click', modalPrevImage, true);
modalPrev.addEventListener('keydown', modalKeyHandler, true);
modalPrev.addEventListener('click', () => modalImageSwitch(-1), true);
// modalPrev.addEventListener('keydown', modalKeyHandler, true);
const modalNext = document.createElement('a');
modalNext.className = 'modalNext';
modalNext.innerHTML = '&#10095;';
modalNext.addEventListener('click', modalNextImage, true);
modalNext.addEventListener('keydown', modalKeyHandler, true);
modalNext.addEventListener('click', () => modalImageSwitch(-1), true);
// modalNext.addEventListener('keydown', modalKeyHandler, true);
const modalControls = document.createElement('div');
modalControls.className = 'modalControls gradio-container';
@@ -240,5 +216,8 @@ document.addEventListener('DOMContentLoaded', () => {
modalControls.appendChild(modalDownload);
modalControls.appendChild(modalClose);
try { gradioApp().appendChild(modal); } catch (e) { gradioApp().body.appendChild(modal); }
});
gradioApp().appendChild(modal);
console.log('initImageViewer');
}
onAfterUiUpdate(initImageViewer);
+11 -4
View File
@@ -15,22 +15,26 @@ async function logMonitor() {
logMonitorEl.parentElement.style.display = 'block';
const lines = await res.json();
for (const line of lines) {
try {
try {
const l = JSON.parse(line);
const row = document.createElement("tr");
const row = document.createElement('tr');
row.style = 'padding: 10px; margin: 0;';
row.innerHTML = `<td>${new Date(1000 * l.created).toISOString()}</td><td>${l.level}</td><td>${l.facility}</td><td>${l.module}</td><td>${l.msg}</td>`;
logMonitorEl.appendChild(row);
} catch {}
}
while (logMonitorEl.childElementCount > 100) logMonitorEl.removeChild(logMonitorEl.firstChild);
logMonitorEl.scrollTop = logMonitorEl.scrollHeight
logMonitorEl.scrollTop = logMonitorEl.scrollHeight;
}
}
async function logMonitorCreate() {
let logMonitorInitialized = false;
async function initLogMonitor() {
if (logMonitorInitialized) return;
const el = document.getElementsByTagName('footer')[0];
if (!el) return;
logMonitorInitialized = true;
el.classList.add('log-monitor');
el.innerHTML = `
<table style="width: 100%;">
@@ -48,4 +52,7 @@ async function logMonitorCreate() {
</table>
`;
logMonitor();
console.log('initLogMonitor');
}
onAfterUiUpdate(initLogMonitor);
+6 -3
View File
@@ -3,7 +3,7 @@
let lastHeadImg = null;
let notificationButton = null;
onAfterUiUpdate(function () {
function initNotifications() {
if (!notificationButton) {
notificationButton = gradioApp().getElementById('request_notifications');
if (notificationButton) notificationButton.addEventListener('click', (evt) => Notification.requestPermission(), true);
@@ -12,7 +12,7 @@ onAfterUiUpdate(function () {
const galleryPreviews = gradioApp().querySelectorAll('div[id^="tab_"][style*="display: block"] div[id$="_results"] .thumbnail-item > img');
if (!galleryPreviews) return;
const headImg = galleryPreviews[0]?.src;
if (!headImg || headImg == lastHeadImg || headImg.endsWith('logo.png')) return;
if (!headImg || headImg === lastHeadImg || headImg.endsWith('logo.png')) return;
const audioNotification = gradioApp().querySelector('#audio_notification audio');
if (audioNotification) audioNotification.play();
lastHeadImg = headImg;
@@ -26,4 +26,7 @@ onAfterUiUpdate(function () {
parent.focus();
this.close();
};
});
console.log('sendNotification');
}
onAfterUiUpdate(initNotifications);
+20 -24
View File
@@ -1,14 +1,10 @@
let lastState = {};
function rememberGallerySelection(id_gallery) {}
function getGallerySelectedIndex(id_gallery) {}
function request(url, data, handler, errorHandler) {
const xhr = new XMLHttpRequest();
xhr.open('POST', url, true);
xhr.setRequestHeader('Content-Type', 'application/json');
xhr.onreadystatechange = function () {
xhr.onreadystatechange = () => {
if (xhr.readyState === 4) {
if (xhr.status === 200) {
try {
@@ -39,33 +35,33 @@ function formatTime(secs) {
function checkPaused(state) {
lastState.paused = state ? !state : !lastState.paused;
document.getElementById('txt2img_pause').innerText = lastState.paused ? 'Resume' : 'Pause'
document.getElementById('img2img_pause').innerText = lastState.paused ? 'Resume' : 'Pause'
document.getElementById('txt2img_pause').innerText = lastState.paused ? 'Resume' : 'Pause';
document.getElementById('img2img_pause').innerText = lastState.paused ? 'Resume' : 'Pause';
}
function setProgress(res) {
elements = ['txt2img_generate', 'img2img_generate', 'extras_generate']
const progress = (res?.progress || 0)
const perc = res && (progress > 0) ? `${Math.round(100.0 * progress)}%` : ''
let sec = res?.eta || 0
const elements = ['txt2img_generate', 'img2img_generate', 'extras_generate'];
const progress = (res?.progress || 0);
const perc = res && (progress > 0) ? `${Math.round(100.0 * progress)}%` : '';
let sec = res?.eta || 0;
let eta = '';
if (res?.paused) eta = 'Paused';
else if (res?.completed || (progress > 0.99)) eta = 'Finishing';
else if (sec === 0) eta = 'Starting';
else {
min = Math.floor(sec / 60);
sec = sec % 60;
eta = min > 0 ? `ETA: ${Math.round(min)}m ${Math.round(sec)}s` : `ETA: ${Math.round(sec)}s`;
const min = Math.floor(sec / 60);
sec %= 60;
eta = min > 0 ? `ETA: ${Math.round(min)}m ${Math.round(sec)}s` : `ETA: ${Math.round(sec)}s`;
}
document.title = 'SD.Next ' + perc;
for (elId of elements) {
el = document.getElementById(elId);
document.title = `SD.Next ${perc}`;
for (const elId of elements) {
const el = document.getElementById(elId);
el.innerText = res
? `${perc} ${eta}`
: 'Generate';
el.style.background = res
el.style.background = res
? `linear-gradient(to right, var(--primary-500) 0%, var(--primary-800) ${perc}, var(--neutral-700) ${perc})`
: 'var(--button-primary-background-fill)'
: 'var(--button-primary-background-fill)';
}
}
@@ -99,15 +95,15 @@ function requestProgress(id_task, progressEl, galleryEl, atEnd = null, onProgres
livePreview.style.width = `${rect.width}px`;
livePreview.style.height = `${rect.height}px`;
}
img.onload = function () {
img.onload = () => {
livePreview.appendChild(img);
if (livePreview.childElementCount > 2) livePreview.removeChild(livePreview.firstElementChild);
};
}
}
};
const done = () => {
console.debug('task end: ', id_task);
console.debug('taskEnd:', id_task);
localStorage.removeItem('task');
setProgress();
if (parentGallery && livePreview) parentGallery.removeChild(livePreview);
@@ -115,12 +111,12 @@ function requestProgress(id_task, progressEl, galleryEl, atEnd = null, onProgres
if (atEnd) atEnd();
};
const start = (id_task, id_live_preview) => {
const start = (id_task, id_live_preview) => { // eslint-disable-line no-shadow
request('./internal/progress', { id_task, id_live_preview }, (res) => {
lastState = res;
const elapsedFromStart = (new Date() - dateStart) / 1000;
hasStarted |= res.active;
if (res.completed || (!res.active && (hasStarted || once)) || (elapsedFromStart > 30 && !res.queued && res.progress == prevProgress)) {
if (res.completed || (!res.active && (hasStarted || once)) || (elapsedFromStart > 30 && !res.queued && res.progress === prevProgress)) {
done();
return;
}
+20 -29
View File
@@ -4,39 +4,30 @@
// If there's a mismatch, the keyword counter turns red and if you hover on it, a tooltip tells you what's wrong.
function checkBrackets(textArea, counterElt) {
var counts = {};
(textArea.value.match(/[(){}[\]]/g) || []).forEach(bracket => {
counts[bracket] = (counts[bracket] || 0) + 1;
});
var errors = [];
const counts = {};
(textArea.value.match(/[(){}[\]]/g) || []).forEach((bracket) => { counts[bracket] = (counts[bracket] || 0) + 1; });
const errors = [];
function checkPair(open, close, kind) {
if (counts[open] !== counts[close]) {
errors.push(
`${open}...${close} - Detected ${counts[open] || 0} opening and ${counts[close] || 0} closing ${kind}.`
);
}
}
function checkPair(open, close, kind) {
if (counts[open] !== counts[close]) errors.push(`${open}...${close} - Detected ${counts[open] || 0} opening and ${counts[close] || 0} closing ${kind}.`);
}
checkPair('(', ')', 'round brackets');
checkPair('[', ']', 'square brackets');
checkPair('{', '}', 'curly brackets');
counterElt.title = errors.join('\n');
counterElt.classList.toggle('error', errors.length !== 0);
checkPair('(', ')', 'round brackets');
checkPair('[', ']', 'square brackets');
checkPair('{', '}', 'curly brackets');
counterElt.title = errors.join('\n');
counterElt.classList.toggle('error', errors.length !== 0);
}
function setupBracketChecking(id_prompt, id_counter) {
var textarea = gradioApp().querySelector("#" + id_prompt + " > label > textarea");
var counter = gradioApp().getElementById(id_counter);
if (textarea && counter) {
textarea.addEventListener("input", () => checkBrackets(textarea, counter));
}
function setupBracketChecking(idPrompt, idCounter) {
const textarea = gradioApp().querySelector(`#${idPrompt} > label > textarea`);
const counter = gradioApp().getElementById(idCounter);
if (textarea && counter) textarea.addEventListener('input', () => checkBrackets(textarea, counter));
}
onAfterUiUpdate(function() {
setupBracketChecking('txt2img_prompt', 'txt2img_token_counter');
setupBracketChecking('txt2img_neg_prompt', 'txt2img_negative_token_counter');
setupBracketChecking('img2img_prompt', 'img2img_token_counter');
setupBracketChecking('img2img_neg_prompt', 'img2img_negative_token_counter');
onAfterUiUpdate(() => {
setupBracketChecking('txt2img_prompt', 'txt2img_token_counter');
setupBracketChecking('txt2img_neg_prompt', 'txt2img_negative_token_counter');
setupBracketChecking('img2img_prompt', 'img2img_token_counter');
setupBracketChecking('img2img_neg_prompt', 'img2img_negative_token_counter');
});
+10 -10
View File
@@ -1,15 +1,15 @@
function gradioApp() {
const elems = document.getElementsByTagName('gradio-app');
const elem = elems.length === 0 ? document : elems[0];
if (elem !== document) elem.getElementById = function (id) { return document.getElementById(id); };
if (elem !== document) elem.getElementById = (id) => document.getElementById(id);
return elem.shadowRoot ? elem.shadowRoot : elem;
}
function get_uiCurrentTab() {
function getUICurrentTab() {
return gradioApp().querySelector('#tabs button.selected');
}
function get_uiCurrentTabContent() {
function getUICurrentTabContent() {
return gradioApp().querySelector('.tabitem[id^=tab_]:not([style*="display: none"])');
}
@@ -44,11 +44,11 @@ function onOptionsChanged(callback) {
function executeCallbacks(queue, arg) {
// if (!uiLoaded) return
for (const callback of queue) {
try {
callback(arg);
} catch (e) {
console.error("error running callback", callback, ":", e);
}
try {
callback(arg);
} catch (e) {
console.error('error running callback', callback, ':', e);
}
}
}
@@ -67,7 +67,7 @@ document.addEventListener('DOMContentLoaded', () => {
}
executeCallbacks(uiUpdateCallbacks, m);
scheduleAfterUiUpdateCallbacks();
const newTab = get_uiCurrentTab();
const newTab = getUICurrentTab();
if (newTab && (newTab !== uiCurrentTab)) {
uiCurrentTab = newTab;
executeCallbacks(uiTabChangeCallbacks);
@@ -87,7 +87,7 @@ document.addEventListener('keydown', (e) => {
if ((e.keyCode === 13 && (e.metaKey || e.ctrlKey || e.altKey))) handled = true;
}
if (handled) {
button = get_uiCurrentTabContent().querySelector('button[id$=_generate]');
const button = getUICurrentTabContent().querySelector('button[id$=_generate]');
if (button) button.click();
e.preventDefault();
}
+16 -17
View File
@@ -1,16 +1,16 @@
let locale = {
const locale = {
data: [],
timeout: null,
finished: false,
type: 2,
el: null,
}
};
function tooltipCreate() {
locale.el = document.createElement('div');
locale.el.className = 'tooltip';
locale.el.id = 'tooltip-container';
locale.el.innerText = 'this is a hint'
locale.el.innerText = 'this is a hint';
gradioApp().appendChild(locale.el);
if (window.opts.tooltips === 'None') locale.type = 0;
if (window.opts.tooltips === 'Browser default') locale.type = 1;
@@ -29,28 +29,28 @@ async function tooltipHide(e) {
}
async function validateHints(elements, data) {
let original = elements.map(e => e.textContent.toLowerCase().trim()).sort((a, b) => a > b)
let original = elements.map((e) => e.textContent.toLowerCase().trim()).sort((a, b) => a > b);
original = [...new Set(original)];
console.log('all hints:', original)
console.log('all hints:', original);
console.log('hints-differences', { elements: original.length, hints: data.length });
const current = data.map(e => e.label.toLowerCase().trim()).sort((a, b) => a > b)
const current = data.map((e) => e.label.toLowerCase().trim()).sort((a, b) => a > b);
let missing = [];
for (let i = 0; i < original.length; i++) {
if (!current.includes(original[i])) missing.push(original[i]);
}
console.log('missing in locale:', missing)
console.log('missing in locale:', missing);
missing = [];
for (let i = 0; i < current.length; i++) {
if (!original.includes(current[i])) missing.push(current[i]);
}
console.log('in locale but not ui:', missing)
console.log('in locale but not ui:', missing);
}
async function setHints() {
if (locale.finished) return;
if (locale.data.length === 0) {
const res = await fetch('/file=html/locale_en.json');
const json = await res.json();
const json = await res.json();
locale.data = Object.values(json).flat();
}
const elements = [
@@ -59,15 +59,12 @@ async function setHints() {
];
if (elements.length === 0) return;
if (Object.keys(opts).length === 0) return;
if (!locale.el) {
tooltipCreate();
logMonitorCreate();
}
if (!locale.el) tooltipCreate();
let localized = 0;
let hints = 0;
locale.finished = true;
for (el of elements) {
const found = locale.data.find(l => l.label === el.textContent.trim());
for (const el of elements) {
const found = locale.data.find((l) => l.label === el.textContent.trim());
if (found?.localized?.length > 0) {
localized++;
el.textContent = found.localized;
@@ -85,11 +82,13 @@ async function setHints() {
}
}
}
console.log('set-hints', { type: locale.type, elements: elements.length, localized, hints, data: locale.data.length });
console.log('setHints', {
type: locale.type, elements: elements.length, localized, hints, data: locale.data.length,
});
// validateHints(elements, locale.data)
}
onAfterUiUpdate(async () => {
if (locale.timeout) clearTimeout(locale.timeout);
locale.timeout = setTimeout(setHints, 250)
locale.timeout = setTimeout(setHints, 250);
});
+3 -1
View File
@@ -388,7 +388,8 @@ div#extras_scale_to_tab div.form{
width: 100%;
height: 100%;
overflow: auto;
background-color: rgba(20, 20, 20, 0.95);
background-color: rgba(20, 20, 20, 0.75);
backdrop-filter: blur(6px);
user-select: none;
-webkit-user-select: none;
flex-direction: row;
@@ -399,6 +400,7 @@ div#extras_scale_to_tab div.form{
.modalControls span { color: white; font-size: 2em; font-weight: bold; cursor: pointer; filter: grayscale(100%); }
.modalControls span:hover, .modalControls span:focus { color: var(--highlight-color); filter: none; }
.lightboxModalPreviewZone { display: flex; width: 100%; height: 100%; }
.lightboxModalPreviewZone:focus-visible { outline: none; }
.lightboxModalPreviewZone > img { display: block; margin: auto; width: auto; }
.lightboxModalPreviewZone > img.modalImageFullscreen{ object-fit: contain; height: 100%; width: 100%; min-height: 0; background: transparent; }
+7 -7
View File
@@ -1,9 +1,9 @@
function start_train_monitoring() {
gradioApp().querySelector('#train_error').innerHTML=''
var id = randomId()
function startTrainMonitor() {
gradioApp().querySelector('#train_error').innerHTML = '';
const id = randomId();
const onProgress = (progress) => gradioApp().getElementById('train_progress').innerHTML = progress.textinfo;
requestProgress(id, gradioApp().getElementById('train_gallery'), null, onProgress, false)
var res = Array.from(arguments);
res[0] = id
return res
requestProgress(id, gradioApp().getElementById('train_gallery'), null, onProgress, false);
const res = Array.from(arguments);
res[0] = id;
return res;
}
+144 -148
View File
@@ -2,17 +2,27 @@ window.opts = {};
window.localization = {};
window.titles = {};
let tabSelected = '';
let txt2img_textarea;
let img2img_textarea;
const wait_time = 800;
const token_timeouts = {};
let uiLoaded = false;
function set_theme(theme) {
const gradioURL = window.location.href;
if (!gradioURL.includes('?__theme=')) window.location.replace(`${gradioURL}?__theme=${theme}`);
}
function update_token_counter(button_id) {
if (token_timeouts[button_id]) clearTimeout(token_timeouts[button_id]);
token_timeouts[button_id] = setTimeout(() => gradioApp().getElementById(button_id)?.click(), wait_time);
}
function clip_gallery_urls(gallery) {
const files = gallery.map((v) => v.data);
navigator.clipboard.writeText(JSON.stringify(files)).then(
() => console.log('clipboard set:', files),
(err) => console.log('clipboard error:', files, err)
() => console.log('clipboard:', files),
(err) => console.error('clipboard:', files, err),
);
}
@@ -97,20 +107,20 @@ function get_tab_index(tabId) {
}
function create_tab_index_args(tabId, args) {
let res = Array.from(args);
const res = Array.from(args);
res[0] = get_tab_index(tabId);
return res;
}
function get_img2img_tab_index(...args) {
let res = Array.from(arguments);
const res = Array.from(arguments);
res.splice(-2);
res[0] = get_tab_index('mode_img2img');
return res;
}
function create_submit_args(args) {
var res = Array.from(args);
const res = Array.from(args);
// As it is currently, txt2img and img2img send back the previous output args (txt2img_gallery, generation_info, html_info) whenever you generate a new image.
// This can lead to uploading a huge gallery of previously generated images, which leads to an unnecessary delay between submitting and beginning to generate.
// I don't know why gradio is sending outputs along with inputs, but we can prevent sending the image gallery here, which seems to be an issue for some.
@@ -122,16 +132,15 @@ function create_submit_args(args) {
function showSubmitButtons(tabname, show) {}
function clearGallery(tabname) {
const gallery = gradioApp().getElementById(`${tabname}_gallery`)
const gallery = gradioApp().getElementById(`${tabname}_gallery`);
gallery.classList.remove('logo');
// gallery.style.height = window.innerHeight - gallery.getBoundingClientRect().top - 200 + 'px'
const footer = gradioApp().getElementById(`${tabname}_footer`)
const footer = gradioApp().getElementById(`${tabname}_footer`);
footer.style.display = 'flex';
}
function submit(...args) {
console.log('Submit txt2img');
rememberGallerySelection('txt2img_gallery');
console.log('submitTxt');
clearGallery('txt2img');
const id = randomId();
requestProgress(id, null, gradioApp().getElementById('txt2img_gallery'));
@@ -141,8 +150,7 @@ function submit(...args) {
}
function submit_img2img(...args) {
console.log('Submit img2img');
rememberGallerySelection('img2img_gallery');
console.log('submitImg');
clearGallery('img2img');
const id = randomId();
requestProgress(id, null, gradioApp().getElementById('img2img_gallery'));
@@ -153,12 +161,11 @@ function submit_img2img(...args) {
}
function submit_postprocessing(...args) {
console.log('Submit extras');
console.log('SubmitExtras');
clearGallery('extras');
return args
return args;
}
function modelmerger(...args) {
const id = randomId();
const res = create_submit_args(args);
@@ -167,7 +174,7 @@ function modelmerger(...args) {
}
function ask_for_style_name(_, prompt_text, negative_prompt_text) {
const name = prompt('Style name:');
const name = prompt('Style name:'); // eslint-disable-line no-alert
return [name, prompt_text, negative_prompt_text];
}
@@ -219,23 +226,24 @@ function register_drag_drop() {
});
}
opts = {}
opts_metadata = {}
function updateOpts(json_string){
let settings_data = JSON.parse(json_string)
opts = settings_data.values
opts_metadata = settings_data.metadata
opts_tabs = {}
Object.entries(opts_metadata).forEach(([opt, meta]) => {
opts_tabs[meta.tab_name] ||= {}
let unsaved = (opts_tabs[meta.tab_name].unsaved_keys ||= new Set())
if (!meta.is_stored) unsaved.add(opt)
})
opts = {};
let opts_metadata = {};
const opts_tabs = {};
function updateOpts(json_string) {
const settings_data = JSON.parse(json_string);
opts = settings_data.values;
opts_metadata = settings_data.metadata;
Object.entries(opts_metadata).forEach(([opt, meta]) => {
if (!opts_tabs[meta.tab_name]) opts_tabs[meta.tab_name] = {};
if (!opts_tabs[meta.tab_name].unsaved_keys) opts_tabs[meta.tab_name].unsaved_keys = new Set();
if (!meta.is_stored) opts_tabs[meta.tab_name].unsaved_keys.add(opt);
});
}
function showAllSettings() {
// Try to ensure that the show all settings tab is opened by clicking on its tab button
let tab_dirty_indicator = gradioApp().getElementById('modification_indicator_show_all_pages');
const tab_dirty_indicator = gradioApp().getElementById('modification_indicator_show_all_pages');
if (tab_dirty_indicator && tab_dirty_indicator.nextSibling) {
tab_dirty_indicator.nextSibling.click();
}
@@ -245,7 +253,71 @@ function showAllSettings() {
});
}
onAfterUiUpdate(() => {
function sort_ui_elements() {
// sort top-level tabs
const currSelected = gradioApp()?.querySelector('.tab-nav > .selected')?.innerText;
if (currSelected === tabSelected || !opts.ui_tab_reorder) return;
tabSelected = currSelected;
const tabs = gradioApp().getElementById('tabs')?.children[0];
if (!tabs) return;
let tabsOrder = opts.ui_tab_reorder?.split(',').map((el) => el.trim().toLowerCase()) || [];
for (const el of Array.from(tabs.children)) {
const elIndex = tabsOrder.indexOf(el.innerText.toLowerCase());
if (elIndex > -1) el.style.order = elIndex - 50; // default is 0 so setting to negative values
}
// sort always-on scripts
const find = (el, ordered) => {
for (const i in ordered) {
if (el.innerText.toLowerCase().startsWith(ordered[i])) return i;
}
return 99;
};
tabsOrder = opts.ui_scripts_reorder?.split(',').map((el) => el.trim().toLowerCase()) || [];
const scriptsTxt = gradioApp().getElementById('scripts_alwayson_txt2img').children;
for (const el of Array.from(scriptsTxt)) el.style.order = find(el, tabsOrder);
const scriptsImg = gradioApp().getElementById('scripts_alwayson_img2img').children;
for (const el of Array.from(scriptsImg)) el.style.order = find(el, tabsOrder);
}
function markIfModified(setting_name, value) {
const elem = gradioApp().getElementById(`modification_indicator_${setting_name}`);
if (elem == null) return;
// Use JSON.stringify to compare nested objects (e.g. arrays for checkbox-groups)
const previous_value_json = JSON.stringify(opts[setting_name]);
const changed_value = JSON.stringify(value) !== previous_value_json;
if (changed_value) {
elem.title = `Click to revert to previous value: ${previous_value_json}`;
}
const is_unsaved = !opts_metadata[setting_name].is_stored;
if (is_unsaved) {
elem.title = 'Default value (not saved to config)';
}
elem.disabled = !(is_unsaved || changed_value);
elem.classList.toggle('changed', changed_value);
elem.classList.toggle('unsaved', is_unsaved);
const { tab_name } = opts_metadata[setting_name];
if (!opts_tabs[tab_name].changed) opts_tabs[tab_name].changed = new Set();
const changed_items = opts_tabs[tab_name].changed;
if (changed_value) changed_items.add(setting_name);
else changed_items.delete(setting_name);
const unsaved = opts_tabs[tab_name].unsaved_keys;
// Set the indicator on the tab nav element
const tab_nav_indicator = gradioApp().getElementById(`modification_indicator_${tab_name}`);
tab_nav_indicator.disabled = (changed_items.size === 0) && (unsaved.size === 0);
tab_nav_indicator.title = '';
tab_nav_indicator.classList.toggle('changed', changed_items.size > 0);
tab_nav_indicator.classList.toggle('unsaved', unsaved.size > 0);
if (changed_items.size > 0) { tab_nav_indicator.title += `Click to reset ${changed_items.size} unapplied change${changed_items.size > 1 ? 's' : ''} in this tab.\n`; }
if (unsaved.size > 0) { tab_nav_indicator.title += `${unsaved.size} new default value${unsaved.size > 1 ? 's' : ''} (not yet saved).`; }
}
onAfterUiUpdate(async () => {
sort_ui_elements();
if (Object.keys(opts).length !== 0) return;
const json_elem = gradioApp().getElementById('settings_json');
@@ -295,9 +367,9 @@ onAfterUiUpdate(() => {
section.querySelectorAll('.dirtyable').forEach((setting) => {
const visible = setting.innerText.toLowerCase().includes(e.target.value.toLowerCase()) || setting.id.toLowerCase().includes(e.target.value.toLowerCase());
if (!visible) {
setting.style.display = 'none'
setting.style.display = 'none';
} else {
setting.style.removeProperty('display')
setting.style.removeProperty('display');
}
});
});
@@ -317,90 +389,49 @@ onOptionsChanged(() => {
}
});
onOptionsChanged(function(){
let setting_elems = gradioApp().querySelectorAll('#settings [id^="setting_"]')
setting_elems.forEach(function(elem){
setting_name = elem.id.replace("setting_", "")
markIfModified(setting_name, opts[setting_name])
})
})
onOptionsChanged(() => {
const setting_elems = gradioApp().querySelectorAll('#settings [id^="setting_"]');
setting_elems.forEach((elem) => {
const setting_name = elem.id.replace('setting_', '');
markIfModified(setting_name, opts[setting_name]);
});
});
onUiLoaded(function(){
let tab_nav_element = gradioApp().querySelector('#settings > .tab-nav')
let tab_nav_buttons = gradioApp().querySelectorAll('#settings > .tab-nav > button')
let tab_elements = gradioApp().querySelectorAll('#settings > div:not(.tab-nav)')
onUiLoaded(() => {
const tab_nav_element = gradioApp().querySelector('#settings > .tab-nav');
const tab_nav_buttons = gradioApp().querySelectorAll('#settings > .tab-nav > button');
const tab_elements = gradioApp().querySelectorAll('#settings > div:not(.tab-nav)');
// HACK Add mutation observer to keep gradio from closing setting tabs when showing all pages
const observer = new MutationObserver(function(mutations) {
const show_all_pages_dummy = gradioApp().getElementById('settings_show_all_pages')
if (show_all_pages_dummy.style.display == "none")
return;
function mutation_on_style(mut) {
return mut.type === 'attributes' && mut.attributeName === 'style'
}
if (mutations.some(mutation_on_style)) {
showAllSettings();
}
})
// Add a wrapper for the tab content (everything but the tab nav)
const tab_content_wrapper = document.createElement('div')
tab_content_wrapper.className = "tab-content"
tab_nav_element.parentElement.insertBefore(tab_content_wrapper, tab_nav_element.nextSibling)
tab_elements.forEach(function(elem, index){
// Move the modification indicator to the toplevel tab button
let tab_name = elem.id.replace("settings_", "")
let indicator = gradioApp().getElementById("modification_indicator_"+tab_name)
tab_nav_element.insertBefore(indicator, tab_nav_buttons[index])
// Add the tab content to the wrapper
tab_content_wrapper.appendChild(elem)
// Add the mutation observer to the tab element
observer.observe(elem, { attributes: true, attributeFilter: ['style'] })
})
})
function markIfModified(setting_name, value) {
let elem = gradioApp().getElementById("modification_indicator_"+setting_name)
if(elem == null) return;
// Use JSON.stringify to compare nested objects (e.g. arrays for checkbox-groups)
let previous_value_json = JSON.stringify(opts[setting_name])
let changed_value = JSON.stringify(value) != previous_value_json
if (changed_value) {
elem.title = `Click to revert to previous value: ${previous_value_json}`
// HACK Add mutation observer to keep gradio from closing setting tabs when showing all pages
const observer = new MutationObserver((mutations) => {
const show_all_pages_dummy = gradioApp().getElementById('settings_show_all_pages');
if (show_all_pages_dummy.style.display === 'none') { return; }
function mutation_on_style(mut) {
return mut.type === 'attributes' && mut.attributeName === 'style';
}
is_unsaved = !opts_metadata[setting_name].is_stored
if (is_unsaved) {
elem.title = 'Default value (not saved to config)';
if (mutations.some(mutation_on_style)) {
showAllSettings();
}
elem.disabled = !(is_unsaved || changed_value)
elem.classList.toggle('changed', changed_value)
elem.classList.toggle('unsaved', is_unsaved)
});
let tab_name = opts_metadata[setting_name].tab_name
let changed_items = (opts_tabs[tab_name].changed ||= new Set())
changed_value ? changed_items.add(setting_name) : changed_items.delete(setting_name)
let unsaved = opts_tabs[tab_name].unsaved_keys
// Add a wrapper for the tab content (everything but the tab nav)
const tab_content_wrapper = document.createElement('div');
tab_content_wrapper.className = 'tab-content';
tab_nav_element.parentElement.insertBefore(tab_content_wrapper, tab_nav_element.nextSibling);
// Set the indicator on the tab nav element
let tab_nav_indicator = gradioApp().getElementById('modification_indicator_'+tab_name)
tab_nav_indicator.disabled = (changed_items.size == 0) && (unsaved.size == 0)
tab_nav_indicator.title = '';
tab_nav_indicator.classList.toggle('changed', changed_items.size > 0)
tab_nav_indicator.classList.toggle('unsaved', unsaved.size > 0)
if (changed_items.size > 0)
tab_nav_indicator.title += `Click to reset ${changed_items.size} unapplied change${changed_items.size > 1 ? 's': ''} in this tab.\n`
if (unsaved.size > 0)
tab_nav_indicator.title += `${unsaved.size} new default value${unsaved.size > 1 ? 's':''} (not yet saved).`;
}
tab_elements.forEach((elem, index) => {
// Move the modification indicator to the toplevel tab button
const tab_name = elem.id.replace('settings_', '');
const indicator = gradioApp().getElementById(`modification_indicator_${tab_name}`);
tab_nav_element.insertBefore(indicator, tab_nav_buttons[index]);
let txt2img_textarea;
let img2img_textarea;
const wait_time = 800;
const token_timeouts = {};
// Add the tab content to the wrapper
tab_content_wrapper.appendChild(elem);
// Add the mutation observer to the tab element
observer.observe(elem, { attributes: true, attributeFilter: ['style'] });
});
});
function update_txt2img_tokens(...args) {
update_token_counter('txt2img_token_button');
@@ -418,11 +449,6 @@ function getTranslation(...args) {
return null;
}
function update_token_counter(button_id) {
if (token_timeouts[button_id]) clearTimeout(token_timeouts[button_id]);
token_timeouts[button_id] = setTimeout(() => gradioApp().getElementById(button_id)?.click(), wait_time);
}
function monitor_server_status() {
document.open();
document.write(`
@@ -484,35 +510,6 @@ function create_theme_element() {
return el;
}
function sort_ui_elements() {
// sort top-level tabs
const currSelected = gradioApp()?.querySelector('.tab-nav > .selected')?.innerText;
if (currSelected === tabSelected || !opts.ui_tab_reorder) return;
tabSelected = currSelected;
const tabs = gradioApp().getElementById('tabs')?.children[0];
if (!tabs) return;
let tabsOrder = opts.ui_tab_reorder?.split(',').map((el) => el.trim().toLowerCase()) || [];
for (const el of Array.from(tabs.children)) {
const elIndex = tabsOrder.indexOf(el.innerText.toLowerCase());
if (elIndex > -1) el.style.order = elIndex - 50; // default is 0 so setting to negative values
}
// sort always-on scripts
const find = (el, ordered) => {
for (const i in ordered) {
if (el.innerText.toLowerCase().startsWith(ordered[i])) return i;
}
return 99;
};
tabsOrder = opts.ui_scripts_reorder?.split(',').map((el) => el.trim().toLowerCase()) || [];
const scriptsTxt = gradioApp().getElementById('scripts_alwayson_txt2img').children;
for (const el of Array.from(scriptsTxt)) el.style.order = find(el, tabsOrder);
const scriptsImg = gradioApp().getElementById('scripts_alwayson_img2img').children;
for (const el of Array.from(scriptsImg)) el.style.order = find(el, tabsOrder);
}
function preview_theme() {
const name = gradioApp().getElementById('setting_gradio_theme').querySelectorAll('input')?.[0].value || '';
if (name === 'black-orange' || name.startsWith('gradio/')) {
@@ -530,19 +527,16 @@ function preview_theme() {
}
}
let uiLoaded = false;
function reconnect_ui() {
function reconnectUI() {
const api_logo = Array.from(gradioApp().querySelectorAll('img')).filter((el) => el?.src?.endsWith('api-logo.svg'));
if (api_logo.length > 0) api_logo[0].remove();
const gallery = gradioApp().getElementById('txt2img_gallery');
const task_id = localStorage.getItem('task');
if (!gallery) return;
clearInterval(start_check);
clearInterval(start_check); // eslint-disable-line no-use-before-define
if (task_id) {
console.debug('task check:', task_id);
rememberGallerySelection('txt2img_gallery');
requestProgress(task_id, null, gallery, null, null, true);
}
uiLoaded = true;
@@ -550,6 +544,7 @@ function reconnect_ui() {
const sd_model = gradioApp().getElementById('setting_sd_model_checkpoint');
let loadingStarted = 0;
let loadingMonitor = 0;
const sd_model_callback = () => {
const loading = sd_model.querySelector('.eta-bar');
if (!loading) {
@@ -565,6 +560,7 @@ function reconnect_ui() {
};
const sd_model_observer = new MutationObserver(sd_model_callback);
sd_model_observer.observe(sd_model, { attributes: true, childList: true, subtree: true });
console.log('reconnectUI');
}
const start_check = setInterval(reconnect_ui, 50);
const start_check = setInterval(reconnectUI, 50);