fix: align purchase forecast task toolbar

bugfix/ai-assessment-evidence-rescore
陈沅 1 month ago
parent c5c23e9202
commit 87f4c728b7

@ -2,11 +2,11 @@
<div class="channel student-training-shell"> <div class="channel student-training-shell">
<main class="training-core"> <main class="training-core">
<section class="task-header"><div class="task-badge"><el-icon><TrendCharts /></el-icon> 核心实训 · 供应渠道管理</div><h1 class="task-title">{{ taskTitle }}</h1></section> <section class="task-header"><div class="task-badge"><el-icon><TrendCharts /></el-icon> 核心实训 · 供应渠道管理</div><h1 class="task-title">{{ taskTitle }}</h1></section>
<TrainingTaskBrief :background="taskBackground" :goals="taskGoals" :requirements="taskRequirement" :show-material="false" /> <TrainingTaskBrief :background="taskBackground" :goals="taskGoals" :requirements="taskRequirement" :show-material="false" :show-toolbar="false" />
<section class="task-card"> <section class="task-card">
<div class="workbench-head workbench-head--actions-only"><div class="workbench-actions"><TrainingMaterialButton :material-name="taskConfig?.materialName" :material-url="taskConfig?.materialUrl" /><button type="button" class="outline-action" @click="exportOutcome"><el-icon><Download /></el-icon>导出实训成果</button></div></div> <div class="workbench-head"><div><p class="section-eyebrow">PURCHASE DEMAND FORECAST</p><h2>{{ activeStepName }}</h2></div><TrainingTaskToolbar class="purchase-forecast-toolbar" :task-key="TASK_KEY" :on-export="exportOutcome" /></div>
<nav v-if="hasConfiguredSteps" class="step-indicator" aria-label="采购需求预测步骤"><template v-for="(step,index) in configuredSteps" :key="`${step}-${index}`"><button type="button" :class="['step-tab',{active:activeStep===index+1,complete:activeStep>index+1}]" :aria-current="activeStep===index+1?'step':undefined" :aria-label="`第${index+1}步:${step}`" @click="setCurrentStep(index+1)"><span class="step-marker">{{ String(index+1).padStart(2,'0') }}</span><span class="step-copy"><strong class="step-name" :title="step">{{ step }}</strong><span class="step-action">{{ activeStep===index+1?'当前步骤':'点击切换' }} <span aria-hidden="true">→</span></span></span></button><span v-if="index<configuredSteps.length-1" class="step-connector" aria-hidden="true"></span></template></nav> <nav v-if="hasConfiguredSteps" class="step-indicator" aria-label="采购需求预测步骤"><template v-for="(step,index) in configuredSteps" :key="`${step}-${index}`"><button type="button" :class="['step-tab',{active:activeStep===index+1,complete:activeStep>index+1}]" :aria-current="activeStep===index+1?'step':undefined" :aria-label="`第${index+1}步:${step}`" @click="setCurrentStep(index+1)"><span class="step-marker">{{ String(index+1).padStart(2,'0') }}</span><span class="step-copy"><strong class="step-name" :title="step">{{ step }}</strong><span class="step-action">{{ activeStep===index+1?'当前步骤':'点击切换' }} <span aria-hidden="true">→</span></span></span></button><span v-if="index<configuredSteps.length-1" class="step-connector" aria-hidden="true"></span></template></nav>
<section v-show="isSectionVisible(1)" class="step-card"><div class="step-title-row"><div><p class="section-eyebrow">Step {{ String(activeStep).padStart(2,'0') }}</p><h3>{{ activeStepName }}</h3></div></div> <section v-show="isSectionVisible(1)" class="step-card">
<p class="linear-forecast-intro">线性预测的核心是拟合趋势线(y=a+bt),是基于历史数据预测未来销量的有效方法。根据案例资料及数据,预测案例店铺产品未来 3 个月市场需求数据。</p> <p class="linear-forecast-intro">线性预测的核心是拟合趋势线(y=a+bt),是基于历史数据预测未来销量的有效方法。根据案例资料及数据,预测案例店铺产品未来 3 个月市场需求数据。</p>
<div class="linear-forecast-panel"> <div class="linear-forecast-panel">
@ -29,7 +29,7 @@
</div> </div>
<el-button type="primary" class="practice-guide-button" @click="downloadPracticeGuide">下载实训操作说明</el-button> <el-button type="primary" class="practice-guide-button" @click="downloadPracticeGuide">下载实训操作说明</el-button>
</section> </section>
</section><section v-show="isSectionVisible(2)" class="step-card"><div class="step-title-row"><div><p class="section-eyebrow">Step {{ String(activeStep).padStart(2,'0') }}</p><h3>{{ activeStepName }}</h3></div></div> </section><section v-show="isSectionVisible(2)" class="step-card">
<p class="forecast-visual-intro">计算未来 3 个月需求量后,使用散点图 + 趋势线绘制需求量预测趋势图,呈现已知的 12 个月销量以及预测数据的整体走势。</p> <p class="forecast-visual-intro">计算未来 3 个月需求量后,使用散点图 + 趋势线绘制需求量预测趋势图,呈现已知的 12 个月销量以及预测数据的整体走势。</p>
<section class="forecast-visual-upload-card"> <section class="forecast-visual-upload-card">
<label v-if="!demandForecastChart.url" class="forecast-visual-dropzone" :class="{ 'is-uploading': uploadingDemandForecastChart }"> <label v-if="!demandForecastChart.url" class="forecast-visual-dropzone" :class="{ 'is-uploading': uploadingDemandForecastChart }">
@ -57,7 +57,7 @@
</div> </div>
<el-button type="primary" class="practice-guide-button" @click="downloadPracticeGuide">下载实训操作说明</el-button> <el-button type="primary" class="practice-guide-button" @click="downloadPracticeGuide">下载实训操作说明</el-button>
</section> </section>
</section><section v-show="isSectionVisible(3)" class="step-card"><div class="step-title-row"><div><p class="section-eyebrow">Step {{ String(activeStep).padStart(2,'0') }}</p><h3>{{ activeStepName }}</h3></div></div> </section><section v-show="isSectionVisible(3)" class="step-card">
<p class="procurement-plan-intro">基于步骤一预测的未来3个月销量,结合安全库存和期初库存,计算各月采购量,填报采购预测表。</p> <p class="procurement-plan-intro">基于步骤一预测的未来3个月销量,结合安全库存和期初库存,计算各月采购量,填报采购预测表。</p>
<section class="procurement-plan-rules"> <section class="procurement-plan-rules">
<h4>采购规则</h4> <h4>采购规则</h4>
@ -94,7 +94,7 @@
</el-table> </el-table>
</div> </div>
<p class="procurement-plan-hint">预测销量由第 1 步同步带入。提交时将按题设规则校验安全库存、期初库存和采购量。</p> <p class="procurement-plan-hint">预测销量由第 1 步同步带入。提交时将按题设规则校验安全库存、期初库存和采购量。</p>
</section><section v-show="isSectionVisible(4)" class="step-card"><div class="step-title-row"><div><p class="section-eyebrow">Step {{ String(activeStep).padStart(2,'0') }}</p><h3>{{ activeStepName }}</h3></div></div> </section><section v-show="isSectionVisible(4)" class="step-card">
<p>未来需求预测,使用线性回归模型预测2025年采购量:</p> <p>未来需求预测,使用线性回归模型预测2025年采购量:</p>
<el-table <el-table
:data="forecastData" :data="forecastData"
@ -138,12 +138,12 @@
import TrainingAiSidebar from "@/views/components/TrainingAiSidebar.vue"; import TrainingAiSidebar from "@/views/components/TrainingAiSidebar.vue";
import TrainingMaterialButton from "@/views/components/TrainingMaterialButton.vue"; import TrainingTaskToolbar from "@/views/components/TrainingTaskToolbar.vue";
import TrainingTaskBrief from "@/views/components/TrainingTaskBrief.vue"; import TrainingTaskBrief from "@/views/components/TrainingTaskBrief.vue";
import * as analysisAPI from "@/api/market-demand-mining.js"; import * as analysisAPI from "@/api/market-demand-mining.js";
import * as echarts from "echarts"; import * as echarts from "echarts";
import useUserStore from "@/store/modules/user"; import useUserStore from "@/store/modules/user";
import { ArrowLeft, ArrowRight, CircleCheck, Download, TrendCharts } from "@element-plus/icons-vue"; import { ArrowLeft, ArrowRight, CircleCheck, TrendCharts } from "@element-plus/icons-vue";
import { getTrainingTaskByKey } from "@/api/trainingTask"; import { getTrainingTaskByKey } from "@/api/trainingTask";
import { getStudentTrainingAnswer, saveStudentTrainingAnswer, uploadStudentTrainingFile, validatePurchaseDemandForecastStepOne } from "@/api/studentTrainingAnswer"; import { getStudentTrainingAnswer, saveStudentTrainingAnswer, uploadStudentTrainingFile, validatePurchaseDemandForecastStepOne } from "@/api/studentTrainingAnswer";
import { parseTrainingArray } from "@/views/training/taskKeyMap"; import { parseTrainingArray } from "@/views/training/taskKeyMap";
@ -959,6 +959,27 @@ onMounted(async () => {
border-bottom: 0; border-bottom: 0;
} }
.workbench-head h2 {
margin: 4px 0 0;
color: #fff;
font-size: 24px;
font-weight: 800;
line-height: 1.3;
}
.purchase-forecast-toolbar {
align-self: center;
justify-content: flex-end;
max-width: 100%;
}
@media (max-width:900px) {
.purchase-forecast-toolbar {
width: 100%;
justify-content: flex-start;
}
}
.linear-forecast-intro { .linear-forecast-intro {
margin: 0 0 22px; margin: 0 0 22px;
color: #d7ecff; color: #d7ecff;

Loading…
Cancel
Save