Merge pull request #10708 from akx/on-ui-update-throttled

Add onAfterUiUpdate callback
This commit is contained in:
AUTOMATIC1111 2023-05-27 20:09:15 +03:00 committed by GitHub
commit 2fc2fbb4ea
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
9 changed files with 65 additions and 21 deletions

View File

@ -50,13 +50,14 @@ module.exports = {
globals: { globals: {
//script.js //script.js
gradioApp: "readonly", gradioApp: "readonly",
executeCallbacks: "readonly",
onAfterUiUpdate: "readonly",
onOptionsChanged: "readonly",
onUiLoaded: "readonly", onUiLoaded: "readonly",
onUiUpdate: "readonly", onUiUpdate: "readonly",
onOptionsChanged: "readonly",
uiCurrentTab: "writable", uiCurrentTab: "writable",
uiElementIsVisible: "readonly",
uiElementInSight: "readonly", uiElementInSight: "readonly",
executeCallbacks: "readonly", uiElementIsVisible: "readonly",
//ui.js //ui.js
opts: "writable", opts: "writable",
all_gallery_buttons: "readonly", all_gallery_buttons: "readonly",

View File

@ -81,7 +81,7 @@ function dimensionChange(e, is_width, is_height) {
} }
onUiUpdate(function() { onAfterUiUpdate(function() {
var arPreviewRect = gradioApp().querySelector('#imageARPreview'); var arPreviewRect = gradioApp().querySelector('#imageARPreview');
if (arPreviewRect) { if (arPreviewRect) {
arPreviewRect.style.display = 'none'; arPreviewRect.style.display = 'none';

View File

@ -167,6 +167,4 @@ var addContextMenuEventListener = initResponse[2];
})(); })();
//End example Context Menu Items //End example Context Menu Items
onUiUpdate(function() { onAfterUiUpdate(addContextMenuEventListener);
addContextMenuEventListener();
});

View File

@ -1,7 +1,7 @@
// attaches listeners to the txt2img and img2img galleries to update displayed generation param text when the image changes // attaches listeners to the txt2img and img2img galleries to update displayed generation param text when the image changes
let txt2img_gallery, img2img_gallery, modal = undefined; let txt2img_gallery, img2img_gallery, modal = undefined;
onUiUpdate(function() { onAfterUiUpdate(function() {
if (!txt2img_gallery) { if (!txt2img_gallery) {
txt2img_gallery = attachGalleryListeners("txt2img"); txt2img_gallery = attachGalleryListeners("txt2img");
} }

View File

@ -39,5 +39,5 @@ function imageMaskResize() {
}); });
} }
onUiUpdate(imageMaskResize); onAfterUiUpdate(imageMaskResize);
window.addEventListener('resize', imageMaskResize); window.addEventListener('resize', imageMaskResize);

View File

@ -170,7 +170,7 @@ function modalTileImageToggle(event) {
event.stopPropagation(); event.stopPropagation();
} }
onUiUpdate(function() { onAfterUiUpdate(function() {
var fullImg_preview = gradioApp().querySelectorAll('.gradio-gallery > div > img'); var fullImg_preview = gradioApp().querySelectorAll('.gradio-gallery > div > img');
if (fullImg_preview != null) { if (fullImg_preview != null) {
fullImg_preview.forEach(setupImageForLightbox); fullImg_preview.forEach(setupImageForLightbox);

View File

@ -4,7 +4,7 @@ let lastHeadImg = null;
let notificationButton = null; let notificationButton = null;
onUiUpdate(function() { onAfterUiUpdate(function() {
if (notificationButton == null) { if (notificationButton == null) {
notificationButton = gradioApp().getElementById('request_notifications'); notificationButton = gradioApp().getElementById('request_notifications');

View File

@ -249,7 +249,7 @@ function confirm_clear_prompt(prompt, negative_prompt) {
var opts = {}; var opts = {};
onUiUpdate(function() { onAfterUiUpdate(function() {
if (Object.keys(opts).length != 0) return; if (Object.keys(opts).length != 0) return;
var json_elem = gradioApp().getElementById('settings_json'); var json_elem = gradioApp().getElementById('settings_json');

View File

@ -19,35 +19,79 @@ function get_uiCurrentTabContent() {
} }
var uiUpdateCallbacks = []; var uiUpdateCallbacks = [];
var uiAfterUpdateCallbacks = [];
var uiLoadedCallbacks = []; var uiLoadedCallbacks = [];
var uiTabChangeCallbacks = []; var uiTabChangeCallbacks = [];
var optionsChangedCallbacks = []; var optionsChangedCallbacks = [];
var uiAfterUpdateTimeout = null;
var uiCurrentTab = null; 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) { function onUiUpdate(callback) {
uiUpdateCallbacks.push(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.
*/
function onUiLoaded(callback) { function onUiLoaded(callback) {
uiLoadedCallbacks.push(callback); uiLoadedCallbacks.push(callback);
} }
/**
* Register callback to be called when the UI tab is changed.
* The callback receives no arguments.
*/
function onUiTabChange(callback) { function onUiTabChange(callback) {
uiTabChangeCallbacks.push(callback); uiTabChangeCallbacks.push(callback);
} }
/**
* Register callback to be called when the options are changed.
* The callback receives no arguments.
* @param callback
*/
function onOptionsChanged(callback) { function onOptionsChanged(callback) {
optionsChangedCallbacks.push(callback); optionsChangedCallbacks.push(callback);
} }
function runCallback(x, m) { function executeCallbacks(queue, arg) {
for (const callback of queue) {
try { try {
x(m); callback(arg);
} catch (e) { } catch (e) {
(console.error || console.log).call(console, e.message, e); console.error("error running callback", callback, ":", e);
} }
} }
function executeCallbacks(queue, m) { }
queue.forEach(function(x) {
runCallback(x, m); /**
}); * 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; var executedOnLoaded = false;
@ -60,6 +104,7 @@ document.addEventListener("DOMContentLoaded", function() {
} }
executeCallbacks(uiUpdateCallbacks, m); executeCallbacks(uiUpdateCallbacks, m);
scheduleAfterUiUpdateCallbacks();
const newTab = get_uiCurrentTab(); const newTab = get_uiCurrentTab();
if (newTab && (newTab !== uiCurrentTab)) { if (newTab && (newTab !== uiCurrentTab)) {
uiCurrentTab = newTab; uiCurrentTab = newTab;