From e6e46be9b4488b17eb89432dc91b5774cf67daa6 Mon Sep 17 00:00:00 2001 From: hannathkadher Date: Sun, 2 Feb 2025 23:16:34 +0400 Subject: [PATCH] fixed issues in create space and duplicate --- .../bloc/space_management_bloc.dart | 2 + .../all_spaces/model/space_model.dart | 3 ++ .../widgets/community_structure_widget.dart | 14 +++--- .../widgets/dialogs/create_space_dialog.dart | 28 +++++++++--- .../widgets/loaded_space_widget.dart | 28 ++++++------ .../helper/space_helper.dart | 43 +++++++++++++++++++ .../models/space_template_model.dart | 1 - 7 files changed, 90 insertions(+), 29 deletions(-) create mode 100644 lib/pages/spaces_management/helper/space_helper.dart diff --git a/lib/pages/spaces_management/all_spaces/bloc/space_management_bloc.dart b/lib/pages/spaces_management/all_spaces/bloc/space_management_bloc.dart index 1b5692c6..31e19af4 100644 --- a/lib/pages/spaces_management/all_spaces/bloc/space_management_bloc.dart +++ b/lib/pages/spaces_management/all_spaces/bloc/space_management_bloc.dart @@ -179,6 +179,7 @@ class SpaceManagementBloc final updatedCommunities = await Future.wait(communities.map((community) async { final spaces = await _fetchSpacesForCommunity(community.uuid); + return CommunityModel( uuid: community.uuid, createdAt: community.createdAt, @@ -313,6 +314,7 @@ class SpaceManagementBloc SelectSpaceEvent event, Emitter emit, ) { + _handleCommunitySpaceStateUpdate( emit: emit, selectedCommunity: event.selectedCommunity, diff --git a/lib/pages/spaces_management/all_spaces/model/space_model.dart b/lib/pages/spaces_management/all_spaces/model/space_model.dart index 6ad91dad..71d365ca 100644 --- a/lib/pages/spaces_management/all_spaces/model/space_model.dart +++ b/lib/pages/spaces_management/all_spaces/model/space_model.dart @@ -95,6 +95,9 @@ class SpaceModel { icon: json['icon'] ?? Assets.location, position: Offset(json['x'] ?? 0, json['y'] ?? 0), isHovered: false, + spaceModel: json['spaceModel'] != null + ? SpaceTemplateModel.fromJson(json['spaceModel']) + : null, tags: (json['tags'] as List?) ?.where((item) => item is Map) // Validate type .map((item) => Tag.fromJson(item as Map)) diff --git a/lib/pages/spaces_management/all_spaces/widgets/community_structure_widget.dart b/lib/pages/spaces_management/all_spaces/widgets/community_structure_widget.dart index 210bda3a..2ae20b9e 100644 --- a/lib/pages/spaces_management/all_spaces/widgets/community_structure_widget.dart +++ b/lib/pages/spaces_management/all_spaces/widgets/community_structure_widget.dart @@ -22,6 +22,7 @@ import 'package:syncrow_web/pages/spaces_management/all_spaces/widgets/curved_li import 'package:syncrow_web/pages/spaces_management/all_spaces/widgets/dialogs/duplicate_process_dialog.dart'; import 'package:syncrow_web/pages/spaces_management/all_spaces/widgets/space_card_widget.dart'; import 'package:syncrow_web/pages/spaces_management/all_spaces/widgets/space_container_widget.dart'; +import 'package:syncrow_web/pages/spaces_management/helper/space_helper.dart'; import 'package:syncrow_web/pages/spaces_management/space_model/models/space_template_model.dart'; import 'package:syncrow_web/utils/color_manager.dart'; @@ -341,6 +342,7 @@ class _CommunityStructureAreaState extends State { } void _showEditSpaceDialog() { + print("parentsdf space is ${widget.selectedSpace?.parent?.name}"); if (widget.selectedSpace != null) { showDialog( context: context, @@ -350,7 +352,10 @@ class _CommunityStructureAreaState extends State { spaceModels: widget.spaceModels, name: widget.selectedSpace!.name, icon: widget.selectedSpace!.icon, + parentSpace: SpaceHelper.findSpaceByInternalId( + widget.selectedSpace?.parent?.internalId, spaces), editSpace: widget.selectedSpace, + currentSpaceModel: widget.selectedSpace?.spaceModel, tags: widget.selectedSpace?.tags, subspaces: widget.selectedSpace?.subspaces, isEdit: true, @@ -650,12 +655,6 @@ class _CommunityStructureAreaState extends State { final Map nameCounters = {}; - String _generateCopyName(String originalName) { - final baseName = originalName.replaceAll(RegExp(r'\(\d+\)$'), '').trim(); - nameCounters[baseName] = (nameCounters[baseName] ?? 0) + 1; - return "$baseName(${nameCounters[baseName]})"; - } - SpaceModel duplicateRecursive(SpaceModel original, Offset parentPosition, SpaceModel? duplicatedParent) { Offset newPosition = parentPosition + Offset(horizontalGap, 0); @@ -666,7 +665,8 @@ class _CommunityStructureAreaState extends State { newPosition += Offset(horizontalGap, 0); } - final duplicatedName = _generateCopyName(original.name); + final duplicatedName = + SpaceHelper.generateUniqueSpaceName(original.name, spaces); final duplicated = SpaceModel( name: duplicatedName, diff --git a/lib/pages/spaces_management/all_spaces/widgets/dialogs/create_space_dialog.dart b/lib/pages/spaces_management/all_spaces/widgets/dialogs/create_space_dialog.dart index 2a0050b2..a435a8fc 100644 --- a/lib/pages/spaces_management/all_spaces/widgets/dialogs/create_space_dialog.dart +++ b/lib/pages/spaces_management/all_spaces/widgets/dialogs/create_space_dialog.dart @@ -40,6 +40,7 @@ class CreateSpaceDialog extends StatefulWidget { final List? subspaces; final List? tags; final List? allTags; + final SpaceTemplateModel? currentSpaceModel; const CreateSpaceDialog( {super.key, @@ -54,7 +55,8 @@ class CreateSpaceDialog extends StatefulWidget { this.selectedProducts = const [], this.spaceModels, this.subspaces, - this.tags}); + this.tags, + this.currentSpaceModel}); @override CreateSpaceDialogState createState() => CreateSpaceDialogState(); @@ -83,6 +85,7 @@ class CreateSpaceDialogState extends State { enteredName.isNotEmpty || nameController.text.isNotEmpty; tags = widget.tags ?? []; subspaces = widget.subspaces ?? []; + selectedSpaceModel = widget.currentSpaceModel; } @override @@ -570,12 +573,23 @@ class CreateSpaceDialogState extends State { } bool _isNameConflict(String value) { - return (widget.parentSpace?.children.any((child) => child.name == value) ?? - false) || - (widget.parentSpace?.name == value) || - (widget.editSpace?.parent?.name == value) || - (widget.editSpace?.children.any((child) => child.name == value) ?? - false); + final parentSpace = widget.parentSpace; + final editSpace = widget.editSpace; + final siblings = parentSpace?.children + .where((child) => child.uuid != editSpace?.uuid) + .toList() ?? + []; + final siblingConflict = siblings.any((child) => child.name == value); + final parentConflict = + parentSpace?.name == value && parentSpace?.uuid != editSpace?.uuid; + final parentOfEditSpaceConflict = editSpace?.parent?.name == value && + editSpace?.parent?.uuid != editSpace?.uuid; + final childConflict = + editSpace?.children.any((child) => child.name == value) ?? false; + return siblingConflict || + parentConflict || + parentOfEditSpaceConflict || + childConflict; } void _showLinkSpaceModelDialog(BuildContext context) { diff --git a/lib/pages/spaces_management/all_spaces/widgets/loaded_space_widget.dart b/lib/pages/spaces_management/all_spaces/widgets/loaded_space_widget.dart index f1e9e753..0ce06c7c 100644 --- a/lib/pages/spaces_management/all_spaces/widgets/loaded_space_widget.dart +++ b/lib/pages/spaces_management/all_spaces/widgets/loaded_space_widget.dart @@ -39,15 +39,25 @@ class _LoadedSpaceViewState extends State { @override void initState() { super.initState(); - _spaceModels = widget.spaceModels ?? []; + _spaceModels = List.from(widget.spaceModels ?? []); + } + + @override + void didUpdateWidget(covariant LoadedSpaceView oldWidget) { + super.didUpdateWidget(oldWidget); + if (widget.spaceModels != oldWidget.spaceModels) { + setState(() { + _spaceModels = List.from(widget.spaceModels ?? []); + }); + } } void _onSpaceModelsUpdated(List updatedModels) { - WidgetsBinding.instance.addPostFrameCallback((_) { + if (mounted && updatedModels != _spaceModels) { setState(() { _spaceModels = updatedModels; }); - }); + } } @override @@ -72,8 +82,7 @@ class _LoadedSpaceViewState extends State { ), child: SpaceModelPage( products: widget.products, - onSpaceModelsUpdated: - _onSpaceModelsUpdated, // Pass callback + onSpaceModelsUpdated: _onSpaceModelsUpdated, ), ), ) @@ -91,13 +100,4 @@ class _LoadedSpaceViewState extends State { ], ); } - - SpaceModel? findSpaceByUuid(String? uuid, List communities) { - for (var community in communities) { - for (var space in community.spaces) { - if (space.uuid == uuid) return space; - } - } - return null; - } } diff --git a/lib/pages/spaces_management/helper/space_helper.dart b/lib/pages/spaces_management/helper/space_helper.dart new file mode 100644 index 00000000..75aebce9 --- /dev/null +++ b/lib/pages/spaces_management/helper/space_helper.dart @@ -0,0 +1,43 @@ +import 'package:syncrow_web/pages/spaces_management/all_spaces/model/community_model.dart'; +import 'package:syncrow_web/pages/spaces_management/all_spaces/model/space_model.dart'; + +class SpaceHelper { + static SpaceModel? findSpaceByUuid( + String? uuid, List communities) { + for (var community in communities) { + for (var space in community.spaces) { + if (space.uuid == uuid) return space; + } + } + return null; + } + + static SpaceModel? findSpaceByInternalId( + String? internalId, List spaces) { + if (internalId != null) { + for (var space in spaces) { + if (space.internalId == internalId) return space; + } + } + + return null; + } + + static String generateUniqueSpaceName( + String originalName, List spaces) { + final baseName = originalName.replaceAll(RegExp(r'\(\d+\)$'), '').trim(); + int maxNumber = 0; + + for (var space in spaces) { + final match = RegExp(r'^(.*?)\((\d+)\)$').firstMatch(space.name); + if (match != null && match.group(1)?.trim() == baseName) { + int existingNumber = int.parse(match.group(2)!); + if (existingNumber > maxNumber) { + maxNumber = existingNumber; + } + } + } + + return "$baseName(${maxNumber + 1})"; + } +} diff --git a/lib/pages/spaces_management/space_model/models/space_template_model.dart b/lib/pages/spaces_management/space_model/models/space_template_model.dart index 5edf912f..22378f1f 100644 --- a/lib/pages/spaces_management/space_model/models/space_template_model.dart +++ b/lib/pages/spaces_management/space_model/models/space_template_model.dart @@ -1,5 +1,4 @@ import 'package:equatable/equatable.dart'; -import 'package:syncrow_web/pages/spaces_management/all_spaces/model/product_model.dart'; import 'package:syncrow_web/pages/spaces_management/space_model/models/subspace_template_model.dart'; import 'package:syncrow_web/pages/spaces_management/space_model/models/tag_model.dart'; import 'package:syncrow_web/pages/spaces_management/space_model/models/tag_update_model.dart';