Compare commits

..

2 Commits

Author SHA1 Message Date
a294988558 add subspace and space information 2025-01-30 10:09:21 +04:00
09c1a785e5 add subspace validation 2025-01-29 22:03:56 +04:00
5 changed files with 91 additions and 11 deletions

View File

@ -0,0 +1,47 @@
class DeviceSubspace {
final String uuid;
final DateTime? createdAt;
final DateTime? updatedAt;
final String subspaceName;
final bool disabled;
DeviceSubspace({
required this.uuid,
this.createdAt,
this.updatedAt,
required this.subspaceName,
required this.disabled,
});
factory DeviceSubspace.fromJson(Map<String, dynamic> json) {
return DeviceSubspace(
uuid: json['uuid'] as String,
createdAt: json['createdAt'] != null
? DateTime.tryParse(json['createdAt'].toString())
: null,
updatedAt: json['updatedAt'] != null
? DateTime.tryParse(json['updatedAt'].toString())
: null,
subspaceName: json['subspaceName'] as String,
disabled: json['disabled'] as bool,
);
}
Map<String, dynamic> toJson() {
return {
'uuid': uuid,
'createdAt': createdAt?.toIso8601String(),
'updatedAt': updatedAt?.toIso8601String(),
'subspaceName': subspaceName,
'disabled': disabled,
};
}
static List<DeviceSubspace> listFromJson(List<dynamic> jsonList) {
return jsonList.map((json) => DeviceSubspace.fromJson(json)).toList();
}
static List<Map<String, dynamic>> listToJson(List<DeviceSubspace> subspaces) {
return subspaces.map((subspace) => subspace.toJson()).toList();
}
}

View File

