import { View, ScrollView, Video } from "@tarojs/components";
import NavBarNormal from "@/components/NavBarNormal/index";
import PageCustom from "@/components/page-custom/index";
import Taro, { useDidShow, useRouter, useUnload } from "@tarojs/taro";
import ChatMessage from "@/components/chat-message";
import InputBar from "./components/input-bar";
import { useEffect, useState, useRef, useMemo } from "react";
import { useTextChat } from "@/store/textChat";
import { TRobotMessage, TMessage, EContentType, EChatRole } from "@/types/bot";
import ChatGreeting from "./components/ChatGreeting";
import IconArrowLeftWhite24 from "@/components/icon/IconArrowLeftWhite24";
import PersonalCard from "./components/personal-card";
import { useAgentStore } from "@/store/agentStore";
import { useLoadMoreInfinite, createKey } from "@/utils/loadMoreInfinite";
import { getMessageHistories } from "@/service/bot";
import RecommendQuestions from './components/RecommendQuestions'
import {useKeyboard} from './components/keyboard'
import { saveMessageToServer } from "./components/input-bar/message";
import { generateUUID, getLoginId } from '@/utils/index'
export default function Index() {
const router = useRouter();
const { agentId, isVisitor } = router.params;
if (!agentId) {
return 没有相应的智能体;
}
const { fetchAgent, fetchAgentProfile, } = useAgentStore()
const agent = useAgentStore((state) => {
if(isVisitor === 'true'){
return state.agentProfile
}
return state.agent
});
const scrollViewRef = useRef(null);
const messageList = useTextChat((state) => state.list);
const {keyboardHeight, marginTopOffset, triggerHeightUpdate,} = useKeyboard(scrollViewRef, '#messageList', '#scrollView')
const { destroy, setScrollTop, genSessionId, sessionId, setAutoScroll } = useTextChat();
const scrollTop = useTextChat((state) => state.scrollTop);
// const autoScroll = useTextChat((state) => state.autoScroll);
const fetcher = async ([_url,{ nextId, pageSize}]) => {
const _nextId = nextId ? decodeURIComponent(nextId) : nextId;
const res = await getMessageHistories({
agentId,
startId: _nextId,
pageSize,
});
return res.data;
};
const { list, loadMore, pageIndex, mutate } = useLoadMoreInfinite(
createKey(`messeagehistories${isVisitor}${agentId}`),
fetcher,
);
const parsedList = list.map((item: TMessage|TRobotMessage) => {
if(item.contentType == EContentType.AiseekQA){
try{
const contentJson = JSON.parse(item.content as string)
item.content = contentJson.answer.text
// 把消息详情放入统一 body 中
item.body = {...item, content: contentJson, contentType: EContentType.AiseekQA}
}catch(e){
// console.error(e)
}
}
return item
})
const allMessages = useMemo(()=> [...[...parsedList].reverse(), ...messageList], [parsedList, messageList])
const messagesLength = useMemo(() => allMessages.length, [allMessages.length]);
const prevLengthRef = useRef(messagesLength);
const [showWelcome, setShowWelcome] = useState(!list.length);
// 加载更多
const onScrollToUpper = () => {
console.log("onscroll");
loadMore();
};
const handleTouchMove = ()=> {
console.log('set auto scroll false')
setAutoScroll(false)
}
useDidShow(()=> {
mutate(undefined,{revalidate: true})
})
useEffect(() => {
if(agentId){
if(isVisitor){
fetchAgentProfile(agentId)
}else{
fetchAgent(agentId);
}
}
}, [agentId, isVisitor]);
// 是否显示欢迎 ui
useEffect(() => {
setShowWelcome(!messageList.length && !list.length);
}, [list, messageList]);
// 将 greeting 开场白存入聊天记录里
// useEffect(()=> {
// console.log(showWelcome, agent)
// if(!showWelcome){
// return;
// }
// const loginId = getLoginId();
// if (!loginId || !agent?.agentId || !agent?.greeting || !sessionId) {
// return;
// }
// saveMessageToServer({
// loginId,
// messages: [{
// content: agent.greeting,
// contentType: EContentType.TextPlain,
// role: EChatRole.Assistant,
// saveStatus: 2,
// isStreaming: false,
// msgUk: generateUUID(),
// }],
// agentId: agent.agentId,
// sessionId,
// })
// }, [showWelcome, sessionId])
// 首次进入界面滚动到底
useEffect(() => {
if (pageIndex === 1) {
setTimeout(() => {
setScrollTop();
}, 300);
}
}, [pageIndex]);
// 首次进入聊天生成 session id
useEffect(() => {
genSessionId();
}, []);
// 监听消息列表变化,触发键盘高度重新计算
useEffect(() => {
// 只在长度真正变化时才触发
if (prevLengthRef.current !== messagesLength) {
prevLengthRef.current = messagesLength;
// 使用 setTimeout 确保 DOM 更新完成后再计算高度
const timer = setTimeout(() => {
triggerHeightUpdate();
}, 100);
return () => clearTimeout(timer);
}
}, [messagesLength, triggerHeightUpdate]);
useUnload(() => {
destroy();
});
const renderNavLeft = () => {
return (
Taro.navigateBack()}
>
);
};
// 大背景可以是视频,也可以是图片
const getBgContent = ()=> {
if(!agent?.avatarUrl || !!!agent?.enabledChatBg){
return ''
}
return agent?.avatarUrl
}
useEffect(()=> {
Taro.setNavigationBarColor({
frontColor: '#ffffff',
backgroundColor: 'transparent'
})
return ()=> {
Taro.setNavigationBarColor({
frontColor: '#000000',
backgroundColor: 'transparent'
})
}
})
return (
{/* <>{`${scrollTop}`}--{autoScroll ? 'true': 'false'}> */}
setAutoScroll(true)}
>
{showWelcome && }
{/* 复制 histories 再 reverse 否则会影响 state */}
{allMessages.map((message) => {
const reasoningContent = (message as any).reasoningContent || '';
return (
);
})}
{(agent) && }
{/* 输入框高度占位块,todo: 改成动态获取输入框块高度 */}
{agent && (
)}
);
}