Initial commit: COPILOT D6 Flutter keyboard controller
Flutter web app replacing legacy WPF CCTV surveillance keyboard controller. Includes wall overview, section view with monitor grid, camera input, PTZ control, alarm/lock/sequence BLoCs, and legacy-matching UI styling. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,78 @@
|
||||
import 'dart:async';
|
||||
|
||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
|
||||
import '../../../data/services/alarm_service.dart';
|
||||
import '../../../data/services/state_service.dart';
|
||||
import 'alarm_event.dart';
|
||||
import 'alarm_state.dart';
|
||||
|
||||
class AlarmBloc extends Bloc<AlarmEvent, AlarmBlocState> {
|
||||
final AlarmService _alarmService;
|
||||
final StateService _stateService;
|
||||
StreamSubscription? _alarmSubscription;
|
||||
|
||||
AlarmBloc({
|
||||
required AlarmService alarmService,
|
||||
required StateService stateService,
|
||||
}) : _alarmService = alarmService,
|
||||
_stateService = stateService,
|
||||
super(const AlarmBlocState()) {
|
||||
on<RefreshAlarms>(_onRefreshAlarms);
|
||||
on<AlarmsUpdated>(_onAlarmsUpdated);
|
||||
on<AcknowledgeAlarm>(_onAcknowledgeAlarm);
|
||||
|
||||
// Subscribe to alarm changes
|
||||
_alarmSubscription = _alarmService.alarms.listen((alarms) {
|
||||
add(AlarmsUpdated(alarms));
|
||||
});
|
||||
}
|
||||
|
||||
Future<void> _onRefreshAlarms(
|
||||
RefreshAlarms event,
|
||||
Emitter<AlarmBlocState> emit,
|
||||
) async {
|
||||
emit(state.copyWith(isLoading: true, error: null));
|
||||
|
||||
try {
|
||||
await _alarmService.queryAllAlarms();
|
||||
emit(state.copyWith(isLoading: false, lastSync: DateTime.now()));
|
||||
} catch (e) {
|
||||
emit(state.copyWith(
|
||||
isLoading: false,
|
||||
error: 'Failed to refresh alarms: $e',
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
void _onAlarmsUpdated(
|
||||
AlarmsUpdated event,
|
||||
Emitter<AlarmBlocState> emit,
|
||||
) {
|
||||
// Filter to only active alarms for display
|
||||
final activeAlarms = event.alarms.where((a) => a.isActive).toList();
|
||||
|
||||
// Sort by start time (newest first)
|
||||
activeAlarms.sort((a, b) => b.startedAt.compareTo(a.startedAt));
|
||||
|
||||
emit(state.copyWith(
|
||||
activeAlarms: activeAlarms,
|
||||
lastSync: DateTime.now(),
|
||||
));
|
||||
}
|
||||
|
||||
Future<void> _onAcknowledgeAlarm(
|
||||
AcknowledgeAlarm event,
|
||||
Emitter<AlarmBlocState> emit,
|
||||
) async {
|
||||
// Alarm acknowledgment would be implemented here
|
||||
// This would call the bridge to acknowledge the alarm
|
||||
// For now, just log that we received the event
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> close() {
|
||||
_alarmSubscription?.cancel();
|
||||
return super.close();
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user