<template>
  <div class="choiceQuestionDetailDialog">
    <div class="content" @click="clickContent(true)" :style="{
      width: slideWidth + 'px',
      height: slideHeight + 'px',
    }">
      <span v-show="false" class="closeIcon" @click.stop="closeSlideIndex()">
        <img src="../../../assets/img/close.png" />
      </span>

      <!-- 选择题 -->
      <div class="c_t45" v-if="workDetail && workDetail.type === '45' && props.showData">
        <div class="c_t45_title">
          <div class="c_title" v-if="props.showData.choiceQuestionListData[props.showData.workIndex]">
            <span>{{
            props.showData.choiceQuestionListData[props.showData.workIndex]
              .teststitle
          }}</span>
            <div class="switch_btn" v-if="props.isCreator && props.roleType == 1">
              <div class="switch">
                <Switch :value="canValue" @update:value="handleCanChange" />
                <span>{{ lang.ssShowResult }}</span>
              </div>
              <!-- <div class="switch">
                <Switch :value="answerValue" @update:value="handleAnswerChange" />
                <span>{{ lang.ssShowAnswer }}</span>
              </div> -->
            </div>
          </div>
          <div class="c_t45_msg" v-if="props.roleType == 1">
            <div>{{ lang.ssAnswerCount }} {{ props.workArray.length }}<span
                v-if="props.unsubmittedStudents.length > 0">/{{ props.workArray.length +
                  props.unsubmittedStudents.length
                }}</span></div>
            <span v-if="props.unsubmittedStudents.length > 0" @click.stop="viewUnsubmittedStudents()">{{
              lang.ssViewSubmitStatus2 }}</span>
          </div>
          <!--<span class="c_t45_t_btn" :class="{'c_t45_t_btn_noActive': props.showData.workIndex <= 0}" @click="changeWorkIndex(0)">{{ lang.ssPrevQ }}</span>-->
          <!--<span class="c_t45_t_btn" :class="{'c_t45_t_btn_noActive': props.showData.workIndex >= props.showData.choiceQuestionListData.length - 1}" @click="changeWorkIndex(1)">{{ lang.ssNextQ }}</span>-->
        </div>
        <img class="c_t45_img" :src="props.showData.choiceQuestionListData[props.showData.workIndex]
          .timuList[0].src
          " v-if="props.showData.choiceQuestionListData[props.showData.workIndex] &&
            props.showData.choiceQuestionListData[props.showData.workIndex]
              .timuList.length > 0
          " @click.stop="previewImageToolRef.previewImage(props.showData.choiceQuestionListData[props.showData.workIndex]
            .timuList[0].src)" />
        <!-- <span class="c_t45_type" v-if="
          props.showData.choiceQuestionListData[props.showData.workIndex]
            .type === '1'
        ">{{ lang.ssSingleSel }}</span>
        <span class="c_t45_type" v-if="
          props.showData.choiceQuestionListData[props.showData.workIndex]
            .type === '2'
        ">{{ lang.ssMultiOpt }}</span> -->
        <!-- <span class="c_t45_type">{{ lang.ssChoiceQuestion }}</span> -->
        <div class="c_t45_echarts" :style="{
          width: slideWidth - 40 + 'px',
        }">
          <div id="echartsArea1" ref="echartsArea1"></div>
        </div>
        <div class="aiAnalysis" v-if="props.workArray.length > 0 && props.roleType == 1">
          <div class="ai_header">
            <div class="ai_title">
              <svg viewBox="0 0 1024 1024" width="200" height="200">
                <path
                  d="M512 170.666667C323.477333 170.666667 170.666667 323.477333 170.666667 512s152.810667 341.333333 341.333333 341.333333 341.333333-152.810667 341.333333-341.333333S700.522667 170.666667 512 170.666667zM85.333333 512C85.333333 276.352 276.352 85.333333 512 85.333333s426.666667 191.018667 426.666667 426.666667-191.018667 426.666667-426.666667 426.666667S85.333333 747.648 85.333333 512z">
                </path>
                <path
                  d="M693.013333 330.986667a42.666667 42.666667 0 0 1 10.304 43.648l-75.413333 226.282666a42.666667 42.666667 0 0 1-26.986667 26.986667l-226.282666 75.413333a42.666667 42.666667 0 0 1-53.973334-53.973333l75.434667-226.261333a42.666667 42.666667 0 0 1 26.986667-26.986667l226.282666-75.413333a42.666667 42.666667 0 0 1 43.648 10.304z m-222.72 139.306666l-41.685333 125.098667 125.077333-41.706667 41.706667-125.077333-125.077333 41.706667z">
                </path>
              </svg>{{ lang.ssAnalysis }}
            </div>
            <div class="ai_refresh" :class="{ 'disabled': currentAnalysis && currentAnalysis.loading }"
              @click.stop="aiAnalysisRefresh45()">
              {{ lang.ssAIGenerate }}
              <svg viewBox="0 0 1024 1024" width="200" height="200">
                <path
                  d="M875 483c-33.4 0-60.5 27.1-60.5 60.5v0.1C814.4 710.3 678.8 846 512 846S209.5 710.3 209.5 543.5 345.2 241 512 241c36.8 0 71.7 7.6 104.4 19.7-32 3-57.4 29.1-57.4 61.9 0 34.8 28.2 63 63 63h201.9c34.8 0 63-28.2 63-63V120c0-34.8-28.2-63-63-63s-63 28.2-63 63v81.4C691 150.5 605.2 120 512 120 278.1 120 88.5 309.6 88.5 543.5S278.1 967 512 967s423.5-189.6 423.5-423.5c0-33.4-27.1-60.5-60.5-60.5z">
                </path>
              </svg>

            </div>
          </div>
          <div class="ai_content" v-if="currentAnalysis && currentAnalysis.json">
            {{ currentAnalysis.json.text }}
          </div>
          <div class="ai_echartsData" v-if="currentAnalysis && currentAnalysis.json.keyword">
            {{ currentAnalysis.json.keyword }}
          </div>
          <div class="generatingContent" v-if="currentAnalysis && currentAnalysis.loading">
            {{ lang.ssGeneratingContent }}...</div>
          <div class="ai_updateTime" v-if="currentAnalysis">{{ lang.ssUpdateTime }}：{{ currentAnalysis.update_at }}
          </div>
        </div>
        <div class="cq_changeBtn" v-if="props.showData.choiceQuestionListData.length > 1">
          <div :class="{ cq_cb_disabled: props.showData.workIndex <= 0 }" @click.stop="changeWorkIndex(0)">
            <svg style="transform: rotate(-90deg);" viewBox="0 0 1024 1024" version="1.1" width="200" height="200">
              <path
                d="M512 330.666667c14.933333 0 29.866667 4.266667 40.533333 14.933333l277.33333399 234.666667c27.733333 23.466667 29.866667 64 8.53333301 89.6-23.466667 27.733333-64 29.866667-89.6 8.53333299L512 477.866667l-236.8 200.53333299c-27.733333 23.466667-68.266667 19.19999999-89.6-8.53333299-23.466667-27.733333-19.19999999-68.266667 8.53333301-89.6l277.33333399-234.666667c10.666667-10.666667 25.6-14.933333 40.533333-14.933333z"
                fill=""></path>
            </svg>
          </div>
          <span>{{ props.showData.workIndex + 1 }}/{{ props.showData.choiceQuestionListData.length }}</span>
          <div :class="{ cq_cb_disabled: props.showData.workIndex >= props.showData.choiceQuestionListData.length - 1 }"
            @click.stop="changeWorkIndex(1)">
            <svg style="transform: rotate(90deg);" viewBox="0 0 1024 1024" version="1.1" width="200" height="200">
              <path
                d="M512 330.666667c14.933333 0 29.866667 4.266667 40.533333 14.933333l277.33333399 234.666667c27.733333 23.466667 29.866667 64 8.53333301 89.6-23.466667 27.733333-64 29.866667-89.6 8.53333299L512 477.866667l-236.8 200.53333299c-27.733333 23.466667-68.266667 19.19999999-89.6-8.53333299-23.466667-27.733333-19.19999999-68.266667 8.53333301-89.6l277.33333399-234.666667c10.666667-10.666667 25.6-14.933333 40.533333-14.933333z"
                fill=""></path>
            </svg>
          </div>
        </div>
      </div>

      <!-- 投票 -->
      <div class="c_t45" v-if="workDetail && workDetail.type === '78' && props.showData">
        <div class="c_t45_title">
          <div class="c_title" v-if="props.showData.choiceQuestionListData[props.showData.workIndex]">
            <span>{{
            props.showData.choiceQuestionListData[props.showData.workIndex]
              .teststitle
          }}</span>
            <div class="switch_btn" v-if="props.isCreator && props.roleType == 1">
              <div class="switch">
                <Switch :value="canValue" @update:value="handleCanChange" />
                <span>{{ lang.ssShowResult }}</span>
              </div>
              <div class="switch">
                <Switch :value="anonymousValue" @update:value="handleAnonymousChange" />
                <span>{{anonymousValue ? lang.ssAnonymous : lang.ssRealName}}</span>
              </div>
            </div>
          </div>
          <div class="c_t45_msg" v-if="props.roleType == 1">
            <div>{{ lang.ssAnswerCount }} {{ props.workArray.length }}<span
                v-if="props.unsubmittedStudents.length > 0">/{{ props.workArray.length +
                  props.unsubmittedStudents.length
                }}</span></div>
            <span v-if="props.unsubmittedStudents.length > 0" @click.stop="viewUnsubmittedStudents()">{{
              lang.ssViewSubmitStatus2 }}</span>
          </div>
          <!--<span class="c_t45_t_btn" :class="{'c_t45_t_btn_noActive': props.showData.workIndex <= 0}" @click="changeWorkIndex(0)">{{ lang.ssPrevQ }}</span>-->
          <!--<span class="c_t45_t_btn" :class="{'c_t45_t_btn_noActive': props.showData.workIndex >= props.showData.choiceQuestionListData.length - 1}" @click="changeWorkIndex(1)">{{ lang.ssNextQ }}</span>-->
        </div>
        <img class="c_t45_img" :src="props.showData.choiceQuestionListData[props.showData.workIndex]
          .timuList[0].src
          " v-if="props.showData.choiceQuestionListData[props.showData.workIndex] &&
            props.showData.choiceQuestionListData[props.showData.workIndex]
              .timuList.length > 0
          " @click.stop="previewImageToolRef.previewImage(props.showData.choiceQuestionListData[props.showData.workIndex]
            .timuList[0].src)" />
        <!-- <span class="c_t45_type" v-if="
          props.showData.choiceQuestionListData[props.showData.workIndex]
            .type === '1'
        ">{{ lang.ssSingleSel }}</span>
        <span class="c_t45_type" v-if="
          props.showData.choiceQuestionListData[props.showData.workIndex]
            .type === '2'
        ">{{ lang.ssMultiOpt }}</span> -->
        <!-- <span class="c_t45_type">{{ lang.ssChoiceQuestion }}</span> -->
        <div class="c_t45_echarts" :style="{
          width: slideWidth - 40 + 'px',
        }">
          <div id="echartsArea1" ref="echartsArea1"></div>
        </div>
        <!-- v-if="props.workArray.length > 0" -->
        <div class="aiAnalysis" v-if="false">
          <div class="ai_header">
            <div class="ai_title">
              <svg viewBox="0 0 1024 1024" width="200" height="200">
                <path
                  d="M512 170.666667C323.477333 170.666667 170.666667 323.477333 170.666667 512s152.810667 341.333333 341.333333 341.333333 341.333333-152.810667 341.333333-341.333333S700.522667 170.666667 512 170.666667zM85.333333 512C85.333333 276.352 276.352 85.333333 512 85.333333s426.666667 191.018667 426.666667 426.666667-191.018667 426.666667-426.666667 426.666667S85.333333 747.648 85.333333 512z">
                </path>
                <path
                  d="M693.013333 330.986667a42.666667 42.666667 0 0 1 10.304 43.648l-75.413333 226.282666a42.666667 42.666667 0 0 1-26.986667 26.986667l-226.282666 75.413333a42.666667 42.666667 0 0 1-53.973334-53.973333l75.434667-226.261333a42.666667 42.666667 0 0 1 26.986667-26.986667l226.282666-75.413333a42.666667 42.666667 0 0 1 43.648 10.304z m-222.72 139.306666l-41.685333 125.098667 125.077333-41.706667 41.706667-125.077333-125.077333 41.706667z">
                </path>
              </svg>{{ lang.ssAnalysis }}
            </div>
            <div class="ai_refresh" :class="{ 'disabled': currentAnalysis && currentAnalysis.loading }"
              @click.stop="aiAnalysisRefresh78()">
              {{ lang.ssAIGenerate }}
              <svg viewBox="0 0 1024 1024" width="200" height="200">
                <path
                  d="M875 483c-33.4 0-60.5 27.1-60.5 60.5v0.1C814.4 710.3 678.8 846 512 846S209.5 710.3 209.5 543.5 345.2 241 512 241c36.8 0 71.7 7.6 104.4 19.7-32 3-57.4 29.1-57.4 61.9 0 34.8 28.2 63 63 63h201.9c34.8 0 63-28.2 63-63V120c0-34.8-28.2-63-63-63s-63 28.2-63 63v81.4C691 150.5 605.2 120 512 120 278.1 120 88.5 309.6 88.5 543.5S278.1 967 512 967s423.5-189.6 423.5-423.5c0-33.4-27.1-60.5-60.5-60.5z">
                </path>
              </svg>

            </div>
          </div>
          <div class="ai_content" v-if="currentAnalysis && currentAnalysis.json">
            {{ currentAnalysis.json.text }}
          </div>
          <div class="ai_echartsData" v-if="currentAnalysis && currentAnalysis.json.keyword">
            {{ currentAnalysis.json.keyword }}
          </div>
          <div class="generatingContent" v-if="currentAnalysis && currentAnalysis.loading">
            {{ lang.ssGeneratingContent }}...</div>
          <div class="ai_updateTime" v-if="currentAnalysis">{{ lang.ssUpdateTime }}：{{ currentAnalysis.update_at }}
          </div>
        </div>
        <div class="cq_changeBtn" v-if="props.showData.choiceQuestionListData.length > 1">
          <div :class="{ cq_cb_disabled: props.showData.workIndex <= 0 }" @click.stop="changeWorkIndex(0)">
            <svg style="transform: rotate(-90deg);" viewBox="0 0 1024 1024" version="1.1" width="200" height="200">
              <path
                d="M512 330.666667c14.933333 0 29.866667 4.266667 40.533333 14.933333l277.33333399 234.666667c27.733333 23.466667 29.866667 64 8.53333301 89.6-23.466667 27.733333-64 29.866667-89.6 8.53333299L512 477.866667l-236.8 200.53333299c-27.733333 23.466667-68.266667 19.19999999-89.6-8.53333299-23.466667-27.733333-19.19999999-68.266667 8.53333301-89.6l277.33333399-234.666667c10.666667-10.666667 25.6-14.933333 40.533333-14.933333z"
                fill=""></path>
            </svg>
          </div>
          <span>{{ props.showData.workIndex + 1 }}/{{ props.showData.choiceQuestionListData.length }}</span>
          <div :class="{ cq_cb_disabled: props.showData.workIndex >= props.showData.choiceQuestionListData.length - 1 }"
            @click.stop="changeWorkIndex(1)">
            <svg style="transform: rotate(90deg);" viewBox="0 0 1024 1024" version="1.1" width="200" height="200">
              <path
                d="M512 330.666667c14.933333 0 29.866667 4.266667 40.533333 14.933333l277.33333399 234.666667c27.733333 23.466667 29.866667 64 8.53333301 89.6-23.466667 27.733333-64 29.866667-89.6 8.53333299L512 477.866667l-236.8 200.53333299c-27.733333 23.466667-68.266667 19.19999999-89.6-8.53333299-23.466667-27.733333-19.19999999-68.266667 8.53333301-89.6l277.33333399-234.666667c10.666667-10.666667 25.6-14.933333 40.533333-14.933333z"
                fill=""></path>
            </svg>
          </div>
        </div>
      </div>

      <!-- 问答题 -->
      <div class="c_t15" v-if="workDetail && workDetail.type === '15' && props.showData">
        <div class="c_t15_title">
          <div class="c_title">
            <span>{{ workDetail.json.answerQ }}</span>
            <div class="switch_btn" v-if="props.isCreator && props.roleType == 1">
              <div class="switch">
                <Switch :value="canValue" @update:value="handleCanChange" />
                <span>{{ lang.ssShowResult }}</span>
              </div>
              <div class="switch">
                <Switch :value="likeValue" @update:value="handleLikeChange" />
                <span>{{ lang.ssLike }}</span>
              </div>
            </div>
          </div>
        </div>
        <span class="c_t15_type">{{ lang.ssQATest }}</span>
        <div class="c_t15_msg" v-if="props.roleType == 1">
          <div>{{ lang.ssAnswerCount }} {{ props.workArray.length }}<span
              v-if="props.unsubmittedStudents.length > 0">/{{ props.workArray.length +
                props.unsubmittedStudents.length
              }}</span></div>
          <span v-if="props.unsubmittedStudents.length > 0" @click.stop="viewUnsubmittedStudents()">{{
            lang.ssViewSubmitStatus2 }}</span>
        </div>
        <div class="c_t15_content" v-show="!lookWorkData">
          <div class="c_t15_c_item" v-for="item in processedWorkArray" :key="item.id" @click.stop="lookWork(item.id)">
            <div class="c_t15_c_i_top">
              <span>{{ item.name.charAt(0) }}</span>
              <div>{{ item.name }}</div>
              <div class="cast_sreen_btn" @click.stop="castScreen(item)"  v-if="props.isCreator && props.roleType == 1 && isFollowModeActive && canValue">
                <IconCastScreen />
                {{ lang.ssCastScreen }}
              </div>
            </div>
            <div class="c_t15_c_i_bottom">
              <span v-html="item.content.answer"></span>
            </div>
            <div class="bottom_btn" v-if="likeValue">
              <div class="bottom_like" :class="{'active': item.isLikes}"  @click.stop="handleLikeClick(item)">
                <IconThumbsUp />
                <span>{{ item.likesCount }}</span>
              </div>
            </div>
          </div>
        </div>

        <div class="aiAnalysis" style="margin-top:1rem ;"
          v-if="processedWorkArray.length > 0 && lookWorkData === null && workDetail.type === '15' && props.roleType == 1"
          @click.stop="clickContent(false)">
          <div class="ai_header">
            <div class="ai_title">
              <svg viewBox="0 0 1024 1024" width="200" height="200">
                <path
                  d="M512 170.666667C323.477333 170.666667 170.666667 323.477333 170.666667 512s152.810667 341.333333 341.333333 341.333333 341.333333-152.810667 341.333333-341.333333S700.522667 170.666667 512 170.666667zM85.333333 512C85.333333 276.352 276.352 85.333333 512 85.333333s426.666667 191.018667 426.666667 426.666667-191.018667 426.666667-426.666667 426.666667S85.333333 747.648 85.333333 512z">
                </path>
                <path
                  d="M693.013333 330.986667a42.666667 42.666667 0 0 1 10.304 43.648l-75.413333 226.282666a42.666667 42.666667 0 0 1-26.986667 26.986667l-226.282666 75.413333a42.666667 42.666667 0 0 1-53.973334-53.973333l75.434667-226.261333a42.666667 42.666667 0 0 1 26.986667-26.986667l226.282666-75.413333a42.666667 42.666667 0 0 1 43.648 10.304z m-222.72 139.306666l-41.685333 125.098667 125.077333-41.706667 41.706667-125.077333-125.077333 41.706667z">
                </path>
              </svg>{{ lang.ssAnalysis }}
            </div>
            <div class="ai_refresh" :class="{ 'disabled': currentAnalysis && currentAnalysis.loading }"
              @click.stop="aiAnalysisRefresh15()">
              {{ lang.ssAIGenerate }}
              <svg viewBox="0 0 1024 1024" width="200" height="200">
                <path
                  d="M875 483c-33.4 0-60.5 27.1-60.5 60.5v0.1C814.4 710.3 678.8 846 512 846S209.5 710.3 209.5 543.5 345.2 241 512 241c36.8 0 71.7 7.6 104.4 19.7-32 3-57.4 29.1-57.4 61.9 0 34.8 28.2 63 63 63h201.9c34.8 0 63-28.2 63-63V120c0-34.8-28.2-63-63-63s-63 28.2-63 63v81.4C691 150.5 605.2 120 512 120 278.1 120 88.5 309.6 88.5 543.5S278.1 967 512 967s423.5-189.6 423.5-423.5c0-33.4-27.1-60.5-60.5-60.5z">
                </path>
              </svg>

            </div>
          </div>
          <div class="ai_content" v-if="currentAnalysis && currentAnalysis.json">
            {{ currentAnalysis.json.text }}
          </div>
          <div class="ai_echartsData" v-if="currentAnalysis && currentAnalysis.json.keyword">
            <div class="title">{{ lang.ssKeyword }}：</div>
            <span v-for="(item, index) in currentAnalysis.json.keyword" :key="index">{{ item }}</span>
            <div class="btn" @click.stop="openEchatsDialog()">{{ lang.ssViewKeywordCloud }}</div>
          </div>
          <div class="generatingContent" v-if="currentAnalysis && currentAnalysis.generatingContent">{{
            lang.ssGeneratingContent }}...</div>
          <div class="ai_updateTime" v-if="currentAnalysis">{{ lang.ssUpdateTime }}：{{ currentAnalysis.update_at }}
          </div>
        </div>


        <div class="c_t15_workDetail" v-if="lookWorkData" @click.stop="clickContent(false)">
          <div class="c_t15_wd_top">
            <img src="../../../assets/img/arrow_left.png" @click.stop="lookWork('')" v-if="!isCastScreen"/>
            <span>{{ lookWorkData.name.charAt(0) }}</span>
            <div>{{ lookWorkData.name }}</div>
            <div class="cast_sreen_btn" @click.stop="exitCastScreen"  v-if="(props.isCreator && props.roleType == 1 && isCastScreen) || (!isFollowModeActive && isCastScreen)">
              <IconCastScreen />
              {{ lang.ssExitCastScreen }}
            </div>
          </div>
          <div class="c_t15_wd_content">
            <span v-html="lookWorkData.content.answer"></span>
            <div class="c_t15_wd_c_imageList" v-if="lookWorkData.content.fileList.length > 0">
              <img v-for="item in lookWorkData.content.fileList" :src="item.url" :key="item.uploadTime"
                @click.stop="lookImage(item.url)" />
            </div>
          </div>
        </div>
      </div>

      <!-- 拍照 -->
      <div class="c_t15" v-if="workDetail && workDetail.type === '79' && props.showData">
        <div class="c_t15_title">
          <div class="c_title">
            <span>{{ workDetail.json.answerQ }}</span>
            <div class="switch_btn" v-if="props.isCreator && props.roleType == 1">
              <div class="switch">
                <Switch :value="canValue" @update:value="handleCanChange" />
                <span>{{ lang.ssShowResult }}</span>
              </div>
              <div class="switch">
                <Switch :value="likeValue" @update:value="handleLikeChange" />
                <span>{{ lang.ssLike }}</span>
              </div>
            </div>
          </div>
        </div>
        <span class="c_t15_type">{{ lang.ssPhoto }}</span>
        <div class="c_t15_msg" v-if="props.roleType == 1">
          <div>{{ lang.ssAnswerCount }} {{ props.workArray.length }}<span
              v-if="props.unsubmittedStudents.length > 0">/{{ props.workArray.length +
                props.unsubmittedStudents.length
              }}</span></div>
          <span v-if="props.unsubmittedStudents.length > 0" @click.stop="viewUnsubmittedStudents()">{{
            lang.ssViewSubmitStatus2 }}</span>
        </div>
        <div class="downloadBtn" @click.stop="downloadAll" :class="{ disabled: downloadLoading }" v-if="props.roleType == 1">
          <IconDownload />
          <span>{{ downloadLoading ? lang.ssDownloadLoading : lang.ssBatchDownload }}</span>
        </div>
        <div class="c_t15_content" v-show="!lookWorkData">
          <div class="c_t15_c_item" v-for="item in processedWorkArray" :key="item.id"
            @click.stop="item.content && item.content.fileList.length > 0 ? lookWork(item.id) : ''">
            <div class="c_t15_c_i_top">
              <span>{{ item.name.charAt(0) }}</span>
              <div>{{ item.name }}</div>
              <div class="cast_sreen_btn" @click.stop="castScreen(item)"  v-if="props.isCreator && props.roleType == 1 && isFollowModeActive && canValue">
                <IconCastScreen />
                {{ lang.ssCastScreen }}
              </div>
            </div>
            <div class="c_t73_c_i_bottom" v-if="item.content && item.content.fileList.length > 0">
              <img :src="item.content.fileList[0].url" />
            </div>
            <div class="c_t73_c_i_bottom" v-else>
              <span>{{ lang.ssNoPhoto }}</span>
            </div>
            <div class="bottom_btn" v-if="likeValue">
              <div class="bottom_like" :class="{'active': item.isLikes}"  @click.stop="handleLikeClick(item)">
                <IconThumbsUp />
                <span>{{ item.likesCount }}</span>
              </div>
            </div>
          </div>
        </div>

        <div class="c_t79_workDetail" v-if="lookWorkData" @click.stop="clickContent(false)">
          <div class="c_t79_wd_top">
            <img src="../../../assets/img/arrow_left.png" @click.stop="lookWork('')" v-if="!isCastScreen"/>
            <span>{{ lookWorkData.name.charAt(0) }}</span>
            <div>{{ lookWorkData.name }}</div>
            <div class="cast_sreen_btn" @click.stop="exitCastScreen"  v-if="(props.isCreator && props.roleType == 1 && isCastScreen) || (!isFollowModeActive && isCastScreen)">
              <IconCastScreen />
              {{ lang.ssExitCastScreen }}
            </div>
          </div>
          <div class="c_t79_wd_content">
            <img :src="lookWorkData.content.fileList[lookWorkIndex].url"
              @click.stop="lookImage(lookWorkData.content.fileList[lookWorkIndex].url)" />
          </div>
          <!-- <div class="nextAndUpBtn" v-if="lookWorkData.content.fileList.length>1">
            <span :class="{no_active:lookWorkIndex==0}" @click="changelookWorkIndex(0)">{{ lang.ssPrevP }}</span>
            <span :class="{no_active:lookWorkData.content.fileList.length-1<=lookWorkIndex}"  @click="changelookWorkIndex(1)">{{ lang.ssNextP }}</span>
          </div> -->
          <div class="cq_changeBtn" v-if="lookWorkData.content.fileList.length > 1">
            <div :class="{ cq_cb_disabled: lookWorkIndex <= 0 }" @click.stop="changelookWorkIndex(0)">
              <svg style="transform: rotate(-90deg);" viewBox="0 0 1024 1024" version="1.1" width="200" height="200">
                <path
                  d="M512 330.666667c14.933333 0 29.866667 4.266667 40.533333 14.933333l277.33333399 234.666667c27.733333 23.466667 29.866667 64 8.53333301 89.6-23.466667 27.733333-64 29.866667-89.6 8.53333299L512 477.866667l-236.8 200.53333299c-27.733333 23.466667-68.266667 19.19999999-89.6-8.53333299-23.466667-27.733333-19.19999999-68.266667 8.53333301-89.6l277.33333399-234.666667c10.666667-10.666667 25.6-14.933333 40.533333-14.933333z"
                  fill=""></path>
              </svg>
            </div>
            <span>{{ lookWorkIndex + 1 }}/{{ lookWorkData.content.fileList.length }}</span>
            <div :class="{ cq_cb_disabled: lookWorkIndex >= lookWorkData.content.fileList.length - 1 }"
              @click.stop="changelookWorkIndex(1)">
              <svg style="transform: rotate(90deg);" viewBox="0 0 1024 1024" version="1.1" width="200" height="200">
                <path
                  d="M512 330.666667c14.933333 0 29.866667 4.266667 40.533333 14.933333l277.33333399 234.666667c27.733333 23.466667 29.866667 64 8.53333301 89.6-23.466667 27.733333-64 29.866667-89.6 8.53333299L512 477.866667l-236.8 200.53333299c-27.733333 23.466667-68.266667 19.19999999-89.6-8.53333299-23.466667-27.733333-19.19999999-68.266667 8.53333301-89.6l277.33333399-234.666667c10.666667-10.666667 25.6-14.933333 40.533333-14.933333z"
                  fill=""></path>
              </svg>
            </div>
          </div>
        </div>
      </div>

      <!-- AI应用 -->
      <div class="c_t72" v-if="props.showData && props.showData.toolType === 72">
        <div class="c_t72_title">
          <div class="c_title">
            <span>{{ lang.ssAiApp }}</span>
            <div class="switch_btn" v-if="props.isCreator && props.roleType == 1">
              <div class="switch">
                <Switch :value="canValue" @update:value="handleCanChange" />
                <span>{{ lang.ssShowResult }}</span>
              </div>
              <div class="switch">
                <Switch :value="likeValue" @update:value="handleLikeChange" />
                <span>{{ lang.ssLike }}</span>
              </div>
            </div>
          </div>
        </div>
        <span class="c_t72_type">{{ lang.ssAiApp }}</span>
        <div class="c_t72_msg" v-if="props.roleType == 1">
          <div>{{ lang.ssAnswerCount }} {{ props.workArray.length }}<span
              v-if="props.unsubmittedStudents.length > 0">/{{ props.workArray.length +
                props.unsubmittedStudents.length
              }}</span></div>
          <span v-if="props.unsubmittedStudents.length > 0" @click.stop="viewUnsubmittedStudents()">{{
            lang.ssViewSubmitStatus2 }}</span>
        </div>
        <div class="c_t72_content" v-show="!lookWorkData">
          <div class="c_t72_c_item" v-for="item in processedWorkArray" :key="item.id" @click.stop="lookWork(item.id)">
            <div class="c_t72_c_i_top">
              <span>{{ item.name.charAt(0) }}</span>
              <div>{{ item.name }}</div>
              <div class="cast_sreen_btn" @click.stop="castScreen(item)"  v-if="props.isCreator && props.roleType == 1 && isFollowModeActive && canValue">
                <IconCastScreen />
                {{ lang.ssCastScreen }}
              </div>
            </div>
            <div class="bottom_btn" v-if="likeValue">
              <div class="bottom_like" :class="{'active': item.isLikes}"  @click.stop="handleLikeClick(item)">
                <IconThumbsUp />
                <span>{{ item.likesCount }}</span>
              </div>
            </div>
          </div>
        </div>

        <div class="aiAnalysis" style="margin-top:1rem ;"
          v-if="processedWorkArray.length > 0 && lookWorkData === null && props.showData.toolType === 72 && props.roleType == 1"
          @click.stop="clickContent(false)">
          <div class="ai_header">
            <div class="ai_title">
              <svg viewBox="0 0 1024 1024" width="200" height="200">
                <path
                  d="M512 170.666667C323.477333 170.666667 170.666667 323.477333 170.666667 512s152.810667 341.333333 341.333333 341.333333 341.333333-152.810667 341.333333-341.333333S700.522667 170.666667 512 170.666667zM85.333333 512C85.333333 276.352 276.352 85.333333 512 85.333333s426.666667 191.018667 426.666667 426.666667-191.018667 426.666667-426.666667 426.666667S85.333333 747.648 85.333333 512z">
                </path>
                <path
                  d="M693.013333 330.986667a42.666667 42.666667 0 0 1 10.304 43.648l-75.413333 226.282666a42.666667 42.666667 0 0 1-26.986667 26.986667l-226.282666 75.413333a42.666667 42.666667 0 0 1-53.973334-53.973333l75.434667-226.261333a42.666667 42.666667 0 0 1 26.986667-26.986667l226.282666-75.413333a42.666667 42.666667 0 0 1 43.648 10.304z m-222.72 139.306666l-41.685333 125.098667 125.077333-41.706667 41.706667-125.077333-125.077333 41.706667z">
                </path>
              </svg>{{ lang.ssAnalysis }}
            </div>
            <div class="ai_refresh" :class="{ 'disabled': currentAnalysis && currentAnalysis.loading }"
              @click.stop="aiAnalysisRefresh72()">
              {{ lang.ssAIGenerate }}
              <svg viewBox="0 0 1024 1024" width="200" height="200">
                <path
                  d="M875 483c-33.4 0-60.5 27.1-60.5 60.5v0.1C814.4 710.3 678.8 846 512 846S209.5 710.3 209.5 543.5 345.2 241 512 241c36.8 0 71.7 7.6 104.4 19.7-32 3-57.4 29.1-57.4 61.9 0 34.8 28.2 63 63 63h201.9c34.8 0 63-28.2 63-63V120c0-34.8-28.2-63-63-63s-63 28.2-63 63v81.4C691 150.5 605.2 120 512 120 278.1 120 88.5 309.6 88.5 543.5S278.1 967 512 967s423.5-189.6 423.5-423.5c0-33.4-27.1-60.5-60.5-60.5z">
                </path>
              </svg>

            </div>
          </div>
          <div class="ai_content" v-if="currentAnalysis && currentAnalysis.json" v-html="currentAnalysis.json.text">
          </div>
          <div class="ai_updateTime" v-if="currentAnalysis">{{ lang.ssUpdateTime }}：{{ currentAnalysis.update_at }}
          </div>
        </div>

        <div class="c_t72_workDetail" v-if="lookWorkData" @click.stop="clickContent(false)">
          <div class="c_t72_wd_top">
            <img src="../../../assets/img/arrow_left.png" @click.stop="lookWork('')" v-if="!isCastScreen"/>
            <span>{{ lookWorkData.name.charAt(0) }}</span>
            <div>{{ lookWorkData.name }}</div>
            <div class="cast_sreen_btn" @click.stop="exitCastScreen"  v-if="(props.isCreator && props.roleType == 1 && isCastScreen) || (!isFollowModeActive && isCastScreen)">
              <IconCastScreen />
              {{ lang.ssExitCastScreen }}
            </div>
          </div>
          <div class="c_t72_wd_content">
            <template v-for="(item, index) in lookWorkData.content" :key="item.id">
              <div class="messageNodeArea" v-if="item.messages || item.imageUrls">
                <div class="messageNode">
                  <div class="mn_title">{{ lang.ssNodeTitle.replace(/\*/g, String(index + 1)) }}</div>
                  <div class="mn_content">
                    <template v-for="(item2, index2) in item.messages" :key="`${index}-${index2}`">
                      <div>
                        <div class="na_m_item" v-if="item2.role == 'user' && item2.content">
                          <div class="na_m_i_name">
                            {{ item2.sender }}
                          </div>
                          <div class="na_m_i_content" v-html="item2.content"></div>
                        </div>
                        <div class="na_m_item" v-if="item2.role == 'assistant' && item2.content">
                          <div class="na_m_i_name aiName">
                            {{ item2.sender }}
                          </div>
                          <div class="na_m_i_content" v-html="item2.content"></div>
                        </div>
                      </div>
                    </template>
                    <template v-if="item.imageUrls" v-for="(item3, index3) in item.imageUrls"
                      :key="`${index}-${index3}`">
                      <div class="na_m_item">
                        <div class="na_m_i_name">
                          {{ item.type }}
                        </div>
                        <div class="na_m_i_content">
                          <img @click.stop="lookImage(item3)" style="height: 100px;width: auto;cursor: pointer;"
                            :src="item3" />
                        </div>
                      </div>
                    </template>
                  </div>
                </div>
              </div>
            </template>
          </div>
        </div>
      </div>

      <!-- H5页面 -->
      <div class="c_t73" v-if="props.showData && props.showData.toolType === 73">
        <div class="c_t73_title">
          <div class="c_title">
            <span>{{ lang.ssPageImage }}</span>
            <div class="switch_btn" v-if="props.isCreator && props.roleType == 1">
              <div class="switch">
                <Switch :value="canValue" @update:value="handleCanChange" />
                <span>{{ lang.ssShowResult }}</span>
              </div>
              <div class="switch">
                <Switch :value="likeValue" @update:value="handleLikeChange" />
                <span>{{ lang.ssLike }}</span>
              </div>
            </div>
          </div>
        </div>
        <span class="c_t73_type">{{ lang.ssHPage }}</span>
        <div class="c_t73_msg" v-if="props.roleType == 1">
          <div>{{ lang.ssAnswerCount }} {{ props.workArray.length }}<span
              v-if="props.unsubmittedStudents.length > 0">/{{ props.workArray.length +
                props.unsubmittedStudents.length
              }}</span></div>
          <span v-if="props.unsubmittedStudents.length > 0" @click.stop="viewUnsubmittedStudents()">{{
            lang.ssViewSubmitStatus2 }}</span>
        </div>
        <div class="c_t73_content" v-show="!lookWorkData">
          <div class="c_t73_c_item" v-for="item in processedWorkArray" :key="item.id" @click.stop="lookWork(item.id)">
            <div class="c_t73_c_i_top">
              <span>{{ item.name.charAt(0) }}</span>
              <div>{{ item.name }}</div>
              <div class="cast_sreen_btn" @click.stop="castScreen(item)"  v-if="props.isCreator && props.roleType == 1 && isFollowModeActive && canValue">
                <IconCastScreen />
                {{ lang.ssCastScreen }}
              </div>
            </div>
            <div class="c_t73_c_i_bottom">
              <img :src="item.content" />
            </div>
            <div class="bottom_btn" v-if="likeValue">
              <div class="bottom_like" :class="{'active': item.isLikes}"  @click.stop="handleLikeClick(item)">
                <IconThumbsUp />
                <span>{{ item.likesCount }}</span>
              </div>
            </div>
          </div>
        </div>

        <div class="c_t73_workDetail" v-if="lookWorkData" @click.stop="clickContent(false)">
          <div class="c_t73_wd_top">
            <img src="../../../assets/img/arrow_left.png" @click.stop="lookWork('')" v-if="!isCastScreen"/>
            <span>{{ lookWorkData.name.charAt(0) }}</span>
            <div>{{ lookWorkData.name }}</div>
            <div class="cast_sreen_btn" @click.stop="exitCastScreen"  v-if="(props.isCreator && props.roleType == 1 && isCastScreen) || (!isFollowModeActive && isCastScreen)">
              <IconCastScreen />
              {{ lang.ssExitCastScreen }}
            </div>
          </div>
          <div class="c_t73_wd_content">
            <img :src="lookWorkData.content" />
          </div>
        </div>
      </div>
    </div>
    <previewImageTool ref="previewImageToolRef" />
    <selectUserDialog ref="selectUserDialogRef" />
    <echartsDialog ref="echartsDialogRef" />
  </div>
