This commit is contained in:
2026-05-27 15:27:35 +08:00
parent 9882d3becc
commit a73d530f07
+83 -232
View File
@@ -1657,10 +1657,8 @@ const ResultView = {
const resultAnchorLinks = [
{ id: 'candidate-schemes', label: '方案' },
{ id: 'preview-3d', label: '预览' },
{ id: 'engineering-summary', label: '工程摘要' },
{ id: 'ai-side-action', label: 'AI倒扣分析' },
{ id: 'dfm-check', label: 'DFM' },
{ id: 'export-cam', label: '导出/CAM' },
{ id: 'export-cam', label: 'CAM/CNC' },
{ id: 'llm-report', label: '设计报告' }
];
@@ -1978,74 +1976,60 @@ const ResultView = {
<span class="badge badge-info">{{ selectedScheme?.title || selectedScheme?.scheme_id || '方案待定' }}</span>
</div>
<div class="info-list">
<div class="info-item">
<span class="info-label">方案说明</span>
<span class="info-value" style="font-weight: 600; font-size: 1.05rem; color: var(--text-primary);">{{ selectedScheme?.summary || selectedScheme?.reason || '基于当前几何与制造约束自动推荐' }}</span>
</div>
<div class="info-item">
<span class="info-label">分型方向</span>
<span class="info-value">{{ formatSchemeDirection(selectedScheme) }}</span>
</div>
<div class="info-item">
<span class="info-label">模具结构</span>
<span class="info-value">{{ selectedScheme?.mold_structure_type === 'two_half_cavity' ? '两板半腔(无独立模芯)' : '型腔 + 模芯' }}</span>
</div>
<div class="info-item">
<span class="info-label">分型面位置</span>
<span class="info-value">{{ selectedScheme?.offset_label || '中面' }}</span>
</div>
<div class="info-item">
<span class="info-label">方案总分</span>
<span class="info-value">{{ formatNumber(selectedScheme?.score || 0) }}</span>
</div>
<div class="info-item">
<span class="info-label">方案可信度</span>
<span class="info-value">{{ formatNumber(selectedScheme?.confidence_score || 0) }}</span>
</div>
<div class="info-item">
<span class="info-label">主要理由</span>
<span class="info-value">{{ selectedScheme?.summary || primaryRecommendation?.description || '基于当前几何与制造约束自动推荐' }}</span>
</div>
<div class="info-item">
<span class="info-label">高优先级建议</span>
<span class="info-value">{{ primaryRecommendation?.description || '未发现高优先级工艺建议' }}</span>
</div>
</div>
</div>
<div class="result-card result-card-highlight">
<div class="summary-header">
<h3>关键操作</h3>
<span :class="['badge', selectedRiskLabel === '高风险' ? 'badge-error' : selectedRiskLabel === '中风险' ? 'badge-warning' : 'badge-success']">
{{ selectedRiskLabel }}
</span>
</div>
<div class="info-list">
<div class="info-item">
<span class="info-label">DFM 风险数</span>
<span class="info-value">{{ selectedDfmCount }} 项</span>
</div>
<div class="info-item">
<span class="info-label">推荐型腔数</span>
<span class="info-label">型腔数</span>
<span class="info-value">{{ selectedCavityCount }} 腔</span>
</div>
<div class="info-item">
<span class="info-label">预计成型周期</span>
<span class="info-value">{{ selectedInjectionSystem?.overall_assessment?.estimated_cycle_time || 'N/A' }} s</span>
</div>
<div class="info-item">
<span class="info-label">下一步</span>
<span class="info-value">{{ selectedDfmCount ? '先处理 DFM 风险,再确认导出或 CAM' : '可进入 3D 复核、导出与 CAM 准备' }}</span>
</div>
</div>
<div v-if="state.task.status === 'completed'" class="export-buttons export-buttons-block">
<button class="btn-sm btn-primary" @click="exportCAD('step')" title="导出STEP格式(UG/FreeCAD/SolidWorks通用)">
导出 STEP
</button>
<button class="btn-sm btn-secondary" @click="exportCAD('iges')" title="导出IGES格式(兼容旧系统)">
导出 IGES
</button>
<button class="btn-sm btn-secondary" @click="exportCAD('stl')" title="导出STL网格格式(3D打印预览)">
导出 STL
</button>
<button class="btn-sm btn-secondary" @click="exportCAD('brep')" title="导出BRep格式(FreeCAD原生)">
导出 BRep
</button>
<button class="btn-sm btn-primary" :disabled="state.camLoading" @click="generateCamPlan()" title="基于当前选中方案生成CAM工艺计划">
{{ state.camLoading ? '生成中...' : '生成 CAM 计划' }}
</button>
</div>
<div class="result-card result-card-highlight" v-if="candidateSchemes.length > 1">
<div class="summary-header">
<h3>备选方案</h3>
<span class="badge badge-warning">{{ candidateSchemes.length - 1 }} 个备选</span>
</div>
<div class="info-list">
<template v-for="scheme in candidateSchemes.slice(1)" :key="'alt-' + scheme.scheme_id">
<div class="info-item" style="padding: var(--space-1) 0; border-bottom: 1px solid var(--border-light);">
<span class="info-label" style="cursor: pointer;" @click="selectScheme(scheme.scheme_id)">
{{ scheme.title || scheme.scheme_id }}
</span>
<span class="info-value">{{ scheme.offset_label || '中面' }} · 总分 {{ formatNumber(scheme.score) }}</span>
</div>
</template>
</div>
<div class="inline-note" style="margin-top: var(--space-2);">点击方案名称可切换查看详情与 3D 预览</div>
</div>
<div class="result-card result-card-highlight" v-else>
<div class="summary-header">
<h3>方案概览</h3>
<span class="badge badge-success">单一方案</span>
</div>
<div class="info-list">
<div class="info-item">
<span class="info-label">详细方案说明</span>
<span class="info-value" style="font-weight: 500;">{{ selectedScheme?.summary || selectedScheme?.reason || '当前仅生成 1 套可用分模方案,已在推荐方案区域展示核心参数。' }}</span>
</div>
</div>
</div>
</div>
@@ -2127,7 +2111,6 @@ const ResultView = {
<div id="candidate-schemes" v-if="candidateSchemes.length" class="viewer-section">
<h3>候选分模方案</h3>
<div class="inline-note">先切换并确认推荐方案,再进入后续工程判断、导出与 CAM。</div>
<div :class="['result-grid', hasSingleScheme ? 'single-scheme-grid' : '']">
<div
v-for="scheme in candidateSchemes"
@@ -2140,6 +2123,10 @@ const ResultView = {
<span class="badge badge-info">总分 {{ formatNumber(scheme.score) }}</span>
</div>
<div class="info-list">
<div class="info-item">
<span class="info-label">方案说明</span>
<span class="info-value" style="font-weight: 600; color: var(--text-primary);">{{ scheme.summary || scheme.reason || '暂无说明' }}</span>
</div>
<div class="info-item">
<span class="info-label">分型方向</span>
<span class="info-value">{{ formatSchemeDirection(scheme) }}</span>
@@ -2152,22 +2139,6 @@ const ResultView = {
<span class="info-label">分型面位置</span>
<span class="info-value">{{ scheme.offset_label || '中面' }}</span>
</div>
<div class="info-item">
<span class="info-label">候选优先级</span>
<span class="info-value">{{ formatNumber(scheme.priority_score || 0) }}</span>
</div>
<div class="info-item">
<span class="info-label">法向匹配度</span>
<span class="info-value">{{ formatNumber(scheme.normal_alignment_score || 0) }}</span>
</div>
<div class="info-item">
<span class="info-label">方法</span>
<span class="info-value">{{ scheme.method || 'rule_based' }}</span>
</div>
<div class="info-item">
<span class="info-label">方案说明</span>
<span class="info-value">{{ scheme.summary || scheme.reason || '暂无说明' }}</span>
</div>
<div class="info-item">
<span class="info-label">可制造性</span>
<span class="info-value">{{ formatNumber(scheme.score_breakdown?.manufacturability || 0) }}</span>
@@ -2180,22 +2151,6 @@ const ResultView = {
<span class="info-label">风险得分</span>
<span class="info-value">{{ formatNumber(scheme.score_breakdown?.risk || 0) }}</span>
</div>
<div class="info-item">
<span class="info-label">DFM 违规项</span>
<span class="info-value">{{ scheme.dfm_violation_count || 0 }}</span>
</div>
<div class="info-item">
<span class="info-label">方案可信度</span>
<span class="info-value">{{ formatNumber(scheme.confidence_score || 0) }}</span>
</div>
<div class="info-item">
<span class="info-label">回退标记</span>
<span class="info-value">{{ scheme.is_fallback ? '是' : '否' }}</span>
</div>
<div v-if="scheme.fallback_reason" class="info-item">
<span class="info-label">回退原因</span>
<span class="info-value">{{ scheme.fallback_reason }}</span>
</div>
</div>
<button v-if="candidateSchemes.length > 1" class="btn-sm btn-primary" @click="selectScheme(scheme.scheme_id)">查看此方案</button>
<div v-else class="inline-note">当前仅生成 1 套可用分模方案</div>
@@ -2213,8 +2168,6 @@ const ResultView = {
<th>方向</th>
<th>位置</th>
<th>总分</th>
<th>可信度</th>
<th>回退</th>
<th>法向匹配</th>
<th>可制造性</th>
<th>分型质量</th>
@@ -2228,8 +2181,6 @@ const ResultView = {
<td>{{ formatSchemeDirection(scheme) }}</td>
<td>{{ scheme.offset_label || '中面' }}</td>
<td>{{ formatNumber(scheme.score) }}</td>
<td>{{ formatNumber(scheme.confidence_score || 0) }}</td>
<td>{{ scheme.is_fallback ? '是' : '否' }}</td>
<td>{{ formatNumber(scheme.normal_alignment_score || 0) }}</td>
<td>{{ formatNumber(scheme.score_breakdown?.manufacturability || 0) }}</td>
<td>{{ formatNumber(scheme.score_breakdown?.parting_quality || 0) }}</td>
@@ -2241,71 +2192,6 @@ const ResultView = {
</div>
</details>
<div id="engineering-summary" v-if="selectedCavityData || selectedKeyInfo" class="viewer-section">
<h3>工程摘要</h3>
<div class="result-grid">
<div class="result-card">
<h4>方案与零件</h4>
<div class="info-list">
<div class="info-item">
<span class="info-label">零件名称</span>
<span class="info-value">{{ selectedCavityData?.metadata?.part_name || selectedKeyInfo?.metadata?.part_name || 'N/A' }}</span>
</div>
<div class="info-item">
<span class="info-label">材料</span>
<span class="info-value">{{ selectedCavityData?.metadata?.material || selectedKeyInfo?.metadata?.material || 'N/A' }}</span>
</div>
<div class="info-item">
<span class="info-label">结构判定</span>
<span class="info-value">{{ selectedScheme?.mold_structure_type === 'two_half_cavity' ? '两板半腔(无独立模芯)' : '型腔 + 模芯' }}</span>
</div>
</div>
</div>
<div class="result-card" v-if="selectedCavityData?.mold_cavities || selectedKeyInfo?.mold_cavities">
<h4>型腔与锁模</h4>
<div class="info-list">
<div class="info-item">
<span class="info-label">型腔数量</span>
<span class="info-value">{{ selectedCavityCount }}</span>
</div>
<div class="info-item">
<span class="info-label">预估锁模力</span>
<span class="info-value">{{ selectedCavityData?.manufacturing_info?.estimated_clamping_force || '自动计算' }}</span>
</div>
</div>
</div>
<div class="result-card" v-if="selectedInjectionSystem">
<h4>注塑模系统</h4>
<div class="info-list">
<div class="info-item">
<span class="info-label">预计成型周期</span>
<span class="info-value">{{ selectedInjectionSystem?.overall_assessment?.estimated_cycle_time || 'N/A' }} s</span>
</div>
<div class="info-item">
<span class="info-label">冷却时间</span>
<span class="info-value">{{ selectedInjectionSystem?.cooling?.cooling_time || 'N/A' }} s</span>
</div>
<div class="info-item">
<span class="info-label">水路数量</span>
<span class="info-value">{{ selectedInjectionSystem?.cooling?.thermal_check?.channel_count || 0 }}</span>
</div>
<div class="info-item">
<span class="info-label">冷却流量</span>
<span class="info-value">{{ selectedInjectionSystem?.cooling?.flow_rate?.flow_rate_lpm || 'N/A' }} L/min</span>
</div>
<div class="info-item">
<span class="info-label">浇口类型</span>
<span class="info-value">{{ selectedInjectionSystem?.gating?.gate_type || 'N/A' }}</span>
</div>
<div class="info-item">
<span class="info-label">流道形式</span>
<span class="info-value">{{ selectedInjectionSystem?.gating?.runner?.type || 'N/A' }}</span>
</div>
</div>
</div>
</div>
</div>
<div id="ai-side-action" class="viewer-section">
<div class="summary-header">
<h3>AI 倒扣与抽芯分析</h3>
@@ -2346,37 +2232,33 @@ const ResultView = {
<span class="info-value">{{ sideActionAiAdvice.source === 'ai' ? 'AI 模型' : '规则回退' }}</span>
</div>
</div>
<div class="inline-note">{{ sideActionAiAdvice.summary || '当前任务未返回更多摘要。' }}</div>
<div class="inline-note" style="margin-top: var(--space-2); font-weight: 600; font-size: 1rem; color: var(--text-primary);">{{ sideActionAiAdvice.summary || '当前任务未返回更多摘要。' }}</div>
</div>
<div class="result-card">
<h4>判断依据</h4>
<div class="recommendations-list" v-if="sideActionAiAdvice.reasons.length">
<div class="recommendation-item medium" v-for="(reason, idx) in sideActionAiAdvice.reasons" :key="'ai-reason-' + idx">
<div class="recommendation-text">{{ reason }}</div>
<div v-if="sideActionAiAdvice.reasons.length">
<h4>判断依据</h4>
<div class="recommendations-list">
<div class="recommendation-item medium" v-for="(reason, idx) in sideActionAiAdvice.reasons" :key="'ai-reason-' + idx">
<div class="recommendation-text">{{ reason }}</div>
</div>
</div>
</div>
<div class="inline-note" v-else>当前任务未返回明确的判断依据。</div>
</div>
<div class="result-card">
<h4>标准化建议</h4>
<div class="recommendations-list" v-if="sideActionAiAdvice.standardAdvice.length">
<div class="recommendation-item low" v-for="(advice, idx) in sideActionAiAdvice.standardAdvice" :key="'ai-advice-' + idx">
<div class="recommendation-text">{{ advice }}</div>
<div v-if="sideActionAiAdvice.standardAdvice.length" style="margin-top: var(--space-3);">
<h4>标准化建议</h4>
<div class="recommendations-list">
<div class="recommendation-item low" v-for="(advice, idx) in sideActionAiAdvice.standardAdvice" :key="'ai-advice-' + idx">
<div class="recommendation-text">{{ advice }}</div>
</div>
</div>
</div>
<div class="inline-note" v-else>当前任务未返回额外标准建议。</div>
</div>
<div class="result-card">
<h4>人工复核项</h4>
<div class="recommendations-list" v-if="sideActionAiAdvice.manualReviewItems.length">
<div class="recommendation-item medium" v-for="(item, idx) in sideActionAiAdvice.manualReviewItems" :key="'ai-review-' + idx">
<div class="recommendation-text">{{ item }}</div>
<div v-if="sideActionAiAdvice.manualReviewItems.length" style="margin-top: var(--space-3);">
<h4>人工复核项</h4>
<div class="recommendations-list">
<div class="recommendation-item medium" v-for="(item, idx) in sideActionAiAdvice.manualReviewItems" :key="'ai-review-' + idx">
<div class="recommendation-text">{{ item }}</div>
</div>
</div>
</div>
<div class="inline-note" v-else>当前任务无需额外人工复核项。</div>
</div>
</div>
@@ -2386,60 +2268,26 @@ const ResultView = {
</div>
</div>
<div id="dfm-check" class="viewer-section">
<h3>DFM 检查</h3>
<div class="result-grid" v-if="selectedDfmViolations.length">
<div class="result-card">
<h4>风险概览</h4>
<div class="info-list">
<div class="info-item">
<span class="info-label">总问题数</span>
<span class="info-value">{{ selectedDfmViolations.length }}</span>
</div>
<div class="info-item">
<span class="info-label">高风险</span>
<span class="info-value">{{ dfmLevelSummary.critical + dfmLevelSummary.high }}</span>
</div>
<div class="info-item">
<span class="info-label">中风险</span>
<span class="info-value">{{ dfmLevelSummary.medium }}</span>
</div>
<div class="info-item">
<span class="info-label">低风险</span>
<span class="info-value">{{ dfmLevelSummary.low }}</span>
</div>
</div>
</div>
<div class="result-card">
<h4>重点判断</h4>
<div class="recommendations-list">
<div class="recommendation-item high" v-if="dfmLevelSummary.critical + dfmLevelSummary.high > 0">
<div class="recommendation-text">当前方案存在较高工艺风险,建议优先调整壁厚、倒扣或分型方式后再进入制造准备。</div>
</div>
<div class="recommendation-item medium" v-else>
<div class="recommendation-text">当前方案未发现显著高风险项,可结合 3D 预览与 AI 倒扣分析继续做工程评审。</div>
</div>
</div>
</div>
</div>
<div v-if="!selectedDfmViolations.length" class="inline-alert inline-alert-warning">
<div class="inline-alert-title">未发现显著 DFM 违规项</div>
<div class="inline-alert-message">当前选中方案未命中高风险规则,可进入下一步工艺评审。</div>
</div>
<div v-else class="dfm-card-list">
<div class="dfm-card" v-for="(item, idx) in selectedDfmViolations" :key="'dfm-' + idx" :class="'dfm-level-' + (item.level || 'medium')">
<div class="dfm-card-header">
<div class="mechanism-title">{{ item.rule || 'DFM 规则' }}</div>
<span class="priority-badge" :class="(item.level || 'medium').toLowerCase()">{{ getPriorityText((item.level || 'medium').toLowerCase()) }}</span>
</div>
<div class="dfm-card-message">{{ item.message || 'N/A' }}</div>
<div class="dfm-card-hint">建议结合上方 3D 预览与 AI 倒扣分析定位具体风险区域。</div>
</div>
</div>
</div>
<div id="export-cam" class="viewer-section">
<h3>导出与 CAM</h3>
<div class="summary-header">
<h3>CAM 与 CNC 加工</h3>
<span class="badge badge-info">计划 | 导出</span>
</div>
<div v-if="state.task.status === 'completed'" class="export-buttons export-buttons-block" style="margin-bottom: var(--space-4);">
<button class="btn-sm btn-primary" @click="exportCAD('step')" title="导出装配体STEP格式(UG/FreeCAD/SolidWorks通用)">
📦 导出 STEP
</button>
<button class="btn-sm btn-secondary" @click="exportCAD('iges')" title="导出IGES格式(兼容旧系统)">
导出 IGES
</button>
<button class="btn-sm btn-secondary" @click="exportCAD('stl')" title="导出STL网格格式(3D打印预览)">
导出 STL
</button>
<button class="btn-sm btn-secondary" @click="exportCAD('brep')" title="导出BRep格式(FreeCAD原生)">
导出 BRep
</button>
</div>
<div class="result-card" style="margin-bottom: var(--space-4);">
<h4>CAM 参数</h4>
<div class="info-list">
@@ -2469,6 +2317,9 @@ const ResultView = {
</label>
</div>
</div>
<button class="btn-sm btn-primary" :disabled="state.camLoading" @click="generateCamPlan()" style="margin-top: var(--space-2);" title="基于当前选中方案生成CAM工艺计划">
{{ state.camLoading ? '⏳ 生成中...' : '🔧 生成 CAM 计划' }}
</button>
</div>
<div v-if="state.camError" class="inline-alert inline-alert-warning">
<div class="inline-alert-title">CAM 计划生成失败</div>