better pill handling

This commit is contained in:
Nate Kelley 2025-01-28 12:55:53 -07:00
parent b850a85199
commit e653d3953b
No known key found for this signature in database
GPG Key ID: FD90372AB8D98B4F
3 changed files with 17 additions and 22 deletions

View File

@ -38,6 +38,11 @@ const pillVariants = {
} }
}; };
const pillPadding = 8; // 4px left + 4px right
const pillMargin = 6; // 1.5 * 4 for gap
const pillBorder = 1; // 0.5px * 2
const font = '11px -apple-system, BlinkMacSystemFont, sans-serif'; // Match your app's font
export const PillContainer: React.FC<{ export const PillContainer: React.FC<{
pills: BusterChatMessage_thought['thought_pills']; pills: BusterChatMessage_thought['thought_pills'];
isCompletedStream: boolean; isCompletedStream: boolean;
@ -49,10 +54,9 @@ export const PillContainer: React.FC<{
const [hasDoneInitialAnimation, setHasDoneInitialAnimation] = useState(false); const [hasDoneInitialAnimation, setHasDoneInitialAnimation] = useState(false);
const containerRef = useRef<HTMLDivElement>(null); const containerRef = useRef<HTMLDivElement>(null);
const useAnimation = !hasDoneInitialAnimation && !isCompletedStream; const useAnimation = !hasDoneInitialAnimation && !isCompletedStream;
const chatContentWidth = useChatLayoutContextSelector((x) => x.chatContentWidth);
const size = useSize(containerRef); const size = useSize(containerRef);
const thoughtContainerWidth = size?.width || chatContentWidth - 85; const thoughtContainerWidth = size?.width;
const debouncedWidth = useDebounce(thoughtContainerWidth, { const debouncedWidth = useDebounce(thoughtContainerWidth, {
wait: 150, wait: 150,
leading: true leading: true
@ -68,23 +72,19 @@ export const PillContainer: React.FC<{
} }
); );
useLayoutEffect(() => { const moreTextWidth = useMemo(() => {
if (!pills) return; return calculateTextWidth('+99 more', font) + pillPadding + pillBorder;
}, [font]);
const containerWidth = containerRef.current?.offsetWidth || thoughtContainerWidth; useLayoutEffect(() => {
console.log(containerWidth, thoughtContainerWidth, chatContentWidth); if (!pills || !containerRef.current) return;
const pillPadding = 8; // 4px left + 4px right
const pillMargin = 6; // 1.5 * 4 for gap const containerWidth = thoughtContainerWidth || 240;
const pillBorder = 1; // 0.5px * 2
const font = '11px -apple-system, BlinkMacSystemFont, sans-serif'; // Match your app's font
let currentLineWidth = 0; let currentLineWidth = 0;
const visible: BusterChatMessage_thoughtPill[] = []; const visible: BusterChatMessage_thoughtPill[] = [];
let hidden = 0; let hidden = 0;
// Calculate width needed for "+X more" pill
const moreTextWidth = calculateTextWidth('+99 more', font) + pillPadding + pillBorder;
for (let i = 0; i < pills.length; i++) { for (let i = 0; i < pills.length; i++) {
const pill = pills[i]; const pill = pills[i];
const textWidth = calculateTextWidth(pill.text, font); const textWidth = calculateTextWidth(pill.text, font);
@ -117,9 +117,7 @@ export const PillContainer: React.FC<{
variants={containerVariants} variants={containerVariants}
initial="hidden" initial="hidden"
animate={pills.length > 0 ? 'visible' : 'hidden'} animate={pills.length > 0 ? 'visible' : 'hidden'}
className={cx( className={cx('flex w-full flex-wrap flex-nowrap gap-1.5 overflow-hidden')}>
'flex w-full flex-wrap flex-nowrap gap-1.5 overflow-hidden border border-red-500'
)}>
{visiblePills.map((pill) => ( {visiblePills.map((pill) => (
<Pill key={pill.id} useAnimation={useAnimation} {...pill} onClick={undefined} /> <Pill key={pill.id} useAnimation={useAnimation} {...pill} onClick={undefined} />
))} ))}

View File

@ -30,10 +30,8 @@ export const useChatLayout = ({
}: UseChatSplitterProps) => { }: UseChatSplitterProps) => {
const [isPending, startTransition] = useTransition(); const [isPending, startTransition] = useTransition();
const onChangePage = useAppLayoutContextSelector((state) => state.onChangePage); const onChangePage = useAppLayoutContextSelector((state) => state.onChangePage);
const chatContentSize = useSize(chatContentRef);
const selectedLayout = defaultSelectedLayout;
const chatContentWidth = chatContentSize?.width || 325; const selectedLayout = defaultSelectedLayout;
const animateOpenSplitter = useMemoizedFn((side: 'left' | 'right' | 'both') => { const animateOpenSplitter = useMemoizedFn((side: 'left' | 'right' | 'both') => {
if (appSplitterRef.current) { if (appSplitterRef.current) {
@ -84,7 +82,6 @@ export const useChatLayout = ({
selectedLayout, selectedLayout,
isPureFile, isPureFile,
isPureChat, isPureChat,
chatContentWidth,
onSetSelectedFile, onSetSelectedFile,
onCollapseFileClick, onCollapseFileClick,
animateOpenSplitter animateOpenSplitter

View File

@ -71,8 +71,8 @@ export const MOCK_CHAT: BusterChat = {
response_messages: [ response_messages: [
createMockResponseMessageText(), createMockResponseMessageText(),
createMockResponseMessageThought(), createMockResponseMessageThought(),
createMockResponseMessageThought(), // createMockResponseMessageThought(),
createMockResponseMessageThought(), // createMockResponseMessageThought(),
// createMockResponseMessageThought(), // createMockResponseMessageThought(),
createMockResponseMessageFile(), createMockResponseMessageFile(),
createMockResponseMessageFile() createMockResponseMessageFile()