</template>

<script setup lang="ts">
import { computed, ref, watch, onUnmounted, nextTick, onMounted } from 'vue'
import * as echarts from 'echarts'
import previewImageTool from '../../components/tool/previewImageTool.vue'
import MarkdownIt from 'markdown-it'
import useImport from '@/hooks/useImport'
import { lang } from '@/main'
import selectUserDialog from './selectUserDialog.vue'
import echartsDialog from './echartsDialog.vue'
import { chat_stream, chat_no_stream } from '@/tools/aiChat'
import axios from '@/services/config'
import Switch from '@/components/Switch.vue'
import { likeWork } from '@/services/course'

const props = defineProps<{
  visible: number[];
  workIndex: number;
  slideWidth: number;
  slideHeight: number;
  slideIndex: number;
  showData: any;
  workArray: any[];
  unsubmittedStudents: any[];
  courseDetail: any;
  userId: string;
  workId: string;
  cid: string;
  workUrl: string;
  roleType: number;
  resultArray: { [key: string]: any };
  isCreator: boolean;
  isFollowModeActive: boolean;
  courseid: string;
}>()

const emit = defineEmits<{
  (e: 'update:visible', v: number[]): void;
  (e: 'changeWorkIndex', v: number): void;
  (e: 'setIsResultArray', v: boolean, key: string): void;
  (e: 'successLike'): void;
  (e: 'sendMessage', v: any): void;
}>()

