/** * 礼物功能模块 * 支持发送普通礼物和情趣玩具 * 情趣玩具支持配送流程和控制界面 */ import { getSettings } from './config.js'; import { requestSave } from './save-manager.js'; import { showToast, showNotificationBanner } from './toast.js'; import { escapeHtml } from './utils.js'; import { refreshChatList } from './ui.js'; import { currentChatIndex, appendMessage, showTypingIndicator, hideTypingIndicator } from './chat.js'; import { callAI } from './ai.js'; import { splitAIMessages } from './config.js'; // SVG图标定义 const ICON_GIFT_CHARACTER = ``; const ICON_GIFT_USER = ``; const ICON_GIFT_BOTH = ``; // 礼物分类数据 const GIFT_CATEGORIES = { normal: { name: '普通礼物', icon: ``, items: [ { id: 'flower', name: '鲜花', emoji: '💐', desc: '一束美丽的鲜花', hasControl: false }, { id: 'chocolate', name: '巧克力', emoji: '🍫', desc: '精美的巧克力礼盒', hasControl: false }, { id: 'ring', name: '戒指', emoji: '💍', desc: '闪耀的戒指', hasControl: false }, { id: 'necklace', name: '项链', emoji: '📿', desc: '精致的项链', hasControl: false }, { id: 'perfume', name: '香水', emoji: '🧴', desc: '迷人的香水', hasControl: false }, { id: 'teddy', name: '玩偶', emoji: '🧸', desc: '可爱的毛绒玩偶', hasControl: false }, { id: 'cake', name: '蛋糕', emoji: '🎂', desc: '美味的蛋糕', hasControl: false }, { id: 'wine', name: '红酒', emoji: '🍷', desc: '醇香的红酒', hasControl: false } ] }, toy: { name: '情趣玩具', icon: ``, items: [ { id: 'vibrator', name: '跳蛋', emoji: '🥚', desc: '遥控跳蛋', hasControl: true, hasShock: false }, { id: 'massager', name: '按摩棒', emoji: '🌡️', desc: '震动按摩棒', hasControl: true, hasShock: false }, { id: 'breastChain', name: '微电流乳链', emoji: '⚡', desc: '微电流乳链', hasControl: true, hasShock: true }, { id: 'analPlug', name: '肛塞', emoji: '🔌', desc: '震动肛塞', hasControl: true, hasShock: false }, { id: 'cockRing', name: '锁精环', emoji: '💍', desc: '震动锁精环', hasControl: true, hasShock: false }, { id: 'breastPump', name: '吸奶器', emoji: '🍼', desc: '电动吸奶器', hasControl: true, hasShock: false }, { id: 'clitSucker', name: '阴蒂吮吸器', emoji: '💋', desc: '吮吸震动二合一', hasControl: true, hasShock: false }, { id: 'butterfly', name: '穿戴式小蝴蝶', emoji: '🦋', desc: '隐蔽穿戴震动', hasControl: true, hasShock: false }, { id: 'collar', name: '项圈', emoji: '⭕', desc: '精致的项圈', hasControl: false }, { id: 'candle', name: '低温蜡烛', emoji: '🕯️', desc: '安全的低温蜡烛', hasControl: false }, { id: 'lingerie', name: '情趣内衣', emoji: '👙', desc: '性感的情趣内衣', hasControl: false }, { id: 'fuckingMachine', name: '炮机', emoji: '🔧', desc: '电动炮机', hasControl: true, hasShock: false }, { id: 'masturbatorCup', name: '飞机杯', emoji: '🥤', desc: '电动飞机杯', hasControl: true, hasShock: false } ] } }; // 当前选中的分类、礼物和目标 let currentCategory = 'normal'; let selectedGift = null; let selectedTarget = 'character'; // 'character' 送角色 | 'user' 送用户 // 多选模式状态 let multiSelectMode = false; let selectedGifts = []; // 多选时存储多个礼物 // 显示礼物页面 export function showGiftPage() { currentCategory = 'normal'; selectedGift = null; selectedTarget = 'character'; multiSelectMode = false; selectedGifts = []; const page = document.getElementById('wechat-gift-page'); if (page) { page.classList.remove('hidden'); renderGiftContent(); } } // 隐藏礼物页面 export function hideGiftPage() { const page = document.getElementById('wechat-gift-page'); if (page) { page.classList.add('hidden'); } } // 渲染礼物内容 function renderGiftContent() { const tabsContainer = document.getElementById('wechat-gift-tabs'); const gridContainer = document.getElementById('wechat-gift-grid'); const sendBtn = document.getElementById('wechat-gift-send'); const targetContainer = document.getElementById('wechat-gift-target'); const headerEl = document.querySelector('.wechat-gift-navbar'); if (!tabsContainer || !gridContainer) return; // 渲染多选按钮(仅情趣玩具分类显示) let multiSelectBtn = document.getElementById('wechat-gift-multi-select-btn'); if (currentCategory === 'toy') { if (!multiSelectBtn && headerEl) { multiSelectBtn = document.createElement('button'); multiSelectBtn.id = 'wechat-gift-multi-select-btn'; multiSelectBtn.className = 'wechat-gift-multi-select-btn'; headerEl.appendChild(multiSelectBtn); } if (multiSelectBtn) { if (multiSelectMode) { multiSelectBtn.textContent = selectedGifts.length > 0 ? `完成(${selectedGifts.length})` : '取消'; multiSelectBtn.classList.add('active'); } else { multiSelectBtn.textContent = '多选'; multiSelectBtn.classList.remove('active'); } multiSelectBtn.onclick = toggleMultiSelectMode; } } else { // 非情趣玩具分类,移除多选按钮并重置状态 if (multiSelectBtn) { multiSelectBtn.remove(); } multiSelectMode = false; selectedGifts = []; } // 渲染送礼目标选择(仅情趣玩具显示) if (targetContainer) { if (currentCategory === 'toy') { targetContainer.classList.remove('hidden'); targetContainer.innerHTML = `
送给谁?
`; // 绑定目标选择事件 targetContainer.querySelectorAll('.wechat-gift-target-btn').forEach(btn => { btn.addEventListener('click', () => { selectedTarget = btn.dataset.target; renderGiftContent(); }); }); } else { targetContainer.classList.add('hidden'); targetContainer.innerHTML = ''; } } // 渲染分类标签 let tabsHtml = ''; for (const [key, category] of Object.entries(GIFT_CATEGORIES)) { const activeClass = key === currentCategory ? 'active' : ''; tabsHtml += ``; } tabsContainer.innerHTML = tabsHtml; // 绑定标签点击事件 tabsContainer.querySelectorAll('.wechat-gift-tab').forEach(tab => { tab.addEventListener('click', () => { currentCategory = tab.dataset.category; selectedGift = null; // 切换分类时不重置多选,只在非toy分类时重置 if (tab.dataset.category !== 'toy') { multiSelectMode = false; selectedGifts = []; } renderGiftContent(); }); }); // 渲染礼物网格 const category = GIFT_CATEGORIES[currentCategory]; let gridHtml = ''; category.items.forEach(item => { // 多选模式下检查是否在selectedGifts中 const isSelectedInMulti = multiSelectMode && selectedGifts.some(g => g.id === item.id); // 单选模式下检查是否是selectedGift const isSelectedSingle = !multiSelectMode && selectedGift?.id === item.id; const selectedClass = (isSelectedInMulti || isSelectedSingle) ? 'selected' : ''; const controlBadge = item.hasControl ? '可控' : ''; // 多选模式下显示勾选标记 const checkMark = isSelectedInMulti ? '' : ''; gridHtml += `
${item.emoji} ${item.name} ${controlBadge} ${checkMark}
`; }); gridContainer.innerHTML = gridHtml; // 绑定礼物点击事件 gridContainer.querySelectorAll('.wechat-gift-item').forEach(item => { item.addEventListener('click', () => { const giftId = item.dataset.giftId; const gift = category.items.find(g => g.id === giftId); if (multiSelectMode && currentCategory === 'toy') { // 多选模式:只能选择有控制功能的玩具 if (!gift.hasControl) { showToast('该玩具不支持多选控制'); return; } // 切换选中状态 const existingIndex = selectedGifts.findIndex(g => g.id === giftId); if (existingIndex >= 0) { selectedGifts.splice(existingIndex, 1); } else { if (selectedGifts.length >= 5) { showToast('最多选择5个玩具'); return; } selectedGifts.push(gift); } } else { // 单选模式 selectedGift = gift; } renderGiftContent(); }); }); // 更新发送按钮状态 if (sendBtn) { if (multiSelectMode && selectedGifts.length > 0) { sendBtn.disabled = false; sendBtn.textContent = `送出 ${selectedGifts.length} 件玩具`; } else if (!multiSelectMode && selectedGift) { sendBtn.disabled = false; sendBtn.textContent = `送出 ${selectedGift.name}`; } else { sendBtn.disabled = true; sendBtn.textContent = '请选择礼物'; } } } // 切换多选模式 function toggleMultiSelectMode() { if (multiSelectMode && selectedGifts.length > 0) { // 如果已有选择,点击"完成"按钮触发发送 sendGift(); } else { // 切换模式 multiSelectMode = !multiSelectMode; if (!multiSelectMode) { selectedGifts = []; } selectedGift = null; renderGiftContent(); } } // 发送礼物 export async function sendGift() { // 检查是否有选择 const isMulti = multiSelectMode && selectedGifts.length > 0; if (!isMulti && !selectedGift) { showToast('请选择礼物'); return; } if (currentChatIndex < 0) { showToast('请先打开聊天'); return; } const settings = getSettings(); const contact = settings.contacts[currentChatIndex]; if (!contact) return; const isToy = currentCategory === 'toy'; const target = isToy ? selectedTarget : null; // 关闭礼物页面 hideGiftPage(); // 获取描述(如果有输入的话) const descInput = document.getElementById('wechat-gift-desc'); const customDesc = descInput?.value?.trim() || ''; if (descInput) descInput.value = ''; // 保存到聊天历史 const now = new Date(); const timeStr = `${now.getFullYear()}-${(now.getMonth()+1).toString().padStart(2,'0')}-${now.getDate().toString().padStart(2,'0')} ${now.getHours().toString().padStart(2,'0')}:${now.getMinutes().toString().padStart(2,'0')}`; if (!contact.chatHistory) { contact.chatHistory = []; } // 多选模式处理 if (isMulti) { const giftsToSend = [...selectedGifts]; const giftNames = giftsToSend.map(g => g.name).join('、'); const giftEmojis = giftsToSend.map(g => g.emoji).join(' '); const targetText = target === 'character' ? '送TA' : target === 'user' ? '送自己' : '同时送'; const giftMessage = `[情趣礼物套装] ${giftEmojis} ${giftNames}(${targetText})${customDesc ? ` - ${customDesc}` : ''}`; const giftRecord = { role: 'user', content: giftMessage, time: timeStr, timestamp: Date.now(), isGift: true, isMultiGift: true, giftInfo: { gifts: giftsToSend.map(g => ({ id: g.id, name: g.name, emoji: g.emoji, desc: g.desc, hasControl: g.hasControl, hasShock: g.hasShock })), isToy: true, target: target, customDesc: customDesc } }; contact.chatHistory.push(giftRecord); // 显示礼物消息(多选版本) appendMultiGiftMessage('user', giftsToSend, customDesc, contact, target); contact.lastMessage = giftMessage; // 添加到待配送列表(作为一个多玩具组合) if (!contact.pendingGifts) { contact.pendingGifts = []; } const multiPendingGift = { isMulti: true, toys: giftsToSend.map(g => ({ giftId: g.id, giftName: g.name, giftEmoji: g.emoji, giftDesc: g.desc, hasControl: g.hasControl, hasShock: g.hasShock || false })), target: target, startMessageCount: contact.chatHistory.length, deliveredAt: null, isDelivered: false, isUsing: false, timestamp: Date.now() }; contact.pendingGifts.push(multiPendingGift); // 显示配送中弹窗 setTimeout(() => { showNotificationBanner('快递', `您选择的${giftsToSend.length}件商品正在配送中~`, 4000); }, 500); // 2秒后弹出加急配送弹窗 setTimeout(() => { showExpressDeliveryModal(multiPendingGift, contact); }, 2000); requestSave(); refreshChatList(); // 显示打字指示器 showTypingIndicator(contact); // 构建给AI的提示 let targetTextAI; if (target === 'character') { targetTextAI = '角色(你)'; } else if (target === 'user') { targetTextAI = '用户'; } else { targetTextAI = '你和用户两人同时'; } const aiPrompt = `[系统提示:用户刚刚购买了一套情趣玩具套装,包括:${giftNames},准备送给${targetTextAI}使用。商品正在配送中,预计很快就会送达。${customDesc ? `用户附言:${customDesc}` : ''} 请根据你的角色性格,对这套即将到来的礼物做出反应: - 如果是送给你的:可以表现出期待、害羞、紧张、好奇等情绪,可以问用户打算怎么用这些 - 如果是送给用户的:可以表现出好奇、调侃、期待看到用户反应等 - 如果是同时送给两人的:可以表现出兴奋、期待、好奇等,想象两人一起使用的场景 - 根据你的人设和与用户的关系,反应可以是含蓄的、热情的、或者假装矜持的 - 回复不要太短,请展现角色的内心活动和情绪变化 【重要】只能输出纯文字消息,禁止输出任何特殊格式标签]`; try { const aiResponse = await callAI(contact, aiPrompt); hideTypingIndicator(); if (aiResponse) { const aiMessages = splitAIMessages(aiResponse); for (const msg of aiMessages) { let reply = msg.trim(); reply = reply.replace(/<\s*meme\s*>[\s\S]*?<\s*\/\s*meme\s*>/gi, '').trim(); reply = reply.replace(/\[.*?\]/g, '').trim(); reply = reply.replace(/([^)]*)/g, '').trim(); reply = reply.replace(/\([^)]*\)/g, '').trim(); if (reply) { contact.chatHistory.push({ role: 'assistant', content: reply, time: timeStr, timestamp: Date.now() }); appendMessage('assistant', reply, contact); } } const lastMsg = aiMessages[aiMessages.length - 1]?.trim()?.replace(/\[.*?\]/g, '').trim(); if (lastMsg) { contact.lastMessage = lastMsg.length > 20 ? lastMsg.substring(0, 20) + '...' : lastMsg; } requestSave(); refreshChatList(); } } catch (err) { hideTypingIndicator(); console.error('[可乐] 礼物AI回复失败:', err); } // 重置多选状态 multiSelectMode = false; selectedGifts = []; return; } // 单选模式处理(原有逻辑) const gift = selectedGift; // 构建礼物消息 let giftMessage; if (isToy) { const targetText = target === 'character' ? '送TA' : target === 'user' ? '送自己' : '同时送'; giftMessage = `[情趣礼物] ${gift.emoji} ${gift.name}(${targetText})${customDesc ? ` - ${customDesc}` : ''}`; } else { giftMessage = `[礼物] ${gift.emoji} ${gift.name}${customDesc ? ` - ${customDesc}` : ''}`; } const giftRecord = { role: 'user', content: giftMessage, time: timeStr, timestamp: Date.now(), isGift: true, giftInfo: { id: gift.id, name: gift.name, emoji: gift.emoji, desc: gift.desc, isToy: isToy, hasControl: gift.hasControl, hasShock: gift.hasShock, target: target, customDesc: customDesc } }; contact.chatHistory.push(giftRecord); // 显示礼物消息 appendGiftMessage('user', gift, isToy, customDesc, contact, target); contact.lastMessage = giftMessage; // 如果是可控制的情趣玩具,添加到待配送列表 if (isToy && gift.hasControl) { if (!contact.pendingGifts) { contact.pendingGifts = []; } const pendingGift = { giftId: gift.id, giftName: gift.name, giftEmoji: gift.emoji, giftDesc: gift.desc, target: target, hasControl: gift.hasControl, hasShock: gift.hasShock || false, startMessageCount: contact.chatHistory.length, deliveredAt: null, isDelivered: false, isUsing: false, timestamp: Date.now() }; contact.pendingGifts.push(pendingGift); // 显示配送中弹窗 setTimeout(() => { showNotificationBanner('快递', '您选择的商品正在配送中~', 4000); }, 500); // 2秒后弹出加急配送弹窗 setTimeout(() => { showExpressDeliveryModal(pendingGift, contact); }, 2000); } requestSave(); refreshChatList(); // 显示打字指示器 showTypingIndicator(contact); // 构建给AI的提示 let aiPrompt; if (isToy && gift.hasControl) { // 可控制的情趣玩具 - 配送中提示词 let targetText; if (target === 'character') { targetText = '你'; } else if (target === 'user') { targetText = '用户'; } else { targetText = '你和用户两人同时'; } aiPrompt = `[系统提示:用户刚刚购买了一个${gift.name}(${gift.desc}),准备送给${targetText}使用。商品正在配送中,预计很快就会送达。${customDesc ? `用户附言:${customDesc}` : ''} 请根据你的角色性格,对这个即将到来的礼物做出反应: - 如果是送给你的:可以表现出期待、害羞、紧张、好奇等情绪 - 如果是送给用户的:可以表现出好奇、调侃、期待看到用户反应等 - 如果是同时送给两人的:可以表现出兴奋、期待、好奇等,想象两人一起使用的场景 - 根据你的人设和与用户的关系,反应可以是含蓄的、热情的、或者假装矜持的 - 可以询问用户打算怎么用、什么时候用等 - 回复不要太短,请展现角色的内心活动和情绪变化 【重要】只能输出纯文字消息,禁止输出任何特殊格式标签]`; } else if (isToy) { // 不可控制的情趣玩具 aiPrompt = `[用户送给你一个情趣礼物:${gift.name}(${gift.desc})${customDesc ? `,附言:${customDesc}` : ''}。请根据你的人设性格对这个礼物做出反应。【重要】只能输出纯文字消息,禁止输出任何特殊格式标签]`; } else { // 普通礼物 aiPrompt = `[用户送给你一个礼物:${gift.name}(${gift.desc})${customDesc ? `,附言:${customDesc}` : ''}。请对这个礼物做出自然的反应。【重要】只能输出纯文字消息,禁止输出任何特殊格式标签]`; } try { const aiResponse = await callAI(contact, aiPrompt); hideTypingIndicator(); if (aiResponse) { const aiMessages = splitAIMessages(aiResponse); for (const msg of aiMessages) { let reply = msg.trim(); // 过滤掉特殊标签 reply = reply.replace(/<\s*meme\s*>[\s\S]*?<\s*\/\s*meme\s*>/gi, '').trim(); reply = reply.replace(/\[.*?\]/g, '').trim(); // 过滤括号动作描写 reply = reply.replace(/([^)]*)/g, '').trim(); reply = reply.replace(/\([^)]*\)/g, '').trim(); if (reply) { contact.chatHistory.push({ role: 'assistant', content: reply, time: timeStr, timestamp: Date.now() }); appendMessage('assistant', reply, contact); } } const lastMsg = aiMessages[aiMessages.length - 1]?.trim()?.replace(/\[.*?\]/g, '').trim(); if (lastMsg) { contact.lastMessage = lastMsg.length > 20 ? lastMsg.substring(0, 20) + '...' : lastMsg; } requestSave(); refreshChatList(); } } catch (err) { hideTypingIndicator(); console.error('[可乐] 礼物AI回复失败:', err); } } // 检查礼物是否送达(在chat.js的消息发送后调用) export function checkGiftDelivery(contact) { if (!contact || !contact.pendingGifts || contact.pendingGifts.length === 0) return; const currentCount = contact.chatHistory?.length || 0; for (const gift of contact.pendingGifts) { // 如果正在使用中或已完成,跳过 if (gift.isUsing || gift.completed) continue; // 首次送达检测 if (!gift.isDelivered && currentCount >= gift.startMessageCount + 25) { // 标记送达 gift.isDelivered = true; gift.deliveredAt = Date.now(); gift.lastAskMessageCount = currentCount; // 记录询问时的消息数 // 显示送达弹窗 showNotificationBanner('快递', '您的商品已送达~', 4000); // 2秒后弹出询问框 setTimeout(() => { showGiftArrivalModal(gift, contact); }, 2000); requestSave(); break; // 一次只处理一个 } // 已送达但点了"稍后",每隔25条消息再次询问 if (gift.isDelivered && !gift.isUsing && gift.lastAskMessageCount) { if (currentCount >= gift.lastAskMessageCount + 25) { gift.lastAskMessageCount = currentCount; // 更新询问时的消息数 // 显示提醒弹窗 showNotificationBanner('快递', '您的商品还在等待使用~', 3000); // 2秒后再次询问 setTimeout(() => { showGiftArrivalModal(gift, contact); }, 2000); requestSave(); break; // 一次只处理一个 } } } } // 显示加急配送弹窗 export function showExpressDeliveryModal(gift, contact) { const modal = document.getElementById('wechat-express-delivery-modal'); if (!modal) return; modal.classList.remove('hidden'); const yesBtn = document.getElementById('wechat-express-yes'); const noBtn = document.getElementById('wechat-express-no'); const handleYes = () => { modal.classList.add('hidden'); yesBtn.removeEventListener('click', handleYes); noBtn.removeEventListener('click', handleNo); // 标记为已送达 gift.isDelivered = true; gift.deliveredAt = Date.now(); requestSave(); // 显示送达通知 showNotificationBanner('快递', '您的商品已送达~', 3000); // 2秒后弹出"是否开始玩"弹窗 setTimeout(() => { showGiftArrivalModal(gift, contact); }, 2000); }; const handleNo = () => { modal.classList.add('hidden'); yesBtn.removeEventListener('click', handleYes); noBtn.removeEventListener('click', handleNo); // 什么都不做,走原有的25条消息检测逻辑 }; yesBtn.addEventListener('click', handleYes); noBtn.addEventListener('click', handleNo); } // 显示礼物送达询问弹窗 export function showGiftArrivalModal(gift, contact) { const modal = document.getElementById('wechat-gift-arrival-modal'); const bodyEl = document.getElementById('wechat-gift-arrival-body'); if (!modal || !bodyEl) return; // 支持多选礼物 if (gift.isMulti) { const toyNames = gift.toys.map(t => t.giftName).join('、'); bodyEl.innerHTML = `您的 ${toyNames} 已送达,您要现在开始玩吗?`; } else { bodyEl.innerHTML = `您的 ${gift.giftName} 已送达,您要现在开始玩吗?`; } // 存储当前礼物信息 modal.dataset.giftId = gift.giftId || (gift.isMulti ? 'multi' : ''); modal.dataset.giftTimestamp = gift.timestamp; modal.classList.remove('hidden'); // 绑定按钮事件 const yesBtn = document.getElementById('wechat-gift-arrival-yes'); const noBtn = document.getElementById('wechat-gift-arrival-no'); const handleYes = async () => { modal.classList.add('hidden'); yesBtn.removeEventListener('click', handleYes); noBtn.removeEventListener('click', handleNo); // 标记礼物为已完成,防止重复触发弹窗 gift.completed = true; requestSave(); // 打开玩具控制界面 const { showToyControlPage } = await import('./toy-control.js'); showToyControlPage(gift, contact, currentChatIndex); }; const handleNo = () => { modal.classList.add('hidden'); yesBtn.removeEventListener('click', handleYes); noBtn.removeEventListener('click', handleNo); // 更新消息计数基准,25条后再次询问 const currentCount = contact.chatHistory?.length || 0; gift.lastAskMessageCount = currentCount; requestSave(); }; yesBtn.addEventListener('click', handleYes); noBtn.addEventListener('click', handleNo); } // 手动打开已送达礼物的控制界面(从心动瞬间历史记录进入) export async function openToyControl(gift, contact, contactIndex) { const { showToyControlPage } = await import('./toy-control.js'); showToyControlPage(gift, contact, contactIndex); } // 添加礼物消息到界面 export function appendGiftMessage(role, gift, isToy, customDesc, contact, target = null) { const messagesContainer = document.getElementById('wechat-chat-messages'); if (!messagesContainer) return; const messageDiv = document.createElement('div'); messageDiv.className = `wechat-message ${role === 'user' ? 'self' : ''}`; const firstChar = contact?.name ? contact.name.charAt(0) : '?'; // 获取用户头像 let avatarContent; if (role === 'user') { const settings = getSettings(); if (settings.userAvatar) { avatarContent = ``; } else { avatarContent = '我'; } } else { avatarContent = contact?.avatar ? `` : firstChar; } const giftTypeClass = isToy ? 'wechat-gift-bubble-toy' : ''; let giftTypeLabel = isToy ? '情趣礼物' : '礼物'; if (isToy && target) { giftTypeLabel = target === 'character' ? '情趣礼物·送TA' : target === 'user' ? '情趣礼物·送自己' : '情趣礼物·同时送'; } messageDiv.innerHTML = `
${avatarContent}
${gift.emoji}
${escapeHtml(gift.name)}
${customDesc ? `
${escapeHtml(customDesc)}
` : ''}
${giftTypeLabel}
`; messagesContainer.appendChild(messageDiv); messagesContainer.scrollTop = messagesContainer.scrollHeight; } // 添加多选礼物消息到界面 export function appendMultiGiftMessage(role, gifts, customDesc, contact, target = null) { const messagesContainer = document.getElementById('wechat-chat-messages'); if (!messagesContainer) return; const messageDiv = document.createElement('div'); messageDiv.className = `wechat-message ${role === 'user' ? 'self' : ''}`; const firstChar = contact?.name ? contact.name.charAt(0) : '?'; // 获取用户头像 let avatarContent; if (role === 'user') { const settings = getSettings(); if (settings.userAvatar) { avatarContent = ``; } else { avatarContent = '我'; } } else { avatarContent = contact?.avatar ? `` : firstChar; } const giftTypeLabel = target === 'character' ? '送TA' : target === 'user' ? '送自己' : '同时送'; // 生成每个礼物的标签 const giftTagsHtml = gifts.map(g => `
${g.emoji} ${escapeHtml(g.name)}
`).join(''); messageDiv.innerHTML = `
${avatarContent}
🎁 情趣套装 ${giftTypeLabel}
${giftTagsHtml}
${customDesc ? `
${escapeHtml(customDesc)}
` : ''}
`; messagesContainer.appendChild(messageDiv); messagesContainer.scrollTop = messagesContainer.scrollHeight; } // 获取礼物分类数据(供其他模块使用) export function getGiftCategories() { return GIFT_CATEGORIES; } // 初始化礼物事件 export function initGiftEvents() { // 返回按钮 document.getElementById('wechat-gift-back')?.addEventListener('click', hideGiftPage); // 发送按钮 document.getElementById('wechat-gift-send')?.addEventListener('click', sendGift); }