mirror of
https://github.com/hellodigua/ChatLab.git
synced 2026-10-25 17:54:34 +08:00
feat: 话题迁移至洞察
This commit is contained in:
1 parent
2b3f1fc04f
commit
c7ad09b2d5
20 files changed
+132
-55
No files matched your search
@@ -1,3 +1,4 @@
|
||||
- 文档:开始开发前,请先查看 `./.docs/README.md`,并阅读与当前需求相关的文档
|
||||
- 目标:用最小改动快速交付正确、可维护、可回归的业务结果
|
||||
- 边界:只解决当前需求,不做与需求无关的重构和“顺手优化”
|
||||
- 文档:开始开发前,请先查看 `./.docs/README.md`,并阅读与当前需求相关的文档
|
||||
- 每次完成任务后,进行类型检查、lint检查和format格式化,确保代码质量
|
||||
@@ -8,10 +8,6 @@ ChatLab focuses on analyzing exported data - we don't provide data extraction fe
|
||||
|
||||
Tips: Welcome to join the [ChatLab Community](../other/community.md) to discuss issues and share feedback.
|
||||
|
||||
::: danger Important Notice **When using third-party export tools, please carefully read their official documentation, privacy policies, and security instructions.**
|
||||
|
||||
**ChatLab has no direct or indirect association with the projects listed below. These links are provided solely as technical information for your reference and do not imply any endorsement, guarantee, or warranty of their safety by ChatLab. Users must evaluate and assume all risks associated with using these third-party tools.** :::
|
||||
|
||||
## WhatsApp
|
||||
|
||||
For WhatsApp, we currently support the official "Export Chat" feature.
|
||||
|
||||
@@ -2,16 +2,6 @@
|
||||
|
||||
歡迎加入社群取得最新進展、回饋問題,或透過郵箱聯繫開發者。
|
||||
|
||||
## 微信群
|
||||
|
||||
<WeChatGroupFlow />
|
||||
|
||||
## QQ 群
|
||||
|
||||
> **注意:QQ群僅討論 QQ 聊天記錄分析相關的話題,其他聊天軟體的問題不提供解答。**
|
||||
|
||||
群號:**1070511173**
|
||||
|
||||
## Discord
|
||||
|
||||
[點擊邀請連結](https://discord.gg/zWZnxNtDNz) 加入討論組
|
||||
|
||||
@@ -2,4 +2,80 @@
|
||||
outline: deep
|
||||
---
|
||||
|
||||
<HowToExportCNDoc />
|
||||
# 匯出聊天記錄
|
||||
|
||||
ChatLab 專注於對已匯出數據的分析,我們不提供抓取數據的功能。您需要先使用官方功能或開源社群的第三方工具,將聊天記錄匯出後,再匯入 ChatLab 進行分析。
|
||||
|
||||
Tips:歡迎訪問 [加入社群](/cn/other/community.html),討論問題以及溝通需求。
|
||||
|
||||
## WhatsApp
|
||||
|
||||
對於 WhatsApp, 目前已適配官方提供的”匯出聊天”功能。
|
||||
|
||||
目前已相容中文語言和英文語言的匯出,如有其他語言需求,請聯繫開發者。
|
||||
|
||||
- **匯出方式**:
|
||||
1. 打開 WhatsApp,進入想要匯出的對話。
|
||||
2. 點擊頂部聯絡人名稱 -> 匯出聊天 (Export Chat)。
|
||||
3. 選擇”不附加媒體”。
|
||||
- **格式**:將匯出後的 `.zip` 包解壓出其中的 `txt` 檔案,將 `txt` 檔案拖入 ChatLab 即可。
|
||||
|
||||
## Discord
|
||||
|
||||
對於 Discord,目前已適配 **DiscordChatExporter** 匯出的 json 格式。
|
||||
|
||||
- **項目地址**:[https://github.com/Tyrrrz/DiscordChatExporter](https://github.com/Tyrrrz/DiscordChatExporter)
|
||||
- **支援平台**:Windows / macOS / Linux
|
||||
- **使用教程**:參考項目 README。
|
||||
- **提示**:請務必選擇匯出格式為 **JSON**,以便 ChatLab 正確解析。
|
||||
|
||||
## Instagram
|
||||
|
||||
對於 Instagram,目前已適配官方提供的匯出功能。
|
||||
|
||||
- **匯出方式**:
|
||||
1. 打開 Instagram 應用或網頁版,進入「設定」。
|
||||
2. 點擊「帳戶中心」->「你的資訊和權限」->「下載你的資訊」。
|
||||
3. 選擇「部分資訊」,然後勾選「訊息」。
|
||||
4. 選擇格式為 **JSON**,日期範圍選擇「所有時間」。
|
||||
5. 點擊「提交請求」,等待 Instagram 處理完成後下載。
|
||||
- **格式**:將下載的壓縮包解壓後,找到 `your_instagram_activity/messages/inbox/` 目錄下對應聊天的 `message_1.json` 檔案,拖入 ChatLab 即可。
|
||||
- **提示**:如果對話內容較多,可能會有多個 `message_*.json` 檔案,建議逐一匯入。
|
||||
|
||||
## LINE
|
||||
|
||||
對於 LINE,目前已適配官方提供的聊天記錄匯出功能。
|
||||
|
||||
- **匯出方式**:
|
||||
1. 打開 LINE,進入想要匯出的對話。
|
||||
2. 移動端:點擊聊天右上角選單 -> 設定 -> 匯出聊天記錄。
|
||||
3. 桌面端(Windows / macOS):進入 Chats,打開對應聊天後,點擊右上角選單 -> Save chat。
|
||||
4. 保存或分享匯出的文本檔案。
|
||||
- **格式**:將匯出的 `.txt` 檔案直接拖入 ChatLab 即可。
|
||||
- **提示**:LINE 官方說明中提到,桌面端僅會保存當前已加載並顯示在聊天視窗中的訊息。
|
||||
|
||||
## iMessage
|
||||
|
||||
計劃相容 https://github.com/ReagentX/imessage-exporter 該項目匯出的 json 格式
|
||||
|
||||
不過目前開發者沒有數據樣本用來測試,如果您有迫切的需求,歡迎提供脫敏後的數據樣本,我會第一時間支援。
|
||||
|
||||
## Q&A:飛書/企微/千牛等的聊天記錄能分析嗎?
|
||||
|
||||
針對各種聊天分析的需求,統一回覆:
|
||||
|
||||
ChatLab 的功能是 **對已匯出的固定文本格式的聊天記錄進行分析**,但前提是**您已經透過合法合規的管道匯出了聊天記錄**。
|
||||
|
||||
如果您有一定的技術基礎,可以嘗試使用 **AI 輔助轉換** 的方式,將您的數據轉換為標準格式。詳情請查看 [AI 輔助轉換指南](/cn/standard/ai-converter.html)。
|
||||
|
||||
此外,如果您是開發者,並已支援了其他聊天應用的聊天記錄匯出,歡迎[相容 ChatLab 格式](/cn/standard/chatlab-format.html),我會將您的 Github 連結加到這裡。
|
||||
|
||||
## ⚠️ 法律與安全聲明
|
||||
|
||||
在嘗試分析上述應用的數據前,請務必知曉:
|
||||
|
||||
- **合法授權原則**:您僅可處理您**本人參與**的聊天記錄。若涉及他人隱私,請務必確保已獲得相關人員的知情同意。
|
||||
- **禁止非法用途**:嚴禁將本軟體用於竊取、監控或分析未經授權的他人隱私,或用於任何侵犯他人權益的行為。
|
||||
- **合規性自負**:從第三方平台取得數據的行為屬於您的個人行為。若因分析行為違反了原始數據來源平台的服務條款而導致帳號受限或其他後果,ChatLab 不承擔任何責任。
|
||||
- **禁止商用**:嚴禁任何個人或機構將本軟體或分析結果用於任何形式的商業盈利行為。
|
||||
- **結果準確性**:軟體生成的分析結果可能存在錯誤或”幻覺”,僅供技術交流參考,不應作為法律證據或決策依據。
|
||||
@@ -59,13 +59,16 @@ export function getJieba(dictType: DictType = 'default'): JiebaInstance {
|
||||
const { Jieba } = require('@node-rs/jieba')
|
||||
|
||||
const diskDict = tryLoadDictFromDisk(effectiveType)
|
||||
if (!diskDict) {
|
||||
throw new Error(`Dict file not found for: ${effectiveType}. Please ensure the dictionary has been downloaded.`)
|
||||
let instance: JiebaInstance
|
||||
if (diskDict) {
|
||||
instance = Jieba.withDict(diskDict)
|
||||
console.log(`[NLP] jieba dict loaded: ${effectiveType} (${diskDict.length} bytes)`)
|
||||
} else {
|
||||
// 词库缺失时仍保留 jieba 能力,避免 FTS 退化为空格切分。
|
||||
instance = new Jieba()
|
||||
console.warn(`[NLP] jieba dict missing: ${effectiveType}, fallback to built-in tokenizer`)
|
||||
}
|
||||
|
||||
const instance: JiebaInstance = Jieba.withDict(diskDict)
|
||||
console.log(`[NLP] jieba dict loaded: ${effectiveType} (${diskDict.length} bytes)`)
|
||||
|
||||
jiebaInstances.set(effectiveType, instance)
|
||||
return instance
|
||||
} catch (error) {
|
||||
|
||||
Vendored
+1
-1
@@ -899,7 +899,7 @@ interface NetworkApi {
|
||||
}
|
||||
|
||||
// NLP API 类型 - 自然语言处理功能
|
||||
type SupportedLocale = 'zh-CN' | 'en-US'
|
||||
type SupportedLocale = 'zh-CN' | 'en-US' | 'zh-TW' | 'ja-JP'
|
||||
|
||||
/** 词性过滤模式 */
|
||||
type PosFilterMode = 'all' | 'meaningful' | 'custom'
|
||||
|
||||
@@ -244,6 +244,9 @@ const KEYWORD_COLORS = ['#6366f1', '#ec4899', '#f97316', '#22c55e', '#3b82f6', '
|
||||
|
||||
<!-- 第二行:独特词汇数 -->
|
||||
<div class="flex items-baseline gap-x-1.5">
|
||||
<span class="text-xl font-medium text-gray-700 dark:text-gray-300">
|
||||
{{ t('quotes.topicProfile.heroMiddleSecond') }}
|
||||
</span>
|
||||
<span class="font-black text-3xl text-pink-500 dark:text-pink-400">
|
||||
{{ uniqueWords.toLocaleString() }}
|
||||
</span>
|
||||
|
||||
@@ -123,8 +123,9 @@ const downloadingDictId = ref<string | null>(null)
|
||||
const showDictPromptModal = ref(false)
|
||||
const DICT_PROMPT_DISMISSED_KEY = 'chatlab_zhTW_dict_prompt_dismissed'
|
||||
|
||||
const locale = computed(() => settingsStore.locale as 'zh-CN' | 'en-US')
|
||||
const locale = computed(() => settingsStore.locale as 'zh-CN' | 'en-US' | 'zh-TW' | 'ja-JP')
|
||||
const isTraditionalChinese = computed(() => settingsStore.locale === 'zh-TW')
|
||||
const requiresChineseDict = computed(() => locale.value.startsWith('zh'))
|
||||
|
||||
const dictOptions = computed(() => {
|
||||
return dictList.value
|
||||
@@ -138,6 +139,7 @@ const dictOptions = computed(() => {
|
||||
const hasAnyDict = computed(() => {
|
||||
return dictList.value.some((d) => d.downloaded)
|
||||
})
|
||||
const canAnalyzeWithoutDictBlocking = computed(() => !requiresChineseDict.value || hasAnyDict.value)
|
||||
|
||||
const undownloadedDicts = computed(() => {
|
||||
return dictList.value.filter((d) => !d.downloaded)
|
||||
@@ -245,7 +247,7 @@ async function loadPosTagDefinitions() {
|
||||
|
||||
// 加载话题迷你词云数据(固定词性过滤)
|
||||
async function loadTopicMiniWords() {
|
||||
if (!props.sessionId || !hasAnyDict.value) return
|
||||
if (!props.sessionId || !canAnalyzeWithoutDictBlocking.value) return
|
||||
try {
|
||||
const result = await window.nlpApi.getWordFrequency({
|
||||
sessionId: props.sessionId,
|
||||
@@ -273,7 +275,7 @@ async function loadTopicMiniWords() {
|
||||
|
||||
// 加载词频数据
|
||||
async function loadWordFrequency() {
|
||||
if (!props.sessionId || !hasAnyDict.value) return
|
||||
if (!props.sessionId || !canAnalyzeWithoutDictBlocking.value) return
|
||||
|
||||
isLoading.value = true
|
||||
try {
|
||||
@@ -390,7 +392,7 @@ onMounted(async () => {
|
||||
<div class="main-content mx-auto max-w-[920px] space-y-6 p-6">
|
||||
<!-- 需要下载词库(全屏提示) -->
|
||||
<div
|
||||
v-if="!hasAnyDict"
|
||||
v-if="requiresChineseDict && !hasAnyDict"
|
||||
class="flex h-64 flex-col items-center justify-center gap-4 rounded-lg border border-dashed border-gray-300 dark:border-gray-600"
|
||||
>
|
||||
<UIcon name="i-heroicons-arrow-down-tray" class="text-4xl text-gray-400" />
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
},
|
||||
"tabs": {
|
||||
"overview": "Overview",
|
||||
"view": "View",
|
||||
"view": "Insights",
|
||||
"ranking": "Rankings",
|
||||
"groupQuotes": "Quotes",
|
||||
"quotes": "Quotes",
|
||||
@@ -53,6 +53,7 @@
|
||||
"subTabs": {
|
||||
"view": {
|
||||
"message": "Messages",
|
||||
"topic": "Topics",
|
||||
"interaction": "Interactions",
|
||||
"ranking": "Rankings",
|
||||
"relationship": "Relationship"
|
||||
|
||||
@@ -139,7 +139,8 @@
|
||||
"dateAll": "All messages",
|
||||
"dateNow": "Present",
|
||||
"heroPrefix": "Analyzed",
|
||||
"heroMiddle": "messages, yielding",
|
||||
"heroMiddle": "messages,",
|
||||
"heroMiddleSecond": "yielding",
|
||||
"heroSuffix": "unique words",
|
||||
"topTopicsPrefix": "You love talking about:",
|
||||
"topKeywords": "Top Keywords",
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
},
|
||||
"tabs": {
|
||||
"overview": "概要",
|
||||
"view": "閲覧",
|
||||
"view": "インサイト",
|
||||
"ranking": "ランキング",
|
||||
"groupQuotes": "名言集",
|
||||
"quotes": "名言集",
|
||||
@@ -53,6 +53,7 @@
|
||||
"subTabs": {
|
||||
"view": {
|
||||
"message": "メッセージ",
|
||||
"topic": "トピック",
|
||||
"interaction": "インタラクション分析",
|
||||
"ranking": "ランキング",
|
||||
"relationship": "関係"
|
||||
|
||||
@@ -140,6 +140,7 @@
|
||||
"dateNow": "現在まで",
|
||||
"heroPrefix": "",
|
||||
"heroMiddle": "件のメッセージを分析し、",
|
||||
"heroMiddleSecond": "その結果、",
|
||||
"heroSuffix": "個のユニークな単語が見つかりました",
|
||||
"topTopicsPrefix": "よく話すトピック:",
|
||||
"topKeywords": "人気キーワード",
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
},
|
||||
"tabs": {
|
||||
"overview": "总览",
|
||||
"view": "视图",
|
||||
"view": "洞察",
|
||||
"ranking": "榜单",
|
||||
"groupQuotes": "语录",
|
||||
"quotes": "语录",
|
||||
@@ -53,6 +53,7 @@
|
||||
"subTabs": {
|
||||
"view": {
|
||||
"message": "消息",
|
||||
"topic": "话题",
|
||||
"interaction": "互动分析",
|
||||
"ranking": "榜单",
|
||||
"relationship": "关系"
|
||||
|
||||
@@ -139,7 +139,8 @@
|
||||
"dateAll": "全部消息",
|
||||
"dateNow": "至今",
|
||||
"heroPrefix": "共分析了",
|
||||
"heroMiddle": "条消息,产生了",
|
||||
"heroMiddle": "条消息,",
|
||||
"heroMiddleSecond": "产生了",
|
||||
"heroSuffix": "个不同词汇",
|
||||
"topTopicsPrefix": "你们最爱聊:",
|
||||
"topKeywords": "热门关键词",
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
},
|
||||
"tabs": {
|
||||
"overview": "總覽",
|
||||
"view": "檢視",
|
||||
"view": "洞察",
|
||||
"ranking": "榜單",
|
||||
"groupQuotes": "金句",
|
||||
"quotes": "金句",
|
||||
@@ -53,6 +53,7 @@
|
||||
"subTabs": {
|
||||
"view": {
|
||||
"message": "訊息",
|
||||
"topic": "話題",
|
||||
"interaction": "互動分析",
|
||||
"ranking": "榜單",
|
||||
"relationship": "關係"
|
||||
|
||||
@@ -139,7 +139,8 @@
|
||||
"dateAll": "全部訊息",
|
||||
"dateNow": "至今",
|
||||
"heroPrefix": "共分析了",
|
||||
"heroMiddle": "則訊息,產生了",
|
||||
"heroMiddle": "則訊息,",
|
||||
"heroMiddleSecond": "產生了",
|
||||
"heroSuffix": "個不同詞彙",
|
||||
"topTopicsPrefix": "你們最愛聊:",
|
||||
"topKeywords": "熱門關鍵詞",
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
import { ref, computed } from 'vue'
|
||||
import { useI18n } from 'vue-i18n'
|
||||
import { SubTabs } from '@/components/UI'
|
||||
import { CatchphraseTab, HotRepeatTab, KeywordAnalysis, WordcloudTab } from '@/components/analysis/quotes'
|
||||
import { CatchphraseTab, HotRepeatTab, KeywordAnalysis } from '@/components/analysis/quotes'
|
||||
|
||||
const { t } = useI18n()
|
||||
|
||||
@@ -18,7 +18,6 @@ const props = defineProps<{
|
||||
|
||||
// 子 Tab 配置
|
||||
const subTabs = computed(() => [
|
||||
{ id: 'wordcloud', label: t('analysis.subTabs.quotes.wordcloud'), icon: 'i-heroicons-cloud' },
|
||||
{ id: 'hot-repeat', label: t('analysis.subTabs.quotes.hotRepeat'), icon: 'i-heroicons-fire' },
|
||||
{
|
||||
id: 'catchphrase',
|
||||
@@ -28,7 +27,7 @@ const subTabs = computed(() => [
|
||||
{ id: 'keyword', label: t('analysis.subTabs.quotes.keywordAnalysis'), icon: 'i-heroicons-magnifying-glass' },
|
||||
])
|
||||
|
||||
const activeSubTab = ref('wordcloud')
|
||||
const activeSubTab = ref('hot-repeat')
|
||||
</script>
|
||||
|
||||
<template>
|
||||
@@ -53,13 +52,6 @@ const activeSubTab = ref('wordcloud')
|
||||
:time-filter="props.timeFilter"
|
||||
/>
|
||||
|
||||
<!-- 词云分析 -->
|
||||
<WordcloudTab
|
||||
v-else-if="activeSubTab === 'wordcloud'"
|
||||
:session-id="props.sessionId"
|
||||
:time-filter="props.timeFilter"
|
||||
/>
|
||||
|
||||
<!-- 关键词分析 -->
|
||||
<div v-else-if="activeSubTab === 'keyword'" class="main-content mx-auto max-w-3xl p-6">
|
||||
<KeywordAnalysis :session-id="props.sessionId" :time-filter="props.timeFilter" />
|
||||
|
||||
@@ -8,6 +8,7 @@ import InteractionView from '@openchatlab/chart-interaction/InteractionView.vue'
|
||||
import RankingView from '@openchatlab/chart-ranking/RankingView.vue'
|
||||
import Relationships from './view/Relationships.vue'
|
||||
import ClusterView from '@openchatlab/chart-cluster/ClusterView.vue'
|
||||
import { WordcloudTab } from '@/components/analysis/quotes'
|
||||
import { isFeatureSupported, type LocaleType } from '@/i18n'
|
||||
|
||||
const { t, locale } = useI18n()
|
||||
@@ -27,6 +28,7 @@ const props = defineProps<{
|
||||
const subTabs = computed(() => {
|
||||
const tabs = [
|
||||
{ id: 'message', label: t('analysis.subTabs.view.message'), icon: 'i-heroicons-chat-bubble-left-right' },
|
||||
{ id: 'topic', label: t('analysis.subTabs.view.topic'), icon: 'i-heroicons-cloud' },
|
||||
{ id: 'interaction', label: t('analysis.subTabs.view.interaction'), icon: 'i-heroicons-arrows-right-left' },
|
||||
{ id: 'relationships', label: t('analysis.subTabs.member.relationships'), icon: 'i-heroicons-heart' },
|
||||
{ id: 'cluster', label: t('analysis.subTabs.member.cluster'), icon: 'i-heroicons-user-group' },
|
||||
@@ -55,7 +57,7 @@ const viewTimeFilter = computed(() => ({
|
||||
<!-- 子 Tab 导航(右侧插槽放成员筛选) -->
|
||||
<SubTabs v-model="activeSubTab" :items="subTabs" persist-key="groupViewTab">
|
||||
<template #right>
|
||||
<UserSelect v-model="selectedMemberId" :session-id="props.sessionId" />
|
||||
<UserSelect v-if="activeSubTab !== 'topic'" v-model="selectedMemberId" :session-id="props.sessionId" />
|
||||
</template>
|
||||
</SubTabs>
|
||||
|
||||
@@ -68,6 +70,11 @@ const viewTimeFilter = computed(() => ({
|
||||
:session-name="props.sessionName"
|
||||
:time-filter="viewTimeFilter"
|
||||
/>
|
||||
<WordcloudTab
|
||||
v-else-if="activeSubTab === 'topic'"
|
||||
:session-id="props.sessionId"
|
||||
:time-filter="props.timeFilter"
|
||||
/>
|
||||
<InteractionView
|
||||
v-else-if="activeSubTab === 'interaction'"
|
||||
:session-id="props.sessionId"
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
import { ref, computed } from 'vue'
|
||||
import { useI18n } from 'vue-i18n'
|
||||
import { SubTabs } from '@/components/UI'
|
||||
import { CatchphraseTab, KeywordAnalysis, WordcloudTab } from '@/components/analysis/quotes'
|
||||
import { CatchphraseTab, KeywordAnalysis } from '@/components/analysis/quotes'
|
||||
|
||||
const { t } = useI18n()
|
||||
|
||||
@@ -16,9 +16,8 @@ const props = defineProps<{
|
||||
timeFilter?: TimeFilter
|
||||
}>()
|
||||
|
||||
// 子 Tab 配置(私聊:词云、口头禅、关键词分析)
|
||||
// 子 Tab 配置(私聊:口头禅、关键词分析)
|
||||
const subTabs = computed(() => [
|
||||
{ id: 'wordcloud', label: t('analysis.subTabs.quotes.wordcloud'), icon: 'i-heroicons-cloud' },
|
||||
{
|
||||
id: 'catchphrase',
|
||||
label: t('analysis.subTabs.quotes.catchphrase'),
|
||||
@@ -27,7 +26,7 @@ const subTabs = computed(() => [
|
||||
{ id: 'keyword', label: t('analysis.subTabs.quotes.keywordAnalysis'), icon: 'i-heroicons-magnifying-glass' },
|
||||
])
|
||||
|
||||
const activeSubTab = ref('wordcloud')
|
||||
const activeSubTab = ref('catchphrase')
|
||||
</script>
|
||||
|
||||
<template>
|
||||
@@ -45,13 +44,6 @@ const activeSubTab = ref('wordcloud')
|
||||
:time-filter="props.timeFilter"
|
||||
/>
|
||||
|
||||
<!-- 词云分析 -->
|
||||
<WordcloudTab
|
||||
v-else-if="activeSubTab === 'wordcloud'"
|
||||
:session-id="props.sessionId"
|
||||
:time-filter="props.timeFilter"
|
||||
/>
|
||||
|
||||
<!-- 关键词分析 -->
|
||||
<div v-else-if="activeSubTab === 'keyword'" class="main-content mx-auto max-w-3xl p-6">
|
||||
<KeywordAnalysis :session-id="props.sessionId" :time-filter="props.timeFilter" />
|
||||
|
||||
@@ -5,6 +5,7 @@ import { SubTabs } from '@/components/UI'
|
||||
import UserSelect from '@/components/common/UserSelect.vue'
|
||||
import MessageView from '@openchatlab/chart-message/MessageView.vue'
|
||||
import RelationshipView from './view/RelationshipView.vue'
|
||||
import { WordcloudTab } from '@/components/analysis/quotes'
|
||||
|
||||
const { t } = useI18n()
|
||||
|
||||
@@ -22,6 +23,7 @@ const props = defineProps<{
|
||||
const subTabs = computed(() => [
|
||||
{ id: 'relationship', label: t('analysis.subTabs.view.relationship'), icon: 'i-heroicons-heart' },
|
||||
{ id: 'message', label: t('analysis.subTabs.view.message'), icon: 'i-heroicons-chat-bubble-left-right' },
|
||||
{ id: 'topic', label: t('analysis.subTabs.view.topic'), icon: 'i-heroicons-cloud' },
|
||||
])
|
||||
|
||||
const activeSubTab = ref('relationship')
|
||||
@@ -59,6 +61,11 @@ const viewTimeFilter = computed(() => ({
|
||||
:session-id="props.sessionId"
|
||||
:time-filter="props.timeFilter"
|
||||
/>
|
||||
<WordcloudTab
|
||||
v-else-if="activeSubTab === 'topic'"
|
||||
:session-id="props.sessionId"
|
||||
:time-filter="props.timeFilter"
|
||||
/>
|
||||
</Transition>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
Reference in new issue
Block a user