print customer statistic with or without price

This commit is contained in:
Frede Hundewadt 2023-08-25 15:35:26 +02:00
parent c5ce40b48e
commit c929e7e17a
10 changed files with 290 additions and 94 deletions

View file

@ -0,0 +1,76 @@
@using Wonky.Client.Models
<table class="table table-striped d-print-table w-100">
<thead>
<tr>
<th class="text-center" colspan="6">
<h2>Produktkøb @CompanyName</h2>
<p>@HeaderGenerated</p>
</th>
</tr>
<tr class="rounded-2 border border-1">
<th scope="col">
Beskrivelse
</th>
<th scope="col">
Vare Nr.
</th>
<th scope="col">
Dato
</th>
<th scope="col">
Antal
</th>
@if (IncludePrice)
{
<th scope="col" class="text-end">
Pris
</th>
<th scope="col" class="text-end">
Afslag
</th>
}
</tr>
</thead>
<tbody>
@foreach (var item in Items)
{
<tr class="align-content-center">
<td>
@item.Description
</td>
<td>
@item.Sku
</td>
<td>
@item.DeliveryDate.ToShortDateString()
</td>
<td>
@item.Quantity
</td>
@if (IncludePrice)
{
<td class="text-end">
@item.Price
</td>
<td class="text-end">
@(item.Discount)%
</td>
}
</tr>
}
</tbody>
</table>
@code {
[Parameter] public string CompanyName { get; set; } = "";
[Parameter] public string HeaderGenerated { get; set; } = "";
[Parameter] public List<InventoryItem> Items { get; set; } = new();
[Parameter] public bool IncludePrice { get; set; }
}

View file

