Refactor category handling in inventory and pantry forms
Test Suite / test (24.15.0) (push) Has been cancelled
Test Suite / test (24.15.0) (push) Has been cancelled
- Introduced `_categorySearchController` and `_categoryOptions` in both `_InventoryFormDialogState` and `_PantryFormDialogState` to manage category selection more effectively. - Implemented `_flattenCategoryOptions` method to create a flat list of category options from nested category nodes. - Updated the initialization and disposal of the new controllers to ensure proper resource management. - Made minor adjustments to the PopupMenuItem definitions in `AppShell` for consistency.
This commit is contained in:
Binary file not shown.
@@ -37,6 +37,6 @@ _flutter.buildConfig = {"engineRevision":"59aa584fdf100e6c78c785d8a5b565d1de4b48
|
|||||||
|
|
||||||
_flutter.loader.load({
|
_flutter.loader.load({
|
||||||
serviceWorkerSettings: {
|
serviceWorkerSettings: {
|
||||||
serviceWorkerVersion: "3795187910" /* Flutter's service worker is deprecated and will be removed in a future Flutter release. */
|
serviceWorkerVersion: "2742817442" /* Flutter's service worker is deprecated and will be removed in a future Flutter release. */
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|||||||
+84414
-79910
File diff suppressed because one or more lines are too long
@@ -210,8 +210,8 @@ class AppShell extends ConsumerWidget {
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
itemBuilder: (context) => const [
|
itemBuilder: (context) => [
|
||||||
PopupMenuItem<String>(
|
const PopupMenuItem<String>(
|
||||||
value: 'profile',
|
value: 'profile',
|
||||||
child: ListTile(
|
child: ListTile(
|
||||||
leading: Icon(Icons.person_outline),
|
leading: Icon(Icons.person_outline),
|
||||||
@@ -220,7 +220,7 @@ class AppShell extends ConsumerWidget {
|
|||||||
),
|
),
|
||||||
),
|
),
|
||||||
if (isAdmin)
|
if (isAdmin)
|
||||||
PopupMenuItem<String>(
|
const PopupMenuItem<String>(
|
||||||
value: 'admin',
|
value: 'admin',
|
||||||
child: ListTile(
|
child: ListTile(
|
||||||
leading: Icon(Icons.admin_panel_settings_outlined),
|
leading: Icon(Icons.admin_panel_settings_outlined),
|
||||||
@@ -228,8 +228,8 @@ class AppShell extends ConsumerWidget {
|
|||||||
contentPadding: EdgeInsets.zero,
|
contentPadding: EdgeInsets.zero,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
PopupMenuDivider(),
|
const PopupMenuDivider(),
|
||||||
PopupMenuItem<String>(
|
const PopupMenuItem<String>(
|
||||||
value: 'logout',
|
value: 'logout',
|
||||||
child: ListTile(
|
child: ListTile(
|
||||||
leading: Icon(Icons.logout),
|
leading: Icon(Icons.logout),
|
||||||
|
|||||||
@@ -781,6 +781,8 @@ class _InventoryFormDialogState extends State<_InventoryFormDialog> {
|
|||||||
late final TextEditingController _receiptNameController;
|
late final TextEditingController _receiptNameController;
|
||||||
late final TextEditingController _suitableForController;
|
late final TextEditingController _suitableForController;
|
||||||
late final TextEditingController _commentController;
|
late final TextEditingController _commentController;
|
||||||
|
late final TextEditingController _categorySearchController;
|
||||||
|
late List<CategorySelectOption> _categoryOptions;
|
||||||
|
|
||||||
int? _ownerUserId;
|
int? _ownerUserId;
|
||||||
int? _productId;
|
int? _productId;
|
||||||
@@ -806,6 +808,8 @@ class _InventoryFormDialogState extends State<_InventoryFormDialog> {
|
|||||||
_receiptNameController = TextEditingController(text: initial?.receiptName ?? '');
|
_receiptNameController = TextEditingController(text: initial?.receiptName ?? '');
|
||||||
_suitableForController = TextEditingController(text: initial?.suitableFor ?? '');
|
_suitableForController = TextEditingController(text: initial?.suitableFor ?? '');
|
||||||
_commentController = TextEditingController(text: initial?.comment ?? '');
|
_commentController = TextEditingController(text: initial?.comment ?? '');
|
||||||
|
_categorySearchController = TextEditingController(text: _categoryPath ?? '');
|
||||||
|
_categoryOptions = _flattenCategoryOptions(widget.categories);
|
||||||
}
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
@@ -817,6 +821,7 @@ class _InventoryFormDialogState extends State<_InventoryFormDialog> {
|
|||||||
_receiptNameController.dispose();
|
_receiptNameController.dispose();
|
||||||
_suitableForController.dispose();
|
_suitableForController.dispose();
|
||||||
_commentController.dispose();
|
_commentController.dispose();
|
||||||
|
_categorySearchController.dispose();
|
||||||
super.dispose();
|
super.dispose();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -853,6 +858,20 @@ class _InventoryFormDialogState extends State<_InventoryFormDialog> {
|
|||||||
.toList();
|
.toList();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
List<CategorySelectOption> _flattenCategoryOptions(
|
||||||
|
List<AdminCategoryNode> nodes, [
|
||||||
|
List<String> parents = const [],
|
||||||
|
]) {
|
||||||
|
final result = <CategorySelectOption>[];
|
||||||
|
for (final node in nodes) {
|
||||||
|
final pathParts = [...parents, node.name];
|
||||||
|
final path = pathParts.join(' > ');
|
||||||
|
result.add((value: node.id.toString(), label: path));
|
||||||
|
result.addAll(_flattenCategoryOptions(node.children, pathParts));
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
Future<void> _pickCategory() async {
|
Future<void> _pickCategory() async {
|
||||||
final selected = await CategoryThenProductPicker.showCategorySheet(
|
final selected = await CategoryThenProductPicker.showCategorySheet(
|
||||||
context,
|
context,
|
||||||
|
|||||||
@@ -506,6 +506,9 @@ class _PantryFormDialog extends StatefulWidget {
|
|||||||
|
|
||||||
class _PantryFormDialogState extends State<_PantryFormDialog> {
|
class _PantryFormDialogState extends State<_PantryFormDialog> {
|
||||||
late final TextEditingController _locationController;
|
late final TextEditingController _locationController;
|
||||||
|
late final TextEditingController _categorySearchController;
|
||||||
|
late List<CategorySelectOption> _categoryOptions;
|
||||||
|
|
||||||
int? _ownerUserId;
|
int? _ownerUserId;
|
||||||
int? _productId;
|
int? _productId;
|
||||||
int? _categoryId;
|
int? _categoryId;
|
||||||
@@ -522,11 +525,14 @@ class _PantryFormDialogState extends State<_PantryFormDialog> {
|
|||||||
_categoryId = initialProduct?.categoryId;
|
_categoryId = initialProduct?.categoryId;
|
||||||
_categoryPath = initialProduct?.categoryPath;
|
_categoryPath = initialProduct?.categoryPath;
|
||||||
_locationController = TextEditingController(text: initial?.location ?? '');
|
_locationController = TextEditingController(text: initial?.location ?? '');
|
||||||
|
_categorySearchController = TextEditingController(text: _categoryPath ?? '');
|
||||||
|
_categoryOptions = _flattenCategoryOptions(widget.categories);
|
||||||
}
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void dispose() {
|
void dispose() {
|
||||||
_locationController.dispose();
|
_locationController.dispose();
|
||||||
|
_categorySearchController.dispose();
|
||||||
super.dispose();
|
super.dispose();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -563,6 +569,20 @@ class _PantryFormDialogState extends State<_PantryFormDialog> {
|
|||||||
.toList();
|
.toList();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
List<CategorySelectOption> _flattenCategoryOptions(
|
||||||
|
List<AdminCategoryNode> nodes, [
|
||||||
|
List<String> parents = const [],
|
||||||
|
]) {
|
||||||
|
final result = <CategorySelectOption>[];
|
||||||
|
for (final node in nodes) {
|
||||||
|
final pathParts = [...parents, node.name];
|
||||||
|
final path = pathParts.join(' > ');
|
||||||
|
result.add((value: node.id.toString(), label: path));
|
||||||
|
result.addAll(_flattenCategoryOptions(node.children, pathParts));
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
Future<void> _pickCategory() async {
|
Future<void> _pickCategory() async {
|
||||||
final selected = await CategoryThenProductPicker.showCategorySheet(
|
final selected = await CategoryThenProductPicker.showCategorySheet(
|
||||||
context,
|
context,
|
||||||
|
|||||||
Reference in New Issue
Block a user