Merge pull request #2615 from SillyTavern/wi-go-brrrrrr-too

Major WI performance improvements on UI usage
This commit is contained in:
Cohee 2024-08-06 00:37:52 +03:00 committed by GitHub
commit d8e0a29c5b
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
4 changed files with 58 additions and 14 deletions

View File

@ -156,6 +156,7 @@ import {
ensureImageFormatSupported,
flashHighlight,
isTrueBoolean,
toggleDrawer,
} from './scripts/utils.js';
import { debounce_timeout } from './scripts/constants.js';
@ -10615,12 +10616,19 @@ jQuery(async function () {
}
});
$(document).on('click', '#OpenAllWIEntries', function () {
$('#world_popup_entries_list').children().find('.down').click();
});
$(document).on('click', '#CloseAllWIEntries', function () {
$('#world_popup_entries_list').children().find('.up').click();
document.addEventListener('click', function (e) {
if (!(e.target instanceof HTMLElement)) return;
if (e.target.matches('#OpenAllWIEntries')) {
document.querySelectorAll('#world_popup_entries_list .inline-drawer').forEach((/** @type {HTMLElement} */ drawer) => {
toggleDrawer(drawer, true);
});
} else if (e.target.matches('#CloseAllWIEntries')) {
document.querySelectorAll('#world_popup_entries_list .inline-drawer').forEach((/** @type {HTMLElement} */ drawer) => {
toggleDrawer(drawer, false);
});
}
});
$(document).on('click', '.open_alternate_greetings', openAlternateGreetings);
/* $('#set_character_world').on('click', openCharacterWorldPopup); */

View File

@ -1728,20 +1728,24 @@ export function select2ModifyOptions(element, items, { select = false, changeEve
/** @type {Select2Option[]} */
const dataItems = items.map(x => typeof x === 'string' ? { id: getSelect2OptionId(x), text: x } : x);
const existingValues = [];
const optionsToSelect = [];
const newOptions = [];
dataItems.forEach(item => {
// Set the value, creating a new option if necessary
if (element.find('option[value=\'' + item.id + '\']').length) {
if (select) existingValues.push(item.id);
if (select) optionsToSelect.push(item.id);
} else {
// Create a DOM Option and optionally pre-select by default
var newOption = new Option(item.text, item.id, select, select);
// Append it to the select
element.append(newOption);
if (select) element.trigger('change', changeEventArgs);
newOptions.push(newOption);
if (select) optionsToSelect.push(item.id);
}
if (existingValues.length) element.val(existingValues).trigger('change', changeEventArgs);
});
element.append(newOptions);
if (optionsToSelect.length) element.val(optionsToSelect).trigger('change', changeEventArgs);
}
/**
@ -1930,6 +1934,34 @@ export function getFreeName(name, list, numberFormatter = (n) => ` #${n}`) {
return `${name}${numberFormatter(counter)}`;
}
/**
* Toggles the visibility of a drawer by changing the display style of its content.
* This function skips the usual drawer animation.
*
* @param {HTMLElement} drawer - The drawer element to toggle
* @param {boolean} [expand=true] - Whether to expand or collapse the drawer
*/
export function toggleDrawer(drawer, expand = true) {
/** @type {HTMLElement} */
const icon = drawer.querySelector('.inline-drawer-icon');
/** @type {HTMLElement} */
const content = drawer.querySelector('.inline-drawer-content');
if (expand) {
icon.classList.remove('up', 'fa-circle-chevron-up');
icon.classList.add('down', 'fa-circle-chevron-down');
content.style.display = 'block';
} else {
icon.classList.remove('down', 'fa-circle-chevron-down');
icon.classList.add('up', 'fa-circle-chevron-up');
content.style.display = 'none';
}
// Set the height of "autoSetHeight" textareas within the inline-drawer to their scroll height
content.querySelectorAll('textarea.autoSetHeight').forEach(resetScrollHeight);
}
export async function fetchFaFile(name) {
const style = document.createElement('style');
style.innerHTML = await (await fetch(`/css/${name}`)).text();

View File

@ -1875,7 +1875,8 @@ function displayWorldEntries(name, data, navigation = navigation_option.none, fl
Trigger %
</small>
</div>`;
const blocks = page.map(entry => getWorldEntry(name, data, entry)).filter(x => x);
const blocksPromises = page.map(async (entry) => await getWorldEntry(name, data, entry)).filter(x => x);
const blocks = await Promise.all(blocksPromises);
const isCustomOrder = $('#world_info_sort_order').find(':selected').data('rule') === 'custom';
if (!isCustomOrder) {
blocks.forEach(block => {
@ -2275,7 +2276,7 @@ export function parseRegexFromString(input) {
}
}
function getWorldEntry(name, data, entry) {
async function getWorldEntry(name, data, entry) {
if (!data.entries[entry.uid]) {
return;
}
@ -2317,6 +2318,9 @@ function getWorldEntry(name, data, entry) {
}
if (isFancyInput) {
// First initialize existing values as options, before initializing select2, to speed up performance
select2ModifyOptions(input, entry[entryPropName], { select: true, changeEventArgs: { skipReset: true, noSave: true } });
input.select2({
ajax: dynamicSelect2DataViaAjax(() => worldEntryKeyOptionsCache),
tags: true,
@ -2358,8 +2362,6 @@ function getWorldEntry(name, data, entry) {
input.next('span.select2-container').find('textarea')
.val(key).trigger('input');
}, { openDrawer: true });
select2ModifyOptions(input, entry[entryPropName], { select: true, changeEventArgs: { skipReset: true, noSave: true } });
}
else {
// Compatibility with mobile devices. On mobile we need a text input field, not a select option control, so we need its own event handlers

View File

@ -3505,6 +3505,8 @@ grammarly-extension {
.drag-handle {
cursor: grab;
/* Make the drag handle not selectable in most browsers */
user-select: none;
}
#form_rename_chat {