const visible = computed({
  get: () => props.visible,
  set: (v: number[]) => emit('update:visible', v),
})

const workDetail = computed(() => {
  if (props.showData) {
    return props.showData.workDetail
  }
  return null
})

const canValue = ref(props.resultArray?.can ?? false)

watch(() => props.resultArray?.can, (newVal) => {
  canValue.value = newVal
})

const likeValue = ref(props.resultArray?.like ?? false)

watch(() => props.resultArray?.like, (newVal) => {
  likeValue.value = newVal
})

const anonymousValue = ref(props.resultArray?.anonymous ?? false)

watch(() => props.resultArray?.anonymous, (newVal) => {
  anonymousValue.value = newVal
})

const answerValue = ref(props.resultArray?.answer ?? false)

watch(() => props.resultArray?.answer, (newVal) => {
  answerValue.value = newVal
  setEchartsArea1()
})



const handleCanChange = (value: boolean) => {
  console.log(value)
  console.log(props.resultArray)
  if (workDetail.value.type === '45') {
    handleAnswerChange(value)
  }
  emit('setIsResultArray', value, 'can')
}

const handleLikeChange = (value: boolean) => {
  if (value && !canValue.value) {
    emit('setIsResultArray', true, 'can')
  }
  console.log(value)
  console.log(props.resultArray)
  emit('setIsResultArray', value, 'like')
}

const handleAnonymousChange = (value: boolean) => {
  console.log(value)
  console.log(props.resultArray)
  emit('setIsResultArray', value, 'anonymous')
}

const handleAnswerChange = (value: boolean) => {
  console.log(value)
  console.log(props.resultArray)
  emit('setIsResultArray', value, 'answer')
}


import _ from 'lodash'
import type { workerData } from 'worker_threads'

const handleLikeClick = _.debounce((item: any) => {
  likeWork({
    wid: item.id,
    lid: props.userId,
    t: 1,
    c: ''
  })
  emit('successLike')
}, 300)

// 预览图片组件
const previewImageToolRef = ref<any>(null)
// 选择用户组件
const selectUserDialogRef = ref<any>(null)
// 词云图组件
const echartsDialogRef = ref<any>(null)

// ai分析数据
const aiAnalysisData = ref<Array<any>>([])

const md = new MarkdownIt({
  html: true,
})
const { getFile } = useImport()

// 判断是否是 URL 链接
const isUrl = (str: string): boolean => {
  try {
    const url = new URL(str)
    return (url.protocol === 'http:' || url.protocol === 'https:') && str.includes('json')
  }
  catch {
    return false
  }
}

// 从链接获取文件内容
const loadContentFromUrl = async (url: string): Promise<string> => {
  try {
    const fileData = await getFile(url)
    if (fileData && fileData.data) {
      // 将 ArrayBuffer 转为字符串
      const uint8Array = new Uint8Array(fileData.data)
      const jsonStr = new TextDecoder('utf-8').decode(uint8Array)
      return jsonStr
    }
    return ''
  }
  catch (error) {
    console.error('获取文件内容失败:', error)
    return ''
  }
}

// 处理单个作业内容
const processWorkContent = async (content: string, toolType: number): Promise<any> => {
  let contentToParse = content

  // 如果是链接，先获取文件内容
  if (isUrl(content)) {
    contentToParse = await loadContentFromUrl(content)
  }

  if (!contentToParse) {
    return null
  }

  try {
    if ([45, 15, 78, 79].includes(toolType)) {
      return JSON.parse(decodeURIComponent(contentToParse))
    }
    else if (toolType === 72) {
      const parsed = JSON.parse(contentToParse)
      if (Array.isArray(parsed)) {
        parsed.forEach((item: any) => {
          if (item.messages && item.messages.length) {
            item.messages.forEach((item2: any) => {
              // 如果已经包含html标签则不再渲染
              if (
                !/^(\s*<[^>]+>.*<\/[^>]+>\s*|<[^>]+\/>\s*)$/s.test(
                  item2.content.trim()
                )
              ) {
                item2.content = item2.content.replace(/&lt;/g, '<').replace(/&quot;/g, '"').replace(/&gt;/g, '>')
                item2.content = md.render(item2.content)
              }
            })
          }
        })
      }
      return parsed
    }
    return contentToParse
  }
  catch (error) {
    console.error('解析内容失败:', error)
    return null
  }
}

const processedWorkArray = ref<any[]>([])

// 监听 workArray 和 showData 变化
watch(
  () => [props.workArray, props.showData?.toolType],
  async () => {
    if (props.workArray && props.showData) {
      const _workArray = JSON.parse(JSON.stringify(props.workArray))

      // 处理每个作业内容
      for (const i of _workArray) {
        if (i.content) {
          const processedContent = await processWorkContent(i.content, props.showData.toolType)
          if (processedContent !== null) {
            i.content = processedContent
          }
        }
      }

      processedWorkArray.value = _workArray
    }
    else {
      processedWorkArray.value = []
    }
  },
  { immediate: true, deep: true }
)

// 关闭对应的作业详细页面
const closeSlideIndex = () => {
  visible.value = visible.value.filter((v) => v !== props.slideIndex)
}

// 切换题目
const changeWorkIndex = (type: number) => {
  emit('changeWorkIndex', type)
  // console.log(props.workIndex, props.showData.choiceQuestionListData.length)
  // if (type === 0 && props.workIndex > 0) {
  //   emit('changeWorkIndex', 0)
  // }
  // else if (type === 1 && props.workIndex < props.showData.choiceQuestionListData.length) {
  //   emit('changeWorkIndex', props.workIndex + 1)
  // }
}

// 选择题图表div
const echartsArea1 = ref<any>(null)

// 查看的作业详细id
const lookWorkDetail = ref<string>('')

// 下载加载状态
const downloadLoading = ref(false)

// 查看作业详细的数据
const lookWorkData = computed(() => {
  let _result = null

  if (lookWorkDetail.value && processedWorkArray.value.length > 0) {
    const _workFind = processedWorkArray.value.find(
      (i: any) => i.id === lookWorkDetail.value
    )

    if (_workFind) {
      _result = _workFind
    }

  }

  return _result
})

// 查看图片
const lookImage = (url: string) => {
  if (previewImageToolRef.value) {
    previewImageToolRef.value.previewImage(url)
  }
}

const lookWorkIndex = ref<number>(0)
// 查看作业
const lookWork = (id: string) => {
  lookWorkIndex.value = 0
  lookWorkDetail.value = id
  if (isCastScreen.value && !id) {
    emit('sendMessage', {
      type: 'exit_cast_screen',
      courseid: props.courseid,
    })
    isCastScreen.value = false
  }
}

const isCastScreen = ref<boolean>(false)
// 投屏
const castScreen = (item: any) => {
  lookWorkIndex.value = 0
  lookWorkDetail.value = item.id
  isCastScreen.value = true
  emit('sendMessage', {
    type: 'cast_screen',
    courseid: props.courseid,
    workerData: item
  })
  console.log(item)
}

// 退出投屏
const exitCastScreen = () => {
  if (props.roleType != 1) {
    isCastScreen.value = false
  }
  lookWork('')
}

// 暴露给父级(Student/index.vue)用 ref 调用
defineExpose({ castScreen, exitCastScreen })

// 切换查看作业图片
const changelookWorkIndex = (type: number) => {
  if (type === 0 && lookWorkIndex.value > 0) {
    lookWorkIndex.value = lookWorkIndex.value - 1
  }
  else if (type === 1 && lookWorkIndex.value < lookWorkData.value.content.fileList.length - 1) {
    lookWorkIndex.value = lookWorkIndex.value + 1
  }
}

// 选择题图表实例
const myChart = ref<any>(null)

// resize防抖定时器
let resizeTimer: ReturnType<typeof setTimeout> | null = null

// 处理ECharts resize
const handleChartResize = () => {
  // 清除之前的定时器
  if (resizeTimer) {
    clearTimeout(resizeTimer)
  }

  resizeTimer = setTimeout(() => {
    nextTick(() => {
      if (
        myChart.value &&
        typeof myChart.value.resize === 'function' &&
        !myChart.value.isDisposed()
      ) {
        try {
          myChart.value.resize()
        }
        catch (e) {
          // console.error('myChart resize error:', e)
          // 如果resize失败，重新初始化图表
          if (
            props.showData &&
            props.showData.workDetail &&
            (props.showData.workDetail.type === '45' || props.showData.workDetail.type === '78')
          ) {
            setEchartsArea1()
          }
        }
      }
    })
  }, 200) // 防抖延迟200ms
}

// 设置选择题图表
const setEchartsArea1 = () => {
  // 如果已有实例且未销毁，先销毁
  if (myChart.value && !myChart.value.isDisposed()) {
    myChart.value.dispose()
  }

  if (echartsArea1.value) {
    myChart.value = echarts.init(echartsArea1.value)
  }
  else {
    myChart.value = null
  }

  if (myChart.value) {
    const _work =
      props.showData.choiceQuestionListData[props.showData.workIndex]
    console.log('_work', _work)
    // 修正版，处理xAxis.data内为图片对象的case，formatter始终只拿到src或自定义label，保证无[object Object]问题
    const option = {
      tooltip: {
        show: false, // 禁用鼠标移动到柱体时的内容显示
      },
      yAxis: {
        show: false, // 不显示最左边的y轴
      },
      xAxis: {
        data: [],
        axisLabel: {
          color: function(option: string, idx: number) {
            console.log(option)
            console.log('answerValue.value', answerValue.value)
            const item = _work.choiceUser[idx]
            if (item && item.isAnswer && answerValue.value) {
              // return '#21ee21'
              return '#29AE2B'
            }
            return 'rgba(0, 0, 0, 0.9)'
          },
          fontWeight: 600,
          fontSize: 17,
          lineHeight: 20,
          interval: 0,
          formatter: function(value: any, idx: number) {
            // 如果是字符串且格式为JSON（图片），则解析处理
            if (typeof value === 'string') {
              try {
                const obj = JSON.parse(value)
                if (obj && typeof obj === 'object' && obj.imgType && obj.src) {
                  return '{img' + idx + '|}'
                }
              }
              catch (e) {
                // 非JSON字符串，直接返回
                // 如果文本文字超过8个字，换行
                if (typeof value === 'string') {
                  // 判断value是否全是英文
                  const isAllEnglish = /^[a-zA-Z0-9\s\p{P}]+$/u.test(value)
                  let displayValue = value
                  const maxLength = isAllEnglish ? 30 : 20
                  const lineLength = isAllEnglish ? 16 : 8

                  if (value.length > maxLength) {
                    displayValue = value.substr(0, maxLength) + '...'
                  }
                  // 换行处理
                  let output = ''
                  for (let i = 0; i < displayValue.length; i += lineLength) {
                    output += displayValue.substr(i, lineLength)
                    if (i + lineLength < displayValue.length) {
                      output += '\n'
                    }
                  }
                  return output
                }
                return value
              }
              return value
            }
            // 兼容老格式(容错)：value本身是对象，并有图片信息
            if (
              value &&
              typeof value === 'object' &&
              value.imgType &&
              value.src
            ) {
              return '{img' + idx + '|}'
            }
            // 其他类型直接空
            return ''
          },
          rich: (() => {
            // 动态生成所有图片的 rich 格式
            const richObj: any = {}
            _work.choiceUser.forEach((op: any, idx: number) => {
              if (
                op.option &&
                typeof op.option === 'object' &&
                op.option.imgType &&
                op.option.src
              ) {
                richObj['img' + idx] = {
                  height: 40,
                  width: 40,
                  align: 'center',
                  backgroundColor: {
                    image: op.option.src,
                  },
                }
              }
            })
            return richObj
          })(),
        },
      },
      series: [
        {
          name: '',
          type: 'bar',
          data: [],
          barMaxWidth: 80, // 柱体最宽80px，数量多则自适应
          itemStyle: {
            color: 'rgba(252, 207, 0, 1)',
          },
          label: {
            show: true,
            position: 'top',
            color: 'rgba(116, 139, 115, 1)',
            fontSize: 22,
            fontWeight: 500,
            lineHeight: 24,
          },
        },
      ],
    }

    _work.choiceUser.forEach((i: any, idx: number) => {
      // 如果是图片，存src对象，否则为字符串
      if (
        i.option &&
        typeof i.option === 'object' &&
        i.option.imgType &&
        i.option.src
      ) {
        (option.xAxis.data as any[]).push(
          JSON.stringify({ imgType: i.option.imgType, src: i.option.src })
        ) // 仅保留相关字段
      }
      else if (typeof i.option === 'string') {
        (option.xAxis.data as any[]).push(i.option)
      }
      else {
        (option.xAxis.data as any[]).push('')
      }
      const isCorrect = i.isAnswer && answerValue.value
      ;(option.series[0].data as any[]).push({
        value: i.user.length,
        itemStyle: {
          color: isCorrect ? '#29AE2B' : 'rgba(252, 207, 0, 1)',
        },
        label: {
          show: true,
          position: 'top',
          color: isCorrect ? '#29AE2B' : 'rgba(116, 139, 115, 1)',
          fontSize: 22,
          fontWeight: 500,
          lineHeight: 24,
        },
      })
    })

    // console.log(option)
    // {
    //   title: {
    //     text: 'ECharts 入门示例'
    //   },
    //   tooltip: {},
    //   xAxis: {
    //     data: ['衬衫', '羊毛衫', '雪纺衫', '裤子', '高跟鞋', '袜子']
    //   },
    //   yAxis: {},
    //   series: [
    //     {
    //       name: '销量',
    //       type: 'bar',
    //       data: [5, 20, 36, 10, 10, 20]
    //     }
    //   ]
    // }
    myChart.value.setOption(option)

    myChart.value.off('click')
    myChart.value.on('click', (params: any) => {
      const idx = params.dataIndex
      const selectedOption = _work.choiceUser[idx]
      if (selectedOption && selectUserDialogRef.value) {
        // console.log(selectedOption)
        console.log('selectedOption', selectedOption)
        const selectedOption2 = {...selectedOption}
        if (anonymousValue.value) {
          selectedOption2.user = selectedOption2.user.map((item: any, index: number) => lang.ssAnonymousUser + (index + 1))
        }
        selectUserDialogRef.value.open(`${lang.ssSelectUser.replace('{a}', '<span>' + selectedOption2.index + '</span>')}`, selectedOption2)
      }
    })
  }
}

// 获取分析
const getAnalysis = () => {
  if (!props.workId) {
    return
  }
  console.log('props.workId', props.workId)
  const params = {
    pid: props.workId + (props.cid ? ',' + props.cid : ''),
  }
  axios.get('https://pbl.cocorobo.cn/api/pbl/select_pptAnalysisByPid?pid=' + params.pid).then(res => {
    const data = res[0]
    if (data.length) {
      data.forEach((item: any) => {
        try {
          item.json = JSON.parse(item.json)
        }
        catch (error) {
          item.json = { text: item.json, echartsData: '' }
        }
      })
      aiAnalysisData.value = data
    }
    else {
      aiAnalysisData.value = []
    }
  }).catch(err => {
    console.log('get_pptAnalysis_err', err)
  })
}

// 监听选择题数据变化
watch(
  () => props.showData,
  (newVal, oldVal) => {
    console.log('发生变化,showData')
    if (
      newVal &&
      newVal.choiceQuestionListData[newVal.workIndex] &&
      (props.showData.workDetail.type === '45' || props.showData.workDetail.type === '78')
    ) {
      if (
        oldVal &&
        newVal.choiceQuestionListData[newVal.workIndex] &&
        oldVal.choiceQuestionListData[oldVal.workIndex]
      ) {
        if (
          JSON.stringify(newVal.choiceQuestionListData[newVal.workIndex]) !==
          JSON.stringify(oldVal.choiceQuestionListData[oldVal.workIndex])
        ) {
          setEchartsArea1()
        }
      }
    }
    else {
      myChart.value = null
    }

    // console.log('newVal', newVal)
    // if(newVal && newVal.workDetail && newVal.workDetail.id){
    //   getAnalysis()
    // }
    // getAnalysis()
  },
  { immediate: true, deep: true }
)



// 监听作业变化
watch(
  () => props.showData?.choiceQuestionListData,
  (newVal, oldVal) => {
    console.log('choiceQuestionListData变化了')
    if (
      (newVal || newVal === 0) &&
      props.showData.workDetail &&
      (props.showData.workDetail.type === '45' || props.showData.workDetail.type === '78')
    ) {
      if (JSON.stringify(newVal) !== JSON.stringify(oldVal)) {
        setEchartsArea1()
      }
      else {
        console.log('choiceQuestionListData没有变化')
      }
    }
    else {
      myChart.value = null
    }
  },
  { deep: true }
)

// 监听作业变化
watch(
  () => props.showData?.workIndex,
  (newVal) => {
    if (
      (newVal || newVal === 0) &&
      props.showData.workDetail &&
      (props.showData.workDetail.type === '45' || props.showData.workDetail.type === '78')
    ) {
      setEchartsArea1()
    }
    else {
      myChart.value = null
    }
  }
)

// 监听echartsArea1变化
watch(
  () => echartsArea1.value,
  (newVal) => {
    if (
      newVal &&
      props.showData &&
      props.showData.workDetail &&
      (props.showData.workDetail.type === '45' || props.showData.workDetail.type === '78')
    ) {
      setEchartsArea1()
    }
    else {
      myChart.value = null
    }
  }
)

// 监听页面宽度变化
watch(
  () => props.slideWidth,
  (newVal) => {
    if (
      newVal &&
      props.showData &&
      props.showData.workDetail &&
      (props.showData.workDetail.type === '45' || props.showData.workDetail.type === '78')
    ) {
      handleChartResize()
    }
  }
)

// 查看未提交学生
const viewUnsubmittedStudents = () => {
  selectUserDialogRef.value.open(lang.ssSubmitStatus, { user: props.unsubmittedStudents.map((item: any) => item.name), notFiledUser: props.unsubmittedStudents.map((item: any) => item.name), isSubmitUser: props.workArray.map((item: any) => item.name) })
  // if (props.unsubmittedStudents.length > 0) {
  // unsubmittedStudentsDialogRef.value.open(props.unsubmittedStudents)
  // }
}

// ai生成选择题分析 选择题
const aiAnalysisRefresh45 = () => {
  const _work = props.showData.choiceQuestionListData[props.showData.workIndex]
  const msg = `# CONTEXT #
你是K-12阶段的AI教育课堂分析助手，基于上传的课件、逐字稿，以及当页的学生答题数据（选择题/问答题/智能体对话）进行智能分析。

# OBJECTIVE #
输出当前学生答题的分析报告：整体表现、核心发现（共性问题/误区）、教学优化(改进方向)，为教师提供教学策略的建议和支持。

#INPUT#
课程数据：
- 课程名称：${props.courseDetail.title}
- 课程学科：${props.courseDetail.name}
当前页面答题数据(选择题)：【分析重点】
- 选择题题目：${_work.teststitle}
- 选项数据：${JSON.stringify(_work.choiceUser)}
- 题目图片：${_work.timuList.lenght ? _work.timuList[0].src : ''}
- 未提交学生：${JSON.stringify(props.showData.unsubmittedStudents.map((item: any) => item.name))}

# ANALYSIS RULES #
1. **问题定位**：明确指出哪个知识点/概念/步骤掌握不佳
2. **建议具体**：给出可执行的教学动作(如“增加XX实例演练”“补充XX对比图”)

# RESPONSE #
采用段落叙述，数据量化呈现，突出可操作建议，严格控制输出为80词内。采用三段式论述：
1. 整体表现-1句话
2. 核心发现-1-2句，指出共性问题+典型案例
3. 改进建议-1句话，提出具体教学动作

# EXAMPLES #
样例：
选择题正确率62%，核心概念“机器学习三步骤”（输入数据→训练模型→预测结果）掌握尚可，但“训练与预测区分”混淆率达38%；建议强化训练vs预测对比教学。`

  if (!currentAnalysis.value) {
    aiAnalysisData.value.push({
      pid: props.workId + (props.cid ? ',' + props.cid : ''),
      index: props.showData.workIndex,
      loading: true,
      generatingContent: true,
      json: { text: '', echartsData: '' },
      noEnd: true,
      update_at: '',
      create_at: '',
    })
  }
  else {
    aiAnalysisData.value.find((item: any) => {
      return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
    }).loading = true
    aiAnalysisData.value.find((item: any) => {
      return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
    }).json = { text: '', echartsData: '' }
  }

  chat_stream(msg, 'a7741704-ba56-40b7-a6b8-62a423ef9376', props.userId, lang.lang, (event) => {
    if (event.type === 'message') {
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).json.text = event.data

      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).loading = false
    }
    else if (event.type === 'messageEnd') {
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).json.text = event.data
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).noEnd = false
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).update_at = new Date().toLocaleString('zh-CN', { year: 'numeric', month: '2-digit', day: '2-digit', hour: '2-digit', minute: '2-digit', second: '2-digit', hour12: false }).replace(/\//g, '-')
      saveAnalysis()
    }
  }).catch(err => {
    console.log('err', err)
  })
}

// ai生成投票分析 投票
const aiAnalysisRefresh78 = () => {
  const _work = props.showData.choiceQuestionListData[props.showData.workIndex]
  const msg = `# CONTEXT #
你是K-12阶段的AI教育课堂分析助手，基于上传的课件、逐字稿，以及当页的学生答题数据（选择题/问答题/智能体对话/投票）进行智能分析。

# OBJECTIVE #
输出当前学生答题的分析报告：整体表现、核心发现（共性问题/误区）、教学优化(改进方向)，为教师提供教学策略的建议和支持。

#INPUT#
课程数据：
- 课程名称：${props.courseDetail.title}
- 课程学科：${props.courseDetail.name}
当前页面答题数据(投票)：【分析重点】
- 投票题目：${_work.teststitle}
- 选项数据：${JSON.stringify(_work.choiceUser)}
- 题目图片：${_work.timuList.lenght ? _work.timuList[0].src : ''}
- 未提交学生：${JSON.stringify(props.showData.unsubmittedStudents.map((item: any) => item.name))}

# ANALYSIS RULES #
1. **问题定位**：明确指出哪个知识点/概念/步骤掌握不佳
2. **建议具体**：给出可执行的教学动作(如“增加XX实例演练”“补充XX对比图”)

# RESPONSE #
采用段落叙述，数据量化呈现，突出可操作建议，严格控制输出为80词内。采用三段式论述：
1. 整体表现-1句话
2. 核心发现-1-2句，指出共性问题+典型案例
3. 改进建议-1句话，提出具体教学动作

# EXAMPLES #
样例：
选择题正确率62%，核心概念“机器学习三步骤”（输入数据→训练模型→预测结果）掌握尚可，但“训练与预测区分”混淆率达38%；建议强化训练vs预测对比教学。`

  if (!currentAnalysis.value) {
    aiAnalysisData.value.push({
      pid: props.workId + (props.cid ? ',' + props.cid : ''),
      index: props.showData.workIndex,
      loading: true,
      generatingContent: true,
      json: { text: '', echartsData: '' },
      noEnd: true,
      update_at: '',
      create_at: '',
    })
  }
  else {
    aiAnalysisData.value.find((item: any) => {
      return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
    }).loading = true
    aiAnalysisData.value.find((item: any) => {
      return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
    }).json = { text: '', echartsData: '' }
  }

  chat_stream(msg, 'a7741704-ba56-40b7-a6b8-62a423ef9376', props.userId, lang.lang, (event) => {
    if (event.type === 'message') {
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).json.text = event.data

      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).loading = false
    }
    else if (event.type === 'messageEnd') {
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).json.text = event.data
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).noEnd = false
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).update_at = new Date().toLocaleString('zh-CN', { year: 'numeric', month: '2-digit', day: '2-digit', hour: '2-digit', minute: '2-digit', second: '2-digit', hour12: false }).replace(/\//g, '-')
      saveAnalysis()
    }
  }).catch(err => {
    console.log('err', err)
  })
}

// 问答题
const aiAnalysisRefresh15 = () => {
  let flag = 0
  const msg = `# CONTEXT #
你是K-12阶段的AI教育课堂分析助手，基于上传的课件、逐字稿，以及当页的学生答题数据（选择题/问答题/智能体对话）进行智能分析。

# OBJECTIVE #
输出当前学生答题的分析报告：整体表现、核心发现（共性问题/误区）、教学优化(改进方向)，为教师提供教学策略的建议和支持。

#INPUT#
课程数据：
- 课程名称：${props.courseDetail.title}
- 课程学科：${props.courseDetail.name}
当前页面答题数据(问答题)：【分析重点】
- 问答题题目：${props.showData.workDetail.json.answerQ}
- 回答数据：${JSON.stringify(processedWorkArray.value.map((i) => ({ user: i.name, answer: i.content.answer })))}
- 未提交学生：${JSON.stringify(props.showData.unsubmittedStudents.map((item: any) => item.name))}

# ANALYSIS RULES #
1. **问题定位**：明确指出哪个知识点/概念/步骤掌握不佳
2. **建议具体**：给出可执行的教学动作(如“增加XX实例演练”“补充XX对比图”)

# RESPONSE #
采用段落叙述，数据量化呈现，突出可操作建议，严格控制输出为80词内。采用三段式论述：
1. 整体表现-1句话
2. 核心发现-1-2句，指出共性问题+典型案例
3. 改进建议-1句话，提出具体教学动作

# EXAMPLES #
样例：
30人中15人提交问答题（参与率50%），核心概念“同理心地图”掌握薄弱。发现学生13在智能体对话中6次答“不知道”,需单独辅导设计思维基础概念。建议课程增加POV框架实例演练，强化痛点识别能力训练。`
  if (!currentAnalysis.value) {
    aiAnalysisData.value.push({
      pid: props.workId + (props.cid ? ',' + props.cid : ''),
      index: props.showData.workIndex,
      loading: true,
      generatingContent: true,
      json: { text: '', echartsData: '' },
      noEnd: true,
      update_at: '',
      create_at: '',
    })
  }
  else {
    aiAnalysisData.value.find((item: any) => {
      return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
    }).loading = true
    aiAnalysisData.value.find((item: any) => {
      return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
    }).json = { text: '', echartsData: '' }
    aiAnalysisData.value.find((item: any) => {
      return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
    }).generatingContent = true
  }
  getWordCloud15().then((res) => {
    flag += 1
    aiAnalysisData.value.find((item: any) => {
      return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
    }).generatingContent = false
    if (flag == 2) {
      saveAnalysis()
    }
  })
  chat_stream(msg, 'a7741704-ba56-40b7-a6b8-62a423ef9376', props.userId, lang.lang, (event) => {
    console.log(event)
    if (event.type === 'message') {
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).json.text = event.data

      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).loading = false
    }
    else if (event.type === 'messageEnd') {
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).json.text = event.data
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).noEnd = false
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).update_at = new Date().toLocaleString('zh-CN', { year: 'numeric', month: '2-digit', day: '2-digit', hour: '2-digit', minute: '2-digit', second: '2-digit', hour12: false }).replace(/\//g, '-')
      flag += 1
      if (flag == 2) {
        saveAnalysis()

      }
    }
  }).catch(err => {
    console.log('err', err)
  })
}

// 打开词云图弹窗
const openEchatsDialog = () => {
  if (echartsDialogRef.value && currentAnalysis.value.json.echartsData) {
    echartsDialogRef.value.open(lang.ssKeywordCloud, currentAnalysis.value.json.echartsData)
  }
}



// 问答题获取词云图与关键词
const getWordCloud15 = () => {

  return new Promise((resolve,) => {
    const msg = `## 任务
请针对文本中学生提交的问答题回答内容进行深度分析，提炼出 10 - 30 个核心关键词，用于绘制词云图。
## 提取准则
1. 聚焦内容主体：仅从学生的具体回答文本中提取关键词。
2. 严格排除杂质：禁止提取任何属于系统元数据或固定格式的词汇，包括但不限于：“课程数据”、“学生姓名”、“回答结果”、“课程标题”、“提交时间”、“作业名称”、“分数”等。
3. 语义去重：将意思相近的词进行合并（例如“高效”与“效率高”），保留最具代表性的词条。
4. 涵盖核心：关键词应准确反映学生回答中的核心观点、关键知识点、高频论据或情感倾向。
## 任务要求
1. 词频统计：计算每个有效关键字在回答内容中出现的频率。
2. 词汇大小：根据词频，确定每个关键字在词云中的权重。词频越高，数值越大，范围 1 - 100。
3. 输出格式：请严格按照 JSON 格式输出，包含关键词、词频及对应的词汇大小。

## 文本
课程数据：
- 课程名称：${props.courseDetail.title}
- 课程学科：${props.courseDetail.name}
- 需要提交人数：${props.showData.workArray.length + props.showData.unsubmittedStudents.length}
- 已提交人数：${props.showData.workArray.length}
当前页面答题数据(问答题)：【分析重点】
- 问答题题目：${props.showData.workDetail.json.answerQ}
- 回答数据：${JSON.stringify(processedWorkArray.value.map((i) => ({ answer: i.content.answer })))}

## 输出示例
{"tooltip":{"show":false},"series":[{"type":"wordCloud","sizeRange":[14,38],"rotationRange":[0,0],"keepAspect":false,"shape":"circle","left":"center","top":"center","right":null,"bottom":null,"width":"100%","height":"100%","rotationStep":20,"data":[{"value":"词汇大小，数值范围1-100","name":"词汇","textStyle":{"color":"词汇颜色（16进制）"}},{"value":"词汇大小，数值范围1-100","name":"词汇","textStyle":{"color":"（16进制）"}}]}]}`


    chat_no_stream(msg, 'a7741704-ba56-40b7-a6b8-62a423ef9376', props.userId, lang.lang).promise.then((res) => {
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).json.echartsData = JSON.parse(res)
      resolve(1)
    }).catch(err => {
      console.log('err', err)
      resolve(0)
    })
  })


}

// ai应用
const aiAnalysisRefresh72 = async () => {

  let chatMsg = ``
  const agentId = 'a7741704-ba56-40b7-a6b8-62a423ef9376'
  console.log('processedWorkArray.value', processedWorkArray.value)
  processedWorkArray.value.forEach((i) => {
    if (typeof i.content === 'object') {
      i.content.forEach(j => {
        if (j.messages) {
          j.messages.forEach((a) => {
            chatMsg += `\n${a.sender}：
${a.content}\n`
          })
        }
        if (j.imageUrls) {
          j.imageUrls.forEach((a) => {
            chatMsg += `\n${a}\n`
          })
        }

      })
    }
  })
  // if(props.userId)

  // - 未提交学生：${JSON.stringify(props.showData.unsubmittedStudents.map((item: any) => item.name))}
  let msg = `# CONTEXT #
你是K-12阶段的AI教育课堂分析助手，基于上传的课件、逐字稿，以及当页的学生答题数据（选择题/问答题/智能体对话）进行智能分析。

# OBJECTIVE #
输出当前学生答题的分析报告：整体表现、核心发现（共性问题/误区）、教学优化(改进方向)，为教师提供教学策略的建议和支持。

#INPUT#
课程数据：
- 课程名称：${props.courseDetail.title}
- 课程学科：${props.courseDetail.name}
- 需要提交人数：${props.showData.workArray.length + props.showData.unsubmittedStudents.length}
- 已提交人数：${props.showData.workArray.length}
当前页面答题数据(问答题)：【分析重点】
- AI应用
- 对话数据：${chatMsg}


# ANALYSIS RULES #
1. **问题定位**：明确指出哪个知识点/概念/步骤掌握不佳
2. **建议具体**：给出可执行的教学动作(如“增加XX实例演练”“补充XX对比图”)

# RESPONSE #
采用段落叙述，数据量化呈现，突出可操作建议，严格控制输出为80词内。采用三段式论述：
1. 整体表现-1句话
2. 核心发现-1-2句，指出共性问题+典型案例
3. 改进建议-1句话，提出具体教学动作

# EXAMPLES #
样例：
智能体对话显示学生对“模型训练”概念模糊，多次询问“为什么不能直接告诉机器答案”。针对概念混淆学生，补充“人类学习类比”相关解释,巩固“从数据中学习规律”核心认知。`


  if (['9c236d45-49cd-11f1-9985-005056924926'].includes(props.userId)) {
    msg = `你是K-12阶段的AI教育课堂分析助手，基于当前课程信息以及当页的学生与单/多智能体对话数据，进行深入的智能分析。

### 任务目标
1. **总体统计分析**：
   - 分析学生表现数据，例如全班学生互动数据，包括但不限于参与度、互动轮次、作文批改分布、作业完成情况等。
   - 提取核心统计指标，例如发现共性问题、互动模式、分层水平分布、关键评分、完成度、优秀或需关注的学生。

2. **洞察（Key Insights）**：
   - 不是所有模块都需要的
   - 输出的模块使用1～3句快速完成核心发现输出
   - 保持简短、直观、易快速理解。
3. **不输出教学建议或干预措施**。

### 输出格式
1. Markdown表格：展示关键统计指标（发言次数、互动频率、提问数量、主题分布）。
2. ASCII条形图（可选）：展示各项指标对比情况（绝对不要ASCII条形图，应该显示指标名字）
3. 洞察与建议：分点呈现，每点对应具体统计指标或数据来源，保持精简，直观、易快速理解。
**注意，不必输出多余的开场白（可以有非常简短的），转场，铺垫，形容词等，尽可能把输出留给有价值的发现**
**对于重点要注意的内容，可以用 <span style="color:red"> 内容 </span> 以及 markdown的强调语法来highlight**

### 注意事项
- 输出简洁明了，重点突出。
- 所有数字列右对齐，必要时显示百分比。
- 避免冗长文字和详细案例描述。
- 保持专业、友好语气，可使用 Emoji 提示情绪、课堂氛围或学生表现状态。
- 输出保持在600字左右

#INPUT#
课程数据：
- 课程名称：${props.courseDetail.title}
- 课程学科：${props.courseDetail.name}
当前页面答题数据(问答题)：【分析重点】
- AI应用
- 对话数据：${chatMsg}
`
  }
  else if (['6c56ec0e-2c74-11ef-bee5-005056b86db5', 'aea65da6-4399-11f1-9985-005056924926'].includes(props.userId)) {

    if (props.workUrl == 'https://knowledge.cocorobo.cn/zh-CN/story-telling/a1a339d4-f522-4336-9aa9-e8394bea9731') {
      msg = `# 角色定位

你是K-12阶段的AI课堂分析助手，负责基于学生对世界名画的英语宣传稿（promotional text）批改记录生成课堂学情分析报告。
本次分析的内容来自六年级英语Art课堂，学生选择一幅画作并完成英语宣传稿写作，由AI智能体完成批改，分为 Level A（独立完成）、Level B（信息辅助）、Level C（支架辅助）两个等级。

---

# 重要：数据解读规则（必须在生成报告前完成）

在输出任何报告内容之前，必须先完成以下两步结构化提取。
所有报告数字必须来源于此，禁止前后矛盾。

---

## 第一步：逐学生提取数据

（此步骤为内部处理步骤，不输出提取结果。）

### 有效作文判断

在提取每位学生数据之前，先判断该学生是否提交了有效作文：

**有效作文：** AI批改记录中出现了完整的"作文批改报告"结构（包含信息完整性表格、表达鲜活度、文化小触角、语法小诊断中至少两项），视为学生已提交有效内容，正常提取数据。

**无效提交：** 以下情况均视为无效提交，不纳入各维度统计，仅在总结部分单独列出：
- AI输出"未检测到有效的写作内容"
- AI批改记录缺失或仅有对话内容而无批改报告结构
- 学生仅回复单个词语、符号或与写作任务完全无关的内容

**注意：** 不得根据学生与AI的后续对话内容（如学生补充回复、追问等）判断写作有效性，仅以AI是否输出完整批改报告为准。

### 等级识别
从批改记录中识别学生选择的等级：
- 选择"I can wtite. 我可以自己写。" → Level A
- 选择"I need information. 我需要信息支持。" → Level B
- 选择"I need structure. 我需要支架。" → Level C

### 信息完整与准确性提取
检查批改报告中的信息完整性表格，逐项记录每位学生的情况：

| 信息点 | 是否正确 |
|---|---|
| 画名 | 是/否 |
| 画家 | 是/否 |
| 绘画种类 | 是/否 |
| 画面描述（颜色/内容） | 是/否 |
| 个人感受 | 是/否 |

对每位学生统计：
- 全部正确的信息点数量（满分5项）
- 有错误或遗漏的具体信息点

### 表达鲜活度提取
从批改记录的"表达鲜活度"部分，判断：
- ✅ 表达生动：使用了形容词、比喻、比较句或个人联想
- ⚠️ 表达平淡：仅使用简单句型，缺乏个人想法

### 文化小触角提取
从批改记录的"文化小触角"部分，判断：
- ✅ 有涉及：自然提到中西艺术差异或文化感悟
- — 未涉及：未提及任何文化对比

### 语法情况提取
从批改记录的"语法小诊断"部分，记录：
- 是否存在明显语法错误
- 错误类型（主谓一致 / 时态 / 冠词 / 其他）

---

## 第二步：汇总数据

将所有学生数据按等级分组汇总，形成统计表。
**一旦汇总完成，报告中所有数字必须与汇总表严格一致，禁止前后矛盾。**

---

# 输出格式

## 第一步输出
输出以下一句话，然后立即继续输出完整报告，不得停止：
"正在逐个提取学生数据中，请稍候……"

## 第二步输出：完整报告

紧接上一句，输出以下完整报告内容：

---

## 英语写作　课堂学情分析报告

**数据来源：** 批改记录　｜　**统计人数：** X 人

---

### 一、分层总览

| 等级 | 人数 | 信息完整率均值 | 表达生动人数 | 文化触角人数 | 有语法问题人数 |
|---|---|---|---|---|---|
| Level A | X | XX% | X人(XX%) | X人(XX%) | X人(XX%) |
| Level B | X | XX% | X人(XX%) | X人(XX%) | X人(XX%) |
| Level C | X | XX% | X人(XX%) | X人(XX%) | X人(XX%) |

---

### 二、信息完整与准确性明细（A / B / C 合并）

| 信息点 | 正确人数 | 正确率 |
|---|---|---|
| 画名 | X | XX% |
| 画家 | X | XX% |
| 绘画种类 | X | XX% |
| 画面描述（颜色/内容） | X | XX% |
| 个人感受 | X | XX% |

[正确率最低项：<span style="color:red">⚠️ [信息点名称]正确率最低，仅 XX%，说明学生在该项普遍存在遗漏或错误。</span>]

---

### 三、表达与文化维度

| 维度 | A 达成人数 | A 达成率 | B 达成人数 | B 达成率 | C 达成人数 | C 达成率 |
|---|---|---|---|---|
| 表达生动（含比喻/形容词/个人联想） | X | XX% | X | XX% | X | XX% |
| 文化小触角（含中西艺术对比） | X | XX% | X | XX% | X | XX% |

[若文化触角整体达成率低于50%：<span style="color:red">⚠️ 文化对比意识普遍薄弱，全班达成率仅 XX%。</span>]

---

### 四、语法问题汇总

| 语法问题类型 | A 出现人次 | B 出现人次 | C 出现人次 |
|---|---|---|
| 主谓一致错误 | X | X | X |
| 时态错误 | X | X | X |
| 冠词错误 | X | X | X |
| 其他 | X | X | X |

*若无明显语法问题，写："本次无明显高频语法问题。✅"*

---

### 五、亮点摘录

**表达生动的例句：**
[列出2–3句来自学生作文的优秀表达原文，注明等级和画作名称。]

**文化感悟的例句：**
[列出1–2句来自学生作文的文化对比原文，注明等级和画作名称。若无，写"本次暂无。"]

---

### 六、总结

**整体：** [1句，简述全班整体写作完成情况。]

**突出：** [1句，指出全班表现最好的维度，例如信息完整率高或表达生动人数较多。]

**关注：** <span style="color:red">[1句，指出最薄弱的维度，例如文化触角普遍缺失或某信息点遗漏率高。]</span>

**跟进：**
- <span style="color:red">无效提交学生：[姓名列表]，AI未能识别其提交内容，建议教师查看原图并确认是否需要重新上传。</span>
- <span style="color:red">写作内容需关注的学生（有效提交中）：[姓名及原因，例如信息缺失3项以上、存在多处语法问题等]；若无，写"有效提交学生中暂无需特别跟进。"</span>

*若全员有效提交且表现均衡，写："本次全员提交有效内容，整体表现均衡，暂无需特别跟进。"*

---

# 注意事项

- 所有数字来源于结构化提取，输出前核对一致性，禁止前后矛盾。
- 对需要教师重点关注的内容使用 <span style="color:red"> 内容 </span> 高亮。
- 禁止输出"如需进一步生成"等对话式内容。
- 不输出教学建议或干预措施。
- 若某等级无学生数据，对应列填"—"，不单独说明。

#INPUT#
课程数据：
- 课程名称：${props.courseDetail.title}
- 课程学科：${props.courseDetail.name}
- 需要提交人数：${props.showData.workArray.length + props.showData.unsubmittedStudents.length}
- 已提交人数：${props.showData.workArray.length}
当前页面答题数据(AI应用)：【分析重点】
- AI应用
- 对话数据：${chatMsg}`
    }
    else if (props.workUrl == 'https://knowledge.cocorobo.cn/zh-CN/story-telling/0d04cef1-876a-41b4-9768-6547088bc162') {
      msg = `# 角色定位

你是K-12阶段的AI课堂分析助手，负责基于学生词句训练对话记录生成课堂学情分析报告。
本次分析的环节为：学生与AI就画作内容进行词句问答训练，分为 Level A、Level B、Level C 三个等级。

---

# 重要：数据解读规则（必须在生成报告前完成）

在输出任何报告内容之前，必须先完成以下两步结构化提取。
所有报告数字必须来源于此，禁止前后矛盾。

---

## 第一步：逐学生提取数据

（此步骤为内部处理步骤，不输出提取结果。）

### 等级识别
从对话记录中的 sender 字段识别等级：
- sender 含"Level A" → Level A
- sender 含"Level B" → Level B
- sender 含"Level C" → Level C

### 完成状态判断
- **完整完成**：所有句子/问题均有学生回应记录
- **部分完成**：至少一条学生回应，但未完成全部
- **未完成**：对话记录中仅有 AI 开场消息，无任何学生回应内容

### Level A 提取项目

**主题覆盖性：** 检查学生是否主动提问了以下 6 个主题：
① name　② artist　③ kind　④ scene　⑤ colours　⑥ why
- ✅ 已提问 / — 未提问

**问题准确性（语法）：** 识别以下错误类型并记录人次：
- 疑问句结构错误 / 主谓一致错误 / 时态错误 / 其他

**创新性：** 6 个主题之外的问题，记录原文。

### Level B 提取项目

**主题覆盖性：**（同 Level A，6个主题）

**问题准确性（语法）：**（同 Level A）

### Level C 提取项目

**流程完成性：** 逐句核对学生是否跟读了全部 6 个问句。
- ✅ 跟读基本正确 / ⚠️ 跟读明显偏差 / — 未跟读

**创新亮点：** 学生是否有自发延伸表达，记录原文。

---

## 第二步：汇总数据

将所有学生数据按等级分组汇总。
**报告中所有数字必须与汇总表严格一致，禁止前后矛盾。**

---

# 输出格式

## 第一步输出
输出以下一句话，然后立即继续输出完整报告，不得停止：
"正在逐个提取学生数据中，请稍候……"

## 第二步输出：完整报告

紧接上一句，输出以下完整报告内容：

---

## 词句问答训练　课堂学情分析报告

**数据来源：** 学生对话记录　｜　**统计人数：** X 人

---

### 一、分层总览

| 等级 | 人数 | 完整完成 | 主题覆盖率均值 | 语法问题人数 | 创新提问/亮点 |
|---|---|---|---|---|---|
| Level A | X | X人(XX%) | XX% | X人 | X人 |
| Level B | X | X人(XX%) | XX% | X人 | — |
| Level C | X | X人(XX%) | — | — | X人 |

[若有未完成学生：<span style="color:red">⚠️ 未完成学生：[姓名列表]</span>]

---

### 二、主题覆盖明细（Level A / B）

| 主题 | A 覆盖率 | B 覆盖率 |
|---|---|---|
| name | XX% | XX% |
| artist | XX% | XX% |
| kind | XX% | XX% |
| scene | XX% | XX% |
| colours | XX% | XX% |
| why | XX% | XX% |

*若本次无某等级学生，对应列填"—"。*

---

### 三、语法问题（Level A / B）

| 问题类型 | A 出现人次 | B 出现人次 |
|---|---|---|
| 疑问句结构错误 | X | X |
| 主谓一致错误 | X | X |
| 时态错误 | X | X |
| 其他 | X | X |

*若无语法问题，写："本次无明显语法问题。✅"*

---

### 四、创新与亮点

**Level A 创新提问：**
[列出学生姓名及原文；若无，写"本次暂无。"]

**Level C 自发延伸：**
[列出学生姓名及原文；若无，写"本次暂无。"]

---

### 五、总结

**整体：** [1句，简述全班完成情况。]

**突出：** [1句，指出表现最好的维度或等级。]

**关注：** <span style="color:red">[1句，指出覆盖率最低的主题或问题最集中的点。]</span>

**跟进：** <span style="color:red">[列出需个别跟进的学生姓名及原因；若无，写"全员表现均衡，暂无需特别跟进。"]</span>

---

# 注意事项

- 所有数字来源于结构化提取，输出前核对一致性，禁止前后矛盾。
- 对需要教师重点关注的内容使用 <span style="color:red"> 内容 </span> 高亮。
- 若某等级无学生数据，相关行/列填"—"，不单独输出该等级报告。
- 禁止输出"如需进一步生成"等对话式内容。
- 不输出教学建议或干预措施。

#INPUT#
课程数据：
- 课程名称：${props.courseDetail.title}
- 课程学科：${props.courseDetail.name}
- 需要提交人数：${props.showData.workArray.length + props.showData.unsubmittedStudents.length}
- 已提交人数：${props.showData.workArray.length}
当前页面答题数据(AI应用)：【分析重点】
- AI应用
- 对话数据：${chatMsg}`
    }

    //     msg = `# 角色定位
    // 你是K-12阶段的AI课堂分析助手，负责基于学生词句训练对话记录生成课堂学情分析报告。
    // 本次分析的环节为：学生与AI就画作内容进行词句问答训练，分为 Level A、Level B、Level C 三个等级。
    // ---
    // # 重要：数据解读规则（必须在生成报告前完成）
    // 在输出任何报告内容之前，必须先完成以下两步结构化提取。
    // 所有报告数字必须来源于此，禁止前后矛盾。
    // ---
    // ## 第一步：逐学生提取数据
    // （此步骤为内部处理步骤，不输出提取结果。）
    // ### 等级识别
    // 从对话记录中的 sender 字段识别等级：
    // - sender 含"Level A" → Level A
    // - sender 含"Level B" → Level B
    // - sender 含"Level C" → Level C
    // ### 完成状态判断
    // - **完整完成**：所有句子/问题均有学生回应记录
    // - **部分完成**：至少一条学生回应，但未完成全部
    // - **未完成**：对话记录中仅有 AI 开场消息，无任何学生回应内容
    // ### Level A 提取项目
    // **主题覆盖性：** 检查学生是否主动提问了以下 6 个主题：
    // ① name　② artist　③ kind　④ scene　⑤ colours　⑥ why
    // - ✅ 已提问 / — 未提问
    // **问题准确性（语法）：** 识别以下错误类型并记录人次：
    // - 疑问句结构错误 / 主谓一致错误 / 时态错误 / 其他
    // **创新性：** 6 个主题之外的问题，记录原文。
    // ### Level B 提取项目
    // **主题覆盖性：**（同 Level A，6个主题）
    // **问题准确性（语法）：**（同 Level A）
    // ### Level C 提取项目
    // **流程完成性：** 逐句核对学生是否跟读了全部 6 个问句。
    // - ✅ 跟读基本正确 / ⚠️ 跟读明显偏差 / — 未跟读
    // **创新亮点：** 学生是否有自发延伸表达，记录原文。
    // ---
    // ## 第二步：汇总数据
    // 将所有学生数据按等级分组汇总。
    // **报告中所有数字必须与汇总表严格一致，禁止前后矛盾。**
    // ---
    // # 输出格式
    // ## 第一步输出
    // 输出以下一句话，然后立即继续输出完整报告，不得停止：
    // "正在逐个提取学生数据中，请稍候……"
    // ## 第二步输出：完整报告
    // 紧接上一句，输出以下完整报告内容：
    // ---
    // ## 词句问答训练　课堂学情分析报告
    // **数据来源：** 学生对话记录　｜　**统计人数：** X 人
    // ---
    // ### 一、分层总览
    // | 等级 | 人数 | 完整完成 | 主题覆盖率均值 | 语法问题人数 | 创新提问/亮点 |
    // |---|---|---|---|---|---|
    // | Level A | X | X人(XX%) | XX% | X人 | X人 |
    // | Level B | X | X人(XX%) | XX% | X人 | — |
    // | Level C | X | X人(XX%) | — | — | X人 |
    // [若有未完成学生：<span style="color:red">⚠️ 未完成学生：[姓名列表]</span>]
    // ---
    // ### 二、主题覆盖明细（Level A / B）
    // | 主题 | A 覆盖率 | B 覆盖率 |
    // |---|---|---|
    // | name | XX% | XX% |
    // | artist | XX% | XX% |
    // | kind | XX% | XX% |
    // | scene | XX% | XX% |
    // | colours | XX% | XX% |
    // | why | XX% | XX% |
    // *若本次无某等级学生，对应列填"—"。*
    // ---
    // ### 三、语法问题（Level A / B）
    // | 问题类型 | A 出现人次 | B 出现人次 |
    // |---|---|---|
    // | 疑问句结构错误 | X | X |
    // | 主谓一致错误 | X | X |
    // | 时态错误 | X | X |
    // | 其他 | X | X |
    // *若无语法问题，写："本次无明显语法问题。✅"*
    // ---
    // ### 四、创新与亮点
    // **Level A 创新提问：**
    // [列出学生姓名及原文；若无，写"本次暂无。"]
    // **Level C 自发延伸：**
    // [列出学生姓名及原文；若无，写"本次暂无。"]
    // ---
    // ### 五、总结
    // **整体：** [1句，简述全班完成情况。]
    // **突出：** [1句，指出表现最好的维度或等级。]
    // **关注：** <span style="color:red">[1句，指出覆盖率最低的主题或问题最集中的点。]</span>
    // **跟进：** <span style="color:red">[列出需个别跟进的学生姓名及原因；若无，写"全员表现均衡，暂无需特别跟进。"]</span>
    // ---
    // # 注意事项
    // - 所有数字来源于结构化提取，输出前核对一致性，禁止前后矛盾。
    // - 对需要教师重点关注的内容使用 <span style="color:red"> 内容 </span> 高亮。
    // - 若某等级无学生数据，相关行/列填"—"，不单独输出该等级报告。
    // - 禁止输出"如需进一步生成"等对话式内容。
    // - 不输出教学建议或干预措施。

    // #INPUT#
    // 课程数据：
    // - 课程名称：${props.courseDetail.title}
    // - 课程学科：${props.courseDetail.name}
    // - 需要提交人数：${props.showData.workArray.length + props.showData.unsubmittedStudents.length}
    // - 已提交人数：${props.showData.workArray.length}
    // 当前页面答题数据(AI应用)：【分析重点】
    // - AI应用
    // - 对话数据：${chatMsg}`


  }



  console.log('workUrl', props.workUrl)
  console.log('ai应用提示词', msg)
  if (!currentAnalysis.value) {
    aiAnalysisData.value.push({
      pid: props.workId + (props.cid ? ',' + props.cid : ''),
      index: props.showData.workIndex,
      loading: true,
      json: { text: '', echartsData: '' },
      noEnd: true,
      update_at: '',
      create_at: '',
    })
  }
  else {
    aiAnalysisData.value.find((item: any) => {
      return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
    }).loading = true
    aiAnalysisData.value.find((item: any) => {
      return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
    }).json = { text: '', echartsData: '' }
  }

  chat_stream(msg, 'a7741704-ba56-40b7-a6b8-62a423ef9376', props.userId, lang.lang, (event) => {
    if (event.type === 'message') {
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).json.text = md.render(event.data)

      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).loading = false
    }
    else if (event.type === 'messageEnd') {
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).json.text = md.render(event.data)
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).noEnd = false
      aiAnalysisData.value.find((item: any) => {
        return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
      }).update_at = new Date().toLocaleString('zh-CN', { year: 'numeric', month: '2-digit', day: '2-digit', hour: '2-digit', minute: '2-digit', second: '2-digit', hour12: false }).replace(/\//g, '-')
      saveAnalysis()
    }
  }, '', [], 'open-qwen-plus-latest').catch(err => {
    console.log('err', err)
  })
}


