Просмотр исходного кода

Merge remote-tracking branch 'origin/wanzi'

liyanbo 1 месяц назад
Родитель
Сommit
c953eadeaa
2 измененных файлов с 142 добавлено и 109 удалено
  1. 116 99
      src/components/study/SelfDirectedLearning.vue
  2. 26 10
      src/views/AIPage/AIGeneralCourse.vue

+ 116 - 99
src/components/study/SelfDirectedLearning.vue

@@ -15,25 +15,69 @@
             @keyup.enter.exact="doSendMessage(prompt.trim())"
             @keyup.enter.exact="doSendMessage(prompt.trim())"
           ></textarea>
           ></textarea>
           <div class="dropdowns-container">
           <div class="dropdowns-container">
-            <el-select
-              v-for="dropdown in dropdowns"
-              :key="dropdown.key"
-              v-model="dropdown.value"
-              @change="(value) => handleSelect(dropdown.key, value)"
-              filterable
-              class="custom-select"
-            >
+            <!-- 生成主题下拉框 -->
+              <el-select
+                v-model="courseDropdown.value"
+                filterable
+                placeholder=""
+                style="width: 150px"
+                class="custom-select"
+                @visible-change="handleVisibleChange('course', $event)"
+              >
               <template #prefix>
               <template #prefix>
-                <el-icon><component :is="dropdown.icon" /></el-icon>
+                <el-icon><component :is="courseDropdown.icon" /></el-icon>
               </template>
               </template>
-              <el-option
-                v-for="item in dropdown.options"
-                :key="item.value"
-                :label="item.label"
-                :value="item.value"
-                class="provinces_select" 
-              />
-            </el-select>
+                <el-option
+                  v-for="item in courseDropdown.options"
+                  :key="item.value"
+                  :label="item.label"
+                  :value="item.value"
+                  class="provinces_select"
+                  @click="handleSelect('course', item.value)"
+                />
+              </el-select>
+              <!-- 主讲下拉框 -->
+              <el-select
+                v-model="teacherDropdown.value"
+                filterable
+                placeholder=""
+                style="width: 150px"
+                class="custom-select"
+                @visible-change="handleVisibleChange('teacher', $event)"
+              >
+              <template #prefix>
+                <el-icon><component :is="teacherDropdown.icon" /></el-icon>
+              </template>
+                <el-option
+                  v-for="item in teacherDropdown.options"
+                  :key="item.value"
+                  :label="item.label"
+                  :value="item.value"
+                  class="provinces_select"
+                  @click="handleSelect('teacher', item.value)"
+                />
+              </el-select>
+              <!-- 助教下拉框 -->
+              <el-select
+                v-model="assistantDropdown.value"
+                filterable
+                placeholder=""
+                style="width: 150px"
+                class="custom-select"
+                @visible-change="handleVisibleChange('assistant', $event)"
+              >
+              <template #prefix>
+                <el-icon><component :is="assistantDropdown.icon" /></el-icon>
+              </template>
+                <el-option
+                  v-for="item in assistantDropdown.options"
+                  :key="item.value"
+                  :label="item.label"
+                  :value="item.value"
+                  class="provinces_select"
+                  @click="handleSelect('assistant', item.value)"
+                />
+              </el-select>
           </div>
           </div>
           <button class="send-button" :class="{ 'active': prompt.trim().length > 0 && (!showNewContainer || allStepsCompleted) }" @click="doSendMessage(prompt.trim())" :disabled="!prompt.trim().length || (showNewContainer && !allStepsCompleted)">
           <button class="send-button" :class="{ 'active': prompt.trim().length > 0 && (!showNewContainer || allStepsCompleted) }" @click="doSendMessage(prompt.trim())" :disabled="!prompt.trim().length || (showNewContainer && !allStepsCompleted)">
             <Top />
             <Top />
