This commit is contained in:
Andision 2024-07-23 12:25:59 +07:00 committed by GitHub
commit 33a09d100f
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
7 changed files with 96 additions and 32 deletions

View File

@ -9,15 +9,15 @@ import {
OnDragEndResponder, OnDragEndResponder,
} from "@hello-pangea/dnd"; } from "@hello-pangea/dnd";
import { useChatStore } from "../store"; import { ChatSession, useChatStore } from "../store";
import Locale from "../locales"; import Locale from "../locales";
import { Link, useLocation, useNavigate } from "react-router-dom"; import { Link, useLocation, useNavigate } from "react-router-dom";
import { Path } from "../constant"; import { Path } from "../constant";
import { MaskAvatar } from "./mask"; import { MaskAvatar } from "./mask";
import { Mask } from "../store/mask"; import { Mask } from "../store/mask";
import { useRef, useEffect } from "react"; import { useRef, useEffect, useState } from "react";
import { showConfirm } from "./ui-lib"; import { showConfirm, SearchInput } from "./ui-lib";
import { useMobileScreen } from "../utils"; import { useMobileScreen } from "../utils";
export function ChatItem(props: { export function ChatItem(props: {
@ -102,7 +102,7 @@ export function ChatItem(props: {
); );
} }
export function ChatList(props: { narrow?: boolean }) { export function ChatList(props: { narrow?: boolean; search: string }) {
const [sessions, selectedIndex, selectSession, moveSession] = useChatStore( const [sessions, selectedIndex, selectSession, moveSession] = useChatStore(
(state) => [ (state) => [
state.sessions, state.sessions,
@ -131,6 +131,24 @@ export function ChatList(props: { narrow?: boolean }) {
moveSession(source.index, destination.index); moveSession(source.index, destination.index);
}; };
function haveSearchKeyword(item: ChatSession): boolean {
if (props.search.length === 0) {
return true;
}
let foundKeyword = false;
item.messages.forEach((message) => {
// console.log(chatListSearch, message.content, message.content.includes(chatListSearch))
if (message.content.includes(props.search)) {
foundKeyword = true;
return;
}
});
return foundKeyword;
}
return ( return (
<DragDropContext onDragEnd={onDragEnd}> <DragDropContext onDragEnd={onDragEnd}>
<Droppable droppableId="chat-list"> <Droppable droppableId="chat-list">
@ -140,7 +158,9 @@ export function ChatList(props: { narrow?: boolean }) {
ref={provided.innerRef} ref={provided.innerRef}
{...provided.droppableProps} {...provided.droppableProps}
> >
{sessions.map((item, i) => ( {sessions.map(
(item, i) =>
haveSearchKeyword(item) && (
<ChatItem <ChatItem
title={item.topic} title={item.topic}
time={new Date(item.lastUpdate).toLocaleString()} time={new Date(item.lastUpdate).toLocaleString()}
@ -164,7 +184,8 @@ export function ChatList(props: { narrow?: boolean }) {
narrow={props.narrow} narrow={props.narrow}
mask={item.mask} mask={item.mask}
/> />
))} ),
)}
{provided.placeholder} {provided.placeholder}
</div> </div>
)} )}

View File

@ -230,6 +230,11 @@
white-space: nowrap; white-space: nowrap;
} }
.chat-list-search {
padding: 10px 0px;
margin-bottom: 10px;
}
.narrow-sidebar { .narrow-sidebar {
.sidebar-title, .sidebar-title,
.sidebar-sub-title { .sidebar-sub-title {

View File

@ -1,4 +1,4 @@
import { useEffect, useRef, useMemo } from "react"; import { useEffect, useRef, useMemo, useState } from "react";
import styles from "./home.module.scss"; import styles from "./home.module.scss";
@ -29,7 +29,7 @@ import {
import { Link, useNavigate } from "react-router-dom"; import { Link, useNavigate } from "react-router-dom";
import { isIOS, useMobileScreen } from "../utils"; import { isIOS, useMobileScreen } from "../utils";
import dynamic from "next/dynamic"; import dynamic from "next/dynamic";
import { showConfirm, showToast } from "./ui-lib"; import { SearchInput, showConfirm, showToast } from "./ui-lib";
const ChatList = dynamic(async () => (await import("./chat-list")).ChatList, { const ChatList = dynamic(async () => (await import("./chat-list")).ChatList, {
loading: () => null, loading: () => null,
@ -141,6 +141,8 @@ export function SideBar(props: { className?: string }) {
[isMobileScreen], [isMobileScreen],
); );
const [chatListSearch, setChatListSearch] = useState("");
useHotKey(); useHotKey();
return ( return (
@ -188,6 +190,16 @@ export function SideBar(props: { className?: string }) {
/> />
</div> </div>
<div className={styles["chat-list-search"]}>
<SearchInput
value={chatListSearch}
onChange={(e) => {
setChatListSearch(e.currentTarget.value);
}}
placeholder={Locale.Home.Search}
></SearchInput>
</div>
<div <div
className={styles["sidebar-body"]} className={styles["sidebar-body"]}
onClick={(e) => { onClick={(e) => {
@ -196,7 +208,7 @@ export function SideBar(props: { className?: string }) {
} }
}} }}
> >
<ChatList narrow={shouldNarrow} /> <ChatList narrow={shouldNarrow} search={chatListSearch} />
</div> </div>
<div className={styles["sidebar-tail"]}> <div className={styles["sidebar-tail"]}>

View File

@ -275,6 +275,20 @@ export function PasswordInput(props: HTMLProps<HTMLInputElement>) {
); );
} }
export function SearchInput(props: HTMLProps<HTMLInputElement>) {
const [visible, setVisible] = useState(false);
function changeVisibility() {
setVisible(!visible);
}
return (
<div className={"search-input-container"}>
<input {...props} type="text" className={"search-input"} />
</div>
);
}
export function Select( export function Select(
props: React.DetailedHTMLProps< props: React.DetailedHTMLProps<
React.SelectHTMLAttributes<HTMLSelectElement>, React.SelectHTMLAttributes<HTMLSelectElement>,

View File

@ -124,6 +124,7 @@ const cn = {
DeleteChat: "确认删除选中的对话?", DeleteChat: "确认删除选中的对话?",
DeleteToast: "已删除会话", DeleteToast: "已删除会话",
Revert: "撤销", Revert: "撤销",
Search: "输入筛选的关键词",
}, },
Settings: { Settings: {
Title: "设置", Title: "设置",

View File

@ -127,6 +127,7 @@ const en: LocaleType = {
DeleteChat: "Confirm to delete the selected conversation?", DeleteChat: "Confirm to delete the selected conversation?",
DeleteToast: "Chat Deleted", DeleteToast: "Chat Deleted",
Revert: "Revert", Revert: "Revert",
Search: "Enter filter keywords",
}, },
Settings: { Settings: {
Title: "Settings", Title: "Settings",

View File

@ -344,6 +344,16 @@ pre {
} }
} }
.search-input-container {
display: flex;
justify-content: center;
.search-input {
min-width: 99%;
text-align: left;
}
}
.user-avatar { .user-avatar {
height: 30px; height: 30px;
min-height: 30px; min-height: 30px;