import 'package:flutter/material.dart'; import 'package:go_router/go_router.dart'; /// Defines a room in the application. /// /// Each feature/room registers itself with metadata for navigation, /// routing, and permission-based access control. class RoomDefinition { const RoomDefinition({ required this.id, required this.label, required this.icon, required this.selectedIcon, required this.defaultRoute, required this.routes, this.requiredPermissions = const [], }); /// Unique identifier used in preferences (e.g., 'front-hall', 'control-room'). final String id; /// Display label for UI. final String label; /// Icon when not selected. final IconData icon; /// Icon when selected. final IconData selectedIcon; /// Default route path when room is selected. final String defaultRoute; /// All routes this room provides to go_router. final List Function() routes; /// Permissions required to access this room (empty = accessible to all). /// User must have ALL listed permissions. final List requiredPermissions; } /// Central registry of all rooms in the application. /// /// Each room's router.dart file registers itself here. /// UI components query this registry to build navigation. class RoomRegistry { RoomRegistry._(); static final RoomRegistry instance = RoomRegistry._(); final List _rooms = []; /// Register a room. Called by each room's router.dart. void register(RoomDefinition room) { // Avoid duplicate registration if (!_rooms.any((r) => r.id == room.id)) { _rooms.add(room); } } /// Get all registered rooms. List get all => List.unmodifiable(_rooms); /// Get rooms filtered by user permissions. /// /// [userPermissions] is the set of permissions the user has. /// Returns rooms where the user has ALL required permissions. List accessibleTo(Set userPermissions) { return _rooms.where((room) { if (room.requiredPermissions.isEmpty) return true; return room.requiredPermissions.every(userPermissions.contains); }).toList(); } /// Get a room by its ID. RoomDefinition? byId(String id) { try { return _rooms.firstWhere((r) => r.id == id); } catch (_) { return null; } } /// Get the index of a room by its ID. int indexOfId(String id) { return _rooms.indexWhere((r) => r.id == id); } /// Get the index of a room by route path. int indexOfRoute(String path) { // Find room whose defaultRoute matches or whose routes start with path for (var i = 0; i < _rooms.length; i++) { final room = _rooms[i]; if (path == room.defaultRoute || path.startsWith('/${room.id}')) { return i; } } return 0; // Default to first room } /// Get all routes from all registered rooms. List allRoutes() { return _rooms.expand((room) => room.routes()).toList(); } /// Clear registry (useful for testing). void clear() { _rooms.clear(); } } /// Global registry instance. final roomRegistry = RoomRegistry.instance;