feat: integrate undergraduate school workflows and period twelve

This commit is contained in:
Codex
2026-10-15 00:28:04 +08:00
parent 7939bd4c3c
commit b28f333720
15 changed files with 573 additions and 26 deletions
+45 -5
View File
@@ -6,12 +6,20 @@ import 'package:flutter/material.dart';
import '../../app/app_controller.dart';
import '../../app/app_theme.dart';
import '../school/school_exam_adapter.dart';
import '../../data/exam_file_import.dart';
import '../../domain/school_identity.dart';
import '../../domain/undergraduate_exam_query.dart';
class ExamsPage extends StatelessWidget {
const ExamsPage({super.key, required this.controller, required this.onSync});
const ExamsPage({
super.key,
required this.controller,
required this.onSync,
this.onQueryOptions,
});
final AppController controller;
final VoidCallback onSync;
final VoidCallback? onQueryOptions;
Future<void> _import(BuildContext context) async {
try {
final file = await FilePicker.pickFile(
@@ -28,7 +36,7 @@ class ExamsPage extends StatelessWidget {
}
bytes.add(chunk);
}
final draft = SchoolExamAdapter.extract(utf8.decode(bytes.takeBytes()));
final draft = ExamFileImport.parse(utf8.decode(bytes.takeBytes()));
if (!context.mounted) return;
final confirmed = await showDialog<bool>(
context: context,
@@ -95,6 +103,12 @@ class ExamsPage extends StatelessWidget {
onPressed: onSync,
icon: const Icon(Icons.sync_rounded),
),
if (onQueryOptions != null)
IconButton(
tooltip: '查询选项',
onPressed: onQueryOptions,
icon: const Icon(Icons.tune_rounded),
),
IconButton(
tooltip: '导入考试 HTML',
onPressed: () => _import(context),
@@ -132,11 +146,21 @@ class ExamsPage extends StatelessWidget {
),
] else ...[
Text(
'${schedule.semesterLabel} · ${schedule.records.length} 门课程',
'${schedule.school.label} · ${schedule.semesterLabel} · ${schedule.records.length} 条考试',
style: TextStyle(fontSize: 13, color: ink.withValues(alpha: 0.55)),
),
const SizedBox(height: 18),
if (schedule.records.isEmpty) const Text('该学期暂无考试课程'),
if (schedule.school == SupportedSchool.uestcUndergraduate)
Text(
'查询类型:${UndergraduateExamQuery.fromSchedule(schedule)!.orderedTypes.map((t) => t.label).join('、')}',
style: const TextStyle(fontSize: 12),
),
if (schedule.records.isEmpty)
Text(
schedule.school == SupportedSchool.uestcUndergraduate
? '所选考试类型暂未安排'
: '该学期暂无考试课程',
),
for (final exam in schedule.records)
Padding(
padding: const EdgeInsets.only(bottom: 14),
@@ -152,9 +176,25 @@ class ExamsPage extends StatelessWidget {
),
),
const SizedBox(height: 14),
if (exam.date.isNotEmpty)
_field(Icons.calendar_today_rounded, '考试日期', exam.date),
_field(Icons.schedule_rounded, '考试时间', exam.time),
_field(Icons.location_on_outlined, '考场', exam.room),
_field(Icons.event_seat_outlined, '座位号', exam.seat),
if (exam.examTypeId != null)
_field(
Icons.category_outlined,
'考试类型',
UndergraduateExamType.fromId(exam.examTypeId!).label,
),
if (exam.status.isNotEmpty)
_field(
Icons.assignment_turned_in_outlined,
'考试情况',
exam.status,
),
if (exam.notes.isNotEmpty)
_field(Icons.info_outline_rounded, '说明', exam.notes),
if (exam.assessment.isNotEmpty)
_field(
Icons.assignment_outlined,