Pārlūkot izejas kodu

perf: 优化DialogWrap.vue组件

1. 新增 DocRefItem.vue 组件,拆离文档引用底部文档展示的效果
2. 将dialogList列表处理方法提出
3. 移除一部分冗余的注释信息
zhupei 1 gadu atpakaļ
vecāks
revīzija
2c1d307602

+ 72 - 66
src/components/DialogWrap.vue

@@ -12,13 +12,6 @@
         </footer>
       </div>
 
-      <!-- <div class="section-suggestions">
-        <div :class="['section-suggestion', readonly ? 'disabled' : '']" v-for="(suggestion, key) in suggestions"
-          :key="key" @click="selectSuggestion(suggestion)">
-          {{ suggestion }}<icon-arrow-right />
-        </div>
-      </div> -->
-
       <Suggestion :suggestions="suggestions" :readonly="readonly"/>
 
       <div class="dialog-list" v-if="dialogList.length > 0">
@@ -36,7 +29,6 @@
           </div>
 
           <div class="dialog-footer" v-if="item?.question">
-            <!-- <p style="margin-top: 0" data-question-content="------">{{ item.question }}</p> -->
             <Question 
               :question="item.question"                 
               :index="key" 
@@ -65,6 +57,7 @@
 
           <div class="dialog-footer" v-else-if="item?.capacity"
             :style="{ display: dialogConfig.type === 'paper' ? 'inline-block' : 'block' }">
+
             <div v-if="type === 'knowledge'" @click="openCapacity(key)"
               :class="[readonly || item.capacity.status === 'loading' ? 'disabled' : '']">
               <a-spin :size="18" v-if="item.capacity.status === 'loading'" />
@@ -74,6 +67,7 @@
               <icon-caret-right size="18" v-if="item.capacity.status === 'loaded' && !menuList[key]?.open" />
               <icon-caret-down size="18" v-if="item.capacity.status === 'loaded' && menuList[key]?.open" />
             </div>
+
             <div v-else v-show="item.capacity.status === 'loading'"
               :class="[readonly || item.capacity.status === 'loading' ? 'disabled' : '']">
               <a-spin :size="18" />
@@ -104,6 +98,7 @@
                     <icon-caret-down size="12" v-if="documentKey === menuList[key].documentOpenIndex" />
                     <icon-caret-right size="12" v-else />
                   </div>
+
                   <div v-show="documentKey === menuList[key].documentOpenIndex">
                     <p v-for="(item, index) in document.list" :key="index">
                       <span>{{ item.title }}</span>
@@ -130,7 +125,6 @@
                   <em>DOCX,13.19KB</em>
                 </span>
               </span>
-              <!-- <span v-else v-html="getHTML(item.answer)"></span> -->
 
               <Answer v-else 
                 :answer="item.answer" 
@@ -145,8 +139,6 @@
           </div>
 
           <div class="dialog-footer" v-else>
-            <!-- <span v-html="getHTML(item.answer)"></span> -->
-
             <Answer 
               :answer="item.answer" 
               :index="key" 
@@ -168,7 +160,14 @@
             </header>
 
             <section>
-              <div v-for="(knowledge, knowledgeIndex) in item.reference" :key="knowledgeIndex">
+              <DocRefItem 
+                v-for="(knowledge, knowledgeIndex) in item.reference" 
+                :key="knowledgeIndex" 
+                :knowledge="knowledge" 
+                :knowledgeIndex="knowledgeIndex"
+              />
+
+              <!-- <div v-for="(knowledge, knowledgeIndex) in item.reference" :key="knowledgeIndex">
                 <a-popover :title="knowledge.doc_name" position="left">
                   <div @click="openDocuementPage(knowledge)">
                     <span>{{ knowledgeIndex + 1 }}</span>
@@ -188,13 +187,11 @@
                             }
                               ">{{ contentIndex + 1 }}</span>
                         </p>
-                        <!-- TODO详情暂时注释 -->
-                        <!-- <p @click="goKnowledge(knowledge.id)">查看详情></p> -->
                       </div>
                     </div>
                   </template>
                 </a-popover>
-              </div>
+              </div> -->
             </section>
           </div>
 
@@ -268,7 +265,7 @@ import { defineComponent, ref, onBeforeUnmount, onMounted, reactive, nextTick, i
 import formatAnwserString from './answer-effect/format-anwser-string';
 import initTempHistory, {getChatIdFromUrl} from './answer-effect/temp-history';
 
-import { getDocumentUrl } from '../ajax/document';
+// import { getDocumentUrl } from '../ajax/document';
 
 import Question from './dialog-wrap/Question.vue';
 import Suggestion from './dialog-wrap/Suggestion.vue';
@@ -278,6 +275,9 @@ import Answer from './dialog-wrap/Answer.vue';
 import {huituSetTempImageIndex} from './dialog-wrap/temp-image'
 
 import generateClientUniqueId from './dialog-wrap/generate-client-unique-id';
+import formatDialogItem from './dialog-wrap/format-dialog-item';
+
+import DocRefItem from './dialog-wrap/DocRefItem.vue';
 
 export default defineComponent({
   components: {
@@ -286,7 +286,9 @@ export default defineComponent({
     Suggestion,
 
     Question,
-    Answer
+    Answer,
+
+    DocRefItem
   },
   props: [
     "open", 
@@ -324,46 +326,50 @@ export default defineComponent({
     const tempHistory = initTempHistory();
 
     const list = props.list.map((item, index) => {
-      return {
-        /**
-         * 客户端生成的ID
-         * 此数据作为列表唯一的key
-         */
-        client_gen_id: generateClientUniqueId(JSON.stringify(item)),
-
-        answer: item.answer && replaceCode(item.answer, index),
-        question: item.question,
-        // 如果有引用
-        reference: (item.reference && item.reference.chunks && item.reference.doc_aggs) ? item.reference.doc_aggs.map(reference => {
-          return {
-            id: reference.doc_id,
-            doc_name: reference.doc_name,
-            page: 0,
-            content_ltks: [item.reference.chunks.find(chunk => chunk.doc_id == reference.doc_id).content_ltks]
-          }
-        }) : [],
-
-        // 完整的引用数据: pdf文档引用效果需要使用此数据
-        fullRefference: item.reference,
-        // 合法可用的图片地址
-        fullImageUrls: (() => {
-          if(item.images){
-            return item.images;
-          }else{
-            return [];
-          }
-        })(),
-
-        // 如果有文件处理完拿第一个,后续有变动再改
-        file: (item.files && item.files.length > 0) ? item.files.map(item => {
-          const port = window.location.port ? `:${window.location.port}` : '';
-          return {
-            file_type: 'word',
-            file_name: item.file_name,
-            file_url: `http://${window.location.hostname}${port}${item.file_url}`,
-          }
-        })[0] : null,
-      }
+      // const client_id = generateClientUniqueId(JSON.stringify(item));
+
+      return formatDialogItem(item, index);
+
+      // return {
+      //   /**
+      //    * 客户端生成的ID
+      //    * 此数据作为列表唯一的key
+      //    */
+      //   client_gen_id: client_id,
+
+      //   answer: item.answer && replaceCode(item.answer, index),
+      //   question: item.question,
+      //   // 如果有引用
+      //   reference: (item.reference && item.reference.chunks && item.reference.doc_aggs) ? item.reference.doc_aggs.map(reference => {
+      //     return {
+      //       id: reference.doc_id,
+      //       doc_name: reference.doc_name,
+      //       page: 0,
+      //       content_ltks: [item.reference.chunks.find(chunk => chunk.doc_id == reference.doc_id).content_ltks]
+      //     }
+      //   }) : [],
+
+      //   // 完整的引用数据: pdf文档引用效果需要使用此数据
+      //   fullRefference: item.reference,
+      //   // 合法可用的图片地址
+      //   fullImageUrls: (() => {
+      //     if(item.images){
+      //       return item.images;
+      //     }else{
+      //       return [];
+      //     }
+      //   })(),
+
+      //   // 如果有文件处理完拿第一个,后续有变动再改
+      //   file: (item.files && item.files.length > 0) ? item.files.map(item => {
+      //     const port = window.location.port ? `:${window.location.port}` : '';
+      //     return {
+      //       file_type: 'word',
+      //       file_name: item.file_name,
+      //       file_url: `http://${window.location.hostname}${port}${item.file_url}`,
+      //     }
+      //   })[0] : null,
+      // }
     });
 
     const dialogList = reactive(list || []);
@@ -456,16 +462,16 @@ export default defineComponent({
     const goKnowledge = () => {
       // emit("go-document");
     };
-    // 点击文档,打开新页面
-    const openDocuementPage = (knowledge) => {
-      const doc_name = knowledge.doc_name;
-      const doc_id = knowledge.id;
+    // // 点击文档,打开新页面
+    // const openDocuementPage = (knowledge) => {
+    //   const doc_name = knowledge.doc_name;
+    //   const doc_id = knowledge.id;
 
-      // const pdf_url = `http://192.168.20.119:11080/v1/document/get/${doc_id}`;
-      const pdf_url = getDocumentUrl(doc_id);
+    //   // const pdf_url = `http://192.168.20.119:11080/v1/document/get/${doc_id}`;
+    //   const pdf_url = getDocumentUrl(doc_id);
 
-      window.open(pdf_url);
-    }
+    //   window.open(pdf_url);
+    // }
 
     const addLoading = (data) => {
       const mockData = DOCUMENT_RESULT;
@@ -899,7 +905,7 @@ export default defineComponent({
       downloadFile,
 
       openDocument,
-      openDocuementPage,
+      // openDocuementPage,
 
       show_info_btns
     };

+ 129 - 0
src/components/dialog-wrap/DocRefItem.vue

@@ -0,0 +1,129 @@
+<template>
+  <div>
+    <a-popover :title="knowledge.doc_name" position="left">
+        <div @click="openDocuementPage(knowledge)" class="doc-ref-container">
+            <span class="doc-ref-index">{{ knowledgeIndex + 1 }}</span>
+            <span class="doc-ref-label">{{ knowledge.doc_name }}</span>
+        </div>
+        <template #content>
+            <div class="knowledge-detail">
+                <div class="knowledge-content">
+                {{ knowledge.content_ltks }}
+                </div>
+                <div class="knowledge-footer">
+                <p>检索片段</p>
+                <p>
+                    <span v-for="(content, contentIndex) in knowledge.content_ltks" :key="contentIndex"
+                    :class="{ active: knowledge.page === contentIndex }" @click="() => {
+                        knowledge.page = contentIndex;
+                    }
+                        ">{{ contentIndex + 1 }}</span>
+                </p>
+                <!-- TODO详情暂时注释 -->
+                <!-- <p @click="goKnowledge(knowledge.id)">查看详情></p> -->
+                </div>
+            </div>
+        </template>
+    </a-popover>
+</div>
+</template>
+<script setup>
+import { defineComponent, ref, onBeforeUnmount, onMounted, reactive, nextTick, inject } from "vue";
+
+import { getDocumentUrl } from '../../ajax/document';
+
+const props = defineProps({
+    knowledge: Object,
+    knowledgeIndex: Number
+});
+
+const openDocuementPage = (knowledge) => {
+    const doc_name = knowledge.doc_name;
+    const doc_id = knowledge.id;
+
+    // const pdf_url = `http://192.168.20.119:11080/v1/document/get/${doc_id}`;
+    const pdf_url = getDocumentUrl(doc_id);
+
+    window.open(pdf_url);
+}
+</script>
+<style scoped>
+.knowledge-detail {
+  width: 320px;
+  padding-top: 20px;
+
+  .knowledge-content {
+    height: 300px;
+    overflow-y: auto;
+    line-height: 30px;
+  }
+
+  .knowledge-footer {
+    border-top: 1px solid rgba(229, 229, 229, 1);
+    margin-top: 20px;
+    padding-top: 20px;
+    display: flex;
+    justify-content: space-between;
+    align-items: center;
+
+    p {
+      &:nth-child(1) {
+        opacity: 0.8;
+      }
+
+      &:nth-child(2) {
+        flex: 1;
+        display: flex;
+        justify-content: left;
+        margin: 0 30px;
+
+        >span {
+          margin: 0 5px;
+          cursor: pointer;
+
+          &:hover,
+          &.active {
+            color: #00aea3;
+          }
+        }
+      }
+
+      &:nth-child(3) {
+        font-weight: bold;
+        cursor: pointer;
+
+        &:hover {
+          color: #00aea3;
+        }
+      }
+    }
+  }
+}
+
+.doc-ref-container{
+    height: 40px;
+    display: inline-flex;
+    align-items: center;
+}
+
+.doc-ref-index{
+    display: inline-block;
+    background-color: #00aea333;
+    color: #00aea3;
+    padding: 1px 5px;
+    border-radius: 2px;
+    margin-right: 5px;
+    font-size: 12px;
+
+    /* margin: 0 5px; */
+    cursor: pointer;
+}
+
+.doc-ref-label{
+    /* margin: 0 5px; */
+    cursor: pointer;
+}
+.doc-ref-label:hover{
+    color: #00aea3;
+}
+</style>

+ 1 - 1
src/components/dialog-wrap/Question.vue

@@ -3,7 +3,7 @@
 </template>
 
 <script setup>
-import { ref, onBeforeUnmount, onMounted, reactive, nextTick, inject, computed, watch, useTemplateRef } from "vue";
+import { onMounted, computed, useTemplateRef } from "vue";
 
 import {getTempImageInfo} from './temp-image';
 

+ 51 - 0
src/components/dialog-wrap/format-dialog-item.js

@@ -0,0 +1,51 @@
+import generateClientUniqueId from './generate-client-unique-id';
+
+const replaceCode = (text, index) => {
+    const icon = `  <span class="circle" data-list-index="${index || 0}"></span>`
+    return text.replace(/##\d\$\$/g, icon);
+}
+
+export default function formatDialogItem(item, index) {
+    const client_id = generateClientUniqueId(JSON.stringify(item));
+
+    return {
+        /**
+         * 客户端生成的ID
+         * 此数据作为列表唯一的key
+         */
+        client_gen_id: client_id,
+
+        answer: item.answer && replaceCode(item.answer, index),
+        question: item.question,
+        // 如果有引用
+        reference: (item.reference && item.reference.chunks && item.reference.doc_aggs) ? item.reference.doc_aggs.map(reference => {
+            return {
+                id: reference.doc_id,
+                doc_name: reference.doc_name,
+                page: 0,
+                content_ltks: [item.reference.chunks.find(chunk => chunk.doc_id == reference.doc_id).content_ltks]
+            }
+        }) : [],
+
+        // 完整的引用数据: pdf文档引用效果需要使用此数据
+        fullRefference: item.reference,
+        // 合法可用的图片地址
+        fullImageUrls: (() => {
+            if (item.images) {
+                return item.images;
+            } else {
+                return [];
+            }
+        })(),
+
+        // 如果有文件处理完拿第一个,后续有变动再改
+        file: (item.files && item.files.length > 0) ? item.files.map(item => {
+            const port = window.location.port ? `:${window.location.port}` : '';
+            return {
+                file_type: 'word',
+                file_name: item.file_name,
+                file_url: `http://${window.location.hostname}${port}${item.file_url}`,
+            }
+        })[0] : null,
+    }
+}

+ 0 - 23
src/views/Home.vue

@@ -17,16 +17,6 @@
 
         <div :class="{ 'border-wrap': true, 'border-no-wrap': navId === -2 }" v-else>
           <div>
-            <!-- <header v-if="!showDialog">
-              <div>
-                <img src="@/assets/other/robot.gif" width="52" />
-                <p>
-                  {{ SYSTEM_NAME }}<span>{{ slider.find(item => item.id === navId).title }}</span>
-                </p>
-                <span>{{ slider.find(item => item.id === navId).dialog }}</span>
-              </div>
-            </header> -->
-
             <!-- 项目与功能特色介绍 -->
             <ProjectIntro v-if="!showDialog" :navId="navId" />
 
@@ -44,7 +34,6 @@
               <!-- 智能数据 -->
               <DocumentsmartData v-if="navId === 5 && !showDialog" :agentId="selectId" />
               <!-- 小数绘图 -->
-              <!-- <PicArticle v-if="navId === 6 && !showDialog" :agentId="selectId" /> -->
               <PicArticle v-if="navId === 6 && !showDialog" :agentId="selectId" />
               <!-- 文档出卷 -->
               <DocumentQuestion v-if="navId === 7 && !showDialog" :agentId="selectId" />
@@ -149,21 +138,9 @@
               <a-button :style="{ width: '500px' }" type="primary" @click="continueCombine">开始</a-button>
             </footer>
 
-            <!-- <footer v-if="navId === 6 && !historyMode">
-              <picture-cards />
-              <MessagePicUpload />
-            </footer> -->
-
             <!-- 小数绘图底部输入栏 -->
             <PictureFooter v-if="navId === 6 && !historyMode" :agentId="selectId"/>
 
-            <!-- <a-tooltip :content="closeOthers ? '收起' : '展开'">
-              <div @click="openAll" v-if="navId !== -2">
-                <img src="@/assets/other/open.svg" width="20" v-if="closeOthers" />
-                <img src="@/assets/other/close.svg" width="20" v-else />
-              </div>
-            </a-tooltip> -->
-
             <!-- 侧边栏切换按钮 -->
             <ToggleBtn v-if="navId !== -2" :closeOthers="closeOthers" @toggle="openAll"/>
           </div>