diff --git a/Nop.Plugin.Misc.AIPlugin/Areas/Admin/Views/Order/List.cshtml b/Nop.Plugin.Misc.AIPlugin/Areas/Admin/Views/Order/List.cshtml new file mode 100644 index 0000000..bbaab15 --- /dev/null +++ b/Nop.Plugin.Misc.AIPlugin/Areas/Admin/Views/Order/List.cshtml @@ -0,0 +1,654 @@ +@model OrderSearchModel + +@inject IStoreService storeService +@using Nop.Services.Stores + +@{ + //page title + ViewBag.PageTitle = T("Admin.Orders").Text; + //active menu item (system name) + NopHtml.SetActiveMenuItemSystemName("Orders"); +} + +@{ + const string hideSearchBlockAttributeName = "OrdersPage.HideSearchBlock"; + var hideSearchBlock = await genericAttributeService.GetAttributeAsync(await workContext.GetCurrentCustomerAsync(), hideSearchBlockAttributeName); +} + +@if (Model.LicenseCheckModel.BlockPages != true) +{ +
+
+

+ @T("Admin.Orders") +

+
+
+ + + +
+ +
+ + + +
+ @await Component.InvokeAsync(typeof(AdminWidgetViewComponent), new { widgetZone = AdminWidgetZones.OrderListButtons, additionalData = Model }) +
+
+
+
+
+
+ + +
+
+ + + @{ + var gridModel = new DataTablesModel + { + Name = "orders-grid", + UrlRead = new DataUrl("OrderList", "Order", null), + SearchButtonId = "search-orders", + Length = Model.PageSize, + LengthMenu = Model.AvailablePageSizes, + FooterCallback = !Model.IsLoggedInAsVendor ? "ordersfootercallback" : null, + FooterColumns = !Model.IsLoggedInAsVendor ? 10 : 0, + Filters = new List + { + new FilterParameter(nameof(Model.StartDate), typeof(DateTime?)), + new FilterParameter(nameof(Model.EndDate), typeof(DateTime?)), + new FilterParameter(nameof(Model.OrderStatusIds)), + new FilterParameter(nameof(Model.PaymentStatusIds)), + new FilterParameter(nameof(Model.ShippingStatusIds)), + new FilterParameter(nameof(Model.StoreId)), + new FilterParameter(nameof(Model.VendorId)), + new FilterParameter(nameof(Model.WarehouseId)), + new FilterParameter(nameof(Model.BillingEmail)), + new FilterParameter(nameof(Model.BillingPhone)), + new FilterParameter(nameof(Model.BillingLastName)), + new FilterParameter(nameof(Model.BillingCountryId)), + new FilterParameter(nameof(Model.PaymentMethodSystemName)), + new FilterParameter(nameof(Model.ProductId)), + new FilterParameter(nameof(Model.OrderNotes)) + } + }; + gridModel.ColumnCollection = new List + { + new ColumnProperty(nameof(OrderModel.Id)) + { + IsMasterCheckBox = true, + Render = new RenderCheckBox("checkbox_orders"), + ClassName = NopColumnClassDefaults.CenterAll, + Width = "50" + }, + new ColumnProperty(nameof(OrderModel.CustomOrderNumber)) + { + Title = T("Admin.Orders.Fields.CustomOrderNumber").Text, + Width = "80" + } + }; + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModelExtended.NeedsMeasurement)) + { + Title = "Needs Measurement", + Width = "100", + Render = new RenderCustom("renderColumnNeedsMeasurement"), + ClassName = NopColumnClassDefaults.CenterAll + }); + + //a vendor does not have access to this functionality + if (!Model.IsLoggedInAsVendor) + { + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.OrderStatus)) + { + Title = T("Admin.Orders.Fields.OrderStatus").Text, + Width = "100", + Render = new RenderCustom("renderColumnOrderStatus") + }); + } + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.PaymentStatus)) + { + Title = T("Admin.Orders.Fields.PaymentStatus").Text, + Width = "150" + }); + //a vendor does not have access to this functionality + if (!Model.IsLoggedInAsVendor) + { + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.ShippingStatus)) + { + Title = T("Admin.Orders.Fields.ShippingStatus").Text, + Width = "150" + }); + } + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.CustomerEmail)) + { + Title = T("Admin.Orders.Fields.Customer").Text, + Render = new RenderCustom("renderColumnCustomer") + }); + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.StoreName)) + { + Title = T("Admin.Orders.Fields.Store").Text, + Width = "100", + Visible = (await storeService.GetAllStoresAsync()).Count > 1 + }); + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.CreatedOn)) + { + Title = T("Admin.Orders.Fields.CreatedOn").Text, + Width = "120", + Render = new RenderDate() + }); + //a vendor does not have access to this functionality + if (!Model.IsLoggedInAsVendor) + { + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.OrderTotal)) + { + Title = T("Admin.Orders.Fields.OrderTotal").Text, + Width = "100", + }); + } + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.Id)) + { + Title = T("Admin.Common.View").Text, + Width = "50", + ClassName = NopColumnClassDefaults.Button, + Render = new RenderButtonView(new DataUrl("~/Admin/Order/Edit")) + }); + var orderSummaryColumnNumber = 8; + } + + @await Html.PartialAsync("Table", gridModel) + + +
+
+
+
+
+
+
+} + + + + +@*export selected (XML). We don't use GET approach because it's limited to 2K-4K chars and won't work for large number of entities*@ +
+ +
+ + + + +@*export selected (Excel). We don't use GET approach because it's limited to 2K-4K chars and won't work for large number of entities*@ +
+ +
+ + + + +@*Print packaging slips selected (XML). We don't use GET approach because it's limited to 2K-4K chars and won't work for large number of entities*@ +
+ +
+ + + + +@*import orders form*@ + + diff --git a/Nop.Plugin.Misc.AIPlugin/Areas/Admin/Views/Order/Test.cshtml b/Nop.Plugin.Misc.AIPlugin/Areas/Admin/Views/Order/Test.cshtml new file mode 100644 index 0000000..48930f0 --- /dev/null +++ b/Nop.Plugin.Misc.AIPlugin/Areas/Admin/Views/Order/Test.cshtml @@ -0,0 +1,4 @@ +@{ + Layout = "_AdminLayout"; +} +

