TIF_E41221079/lib/features/discipline/discipline_screen.dart

218 lines
6.8 KiB
Dart

// lib/features/discipline/discipline_screen.dart
import 'package:flutter/material.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:smpn1_lengkong/core/models/student_model.dart';
import 'package:smpn1_lengkong/core/constants/app_colors.dart';
import 'package:smpn1_lengkong/core/service/student_service.dart';
class DisciplineScreen extends StatefulWidget {
const DisciplineScreen({super.key});
@override
State<DisciplineScreen> createState() => _DisciplineScreenState();
}
class _DisciplineScreenState extends State<DisciplineScreen> {
StudentModel? _studentState;
String?
_currentClassFilter; // Variabel untuk mengunci kelas yang sedang dilihat
bool _isInitialized = false;
@override
void didChangeDependencies() {
super.didChangeDependencies();
// Inisialisasi data hanya sekali saat halaman dibuka
if (!_isInitialized) {
final args = ModalRoute.of(context)!.settings.arguments as StudentModel;
_studentState = args;
// Mengunci filter berdasarkan className yang dikirim saat navigasi
_currentClassFilter = args.className;
_isInitialized = true;
}
}
/// Fungsi untuk menarik data terbaru dari Firestore
Future<void> _handleRefresh() async {
if (_studentState == null) return;
try {
// Mengambil data profil siswa terbaru dari StudentService
final updatedStudent = await StudentService().getCurrentStudentData();
setState(() {
// Menggunakan copyWith untuk memastikan className tetap pada kelas yang dipilih
_studentState = updatedStudent.copyWith(className: _currentClassFilter);
});
if (mounted) {}
} catch (e) {}
}
@override
Widget build(BuildContext context) {
if (_studentState == null) {
return const Scaffold(body: Center(child: CircularProgressIndicator()));
}
final student = _studentState!;
// 1. Filter Pelanggaran sesuai kelas yang dipilih
final filteredViolations =
student.violationHistory.where((v) {
return v.className == _currentClassFilter;
}).toList();
// 2. LOGIKA SORTING: Mengurutkan dari tanggal TERBARU ke TERLAMA
filteredViolations.sort((a, b) {
try {
// Mengubah string tanggal menjadi DateTime untuk dibandingkan
DateTime dateA = DateTime.parse(a.date);
DateTime dateB = DateTime.parse(b.date);
return dateB.compareTo(dateA); // Descending (Terbaru di atas)
} catch (e) {
// Jika format tanggal tidak valid, biarkan urutan apa adanya
return 0;
}
});
// 3. Hitung total poin secara dinamis berdasarkan hasil filter
final int totalPoints = filteredViolations.fold(
0,
(sum, item) => sum + item.point,
);
return Scaffold(
backgroundColor: AppColors.backgroundWhite,
appBar: AppBar(
title: Text(
"Kedisiplinan - Kelas $_currentClassFilter",
style: const TextStyle(color: Colors.white),
),
backgroundColor: AppColors.primaryBlue,
foregroundColor: Colors.white,
elevation: 0,
),
body: RefreshIndicator(
onRefresh: _handleRefresh,
color: AppColors.primaryBlue,
child: Column(
children: [
// Header Card Poin Pelanggaran
Container(
width: double.infinity,
padding: EdgeInsets.all(24.w),
margin: EdgeInsets.all(20.w),
decoration: BoxDecoration(
gradient: const LinearGradient(
colors: [AppColors.warningOrange, Colors.orangeAccent],
),
borderRadius: BorderRadius.circular(16.r),
),
child: Column(
children: [
Text(
"Total Poin Pelanggaran (Kelas $_currentClassFilter)",
style: TextStyle(color: Colors.white, fontSize: 14.sp),
),
SizedBox(height: 8.h),
Text(
"$totalPoints",
style: TextStyle(
fontSize: 48.sp,
fontWeight: FontWeight.bold,
color: Colors.white,
),
),
],
),
),
// Daftar Riwayat Pelanggaran
Expanded(
child: Container(
width: double.infinity,
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.vertical(
top: Radius.circular(30.r),
),
),
child:
filteredViolations.isEmpty
? _buildEmptyState()
: ListView.separated(
physics: const AlwaysScrollableScrollPhysics(),
padding: EdgeInsets.all(24.w),
itemCount: filteredViolations.length,
separatorBuilder:
(context, index) => Divider(height: 30.h),
itemBuilder: (context, index) {
final item = filteredViolations[index];
return _buildViolationItem(item);
},
),
),
),
],
),
),
);
}
Widget _buildViolationItem(dynamic item) {
return Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Icon(Icons.circle, size: 12.sp, color: AppColors.dangerRed),
SizedBox(width: 16.w),
Expanded(
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Text(
item.date,
style: TextStyle(fontSize: 12.sp, color: Colors.grey),
),
Text(
item.description,
style: TextStyle(
fontSize: 16.sp,
fontWeight: FontWeight.normal,
color: AppColors.textPrimary,
),
),
Text(
"Kategori: ${item.category}",
style: TextStyle(fontSize: 12.sp, color: Colors.grey),
),
],
),
),
Text(
"+${item.point}",
style: const TextStyle(
color: AppColors.dangerRed,
fontWeight: FontWeight.bold,
),
),
],
);
}
Widget _buildEmptyState() {
return ListView(
physics: const AlwaysScrollableScrollPhysics(),
children: [
SizedBox(height: 100.h),
const Center(
child: Text(
"Tidak ada catatan pelanggaran",
style: TextStyle(color: Colors.grey),
),
),
],
);
}
}