mirror of
https://github.com/pewdiepie-archdaemon/odysseus.git
synced 2026-09-27 18:42:20 +02:00
Squash Odysseus development history
This commit is contained in:
+51
-25
@@ -3,19 +3,35 @@
|
||||
|
||||
import Storage from './storage.js';
|
||||
|
||||
function markComposerUserEdited() {
|
||||
const msgInput = document.getElementById('message');
|
||||
if (!msgInput || msgInput.dataset.startupPreserveBound === '1') return;
|
||||
msgInput.dataset.startupPreserveBound = '1';
|
||||
msgInput.addEventListener('input', () => {
|
||||
window.__odysseusComposerUserEdited = !!msgInput.value;
|
||||
});
|
||||
}
|
||||
|
||||
function clearFreshComposerRestore() {
|
||||
const msgInput = document.getElementById('message');
|
||||
if (!msgInput) return;
|
||||
const hasSessionTarget = !!(window.location.hash || Storage.get('lastSessionId'));
|
||||
markComposerUserEdited();
|
||||
const hash = window.location.hash || '';
|
||||
const isEntityHash = /^#(?:document|note|image|email|event|task|skill|research)-/.test(hash)
|
||||
|| /^#open=notes¬e=/.test(hash);
|
||||
const hasSessionTarget = !!(hash && !isEntityHash);
|
||||
if (hasSessionTarget) return;
|
||||
if (window.__odysseusComposerUserEdited || document.activeElement === msgInput) return;
|
||||
if (msgInput.value) {
|
||||
msgInput.value = '';
|
||||
msgInput.dispatchEvent(new Event('input', { bubbles: true }));
|
||||
}
|
||||
}
|
||||
|
||||
markComposerUserEdited();
|
||||
clearFreshComposerRestore();
|
||||
window.addEventListener('pageshow', clearFreshComposerRestore);
|
||||
document.addEventListener('DOMContentLoaded', markComposerUserEdited, { once: true });
|
||||
|
||||
// SECURITY: defense-in-depth state wipe on user switch. If the authenticated
|
||||
// user is different from the one whose state is cached in this browser,
|
||||
@@ -62,7 +78,7 @@ window.addEventListener('pageshow', clearFreshComposerRestore);
|
||||
// Research — sidebar tool + the in-input deep-research toggle.
|
||||
hideOn('#tool-research-btn, #research-toggle-btn', privs.can_use_research);
|
||||
// Memory & skills (rail/tool button only — UI/API entry).
|
||||
hideOn('#tool-memory-btn', privs.can_manage_memory);
|
||||
hideOn('#tool-memory-btn, #rail-memory, #tool-skills-btn, #rail-skills', privs.can_manage_memory);
|
||||
// Agent mode toggle — force chat mode by hiding the Agent toggle button.
|
||||
if (privs.can_use_agent === false) {
|
||||
const _agent = document.getElementById('mode-agent-btn');
|
||||
@@ -165,6 +181,39 @@ window.addEventListener('pageshow', clearFreshComposerRestore);
|
||||
window.addEventListener('resize', _sync);
|
||||
}
|
||||
|
||||
/* Keep minimized tool chips above the composer. Both the current modalManager
|
||||
dock and the legacy fallback dock consume this root-level clearance. */
|
||||
{
|
||||
const root = document.documentElement;
|
||||
const chatBar = document.querySelector('.chat-input-bar');
|
||||
const attachStrip = document.getElementById('attach-strip');
|
||||
const chatContainer = document.getElementById('chat-container');
|
||||
const _syncComposerClearance = () => {
|
||||
let top = window.innerHeight;
|
||||
for (const el of [attachStrip, chatBar]) {
|
||||
if (!el) continue;
|
||||
const rect = el.getBoundingClientRect();
|
||||
if (rect.height > 0) top = Math.min(top, rect.top);
|
||||
}
|
||||
const clearance = Math.max(12, Math.ceil(window.innerHeight - top + 8));
|
||||
root.style.setProperty('--composer-clearance', clearance + 'px');
|
||||
};
|
||||
requestAnimationFrame(_syncComposerClearance);
|
||||
if (typeof ResizeObserver !== 'undefined') {
|
||||
const ro = new ResizeObserver(_syncComposerClearance);
|
||||
if (chatBar) ro.observe(chatBar);
|
||||
if (attachStrip) ro.observe(attachStrip);
|
||||
}
|
||||
if (chatContainer && typeof MutationObserver !== 'undefined') {
|
||||
new MutationObserver(_syncComposerClearance).observe(chatContainer, {
|
||||
attributes: true,
|
||||
attributeFilter: ['class'],
|
||||
});
|
||||
}
|
||||
if (chatBar) chatBar.addEventListener('transitionend', _syncComposerClearance);
|
||||
window.addEventListener('resize', _syncComposerClearance);
|
||||
}
|
||||
|
||||
/* ---- Resizable sidebar — drag edge to resize, collapse if small, drag rail edge to expand ---- */
|
||||
{
|
||||
const sidebar = document.getElementById('sidebar');
|
||||
@@ -323,29 +372,6 @@ window.addEventListener('pageshow', clearFreshComposerRestore);
|
||||
});
|
||||
}
|
||||
|
||||
// Fade welcome screen when mobile keyboard opens (input focus/blur)
|
||||
if ('ontouchstart' in window) {
|
||||
document.addEventListener('DOMContentLoaded', function() {
|
||||
var _msgInput = document.getElementById('message');
|
||||
if (!_msgInput) return;
|
||||
_msgInput.addEventListener('focus', function() {
|
||||
var welcome = document.getElementById('welcome-screen');
|
||||
if (welcome && !welcome.classList.contains('hidden')) {
|
||||
welcome.style.transition = 'opacity 0.2s ease, transform 0.2s ease';
|
||||
welcome.style.opacity = '0';
|
||||
welcome.style.transform = 'translate(-50%, -50%) scale(0.92)';
|
||||
}
|
||||
});
|
||||
_msgInput.addEventListener('blur', function() {
|
||||
var welcome = document.getElementById('welcome-screen');
|
||||
if (welcome && !welcome.classList.contains('hidden')) {
|
||||
welcome.style.transition = 'opacity 0.3s ease, transform 0.3s cubic-bezier(0.34, 1.56, 0.64, 1)';
|
||||
welcome.style.opacity = '';
|
||||
welcome.style.transform = '';
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
/* ── Release welcome-screen entrance animations once the page is settled ──
|
||||
|
||||
Reference in New Issue
Block a user