mirror of
https://github.com/SillyTavern/SillyTavern.git
synced 2025-06-05 21:59:27 +02:00
Merge branch 'dev' into dev
This commit is contained in:
@@ -2787,7 +2787,6 @@
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div id="group_list_template" class="template_element">
|
||||
<div class="group_select flex-container wide100p alignitemsflexstart">
|
||||
<div class="avatar">
|
||||
|
@@ -5486,16 +5486,17 @@ $(document).ready(function () {
|
||||
" -- Name: " +
|
||||
characters[this_chid].name
|
||||
);
|
||||
const avatar = characters[this_chid].avatar;
|
||||
const name = characters[this_chid].name;
|
||||
var msg = jQuery("#form_create").serialize(); // ID form
|
||||
jQuery.ajax({
|
||||
method: "POST",
|
||||
url: "/deletecharacter",
|
||||
beforeSend: function () {
|
||||
select_rm_info("char_delete", characters[this_chid].name);
|
||||
},
|
||||
data: msg,
|
||||
cache: false,
|
||||
success: function (html) {
|
||||
success: async function (html) {
|
||||
//RossAscends: New handling of character deletion that avoids page refreshes and should have
|
||||
// fixed char corruption due to cache problems.
|
||||
//due to how it is handled with 'popup_type', i couldn't find a way to make my method completely
|
||||
@@ -5516,7 +5517,9 @@ $(document).ready(function () {
|
||||
.text(""); // removes character name from nav tabs
|
||||
clearChat(); // removes deleted char's chat
|
||||
this_chid = undefined; // prevents getCharacters from trying to load an invalid char.
|
||||
getCharacters(); // gets the new list of characters (that doesn't include the deleted one)
|
||||
delete tag_map[avatar]; // removes deleted char's avatar from tag_map
|
||||
await getCharacters(); // gets the new list of characters (that doesn't include the deleted one)
|
||||
select_rm_info("char_delete", name); // also updates the 'deleted character' message
|
||||
printMessages(); // prints out system user's 'deleted character' message
|
||||
//console.log("#dialogue_popup_ok(del-char) >>>> saving");
|
||||
saveSettingsDebounced(); // saving settings to keep changes to variables
|
||||
|
@@ -78,7 +78,6 @@ async function updateVisualNovelMode(name, expression) {
|
||||
async function visualNovelRemoveInactive(container) {
|
||||
const context = getContext();
|
||||
const group = context.groups.find(x => x.id == context.groupId);
|
||||
const members = group.members;
|
||||
const removeInactiveCharactersPromises = [];
|
||||
|
||||
// remove inactive characters after 1 second
|
||||
@@ -87,7 +86,7 @@ async function visualNovelRemoveInactive(container) {
|
||||
const element = $(current);
|
||||
const avatar = element.data('avatar');
|
||||
|
||||
if (!members.includes(avatar) || group.disabled_members.includes(avatar)) {
|
||||
if (!group.members.includes(avatar) || group.disabled_members.includes(avatar)) {
|
||||
element.fadeOut(250, () => {
|
||||
element.remove();
|
||||
resolve();
|
||||
@@ -106,13 +105,12 @@ async function visualNovelRemoveInactive(container) {
|
||||
async function visualNovelSetCharacterSprites(container, name, expression) {
|
||||
const context = getContext();
|
||||
const group = context.groups.find(x => x.id == context.groupId);
|
||||
const members = group.members;
|
||||
const labels = await getExpressionsList();
|
||||
|
||||
const createCharacterPromises = [];
|
||||
const setSpritePromises = [];
|
||||
|
||||
for (const avatar of members) {
|
||||
for (const avatar of group.members) {
|
||||
const isDisabled = group.disabled_members.includes(avatar);
|
||||
|
||||
// skip disabled characters
|
||||
@@ -121,6 +119,11 @@ async function visualNovelSetCharacterSprites(container, name, expression) {
|
||||
}
|
||||
|
||||
const character = context.characters.find(x => x.avatar == avatar);
|
||||
|
||||
if (!character) {
|
||||
continue;
|
||||
}
|
||||
|
||||
let spriteFolderName = character.name;
|
||||
const avatarFileName = getSpriteFolderName({ original_avatar: character.avatar });
|
||||
const expressionOverride = extension_settings.expressionOverrides.find((e) =>
|
||||
@@ -142,7 +145,9 @@ async function visualNovelSetCharacterSprites(container, name, expression) {
|
||||
const noSprites = sprites.length === 0;
|
||||
|
||||
if (expressionImage.length > 0) {
|
||||
if (name == character.name) {
|
||||
if (name == spriteFolderName) {
|
||||
await validateImages(spriteFolderName, true);
|
||||
setExpressionOverrideHtml(true); // <= force clear expression override input
|
||||
const currentSpritePath = labels.includes(expression) ? sprites.find(x => x.label === expression)?.path : '';
|
||||
|
||||
const path = currentSpritePath || defaultSpritePath || '';
|
||||
@@ -175,9 +180,8 @@ async function visualNovelSetCharacterSprites(container, name, expression) {
|
||||
async function visualNovelUpdateLayers(container) {
|
||||
const context = getContext();
|
||||
const group = context.groups.find(x => x.id == context.groupId);
|
||||
const members = group.members;
|
||||
const recentMessages = context.chat.map(x => x.original_avatar).filter(x => x).reverse().filter(onlyUnique);
|
||||
const filteredMembers = members.filter(x => !group.disabled_members.includes(x));
|
||||
const filteredMembers = group.members.filter(x => !group.disabled_members.includes(x));
|
||||
const layerIndices = filteredMembers.slice().sort((a, b) => recentMessages.indexOf(b) - recentMessages.indexOf(a));
|
||||
|
||||
const setLayerIndicesPromises = [];
|
||||
@@ -270,6 +274,8 @@ function setImage(img, path) {
|
||||
img.removeClass('default');
|
||||
img.off('error');
|
||||
img.on('error', function () {
|
||||
console.debug('Error loading image', path);
|
||||
$(this).off('error');
|
||||
$(this).attr('src', '');
|
||||
});
|
||||
}
|
||||
@@ -362,6 +368,7 @@ async function moduleWorker() {
|
||||
spriteCache = {};
|
||||
expressionsList = await getExpressionsList();
|
||||
await validateImages(spriteFolderName, true);
|
||||
await forceUpdateVisualNovelMode();
|
||||
}
|
||||
|
||||
offlineMode.css('display', 'none');
|
||||
@@ -423,7 +430,6 @@ function getSpriteFolderName(message) {
|
||||
}
|
||||
|
||||
const folderName = avatarPath.replace(/\.[^/.]+$/, "");
|
||||
console.debug(`Folder for ${message.name}:`, folderName);
|
||||
return folderName;
|
||||
}
|
||||
|
||||
@@ -622,7 +628,9 @@ async function setExpression(character, expression, force) {
|
||||
img.removeClass('default');
|
||||
img.off('error');
|
||||
img.on('error', function () {
|
||||
console.debug('Expression image error', sprite.path);
|
||||
$(this).attr('src', '');
|
||||
$(this).off('error');
|
||||
if (force && extension_settings.expressions.showDefault) {
|
||||
setDefault();
|
||||
}
|
||||
@@ -845,7 +853,7 @@ async function onClickExpressionDelete(event) {
|
||||
await validateImages(name);
|
||||
}
|
||||
|
||||
function setExpressionOverrideHtml() {
|
||||
function setExpressionOverrideHtml(forceClear = false) {
|
||||
const currentLastMessage = getLastCharacterMessage();
|
||||
const avatarFileName = getSpriteFolderName(currentLastMessage);
|
||||
if (!avatarFileName) {
|
||||
@@ -861,6 +869,10 @@ function setExpressionOverrideHtml() {
|
||||
} else if (expressionOverride) {
|
||||
delete extension_settings.expressionOverrides[expressionOverride.name];
|
||||
}
|
||||
|
||||
if (forceClear && !expressionOverride) {
|
||||
$("#expression_override").val("");
|
||||
}
|
||||
}
|
||||
|
||||
(function () {
|
||||
|
@@ -18,7 +18,7 @@
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
#visual-novel-wrapper .expression-holder {
|
||||
#visual-novel-wrapper .expression-holder {
|
||||
width: max-content;
|
||||
}
|
||||
|
||||
@@ -75,6 +75,7 @@ img.expression.default {
|
||||
.expression_list_item {
|
||||
position: relative;
|
||||
max-width: 20%;
|
||||
min-width: 100px;
|
||||
max-height: 200px;
|
||||
background-color: #515151b0;
|
||||
border-radius: 10px;
|
||||
@@ -108,10 +109,16 @@ img.expression.default {
|
||||
flex-direction: row;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
height: 20%;
|
||||
/* height: 20%; */
|
||||
padding: 0.25rem;
|
||||
}
|
||||
|
||||
.menu_button.expression_list_delete,
|
||||
.menu_button.expression_list_upload {
|
||||
margin-top: 0;
|
||||
margin-bottom: 0;
|
||||
}
|
||||
|
||||
.expression_list_image {
|
||||
max-width: 100%;
|
||||
height: 100%;
|
||||
@@ -164,4 +171,4 @@ img.expression.default {
|
||||
div.expression {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
}
|
@@ -633,11 +633,11 @@ function isConnectedToExtras() {
|
||||
|
||||
async function moduleWorker() {
|
||||
if (isConnectedToExtras() || extension_settings.sd.horde) {
|
||||
$('#sd_gen').show(200);
|
||||
$('#sd_gen').show();
|
||||
$('.sd_message_gen').show();
|
||||
}
|
||||
else {
|
||||
$('#sd_gen').hide(200);
|
||||
$('#sd_gen').hide();
|
||||
$('.sd_message_gen').hide();
|
||||
}
|
||||
}
|
||||
|
@@ -57,7 +57,7 @@ import {
|
||||
event_types,
|
||||
getCurrentChatId,
|
||||
} from "../script.js";
|
||||
import { appendTagToList, createTagMapFromList, getTagsList, applyTagsOnCharacterSelect } from './tags.js';
|
||||
import { appendTagToList, createTagMapFromList, getTagsList, applyTagsOnCharacterSelect, tag_map } from './tags.js';
|
||||
|
||||
export {
|
||||
selected_group,
|
||||
@@ -786,6 +786,7 @@ async function deleteGroup(id) {
|
||||
|
||||
if (response.ok) {
|
||||
selected_group = null;
|
||||
delete tag_map[id];
|
||||
resetChatState();
|
||||
clearChat();
|
||||
printMessages();
|
||||
@@ -1004,7 +1005,7 @@ function select_group_chats(groupId, skipAnimation) {
|
||||
}
|
||||
|
||||
$("#dialogue_popup").data("group_id", groupId);
|
||||
callPopup("<h3>Delete the group?</h3>", "del_group");
|
||||
callPopup('<h3>Delete the group?</h3><p>This will also delete all your chats with that group. If you want to delete a single conversation, select a "View past chats" option in the lower left menu.</p>', "del_group");
|
||||
});
|
||||
|
||||
updateFavButtonState(group?.fav ?? false);
|
||||
|
@@ -423,7 +423,7 @@ code {
|
||||
margin: 0 auto 0 auto;
|
||||
border: 1px solid var(--grey30a);
|
||||
|
||||
border-radius: 0 0 20px 20px;
|
||||
border-radius: 0 0 10px 10px;
|
||||
background-color: var(--SmartThemeBlurTintColor);
|
||||
backdrop-filter: blur(var(--SmartThemeBlurStrength));
|
||||
}
|
||||
@@ -511,12 +511,12 @@ code {
|
||||
display: block;
|
||||
background-color: var(--SmartThemeBlurTintColor);
|
||||
border: 1px solid var(--white30a);
|
||||
border-radius: 15px;
|
||||
border-radius: 10px;
|
||||
box-shadow: 0 0 5px black;
|
||||
text-shadow: 0px 0px calc(var(--shadowWidth) * 1px) var(--SmartThemeShadowColor);
|
||||
backdrop-filter: blur(calc(var(--SmartThemeBlurStrength)*2));
|
||||
z-index: 2000;
|
||||
margin-bottom: 3px;
|
||||
/* margin-bottom: 0px;*/
|
||||
}
|
||||
|
||||
.options-content i {
|
||||
@@ -578,10 +578,11 @@ hr {
|
||||
.options-content a,
|
||||
#extensionsMenu>div {
|
||||
color: var(--SmartThemeBodyColor);
|
||||
padding: 12px 16px;
|
||||
padding: 5px 5px;
|
||||
padding-bottom: 5px;
|
||||
text-decoration: none;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
/* align-items: center; */
|
||||
column-gap: 10px;
|
||||
cursor: pointer;
|
||||
}
|
||||
@@ -3363,7 +3364,7 @@ a {
|
||||
background-color: var(--SmartThemeBlurTintColor);
|
||||
backdrop-filter: blur(calc(var(--SmartThemeBlurStrength)*2));
|
||||
border: 1px solid var(--white30a);
|
||||
border-radius: 15px;
|
||||
border-radius: 10px;
|
||||
box-shadow: 0 0 5px black;
|
||||
text-shadow: 0px 0px calc(var(--shadowWidth) * 1px) var(--SmartThemeShadowColor);
|
||||
}
|
||||
@@ -3727,9 +3728,10 @@ label[for="extensions_autoconnect"] {
|
||||
left: 0;
|
||||
right: auto;
|
||||
padding: 5px;
|
||||
border-radius: 0 0 20px 0;
|
||||
border-radius: 10px;
|
||||
box-shadow: none;
|
||||
overflow: hidden;
|
||||
border: 1px solid var(--grey30a);
|
||||
}
|
||||
|
||||
.scrollableInner {
|
||||
|
23
server.js
23
server.js
@@ -2181,16 +2181,29 @@ app.post('/deletegroup', jsonParser, async (request, response) => {
|
||||
|
||||
const id = request.body.id;
|
||||
const pathToGroup = path.join(directories.groups, sanitize(`${id}.json`));
|
||||
const pathToChat = path.join(directories.groupChats, sanitize(`${id}.jsonl`));
|
||||
|
||||
try {
|
||||
// Delete group chats
|
||||
const group = json5.parse(fs.readFileSync(pathToGroup));
|
||||
|
||||
if (group && Array.isArray(group.chats)) {
|
||||
for (const chat of group.chats) {
|
||||
console.log('Deleting group chat', chat);
|
||||
const pathToFile = path.join(directories.groupChats, `${id}.jsonl`);
|
||||
|
||||
if (fs.existsSync(pathToFile)) {
|
||||
fs.rmSync(pathToFile);
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (error) {
|
||||
console.error('Could not delete group chats. Clean them up manually.', error);
|
||||
}
|
||||
|
||||
if (fs.existsSync(pathToGroup)) {
|
||||
fs.rmSync(pathToGroup);
|
||||
}
|
||||
|
||||
if (fs.existsSync(pathToChat)) {
|
||||
fs.rmSync(pathToChat);
|
||||
}
|
||||
|
||||
return response.send({ ok: true });
|
||||
});
|
||||
|
||||
|
Reference in New Issue
Block a user