@ -132,7 +132,7 @@ public class CabinetDrawerService : ICabinetDrawerService
if (drawer == null) force = true; if (drawer == null) force = true;
if (!force) return drawer ?? new StatisticDrawer(); if (!force) return drawer ?? new StatisticDrawer();
var result = await _historyRepo.GetProductInvoiceLines(companyId); var result = await _historyRepo.GetProductInvoiceLines(companyId);
var content = result.Select(x => new HistoryFilter var content = result.Select(x => new InventoryItem
{ {
DeliveryDate = DateTime.Parse(x.DeliveryDate), DeliveryDate = DateTime.Parse(x.DeliveryDate),
Description = x.Description, Description = x.Description,

View file

@ -0,0 +1,9 @@
namespace Wonky.Client.Models;
public class DkStatisticPrint
{
public string DeliveryDate { get; set; } = "";
public string Description { get; set; } = "";
public string Sku { get; set; } = "";
public int Quantity { get; set; }
}

View file

@ -1,6 +1,6 @@
namespace Wonky.Client.Models; namespace Wonky.Client.Models;
public class HistoryFilter public class InventoryItem
{ {
public DateTime DeliveryDate { get; set; } public DateTime DeliveryDate { get; set; }
public string Description { get; set; } = ""; public string Description { get; set; } = "";

View file

@ -6,5 +6,5 @@ public class StatisticDrawer
{ {
public const string Label = "Statistic"; public const string Label = "Statistic";
public DateTime LastDateModified { get; set; } public DateTime LastDateModified { get; set; }
public List<HistoryFilter> Content { get; set; } = new(); public List<InventoryItem> Content { get; set; } = new();
} }

View file

@ -20,80 +20,27 @@
<PageTitle>Produktkøb @_company.Name</PageTitle> <PageTitle>Produktkøb @_company.Name</PageTitle>
<div class="row d-print-none pb-3 mb-3 border-bottom"> <div class="row d-print-none pb-3 mb-3 border-bottom">
<div class="col-sm-5"></div> <div class="col-sm-3"></div>
<div class="col-sm-2 text-end"> <div class="col-sm-3 text-end">
<select class="form-select bg-info text-bg-info me-3" @bind-value="Months" @bind-value:event="oninput" @onchange="@OnSelectChanged"> <select class="form-select bg-info text-bg-info me-3" @bind-value="_months" @bind-value:event="oninput" @onchange="@OnSelectChanged">
<option value="6">Vis 6 måneder</option> <option value="6">Vis 6 måneder</option>
<option value="12">Vis 12 måneder</option> <option value="12">Vis 12 måneder</option>
<option value="18">Vis 18 måneder</option> <option value="18">Vis 18 måneder</option>
<option value="24">Vis 24 måneder</option> <option value="24">Vis 24 måneder</option>
</select> </select>
</div> </div>
<div class="col-sm-5 text-end"> <div class="col-sm-6 text-end">
<button type="button" class="btn btn-primary me-3" onclick="window.print();"><i class="bi-printer"></i> Udskriv (24 md.)</button> <button type="button" class="btn btn-warning me-3 @(_includePrice ? "active" : "")"
data-bs-toggle="button" aria-pressed="@_includePrice" @onclick="@TogglePrice">
@(_includePrice ? "Uden priser" : "Med priser")
</button>
<button type="button" class="btn btn-primary me-3" @onclick="@PrintReport"><i class="bi-printer"></i> Vis Udskrift</button>
<a class="btn btn-primary" href="/advisor/customers/@CompanyId"><i class="bi-chevron-left"></i> Tilbage</a> <a class="btn btn-primary" href="/advisor/customers/@CompanyId"><i class="bi-chevron-left"></i> Tilbage</a>
</div> </div>
</div> </div>
@if (DisplayList.Any()) <div class="container">
{ <AdvisorCustomerStatisticComponent Items="_displayList" CompanyName="@_company.Name"
<table class="table table-striped d-print-table"> HeaderGenerated="@_headerGenerated" IncludePrice="_includePrice" />
<thead> </div>
<tr>
<th class="text-center" colspan="6">
<h2>Produktkøb @_company.Name</h2>
<p>Dannet @DateTime.Today.ToLongDateString() (@Months md.)</p>
</th>
</tr>
<tr class="rounded-2 border border-1">
<th scope="col">
Beskrivelse
</th>
<th scope="col">
Vare Nr.
</th>
<th scope="col">
Dato
</th>
<th scope="col" class="text-end">
Antal
</th>
<th scope="col" class="text-end">
Pris
</th>
<th scope="col" class="text-end">
Afslag
</th>
</tr>
</thead>
<tbody>
@foreach (var item in DisplayList)
{
<tr class="align-content-center">
<td>
@item.Description
</td>
<td>
@item.Sku
</td>
<td>
@item.DeliveryDate.ToShortDateString()
</td>
<td class="text-end">
@item.Quantity
</td>
<td class="text-end">
@item.Price
</td>
<td class="text-end">
@(item.Discount)%
</td>
</tr>
}
</tbody>
</table>
}
else
{
<div>Ingen data</div>
}

View file

@ -2,7 +2,6 @@ using Microsoft.AspNetCore.Components;
using Wonky.Client.Local.Services; using Wonky.Client.Local.Services;
using Wonky.Client.Models; using Wonky.Client.Models;
using Wonky.Entity.DTO; using Wonky.Entity.DTO;
using Wonky.Entity.Views;
#pragma warning disable CS8618 #pragma warning disable CS8618
@ -10,45 +9,83 @@ namespace Wonky.Client.Pages;
public partial class AdvisorCustomerStatisticPage public partial class AdvisorCustomerStatisticPage
{ {
// ##############################################################
[Inject] public ICabinetDrawerService DrawerService { get; set; } [Inject] public ICabinetDrawerService DrawerService { get; set; }
[Inject] public ILogger<AdvisorCustomerStatisticPage> Logger { get; set; }
[Inject] public NavigationManager Navigator { get; set; }
// ##############################################################
[Parameter] public string CompanyId { get; set; } = ""; [Parameter] public string CompanyId { get; set; } = "";
// ##############################################################
private InfoDrawer _infoDrawer = new(); private InfoDrawer _infoDrawer = new();
private StatisticDrawer _statisticDrawer = new(); private StatisticDrawer _statisticDrawer = new();
private List<HistoryFilter> DisplayList { get; set; } = new();
private CompanyDto _company = new(); private CompanyDto _company = new();
private int Months { get; set; } private List<InventoryItem> _displayList = new();
private string _headerGenerated = "";
private string _baseUri = "";
private int _months = 24;
private bool _includePrice = true;
protected override async Task OnInitializedAsync() protected override async Task OnInitializedAsync()
{ {
_infoDrawer = await DrawerService.GetInfoDrawerAsync(CompanyId); _infoDrawer = await DrawerService.GetInfoDrawerAsync(CompanyId);
_statisticDrawer = await DrawerService.GetStatisticDrawerAsync(CompanyId); _statisticDrawer = await DrawerService.GetStatisticDrawerAsync(CompanyId);
_company = _infoDrawer.Content; _company = _infoDrawer.Content;
if (Months == 0) _baseUri = Navigator.Uri.Split("?")[0];
{ _displayList = GenerateDisplayList(_months, _includePrice);
Months = 24; UpdateDisplayData(_months, _includePrice);
}
FilterDisplayList(Months);
} }
private void FilterDisplayList(int months)
private void PrintReport()
{ {
if (_statisticDrawer.Content.Any()) Navigator.NavigateTo($"{_baseUri}/print/{_months}/{_includePrice}");
}
private void TogglePrice()
{ {
DisplayList = _statisticDrawer.Content _includePrice = !_includePrice;
.Where(x => x.DeliveryDate > DateTime.Now.AddMonths(-months)) UpdateDisplayData(_months, _includePrice);
.OrderBy(x => x.Description).ThenByDescending(x => x.DeliveryDate)
.ToList();
}
} }
private void OnSelectChanged(ChangeEventArgs e) private void OnSelectChanged(ChangeEventArgs e)
{ {
var val = e.Value?.ToString(); var val = e.Value?.ToString();
var x = Convert.ToInt32(val); var months = Convert.ToInt32(val);
if (x > 24) x = 24; if (months > 24) months = 24;
FilterDisplayList(x); _months = months;
UpdateDisplayData(_months, _includePrice);
} }
private void UpdateDisplayData(int months, bool includePrice)
{
_headerGenerated = $"Dannet {DateTime.Today.ToLongDateString()} ({months} md.)";
_displayList = GenerateDisplayList(months, includePrice);
}
private List<InventoryItem> GenerateDisplayList(int months, bool includePrice)
{
return includePrice
? _statisticDrawer.Content
.Where(x => x.DeliveryDate > DateTime.Now.AddMonths(-months))
.OrderBy(x => x.Description).ThenByDescending(x => x.DeliveryDate)
.ToList()
: _statisticDrawer.Content
.Where(x => x.DeliveryDate > DateTime.Now.AddMonths(-months))
.OrderBy(x => x.Description).ThenByDescending(x => x.DeliveryDate)
.Select(x =>
new InventoryItem
{
DeliveryDate = x.DeliveryDate,
Description = x.Description,
Quantity = x.Quantity,
Sku = x.Sku
}).ToList();
}
} }

View file

@ -0,0 +1,36 @@
@* Copyright (C) 2022 FCS Frede's Computer Services.
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU Affero General Public License as
// published by the Free Software Foundation, either version 3 of the
// License, or (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Affero General Public License for more details.
//
// You should have received a copy of the GNU Affero General Public License
// along with this program. If not, see [https://www.gnu.org/licenses/agpl-3.0.en.html]
*@
@using Wonky.Client.Components
@using Microsoft.AspNetCore.Authorization
@attribute [Authorize(Roles = "Advisor")]
@page "/advisor/customers/{CompanyId}/statistic/print/{Months}/{IncludePrice}"
<PageTitle>Produktkøb @_company.Name</PageTitle>
<div class="row d-print-none">
<div class="col text-end">
<button type="button" class="btn btn-primary me-3" @onclick="@DoPrint"><i class="bi-printer"></i> Print</button>
<button type="button" class="btn btn-secondary me-3" onclick="history.back(1)"><i class="bi-arrow-left"></i> Tilbage</button>
</div>
</div>
<div class="row">
<div class="col">
<AdvisorCustomerStatisticComponent Items="_displayList" CompanyName="@_company.Name"
HeaderGenerated="@_headerGenerated" IncludePrice="_includePrice" />
</div>
</div>

View file

@ -0,0 +1,91 @@
using System.Text.Json;
using Microsoft.AspNetCore.Components;
using Microsoft.AspNetCore.Components.Routing;
using Microsoft.JSInterop;
using Wonky.Client.Helpers;
using Wonky.Client.Local.Services;
using Wonky.Client.Models;
using Wonky.Entity.DTO;
#pragma warning disable CS8618
namespace Wonky.Client.Pages;
public partial class AdvisorCustomerStatisticPrintPage
{
// ##############################################################
[Inject] public ICabinetDrawerService DrawerService { get; set; }
[Inject] public ILogger<AdvisorCustomerStatisticPrintPage> Logger { get; set; }
[Inject] public NavigationManager Navigator { get; set; }
[Inject] public IJSRuntime JsRuntime { get; set; }
// ##############################################################
[Parameter] public string CompanyId { get; set; } = "";
[Parameter] public string Months { get; set; }
[Parameter] public string IncludePrice { get; set; }
// ##############################################################
private IJSObjectReference JsModule { get; set; }
private InfoDrawer _infoDrawer = new();
private StatisticDrawer _statisticDrawer = new();
private CompanyDto _company = new();
private List<InventoryItem> _displayList = new();
private string _headerGenerated = "";
private int _months;
private bool _includePrice;
protected override async Task OnInitializedAsync()
{
Logger.LogDebug(Months);
Logger.LogDebug(IncludePrice);
_infoDrawer = await DrawerService.GetInfoDrawerAsync(CompanyId);
_company = _infoDrawer.Content;
_statisticDrawer = await DrawerService.GetStatisticDrawerAsync(CompanyId);
_includePrice = Convert.ToBoolean(IncludePrice);
_months = Convert.ToInt32(Months);
_displayList = GenerateDisplayList(_months, _includePrice);
Logger.LogDebug("{}", JsonSerializer.Serialize(_displayList));
_headerGenerated = $"Dannet {DateTime.Today.ToLongDateString()} ({Months} md.)";
}
protected override async Task OnAfterRenderAsync(bool firstRender)
{
if (firstRender)
{
JsModule = await JsRuntime
.InvokeAsync<IJSObjectReference>("import", "/scripts/print-invoke.js");
}
}
private async Task DoPrint()
{
await JsModule.InvokeVoidAsync("printInvoke");
}
private List<InventoryItem> GenerateDisplayList(int months, bool includePrice)
{
return includePrice
? _statisticDrawer.Content
.Where(x => x.DeliveryDate > DateTime.Now.AddMonths(-months))
.OrderBy(x => x.Description).ThenByDescending(x => x.DeliveryDate)
.ToList()
: _statisticDrawer.Content
.Where(x => x.DeliveryDate > DateTime.Now.AddMonths(-months))
.OrderBy(x => x.Description).ThenByDescending(x => x.DeliveryDate)
.Select(x =>
new InventoryItem
{
DeliveryDate = x.DeliveryDate,
Description = x.Description,
Quantity = x.Quantity,
Sku = x.Sku
}).ToList();
}
}

View file

@ -1,9 +1,9 @@
{ {
"appInfo": { "appInfo": {
"name": "Wonky Online", "name": "Wonky Online",
"version": "224.0", "version": "227.0",
"rc": true, "rc": true,
"sandBox": false, "sandBox": true,
"image": "grumpy-coder.png", "image": "grumpy-coder.png",
"sdk": "dotnet 7.0" "sdk": "dotnet 7.0"
}, },