// 当前分析
const currentAnalysis = computed(() => {
  const _result = aiAnalysisData.value.find((item: any) => {
    return item.pid === props.workId + (props.cid ? ',' + props.cid : '') && item.index === props.showData.workIndex
  })

  if (_result?.json?.echartsData) {
    _result.json.keyword = _result.json.echartsData?.series?.[0]?.data?.slice(0, 5).map((item: any) => item.name)
  }


  if (_result) {
    return _result
  }

  return null

})

// 保存分析
const saveAnalysis = () => {
  if (!currentAnalysis.value) {
    return
  }
  const params = [{
    pid: props.workId + (props.cid ? ',' + props.cid : ''),
    idx: props.showData.workIndex,
    json: JSON.stringify(currentAnalysis.value.json),
  }]

  console.log(params)
  axios.post('https://pbl.cocorobo.cn/api/pbl/insert_pptAnalysis', params).then(res => {
    if (res == 1) {
      console.log('保存成功')
    }
  }).catch(err => {
    console.log('insert_pptAnalysis_err', err)
  })
}


// 点击边框
const clickContent = (flag: boolean) => {
  if (flag && lookWorkDetail.value && workDetail.value?.type !== '45' && workDetail.value?.type !== '78') {
    if (props.roleType != 1 && isCastScreen.value) {
      return
    }
    lookWork('')
  }
}

// 监听 props.showData.workDetail.id 变化
watch(
  () => props.showData?.workDetail,
  (newId, oldId) => {
    getAnalysis()
  },
  { immediate: true }
)


// 批量下载
const downloadAll = async () => {
  if (!processedWorkArray.value || processedWorkArray.value.length === 0) {
    return
  }
  if (downloadLoading.value) {
    return
  }
  // 设置加载状态
  downloadLoading.value = true

  try {
    // 动态导入 JSZip
    const JSZip = (await import('jszip')).default
    const { saveAs } = await import('file-saver')

    const zip = new JSZip()

    // 遍历所有学生
    for (const student of processedWorkArray.value) {
      if (!student.content || !student.content.fileList || student.content.fileList.length === 0) {
        continue
      }

      // 遍历学生的所有照片
      for (let i = 0; i < student.content.fileList.length; i++) {
        const file = student.content.fileList[i]
        const fileName = student.content.fileList.length > 1
          ? `${student.name}${String(i + 1).padStart(2, '0')}.jpg`
          : `${student.name}.jpg`

        try {
          // 获取图片数据
          const response = await fetch(file.url)
          const blob = await response.blob()
          zip.file(fileName, blob)
        }
        catch (error) {
          console.error(`下载 ${fileName} 失败:`, error)
        }
      }
    }

    // 生成压缩包并下载
    const content = await zip.generateAsync({ type: 'blob' })
    saveAs(content, `${lang.ssBatchDownload}.zip`)
  }
  catch (error) {
    console.error('批量下载失败:', error)
  }
  finally {
    // 重置加载状态
    downloadLoading.value = false
  }
}




// 组件卸载时清理ECharts实例
onUnmounted(() => {
  // 清除定时器
  if (resizeTimer) {
    clearTimeout(resizeTimer)
    resizeTimer = null
  }

  // 销毁ECharts实例
  if (myChart.value && !myChart.value.isDisposed()) {
    myChart.value.dispose()
    myChart.value = null
  }
})
</script>

