From 9c54b78d9dde5601e916f308d9a9d6953ec39430 Mon Sep 17 00:00:00 2001 From: Aarni Koskela Date: Wed, 17 May 2023 15:46:58 +0300 Subject: Run `eslint --fix` (and normalize tabs to spaces) --- script.js | 74 ++++++++++++++++++++++++++++++++++----------------------------- 1 file changed, 40 insertions(+), 34 deletions(-) (limited to 'script.js') diff --git a/script.js b/script.js index 03afe844..f6a3883a 100644 --- a/script.js +++ b/script.js @@ -1,66 +1,72 @@ function gradioApp() { - const elems = document.getElementsByTagName('gradio-app') - const elem = elems.length == 0 ? document : elems[0] + 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) } - return elem.shadowRoot ? elem.shadowRoot : elem + if (elem !== document) { + elem.getElementById = function(id) { + return document.getElementById(id); + }; + } + return elem.shadowRoot ? elem.shadowRoot : elem; } function get_uiCurrentTab() { - return gradioApp().querySelector('#tabs button.selected') + return gradioApp().querySelector('#tabs button.selected'); } function get_uiCurrentTabContent() { - return gradioApp().querySelector('.tabitem[id^=tab_]:not([style*="display: none"])') + return gradioApp().querySelector('.tabitem[id^=tab_]:not([style*="display: none"])'); } -uiUpdateCallbacks = [] -uiLoadedCallbacks = [] -uiTabChangeCallbacks = [] -optionsChangedCallbacks = [] -let uiCurrentTab = null +uiUpdateCallbacks = []; +uiLoadedCallbacks = []; +uiTabChangeCallbacks = []; +optionsChangedCallbacks = []; +let uiCurrentTab = null; -function onUiUpdate(callback){ - uiUpdateCallbacks.push(callback) +function onUiUpdate(callback) { + uiUpdateCallbacks.push(callback); } -function onUiLoaded(callback){ - uiLoadedCallbacks.push(callback) +function onUiLoaded(callback) { + uiLoadedCallbacks.push(callback); } -function onUiTabChange(callback){ - uiTabChangeCallbacks.push(callback) +function onUiTabChange(callback) { + uiTabChangeCallbacks.push(callback); } -function onOptionsChanged(callback){ - optionsChangedCallbacks.push(callback) +function onOptionsChanged(callback) { + optionsChangedCallbacks.push(callback); } -function runCallback(x, m){ +function runCallback(x, m) { try { - x(m) + x(m); } catch (e) { (console.error || console.log).call(console, e.message, e); } } function executeCallbacks(queue, m) { - queue.forEach(function(x){runCallback(x, m)}) + queue.forEach(function(x) { + runCallback(x, m); + }); } var executedOnLoaded = false; document.addEventListener("DOMContentLoaded", function() { - var mutationObserver = new MutationObserver(function(m){ - if(!executedOnLoaded && gradioApp().querySelector('#txt2img_prompt')){ + var mutationObserver = new MutationObserver(function(m) { + if (!executedOnLoaded && gradioApp().querySelector('#txt2img_prompt')) { executedOnLoaded = true; executeCallbacks(uiLoadedCallbacks); } executeCallbacks(uiUpdateCallbacks, m); const newTab = get_uiCurrentTab(); - if ( newTab && ( newTab !== uiCurrentTab ) ) { + if (newTab && (newTab !== uiCurrentTab)) { uiCurrentTab = newTab; executeCallbacks(uiTabChangeCallbacks); } }); - mutationObserver.observe( gradioApp(), { childList:true, subtree:true }) + mutationObserver.observe(gradioApp(), { childList: true, subtree: true }); }); /** @@ -69,9 +75,9 @@ document.addEventListener("DOMContentLoaded", function() { document.addEventListener('keydown', function(e) { var handled = false; if (e.key !== undefined) { - if((e.key == "Enter" && (e.metaKey || e.ctrlKey || e.altKey))) handled = true; + if ((e.key == "Enter" && (e.metaKey || e.ctrlKey || e.altKey))) handled = true; } else if (e.keyCode !== undefined) { - if((e.keyCode == 13 && (e.metaKey || e.ctrlKey || e.altKey))) handled = true; + if ((e.keyCode == 13 && (e.metaKey || e.ctrlKey || e.altKey))) handled = true; } if (handled) { button = get_uiCurrentTabContent().querySelector('button[id$=_generate]'); @@ -80,22 +86,22 @@ document.addEventListener('keydown', function(e) { } e.preventDefault(); } -}) +}); /** * checks that a UI element is not in another hidden element or tab content */ function uiElementIsVisible(el) { let isVisible = !el.closest('.\\!hidden'); - if ( ! isVisible ) { + if (!isVisible) { return false; } - while( isVisible = el.closest('.tabitem')?.style.display !== 'none' ) { - if ( ! isVisible ) { + while (isVisible = el.closest('.tabitem')?.style.display !== 'none') { + if (!isVisible) { return false; - } else if ( el.parentElement ) { - el = el.parentElement + } else if (el.parentElement) { + el = el.parentElement; } else { break; } -- cgit v1.2.3 From 57b75f4a037658c1122aa092d1775ac52036b2cf Mon Sep 17 00:00:00 2001 From: AUTOMATIC <16777216c@gmail.com> Date: Thu, 18 May 2023 09:59:10 +0300 Subject: eslint related file edits --- script.js | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) (limited to 'script.js') diff --git a/script.js b/script.js index f6a3883a..db4d9157 100644 --- a/script.js +++ b/script.js @@ -18,11 +18,11 @@ function get_uiCurrentTabContent() { return gradioApp().querySelector('.tabitem[id^=tab_]:not([style*="display: none"])'); } -uiUpdateCallbacks = []; -uiLoadedCallbacks = []; -uiTabChangeCallbacks = []; -optionsChangedCallbacks = []; -let uiCurrentTab = null; +var uiUpdateCallbacks = []; +var uiLoadedCallbacks = []; +var uiTabChangeCallbacks = []; +var optionsChangedCallbacks = []; +var uiCurrentTab = null; function onUiUpdate(callback) { uiUpdateCallbacks.push(callback); @@ -66,7 +66,7 @@ document.addEventListener("DOMContentLoaded", function() { executeCallbacks(uiTabChangeCallbacks); } }); - mutationObserver.observe(gradioApp(), { childList: true, subtree: true }); + mutationObserver.observe(gradioApp(), {childList: true, subtree: true}); }); /** @@ -80,7 +80,7 @@ document.addEventListener('keydown', function(e) { if ((e.keyCode == 13 && (e.metaKey || e.ctrlKey || e.altKey))) handled = true; } if (handled) { - button = get_uiCurrentTabContent().querySelector('button[id$=_generate]'); + var button = get_uiCurrentTabContent().querySelector('button[id$=_generate]'); if (button) { button.click(); } @@ -97,7 +97,7 @@ function uiElementIsVisible(el) { return false; } - while (isVisible = el.closest('.tabitem')?.style.display !== 'none') { + while ((isVisible = el.closest('.tabitem')?.style.display) !== 'none') { if (!isVisible) { return false; } else if (el.parentElement) { -- cgit v1.2.3 From e373fd0c009beed4cd78af78583bf71b425b118e Mon Sep 17 00:00:00 2001 From: Thottyottyotty Date: Thu, 18 May 2023 16:09:09 -0700 Subject: rewrite uiElementIsVisible rewrite visibility checking to be more generic/cleaner as well as add functionality to check if the element is scrolled on screen for more intuitive paste-target selection --- script.js | 24 +++++++++++------------- 1 file changed, 11 insertions(+), 13 deletions(-) (limited to 'script.js') diff --git a/script.js b/script.js index db4d9157..53390be3 100644 --- a/script.js +++ b/script.js @@ -92,19 +92,17 @@ document.addEventListener('keydown', function(e) { * checks that a UI element is not in another hidden element or tab content */ function uiElementIsVisible(el) { - let isVisible = !el.closest('.\\!hidden'); - if (!isVisible) { - return false; + if (el === document) { + return true; } - while ((isVisible = el.closest('.tabitem')?.style.display) !== 'none') { - if (!isVisible) { - return false; - } else if (el.parentElement) { - el = el.parentElement; - } else { - break; - } - } - return isVisible; + const computedStyle = getComputedStyle(el); + const isVisible = computedStyle.display !== 'none'; + + const clRect = el.getBoundingClientRect(); + const windowHeight = window.innerHeight; + const onScreen = clRect.bottom > 0 && clRect.top < windowHeight; + + if (!isVisible || !onScreen) return false; + return uiElementIsVisible(el.parentNode); } -- cgit v1.2.3 From 7b61acbd35e9db43a5279a42afad3f3dc68462c9 Mon Sep 17 00:00:00 2001 From: Thottyottyotty Date: Thu, 18 May 2023 23:43:01 -0700 Subject: split visibility method and sort instead split out the visibility method for pasting and use a sort inside the paste handler to prioritize on-screen fields rather than targeting ONLY on screen fields --- script.js | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) (limited to 'script.js') diff --git a/script.js b/script.js index 53390be3..f7612779 100644 --- a/script.js +++ b/script.js @@ -99,10 +99,14 @@ function uiElementIsVisible(el) { const computedStyle = getComputedStyle(el); const isVisible = computedStyle.display !== 'none'; + if (!isVisible) return false; + return uiElementIsVisible(el.parentNode); +} + +function uiElementInSight(el) { const clRect = el.getBoundingClientRect(); const windowHeight = window.innerHeight; - const onScreen = clRect.bottom > 0 && clRect.top < windowHeight; + const isOnScreen = clRect.bottom > 0 && clRect.top < windowHeight; - if (!isVisible || !onScreen) return false; - return uiElementIsVisible(el.parentNode); + return isOnScreen; } -- cgit v1.2.3 From f661fb0fd39cceca121b455cb0133e829cfe72aa Mon Sep 17 00:00:00 2001 From: Aarni Koskela Date: Thu, 25 May 2023 09:00:45 +0300 Subject: Just use console.error, it's in all browsers --- script.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'script.js') diff --git a/script.js b/script.js index f7612779..12f00cb1 100644 --- a/script.js +++ b/script.js @@ -41,7 +41,7 @@ function runCallback(x, m) { try { x(m); } catch (e) { - (console.error || console.log).call(console, e.message, e); + console.error("error running callback", x, ":", e); } } function executeCallbacks(queue, m) { -- cgit v1.2.3 From 9574ebe2128ae3a1b04935c13c3067e4c9a54e63 Mon Sep 17 00:00:00 2001 From: Aarni Koskela Date: Thu, 25 May 2023 09:02:38 +0300 Subject: Merge executeCallbacks and runCallback, simplify + optimize --- script.js | 16 +++++++--------- 1 file changed, 7 insertions(+), 9 deletions(-) (limited to 'script.js') diff --git a/script.js b/script.js index 12f00cb1..77758571 100644 --- a/script.js +++ b/script.js @@ -37,17 +37,15 @@ function onOptionsChanged(callback) { optionsChangedCallbacks.push(callback); } -function runCallback(x, m) { - try { - x(m); - } catch (e) { - console.error("error running callback", x, ":", e); +function executeCallbacks(queue, arg) { + for (const callback of queue) { + try { + callback(arg); + } catch (e) { + console.error("error running callback", callback, ":", e); + } } } -function executeCallbacks(queue, m) { - queue.forEach(function(x) { - runCallback(x, m); - }); } var executedOnLoaded = false; -- cgit v1.2.3 From 54696dce056ece694bbca3f6c0252532fdd05bbd Mon Sep 17 00:00:00 2001 From: Aarni Koskela Date: Thu, 25 May 2023 09:03:14 +0300 Subject: Document on* handlers (for extension authors' sake) --- script.js | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) (limited to 'script.js') diff --git a/script.js b/script.js index 77758571..46310f35 100644 --- a/script.js +++ b/script.js @@ -24,15 +24,35 @@ var uiTabChangeCallbacks = []; var optionsChangedCallbacks = []; var uiCurrentTab = null; +/** + * Register callback to be called at each UI update. + * The callback receives an array of MutationRecords as an argument. + */ function onUiUpdate(callback) { uiUpdateCallbacks.push(callback); } + +/** + * Register callback to be called when the UI is loaded. + * The callback receives no arguments. + */ function onUiLoaded(callback) { uiLoadedCallbacks.push(callback); } + +/** + * Register callback to be called when the UI tab is changed. + * The callback receives no arguments. + */ function onUiTabChange(callback) { uiTabChangeCallbacks.push(callback); } + +/** + * Register callback to be called when the options are changed. + * The callback receives no arguments. + * @param callback + */ function onOptionsChanged(callback) { optionsChangedCallbacks.push(callback); } -- cgit v1.2.3 From bc53ecf298478ecd9d01a78ece50fea06a609d6a Mon Sep 17 00:00:00 2001 From: Aarni Koskela Date: Thu, 25 May 2023 09:05:06 +0300 Subject: Add onAfterUiUpdate callback --- script.js | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+) (limited to 'script.js') diff --git a/script.js b/script.js index 46310f35..de9d7e22 100644 --- a/script.js +++ b/script.js @@ -19,9 +19,11 @@ function get_uiCurrentTabContent() { } var uiUpdateCallbacks = []; +var uiAfterUpdateCallbacks = []; var uiLoadedCallbacks = []; var uiTabChangeCallbacks = []; var optionsChangedCallbacks = []; +var uiAfterUpdateTimeout = null; var uiCurrentTab = null; /** @@ -32,6 +34,18 @@ function onUiUpdate(callback) { uiUpdateCallbacks.push(callback); } +/** + * Register callback to be called soon after UI updates. + * The callback receives no arguments. + * + * This is preferred over `onUiUpdate` if you don't need + * access to the MutationRecords, as your function will + * not be called quite as often. + */ +function onAfterUiUpdate(callback) { + uiAfterUpdateCallbacks.push(callback); +} + /** * Register callback to be called when the UI is loaded. * The callback receives no arguments. @@ -66,6 +80,18 @@ function executeCallbacks(queue, arg) { } } } + +/** + * Schedule the execution of the callbacks registered with onAfterUiUpdate. + * The callbacks are executed after a short while, unless another call to this function + * is made before that time. IOW, the callbacks are executed only once, even + * when there are multiple mutations observed. + */ +function scheduleAfterUiUpdateCallbacks() { + clearTimeout(uiAfterUpdateTimeout); + uiAfterUpdateTimeout = setTimeout(function() { + executeCallbacks(uiAfterUpdateCallbacks); + }, 200); } var executedOnLoaded = false; @@ -78,6 +104,7 @@ document.addEventListener("DOMContentLoaded", function() { } executeCallbacks(uiUpdateCallbacks, m); + scheduleAfterUiUpdateCallbacks(); const newTab = get_uiCurrentTab(); if (newTab && (newTab !== uiCurrentTab)) { uiCurrentTab = newTab; -- cgit v1.2.3 From f81931c591d4513420a0998bbf1591e35a92d14e Mon Sep 17 00:00:00 2001 From: Aarni Koskela Date: Tue, 30 May 2023 17:50:09 +0300 Subject: Frontend: only look at top-level tabs, not nested tabs Refs https://github.com/adieyal/sd-dynamic-prompts/issues/459#issuecomment-1568543926 --- script.js | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) (limited to 'script.js') diff --git a/script.js b/script.js index de9d7e22..34cca765 100644 --- a/script.js +++ b/script.js @@ -10,12 +10,18 @@ function gradioApp() { return elem.shadowRoot ? elem.shadowRoot : elem; } +/** + * Get the currently selected top-level UI tab button (e.g. the button that says "Extras"). + */ function get_uiCurrentTab() { - return gradioApp().querySelector('#tabs button.selected'); + return gradioApp().querySelector('#tabs > .tab-nav > button.selected'); } +/** + * Get the first currently visible top-level UI tab content (e.g. the div hosting the "txt2img" UI). + */ function get_uiCurrentTabContent() { - return gradioApp().querySelector('.tabitem[id^=tab_]:not([style*="display: none"])'); + return gradioApp().querySelector('#tabs > .tabitem[id^=tab_]:not([style*="display: none"])'); } var uiUpdateCallbacks = []; -- cgit v1.2.3