Add pagination for characters list view
This commit is contained in:
parent
303f961ee2
commit
602c5cd791
|
@ -42,6 +42,7 @@
|
|||
<script src="scripts/droll.js"></script>
|
||||
<script src="scripts/localforage.min.js"></script>
|
||||
<script src="scripts/handlebars.js"></script>
|
||||
<script src="scripts/pagination.js"></script>
|
||||
<script type="module" src="scripts/eventemitter.js"></script>
|
||||
<script type="module" src="scripts/power-user.js"></script>
|
||||
<script type="module" src="scripts/swiped-events.js"></script>
|
||||
|
@ -98,6 +99,7 @@
|
|||
<script type="module" src="scripts/extensions.js"></script>
|
||||
<script type="module" src="scripts/authors-note.js"></script>
|
||||
<script type="module" src="scripts/preset-manager.js"></script>
|
||||
<script type="module" src="scripts/filters.js"></script>
|
||||
<script type="text/javascript" src="scripts/toolcool-color-picker.js"></script>
|
||||
|
||||
<title>SillyTavern</title>
|
||||
|
@ -2988,7 +2990,7 @@
|
|||
<div id="rm_button_selected_ch">
|
||||
<h2></h2>
|
||||
</div>
|
||||
<i id="hideCharPanelAvatarButton" class="fa-solid fa-eye menu_button"></i>
|
||||
<i id="hideCharPanelAvatarButton" class="fa-solid fa-eye right_menu_button"></i>
|
||||
</div>
|
||||
</div>
|
||||
<!-- end group peeking cope structure-->
|
||||
|
@ -3255,14 +3257,12 @@
|
|||
<div class="rm_tag_controls">
|
||||
<div class="tags rm_tag_filter"></div>
|
||||
</div>
|
||||
<!-- a div containing a dynamically updated count of characters currently displayed -->
|
||||
<div class="flex-container alignitemscenter">
|
||||
<div id="rm_character_count"></div>
|
||||
<i id="charListGridToggle" class="fa-solid fa-table-cells-large menu_button" title="Toggle character grid view"></i>
|
||||
</div>
|
||||
<hr>
|
||||
</div>
|
||||
|
||||
<div id="rm_print_characters_pagination">
|
||||
<i id="charListGridToggle" class="fa-solid fa-table-cells-large menu_button" title="Toggle character grid view"></i>
|
||||
</div>
|
||||
<div id="rm_print_characters_block" class="flexFlowColumn"></div>
|
||||
</div>
|
||||
|
||||
|
@ -4286,4 +4286,4 @@
|
|||
</script>
|
||||
</body>
|
||||
|
||||
</html>
|
||||
</html>
|
||||
|
|
305
public/script.js
305
public/script.js
|
@ -40,7 +40,6 @@ import {
|
|||
generateGroupWrapper,
|
||||
deleteGroup,
|
||||
is_group_generating,
|
||||
printGroups,
|
||||
resetSelectedGroup,
|
||||
select_group_chats,
|
||||
regenerateGroup,
|
||||
|
@ -55,13 +54,13 @@ import {
|
|||
deleteGroupChat,
|
||||
renameGroupChat,
|
||||
importGroupChat,
|
||||
getGroupBlock,
|
||||
} from "./scripts/group-chats.js";
|
||||
|
||||
import {
|
||||
collapseNewlines,
|
||||
loadPowerUserSettings,
|
||||
playMessageSound,
|
||||
sortCharactersList,
|
||||
fixMarkdown,
|
||||
power_user,
|
||||
pygmalion_options,
|
||||
|
@ -72,10 +71,9 @@ import {
|
|||
persona_description_positions,
|
||||
loadMovingUIState,
|
||||
getCustomStoppingStrings,
|
||||
fuzzySearchCharacters,
|
||||
MAX_CONTEXT_DEFAULT,
|
||||
fuzzySearchGroups,
|
||||
renderStoryString,
|
||||
sortEntitiesList,
|
||||
} from "./scripts/power-user.js";
|
||||
|
||||
import {
|
||||
|
@ -165,6 +163,7 @@ import { NOTE_MODULE_NAME, metadata_keys, setFloatingPrompt, shouldWIAddPrompt }
|
|||
import { deviceInfo } from "./scripts/RossAscends-mods.js";
|
||||
import { registerPromptManagerMigration } from "./scripts/PromptManager.js";
|
||||
import { getRegexedString, regex_placement } from "./scripts/extensions/regex/engine.js";
|
||||
import { FILTER_TYPES, FilterHelper } from "./scripts/filters.js";
|
||||
|
||||
//exporting functions and vars for mods
|
||||
export {
|
||||
|
@ -233,7 +232,6 @@ export {
|
|||
talkativeness_default,
|
||||
default_ch_mes,
|
||||
extension_prompt_types,
|
||||
updateVisibleDivs,
|
||||
mesForShowdownParse,
|
||||
printCharacters,
|
||||
}
|
||||
|
@ -817,8 +815,9 @@ let token;
|
|||
|
||||
var PromptArrayItemForRawPromptDisplay;
|
||||
|
||||
export let active_character = ""
|
||||
export let active_group = ""
|
||||
export let active_character = "";
|
||||
export let active_group = "";
|
||||
export const entitiesFilter = new FilterHelper(debounce(printCharacters, 100));
|
||||
|
||||
export function getRequestHeaders() {
|
||||
return {
|
||||
|
@ -965,60 +964,129 @@ function resultCheckStatus() {
|
|||
$("#api_button_textgenerationwebui").css("display", "inline-block");
|
||||
}
|
||||
|
||||
async function printCharacters() {
|
||||
$("#rm_print_characters_block").empty();
|
||||
characters.forEach(function (item, i, arr) {
|
||||
let this_avatar = default_avatar;
|
||||
if (item.avatar != "none") {
|
||||
this_avatar = getThumbnailUrl('avatar', item.avatar);
|
||||
}
|
||||
// Populate the template
|
||||
const template = $('#character_template .character_select').clone();
|
||||
template.attr({ 'chid': i, 'id': `CharID${i}` });
|
||||
template.find('img').attr('src', this_avatar);
|
||||
template.find('.avatar').attr('title', item.avatar);
|
||||
template.find('.ch_name').text(item.name);
|
||||
if (power_user.show_card_avatar_urls) {
|
||||
template.find('.ch_avatar_url').text(item.avatar);
|
||||
}
|
||||
template.find('.ch_fav_icon').css("display", 'none');
|
||||
template.toggleClass('is_fav', item.fav || item.fav == 'true');
|
||||
template.find('.ch_fav').val(item.fav);
|
||||
export function selectCharacterById(id) {
|
||||
if (characters[id] == undefined) {
|
||||
return;
|
||||
}
|
||||
|
||||
const description = item.data?.creator_notes?.split('\n', 1)[0] || '';
|
||||
if (description) {
|
||||
template.find('.ch_description').text(description);
|
||||
}
|
||||
else {
|
||||
template.find('.ch_description').hide();
|
||||
}
|
||||
if (selected_group && is_group_generating) {
|
||||
return;
|
||||
}
|
||||
|
||||
const version = item.data?.character_version || '';
|
||||
if (version) {
|
||||
template.find('.character_version').text(version);
|
||||
if (selected_group || this_chid !== id) {
|
||||
//if clicked on a different character from what was currently selected
|
||||
if (!is_send_press) {
|
||||
cancelTtsPlay();
|
||||
resetSelectedGroup();
|
||||
this_edit_mes_id = undefined;
|
||||
selected_button = "character_edit";
|
||||
this_chid = id;
|
||||
clearChat();
|
||||
chat.length = 0;
|
||||
chat_metadata = {};
|
||||
getChat();
|
||||
}
|
||||
else {
|
||||
template.find('.character_version').hide();
|
||||
} else {
|
||||
//if clicked on character that was already selected
|
||||
selected_button = "character_edit";
|
||||
select_selected_character(this_chid);
|
||||
}
|
||||
}
|
||||
|
||||
function getCharacterBlock(item, id) {
|
||||
let this_avatar = default_avatar;
|
||||
if (item.avatar != "none") {
|
||||
this_avatar = getThumbnailUrl('avatar', item.avatar);
|
||||
}
|
||||
// Populate the template
|
||||
const template = $('#character_template .character_select').clone();
|
||||
template.attr({ 'chid': id, 'id': `CharID${id}` });
|
||||
template.find('img').attr('src', this_avatar);
|
||||
template.find('.avatar').attr('title', item.avatar);
|
||||
template.find('.ch_name').text(item.name);
|
||||
if (power_user.show_card_avatar_urls) {
|
||||
template.find('.ch_avatar_url').text(item.avatar);
|
||||
}
|
||||
template.find('.ch_fav_icon').css("display", 'none');
|
||||
template.toggleClass('is_fav', item.fav || item.fav == 'true');
|
||||
template.find('.ch_fav').val(item.fav);
|
||||
|
||||
const description = item.data?.creator_notes?.split('\n', 1)[0] || '';
|
||||
if (description) {
|
||||
template.find('.ch_description').text(description);
|
||||
}
|
||||
else {
|
||||
template.find('.ch_description').hide();
|
||||
}
|
||||
|
||||
const version = item.data?.character_version || '';
|
||||
if (version) {
|
||||
template.find('.character_version').text(version);
|
||||
}
|
||||
else {
|
||||
template.find('.character_version').hide();
|
||||
}
|
||||
|
||||
// Display inline tags
|
||||
const tags = getTagsList(item.avatar);
|
||||
const tagsElement = template.find('.tags');
|
||||
tags.forEach(tag => appendTagToList(tagsElement, tag, {}));
|
||||
|
||||
// Add to the list
|
||||
return template;
|
||||
}
|
||||
|
||||
async function printCharacters(fullRefresh = false) {
|
||||
const storageKey = 'Characters_PerPage';
|
||||
$("#rm_print_characters_pagination").pagination({
|
||||
dataSource: getEntitiesList({ doFilter: true }),
|
||||
pageSize: Number(localStorage.getItem(storageKey)) || 50,
|
||||
sizeChangerOptions: [25, 50, 100, 250, 500, 1000],
|
||||
pageRange: 1,
|
||||
position: 'top',
|
||||
showPageNumbers: false,
|
||||
showSizeChanger: true,
|
||||
prevText: '<',
|
||||
nextText: '>',
|
||||
showNavigator: true,
|
||||
callback: function (data) {
|
||||
$("#rm_print_characters_block").empty();
|
||||
for (const i of data) {
|
||||
if (i.type === 'character') {
|
||||
$("#rm_print_characters_block").append(getCharacterBlock(i.item, i.id));
|
||||
}
|
||||
if (i.type === 'group') {
|
||||
$("#rm_print_characters_block").append(getGroupBlock(i.item));
|
||||
}
|
||||
}
|
||||
},
|
||||
afterSizeSelectorChange: function (e) {
|
||||
localStorage.setItem(storageKey, e.target.value);
|
||||
}
|
||||
|
||||
// Display inline tags
|
||||
const tags = getTagsList(item.avatar);
|
||||
const tagsElement = template.find('.tags');
|
||||
tags.forEach(tag => appendTagToList(tagsElement, tag, {}));
|
||||
|
||||
// Add to the list
|
||||
$("#rm_print_characters_block").append(template);
|
||||
});
|
||||
|
||||
printTagFilters(tag_filter_types.character);
|
||||
printTagFilters(tag_filter_types.group_member);
|
||||
printGroups();
|
||||
sortCharactersList();
|
||||
favsToHotswap();
|
||||
await delay(300);
|
||||
updateVisibleDivs('#rm_print_characters_block', true);
|
||||
displayOverrideWarnings();
|
||||
|
||||
if (fullRefresh) {
|
||||
printTagFilters(tag_filter_types.character);
|
||||
printTagFilters(tag_filter_types.group_member);
|
||||
|
||||
await delay(300);
|
||||
displayOverrideWarnings();
|
||||
}
|
||||
}
|
||||
|
||||
export function getEntitiesList({ doFilter } = {}) {
|
||||
let entities = [];
|
||||
entities.push(...characters.map((item, index) => ({ item, id: index, type: 'character' })));
|
||||
entities.push(...groups.map((item) => ({ item, id: item.id, type: 'group' })));
|
||||
|
||||
if (doFilter) {
|
||||
entities = entitiesFilter.applyFilters(entities);
|
||||
}
|
||||
|
||||
sortEntitiesList(entities);
|
||||
return entities;
|
||||
}
|
||||
|
||||
async function getCharacters() {
|
||||
|
@ -1050,10 +1118,7 @@ async function getCharacters() {
|
|||
}
|
||||
|
||||
await getGroups();
|
||||
await printCharacters();
|
||||
|
||||
|
||||
updateCharacterCount('#rm_print_characters_block > div');
|
||||
await printCharacters(true);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -4209,7 +4274,7 @@ async function renameCharacter() {
|
|||
if (newChId !== -1) {
|
||||
// Select the character after the renaming
|
||||
this_chid = -1;
|
||||
$(`.character_select[chid="${newChId}"]`).click();
|
||||
selectCharacterById(String(newChId));
|
||||
|
||||
// Async delay to update UI
|
||||
await delay(1);
|
||||
|
@ -4303,7 +4368,6 @@ async function saveChat(chat_name, withMetadata, mesId) {
|
|||
const metadata = { ...chat_metadata, ...(withMetadata || {}) };
|
||||
let file_name = chat_name ?? characters[this_chid].chat;
|
||||
characters[this_chid]['date_last_chat'] = Date.now();
|
||||
sortCharactersList();
|
||||
chat.forEach(function (item, i) {
|
||||
if (item["is_group"]) {
|
||||
toastr.error('Trying to save group chat with regular saveChat function. Aborting to prevent corruption.');
|
||||
|
@ -5852,7 +5916,6 @@ function select_rm_characters() {
|
|||
menu_type = "characters";
|
||||
selectRightMenuWithAnimation('rm_characters_block');
|
||||
setRightTabSelectedClass('rm_button_characters');
|
||||
updateVisibleDivs('#rm_print_characters_block', true);
|
||||
}
|
||||
|
||||
function setExtensionPrompt(key, value, position, depth) {
|
||||
|
@ -6199,7 +6262,6 @@ async function deleteMessageImage() {
|
|||
mesBlock.find('.mes_img_container').removeClass('img_extra');
|
||||
mesBlock.find('.mes_img').attr('src', '');
|
||||
saveChatConditional();
|
||||
/*updateVisibleDivs('#chat', false);*/
|
||||
}
|
||||
|
||||
function enlargeMessageImage() {
|
||||
|
@ -6932,51 +6994,6 @@ const swipe_right = () => {
|
|||
}
|
||||
}
|
||||
|
||||
export function updateCharacterCount(characterSelector) {
|
||||
const visibleCharacters = $(characterSelector)
|
||||
.not(".hiddenBySearch")
|
||||
.not(".hiddenByTag")
|
||||
.not(".hiddenByGroup")
|
||||
.not(".hiddenByGroupMember")
|
||||
.not(".hiddenByFav");
|
||||
const visibleCharacterCount = visibleCharacters.length;
|
||||
const totalCharacterCount = $(characterSelector).length;
|
||||
|
||||
$("#rm_character_count").text(
|
||||
`(${visibleCharacterCount} / ${totalCharacterCount}) Characters`
|
||||
);
|
||||
console.log("visibleCharacters.length: " + visibleCharacters.length);
|
||||
}
|
||||
|
||||
function updateVisibleDivs(containerSelector, resizecontainer) {
|
||||
var $container = $(containerSelector);
|
||||
var $children = $container.children();
|
||||
var totalHeight = 0;
|
||||
$children.each(function () {
|
||||
totalHeight += $(this).outerHeight();
|
||||
});
|
||||
if (resizecontainer) {
|
||||
$container.css({
|
||||
height: totalHeight,
|
||||
});
|
||||
}
|
||||
var containerTop = $container.offset() ? $container.offset().top : 0;
|
||||
var firstVisibleIndex = null;
|
||||
var lastVisibleIndex = null;
|
||||
$children.each(function (index) {
|
||||
var $child = $(this);
|
||||
var childTop = $child.offset().top - containerTop;
|
||||
var childBottom = childTop + $child.outerHeight();
|
||||
if (childTop <= $container.height() && childBottom >= 0) {
|
||||
if (firstVisibleIndex === null) {
|
||||
firstVisibleIndex = index;
|
||||
}
|
||||
lastVisibleIndex = index;
|
||||
}
|
||||
$child.toggleClass('hiddenByScroll', childTop > $container.height() || childBottom < 0);
|
||||
});
|
||||
}
|
||||
|
||||
function displayOverrideWarnings() {
|
||||
if (!this_chid || !selected_group) {
|
||||
$('.prompt_overridden').hide();
|
||||
|
@ -7161,8 +7178,7 @@ function doCharListDisplaySwitch() {
|
|||
console.debug('toggling body charListGrid state')
|
||||
$("body").toggleClass('charListGrid')
|
||||
power_user.charListGrid = $("body").hasClass("charListGrid") ? true : false;
|
||||
saveSettingsDebounced()
|
||||
updateVisibleDivs('#rm_print_characters_block', true);
|
||||
saveSettingsDebounced();
|
||||
}
|
||||
|
||||
function doCloseChat() {
|
||||
|
@ -7256,18 +7272,11 @@ $(document).ready(function () {
|
|||
registerSlashCommand('closechat', doCloseChat, [], "- closes the current chat", true, true);
|
||||
registerSlashCommand('panels', doTogglePanels, ['togglepanels'], "- toggle UI panels on/off", true, true);
|
||||
|
||||
|
||||
|
||||
setTimeout(function () {
|
||||
$("#groupControlsToggle").trigger('click');
|
||||
$("#groupCurrentMemberListToggle .inline-drawer-icon").trigger('click');
|
||||
}, 200);
|
||||
|
||||
|
||||
$("#rm_print_characters_block").on('scroll', debounce(() => {
|
||||
updateVisibleDivs('#rm_print_characters_block', true);
|
||||
}, 5));
|
||||
|
||||
$('#chat').on('scroll', async () => {
|
||||
// if on the start of the chat and has hidden messages
|
||||
if ($('#chat').scrollTop() === 0 && $('#chat').children('.mes').not(':visible').length > 0) {
|
||||
|
@ -7330,43 +7339,8 @@ $(document).ready(function () {
|
|||
$(document).on('click', '.swipe_left', swipe_left);
|
||||
|
||||
$("#character_search_bar").on("input", function () {
|
||||
const selector = ['#rm_print_characters_block .character_select', '#rm_print_characters_block .group_select'].join(',');
|
||||
const searchValue = $(this).val().trim().toLowerCase();
|
||||
const fuzzySearchCharactersResults = power_user.fuzzy_search ? fuzzySearchCharacters(searchValue) : [];
|
||||
const fuzzySearchGroupsResults = power_user.fuzzy_search ? fuzzySearchGroups(searchValue) : [];
|
||||
|
||||
function getIsValidSearch(_this) {
|
||||
const name = $(_this).find(".ch_name").text().toLowerCase();
|
||||
const chid = $(_this).attr("chid");
|
||||
const grid = $(_this).attr("grid");
|
||||
|
||||
if (power_user.fuzzy_search) {
|
||||
if (chid !== undefined) {
|
||||
return fuzzySearchCharactersResults.includes(parseInt(chid));
|
||||
} else if (grid !== undefined) {
|
||||
return fuzzySearchGroupsResults.includes(String(grid));
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
else {
|
||||
return name.includes(searchValue);
|
||||
}
|
||||
}
|
||||
|
||||
if (!searchValue) {
|
||||
$(selector).removeClass('hiddenBySearch');
|
||||
updateVisibleDivs('#rm_print_characters_block', true);
|
||||
} else {
|
||||
$(selector).each(function () {
|
||||
const isValidSearch = getIsValidSearch(this);
|
||||
$(this).toggleClass('hiddenBySearch', !isValidSearch);
|
||||
});
|
||||
updateVisibleDivs('#rm_print_characters_block', true);
|
||||
}
|
||||
updateCharacterCount(selector);
|
||||
|
||||
|
||||
const searchValue = $(this).val().toLowerCase();
|
||||
entitiesFilter.setFilterData(FILTER_TYPES.SEARCH, searchValue);
|
||||
});
|
||||
|
||||
$("#send_but").click(function () {
|
||||
|
@ -7406,32 +7380,11 @@ $(document).ready(function () {
|
|||
$("#character_search_bar").val("").trigger("input");
|
||||
});
|
||||
|
||||
$(document).on("click", ".character_select", function () {
|
||||
if (selected_group && is_group_generating) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (selected_group || this_chid !== $(this).attr("chid")) {
|
||||
//if clicked on a different character from what was currently selected
|
||||
if (!is_send_press) {
|
||||
cancelTtsPlay();
|
||||
resetSelectedGroup();
|
||||
this_edit_mes_id = undefined;
|
||||
selected_button = "character_edit";
|
||||
this_chid = $(this).attr("chid");
|
||||
clearChat();
|
||||
chat.length = 0;
|
||||
chat_metadata = {};
|
||||
getChat();
|
||||
}
|
||||
} else {
|
||||
//if clicked on character that was already selected
|
||||
selected_button = "character_edit";
|
||||
select_selected_character(this_chid);
|
||||
}
|
||||
$(document).on("click", ".character_select", function() {
|
||||
const id = $(this).attr("chid");
|
||||
selectCharacterById(id);
|
||||
});
|
||||
|
||||
|
||||
$(document).on("input", ".edit_textarea", function () {
|
||||
scroll_holder = $("#chat").scrollTop();
|
||||
$(this).height(0).height(this.scrollHeight);
|
||||
|
|
|
@ -13,11 +13,13 @@ import {
|
|||
menu_type,
|
||||
max_context,
|
||||
saveSettingsDebounced,
|
||||
eventSource,
|
||||
active_group,
|
||||
active_character,
|
||||
setActiveGroup,
|
||||
setActiveCharacter,
|
||||
getEntitiesList,
|
||||
getThumbnailUrl,
|
||||
selectCharacterById,
|
||||
} from "../script.js";
|
||||
|
||||
import {
|
||||
|
@ -348,12 +350,13 @@ async function RA_autoloadchat() {
|
|||
// active character is the name, we should look it up in the character list and get the id
|
||||
let active_character_id = Object.keys(characters).find(key => characters[key].avatar === active_character);
|
||||
|
||||
var charToAutoLoad = document.getElementById('CharID' + active_character_id);
|
||||
let groupToAutoLoad = document.querySelector(`.group_select[grid="${active_group}"]`);
|
||||
if (charToAutoLoad != null) {
|
||||
$(charToAutoLoad).click();
|
||||
if (active_character_id !== null) {
|
||||
selectCharacterById(String(active_character_id));
|
||||
}
|
||||
else if (groupToAutoLoad != null) {
|
||||
|
||||
let groupToAutoLoad = document.querySelector(`.group_select[grid="${active_group}"]`);
|
||||
|
||||
if (groupToAutoLoad != null) {
|
||||
$(groupToAutoLoad).click();
|
||||
}
|
||||
|
||||
|
@ -362,53 +365,60 @@ async function RA_autoloadchat() {
|
|||
}
|
||||
|
||||
export async function favsToHotswap() {
|
||||
const selector = ['#rm_print_characters_block .character_select', '#rm_print_characters_block .group_select'].join(',');
|
||||
const entities = getEntitiesList({ doFilter: false });
|
||||
const container = $('#right-nav-panel .hotswap');
|
||||
const template = $('#hotswap_template .hotswapAvatar');
|
||||
container.empty();
|
||||
const maxCount = 6;
|
||||
let count = 0;
|
||||
|
||||
$(selector).sort(sortByCssOrder).each(function () {
|
||||
if ($(this).hasClass('is_fav') && count < maxCount) {
|
||||
const isCharacter = $(this).hasClass('character_select');
|
||||
const isGroup = $(this).hasClass('group_select');
|
||||
const grid = Number($(this).attr('grid'));
|
||||
const chid = Number($(this).attr('chid'));
|
||||
let thisHotSwapSlot = template.clone();
|
||||
thisHotSwapSlot.toggleClass('character_select', isCharacter);
|
||||
thisHotSwapSlot.toggleClass('group_select', isGroup);
|
||||
thisHotSwapSlot.attr('grid', isGroup ? grid : '');
|
||||
thisHotSwapSlot.attr('chid', isCharacter ? chid : '');
|
||||
thisHotSwapSlot.data('id', isGroup ? grid : chid);
|
||||
thisHotSwapSlot.attr('title', '');
|
||||
|
||||
if (isGroup) {
|
||||
const group = groups.find(x => x.id === grid);
|
||||
const avatar = getGroupAvatar(group);
|
||||
$(thisHotSwapSlot).find('img').replaceWith(avatar);
|
||||
}
|
||||
|
||||
if (isCharacter) {
|
||||
const avatarUrl = $(this).find('img').attr('src');
|
||||
$(thisHotSwapSlot).find('img').attr('src', avatarUrl);
|
||||
}
|
||||
|
||||
$(thisHotSwapSlot).css('cursor', 'pointer');
|
||||
container.append(thisHotSwapSlot);
|
||||
count++;
|
||||
for (const entity of entities) {
|
||||
if (count >= maxCount) {
|
||||
break;
|
||||
}
|
||||
});
|
||||
|
||||
//console.log('about to check for leftover selectors...')
|
||||
const isFavorite = entity.item.fav || entity.item.fav == 'true';
|
||||
|
||||
if (!isFavorite) {
|
||||
continue;
|
||||
}
|
||||
|
||||
const isCharacter = entity.type === 'character';
|
||||
const isGroup = entity.type === 'group';
|
||||
|
||||
const grid = isGroup ? entity.id : '';
|
||||
const chid = isCharacter ? entity.id : '';
|
||||
|
||||
let slot = template.clone();
|
||||
slot.toggleClass('character_select', isCharacter);
|
||||
slot.toggleClass('group_select', isGroup);
|
||||
slot.attr('grid', isGroup ? grid : '');
|
||||
slot.attr('chid', isCharacter ? chid : '');
|
||||
slot.data('id', isGroup ? grid : chid);
|
||||
slot.attr('title', '');
|
||||
|
||||
if (isGroup) {
|
||||
const group = groups.find(x => x.id === grid);
|
||||
const avatar = getGroupAvatar(group);
|
||||
$(slot).find('img').replaceWith(avatar);
|
||||
}
|
||||
|
||||
if (isCharacter) {
|
||||
const avatarUrl = getThumbnailUrl('avatar', entity.item.avatar);
|
||||
$(slot).find('img').attr('src', avatarUrl);
|
||||
}
|
||||
|
||||
$(slot).css('cursor', 'pointer');
|
||||
container.append(slot);
|
||||
count++;
|
||||
}
|
||||
|
||||
// there are 6 slots in total,
|
||||
if (count < maxCount) { //if any are left over
|
||||
let leftOverSlots = maxCount - count;
|
||||
for (let i = 1; i <= leftOverSlots; i++) {
|
||||
container.append(template.clone());
|
||||
}
|
||||
} else {
|
||||
//console.log(`count was ${count} so no need to knock off any selectors!`);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,129 @@
|
|||
import { fuzzySearchCharacters, fuzzySearchGroups, power_user } from "./power-user.js";
|
||||
import { tag_map } from "./tags.js";
|
||||
|
||||
export const FILTER_TYPES = {
|
||||
SEARCH: 'search',
|
||||
TAG: 'tag',
|
||||
FAV: 'fav',
|
||||
GROUP: 'group',
|
||||
};
|
||||
|
||||
export class FilterHelper {
|
||||
constructor(onDataChanged) {
|
||||
this.onDataChanged = onDataChanged;
|
||||
}
|
||||
|
||||
filterFunctions = {
|
||||
[FILTER_TYPES.SEARCH]: this.searchFilter.bind(this),
|
||||
[FILTER_TYPES.GROUP]: this.groupFilter.bind(this),
|
||||
[FILTER_TYPES.FAV]: this.favFilter.bind(this),
|
||||
[FILTER_TYPES.TAG]: this.tagFilter.bind(this),
|
||||
}
|
||||
|
||||
filterData = {
|
||||
[FILTER_TYPES.SEARCH]: '',
|
||||
[FILTER_TYPES.GROUP]: false,
|
||||
[FILTER_TYPES.FAV]: false,
|
||||
[FILTER_TYPES.TAG]: { excluded: [], selected: [] },
|
||||
}
|
||||
|
||||
tagFilter(data) {
|
||||
const TAG_LOGIC_AND = true; // switch to false to use OR logic for combining tags
|
||||
const { selected, excluded } = this.filterData[FILTER_TYPES.TAG];
|
||||
|
||||
if (!selected.length && !excluded.length) {
|
||||
return data;
|
||||
}
|
||||
|
||||
function isElementTagged(entity, tagId) {
|
||||
const isCharacter = entity.type === 'character';
|
||||
const lookupValue = isCharacter ? entity.item.avatar : String(entity.id);
|
||||
const isTagged = Array.isArray(tag_map[lookupValue]) && tag_map[lookupValue].includes(tagId);
|
||||
return isTagged;
|
||||
}
|
||||
|
||||
function getIsTagged(entity) {
|
||||
const tagFlags = selected.map(tagId => isElementTagged(entity, tagId));
|
||||
const trueFlags = tagFlags.filter(x => x);
|
||||
const isTagged = TAG_LOGIC_AND ? tagFlags.length === trueFlags.length : trueFlags.length > 0;
|
||||
|
||||
const excludedTagFlags = excluded.map(tagId => isElementTagged(entity, tagId));
|
||||
const isExcluded = excludedTagFlags.includes(true);
|
||||
|
||||
if (isExcluded) {
|
||||
return false;
|
||||
} else if (selected.length > 0 && !isTagged) {
|
||||
return false;
|
||||
} else {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return data.filter(entity => getIsTagged(entity));
|
||||
}
|
||||
|
||||
favFilter(data) {
|
||||
if (!this.filterData[FILTER_TYPES.FAV]) {
|
||||
return data;
|
||||
}
|
||||
|
||||
return data.filter(entity => entity.item.fav || entity.item.fav == "true");
|
||||
}
|
||||
|
||||
groupFilter(data) {
|
||||
if (!this.filterData[FILTER_TYPES.GROUP]) {
|
||||
return data;
|
||||
}
|
||||
|
||||
return data.filter(entity => entity.type === 'group');
|
||||
}
|
||||
|
||||
searchFilter(data) {
|
||||
if (!this.filterData[FILTER_TYPES.SEARCH]) {
|
||||
return data;
|
||||
}
|
||||
|
||||
const searchValue = this.filterData[FILTER_TYPES.SEARCH].trim().toLowerCase();
|
||||
const fuzzySearchCharactersResults = power_user.fuzzy_search ? fuzzySearchCharacters(searchValue) : [];
|
||||
const fuzzySearchGroupsResults = power_user.fuzzy_search ? fuzzySearchGroups(searchValue) : [];
|
||||
|
||||
function getIsValidSearch(entity) {
|
||||
const isGroup = entity.type === 'group';
|
||||
const isCharacter = entity.type === 'character';
|
||||
|
||||
if (power_user.fuzzy_search) {
|
||||
if (isCharacter) {
|
||||
return fuzzySearchCharactersResults.includes(parseInt(entity.id));
|
||||
} else if (isGroup) {
|
||||
return fuzzySearchGroupsResults.includes(String(entity.id));
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
else {
|
||||
return entity.item?.name?.toLowerCase()?.includes(searchValue) || false;
|
||||
}
|
||||
}
|
||||
|
||||
return data.filter(entity => getIsValidSearch(entity));
|
||||
}
|
||||
|
||||
setFilterData(filterType, data) {
|
||||
const oldData = this.filterData[filterType];
|
||||
this.filterData[filterType] = data;
|
||||
|
||||
// only trigger a data change if the data actually changed
|
||||
if (JSON.stringify(oldData) !== JSON.stringify(data)) {
|
||||
this.onDataChanged();
|
||||
}
|
||||
}
|
||||
|
||||
getFilterData(filterType) {
|
||||
return this.filterData[filterType];
|
||||
}
|
||||
|
||||
applyFilters(data) {
|
||||
return Object.values(this.filterFunctions)
|
||||
.reduce((data, fn) => fn(data), data);
|
||||
}
|
||||
}
|
|
@ -8,7 +8,7 @@ import {
|
|||
extractAllWords,
|
||||
} from './utils.js';
|
||||
import { RA_CountCharTokens, humanizedDateTime, dragElement } from "./RossAscends-mods.js";
|
||||
import { sortCharactersList, sortGroupMembers, loadMovingUIState } from './power-user.js';
|
||||
import { sortGroupMembers, loadMovingUIState } from './power-user.js';
|
||||
|
||||
import {
|
||||
chat,
|
||||
|
@ -63,6 +63,7 @@ import {
|
|||
getCropPopup,
|
||||
} from "../script.js";
|
||||
import { appendTagToList, createTagMapFromList, getTagsList, applyTagsOnCharacterSelect, tag_map } from './tags.js';
|
||||
import { FilterHelper } from './filters.js';
|
||||
|
||||
export {
|
||||
selected_group,
|
||||
|
@ -75,7 +76,6 @@ export {
|
|||
deleteGroup,
|
||||
getGroupAvatar,
|
||||
getGroups,
|
||||
printGroups,
|
||||
regenerateGroup,
|
||||
resetSelectedGroup,
|
||||
select_group_chats,
|
||||
|
@ -94,9 +94,15 @@ export const group_activation_strategy = {
|
|||
LIST: 1,
|
||||
};
|
||||
|
||||
export const groupCandidatesFilter = new FilterHelper(debounce(printGroupCandidates, 100));
|
||||
const groupAutoModeInterval = setInterval(groupChatAutoModeWorker, 5000);
|
||||
const saveGroupDebounced = debounce(async (group) => await _save(group), 500);
|
||||
|
||||
function printGroupCandidates(fullRefresh = false) {
|
||||
toastr.info('Group candidates tags filter is temporarily unavailable.');
|
||||
console.log('TODO: implement printGroupCandidates');
|
||||
}
|
||||
|
||||
async function _save(group, reload = true) {
|
||||
await fetch("/editgroup", {
|
||||
method: "POST",
|
||||
|
@ -228,7 +234,6 @@ async function saveGroupChat(groupId, shouldSaveGroup) {
|
|||
if (shouldSaveGroup && response.ok) {
|
||||
await editGroup(groupId);
|
||||
}
|
||||
sortCharactersList();
|
||||
}
|
||||
|
||||
export async function renameGroupMember(oldAvatar, newAvatar, newName) {
|
||||
|
@ -330,8 +335,7 @@ async function getGroups() {
|
|||
}
|
||||
}
|
||||
|
||||
function printGroups() {
|
||||
for (let group of groups) {
|
||||
export function getGroupBlock(group) {
|
||||
const template = $("#group_list_template .group_select").clone();
|
||||
template.data("id", group.id);
|
||||
template.attr("grid", group.id);
|
||||
|
@ -345,10 +349,14 @@ function printGroups() {
|
|||
const tagsElement = template.find('.tags');
|
||||
tags.forEach(tag => appendTagToList(tagsElement, tag, {}));
|
||||
|
||||
$("#rm_print_characters_block").prepend(template);
|
||||
updateGroupAvatar(group);
|
||||
}
|
||||
const avatar = getGroupAvatar(group);
|
||||
if (avatar) {
|
||||
$(template).find(".avatar").replaceWith(avatar);
|
||||
}
|
||||
|
||||
return template;
|
||||
}
|
||||
|
||||
function updateGroupAvatar(group) {
|
||||
$("#rm_print_characters_block .group_select").each(function () {
|
||||
if ($(this).data("id") == group.id) {
|
||||
|
@ -1353,7 +1361,6 @@ export async function openGroupChat(groupId, chatId) {
|
|||
|
||||
await editGroup(groupId, true);
|
||||
await getGroupChat(groupId);
|
||||
sortCharactersList();
|
||||
}
|
||||
|
||||
export async function renameGroupChat(groupId, oldChatId, newChatId) {
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -8,7 +8,6 @@ import {
|
|||
reloadCurrentChat,
|
||||
getRequestHeaders,
|
||||
substituteParams,
|
||||
updateVisibleDivs,
|
||||
eventSource,
|
||||
event_types,
|
||||
getCurrentChatId,
|
||||
|
@ -18,7 +17,7 @@ import {
|
|||
setCharacterId,
|
||||
setEditedMessageId
|
||||
} from "../script.js";
|
||||
import { favsToHotswap, isMobile, initMovingUI } from "./RossAscends-mods.js";
|
||||
import { isMobile, initMovingUI } from "./RossAscends-mods.js";
|
||||
import {
|
||||
groups,
|
||||
resetSelectedGroup,
|
||||
|
@ -35,7 +34,7 @@ export {
|
|||
collapseNewlines,
|
||||
playMessageSound,
|
||||
sortGroupMembers,
|
||||
sortCharactersList,
|
||||
sortEntitiesList,
|
||||
fixMarkdown,
|
||||
power_user,
|
||||
pygmalion_options,
|
||||
|
@ -803,7 +802,6 @@ function loadPowerUserSettings(settings, data) {
|
|||
|
||||
|
||||
$(`#character_sort_order option[data-order="${power_user.sort_order}"][data-field="${power_user.sort_field}"]`).prop("selected", true);
|
||||
sortCharactersList();
|
||||
reloadMarkdownProcessor(power_user.render_formulas);
|
||||
loadInstructMode();
|
||||
loadContextSettings();
|
||||
|
@ -812,7 +810,6 @@ function loadPowerUserSettings(settings, data) {
|
|||
switchSpoilerMode();
|
||||
loadMovingUIState();
|
||||
loadCharListState();
|
||||
|
||||
}
|
||||
|
||||
async function loadCharListState() {
|
||||
|
@ -1129,32 +1126,12 @@ const compareFunc = (first, second) => {
|
|||
}
|
||||
};
|
||||
|
||||
function sortCharactersList() {
|
||||
const arr1 = groups.map(x => ({
|
||||
item: x,
|
||||
id: x.id,
|
||||
selector: '.group_select',
|
||||
attribute: 'grid',
|
||||
}))
|
||||
const arr2 = characters.map((x, index) => ({
|
||||
item: x,
|
||||
id: index,
|
||||
selector: '.character_select',
|
||||
attribute: 'chid',
|
||||
}));
|
||||
|
||||
const array = [...arr1, ...arr2];
|
||||
|
||||
if (power_user.sort_field == undefined || array.length === 0) {
|
||||
function sortEntitiesList(entities) {
|
||||
if (power_user.sort_field == undefined || entities.length === 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
let orderedList = array.slice().sort((a, b) => sortFunc(a.item, b.item));
|
||||
|
||||
for (const item of array) {
|
||||
$(`${item.selector}[${item.attribute}="${item.id}"]`).css({ 'order': orderedList.indexOf(item) });
|
||||
}
|
||||
updateVisibleDivs('#rm_print_characters_block', true);
|
||||
entities.sort((a, b) => sortFunc(a.item, b.item));
|
||||
}
|
||||
|
||||
function sortGroupMembers(selector) {
|
||||
|
@ -1900,6 +1877,7 @@ $(document).ready(() => {
|
|||
power_user.never_resize_avatars = !!$(this).prop('checked');
|
||||
saveSettingsDebounced();
|
||||
});
|
||||
|
||||
$("#show_card_avatar_urls").on('input', function () {
|
||||
power_user.show_card_avatar_urls = !!$(this).prop('checked');
|
||||
printCharacters();
|
||||
|
@ -1925,8 +1903,7 @@ $(document).ready(() => {
|
|||
power_user.sort_field = $(this).find(":selected").data('field');
|
||||
power_user.sort_order = $(this).find(":selected").data('order');
|
||||
power_user.sort_rule = $(this).find(":selected").data('rule');
|
||||
sortCharactersList();
|
||||
favsToHotswap();
|
||||
printCharacters();
|
||||
saveSettingsDebounced();
|
||||
});
|
||||
|
||||
|
@ -2038,12 +2015,6 @@ $(document).ready(() => {
|
|||
saveSettingsDebounced();
|
||||
});
|
||||
|
||||
/* $("#removeXML").on("input", function () {
|
||||
power_user.removeXML = !!$(this).prop('checked');
|
||||
reloadCurrentChat();
|
||||
saveSettingsDebounced();
|
||||
}); */
|
||||
|
||||
$("#token_padding").on("input", function () {
|
||||
power_user.token_padding = Number($(this).val());
|
||||
saveSettingsDebounced();
|
||||
|
|
|
@ -4,12 +4,12 @@ import {
|
|||
this_chid,
|
||||
callPopup,
|
||||
menu_type,
|
||||
updateVisibleDivs,
|
||||
getCharacters,
|
||||
updateCharacterCount,
|
||||
entitiesFilter,
|
||||
} from "../script.js";
|
||||
import { FILTER_TYPES } from "./filters.js";
|
||||
|
||||
import { selected_group } from "./group-chats.js";
|
||||
import { groupCandidatesFilter, selected_group } from "./group-chats.js";
|
||||
import { uuidv4 } from "./utils.js";
|
||||
|
||||
export {
|
||||
|
@ -17,7 +17,6 @@ export {
|
|||
tag_map,
|
||||
loadTagsSettings,
|
||||
printTagFilters,
|
||||
isElementTagged,
|
||||
getTagsList,
|
||||
appendTagToList,
|
||||
createTagMapFromList,
|
||||
|
@ -26,18 +25,11 @@ export {
|
|||
};
|
||||
|
||||
const random_id = () => uuidv4();
|
||||
const TAG_LOGIC_AND = true; // switch to false to use OR logic for combining tags
|
||||
const CHARACTER_SELECTOR = '#rm_print_characters_block > div';
|
||||
const GROUP_MEMBER_SELECTOR = '#rm_group_add_members > div';
|
||||
const CHARACTER_FILTER_SELECTOR = '#rm_characters_block .rm_tag_filter';
|
||||
const GROUP_FILTER_SELECTOR = '#rm_group_chats_block .rm_tag_filter';
|
||||
|
||||
function getCharacterSelector(listSelector) {
|
||||
if ($(listSelector).is(GROUP_FILTER_SELECTOR)) {
|
||||
return GROUP_MEMBER_SELECTOR;
|
||||
}
|
||||
|
||||
return CHARACTER_SELECTOR;
|
||||
function getFilterHelper(listSelector) {
|
||||
return $(listSelector).is(GROUP_FILTER_SELECTOR) ? groupCandidatesFilter : entitiesFilter;
|
||||
}
|
||||
|
||||
export const tag_filter_types = {
|
||||
|
@ -68,37 +60,20 @@ const DEFAULT_TAGS = [
|
|||
let tags = [];
|
||||
let tag_map = {};
|
||||
|
||||
function applyFavFilter(characterSelector) {
|
||||
function applyFavFilter(filterHelper) {
|
||||
const isSelected = $(this).hasClass('selected');
|
||||
const displayFavoritesOnly = !isSelected;
|
||||
|
||||
$(this).toggleClass('selected', displayFavoritesOnly);
|
||||
$(characterSelector).removeClass('hiddenByFav');
|
||||
|
||||
$(characterSelector).each(function () {
|
||||
if (displayFavoritesOnly) {
|
||||
if ($(this).find(".ch_fav").length !== 0) {
|
||||
const shouldBeDisplayed = $(this).find(".ch_fav").val().toLowerCase().includes(true);
|
||||
$(this).toggleClass('hiddenByFav', !shouldBeDisplayed);
|
||||
}
|
||||
}
|
||||
|
||||
});
|
||||
updateCharacterCount(characterSelector);
|
||||
updateVisibleDivs('#rm_print_characters_block', true);
|
||||
filterHelper.setFilterData(FILTER_TYPES.FAV, displayFavoritesOnly);
|
||||
}
|
||||
|
||||
function filterByGroups(characterSelector) {
|
||||
function filterByGroups(filterHelper) {
|
||||
const isSelected = $(this).hasClass('selected');
|
||||
const displayGroupsOnly = !isSelected;
|
||||
$(this).toggleClass('selected', displayGroupsOnly);
|
||||
$(characterSelector).removeClass('hiddenByGroup');
|
||||
|
||||
$(characterSelector).each((_, element) => {
|
||||
$(element).toggleClass('hiddenByGroup', displayGroupsOnly && !$(element).hasClass('group_select'));
|
||||
});
|
||||
updateCharacterCount(characterSelector);
|
||||
updateVisibleDivs('#rm_print_characters_block', true);
|
||||
filterHelper.setFilterData(FILTER_TYPES.GROUP, displayGroupsOnly);
|
||||
}
|
||||
|
||||
function loadTagsSettings(settings) {
|
||||
|
@ -291,7 +266,6 @@ function appendTagToList(listElement, tag, { removable, selectable, action, isGe
|
|||
return;
|
||||
}
|
||||
|
||||
const characterSelector = getCharacterSelector($(listElement));
|
||||
|
||||
let tagElement = $('#tag_template .tag').clone();
|
||||
tagElement.attr('id', tag.id);
|
||||
|
@ -316,11 +290,12 @@ function appendTagToList(listElement, tag, { removable, selectable, action, isGe
|
|||
}
|
||||
|
||||
if (selectable) {
|
||||
tagElement.on('click', () => onTagFilterClick.bind(tagElement)(listElement, characterSelector));
|
||||
tagElement.on('click', () => onTagFilterClick.bind(tagElement)(listElement));
|
||||
}
|
||||
|
||||
if (action) {
|
||||
tagElement.on('click', () => action.bind(tagElement)(characterSelector));
|
||||
const filter = getFilterHelper($(listElement));
|
||||
tagElement.on('click', () => action.bind(tagElement)(filter));
|
||||
tagElement.addClass('actionable');
|
||||
}
|
||||
if (action && tag.id === 2) {
|
||||
|
@ -330,7 +305,7 @@ function appendTagToList(listElement, tag, { removable, selectable, action, isGe
|
|||
$(listElement).append(tagElement);
|
||||
}
|
||||
|
||||
function onTagFilterClick(listElement, characterSelector) {
|
||||
function onTagFilterClick(listElement) {
|
||||
let excludeTag;
|
||||
if ($(this).hasClass('selected')) {
|
||||
$(this).removeClass('selected');
|
||||
|
@ -356,44 +331,10 @@ function onTagFilterClick(listElement, characterSelector) {
|
|||
}
|
||||
}
|
||||
|
||||
// TODO: Overhaul this somehow to use settings tag IDs instead
|
||||
const tagIds = [...($(listElement).find(".tag.selected:not(.actionable)").map((_, el) => $(el).attr("id")))];
|
||||
const excludedTagIds = [...($(listElement).find(".tag.excluded:not(.actionable)").map((_, el) => $(el).attr("id")))];
|
||||
$(characterSelector).each((_, element) => applyFilterToElement(tagIds, excludedTagIds, element));
|
||||
updateCharacterCount(characterSelector);
|
||||
updateVisibleDivs('#rm_print_characters_block', true);
|
||||
}
|
||||
|
||||
function applyFilterToElement(tagIds, excludedTagIds, element) {
|
||||
const tagFlags = tagIds.map(tagId => isElementTagged(element, tagId));
|
||||
const trueFlags = tagFlags.filter(x => x);
|
||||
const isTagged = TAG_LOGIC_AND ? tagFlags.length === trueFlags.length : trueFlags.length > 0;
|
||||
|
||||
const excludedTagFlags = excludedTagIds.map(tagId => isElementTagged(element, tagId));
|
||||
const isExcluded = excludedTagFlags.includes(true);
|
||||
|
||||
if (isExcluded) {
|
||||
$(element).addClass('hiddenByTag');
|
||||
} else if (tagIds.length > 0 && !isTagged) {
|
||||
$(element).addClass('hiddenByTag');
|
||||
} else {
|
||||
$(element).removeClass('hiddenByTag');
|
||||
}
|
||||
}
|
||||
|
||||
function isElementTagged(element, tagId) {
|
||||
const isGroup = $(element).hasClass('group_select');
|
||||
const isCharacter = $(element).hasClass('character_select') || $(element).hasClass('group_member');
|
||||
const idAttr = isGroup ? 'grid' : 'chid';
|
||||
const elementId = $(element).attr(idAttr);
|
||||
const lookupValue = isCharacter ? characters[elementId].avatar : elementId;
|
||||
const isTagged = Array.isArray(tag_map[lookupValue]) && tag_map[lookupValue].includes(tagId);
|
||||
return isTagged;
|
||||
}
|
||||
|
||||
function clearTagsFilter(characterSelector) {
|
||||
$('.rm_tag_filter .tag').removeClass('selected');
|
||||
$(characterSelector).removeClass('hiddenByTag');
|
||||
const filterHelper = getFilterHelper($(listElement));
|
||||
filterHelper.setFilterData(FILTER_TYPES.TAG, { excluded: excludedTagIds, selected: tagIds });
|
||||
}
|
||||
|
||||
function printTagFilters(type = tag_filter_types.character) {
|
||||
|
|
|
@ -1270,18 +1270,18 @@ input[type="file"] {
|
|||
filter: brightness(150%);
|
||||
}
|
||||
|
||||
#rm_character_count {
|
||||
padding: 5px;
|
||||
font-size: calc(var(--mainFontSize) * .8);
|
||||
font-weight: bold;
|
||||
#rm_print_characters_pagination {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
gap: 5px;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
#rm_print_characters_block {
|
||||
/* padding: 5px 0; */
|
||||
overflow-y: auto;
|
||||
flex-grow: 1;
|
||||
display: flex;
|
||||
/* row-gap: 5px; */
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
body.charListGrid #rm_print_characters_block {
|
||||
|
@ -1501,6 +1501,7 @@ select option:not(:checked) {
|
|||
display: flex;
|
||||
overflow-y: auto;
|
||||
flex-direction: column;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
#rm_characters_block .right_menu_button {
|
||||
|
@ -5616,3 +5617,64 @@ body.waifuMode .zoomed_avatar {
|
|||
vertical-align: middle;
|
||||
/* To align with adjacent text */
|
||||
}
|
||||
|
||||
.paginationjs {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
flex-direction: row;
|
||||
}
|
||||
|
||||
/* Pagination */
|
||||
.paginationsjs-pages {
|
||||
margin: 0.5em 0;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.paginationjs-pages ul {
|
||||
list-style-type: none;
|
||||
margin: 0.25em;
|
||||
padding: 0;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
gap: 5px;
|
||||
}
|
||||
|
||||
.paginationjs-size-changer select {
|
||||
width: unset;
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
.paginationjs-pages ul li a {
|
||||
padding: 0.05em 0.5em;
|
||||
text-decoration: none;
|
||||
color: var(--SmartThemeBodyColor);
|
||||
border: 1px solid var(--white30a);
|
||||
border-radius: 5px;
|
||||
transition: opacity 0.2s;
|
||||
opacity: 0.8;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.paginationjs-pages ul li a:hover {
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
.paginationjs-pages ul li.active a {
|
||||
color: var(--SmartThemeQuoteColor);
|
||||
border-color: var(--SmartThemeQuoteColor);
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
.paginationjs-pages ul li.disabled a {
|
||||
opacity: 0.5;
|
||||
cursor: not-allowed;
|
||||
}
|
||||
|
||||
.paginationjs-nav {
|
||||
padding: 5px;
|
||||
font-size: calc(var(--mainFontSize) * .8);
|
||||
font-weight: bold;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue