@elizaos/ui 2.0.0-alpha.344 → 2.0.0-alpha.346
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +1 -1
- package/packages/typescript/src/features/basic-capabilities/providers/actionState.d.ts.map +1 -1
- package/packages/typescript/src/features/basic-capabilities/providers/actionState.js +8 -51
- package/packages/typescript/src/features/basic-capabilities/providers/actions.d.ts.map +1 -1
- package/packages/typescript/src/features/basic-capabilities/providers/actions.js +2 -2
- package/packages/typescript/src/features/basic-capabilities/providers/non-actionable-chatter.d.ts.map +1 -1
- package/packages/typescript/src/features/basic-capabilities/providers/non-actionable-chatter.js +2 -4
- package/packages/typescript/src/features/basic-capabilities/providers/providers.d.ts.map +1 -1
- package/packages/typescript/src/features/basic-capabilities/providers/providers.js +2 -2
- package/packages/typescript/src/features/knowledge/utils.d.ts.map +1 -1
- package/packages/typescript/src/features/knowledge/utils.js +4 -3
- package/packages/typescript/src/runtime.d.ts +2 -0
- package/packages/typescript/src/runtime.d.ts.map +1 -1
- package/packages/typescript/src/runtime.js +80 -0
- package/packages/typescript/src/services/message.d.ts +3 -1
- package/packages/typescript/src/services/message.d.ts.map +1 -1
- package/packages/typescript/src/services/message.js +91 -135
- package/packages/typescript/src/utils/action-results.d.ts +33 -0
- package/packages/typescript/src/utils/action-results.d.ts.map +1 -0
- package/packages/typescript/src/utils/action-results.js +169 -0
- package/packages/typescript/src/utils/context-catalog.d.ts.map +1 -1
- package/packages/typescript/src/utils/context-catalog.js +11 -0
- package/packages/typescript/src/utils/context-routing.d.ts +3 -0
- package/packages/typescript/src/utils/context-routing.d.ts.map +1 -1
- package/packages/typescript/src/utils/context-routing.js +88 -0
- package/packages/typescript/src/utils/message-text.d.ts +5 -0
- package/packages/typescript/src/utils/message-text.d.ts.map +1 -0
- package/packages/typescript/src/utils/message-text.js +24 -0
- package/packages/typescript/src/utils.d.ts +2 -1
- package/packages/typescript/src/utils.d.ts.map +1 -1
- package/packages/typescript/src/utils.js +2 -1
- package/packages/ui/src/components/composites/chat/chat-composer.d.ts.map +1 -1
- package/packages/ui/src/components/composites/chat/chat-composer.js +101 -19
- package/packages/ui/src/layouts/page-layout/page-layout-mobile-drawer.d.ts.map +1 -1
- package/packages/ui/src/layouts/page-layout/page-layout-mobile-drawer.js +23 -4
- package/packages/ui/src/layouts/workspace-layout/index.d.ts +1 -0
- package/packages/ui/src/layouts/workspace-layout/index.d.ts.map +1 -1
- package/packages/ui/src/layouts/workspace-layout/index.js +1 -0
- package/packages/ui/src/layouts/workspace-layout/workspace-layout.d.ts.map +1 -1
- package/packages/ui/src/layouts/workspace-layout/workspace-layout.js +8 -2
- package/packages/ui/src/layouts/workspace-layout/workspace-mobile-sidebar-controls.d.ts +13 -0
- package/packages/ui/src/layouts/workspace-layout/workspace-mobile-sidebar-controls.d.ts.map +1 -0
- package/packages/ui/src/layouts/workspace-layout/workspace-mobile-sidebar-controls.js +5 -0
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { resolveActionContexts, resolveProviderContexts, } from "./context-catalog";
|
|
2
|
+
import { normalizeUserMessageText } from "./message-text";
|
|
2
3
|
export const AVAILABLE_CONTEXTS_STATE_KEY = "availableContexts";
|
|
3
4
|
export const CONTEXT_ROUTING_METADATA_KEY = "__responseContext";
|
|
4
5
|
export const CONTEXT_ROUTING_STATE_KEY = "__contextRouting";
|
|
@@ -107,6 +108,9 @@ export function getActiveRoutingContexts(routing) {
|
|
|
107
108
|
contextSet.add("general");
|
|
108
109
|
return Array.from(contextSet);
|
|
109
110
|
}
|
|
111
|
+
export function getActiveRoutingContextsForTurn(state, message) {
|
|
112
|
+
return getActiveRoutingContexts(mergeContextRouting(state, message));
|
|
113
|
+
}
|
|
110
114
|
export function shouldIncludeByContext(declaredContexts, activeContexts) {
|
|
111
115
|
if (!declaredContexts || declaredContexts.length === 0) {
|
|
112
116
|
return true;
|
|
@@ -152,6 +156,90 @@ export function deriveAvailableContexts(actions, providers) {
|
|
|
152
156
|
}
|
|
153
157
|
return Array.from(contextSet).sort((a, b) => `${a}`.localeCompare(`${b}`));
|
|
154
158
|
}
|
|
159
|
+
const CONTEXT_SIGNALS = [
|
|
160
|
+
{
|
|
161
|
+
context: "code",
|
|
162
|
+
patterns: [
|
|
163
|
+
/\b(repo|repository|codebase|branch|commit|pull request|pr|diff|workspace|file|directory)\b/u,
|
|
164
|
+
/\b(code|coding|implement|debug|fix|refactor|patch|test|typecheck|lint|build|component|api|server|client)\b/u,
|
|
165
|
+
/\b(task agents?|sub-?agents?|coding agents?|codex|claude code|spawn an? agent|agent running|what are you working on)\b/u,
|
|
166
|
+
],
|
|
167
|
+
},
|
|
168
|
+
{
|
|
169
|
+
context: "automation",
|
|
170
|
+
patterns: [
|
|
171
|
+
/\b(schedule|remind|reminder|cron|workflow|automate|automation|run this|execute|deploy|release|monitor)\b/u,
|
|
172
|
+
/\b(task agents?|sub-?agents?|agent running|pause that|resume that|stop that|continue that|what are you working on)\b/u,
|
|
173
|
+
],
|
|
174
|
+
},
|
|
175
|
+
{
|
|
176
|
+
context: "knowledge",
|
|
177
|
+
patterns: [
|
|
178
|
+
/\b(uploaded|document|file|pdf|knowledge|remember|recall|search|lookup|find|summari[sz]e|analy[sz]e|research)\b/u,
|
|
179
|
+
/\b(what is|what was|where is|tell me about|explain)\b/u,
|
|
180
|
+
],
|
|
181
|
+
},
|
|
182
|
+
{
|
|
183
|
+
context: "browser",
|
|
184
|
+
patterns: [
|
|
185
|
+
/\b(browser|browse|website|web page|url|click|type into|screenshot|navigate|extract page)\b/u,
|
|
186
|
+
],
|
|
187
|
+
},
|
|
188
|
+
{
|
|
189
|
+
context: "media",
|
|
190
|
+
patterns: [
|
|
191
|
+
/\b(image|picture|photo|video|audio|voice|transcribe|screenshot|draw|generate an image)\b/u,
|
|
192
|
+
],
|
|
193
|
+
},
|
|
194
|
+
{
|
|
195
|
+
context: "wallet",
|
|
196
|
+
patterns: [
|
|
197
|
+
/\b(wallet|token|swap|bridge|stake|unstake|balance|portfolio|transaction|sign message|contract)\b/u,
|
|
198
|
+
],
|
|
199
|
+
},
|
|
200
|
+
{
|
|
201
|
+
context: "social",
|
|
202
|
+
patterns: [
|
|
203
|
+
/\b(message|dm|email|inbox|contact|relationship|follow up|calendar|meeting|call|send .* to)\b/u,
|
|
204
|
+
],
|
|
205
|
+
},
|
|
206
|
+
{
|
|
207
|
+
context: "system",
|
|
208
|
+
patterns: [
|
|
209
|
+
/\b(settings?|configure|configuration|plugin|secret|api key|model provider|oauth|login|auth)\b/u,
|
|
210
|
+
],
|
|
211
|
+
},
|
|
212
|
+
];
|
|
213
|
+
export function inferContextRoutingFromText(text) {
|
|
214
|
+
const normalized = normalizeUserMessageText({
|
|
215
|
+
content: { text: text ?? "" },
|
|
216
|
+
});
|
|
217
|
+
if (!normalized) {
|
|
218
|
+
return { primaryContext: "general", secondaryContexts: [] };
|
|
219
|
+
}
|
|
220
|
+
const scored = CONTEXT_SIGNALS.map((signal) => ({
|
|
221
|
+
context: signal.context,
|
|
222
|
+
score: signal.patterns.reduce((score, pattern) => score + (pattern.test(normalized) ? 1 : 0), 0),
|
|
223
|
+
}))
|
|
224
|
+
.filter((entry) => entry.score > 0)
|
|
225
|
+
.sort((left, right) => right.score - left.score);
|
|
226
|
+
if (scored.length === 0) {
|
|
227
|
+
return { primaryContext: "general", secondaryContexts: [] };
|
|
228
|
+
}
|
|
229
|
+
const primaryContext = scored[0].context;
|
|
230
|
+
const secondaryContexts = scored
|
|
231
|
+
.slice(1)
|
|
232
|
+
.filter((entry) => entry.score >= Math.max(1, scored[0].score - 1))
|
|
233
|
+
.map((entry) => entry.context);
|
|
234
|
+
return { primaryContext, secondaryContexts };
|
|
235
|
+
}
|
|
236
|
+
export function inferContextRoutingFromMessage(message) {
|
|
237
|
+
return inferContextRoutingFromText(typeof message.content === "string"
|
|
238
|
+
? message.content
|
|
239
|
+
: typeof message.content?.text === "string"
|
|
240
|
+
? message.content.text
|
|
241
|
+
: "");
|
|
242
|
+
}
|
|
155
243
|
export function attachAvailableContexts(state, runtime) {
|
|
156
244
|
const availableContexts = deriveAvailableContexts(runtime.actions, runtime.providers);
|
|
157
245
|
return {
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import type { Memory } from "../types/memory";
|
|
2
|
+
export declare function extractUserText(raw: string): string;
|
|
3
|
+
export declare function getUserMessageText(message: Pick<Memory, "content"> | null | undefined): string;
|
|
4
|
+
export declare function normalizeUserMessageText(message: Pick<Memory, "content"> | null | undefined): string;
|
|
5
|
+
//# sourceMappingURL=message-text.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"message-text.d.ts","sourceRoot":"","sources":["../../../../../../typescript/src/utils/message-text.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,iBAAiB,CAAC;AAO9C,wBAAgB,eAAe,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CASnD;AAED,wBAAgB,kBAAkB,CACjC,OAAO,EAAE,IAAI,CAAC,MAAM,EAAE,SAAS,CAAC,GAAG,IAAI,GAAG,SAAS,GACjD,MAAM,CAQR;AAED,wBAAgB,wBAAwB,CACvC,OAAO,EAAE,IAAI,CAAC,MAAM,EAAE,SAAS,CAAC,GAAG,IAAI,GAAG,SAAS,GACjD,MAAM,CAER"}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
const KNOWLEDGE_AUGMENTATION_PREFIX = "Answer the user request using the contextual knowledge";
|
|
2
|
+
const USER_REQUEST_WRAPPER = /<user_request>\s*([\s\S]*?)\s*<\/user_request>/i;
|
|
3
|
+
const LANGUAGE_INSTRUCTION_SUFFIX = /\n*\[language instruction:[^\]]*\]\s*$/i;
|
|
4
|
+
export function extractUserText(raw) {
|
|
5
|
+
let text = raw;
|
|
6
|
+
if (text.trimStart().startsWith(KNOWLEDGE_AUGMENTATION_PREFIX)) {
|
|
7
|
+
const match = text.match(USER_REQUEST_WRAPPER);
|
|
8
|
+
if (match?.[1]) {
|
|
9
|
+
text = match[1];
|
|
10
|
+
}
|
|
11
|
+
}
|
|
12
|
+
return text.replace(LANGUAGE_INSTRUCTION_SUFFIX, "").trim();
|
|
13
|
+
}
|
|
14
|
+
export function getUserMessageText(message) {
|
|
15
|
+
const raw = typeof message?.content === "string"
|
|
16
|
+
? message.content
|
|
17
|
+
: typeof message?.content?.text === "string"
|
|
18
|
+
? message.content.text
|
|
19
|
+
: "";
|
|
20
|
+
return extractUserText(raw);
|
|
21
|
+
}
|
|
22
|
+
export function normalizeUserMessageText(message) {
|
|
23
|
+
return getUserMessageText(message).toLowerCase().replace(/\s+/g, " ").trim();
|
|
24
|
+
}
|
|
@@ -185,8 +185,9 @@ export declare function stringToUuid(target: string | number): UUID;
|
|
|
185
185
|
*/
|
|
186
186
|
export declare function prewarmUuidCache(values: string[]): Promise<void>;
|
|
187
187
|
export declare const getContentTypeFromMimeType: (mimeType: string) => ContentType | undefined;
|
|
188
|
-
export { AVAILABLE_CONTEXTS_STATE_KEY, attachAvailableContexts, CONTEXT_ROUTING_METADATA_KEY, CONTEXT_ROUTING_STATE_KEY, type ContextRoutingDecision, deriveAvailableContexts, getActiveRoutingContexts, getContextRoutingFromMessage, getContextRoutingFromState, mergeContextRouting, parseContextList, parseContextRoutingMetadata, setContextRoutingMetadata, shouldIncludeByContext, } from "./utils/context-routing";
|
|
188
|
+
export { AVAILABLE_CONTEXTS_STATE_KEY, attachAvailableContexts, CONTEXT_ROUTING_METADATA_KEY, CONTEXT_ROUTING_STATE_KEY, type ContextRoutingDecision, deriveAvailableContexts, getActiveRoutingContexts, getActiveRoutingContextsForTurn, getContextRoutingFromMessage, getContextRoutingFromState, inferContextRoutingFromMessage, inferContextRoutingFromText, mergeContextRouting, parseContextList, parseContextRoutingMetadata, setContextRoutingMetadata, shouldIncludeByContext, } from "./utils/context-routing";
|
|
189
189
|
export { extractAndParseJSONObjectFromText } from "./utils/json-llm";
|
|
190
|
+
export { extractUserText, getUserMessageText, normalizeUserMessageText, } from "./utils/message-text";
|
|
190
191
|
export { getLocalServerUrl } from "./utils/node";
|
|
191
192
|
export { extractFirstSentence, hasFirstSentence } from "./utils/text-splitting";
|
|
192
193
|
//# sourceMappingURL=utils.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../../../../typescript/src/utils.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../../../../typescript/src/utils.ts"],"names":[],"mappings":"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"}
|
|
@@ -1111,8 +1111,9 @@ export const getContentTypeFromMimeType = (mimeType) => {
|
|
|
1111
1111
|
}
|
|
1112
1112
|
return undefined;
|
|
1113
1113
|
};
|
|
1114
|
-
export { AVAILABLE_CONTEXTS_STATE_KEY, attachAvailableContexts, CONTEXT_ROUTING_METADATA_KEY, CONTEXT_ROUTING_STATE_KEY, deriveAvailableContexts, getActiveRoutingContexts, getContextRoutingFromMessage, getContextRoutingFromState, mergeContextRouting, parseContextList, parseContextRoutingMetadata, setContextRoutingMetadata, shouldIncludeByContext, } from "./utils/context-routing";
|
|
1114
|
+
export { AVAILABLE_CONTEXTS_STATE_KEY, attachAvailableContexts, CONTEXT_ROUTING_METADATA_KEY, CONTEXT_ROUTING_STATE_KEY, deriveAvailableContexts, getActiveRoutingContexts, getActiveRoutingContextsForTurn, getContextRoutingFromMessage, getContextRoutingFromState, inferContextRoutingFromMessage, inferContextRoutingFromText, mergeContextRouting, parseContextList, parseContextRoutingMetadata, setContextRoutingMetadata, shouldIncludeByContext, } from "./utils/context-routing";
|
|
1115
1115
|
export { extractAndParseJSONObjectFromText } from "./utils/json-llm";
|
|
1116
|
+
export { extractUserText, getUserMessageText, normalizeUserMessageText, } from "./utils/message-text";
|
|
1116
1117
|
// `export * from "./utils"` (in index.node.ts etc.) resolves to this file, not
|
|
1117
1118
|
// to a `./utils/index.ts`. Any helper in the `utils/` directory that needs to be
|
|
1118
1119
|
// reachable from `@elizaos/core` must be re-exported here.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"chat-composer.d.ts","sourceRoot":"","sources":["../../../../../../../src/components/composites/chat/chat-composer.tsx"],"names":[],"mappings":"AAYA,OAAO,EACL,KAAK,aAAa,EAElB,KAAK,SAAS,
|
|
1
|
+
{"version":3,"file":"chat-composer.d.ts","sourceRoot":"","sources":["../../../../../../../src/components/composites/chat/chat-composer.tsx"],"names":[],"mappings":"AAYA,OAAO,EACL,KAAK,aAAa,EAElB,KAAK,SAAS,EAKf,MAAM,OAAO,CAAC;AAIf,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,cAAc,CAAC;AAiEhD,MAAM,WAAW,sBAAsB;IACrC,mBAAmB,CAAC,EAAE,UAAU,GAAG,UAAU,CAAC;IAC9C,WAAW,EAAE,MAAM,GAAG,SAAS,GAAG,cAAc,CAAC;IACjD,iBAAiB,EAAE,MAAM,CAAC;IAC1B,WAAW,EAAE,OAAO,CAAC;IACrB,UAAU,EAAE,OAAO,CAAC;IACpB,cAAc,EAAE,CAAC,IAAI,CAAC,EAAE,SAAS,GAAG,cAAc,KAAK,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IAC5E,aAAa,EAAE,CAAC,OAAO,CAAC,EAAE;QAAE,MAAM,CAAC,EAAE,OAAO,CAAA;KAAE,KAAK,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IACxE,SAAS,EAAE,OAAO,CAAC;IACnB,eAAe,EAAE,MAAM,IAAI,CAAC;CAC7B;AAED,MAAM,WAAW,iBAAiB;IAChC,iBAAiB,EAAE,OAAO,CAAC;IAC3B,SAAS,EAAE,MAAM,CAAC;IAClB,sBAAsB,EAAE,MAAM,CAAC;IAC/B,WAAW,EAAE,OAAO,CAAC;IACrB,eAAe,EAAE,OAAO,CAAC;IACzB,gBAAgB,EAAE,OAAO,CAAC;IAC1B,MAAM,CAAC,EAAE,SAAS,GAAG,QAAQ,CAAC;IAC9B,aAAa,EAAE,MAAM,IAAI,CAAC;IAC1B,iBAAiB,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IAC3C,SAAS,EAAE,CAAC,KAAK,EAAE,aAAa,CAAC,mBAAmB,CAAC,KAAK,IAAI,CAAC;IAC/D,MAAM,EAAE,MAAM,IAAI,CAAC;IACnB,MAAM,EAAE,MAAM,IAAI,CAAC;IACnB,cAAc,EAAE,MAAM,IAAI,CAAC;IAC3B,kBAAkB,EAAE,MAAM,IAAI,CAAC;IAC/B,oBAAoB,CAAC,EAAE,OAAO,CAAC;IAC/B,CAAC,EAAE,CAAC,GAAG,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAAK,MAAM,CAAC;IAC9D,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B,WAAW,EAAE,SAAS,CAAC,mBAAmB,GAAG,IAAI,CAAC,CAAC;IACnD,OAAO,EAAE,WAAW,CAAC;IACrB,KAAK,EAAE,sBAAsB,CAAC;IAC9B,qBAAqB,CAAC,EAAE,OAAO,CAAC;IAChC,YAAY,CAAC,EAAE,CAAC,WAAW,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,KAAK,IAAI,CAAC;IAChE,uFAAuF;IACvF,gBAAgB,CAAC,EAAE,OAAO,CAAC;IAC3B,6CAA6C;IAC7C,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED,wBAAgB,YAAY,CAAC,EAC3B,OAAO,EACP,MAAkB,EAClB,WAAW,EACX,SAAS,EACT,sBAAsB,EACtB,gBAAgB,EAChB,eAAe,EACf,WAAW,EACX,KAAK,EACL,iBAAiB,EACjB,oBAA2B,EAC3B,CAAC,EACD,aAAa,EACb,iBAAiB,EACjB,SAAS,EACT,MAAM,EACN,MAAM,EACN,cAAc,EACd,kBAAkB,EAClB,qBAA6B,EAC7B,YAAY,EACZ,gBAAwB,EACxB,WAAW,EACX,iBAAiB,GAClB,EAAE,iBAAiB,2CAooBnB"}
|
|
@@ -1,12 +1,51 @@
|
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
2
|
import { ArrowUp, Mic, Paperclip, Plus, Send, Square, Volume2, VolumeX, } from "lucide-react";
|
|
3
|
-
import { useEffect, useRef, useState, } from "react";
|
|
3
|
+
import { useEffect, useLayoutEffect, useRef, useState, } from "react";
|
|
4
4
|
import { Button } from "../../ui/button";
|
|
5
5
|
import { Textarea } from "../../ui/textarea";
|
|
6
6
|
import { CreateTaskPopover } from "./create-task-popover";
|
|
7
|
+
const INLINE_TEXTAREA_MIN_HEIGHT_PX = 32;
|
|
8
|
+
const INLINE_TEXTAREA_MAX_HEIGHT_PX = 128;
|
|
9
|
+
const INLINE_STACKED_INLINE_PADDING_PX = 12;
|
|
10
|
+
const inlineTextareaClass = "block h-8 max-h-[128px] min-h-0 w-full min-w-0 resize-none overflow-y-hidden appearance-none rounded-none border-0 bg-transparent px-2 py-[6px] text-sm leading-5 text-txt shadow-none outline-none ring-0 placeholder:text-muted/60 focus:!border-0 focus:!outline-none focus:!ring-0 focus-visible:!border-0 focus-visible:!outline-none focus-visible:!ring-0 focus-visible:!ring-offset-0 focus-visible:!shadow-none";
|
|
11
|
+
const inlineMeasureTextareaClass = `${inlineTextareaClass} pointer-events-none fixed left-0 top-0 z-[-1] opacity-0`;
|
|
12
|
+
const chatComposerFocusResetClass = "[&_button:focus]:!outline-none [&_button:focus-visible]:!outline-none [&_button:focus-visible]:!ring-0 [&_button:focus-visible]:!ring-offset-0 [&_button:focus-visible]:!shadow-none [&_textarea:focus]:!outline-none [&_textarea:focus-visible]:!outline-none [&_textarea:focus-visible]:!ring-0 [&_textarea:focus-visible]:!ring-offset-0 [&_textarea:focus-visible]:!shadow-none";
|
|
13
|
+
function getTextareaVerticalPadding(textarea) {
|
|
14
|
+
const styles = window.getComputedStyle(textarea);
|
|
15
|
+
const paddingTop = Number.parseFloat(styles.paddingTop);
|
|
16
|
+
const paddingBottom = Number.parseFloat(styles.paddingBottom);
|
|
17
|
+
const verticalPadding = paddingTop + paddingBottom;
|
|
18
|
+
if (Number.isFinite(paddingTop) &&
|
|
19
|
+
Number.isFinite(paddingBottom) &&
|
|
20
|
+
verticalPadding > 0) {
|
|
21
|
+
return verticalPadding;
|
|
22
|
+
}
|
|
23
|
+
return 12;
|
|
24
|
+
}
|
|
25
|
+
function getTextareaLineHeight(textarea) {
|
|
26
|
+
const lineHeight = Number.parseFloat(window.getComputedStyle(textarea).lineHeight);
|
|
27
|
+
return Number.isFinite(lineHeight) && lineHeight > 0 ? lineHeight : 20;
|
|
28
|
+
}
|
|
29
|
+
function measureInlineTextarea(textarea, value, width) {
|
|
30
|
+
textarea.value = value.endsWith("\n") ? `${value} ` : value || " ";
|
|
31
|
+
textarea.style.width = `${Math.max(1, width)}px`;
|
|
32
|
+
textarea.style.height = "auto";
|
|
33
|
+
textarea.style.overflowY = "hidden";
|
|
34
|
+
const scrollHeight = textarea.scrollHeight;
|
|
35
|
+
const contentHeight = Math.max(0, scrollHeight - getTextareaVerticalPadding(textarea));
|
|
36
|
+
const lineHeight = getTextareaLineHeight(textarea);
|
|
37
|
+
return {
|
|
38
|
+
scrollHeight,
|
|
39
|
+
wraps: contentHeight > lineHeight * 1.25,
|
|
40
|
+
};
|
|
41
|
+
}
|
|
7
42
|
export function ChatComposer({ variant, layout = "default", textareaRef, chatInput, chatPendingImagesCount, isComposerLocked, isAgentStarting, chatSending, voice, agentVoiceEnabled, showAgentVoiceToggle = true, t, onAttachImage, onChatInputChange, onKeyDown, onSend, onStop, onStopSpeaking, onToggleAgentVoice, codingAgentsAvailable = false, onCreateTask, hideAttachButton = false, placeholder, textareaAriaLabel, }) {
|
|
8
43
|
const [isNarrow, setIsNarrow] = useState(() => typeof window !== "undefined" && window.innerWidth < 310);
|
|
9
44
|
const [isInlineMultiline, setIsInlineMultiline] = useState(false);
|
|
45
|
+
const [inlineMeasureVersion, setInlineMeasureVersion] = useState(0);
|
|
46
|
+
const inlineRootRef = useRef(null);
|
|
47
|
+
const inlineMeasureRef = useRef(null);
|
|
48
|
+
const lastInlineSingleLineWidthRef = useRef(null);
|
|
10
49
|
useEffect(() => {
|
|
11
50
|
if (typeof window === "undefined" || !window.matchMedia)
|
|
12
51
|
return;
|
|
@@ -53,9 +92,6 @@ export function ChatComposer({ variant, layout = "default", textareaRef, chatInp
|
|
|
53
92
|
? t("chat.listening")
|
|
54
93
|
: inputPlaceholder
|
|
55
94
|
: inputPlaceholder;
|
|
56
|
-
const inlineTextareaClass = isInlineMultiline
|
|
57
|
-
? "block h-8 max-h-[128px] min-h-0 w-full min-w-0 resize-none overflow-y-hidden appearance-none rounded-none border-0 bg-transparent px-2 py-[6px] text-sm leading-5 text-txt shadow-none outline-none ring-0 placeholder:text-muted/60 focus:border-0 focus:outline-none focus:ring-0 focus-visible:border-0 focus-visible:outline-none focus-visible:ring-0 focus-visible:ring-offset-0 focus-visible:shadow-none"
|
|
58
|
-
: "block h-8 max-h-[128px] min-h-0 w-full min-w-0 resize-none overflow-y-hidden appearance-none rounded-none border-0 bg-transparent px-1 py-[5px] text-sm leading-5 text-txt shadow-none outline-none ring-0 placeholder:text-muted/60 focus:border-0 focus:outline-none focus:ring-0 focus-visible:border-0 focus-visible:outline-none focus-visible:ring-0 focus-visible:ring-offset-0 focus-visible:shadow-none";
|
|
59
95
|
useEffect(() => {
|
|
60
96
|
return () => {
|
|
61
97
|
if (holdTimerRef.current) {
|
|
@@ -64,24 +100,70 @@ export function ChatComposer({ variant, layout = "default", textareaRef, chatInp
|
|
|
64
100
|
}
|
|
65
101
|
};
|
|
66
102
|
}, []);
|
|
67
|
-
// biome-ignore lint/correctness/useExhaustiveDependencies: chatInput changes must rerun inline textarea autosizing.
|
|
68
103
|
useEffect(() => {
|
|
104
|
+
if (!isInline)
|
|
105
|
+
return;
|
|
106
|
+
const root = inlineRootRef.current;
|
|
107
|
+
if (!root || typeof ResizeObserver === "undefined")
|
|
108
|
+
return;
|
|
109
|
+
let frame = 0;
|
|
110
|
+
const observer = new ResizeObserver(() => {
|
|
111
|
+
if (frame)
|
|
112
|
+
cancelAnimationFrame(frame);
|
|
113
|
+
frame = requestAnimationFrame(() => {
|
|
114
|
+
setInlineMeasureVersion((version) => version + 1);
|
|
115
|
+
});
|
|
116
|
+
});
|
|
117
|
+
observer.observe(root);
|
|
118
|
+
return () => {
|
|
119
|
+
if (frame)
|
|
120
|
+
cancelAnimationFrame(frame);
|
|
121
|
+
observer.disconnect();
|
|
122
|
+
};
|
|
123
|
+
}, [isInline]);
|
|
124
|
+
// biome-ignore lint/correctness/useExhaustiveDependencies: inlineMeasureVersion is a ResizeObserver tick that reruns measurement after width changes.
|
|
125
|
+
useLayoutEffect(() => {
|
|
69
126
|
if (!isInline) {
|
|
70
127
|
setIsInlineMultiline(false);
|
|
128
|
+
lastInlineSingleLineWidthRef.current = null;
|
|
71
129
|
return;
|
|
72
130
|
}
|
|
73
131
|
const textarea = textareaRef.current;
|
|
74
|
-
|
|
132
|
+
const measureTextarea = inlineMeasureRef.current;
|
|
133
|
+
const root = inlineRootRef.current;
|
|
134
|
+
if (!textarea || !measureTextarea || !root)
|
|
75
135
|
return;
|
|
76
|
-
const
|
|
77
|
-
const
|
|
78
|
-
|
|
79
|
-
|
|
136
|
+
const measuredSingleLineWidth = textarea.clientWidth > 0 ? textarea.clientWidth : null;
|
|
137
|
+
const currentSingleLineWidth = isInlineMultiline
|
|
138
|
+
? lastInlineSingleLineWidthRef.current
|
|
139
|
+
: measuredSingleLineWidth;
|
|
140
|
+
if (!isInlineMultiline && measuredSingleLineWidth) {
|
|
141
|
+
lastInlineSingleLineWidthRef.current = measuredSingleLineWidth;
|
|
142
|
+
}
|
|
143
|
+
const decisionWidth = currentSingleLineWidth ??
|
|
144
|
+
Math.max(1, root.clientWidth - INLINE_STACKED_INLINE_PADDING_PX);
|
|
145
|
+
const stackedWidth = Math.max(1, root.clientWidth - INLINE_STACKED_INLINE_PADDING_PX);
|
|
146
|
+
const decision = measureInlineTextarea(measureTextarea, chatInput, decisionWidth);
|
|
147
|
+
const nextIsInlineMultiline = chatInput.includes("\n") || decision.wraps;
|
|
148
|
+
const heightMeasurement = nextIsInlineMultiline
|
|
149
|
+
? measureInlineTextarea(measureTextarea, chatInput, stackedWidth)
|
|
150
|
+
: decision;
|
|
151
|
+
const nextHeight = nextIsInlineMultiline
|
|
152
|
+
? Math.min(Math.max(heightMeasurement.scrollHeight, INLINE_TEXTAREA_MIN_HEIGHT_PX), INLINE_TEXTAREA_MAX_HEIGHT_PX)
|
|
153
|
+
: INLINE_TEXTAREA_MIN_HEIGHT_PX;
|
|
80
154
|
textarea.style.height = `${nextHeight}px`;
|
|
81
155
|
textarea.style.overflowY =
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
156
|
+
heightMeasurement.scrollHeight > INLINE_TEXTAREA_MAX_HEIGHT_PX
|
|
157
|
+
? "auto"
|
|
158
|
+
: "hidden";
|
|
159
|
+
setIsInlineMultiline(nextIsInlineMultiline);
|
|
160
|
+
}, [
|
|
161
|
+
chatInput,
|
|
162
|
+
inlineMeasureVersion,
|
|
163
|
+
isInline,
|
|
164
|
+
isInlineMultiline,
|
|
165
|
+
textareaRef,
|
|
166
|
+
]);
|
|
85
167
|
const startPushToTalk = () => {
|
|
86
168
|
if (isComposerLocked || voice.isListening)
|
|
87
169
|
return;
|
|
@@ -161,13 +243,13 @@ export function ChatComposer({ variant, layout = "default", textareaRef, chatInp
|
|
|
161
243
|
const inlineStopButton = (_jsx(Button, { variant: "surfaceDestructive", "data-testid": "chat-composer-action", className: "h-8 w-8 shrink-0 rounded-full bg-danger/15 p-0 text-danger shadow-none transition-colors hover:bg-danger/25 focus-visible:ring-0 focus-visible:ring-offset-0", onClick: onStop, size: "icon", title: actionButtonLabel, "aria-label": actionButtonLabel, children: _jsx(Square, { className: "h-3.5 w-3.5 fill-current" }) }));
|
|
162
244
|
const inlineStopSpeakingButton = (_jsx(Button, { variant: "surfaceDestructive", "data-testid": "chat-composer-action", className: "h-8 w-8 shrink-0 rounded-full bg-danger/15 p-0 text-danger shadow-none transition-colors hover:bg-danger/25 focus-visible:ring-0 focus-visible:ring-offset-0", onClick: onStopSpeaking, size: "icon", title: actionButtonLabel, "aria-label": actionButtonLabel, children: _jsx(Square, { className: "h-3.5 w-3.5 fill-current" }) }));
|
|
163
245
|
const inlineTrailingActions = shouldShowStopButton ? (inlineStopButton) : !isGameModal && voice.isSpeaking && !hasDraft ? (inlineStopSpeakingButton) : isInlineMultiline ? (_jsxs(_Fragment, { children: [inlineMicButton, inlineSendButton] })) : hasDraft ? (inlineSendButton) : (inlineMicButton);
|
|
164
|
-
return (
|
|
165
|
-
?
|
|
166
|
-
:
|
|
246
|
+
return (_jsxs("div", { ref: inlineRootRef, "data-chat-composer": "true", "data-inline-layout": isInlineMultiline ? "stacked" : "single-line", className: isInlineMultiline
|
|
247
|
+
? `flex min-h-[64px] flex-col gap-1 rounded-[22px] border border-border/35 bg-card/45 px-1.5 py-1.5 ${chatComposerFocusResetClass}`
|
|
248
|
+
: `flex min-h-[40px] items-center gap-1 rounded-full border border-border/35 bg-card/45 px-1 py-1 ${chatComposerFocusResetClass}`, children: [_jsx("textarea", { ref: inlineMeasureRef, "aria-hidden": "true", className: inlineMeasureTextareaClass, "data-chat-composer-measure": "true", readOnly: true, rows: 1, tabIndex: -1, value: chatInput }), isInlineMultiline ? (_jsxs(_Fragment, { children: [inlineTextarea, _jsxs("div", { className: "flex min-w-0 items-center gap-1", children: [inlineAttachButton, renderCreateTaskButton(), _jsx("div", { className: "min-w-0 flex-1" }), inlineTrailingActions] })] })) : (_jsxs(_Fragment, { children: [inlineAttachButton, renderCreateTaskButton(), inlineTextarea, inlineTrailingActions] }))] }));
|
|
167
249
|
}
|
|
168
|
-
return (_jsxs("div", { className: isGameModal
|
|
169
|
-
?
|
|
170
|
-
:
|
|
250
|
+
return (_jsxs("div", { "data-chat-composer": "true", className: isGameModal
|
|
251
|
+
? `relative flex w-full items-end gap-2 transition-all max-[380px]:gap-1.5 ${chatComposerFocusResetClass}`
|
|
252
|
+
: `flex items-center gap-1.5 sm:gap-2 ${chatComposerFocusResetClass}`, children: [!isGameModal && !hideAttachButton ? (_jsx(Button, { variant: "ghost", size: "icon", className: isInline
|
|
171
253
|
? `h-8 w-8 shrink-0 rounded-full bg-bg/60 p-0 text-muted shadow-none transition-colors hover:bg-bg/60 hover:text-txt focus-visible:ring-0 focus-visible:ring-offset-0 ${chatPendingImagesCount > 0
|
|
172
254
|
? "text-accent hover:text-accent"
|
|
173
255
|
: ""}`
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"page-layout-mobile-drawer.d.ts","sourceRoot":"","sources":["../../../../../../src/layouts/page-layout/page-layout-mobile-drawer.tsx"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"page-layout-mobile-drawer.d.ts","sourceRoot":"","sources":["../../../../../../src/layouts/page-layout/page-layout-mobile-drawer.tsx"],"names":[],"mappings":"AAMA,OAAO,KAAK,EAAE,2BAA2B,EAAE,MAAM,qBAAqB,CAAC;AAEvE,wBAAgB,sBAAsB,CAAC,EACrC,SAAS,EACT,kBAAkB,EAClB,iBAAiB,EACjB,6BAA6B,EAC7B,yBAAyB,EACzB,OAAO,GACR,EAAE,2BAA2B,kDAsE7B"}
|
|
@@ -2,11 +2,11 @@ import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-run
|
|
|
2
2
|
import { PanelLeftOpen } from "lucide-react";
|
|
3
3
|
import * as React from "react";
|
|
4
4
|
import { Button } from "../../components/ui/button";
|
|
5
|
-
import { DrawerSheet, DrawerSheetContent, DrawerSheetHeader, DrawerSheetTitle, } from "../../components/ui/drawer-sheet";
|
|
6
5
|
import { cn } from "../../lib/utils";
|
|
6
|
+
import { useWorkspaceMobileSidebarControls } from "../workspace-layout/workspace-mobile-sidebar-controls";
|
|
7
7
|
export function PageLayoutMobileDrawer({ isDesktop, mobileSidebarLabel, mobileSidebarOpen, mobileSidebarTriggerClassName, onMobileSidebarOpenChange, sidebar, }) {
|
|
8
|
-
|
|
9
|
-
|
|
8
|
+
const controls = useWorkspaceMobileSidebarControls();
|
|
9
|
+
const sidebarId = React.useId();
|
|
10
10
|
const mobileSidebarElement = React.cloneElement(sidebar, {
|
|
11
11
|
className: cn("!mt-0 !h-full !w-full !min-w-0", sidebar.props.className),
|
|
12
12
|
collapsible: false,
|
|
@@ -14,5 +14,24 @@ export function PageLayoutMobileDrawer({ isDesktop, mobileSidebarLabel, mobileSi
|
|
|
14
14
|
onMobileClose: () => onMobileSidebarOpenChange(false),
|
|
15
15
|
});
|
|
16
16
|
const drawerLabel = sidebar.props.mobileTitle ?? mobileSidebarLabel ?? "Browse";
|
|
17
|
-
|
|
17
|
+
React.useEffect(() => {
|
|
18
|
+
if (!controls || isDesktop)
|
|
19
|
+
return undefined;
|
|
20
|
+
return controls.register({
|
|
21
|
+
id: sidebarId,
|
|
22
|
+
label: drawerLabel,
|
|
23
|
+
open: mobileSidebarOpen,
|
|
24
|
+
setOpen: onMobileSidebarOpenChange,
|
|
25
|
+
});
|
|
26
|
+
}, [
|
|
27
|
+
controls,
|
|
28
|
+
drawerLabel,
|
|
29
|
+
isDesktop,
|
|
30
|
+
mobileSidebarOpen,
|
|
31
|
+
onMobileSidebarOpenChange,
|
|
32
|
+
sidebarId,
|
|
33
|
+
]);
|
|
34
|
+
if (isDesktop)
|
|
35
|
+
return null;
|
|
36
|
+
return (_jsxs(_Fragment, { children: [!mobileSidebarOpen && !controls ? (_jsx("div", { className: "pointer-events-none fixed left-2 z-40 md:hidden", style: { top: "calc(var(--safe-area-top, 0px) + 2.75rem)" }, children: _jsx("div", { className: "pointer-events-auto", children: _jsxs(Button, { type: "button", variant: "outline", size: "sm", className: cn("h-[2.375rem] max-w-[min(11rem,calc(100vw-5.5rem))] rounded-full border-border/40 bg-card/92 px-3 text-sm font-semibold text-txt shadow-sm backdrop-blur-md", mobileSidebarTriggerClassName), "data-testid": "page-layout-mobile-sidebar-trigger", onClick: () => onMobileSidebarOpenChange(true), children: [_jsx(PanelLeftOpen, { className: "h-4 w-4 shrink-0" }), _jsx("span", { className: "truncate", children: drawerLabel })] }) }) })) : null, mobileSidebarOpen ? (_jsx("section", { className: "flex min-h-0 w-full flex-1 overflow-hidden", "data-testid": "page-layout-mobile-sidebar-drawer", "aria-label": typeof drawerLabel === "string" ? drawerLabel : undefined, children: mobileSidebarElement })) : null] }));
|
|
18
37
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../../../src/layouts/workspace-layout/index.ts"],"names":[],"mappings":"AAAA,cAAc,oBAAoB,CAAC;AACnC,cAAc,0BAA0B,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../../../src/layouts/workspace-layout/index.ts"],"names":[],"mappings":"AAAA,cAAc,oBAAoB,CAAC;AACnC,cAAc,0BAA0B,CAAC;AACzC,cAAc,qCAAqC,CAAC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"workspace-layout.d.ts","sourceRoot":"","sources":["../../../../../../src/layouts/workspace-layout/workspace-layout.tsx"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,0BAA0B,CAAC;AAiDrE,wBAAgB,eAAe,CAAC,EAC9B,QAAQ,EACR,SAAS,EACT,gBAAgB,EAChB,aAAa,EACb,sBAAsB,EACtB,qBAAqB,EACrB,cAAqB,EACrB,UAAU,EACV,MAAM,EACN,eAAe,EACf,eAA2B,EAC3B,kBAAkB,EAClB,6BAA6B,EAC7B,OAAO,EACP,kBAAyB,EACzB,GAAG,KAAK,EACT,EAAE,oBAAoB,
|
|
1
|
+
{"version":3,"file":"workspace-layout.d.ts","sourceRoot":"","sources":["../../../../../../src/layouts/workspace-layout/workspace-layout.tsx"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,0BAA0B,CAAC;AAiDrE,wBAAgB,eAAe,CAAC,EAC9B,QAAQ,EACR,SAAS,EACT,gBAAgB,EAChB,aAAa,EACb,sBAAsB,EACtB,qBAAqB,EACrB,cAAqB,EACrB,UAAU,EACV,MAAM,EACN,eAAe,EACf,eAA2B,EAC3B,kBAAkB,EAClB,6BAA6B,EAC7B,OAAO,EACP,kBAAyB,EACzB,GAAG,KAAK,EACT,EAAE,oBAAoB,2CAwGtB"}
|
|
@@ -41,6 +41,7 @@ function useWorkspaceLayoutDesktopMode() {
|
|
|
41
41
|
export function WorkspaceLayout({ children, className, contentClassName, contentHeader, contentHeaderClassName, contentInnerClassName, contentPadding = true, contentRef, footer, footerClassName, headerPlacement = "outside", mobileSidebarLabel, mobileSidebarTriggerClassName, sidebar, sidebarCollapsible = true, ...props }) {
|
|
42
42
|
const isDesktop = useWorkspaceLayoutDesktopMode();
|
|
43
43
|
const [mobileSidebarOpen, setMobileSidebarOpen] = React.useState(false);
|
|
44
|
+
const showMobileSidebarPane = Boolean(sidebar && !isDesktop && mobileSidebarOpen);
|
|
44
45
|
React.useEffect(() => {
|
|
45
46
|
if (isDesktop) {
|
|
46
47
|
setMobileSidebarOpen(false);
|
|
@@ -54,6 +55,11 @@ export function WorkspaceLayout({ children, className, contentClassName, content
|
|
|
54
55
|
})
|
|
55
56
|
: null;
|
|
56
57
|
const headerElement = contentHeader ? (_jsx(PageLayoutHeader, { className: contentHeaderClassName, children: contentHeader })) : null;
|
|
57
|
-
return (_jsxs("div", { className: cn("flex w-full min-h-0 min-w-0 flex-1 flex-col overflow-hidden", className), ...props, children: [contentHeader && headerPlacement === "outside" ? (_jsx("div", { className: cn("shrink-0", contentPadding && "px-4 pt-2 sm:px-6 sm:pt-3 lg:px-7 lg:pt-4"), children: headerElement })) : null, _jsxs("div", { className: cn("flex w-full min-h-0 min-w-0 flex-1 flex-col", sidebar && "md:flex-row"), children: [desktopSidebarElement ? (_jsx("div", { className: cn("hidden min-h-0 w-full shrink-0 items-stretch px-0 pb-0 md:flex md:w-auto", contentPadding && "pt-2 sm:pt-3 lg:pt-4"), children: desktopSidebarElement })) : null, _jsxs("main", { ref: (node) => assignRef(contentRef, node), className: cn("chat-native-scrollbar relative flex min-w-0 flex-1 flex-col overflow-y-auto
|
|
58
|
-
|
|
58
|
+
return (_jsxs("div", { className: cn("flex w-full min-h-0 min-w-0 flex-1 flex-col overflow-hidden", className), ...props, children: [contentHeader && headerPlacement === "outside" ? (_jsx("div", { className: cn("shrink-0", contentPadding && "px-4 pt-2 sm:px-6 sm:pt-3 lg:px-7 lg:pt-4"), children: headerElement })) : null, _jsxs("div", { className: cn("flex w-full min-h-0 min-w-0 flex-1 flex-col", sidebar && "md:flex-row"), children: [desktopSidebarElement ? (_jsx("div", { className: cn("hidden min-h-0 w-full shrink-0 items-stretch px-0 pb-0 md:flex md:w-auto", contentPadding && "pt-2 sm:pt-3 lg:pt-4"), children: desktopSidebarElement })) : null, _jsxs("main", { ref: (node) => assignRef(contentRef, node), className: cn("chat-native-scrollbar relative flex min-w-0 flex-1 flex-col bg-transparent", showMobileSidebarPane ? "overflow-hidden" : "overflow-y-auto", contentPadding &&
|
|
59
|
+
!showMobileSidebarPane &&
|
|
60
|
+
"px-4 pb-4 pt-2 sm:px-6 sm:pb-6 sm:pt-3 lg:px-7 lg:pb-7 lg:pt-4", !showMobileSidebarPane && contentClassName), children: [sidebar ? (_jsx(PageLayoutMobileDrawer, { isDesktop: isDesktop, mobileSidebarLabel: mobileSidebarLabel, mobileSidebarOpen: mobileSidebarOpen, mobileSidebarTriggerClassName: mobileSidebarTriggerClassName, onMobileSidebarOpenChange: setMobileSidebarOpen, sidebar: sidebar })) : null, contentHeader &&
|
|
61
|
+
headerPlacement === "inside" &&
|
|
62
|
+
!showMobileSidebarPane
|
|
63
|
+
? headerElement
|
|
64
|
+
: null, _jsx("div", { className: cn("flex w-full min-h-0 flex-1 flex-col", contentInnerClassName, showMobileSidebarPane && "hidden"), children: children })] })] })] }));
|
|
59
65
|
}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import * as React from "react";
|
|
2
|
+
export interface WorkspaceMobileSidebarControl {
|
|
3
|
+
id: string;
|
|
4
|
+
label?: React.ReactNode;
|
|
5
|
+
open: boolean;
|
|
6
|
+
setOpen: (open: boolean) => void;
|
|
7
|
+
}
|
|
8
|
+
export interface WorkspaceMobileSidebarControls {
|
|
9
|
+
register: (control: WorkspaceMobileSidebarControl) => () => void;
|
|
10
|
+
}
|
|
11
|
+
export declare const WorkspaceMobileSidebarControlsContext: React.Context<WorkspaceMobileSidebarControls | null>;
|
|
12
|
+
export declare function useWorkspaceMobileSidebarControls(): WorkspaceMobileSidebarControls | null;
|
|
13
|
+
//# sourceMappingURL=workspace-mobile-sidebar-controls.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"workspace-mobile-sidebar-controls.d.ts","sourceRoot":"","sources":["../../../../../../src/layouts/workspace-layout/workspace-mobile-sidebar-controls.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAE/B,MAAM,WAAW,6BAA6B;IAC5C,EAAE,EAAE,MAAM,CAAC;IACX,KAAK,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC;IACxB,IAAI,EAAE,OAAO,CAAC;IACd,OAAO,EAAE,CAAC,IAAI,EAAE,OAAO,KAAK,IAAI,CAAC;CAClC;AAED,MAAM,WAAW,8BAA8B;IAC7C,QAAQ,EAAE,CAAC,OAAO,EAAE,6BAA6B,KAAK,MAAM,IAAI,CAAC;CAClE;AAED,eAAO,MAAM,qCAAqC,sDACgB,CAAC;AAEnE,wBAAgB,iCAAiC,IAAI,8BAA8B,GAAG,IAAI,CAEzF"}
|