Focus input on submission and fix scroll (#441)
This commit is contained in:
parent
23660c5ad1
commit
2705d83d6c
5 changed files with 61 additions and 8 deletions
|
|
@ -40,15 +40,16 @@ export function Chat({
|
|||
>
|
||||
{messages.length === 0 && <Overview />}
|
||||
|
||||
{messages.map((message, index) => (
|
||||
{messages.map((message) => (
|
||||
<PreviewMessage
|
||||
key={`${id}-${index}`}
|
||||
key={message.id}
|
||||
role={message.role}
|
||||
content={message.content}
|
||||
attachments={message.experimental_attachments}
|
||||
toolInvocations={message.toolInvocations}
|
||||
/>
|
||||
))}
|
||||
|
||||
<div
|
||||
ref={messagesEndRef}
|
||||
className="shrink-0 min-w-[24px] min-h-[24px]"
|
||||
|
|
|
|||
|
|
@ -15,6 +15,7 @@ import { toast } from "sonner";
|
|||
|
||||
import { ArrowUpIcon, PaperclipIcon, StopIcon } from "./icons";
|
||||
import { PreviewAttachment } from "./preview-attachment";
|
||||
import useWindowSize from "./use-window-size";
|
||||
import { Button } from "../ui/button";
|
||||
import { Textarea } from "../ui/textarea";
|
||||
|
||||
|
|
@ -22,7 +23,7 @@ const suggestedActions = [
|
|||
{
|
||||
title: "What is the weather",
|
||||
label: "in San Francisco?",
|
||||
action: "what is the weather in San Francisco?",
|
||||
action: "What is the weather in San Francisco?",
|
||||
},
|
||||
{
|
||||
title: "Answer like I'm 5,",
|
||||
|
|
@ -61,6 +62,7 @@ export function MultimodalInput({
|
|||
) => void;
|
||||
}) {
|
||||
const textareaRef = useRef<HTMLTextAreaElement>(null);
|
||||
const { width } = useWindowSize();
|
||||
|
||||
useEffect(() => {
|
||||
if (textareaRef.current) {
|
||||
|
|
@ -89,7 +91,11 @@ export function MultimodalInput({
|
|||
});
|
||||
|
||||
setAttachments([]);
|
||||
}, [attachments, handleSubmit, setAttachments]);
|
||||
|
||||
if (width && width > 768) {
|
||||
textareaRef.current?.focus();
|
||||
}
|
||||
}, [attachments, handleSubmit, setAttachments, width]);
|
||||
|
||||
const uploadFile = async (file: File) => {
|
||||
const formData = new FormData();
|
||||
|
|
@ -242,7 +248,8 @@ export function MultimodalInput({
|
|||
<Button
|
||||
className="rounded-full p-1.5 h-fit absolute bottom-2 right-2 m-0.5"
|
||||
onClick={(event) => {
|
||||
handleSubmit(event);
|
||||
event.preventDefault();
|
||||
submitForm();
|
||||
}}
|
||||
disabled={input.length === 0 || uploadQueue.length > 0}
|
||||
>
|
||||
|
|
|
|||
|
|
@ -19,6 +19,8 @@ export function useScrollToBottom<T extends HTMLElement>(): [
|
|||
observer.observe(container, {
|
||||
childList: true,
|
||||
subtree: true,
|
||||
attributes: true,
|
||||
characterData: true,
|
||||
});
|
||||
|
||||
return () => observer.disconnect();
|
||||
|
|
|
|||
39
components/custom/use-window-size.tsx
Normal file
39
components/custom/use-window-size.tsx
Normal file
|
|
@ -0,0 +1,39 @@
|
|||
"use client";
|
||||
|
||||
import { useState, useEffect } from "react";
|
||||
|
||||
interface WindowSize {
|
||||
width: number | undefined;
|
||||
height: number | undefined;
|
||||
}
|
||||
|
||||
function useWindowSize(): WindowSize {
|
||||
const [windowSize, setWindowSize] = useState<WindowSize>({
|
||||
width: undefined,
|
||||
height: undefined,
|
||||
});
|
||||
|
||||
useEffect(() => {
|
||||
// Handler to call on window resize
|
||||
function handleResize() {
|
||||
// Set window width/height to state
|
||||
setWindowSize({
|
||||
width: window.innerWidth,
|
||||
height: window.innerHeight,
|
||||
});
|
||||
}
|
||||
|
||||
// Add event listener
|
||||
window.addEventListener("resize", handleResize);
|
||||
|
||||
// Call handler right away so state gets updated with initial window size
|
||||
handleResize();
|
||||
|
||||
// Remove event listener on cleanup
|
||||
return () => window.removeEventListener("resize", handleResize);
|
||||
}, []); // Empty array ensures that effect is only run on mount and unmount
|
||||
|
||||
return windowSize;
|
||||
}
|
||||
|
||||
export default useWindowSize;
|
||||
|
|
@ -197,6 +197,10 @@ const SAMPLE = {
|
|||
},
|
||||
};
|
||||
|
||||
function n(num: number): number {
|
||||
return Math.ceil(num);
|
||||
}
|
||||
|
||||
export function Weather({
|
||||
weatherAtLocation = SAMPLE,
|
||||
}: {
|
||||
|
|
@ -270,12 +274,12 @@ export function Weather({
|
|||
)}
|
||||
/>
|
||||
<div className="text-4xl font-medium text-blue-50">
|
||||
{weatherAtLocation.current.temperature_2m}
|
||||
{n(weatherAtLocation.current.temperature_2m)}
|
||||
{weatherAtLocation.current_units.temperature_2m}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="text-blue-50">{`H:${currentHigh}° L:${currentLow}°`}</div>
|
||||
<div className="text-blue-50">{`H:${n(currentHigh)}° L:${n(currentLow)}°`}</div>
|
||||
</div>
|
||||
|
||||
<div className="flex flex-row justify-between">
|
||||
|
|
@ -296,7 +300,7 @@ export function Weather({
|
|||
)}
|
||||
/>
|
||||
<div className="text-blue-50 text-sm">
|
||||
{displayTemperatures[index]}
|
||||
{n(displayTemperatures[index])}
|
||||
{weatherAtLocation.hourly_units.temperature_2m}
|
||||
</div>
|
||||
</div>
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue