학생 계정 관리 타일 크기/폰트를 실시간 출석 확인 목록과 통일

계정 추가/엑셀 등록 칸과 학생 목록 타일 모두 "실시간 출석 확인"
목록의 타일 규격(220x148, 이름15/상태11.5/칩11 폰트)에 맞춰
동일한 비율로 재조정.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
2026-09-01 08:20:47 +09:00
co-authored by Claude Sonnet 5
parent eba23ecf9b
commit d9ab6adb51
+41 -31
View File
@@ -6,6 +6,10 @@ import 'package:flutter/material.dart';
import '../function/excel_file_picker.dart';
import '../function/teacher_student_management_controller.dart';
// 📐 "실시간 출석 확인" 목록(teacher_attendance_page.dart)의 타일 규격과 동일하게 맞춘다.
const double kAttendanceTileWidth = 220;
const double kAttendanceTileHeight = 148;
// -----------------------------------------------------------------------------
// 👥 [서브 화면 2] 학생 계정 관리 란 (추가 양식 폼 + 강제 삭제 다이얼로그 완전 내장)
// -----------------------------------------------------------------------------
@@ -545,28 +549,37 @@ class _TeacherStudentManagementPageState
final bool needsReset = student['device'] == '초기화 필요';
return Container(
padding: const EdgeInsets.all(8),
padding: const EdgeInsets.all(14),
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.circular(14),
borderRadius: BorderRadius.circular(20),
boxShadow: [
BoxShadow(color: Colors.black.withValues(alpha: 0.04), blurRadius: 8),
BoxShadow(
color: Colors.black.withValues(alpha: 0.03),
blurRadius: 12,
offset: const Offset(0, 4),
),
],
),
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
crossAxisAlignment: CrossAxisAlignment.center,
children: [
CircleAvatar(
radius: 20,
backgroundColor: needsReset ? Colors.red[50] : Colors.blue[50],
Container(
padding: const EdgeInsets.all(8),
decoration: BoxDecoration(
color: (needsReset ? Colors.red : Colors.blue).withValues(
alpha: 0.1,
),
shape: BoxShape.circle,
),
child: Icon(
needsReset ? Icons.lock_reset : Icons.person,
size: 20,
size: 18,
color: needsReset ? Colors.red : Colors.blue,
),
),
const SizedBox(height: 6),
const SizedBox(height: 8),
Text(
'$studentName ($studentId)',
textAlign: TextAlign.center,
@@ -574,13 +587,13 @@ class _TeacherStudentManagementPageState
overflow: TextOverflow.ellipsis,
style: const TextStyle(fontWeight: FontWeight.bold, fontSize: 15),
),
const SizedBox(height: 2),
const SizedBox(height: 4),
Text(
needsReset ? '초기화 대기중' : '정상 등록',
textAlign: TextAlign.center,
style: TextStyle(
fontSize: 12,
color: needsReset ? Colors.red : Colors.grey,
fontSize: 11.5,
color: needsReset ? Colors.red[700] : Colors.grey[600],
fontWeight: needsReset ? FontWeight.bold : FontWeight.normal,
),
),
@@ -597,7 +610,7 @@ class _TeacherStudentManagementPageState
labelPadding: const EdgeInsets.symmetric(horizontal: 6),
label: Text(
grade != null ? '$grade학년' : '미배정',
style: const TextStyle(fontSize: 12),
style: const TextStyle(fontSize: 11),
),
onPressed: () => _showGradeMenu(
chipContext,
@@ -611,22 +624,22 @@ class _TeacherStudentManagementPageState
icon: const Icon(
Icons.lock_reset,
color: Colors.purple,
size: 20,
size: 18,
),
tooltip: '기기 리셋',
padding: EdgeInsets.zero,
constraints: const BoxConstraints(minWidth: 30, minHeight: 30),
constraints: const BoxConstraints(minWidth: 28, minHeight: 28),
onPressed: () => _confirmResetDevice(studentId, studentName),
),
IconButton(
icon: const Icon(
Icons.delete_forever_rounded,
color: Colors.redAccent,
size: 20,
size: 18,
),
tooltip: '계정 영구 삭제',
padding: EdgeInsets.zero,
constraints: const BoxConstraints(minWidth: 30, minHeight: 30),
constraints: const BoxConstraints(minWidth: 28, minHeight: 28),
onPressed: () => _confirmDeleteStudent(studentId, studentName),
),
],
@@ -656,14 +669,10 @@ class _TeacherStudentManagementPageState
padding: const EdgeInsets.all(24.0),
child: LayoutBuilder(
builder: (context, constraints) {
// 🖥️ 웹(넓은 화면)은 계정 추가/엑셀 등록을 정사각형 2칸으로 나란히, 폰은 기존처럼 세로로 쌓는다.
// 🖥️ 웹(넓은 화면)은 계정 추가/엑셀 등록을 나란히, 폰은 기존처럼 세로로 쌓는다.
// 📐 크기/폰트 비율은 "실시간 출석 확인" 목록의 타일(220x148)과 동일하게 맞춘다.
final bool isWide = constraints.maxWidth >= 800;
final double listWidth = constraints.maxWidth;
// 📐 학생 목록 타일과 동일한 크기를 계정 추가/엑셀 등록 칸에도 사용한다.
final double tileSize =
((listWidth - (isWide ? 7 : 3) * 10) / (isWide ? 8 : 4)) *
1.5;
final double formSquareSize = tileSize;
final Widget addBoxColumn = Column(
crossAxisAlignment: CrossAxisAlignment.start,
@@ -671,8 +680,8 @@ class _TeacherStudentManagementPageState
_sectionTitle('신규 학생 계정 추가'),
const SizedBox(height: 16),
SizedBox(
width: isWide ? formSquareSize : double.infinity,
height: isWide ? formSquareSize : null,
width: isWide ? kAttendanceTileWidth : double.infinity,
height: isWide ? kAttendanceTileHeight : null,
child: _buildAddAccountBox(),
),
],
@@ -684,8 +693,8 @@ class _TeacherStudentManagementPageState
_sectionTitle('엑셀로 한번에 추가 (신입생 등)'),
const SizedBox(height: 16),
SizedBox(
width: isWide ? formSquareSize : double.infinity,
height: isWide ? formSquareSize : 240,
width: isWide ? kAttendanceTileWidth : double.infinity,
height: isWide ? kAttendanceTileHeight : 240,
child: _buildExcelBox(),
),
],
@@ -762,11 +771,12 @@ class _TeacherStudentManagementPageState
shrinkWrap: true,
physics: const NeverScrollableScrollPhysics(),
gridDelegate:
SliverGridDelegateWithMaxCrossAxisExtent(
maxCrossAxisExtent: tileSize,
crossAxisSpacing: 10,
mainAxisSpacing: 10,
childAspectRatio: 1,
const SliverGridDelegateWithMaxCrossAxisExtent(
maxCrossAxisExtent:
kAttendanceTileWidth,
mainAxisExtent: kAttendanceTileHeight,
crossAxisSpacing: 12,
mainAxisSpacing: 12,
),
itemCount: _controller.students.length,
itemBuilder: (context, index) =>