TEST VIEW FROM PLUGIN

\ No newline at end of file diff --git a/Nop.Plugin.Misc.AIPlugin/Factories/CustomOrderModelFactory.cs b/Nop.Plugin.Misc.AIPlugin/Factories/CustomOrderModelFactory.cs new file mode 100644 index 0000000..0f0f8f0 --- /dev/null +++ b/Nop.Plugin.Misc.AIPlugin/Factories/CustomOrderModelFactory.cs @@ -0,0 +1,213 @@ +using Microsoft.AspNetCore.Mvc.Infrastructure; +using Microsoft.AspNetCore.Mvc.Routing; +using Nop.Core.Domain.Catalog; +using Nop.Core.Domain.Common; +using Nop.Core.Domain.Directory; +using Nop.Core.Domain.Orders; +using Nop.Core.Domain.Shipping; +using Nop.Core.Domain.Tax; +using Nop.Core; +using Nop.Plugin.Misc.FruitBankPlugin.Services; +using Nop.Services.Affiliates; +using Nop.Services.Catalog; +using Nop.Services.Common; +using Nop.Services.Configuration; +using Nop.Services.Customers; +using Nop.Services.Directory; +using Nop.Services.Discounts; +using Nop.Services.Helpers; +using Nop.Services.Localization; +using Nop.Services.Media; +using Nop.Services.Orders; +using Nop.Services.Payments; +using Nop.Services.Security; +using Nop.Services.Seo; +using Nop.Services.Shipping; +using Nop.Services.Stores; +using Nop.Services.Tax; +using Nop.Services.Vendors; +using Nop.Web.Areas.Admin.Factories; +using Nop.Web.Areas.Admin.Models.Orders; +using Nop.Plugin.Misc.FruitBankPlugin.Models; +using System.Reflection; +using Nop.Plugin.Misc.FruitBankPlugin.Helpers; + +namespace Nop.Plugin.Misc.FruitBankPlugin.Factories +{ + public class CustomOrderModelFactory : OrderModelFactory + { + private readonly IOrderMeasurementService _orderMeasurementService; + + public CustomOrderModelFactory( + IOrderMeasurementService orderMeasurementService, + AddressSettings addressSettings, + CatalogSettings catalogSettings, + CurrencySettings currencySettings, + IActionContextAccessor actionContextAccessor, + IAddressModelFactory addressModelFactory, + IAddressService addressService, + IAffiliateService affiliateService, + IBaseAdminModelFactory baseAdminModelFactory, + ICountryService countryService, + ICurrencyService currencyService, + ICustomerService customerService, + IDateTimeHelper dateTimeHelper, + IDiscountService discountService, + IDownloadService downloadService, + IEncryptionService encryptionService, + IGiftCardService giftCardService, + ILocalizationService localizationService, + IMeasureService measureService, + IOrderProcessingService orderProcessingService, + IOrderReportService orderReportService, + IOrderService orderService, + IPaymentPluginManager paymentPluginManager, + IPaymentService paymentService, + IPictureService pictureService, + IPriceCalculationService priceCalculationService, + IPriceFormatter priceFormatter, + IProductAttributeService productAttributeService, + IProductService productService, + IReturnRequestService returnRequestService, + IRewardPointService rewardPointService, + ISettingService settingService, + IShipmentService shipmentService, + IShippingService shippingService, + IStateProvinceService stateProvinceService, + IStoreService storeService, + ITaxService taxService, + IUrlHelperFactory urlHelperFactory, + IVendorService vendorService, + IWorkContext workContext, + MeasureSettings measureSettings, + NopHttpClient nopHttpClient, + OrderSettings orderSettings, + ShippingSettings shippingSettings, + IUrlRecordService urlRecordService, + TaxSettings taxSettings + ) : base(addressSettings, + catalogSettings, + currencySettings, + actionContextAccessor, + addressModelFactory, + addressService, + affiliateService, + baseAdminModelFactory, + countryService, + currencyService, + customerService, + dateTimeHelper, + discountService, + downloadService, + encryptionService, + giftCardService, + localizationService, + measureService, + orderProcessingService, + orderReportService, + orderService, + paymentPluginManager, + paymentService, + pictureService, + priceCalculationService, + priceFormatter, + productAttributeService, + productService, + returnRequestService, + rewardPointService, + settingService, + shipmentService, + shippingService, + stateProvinceService, + storeService, + taxService, + urlHelperFactory, + vendorService, + workContext, + measureSettings, + nopHttpClient, + orderSettings, + shippingSettings, + urlRecordService, + taxSettings + ) + { + _orderMeasurementService = orderMeasurementService; + } + + public override async Task PrepareOrderSearchModelAsync(OrderSearchModel searchModel) + { + // let base prepare default model first + var baseModel = await base.PrepareOrderSearchModelAsync(searchModel); + + // create derived/extended instance + var extended = new OrderSearchModelExtended(); + + // copy all public instance properties from baseModel to extended + CopyModelHelper.CopyPublicProperties(baseModel, extended); + + // try to obtain NeedsMeasurement from the incoming searchModel (if it's extended) + bool? needsMeasurement = null; + var prop = searchModel?.GetType().GetProperty("NeedsMeasurement", BindingFlags.Public | BindingFlags.Instance); + if (prop != null && prop.PropertyType == typeof(bool?)) + { + needsMeasurement = (bool?)prop.GetValue(searchModel); + } + + extended.NeedsMeasurement = needsMeasurement; + + // return the extended object (it's assignable to OrderSearchModel) + return extended; + } + + public override async Task PrepareOrderListModelAsync(OrderSearchModel searchModel) + { + // get the default model first + var baseModel = await base.PrepareOrderListModelAsync(searchModel); + + + + // project the rows into your extended row type + var extendedRows = baseModel.Data.Select(async order => new OrderModelExtended + { + Id = order.Id, + CustomOrderNumber = order.CustomOrderNumber, + OrderStatus = order.OrderStatus, + PaymentStatus = order.PaymentStatus, + ShippingStatus = order.ShippingStatus, + OrderTotal = order.OrderTotal, + CreatedOn = order.CreatedOn, + + // custom field + NeedsMeasurement = await ShouldMarkAsNeedsMeasurementAsync(order) + }).ToList(); + + // build a new OrderListModel but replace Data with the extended items + var model = new OrderListModel + { + Data = extendedRows.Cast().ToList(), // still satisfies the grid + //Total = baseModel.Total + }; + + return model; + } + + // example async custom logic + private async Task ShouldMarkAsNeedsMeasurementAsync(OrderModel order) + { + // TODO: your logic (e.g. check if order has products that need measuring) + if (order == null) + return false; + + var fullOrder = await _orderService.GetOrderByIdAsync(order.Id); + if (fullOrder != null) + { + return await _orderMeasurementService.IsPendingMeasurementAsync(fullOrder); + } + return await Task.FromResult(false); + } + + + } +} + diff --git a/Nop.Plugin.Misc.AIPlugin/Filters/PendingMeasurementCheckoutFilter.cs b/Nop.Plugin.Misc.AIPlugin/Filters/PendingMeasurementCheckoutFilter.cs index 25521f9..2547364 100644 --- a/Nop.Plugin.Misc.AIPlugin/Filters/PendingMeasurementCheckoutFilter.cs +++ b/Nop.Plugin.Misc.AIPlugin/Filters/PendingMeasurementCheckoutFilter.cs @@ -39,6 +39,7 @@ namespace Nop.Plugin.Misc.FruitBankPlugin.Filters if (order != null && await _orderMeasurementService.IsPendingMeasurementAsync(order)) { + order.OrderStatus = OrderStatus.Processing; context.Result = new RedirectToRouteResult(new { controller = "Checkout", diff --git a/Nop.Plugin.Misc.AIPlugin/Helpers/CopyModelHelper.cs b/Nop.Plugin.Misc.AIPlugin/Helpers/CopyModelHelper.cs new file mode 100644 index 0000000..9af2d64 --- /dev/null +++ b/Nop.Plugin.Misc.AIPlugin/Helpers/CopyModelHelper.cs @@ -0,0 +1,28 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Reflection; +using System.Text; +using System.Threading.Tasks; + +namespace Nop.Plugin.Misc.FruitBankPlugin.Helpers +{ + public static class CopyModelHelper + { + public static void CopyPublicProperties(TSource src, TDestination dest) + { + if (src == null || dest == null) return; + + var srcProps = typeof(TSource) + .GetProperties(BindingFlags.Public | BindingFlags.Instance) + .Where(p => p.CanRead); + + foreach (var sp in srcProps) + { + var dp = typeof(TDestination).GetProperty(sp.Name, BindingFlags.Public | BindingFlags.Instance); + if (dp == null || !dp.CanWrite) continue; + dp.SetValue(dest, sp.GetValue(src)); + } + } + } +} diff --git a/Nop.Plugin.Misc.AIPlugin/Infrastructure/PluginNopStartup.cs b/Nop.Plugin.Misc.AIPlugin/Infrastructure/PluginNopStartup.cs index 891baa7..711e0ea 100644 --- a/Nop.Plugin.Misc.AIPlugin/Infrastructure/PluginNopStartup.cs +++ b/Nop.Plugin.Misc.AIPlugin/Infrastructure/PluginNopStartup.cs @@ -13,9 +13,14 @@ using Microsoft.Extensions.Configuration; using Microsoft.Extensions.DependencyInjection; using Nop.Core.Infrastructure; using Nop.Plugin.Misc.FruitBankPlugin.Domains.DataLayer; +using Nop.Plugin.Misc.FruitBankPlugin.Factories; using Nop.Plugin.Misc.FruitBankPlugin.Filters; +using Nop.Plugin.Misc.FruitBankPlugin.Models; using Nop.Plugin.Misc.FruitBankPlugin.Services; using Nop.Services.Catalog; +using Nop.Web.Areas.Admin.Factories; +using Nop.Web.Areas.Admin.Models.Catalog; +using Nop.Web.Areas.Admin.Models.Orders; using FruitBankDataController = Nop.Plugin.Misc.FruitBankPlugin.Controllers.FruitBankDataController; namespace Nop.Plugin.Misc.FruitBankPlugin.Infrastructure; @@ -55,6 +60,10 @@ public class PluginNopStartup : INopStartup services.AddScoped(); services.AddScoped(); services.AddScoped(); + services.AddScoped(); + services.AddScoped(); + services.AddScoped(); + services.AddScoped(); services.AddControllersWithViews(options => { options.Filters.AddService(); diff --git a/Nop.Plugin.Misc.AIPlugin/Models/OrderListModelExtended.cs b/Nop.Plugin.Misc.AIPlugin/Models/OrderListModelExtended.cs new file mode 100644 index 0000000..79217ee --- /dev/null +++ b/Nop.Plugin.Misc.AIPlugin/Models/OrderListModelExtended.cs @@ -0,0 +1,10 @@ +using Nop.Web.Areas.Admin.Models.Orders; + +namespace Nop.Plugin.Misc.FruitBankPlugin.Models +{ + public partial record OrderListModelExtended : OrderListModel + { + public bool? NeedsMeasurement { get; set; } + } +} + diff --git a/Nop.Plugin.Misc.AIPlugin/Models/OrderModelExtended.cs b/Nop.Plugin.Misc.AIPlugin/Models/OrderModelExtended.cs new file mode 100644 index 0000000..afef1c0 --- /dev/null +++ b/Nop.Plugin.Misc.AIPlugin/Models/OrderModelExtended.cs @@ -0,0 +1,10 @@ +using Nop.Web.Areas.Admin.Models.Orders; + +namespace Nop.Plugin.Misc.FruitBankPlugin.Models +{ + public partial record OrderModelExtended : OrderModel + { + public bool NeedsMeasurement { get; set; } + } +} + diff --git a/Nop.Plugin.Misc.AIPlugin/Models/OrderSearchModelExtended.cs b/Nop.Plugin.Misc.AIPlugin/Models/OrderSearchModelExtended.cs new file mode 100644 index 0000000..7d46408 --- /dev/null +++ b/Nop.Plugin.Misc.AIPlugin/Models/OrderSearchModelExtended.cs @@ -0,0 +1,10 @@ +using Nop.Web.Areas.Admin.Models.Orders; + +namespace Nop.Plugin.Misc.FruitBankPlugin.Models +{ + public partial record OrderSearchModelExtended : OrderSearchModel + { + public bool? NeedsMeasurement { get; set; } + } +} + diff --git a/Nop.Plugin.Misc.AIPlugin/Nop.Plugin.Misc.FruitBankPlugin.csproj b/Nop.Plugin.Misc.AIPlugin/Nop.Plugin.Misc.FruitBankPlugin.csproj index bbc516c..293ead4 100644 --- a/Nop.Plugin.Misc.AIPlugin/Nop.Plugin.Misc.FruitBankPlugin.csproj +++ b/Nop.Plugin.Misc.AIPlugin/Nop.Plugin.Misc.FruitBankPlugin.csproj @@ -55,8 +55,6 @@ - - @@ -135,9 +133,18 @@ Always + + Always + + + Always + Always + + Always + Always diff --git a/Nop.Plugin.Misc.AIPlugin/Views/Admin/Order/List.cshtml b/Nop.Plugin.Misc.AIPlugin/Views/Admin/Order/List.cshtml new file mode 100644 index 0000000..f93834b --- /dev/null +++ b/Nop.Plugin.Misc.AIPlugin/Views/Admin/Order/List.cshtml @@ -0,0 +1,657 @@ +@model OrderSearchModel + +@inject IStoreService storeService +@using Nop.Services.Stores + +@{ + //page title + ViewBag.PageTitle = T("Admin.Orders").Text; + //active menu item (system name) + NopHtml.SetActiveMenuItemSystemName("Orders"); +} + +@{ + const string hideSearchBlockAttributeName = "OrdersPage.HideSearchBlock"; + var hideSearchBlock = await genericAttributeService.GetAttributeAsync(await workContext.GetCurrentCustomerAsync(), hideSearchBlockAttributeName); +} + +@if (Model.LicenseCheckModel.BlockPages != true) +{ +
+
+

+ @T("Admin.Orders") +

+
+
+ + + +
+ +
+ + + +
+ @await Component.InvokeAsync(typeof(AdminWidgetViewComponent), new { widgetZone = AdminWidgetZones.OrderListButtons, additionalData = Model }) +
+
+
+
+
+
+ + +
+

+ khfdsjklfkl fklsh fjsklhfjskl fhsjklhf sjklhfdsklhf djkfldsh fjklsdjkl +

+
+ + + @{ + var gridModel = new DataTablesModel + { + Name = "orders-grid", + UrlRead = new DataUrl("OrderList", "Order", null), + SearchButtonId = "search-orders", + Length = Model.PageSize, + LengthMenu = Model.AvailablePageSizes, + FooterCallback = !Model.IsLoggedInAsVendor ? "ordersfootercallback" : null, + FooterColumns = !Model.IsLoggedInAsVendor ? 10 : 0, + Filters = new List + { + new FilterParameter(nameof(Model.StartDate), typeof(DateTime?)), + new FilterParameter(nameof(Model.EndDate), typeof(DateTime?)), + new FilterParameter(nameof(Model.OrderStatusIds)), + new FilterParameter(nameof(Model.PaymentStatusIds)), + new FilterParameter(nameof(Model.ShippingStatusIds)), + new FilterParameter(nameof(Model.StoreId)), + new FilterParameter(nameof(Model.VendorId)), + new FilterParameter(nameof(Model.WarehouseId)), + new FilterParameter(nameof(Model.BillingEmail)), + new FilterParameter(nameof(Model.BillingPhone)), + new FilterParameter(nameof(Model.BillingLastName)), + new FilterParameter(nameof(Model.BillingCountryId)), + new FilterParameter(nameof(Model.PaymentMethodSystemName)), + new FilterParameter(nameof(Model.ProductId)), + new FilterParameter(nameof(Model.OrderNotes)) + } + }; + gridModel.ColumnCollection = new List + { + new ColumnProperty(nameof(OrderModel.Id)) + { + IsMasterCheckBox = true, + Render = new RenderCheckBox("checkbox_orders"), + ClassName = NopColumnClassDefaults.CenterAll, + Width = "50" + }, + new ColumnProperty(nameof(OrderModel.CustomOrderNumber)) + { + Title = T("Admin.Orders.Fields.CustomOrderNumber").Text, + Width = "80" + } + }; + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModelExtended.NeedsMeasurement)) + { + Title = "Needs Measurement", + Width = "100", + Render = new RenderCustom("renderColumnNeedsMeasurement"), + ClassName = NopColumnClassDefaults.CenterAll + }); + + //a vendor does not have access to this functionality + if (!Model.IsLoggedInAsVendor) + { + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.OrderStatus)) + { + Title = T("Admin.Orders.Fields.OrderStatus").Text, + Width = "100", + Render = new RenderCustom("renderColumnOrderStatus") + }); + } + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.PaymentStatus)) + { + Title = T("Admin.Orders.Fields.PaymentStatus").Text, + Width = "150" + }); + //a vendor does not have access to this functionality + if (!Model.IsLoggedInAsVendor) + { + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.ShippingStatus)) + { + Title = T("Admin.Orders.Fields.ShippingStatus").Text, + Width = "150" + }); + } + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.CustomerEmail)) + { + Title = T("Admin.Orders.Fields.Customer").Text, + Render = new RenderCustom("renderColumnCustomer") + }); + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.StoreName)) + { + Title = T("Admin.Orders.Fields.Store").Text, + Width = "100", + Visible = (await storeService.GetAllStoresAsync()).Count > 1 + }); + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.CreatedOn)) + { + Title = T("Admin.Orders.Fields.CreatedOn").Text, + Width = "120", + Render = new RenderDate() + }); + //a vendor does not have access to this functionality + if (!Model.IsLoggedInAsVendor) + { + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.OrderTotal)) + { + Title = T("Admin.Orders.Fields.OrderTotal").Text, + Width = "100", + }); + } + gridModel.ColumnCollection.Add(new ColumnProperty(nameof(OrderModel.Id)) + { + Title = T("Admin.Common.View").Text, + Width = "50", + ClassName = NopColumnClassDefaults.Button, + Render = new RenderButtonView(new DataUrl("~/Admin/Order/Edit")) + }); + var orderSummaryColumnNumber = 8; + } + + @await Html.PartialAsync("Table", gridModel) + + +
+
+
+
+
+
+
+} + + + + +@*export selected (XML). We don't use GET approach because it's limited to 2K-4K chars and won't work for large number of entities*@ +
+ +
+ + + + +@*export selected (Excel). We don't use GET approach because it's limited to 2K-4K chars and won't work for large number of entities*@ +
+ +
+ + + + +@*Print packaging slips selected (XML). We don't use GET approach because it's limited to 2K-4K chars and won't work for large number of entities*@ +
+ +
+ + + + +@*import orders form*@ + +