ai界面可用

main
勿妄 1 month ago
parent dbbbcc9e13
commit 943cee36ec

@ -9,32 +9,57 @@
<aside class="sidebar">
<h2 class="sidebar-title">历史对话</h2>
<ul class="history-list">
<li class="history-item" v-for="(item, index) in historyItems" :key="index">
<span class="history-text">{{ item.text }}</span>
<li class="history-item"
v-for="conversation in conversations"
:key="conversation.id"
@click="selectConversation(conversation)">
<span class="history-text">{{ conversation.title }}</span>
<div class="history-actions">
<!-- 编辑按钮 -->
<button class="action-btn" title="编辑" @click.stop="editItem(item)">
<button class="action-btn" title="编辑" @click.stop="editConversationTitle(conversation)">
<img src="@/assets/images/edit.png" alt="编辑" />
</button>
<!-- 删除按钮 -->
<button class="action-btn" title="删除" @click.stop="deleteItem(item)">
<button class="action-btn" title="删除" @click.stop="deleteConversation(conversation)">
<img src="@/assets/images/delete.png" alt="删除" />
</button>
</div>
</li>
</ul>
<!-- 新建对话按钮 -->
<button class="new-chat-btn" @click="createNewChat">
<span>新建对话</span>
</button>
</aside>
<!-- 聊天区域 -->
<main class="chat-area">
<div class="chat-content">
<!-- 欢迎消息始终显示在最上方 -->
<div class="welcome-message">
<!-- 机器人头像 -->
<div class="bot-avatar">
<img src="@/assets/images/aiRobot.png" alt="机器人头像" />
</div>
<div class="welcome-text">我可以回答各种问题欢迎提问</div>
</div>
<!-- 对话消息 -->
<template v-if="currentConversation">
<div v-for="message in currentConversation.messages"
:key="message.id"
:class="message.isUser ? 'user-message' : 'bot-message'">
<template v-if="message.isUser">
<div class="message-text">{{ message.text }}</div>
<div class="user-avatar">
<img src="@/assets/images/aiRobot.png" alt="用户头像" />
</div>
</template>
<template v-else>
<div class="bot-avatar">
<img src="@/assets/images/aiRobot.png" alt="机器人头像" />
</div>
<div class="message-text">{{ message.text }}</div>
</template>
</div>
</template>
</div>
<!-- 输入区域 -->
@ -58,6 +83,21 @@
id: number; //
text: string; //
}
//
interface Message {
id: number;
text: string;
isUser: boolean; // true false
}
//
interface Conversation {
id: number;
title: string; // 20
messages: Message[]; //
timestamp: number; //
}
//
const historyItems = ref<HistoryItem[]>([
@ -67,31 +107,116 @@ const historyItems = ref<HistoryItem[]>([
//
const message = ref('');
//
const chatMessages = ref<HistoryItem[]>([]);
//
const sendMessage = () => {
const sendMessage = async () => {
const msg = message.value.trim();
if (msg) {
const newItem: HistoryItem = {
id: Date.now(), // 使
text: msg,
if (!msg) return;
//
if (!currentConversation.value) {
currentConversation.value = {
id: Date.now(),
title: msg.slice(0, 20) + (msg.length > 20 ? '...' : ''),
messages: [],
timestamp: Date.now()
};
conversations.value.push(currentConversation.value);
}
//
const userMessage: Message = {
id: Date.now(),
text: msg,
isUser: true
};
currentConversation.value.messages.push(userMessage);
//
message.value = '';
//
try {
// TODO: AI
const botResponse = await mockBotResponse(msg);
const botMessage: Message = {
id: Date.now(),
text: botResponse,
isUser: false
};
historyItems.value.push(newItem); //
message.value = ''; //
currentConversation.value.messages.push(botMessage);
} catch (error) {
console.error('发送消息失败:', error);
}
};
//
const editItem = (item: HistoryItem) => {
//
const editItem = (item: HistoryItem) => {
const newText = prompt('编辑对话内容:', item.text);
if (newText !== null) {
item.text = newText.trim();
const chatItem = chatMessages.value.find((chat) => chat.id === item.id);
if (chatItem) {
chatItem.text = newText.trim(); //
}
}
};
//
const deleteItem = (item: HistoryItem) => {
historyItems.value = historyItems.value.filter((history) => history.id !== item.id);
chatMessages.value = chatMessages.value.filter((chat) => chat.id !== item.id); //
};
//
const conversations = ref<Conversation[]>([]);
//
const currentConversation = ref<Conversation | null>(null);
//
const selectConversation = (conversation: Conversation) => {
currentConversation.value = conversation;
};
//
const deleteConversation = (conversation: Conversation) => {
conversations.value = conversations.value.filter(c => c.id !== conversation.id);
if (currentConversation.value?.id === conversation.id) {
currentConversation.value = null;
}
};
//
const createNewChat = () => {
const newConversation: Conversation = {
id: Date.now(),
title: '新对话',
messages: [],
timestamp: Date.now()
};
conversations.value.push(newConversation);
currentConversation.value = newConversation;
};
//
const editConversationTitle = (conversation: Conversation) => {
const newTitle = prompt('编辑对话标题:', conversation.title);
if (newTitle !== null && newTitle.trim() !== '') {
conversation.title = newTitle.trim();
}
};
//
const mockBotResponse = async (msg: string): Promise<string> => {
return new Promise(resolve => {
setTimeout(() => {
resolve(`这是对 "${msg}" 的回复`);
}, 1000);
});
};
</script>
@ -194,6 +319,29 @@ const deleteItem = (item: HistoryItem) => {
.action-btn:hover {
color: #9c88ff;
}
.new-chat-btn {
width: 100%;
padding: 12px 16px;
background: linear-gradient(45deg, #9c88ff, #ff6b9d);
color: white;
border: none;
border-radius: 8px;
font-size: 18px;
cursor: pointer;
transition: transform 0.2s, box-shadow 0.2s;
text-align: center;
margin-top: 20px;
}
.new-chat-btn:hover {
transform: translateY(-2px);
box-shadow: 0 4px 15px rgba(156, 136, 255, 0.3);
}
.new-chat-btn:active {
transform: translateY(0);
}
/* 聊天区域 */
.chat-area {
@ -214,10 +362,9 @@ const deleteItem = (item: HistoryItem) => {
overflow-y: auto;
display: flex;
flex-direction: column;
justify-content: flex-start; /* 垂直方向上靠上 */
align-items: flex-start; /* 水平方向上靠左 */
gap: 16px;
}
.welcome-message {
display: flex;
align-items: center;
@ -226,6 +373,8 @@ const deleteItem = (item: HistoryItem) => {
border-radius: 20px;
padding: 16px 24px;
box-shadow: 0 4px 20px rgba(156, 136, 255, 0.1);
max-width: 60%;
margin-bottom: 16px;
}
.bot-avatar {
@ -238,6 +387,7 @@ const deleteItem = (item: HistoryItem) => {
justify-content: center;
font-size: 18px;
color: white;
margin-right: 16px;
}
.bot-avatar img {
@ -250,6 +400,62 @@ const deleteItem = (item: HistoryItem) => {
font-size: 20px;
color: #333;
}
.user-message {
display: flex;
align-items: center;
justify-content: flex-end;
background: rgba(255, 255, 255, 0.9);
border: 1px solid rgba(200, 180, 255, 0.3);
border-radius: 20px;
padding: 16px 24px;
box-shadow: 0 4px 20px rgba(156, 136, 255, 0.1);
max-width: 60%;
margin-bottom: 16px;
align-self: flex-end;
}
.user-text {
font-size: 16px;
color: #333;
margin-right: 16px;
}
.user-avatar {
width: 40px;
height: 40px;
background: transparent;
border-radius: 50%;
display: flex;
align-items: center;
justify-content: center;
overflow: hidden;
}
.user-avatar img {
width: 100%;
height: 100%;
object-fit: cover;
}
.bot-message {
display: flex;
align-items: center;
background: rgba(255, 255, 255, 0.9);
border: 1px solid rgba(200, 180, 255, 0.3);
border-radius: 20px;
padding: 16px 24px;
box-shadow: 0 4px 20px rgba(156, 136, 255, 0.1);
max-width: 60%;
margin-bottom: 16px;
align-self: flex-start;
}
.message-text {
font-size: 16px;
color: #333;
margin: 0 16px;
}
/* 输入区域 */
.input-area {
@ -370,4 +576,3 @@ const deleteItem = (item: HistoryItem) => {
background: rgba(156, 136, 255, 0.5);
}
</style>
Loading…
Cancel
Save