Die monolithische ui.js (1534 Zeilen) zusammen mit chat.js (612) und history.js (626) in fokussierte Module aufgeteilt: Neue Dateien aus ui.js: - ui-helpers.js (126) - DOM-Utilities, $, esc, truncate, scrollDown, Toast - markdown.js (143) - renderMarkdown, wrapKreaGalleries, LaTeX/Code-Schutz - cards.js (90) - buildSessionCard, buildAgentCard - msg-actions.js (208) - Delete, Mark, Share, Reply-Button, Timestamp - tool-ui.js (332) - Tool-Boxes, Diffs, Todo-Liste, Visibility - modals.js (190) - System-Prompt, Command-Output, Krea-Image Modals - stream-ui.js (124) - Stream-Bubble, Review-Streaming - bubbles.js (312) - User/Assistant/Error/Warning/Choice/Review Bubbles Neue Dateien aus chat.js: - reply.js (54) - Reply/Quote-Handling mit pendingReply State - files.js (110) - File-Upload, Workspace-Refs mit pendingFiles/Refs State Neue Datei aus history.js: - archive.js (173) - Archiv-Loading mit loadedArchiveCount State Verbleibend: - chat.js (448) - Stream-Events, sendMessage, handleChoiceClick, Plan-Mode - history.js (464) - History laden, Polling, Message-Rendering Kein Code verändert, nur verschoben. Alle 94 Funktionen verifiziert. Globale Variablen in die Module verschoben, wo sie primär genutzt werden.
191 lines
6.0 KiB
JavaScript
191 lines
6.0 KiB
JavaScript
// ── System-Prompt Modal ──
|
|
|
|
function _renderSystemPromptBlocks(container, blocks) {
|
|
for (var i = 0; i < blocks.length; i++) {
|
|
var block = blocks[i];
|
|
if (!block.content) continue;
|
|
|
|
var wrapper = document.createElement('div');
|
|
wrapper.className = 'sp-block';
|
|
|
|
var label = document.createElement('div');
|
|
label.className = 'sp-block-label';
|
|
label.innerHTML = '<i class="fa ' + esc(block.icon || 'fa-cog') + '"></i> ' + esc(block.label || 'Block');
|
|
wrapper.appendChild(label);
|
|
|
|
var content = document.createElement('div');
|
|
content.className = 'sp-block-content markdown';
|
|
content.innerHTML = renderMarkdown(block.content);
|
|
parseFluentEmojis(content);
|
|
wrapper.appendChild(content);
|
|
|
|
container.appendChild(wrapper);
|
|
}
|
|
}
|
|
|
|
async function showSystemPromptModal(sessionId) {
|
|
// Overlay
|
|
const overlay = document.createElement('div');
|
|
overlay.className = 'sp-overlay';
|
|
|
|
// Modal
|
|
const modal = document.createElement('div');
|
|
modal.className = 'sp-modal';
|
|
|
|
// Header
|
|
const header = document.createElement('div');
|
|
header.className = 'sp-header';
|
|
const title = document.createElement('span');
|
|
title.textContent = 'System-Prompt';
|
|
const closeBtn = document.createElement('button');
|
|
closeBtn.innerHTML = '<i class="fa fa-times"></i>';
|
|
closeBtn.className = 'sp-close icon-btn';
|
|
header.appendChild(title);
|
|
header.appendChild(closeBtn);
|
|
|
|
// Body
|
|
const body = document.createElement('div');
|
|
body.className = 'sp-body markdown';
|
|
body.innerHTML = '<div class="sp-loading">Laden...</div>';
|
|
|
|
modal.appendChild(header);
|
|
modal.appendChild(body);
|
|
overlay.appendChild(modal);
|
|
document.body.appendChild(overlay);
|
|
|
|
// Schließen
|
|
const close = () => overlay.remove();
|
|
closeBtn.addEventListener('click', close);
|
|
overlay.addEventListener('click', (e) => {
|
|
if (e.target === overlay) close();
|
|
});
|
|
const onKey = (e) => {
|
|
if (e.key === 'Escape') { close(); document.removeEventListener('keydown', onKey); }
|
|
};
|
|
document.addEventListener('keydown', onKey);
|
|
|
|
// Laden
|
|
try {
|
|
const blocks = await apiGetSystemPromptBlocks(sessionId, typeof _planModeActive !== 'undefined' && _planModeActive);
|
|
body.innerHTML = '';
|
|
_renderSystemPromptBlocks(body, blocks);
|
|
} catch (e) {
|
|
body.innerHTML = '<div class="sp-loading" style="color:var(--dangerous)">Fehler beim Laden des System-Prompts</div>';
|
|
}
|
|
}
|
|
|
|
// ── Command Output Modal ──
|
|
|
|
function showCommandOutputModal(name, command, result) {
|
|
const overlay = document.createElement('div');
|
|
overlay.className = 'sp-overlay';
|
|
|
|
const modal = document.createElement('div');
|
|
modal.className = 'sp-modal cmd-output-modal';
|
|
|
|
// Header
|
|
const header = document.createElement('div');
|
|
header.className = 'sp-header';
|
|
const title = document.createElement('span');
|
|
title.textContent = name;
|
|
const closeBtn = document.createElement('button');
|
|
closeBtn.innerHTML = '<i class="fa fa-times"></i>';
|
|
closeBtn.className = 'sp-close icon-btn';
|
|
header.appendChild(title);
|
|
header.appendChild(closeBtn);
|
|
|
|
// Body
|
|
const body = document.createElement('div');
|
|
body.className = 'sp-body';
|
|
|
|
const exitCode = result.exitCode != null ? result.exitCode : '?';
|
|
const isError = exitCode !== 0;
|
|
const statusText = result.status === 'timeout' ? 'Timeout' : (isError ? `Exit ${exitCode}` : `Exit ${exitCode}`);
|
|
|
|
const meta = document.createElement('div');
|
|
meta.className = 'cmd-output-meta';
|
|
meta.innerHTML = `<code>${esc(command)}</code> <span class="cmd-exit-code${isError ? ' cmd-exit-error' : ''}">${esc(statusText)}</span>`;
|
|
body.appendChild(meta);
|
|
|
|
const output = document.createElement('pre');
|
|
output.className = 'cmd-output-content';
|
|
output.textContent = result.output || '(kein Output)';
|
|
body.appendChild(output);
|
|
|
|
modal.appendChild(header);
|
|
modal.appendChild(body);
|
|
overlay.appendChild(modal);
|
|
document.body.appendChild(overlay);
|
|
|
|
// Schließen
|
|
const close = () => overlay.remove();
|
|
closeBtn.addEventListener('click', close);
|
|
overlay.addEventListener('click', (e) => {
|
|
if (e.target === overlay) close();
|
|
});
|
|
const onKey = (e) => {
|
|
if (e.key === 'Escape') { close(); document.removeEventListener('keydown', onKey); }
|
|
};
|
|
document.addEventListener('keydown', onKey);
|
|
}
|
|
|
|
// ── Krea Image Preview Modal ──
|
|
|
|
function showKreaImageModal(title, fullUrl) {
|
|
var overlay = document.createElement('div');
|
|
overlay.className = 'sp-overlay krea-overlay';
|
|
|
|
var modal = document.createElement('div');
|
|
modal.className = 'sp-modal krea-modal';
|
|
|
|
// Header
|
|
var header = document.createElement('div');
|
|
header.className = 'sp-header';
|
|
var titleEl = document.createElement('span');
|
|
titleEl.textContent = title;
|
|
var closeBtn = document.createElement('button');
|
|
closeBtn.innerHTML = '<i class="fa fa-times"></i>';
|
|
closeBtn.className = 'sp-close icon-btn';
|
|
header.appendChild(titleEl);
|
|
header.appendChild(closeBtn);
|
|
|
|
// Body
|
|
var body = document.createElement('div');
|
|
body.className = 'sp-body krea-modal-body';
|
|
|
|
var img = document.createElement('img');
|
|
img.src = fullUrl;
|
|
img.className = 'krea-modal-image';
|
|
img.alt = title;
|
|
img.addEventListener('error', function() {
|
|
body.innerHTML = '<div class="sp-loading" style="color:var(--dangerous)">Bild konnte nicht geladen werden</div>';
|
|
});
|
|
|
|
body.appendChild(img);
|
|
modal.appendChild(header);
|
|
modal.appendChild(body);
|
|
overlay.appendChild(modal);
|
|
document.body.appendChild(overlay);
|
|
|
|
// Schließen
|
|
var close = function() { overlay.remove(); };
|
|
closeBtn.addEventListener('click', close);
|
|
overlay.addEventListener('click', function(e) {
|
|
if (e.target === overlay) close();
|
|
});
|
|
var onKey = function(e) {
|
|
if (e.key === 'Escape') { close(); document.removeEventListener('keydown', onKey); }
|
|
};
|
|
document.addEventListener('keydown', onKey);
|
|
}
|
|
|
|
// Event-Delegation für Krea-Thumbnails im Chat
|
|
document.addEventListener('click', function(e) {
|
|
var ref = e.target.closest('.krea-ref');
|
|
if (ref) {
|
|
var fullUrl = ref.dataset.fullurl;
|
|
var filename = ref.dataset.filename;
|
|
if (fullUrl) showKreaImageModal(filename || 'Bild', fullUrl);
|
|
}
|
|
});
|