@ -1,5 +1,6 @@
import 'package:syncrow_web/pages/device_managment/all_devices/models/device_community.model.dart'; import 'package:syncrow_web/pages/device_managment/all_devices/models/device_community.model.dart';
import 'package:syncrow_web/pages/device_managment/all_devices/models/device_space_model.dart'; import 'package:syncrow_web/pages/device_managment/all_devices/models/device_space_model.dart';
import 'package:syncrow_web/pages/device_managment/all_devices/models/device_subspace.model.dart';
import 'package:syncrow_web/pages/device_managment/all_devices/models/room.dart'; import 'package:syncrow_web/pages/device_managment/all_devices/models/room.dart';
import 'package:syncrow_web/pages/device_managment/all_devices/models/unit.dart'; import 'package:syncrow_web/pages/device_managment/all_devices/models/unit.dart';
import 'package:syncrow_web/pages/routiens/models/ac/ac_function.dart'; import 'package:syncrow_web/pages/routiens/models/ac/ac_function.dart';
@ -47,6 +48,7 @@ class AllDevicesModel {
*/ */
DevicesModelRoom? room; DevicesModelRoom? room;
DeviceSubspace? subspace;
DevicesModelUnit? unit; DevicesModelUnit? unit;
DeviceCommunityModel? community; DeviceCommunityModel? community;
String? productUuid; String? productUuid;
@ -77,6 +79,7 @@ class AllDevicesModel {
AllDevicesModel({ AllDevicesModel({
this.room, this.room,
this.subspace,
this.unit, this.unit,
this.community, this.community,
this.productUuid, this.productUuid,
@ -110,6 +113,9 @@ class AllDevicesModel {
room = (json['room'] != null && (json['room'] is Map)) room = (json['room'] != null && (json['room'] is Map))
? DevicesModelRoom.fromJson(json['room']) ? DevicesModelRoom.fromJson(json['room'])
: null; : null;
subspace = (json['subspace'] != null && (json['subspace'] is Map))
? DeviceSubspace.fromJson(json['subspace'])
: null;
unit = (json['unit'] != null && (json['unit'] is Map)) unit = (json['unit'] != null && (json['unit'] is Map))
? DevicesModelUnit.fromJson(json['unit']) ? DevicesModelUnit.fromJson(json['unit'])
: null; : null;
@ -288,6 +294,9 @@ SOS
if (room != null) { if (room != null) {
data['room'] = room!.toJson(); data['room'] = room!.toJson();
} }
if (subspace != null) {
data['subspace'] = subspace!.toJson();
}
if (unit != null) { if (unit != null) {
data['unit'] = unit!.toJson(); data['unit'] = unit!.toJson();
} }
@ -330,6 +339,7 @@ SOS
return other is AllDevicesModel && return other is AllDevicesModel &&
other.room == room && other.room == room &&
other.subspace == subspace &&
other.unit == unit && other.unit == unit &&
other.productUuid == productUuid && other.productUuid == productUuid &&
other.productType == productType && other.productType == productType &&
@ -360,6 +370,7 @@ SOS
@override @override
int get hashCode { int get hashCode {
return room.hashCode ^ return room.hashCode ^
subspace.hashCode ^
unit.hashCode ^ unit.hashCode ^
productUuid.hashCode ^ productUuid.hashCode ^
productType.hashCode ^ productType.hashCode ^

View File

@ -95,8 +95,9 @@ class DeviceControlDialog extends StatelessWidget with RouteControlsBasedCode {
]), ]),
TableRow( TableRow(
children: [ children: [
_buildInfoRow('Space Name:', device.unit?.name ?? 'N/A'), _buildInfoRow('Space Name:',
_buildInfoRow('Room:', device.room?.name ?? 'N/A'), device.spaces?.firstOrNull?.spaceName ?? 'N/A'),
_buildInfoRow('Room:', device.subspace?.subspaceName ?? 'N/A'),
], ],
), ),
TableRow( TableRow(
@ -111,9 +112,13 @@ class DeviceControlDialog extends StatelessWidget with RouteControlsBasedCode {
), ),
_buildInfoRow( _buildInfoRow(
'Battery Level:', 'Battery Level:',
device.batteryLevel != null ? '${device.batteryLevel ?? 0}%' : "-", device.batteryLevel != null
? '${device.batteryLevel ?? 0}%'
: "-",
statusColor: device.batteryLevel != null statusColor: device.batteryLevel != null
? (device.batteryLevel! < 20 ? ColorsManager.red : ColorsManager.green) ? (device.batteryLevel! < 20
? ColorsManager.red
: ColorsManager.green)
: null, : null,
), ),
], ],

View File

@ -1,5 +1,6 @@
import 'package:syncrow_web/pages/spaces_management/all_spaces/model/product_model.dart'; import 'package:syncrow_web/pages/spaces_management/all_spaces/model/product_model.dart';
import 'package:syncrow_web/utils/constants/action_enum.dart'; import 'package:syncrow_web/utils/constants/action_enum.dart';
import 'package:uuid/uuid.dart';
import 'tag.dart'; import 'tag.dart';
@ -8,19 +9,24 @@ class SubspaceModel {
String subspaceName; String subspaceName;
final bool disabled; final bool disabled;
List<Tag>? tags; List<Tag>? tags;
String internalId;
SubspaceModel({ SubspaceModel({
this.uuid, this.uuid,
required this.subspaceName, required this.subspaceName,
required this.disabled, required this.disabled,
this.tags, this.tags,
}); String? internalId,
}) : internalId = internalId ?? const Uuid().v4();
factory SubspaceModel.fromJson(Map<String, dynamic> json) { factory SubspaceModel.fromJson(Map<String, dynamic> json) {
final String internalId = json['internalId'] ?? const Uuid().v4();
return SubspaceModel( return SubspaceModel(
uuid: json['uuid'] ?? '', uuid: json['uuid'] ?? '',
subspaceName: json['subspaceName'] ?? '', subspaceName: json['subspaceName'] ?? '',
disabled: json['disabled'] ?? false, disabled: json['disabled'] ?? false,
internalId: internalId,
tags: (json['tags'] as List<dynamic>?) tags: (json['tags'] as List<dynamic>?)
?.map((item) => Tag.fromJson(item)) ?.map((item) => Tag.fromJson(item))
.toList() ?? .toList() ??

View File

@ -358,10 +358,21 @@ class CreateSpaceDialogState extends State<CreateSpaceDialog> {
SubspaceNameDisplayWidget( SubspaceNameDisplayWidget(
text: subspace.subspaceName, text: subspace.subspaceName,
validateName: (updatedName) { validateName: (updatedName) {
return subspaces!.any((s) => bool nameExists =
s != subspace && subspaces!.any((s) {
s.subspaceName == bool isSameId = s.internalId ==
updatedName); subspace.internalId;
bool isSameName = s.subspaceName
.trim()
.toLowerCase() ==
updatedName
.trim()
.toLowerCase();
return !isSameId && isSameName;
});
return !nameExists;
}, },
onNameChanged: (updatedName) { onNameChanged: (updatedName) {
setState(() { setState(() {