<style lang="scss" scoped>
.choiceQuestionDetailDialog {
  background: none;
  position: relative;
  width: 100%;
  height: 100%;
  z-index: 1;

  .content {
    width: 100%;
    height: 100%;
    position: relative;
    background: #fff;
    box-sizing: border-box;
    padding: 40px;
    overflow: auto;

    .closeIcon {
      position: absolute;
      right: 20px;
      top: 20px;
      cursor: pointer;
      width: 20px;
      height: 20px;

      img {
        width: 100%;
        height: 100%;
      }
    }

    .c_t45 {
      width: 100%;
      min-height: 100%;
      display: flex;
      // align-items: center;
      flex-direction: column;
      height: auto;

      .c_t45_title {
        color: rgba(0, 0, 0, 0.9);
        font-weight: 600;
        font-size: 24px;
        line-height: 24px;
        position: relative;
        width: 100%;
        display: flex;
        flex-direction: column;
        // align-items: center;
        // justify-content: center;
        user-select: none;
        gap: .4rem;

        &>div {
          max-width: calc(100%);
        }

        &>span {
          position: absolute;
          top: 20px;
          cursor: pointer;

          &:nth-of-type(1) {
            left: 0;
          }

          &:nth-of-type(2) {
            right: 0;
          }
        }

        .c_t45_t_btn_noActive {
          color: #CCCCCC;
        }

        .c_t45_msg {
          display: flex;
          align-items: center;
          font-size: .9rem;
          font-weight: 400;
          gap: 1rem;

          &>span {
            text-decoration: underline;
            cursor: pointer;
          }
        }
      }

      .c_t45_img {
        max-width: 200px;
        max-height: 200px;
        object-fit: cover;
        margin-top: 20px;
      }

      .c_t45_type {
        font-weight: 400;
        font-size: 15px;
        line-height: 21px;
        letter-spacing: 0.5px;
        color: rgba(0, 0, 0, 1);
        opacity: 0.5;
        margin-top: 20px;
      }

      .c_t45_echarts {
        width: 100%;
        max-width: 100%;
        flex: 1;
        min-height: 400px;
        display: flex;
        align-items: center;
        box-sizing: border-box;

        &>div {
          width: 100%;
          height: 400px;
        }
      }

      .cq_changeBtn {
        display: flex;
        align-items: center;
        gap: 1.5rem;
        margin: 1rem auto;

        &>div {
          padding: .6rem;
          border-radius: .5rem;
          border: solid 2px #F6C82B;
          display: flex;
          justify-content: center;
          align-items: center;
          cursor: pointer;

          &>svg {
            fill: #F6C82D;
            width: 1rem;
            height: 1rem;
          }

          &.cq_cb_disabled {
            cursor: not-allowed !important;
            border-color: #FEF8E9 !important;
          }

          &.cq_cb_disabled>svg {
            fill: #A3A3A3 !important;
          }
        }

        &>span {
          font-weight: 500;
        }
      }


    }

    .c_t15 {
      width: 100%;
      min-height: 100%;
      display: flex;
      // align-items: center;
      flex-direction: column;
      height: auto;
      padding: 40px;

      .c_t15_title {
        color: rgba(0, 0, 0, 0.9);
        font-weight: 600;
        font-size: 24px;
        line-height: 24px;
      }

      .c_t15_msg {
        display: flex;
        align-items: center;
        font-size: .9rem;
        font-weight: 400;
        gap: 1rem;

        &>span {
          text-decoration: underline;
          cursor: pointer;
        }
      }

      .c_t15_type {
        font-weight: 400;
        font-size: 15px;
        line-height: 21px;
        letter-spacing: 0.5px;
        color: rgba(0, 0, 0, 1);
        opacity: 0.5;
        margin: 10px 0;
      }

      .c_t15_content {
        width: 100%;
        height: auto;
        display: grid;
        grid-template-columns: repeat(3, 1fr);
        gap: 20px;
        margin-top: 40px;

        .c_t15_c_item {
          width: 100%;
          height: auto;
          box-shadow: 2px 4px 20px 0px rgba(0, 0, 0, 0.2);
          box-sizing: border-box;
          border-radius: 12px;
          padding: 16px;
          background: rgba(255, 255, 255, 0.6);
          transition: 0.3s;
          cursor: pointer;
          overflow: hidden;

          &:hover {
            box-shadow: 4px 4px 14px 0px rgba(252, 207, 0, 0.5);
            background: rgba(255, 255, 255, 0.6);
          }

          .c_t15_c_i_top {
            display: flex;
            align-items: center;
            gap: 10px;
            width: 100%;
            overflow: hidden;

            &>span {
              min-width: 25px;
              height: 25px;
              display: flex;
              align-items: center;
              justify-content: center;
              background: rgba(252, 207, 0, 1);
              border-radius: 4px;
              color: rgba(255, 255, 255, 1);
              font-weight: bold;
              font-size: 14px;
            }

            &>div {
              color: rgba(0, 0, 0, 0.7);
              font-weight: 800;
              overflow: hidden;
              text-overflow: ellipsis;
              white-space: nowrap;
            }
          }

          .c_t15_c_i_bottom {
            margin-top: 15px;
            font-weight: 300;
            font-size: 14px;
            height: 40px;
            max-width: 100%;
            overflow: hidden;
            text-overflow: ellipsis;
            display: -webkit-box;
            -webkit-line-clamp: 2;
            -webkit-box-orient: vertical;
          }

          .c_t73_c_i_bottom {
            margin-top: 15px;
            font-weight: 300;
            font-size: 14px;
            // height: 40px;
            max-width: 100%;
            overflow: hidden;
            text-overflow: ellipsis;
            display: -webkit-box;
            -webkit-line-clamp: 2;
            -webkit-box-orient: vertical;

            img {
              width: 100%;
              height: 200px;
              object-fit: cover;
            }

            span {
              width: 100%;
              height: 200px;
              display: flex;
              align-items: center;
              justify-content: center;
            }
          }
        }
      }

      .c_t15_workDetail {
        width: 100%;
        height: auto;
        margin-top: 40px;
        box-shadow: 4px 4px 14px 0px rgba(252, 207, 0, 0.5);
        box-sizing: border-box;
        padding: 16px;
        border-radius: 12px;
        display: flex;
        flex-direction: column;

        .c_t15_wd_top {
          width: 100%;
          display: flex;
          align-items: center;
          gap: 15px;

          &>img {
            width: 25px;
            height: 25px;
            cursor: pointer;
          }

          &>span {
            display: block;
            width: 30px;
            height: 30px;
            display: flex;
            align-items: center;
            justify-content: center;
            background: rgba(252, 207, 0, 1);
            border-radius: 4px;
            color: rgba(255, 255, 255, 1);
            font-weight: bold;
            font-size: 16px;
          }

          &>div {
            color: rgba(0, 0, 0, 0.7);
            font-weight: 800;
            font-size: 18px;
          }
        }

        .c_t15_wd_content {
          width: 100%;
          margin-top: 20px;
          max-height: 100%;
          overflow: auto;
          flex-wrap: wrap;

          .c_t15_wd_c_imageList {
            width: 100%;
            gap: 20px;
            margin-top: 20px;

            &>img {
              width: 100px;
              height: auto;
              cursor: pointer;
              margin-right: 20px;
              object-fit: cover;
            }
          }
        }
      }

      .c_t79_workDetail {
        width: 100%;
        height: auto;
        margin-top: 40px;
        box-shadow: 4px 4px 14px 0px rgba(252, 207, 0, 0.5);
        box-sizing: border-box;
        padding: 16px;
        border-radius: 12px;
        display: flex;
        flex-direction: column;

        .c_t79_wd_top {
          width: 100%;
          display: flex;
          align-items: center;
          gap: 15px;

          &>img {
            width: 25px;
            height: 25px;
            cursor: pointer;
          }

          &>span {
            display: block;
            width: 30px;
            height: 30px;
            display: flex;
            align-items: center;
            justify-content: center;
            background: rgba(252, 207, 0, 1);
            border-radius: 4px;
            color: rgba(255, 255, 255, 1);
            font-weight: bold;
            font-size: 16px;
          }

          &>div {
            color: rgba(0, 0, 0, 0.7);
            font-weight: 800;
            font-size: 18px;
          }
        }

        .c_t79_wd_content {
          width: 100%;
          margin-top: 20px;
          max-height: 100%;
          overflow: auto;
          flex-wrap: wrap;
          display: flex;
          align-items: center;
          justify-content: center;

          &>img {
            max-width: 100%;
            height: 300px;
            object-fit: cover;
          }
        }
      }

      .cq_changeBtn {
        display: flex;
        align-items: center;
        gap: 1.5rem;
        margin: 1rem auto;

        &>div {
          padding: .6rem;
          border-radius: .5rem;
          border: solid 2px #F6C82B;
          display: flex;
          justify-content: center;
          align-items: center;
          cursor: pointer;

          &>svg {
            fill: #F6C82D;
            width: 1rem;
            height: 1rem;
          }

          &.cq_cb_disabled {
            cursor: not-allowed !important;
            border-color: #FEF8E9 !important;
          }

          &.cq_cb_disabled>svg {
            fill: #A3A3A3 !important;
          }
        }

        &>span {
          font-weight: 500;
        }
      }
    }

    .c_t72 {
      width: 100%;
      min-height: 100%;
      display: flex;
      // align-items: center;
      flex-direction: column;
      height: auto;
      padding: 40px;

      .c_t72_title {
        color: rgba(0, 0, 0, 0.9);
        font-weight: 600;
        font-size: 24px;
        line-height: 24px;
      }

      .c_t72_type {
        font-weight: 400;
        font-size: 15px;
        line-height: 21px;
        letter-spacing: 0.5px;
        color: rgba(0, 0, 0, 1);
        opacity: 0.5;
        margin: 10px 0;
      }

      .c_t72_msg {
        display: flex;
        align-items: center;
        font-size: .9rem;
        font-weight: 400;
        gap: 1rem;

        &>span {
          text-decoration: underline;
          cursor: pointer;
        }
      }

      .c_t72_content {
        width: 100%;
        height: auto;
        display: grid;
        grid-template-columns: repeat(4, 1fr);
        gap: 20px;
        margin-top: 40px;

        .c_t72_c_item {
          width: 100%;
          height: auto;
          box-shadow: 2px 4px 20px 0px rgba(0, 0, 0, 0.2);
          box-sizing: border-box;
          border-radius: 12px;
          padding: 16px;
          background: rgba(255, 255, 255, 0.6);
          transition: 0.3s;
          cursor: pointer;
          overflow: hidden;

          &:hover {
            box-shadow: 4px 4px 14px 0px rgba(252, 207, 0, 0.5);
            background: rgba(255, 255, 255, 0.6);
          }

          .c_t72_c_i_top {
            display: flex;
            align-items: center;
            gap: 10px;
            width: 100%;
            overflow: hidden;

            &>span {
              min-width: 25px;
              height: 25px;
              display: flex;
              align-items: center;
              justify-content: center;
              background: rgba(252, 207, 0, 1);
              border-radius: 4px;
              color: rgba(255, 255, 255, 1);
              font-weight: bold;
              font-size: 14px;
            }

            &>div {
              color: rgba(0, 0, 0, 0.7);
              font-weight: 800;
            }
          }

          .c_t72_c_i_bottom {
            margin-top: 15px;
            font-weight: 300;
            font-size: 14px;
            // height: 40px;
            max-width: 100%;
            overflow: hidden;
            text-overflow: ellipsis;
            display: -webkit-box;
            -webkit-line-clamp: 2;
            -webkit-box-orient: vertical;

            img {
              width: 100%;
              max-height: 200px;
              object-fit: cover;
            }
          }
        }
      }

      .c_t72_workDetail {
        width: 100%;
        height: auto;
        margin-top: 40px;
        box-shadow: 4px 4px 14px 0px rgba(252, 207, 0, 0.5);
        box-sizing: border-box;
        padding: 16px;
        border-radius: 12px;
        display: flex;
        flex-direction: column;

        .c_t72_wd_top {
          width: 100%;
          display: flex;
          align-items: center;
          gap: 15px;

          &>img {
            width: 25px;
            height: 25px;
            cursor: pointer;
          }

          &>span {
            display: block;
            width: 30px;
            height: 30px;
            display: flex;
            align-items: center;
            justify-content: center;
            background: rgba(252, 207, 0, 1);
            border-radius: 4px;
            color: rgba(255, 255, 255, 1);
            font-weight: bold;
            font-size: 16px;
          }

          &>div {
            color: rgba(0, 0, 0, 0.7);
            font-weight: 800;
            font-size: 18px;
          }
        }

        .c_t72_wd_content {
          width: 100%;
          margin-top: 20px;
          max-height: 100%;
          overflow: auto;
          flex-wrap: wrap;
          display: flex;
          align-items: center;
          justify-content: center;

          .na_m_item {
            width: 100%;
            height: auto;
            margin: 10px 0;
          }

          .na_m_i_name {
            width: fit-content;
            max-width: 100%;
            height: auto;
            box-sizing: border-box;
            padding: 10px 10px;
            display: flex;
            align-items: center;
            border-radius: 10px 10px 0 0;
            background-color: #9747ff;
            color: #fff;
            text-overflow: ellipsis;
            overflow: hidden;
            white-space: nowrap;
          }

          .aiName {
            background-color: #0560fc;
          }

          .na_m_i_content {
            padding: 10px;
            border: solid 1px #e7e7e7;
            box-shadow: 0 4px 20px 0 rgba(0, 0, 0, 0.1);
            border-radius: 0 0 12px 12px;
            background-color: #fff;

            :deep(img) {
              max-width: 100%;
            }
          }

          .messageNode {
            width: 100%;
            height: auto;
            box-sizing: border-box;
            padding: 10px 10px;
            border: 0.5px solid #e7e7e7;
            border-radius: 12px;
            gap: 10px;
            margin-top: 20px;
          }

          .messageNodeArea {
            width: 100%;
            height: auto;
          }
        }
      }
    }

    .c_t73 {
      width: 100%;
      min-height: 100%;
      display: flex;
      // align-items: center;
      flex-direction: column;
      height: auto;
      padding: 40px;

      .c_t73_title {
        color: rgba(0, 0, 0, 0.9);
        font-weight: 600;
        font-size: 24px;
        line-height: 24px;
      }

      .c_t73_type {
        font-weight: 400;
        font-size: 15px;
        line-height: 21px;
        letter-spacing: 0.5px;
        color: rgba(0, 0, 0, 1);
        opacity: 0.5;
        margin: 10px 0;
      }

      .c_t73_msg {
        display: flex;
        align-items: center;
        font-size: .9rem;
        font-weight: 400;
        gap: 1rem;

        &>span {
          text-decoration: underline;
          cursor: pointer;
        }
      }

      .c_t73_content {
        width: 100%;
        height: auto;
        display: grid;
        grid-template-columns: repeat(3, 1fr);
        gap: 20px;
        margin-top: 40px;

        .c_t73_c_item {
          width: 100%;
          height: auto;
          box-shadow: 2px 4px 20px 0px rgba(0, 0, 0, 0.2);
          box-sizing: border-box;
          border-radius: 12px;
          padding: 16px;
          background: rgba(255, 255, 255, 0.6);
          transition: 0.3s;
          cursor: pointer;
          overflow: hidden;

          &:hover {
            box-shadow: 4px 4px 14px 0px rgba(252, 207, 0, 0.5);
            background: rgba(255, 255, 255, 0.6);
          }

          .c_t73_c_i_top {
            display: flex;
            align-items: center;
            gap: 10px;
            width: 100%;
            overflow: hidden;

            &>span {
              min-width: 25px;
              height: 25px;
              display: flex;
              align-items: center;
              justify-content: center;
              background: rgba(252, 207, 0, 1);
              border-radius: 4px;
              color: rgba(255, 255, 255, 1);
              font-weight: bold;
              font-size: 14px;
            }

            &>div {
              color: rgba(0, 0, 0, 0.7);
              font-weight: 800;
            }
          }

          .c_t73_c_i_bottom {
            margin-top: 15px;
            font-weight: 300;
            font-size: 14px;
            // height: 40px;
            max-width: 100%;
            overflow: hidden;
            text-overflow: ellipsis;
            display: -webkit-box;
            -webkit-line-clamp: 2;
            -webkit-box-orient: vertical;

            img {
              width: 100%;
              max-height: 200px;
              object-fit: cover;
            }
          }
        }
      }

      .c_t73_workDetail {
        width: 100%;
        height: auto;
        margin-top: 40px;
        box-shadow: 4px 4px 14px 0px rgba(252, 207, 0, 0.5);
        box-sizing: border-box;
        padding: 16px;
        border-radius: 12px;
        display: flex;
        flex-direction: column;

        .c_t73_wd_top {
          width: 100%;
          display: flex;
          align-items: center;
          gap: 15px;

          &>img {
            width: 25px;
            height: 25px;
            cursor: pointer;
          }

          &>span {
            display: block;
            width: 30px;
            height: 30px;
            display: flex;
            align-items: center;
            justify-content: center;
            background: rgba(252, 207, 0, 1);
            border-radius: 4px;
            color: rgba(255, 255, 255, 1);
            font-weight: bold;
            font-size: 16px;
          }

          &>div {
            color: rgba(0, 0, 0, 0.7);
            font-weight: 800;
            font-size: 18px;
          }
        }

        .c_t73_wd_content {
          width: 100%;
          margin-top: 20px;
          max-height: 100%;
          overflow: auto;
          flex-wrap: wrap;
          display: flex;
          align-items: center;
          justify-content: center;

          &>img {
            max-width: 100%;
            object-fit: cover;
          }
        }
      }
    }
  }
}

.aiAnalysis {
  width: 100%;
  height: auto;
  display: flex;
  flex-direction: column;
  padding: 1rem;
  border: solid 1px #F6C82B;
  border-left-width: 4px;
  border-radius: 1rem;
  gap: 1rem;

  &>.ai_header {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 1rem;

    &>div {
      display: flex;
      align-items: center;
      gap: .5rem;

      &>svg {
        width: 1rem;
        height: 1rem;

      }
    }

    &>.ai_title {
      color: #F7CD49;
      font-weight: 500;

      &>svg {
        fill: #F7CD49;
        width: 1.2rem;
        height: 1.2rem;
      }
    }

    &>.ai_refresh {
      padding: .5rem 1rem;
      border-radius: .5rem;
      background: #F6C82B;
      display: flex;
      justify-content: center;
      align-items: center;
      cursor: pointer;
      color: #000;
      font-weight: bold;
      font-size: .8rem;
      gap: .5rem;

      &>svg {
        fill: #000;
        width: .8rem;
        height: .8rem;
      }

      &.disabled {
        cursor: not-allowed !important;
        background: #FEF8E9 !important;
      }
    }
  }

  &>.ai_content {
    font-size: 1rem;
    font-weight: 500;

    :deep(table) {
      border-collapse: collapse;
      width: 100%;
      margin: 0.5rem 0;

      th,
      td {
        border: 1px solid #ddd;
        padding: 0.5rem;
        text-align: left;
      }

      th {
        background: #f5f5f5;
      }
    }
  }

  &>.ai_echartsData {
    display: flex;
    flex-wrap: wrap;
    gap: .5rem;

    &>span {
      padding: .2rem .5rem;
      border-radius: .25rem;
      background: #E6F4FF;
      display: flex;
      justify-content: center;
      align-items: center;
      color: #141517;
      font-size: .75rem;
    }

    &>.title {
      font-weight: 600;
    }

    &>.btn {
      font-size: .9rem;
      text-decoration: underline;
      color: #F6C82B;
      cursor: pointer;
    }
  }

  &>.ai_updateTime {
    font-size: .8rem;
    font-weight: 500;
  }
}

.nextAndUpBtn {
  width: 100%;
  height: auto;
  display: grid;
  grid-template-columns: 1fr 1fr;
  margin-top: 20px;
  gap: 15px;

  &>span {
    display: flex;
    justify-content: center;
    align-items: center;
    width: 100%;
    height: 40px;
    border-radius: 5px;
    font-size: 14px;
    font-weight: 500;
    color: #fff;
    background: #f6c82b;
    cursor: pointer;
  }

  &>.no_active {
    background: #cccccc !important;
    color: #999999 !important;
    cursor: not-allowed !important;
    pointer-events: none !important;
  }
}

.c_title{
  display: flex;

  &>span {
    flex: 1;
    word-break: break-all;
  }
}

.switch_btn{
  display: flex;
  align-items: center;
  gap: .5rem;

  &>.switch{
    display: flex;
    align-items: center;
    gap: .5rem;
    font-size: .8rem;
    color: #141517;

    +.switch{
      margin-left: .5rem;
    }
  }
}

.bottom_btn{
  display: flex;
  align-items: center;
  gap: 5px;
  font-weight: 300;
  font-size: 14px;
  color: rgba(0, 0, 0, 0.7);

  .bottom_like{
    margin-left: auto;
    cursor: pointer;
    display: flex;
    align-items: center;
    gap: 5px;
    color: rgba(0, 0, 0, 0.7);
    
    &.active{
      color: rgba(252, 207, 0, 1);
    }
  }
}

.cast_sreen_btn{
  display: flex;
  align-items: center;
  gap: 5px;
  font-weight: 300;
  font-size: 14px;
  color: rgba(0, 0, 0, 0.7);
  cursor: pointer;
  margin-left: auto;
  border-radius: 5px;
  border: solid 1px rgba(252, 207, 0, .7);
  padding: .5rem 0.6rem;
  min-width: 65px;
  justify-content: center;
}

.downloadBtn{
  display: flex;
  align-items: center;
  gap: 5px;
  font-weight: 300;
  font-size: 14px;
  color: rgba(0, 0, 0, 0.7);
  cursor: pointer;
  margin-left: auto;
  border-radius: 5px;
  border: solid 1px rgba(252, 207, 0, .7);
  padding: .5rem 0.6rem;
  min-width: 65px;
  justify-content: center;
}
</style>