@@ -104,6 +148,8 @@ import {
 import {Message} from "@/utils/message/Message.js";
 import {Message} from "@/utils/message/Message.js";
 import {teacherList} from "@/api/teachers.js";
 import {teacherList} from "@/api/teachers.js";
 
 
+
+
 // 本地数字人列表
 // 本地数字人列表
 const localScriptRoles = ref([])
 const localScriptRoles = ref([])
 
 
@@ -852,31 +898,35 @@ const progressCounters = ref({
 // 计算主讲下拉框选项
 // 计算主讲下拉框选项
 const teacherOptions = computed(() => {
 const teacherOptions = computed(() => {
   const roles = localScriptRoles.value.length > 0 ? localScriptRoles.value : localScriptRoles.value;
   const roles = localScriptRoles.value.length > 0 ? localScriptRoles.value : localScriptRoles.value;
-  return roles.map(role => ({
+  const options = roles.map(role => ({
     label: role.name,
     label: role.name,
     value: role.name
     value: role.name
   }));
   }));
+  return options;
 });
 });
 
 
 // 计算助教下拉框选项
 // 计算助教下拉框选项
 const assistantOptions = computed(() => {
 const assistantOptions = computed(() => {
   const roles = localScriptRoles.value.length > 0 ? localScriptRoles.value : localScriptRoles.value;
   const roles = localScriptRoles.value.length > 0 ? localScriptRoles.value : localScriptRoles.value;
-  return roles.map(role => ({
+  const options = roles.map(role => ({
     label: role.name,
     label: role.name,
     value: role.name
     value: role.name
   }));
   }));
+  return options;
 });
 });
 
 
 // 计算生成主题下拉框选项,基于 lessonList 动态生成
 // 计算生成主题下拉框选项,基于 lessonList 动态生成
 const courseOptions = computed(() => {
 const courseOptions = computed(() => {
   // 提取 lessonList 中的课程名称
   // 提取 lessonList 中的课程名称
   const lessonNames = lessonList.value.map(lesson => lesson.name).join('、');
   const lessonNames = lessonList.value.map(lesson => lesson.name).join('、');
-  return [
+  const options = [
     {
     {
       label: `诗词课(${lessonNames})`,
       label: `诗词课(${lessonNames})`,
       value: '诗词课'
       value: '诗词课'
     }
     }
   ];
   ];
+  console.log('【生成主题下拉框选项】', options);
+  return options;
 });
 });
 
 
 /**
 /**
@@ -903,90 +953,57 @@ const getRoleList = async () => {
 }
 }
 
 
 // 下拉框配置
 // 下拉框配置
-const dropdowns = ref([
-  {
-    key: 'course',
-    value: '生成主题',
-    visible: false,
-    icon: Search,
-    options: courseOptions.value
-  },
-  {
-    key: 'teacher',
-    value: '主讲',
-    visible: false,
-    icon: User,
-    options: teacherOptions.value
-  },
-  {
-    key: 'assistant',
-    value: '助教',
-    visible: false,
-    icon: Memo,
-    options: assistantOptions.value
-  }
-]);
+const courseDropdown = ref({
+  key: 'course',
+  value: '生成主题',
+  visible: false,
+  icon: Search,
+  options: courseOptions.value
+});
+
+const teacherDropdown = ref({
+  key: 'teacher',
+  value: '主讲',
+  visible: false,
+  icon: User,
+  options: teacherOptions.value
+});
+
+const assistantDropdown = ref({
+  key: 'assistant',
+  value: '助教',
+  visible: false,
+  icon: Memo,
+  options: assistantOptions.value
+});
 
 
-// 下拉框配置映射,用于生成内容和正则表达式
-const dropdownConfig = {
-  course: {
-    prefix: '诗词课',
-    default: '诗词课',
-    regex: /诗词课[^,]+/g
-  },
-  teacher: {
-    prefix: '主讲为',
-    default: '主讲',
-    regex: /主讲为[^,]+/g
-  },
-  assistant: {
-    prefix: '助教为',
-    default: '助教',
-    regex: /助教为[^,]+/g
-  }
-};
 
 
 // 处理下拉框选择
 // 处理下拉框选择
 const handleSelect = (key, command) => {
 const handleSelect = (key, command) => {
-  const dropdown = dropdowns.value.find(item => item.key === key);
-  if (dropdown && dropdownConfig[key]) {
-     // 更新下拉框显示值
-    dropdown.value = command;
-    // 如果选择的是主讲,更新selectedMainTeacher
-    if (key === 'teacher') {
-      selectedMainTeacher.value = command;
-    }
-    // 如果选择的是助教,更新selectedAssistants
-    else if (key === 'assistant') {
-      selectedAssistants.value = [command];
-    }
-    // const config = dropdownConfig[key];
-
-    // // 生成新内容,仅当选择的值与默认值不同时添加
-    // const newContent = command === config.default
-    //   ? config.prefix
-    //   : `${config.prefix}${command}`;
-
-    // // 检查输入框中是否已存在该类型的内容
-    // if (config.regex.test(prompt.value)) {
-    //   // 替换已存在的内容
-    //   prompt.value = prompt.value.replace(config.regex, newContent);
-    // } else {
-    //   // 添加到输入框,用逗号隔开
-    //   if (prompt.value.trim()) {
-    //     prompt.value += `, ${newContent}`;
-    //   } else {
-    //     prompt.value = newContent;
-    //   }
-    // }
+  if (key === 'course' && courseDropdown.value) {
+     courseDropdown.value.value = command;
+  }
+  else if (key === 'teacher' && teacherDropdown.value) {
+    teacherDropdown.value.value = command;
+    selectedMainTeacher.value = command;
+  }
+  else if (key === 'assistant' && assistantDropdown.value) {
+    assistantDropdown.value.value = command;
+    selectedAssistants.value = [command];
+    console.log('【助教下拉框选择】', command);
   }
   }
 };
 };
 
 
 // 处理下拉框可见性变化
 // 处理下拉框可见性变化
 const handleVisibleChange = (key, visible) => {
 const handleVisibleChange = (key, visible) => {
-  const dropdown = dropdowns.value.find(item => item.key === key);
-  if (dropdown) {
-    dropdown.visible = visible;
+  if (key === 'course' && courseDropdown.value) {
+    courseDropdown.value.visible = visible;
+  }
+  else if (key === 'teacher' && teacherDropdown.value) {
+    teacherDropdown.value.visible = visible;
+  }
+  else if (key === 'assistant' && assistantDropdown.value) {
+    assistantDropdown.value.visible = visible;
   }
   }
 };
 };
 
 
@@ -1039,11 +1056,11 @@ onMounted(async () => {
   await getRoleList();
   await getRoleList();
 
 
   // 初始化生成主题下拉框选项
   // 初始化生成主题下拉框选项
-  dropdowns.value[0].options = courseOptions.value;
+  courseDropdown.value.options = courseOptions.value;
   // 初始化主讲下拉框选项
   // 初始化主讲下拉框选项
-  dropdowns.value[1].options = teacherOptions.value;
+  teacherDropdown.value.options = teacherOptions.value;
   // 初始化助教下拉框选项
   // 初始化助教下拉框选项
-  dropdowns.value[2].options = assistantOptions.value;
+  assistantDropdown.value.options = assistantOptions.value;
 });
 });
 </script>
 </script>
 
 
@@ -1156,7 +1173,7 @@ onMounted(async () => {
   width: auto;
   width: auto;
   height: rpx(18);
   height: rpx(18);
   font-size: rpx(8);
   font-size: rpx(8);
-  max-width: rpx(80);
+  max-width : rpx ( 80 );
 }
 }
 
 
 .dropdowns-container .custom-select :deep(.el-select__wrapper) {
 .dropdowns-container .custom-select :deep(.el-select__wrapper) {

+ 26 - 10
src/views/AIPage/AIGeneralCourse.vue

@@ -29,6 +29,7 @@
             <el-row class="tac">
             <el-row class="tac">
               <el-col :span="12">
               <el-col :span="12">
                 <el-menu
                 <el-menu
+                  v-if="menuInitialized"
                   :default-active="currentActiveIndex"
                   :default-active="currentActiveIndex"
                   :default-openeds="[currentOpenedMenu]"
                   :default-openeds="[currentOpenedMenu]"
                   :class="{ 'el-menu-vertical-demo': true }"
                   :class="{ 'el-menu-vertical-demo': true }"
@@ -39,7 +40,7 @@
                     v-for="menu in menuList" 
                     v-for="menu in menuList" 
                     :key="menu.id"
                     :key="menu.id"
                     :index="menu.id"
                     :index="menu.id"
-                    @click="showPracticalCourse = menu.isPractical; showAICourse = menu.isAICourse; currentOpenedMenu = menu.id"
+                    @click="handleMenuClick(menu)"
                   >
                   >
                     <template #title>
                     <template #title>
                       <span>{{ menu.title }}</span>
                       <span>{{ menu.title }}</span>
@@ -200,6 +201,8 @@ const menuConfig = [
 const currentActiveIndex = ref('general-1')
 const currentActiveIndex = ref('general-1')
 // 当前打开的菜单
 // 当前打开的菜单
 const currentOpenedMenu = ref('general')
 const currentOpenedMenu = ref('general')
+// 菜单初始化状态
+const menuInitialized = ref(false)
 // 存储选中状态的键名
 // 存储选中状态的键名
 const activeMenuKey = 'aiGeneralCourseActiveMenu'
 const activeMenuKey = 'aiGeneralCourseActiveMenu'
 const activeIndexKey = 'aiGeneralCourseActiveIndex'
 const activeIndexKey = 'aiGeneralCourseActiveIndex'
@@ -251,6 +254,17 @@ const fetchClassOutline = async (classId) => {
   }
   }
 }
 }
 
 
+// 处理菜单点击
+const handleMenuClick = (menu) => {
+  currentOpenedMenu.value = menu.id
+  saveActiveState(menu.id, menu.id)
+  
+  // 如果该菜单下有课程数据,设置默认选中第一项
+  if (menu.data && menu.data.length > 0) {
+    currentActiveIndex.value = menu.id + '-1'
+  }
+}
+
 // 处理下拉菜单选择
 // 处理下拉菜单选择
 const handleGradeSelect = command => {
 const handleGradeSelect = command => {
   selectedGrade.value = command
   selectedGrade.value = command
@@ -265,15 +279,13 @@ const handleGradeSelect = command => {
     localStorage.setItem('selectedGradeId', selectedItem.id)
     localStorage.setItem('selectedGradeId', selectedItem.id)
     // 获取课程大纲
     // 获取课程大纲
     fetchClassOutline(selectedItem.id).then(() => {
     fetchClassOutline(selectedItem.id).then(() => {
-      // 检查是否当前显示的是实操课但没有实操课数据
-      // if (showPracticalCourse.value && ClassOutlineScData.value.length === 0) {
-      //   // 切换回通识课
-      //   showPracticalCourse.value = false
-      //   // 显示提示
-      //   Message().notifyWarning('此版本未开放,敬请期待!', true)
-      //   // 更新localStorage中的状态
-      //   localStorage.setItem('showPracticalCourse', 'false')
-      // }
+      // 数据加载完成后,恢复之前的菜单选中状态
+      const savedMenu = localStorage.getItem(activeMenuKey)
+      const savedIndex = localStorage.getItem(activeIndexKey)
+      if (savedMenu && savedIndex) {
+        currentOpenedMenu.value = savedMenu
+        currentActiveIndex.value = savedIndex
+      }
     })
     })
   }
   }
 }
 }
@@ -325,6 +337,7 @@ const getCourseTitle = index => {
 const pageTitle = ref('返回首页')
 const pageTitle = ref('返回首页')
 onMounted(() => {
 onMounted(() => {
   fetchCtTypes()
   fetchCtTypes()
+  
   // 读取之前保存的选中状态
   // 读取之前保存的选中状态
   const savedMenu = localStorage.getItem(activeMenuKey)
   const savedMenu = localStorage.getItem(activeMenuKey)
   const savedIndex = localStorage.getItem(activeIndexKey)
   const savedIndex = localStorage.getItem(activeIndexKey)
@@ -333,6 +346,9 @@ onMounted(() => {
     currentOpenedMenu.value = savedMenu
     currentOpenedMenu.value = savedMenu
     currentActiveIndex.value = savedIndex
     currentActiveIndex.value = savedIndex
   }
   }
+  
+  // 标记菜单已初始化,触发el-menu重新渲染
+  menuInitialized.value = true