feat(ui): make chat the landing view
This commit is contained in:
@@ -70,7 +70,7 @@ const DEFAULT_CRON_FORM: CronFormState = {
|
||||
export class ClawdisApp extends LitElement {
|
||||
@state() settings: UiSettings = loadSettings();
|
||||
@state() password = "";
|
||||
@state() tab: Tab = "overview";
|
||||
@state() tab: Tab = "chat";
|
||||
@state() connected = false;
|
||||
@state() hello: GatewayHelloOk | null = null;
|
||||
@state() lastError: string | null = null;
|
||||
@@ -156,6 +156,7 @@ export class ClawdisApp extends LitElement {
|
||||
@state() debugCallError: string | null = null;
|
||||
|
||||
client: GatewayBrowserClient | null = null;
|
||||
private chatScrollFrame: number | null = null;
|
||||
|
||||
createRenderRoot() {
|
||||
return this;
|
||||
@@ -166,6 +167,18 @@ export class ClawdisApp extends LitElement {
|
||||
this.connect();
|
||||
}
|
||||
|
||||
protected updated(changed: Map<PropertyKey, unknown>) {
|
||||
if (
|
||||
this.tab === "chat" &&
|
||||
(changed.has("chatMessages") ||
|
||||
changed.has("chatStream") ||
|
||||
changed.has("chatLoading") ||
|
||||
changed.has("tab"))
|
||||
) {
|
||||
this.scheduleChatScroll();
|
||||
}
|
||||
}
|
||||
|
||||
connect() {
|
||||
this.lastError = null;
|
||||
this.hello = null;
|
||||
@@ -199,6 +212,16 @@ export class ClawdisApp extends LitElement {
|
||||
this.client.start();
|
||||
}
|
||||
|
||||
private scheduleChatScroll() {
|
||||
if (this.chatScrollFrame) cancelAnimationFrame(this.chatScrollFrame);
|
||||
this.chatScrollFrame = requestAnimationFrame(() => {
|
||||
this.chatScrollFrame = null;
|
||||
const container = this.querySelector(".messages") as HTMLElement | null;
|
||||
if (!container) return;
|
||||
container.scrollTop = container.scrollHeight;
|
||||
});
|
||||
}
|
||||
|
||||
private onEvent(evt: GatewayEventFrame) {
|
||||
this.eventLog = [
|
||||
{ ts: Date.now(), event: evt.event, payload: evt.payload },
|
||||
|
||||
@@ -1,10 +1,11 @@
|
||||
export const TAB_GROUPS = [
|
||||
{ label: "Chat", tabs: ["chat"] },
|
||||
{
|
||||
label: "Control",
|
||||
tabs: ["overview", "connections", "instances", "sessions", "cron"],
|
||||
},
|
||||
{ label: "Agent", tabs: ["chat", "skills", "nodes"] },
|
||||
{ label: "Gateway", tabs: ["config", "debug"] },
|
||||
{ label: "Agent", tabs: ["skills", "nodes"] },
|
||||
{ label: "Settings", tabs: ["config", "debug"] },
|
||||
] as const;
|
||||
|
||||
export type Tab =
|
||||
@@ -72,4 +73,3 @@ export function subtitleForTab(tab: Tab) {
|
||||
return "";
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -38,6 +38,7 @@ export function renderChat(props: ChatProps) {
|
||||
</div>
|
||||
|
||||
<div class="messages" style="margin-top: 12px;">
|
||||
${props.loading ? html`<div class="muted">Loading chat…</div>` : nothing}
|
||||
${props.messages.map((m) => renderMessage(m))}
|
||||
${props.stream
|
||||
? html`${renderMessage({
|
||||
@@ -113,4 +114,3 @@ function extractText(message: unknown): string | null {
|
||||
if (typeof m.text === "string") return m.text;
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user