diff --git a/lib/api.dart b/lib/api.dart index f0fdc839..3e147774 100644 --- a/lib/api.dart +++ b/lib/api.dart @@ -285,6 +285,9 @@ class InvenTreeAPI { // ReturnOrder supports API v104 or newer bool get supportsReturnOrders => isConnected() && apiVersion >= 104; + // "Contact" model exposed to API + bool get supportsContactModel => isConnected() && apiVersion >= 104; + // Status label endpoints API v105 or newer bool get supportsStatusLabelEndpoints => isConnected() && apiVersion >= 105; diff --git a/lib/api_form.dart b/lib/api_form.dart index 360617a4..341d7406 100644 --- a/lib/api_form.dart +++ b/lib/api_form.dart @@ -523,18 +523,17 @@ class APIFormField { ), selectedItem: initial_data, asyncItems: (String filter) async { - Map filters = {}; + Map _filters = {}; filters.forEach((key, value) { - filters[key] = value; + _filters[key] = value; }); - filters["search"] = filter; - filters["offset"] = "0"; - filters["limit"] = "25"; + _filters["search"] = filter; + _filters["offset"] = "0"; + _filters["limit"] = "25"; - final APIResponse response = - await InvenTreeAPI().get(api_url, params: filters); + final APIResponse response = await InvenTreeAPI().get(api_url, params: _filters); if (response.isValid()) { List results = []; @@ -650,6 +649,13 @@ class APIFormField { title: Text(name), leading: FaIcon(isGroup ? FontAwesomeIcons.users : FontAwesomeIcons.user), ); + case "contact": + String name = (data["name"] ?? "") as String; + String role = (data["role"] ?? "") as String; + return ListTile( + title: Text(name), + subtitle: Text(role), + ); case "company": var company = InvenTreeCompany.fromJson(data); return ListTile( diff --git a/lib/inventree/purchase_order.dart b/lib/inventree/purchase_order.dart index 2194328d..23f5819b 100644 --- a/lib/inventree/purchase_order.dart +++ b/lib/inventree/purchase_order.dart @@ -26,11 +26,21 @@ class InvenTreePurchaseOrder extends InvenTreeModel { Map formFields() { return { "reference": {}, + "supplier": { + "filters": { + "is_supplier": true, + }, + }, "supplier_reference": {}, "description": {}, "target_date": {}, "link": {}, "responsible": {}, + "contact": { + "filters": { + "company": supplierId, + } + }, }; } diff --git a/lib/l10n/app_en.arb b/lib/l10n/app_en.arb index f01d2531..b1895543 100644 --- a/lib/l10n/app_en.arb +++ b/lib/l10n/app_en.arb @@ -726,6 +726,9 @@ "purchaseOrder": "Purchase Order", "@purchaseOrder": {}, + "purchaseOrderCreate": "New Purchase Order", + "@purchaseOrderCreate": {}, + "purchaseOrderEdit": "Edit Purchase Order", "@purchaseOrderEdit": {}, diff --git a/lib/widget/purchase_order_detail.dart b/lib/widget/purchase_order_detail.dart index f70d09a3..77337ef8 100644 --- a/lib/widget/purchase_order_detail.dart +++ b/lib/widget/purchase_order_detail.dart @@ -83,11 +83,19 @@ class _PurchaseOrderDetailState extends RefreshableState editOrder(BuildContext context) async { + var fields = order.formFields(); + fields.remove("supplier"); + + if (!api.supportsContactModel) { + fields.remove("contact"); + } order.editForm( context, L10().purchaseOrderEdit, + fields: fields, onSuccess: (data) async { refresh(context); showSnackIcon(L10().purchaseOrderUpdated, success: true); @@ -143,8 +151,8 @@ class _PurchaseOrderDetailState extends RefreshableState tiles = []; - tiles.add(headerTile(context)); - for (var line in lines) { InvenTreeSupplierPart? supplierPart = line.supplierPart; @@ -347,9 +347,6 @@ class _PurchaseOrderDetailState extends RefreshableState actionButtons(BuildContext context) { + List actions = []; + + if (api.checkPermission("purchase_order", "add")) { + actions.add( + SpeedDialChild( + child: FaIcon(FontAwesomeIcons.circlePlus), + label: L10().purchaseOrderCreate, + onTap: () { + createPurchaseOrder(context); + } + ) + ); + } + + return actions; + } + + Future createPurchaseOrder(BuildContext context) async { + var fields = InvenTreePurchaseOrder().formFields(); + + fields.remove("contact"); + + InvenTreePurchaseOrder().createForm( + context, + L10().purchaseOrderCreate, + fields: fields, + onSuccess: (result) async { + Map data = result as Map; + + if (data.containsKey("pk")) { + var order = InvenTreePurchaseOrder.fromJson(data); + + Navigator.push( + context, + MaterialPageRoute( + builder: (context) => PurchaseOrderDetailWidget(order) + ) + ); + } + } + ); + } + @override Widget getBody(BuildContext context) { return PaginatedPurchaseOrderList(filters, showFilterOptions);