3 Commits

Author SHA1 Message Date
626408412b Primo sviluppo sincronizzazione e migliorie ui 2025-05-19 16:47:21 +02:00
6f08ba87be Aggiunta visualizzazione mensile in agenda 2025-05-13 09:43:00 +02:00
bc3809b61c Pagina profilo e modiche al theme 2025-05-12 10:39:51 +02:00
77 changed files with 2625 additions and 109 deletions

View File

@@ -1,6 +1,6 @@
using Template.Shared.Interfaces;
using Template.Shared.Core.Interface;
namespace Template.Maui.Services;
namespace Template.Maui.Core.Services;
public class FormFactor : IFormFactor
{

View File

@@ -0,0 +1,76 @@
using System.Linq.Expressions;
using SQLite;
using Template.Shared.Core.Entity;
namespace Template.Maui.Core.Services;
public class LocalDbService
{
private const string DB_NAME = "task_db.db3";
private readonly SQLiteAsyncConnection _connection;
public LocalDbService()
{
_connection = new SQLiteAsyncConnection(Path.Combine(FileSystem.AppDataDirectory, DB_NAME));
//Creazione tabelle database
_connection.CreateTableAsync<AnagClie>();
_connection.CreateTableAsync<JtbComt>();
_connection.CreateTableAsync<PtbPros>();
_connection.CreateTableAsync<PtbProsRif>();
_connection.CreateTableAsync<StbActivity>();
_connection.CreateTableAsync<VtbCliePersRif>();
_connection.CreateTableAsync<VtbDest>();
}
public async Task ResetDb()
{
try
{
await _connection.ExecuteAsync("DROP TABLE IF EXISTS anag_clie;");
await _connection.ExecuteAsync("DROP TABLE IF EXISTS jtb_comt;");
await _connection.ExecuteAsync("DROP TABLE IF EXISTS ptb_pros;");
await _connection.ExecuteAsync("DROP TABLE IF EXISTS ptb_pros_rif;");
await _connection.ExecuteAsync("DROP TABLE IF EXISTS stb_activity;");
await _connection.ExecuteAsync("DROP TABLE IF EXISTS vtb_clie_pers_rif;");
await _connection.ExecuteAsync("DROP TABLE IF EXISTS vtb_dest;");
await _connection.CreateTableAsync<AnagClie>();
await _connection.CreateTableAsync<JtbComt>();
await _connection.CreateTableAsync<PtbPros>();
await _connection.CreateTableAsync<PtbProsRif>();
await _connection.CreateTableAsync<StbActivity>();
await _connection.CreateTableAsync<VtbCliePersRif>();
await _connection.CreateTableAsync<VtbDest>();
Console.WriteLine("Database resettato con successo.");
}
catch (Exception ex)
{
Console.WriteLine($"Errore durante il reset del database: {ex.Message}");
throw;
}
}
public Task Insert<T>(List<T> entityList) =>
_connection.InsertAllAsync(entityList, typeof(T));
public async Task InsertOrUpdate<T>(List<T> entityList)
{
foreach (var entity in entityList)
{
var result = await _connection.UpdateAsync(entity);
if (result == 0)
{
await _connection.InsertAsync(entity);
}
}
}
public Task<List<T>> Get<T>(Expression<Func<T, bool>>? whereCond = null) where T : new() =>
whereCond is null
? _connection.Table<T>().ToListAsync()
: _connection.Table<T>().Where(whereCond).ToListAsync();
public List<T> Get<T>(string sql) where T : new() => _connection.QueryAsync<T>(sql).Result;
}

View File

@@ -0,0 +1,72 @@
using AutoMapper;
using System.Linq.Expressions;
using Template.Shared.Core.Dto;
using Template.Shared.Core.Entity;
using Template.Shared.Core.Helpers.Enum;
using Template.Shared.Core.Interface;
namespace Template.Maui.Core.Services;
public class ManageDataService(LocalDbService localDb, IMapper mapper) : IManageDataService
{
public Task<List<AnagClie>> GetAnagClie(Expression<Func<AnagClie, bool>>? whereCond = null) =>
localDb.Get(whereCond);
public Task<List<JtbComt>> GetJtbComt(Expression<Func<JtbComt, bool>>? whereCond = null) =>
localDb.Get(whereCond);
public Task<List<PtbPros>> GetPtbPros(Expression<Func<PtbPros, bool>>? whereCond = null) =>
localDb.Get(whereCond);
public Task<List<PtbProsRif>> GetPtbProsRif(Expression<Func<PtbProsRif, bool>>? whereCond = null) =>
localDb.Get(whereCond);
public Task<List<StbActivity>> GetStbActivity(Expression<Func<StbActivity, bool>>? whereCond = null) =>
localDb.Get(whereCond);
public Task<List<VtbCliePersRif>> GetVtbCliePersRif(Expression<Func<VtbCliePersRif, bool>>? whereCond = null) =>
localDb.Get(whereCond);
public Task<List<VtbDest>> GetVtbDest(Expression<Func<VtbDest, bool>>? whereCond = null) =>
localDb.Get(whereCond);
public async Task<List<ActivityDTO>> GetActivity(Expression<Func<StbActivity, bool>>? whereCond = null)
{
var activities = await localDb.Get(whereCond);
var codJcomList = activities
.Select(x => x.CodJcom)
.Where(x => !string.IsNullOrEmpty(x))
.Distinct()
.ToList();
var jtbComtList = await localDb.Get<JtbComt>(x => codJcomList.Contains(x.CodJcom));
var commesseDict = jtbComtList.ToDictionary(x => x.CodJcom, x => x.Descrizione);
var returnDto = activities
.Select(activity =>
{
var dto = mapper.Map<ActivityDTO>(activity);
if (activity.CodJcom != null)
{
dto.Category = ActivityCategoryEnum.Commessa;
}
else
{
dto.Category = activity.CodAnag != null ? ActivityCategoryEnum.Interna : ActivityCategoryEnum.Memo;
}
dto.Commessa = activity.CodJcom != null && commesseDict.TryGetValue(activity.CodJcom, out var descr)
? descr
: null;
return dto;
})
.ToList();
return returnDto;
}
public async Task ClearDb() =>
await localDb.ResetDb();
}

View File

@@ -0,0 +1,12 @@
using Template.Shared.Core.Interface;
namespace Template.Maui.Core.Services;
public class NetworkService : INetworkService
{
public bool IsNetworkAvailable()
{
return Connectivity.Current.NetworkAccess == NetworkAccess.Internet;
}
}

View File

@@ -0,0 +1,69 @@
using Template.Shared.Core.Interface;
namespace Template.Maui.Core.Services;
public class SyncDbService(IIntegryApiService integryApiService, LocalDbService localDb) : ISyncDbService
{
public async Task GetAndSaveActivity(string? dateFilter)
{
var allActivity = await integryApiService.GetActivity(dateFilter);
if (allActivity is not null)
if (dateFilter is null)
await localDb.Insert(allActivity);
else
await localDb.InsertOrUpdate(allActivity);
}
public async Task GetAndSaveCommesse(string? dateFilter)
{
var allCommesse = await integryApiService.GetAllCommesse(dateFilter);
if (allCommesse is not null)
if (dateFilter is null)
await localDb.Insert(allCommesse);
else
await localDb.InsertOrUpdate(allCommesse);
}
public async Task GetAndSaveProspect(string? dateFilter)
{
var taskSyncResponseDto = await integryApiService.GetProspect(dateFilter);
if (taskSyncResponseDto.PtbPros is not null)
if (dateFilter is null)
await localDb.Insert(taskSyncResponseDto.PtbPros);
else
await localDb.InsertOrUpdate(taskSyncResponseDto.PtbPros);
if (taskSyncResponseDto.PtbProsRif is not null)
if (dateFilter is null)
await localDb.Insert(taskSyncResponseDto.PtbProsRif);
else
await localDb.InsertOrUpdate(taskSyncResponseDto.PtbProsRif);
}
public async Task GetAndSaveClienti(string? dateFilter)
{
var taskSyncResponseDto = await integryApiService.GetAnagClie(dateFilter);
if (taskSyncResponseDto.AnagClie is not null)
if (dateFilter is null)
await localDb.Insert(taskSyncResponseDto.AnagClie);
else
await localDb.InsertOrUpdate(taskSyncResponseDto.AnagClie);
if (taskSyncResponseDto.VtbDest is not null)
if (dateFilter is null)
await localDb.Insert(taskSyncResponseDto.VtbDest);
else
await localDb.InsertOrUpdate(taskSyncResponseDto.VtbDest);
if (taskSyncResponseDto.VtbCliePersRif is not null)
if (dateFilter is null)
await localDb.Insert(taskSyncResponseDto.VtbCliePersRif);
else
await localDb.InsertOrUpdate(taskSyncResponseDto.VtbCliePersRif);
}
}

View File

@@ -1,3 +1,6 @@
using CommunityToolkit.Mvvm.Messaging;
using Template.Shared.Core.Messages;
namespace Template.Maui
{
public partial class MainPage : ContentPage
@@ -6,5 +9,12 @@ namespace Template.Maui
{
InitializeComponent();
}
protected override bool OnBackButtonPressed()
{
WeakReferenceMessenger.Default.Send(new HardwareBackMessage("back"));
return true;
}
}
}

View File

@@ -2,10 +2,12 @@ using IntegryApiClient.MAUI;
using Microsoft.AspNetCore.Components.Authorization;
using Microsoft.Extensions.Logging;
using MudBlazor.Services;
using Template.Maui.Services;
using Template.Maui.Core.Services;
using Template.Shared;
using Template.Shared.Core.Helpers;
using Template.Shared.Core.Interface;
using Template.Shared.Core.Messages;
using Template.Shared.Core.Services;
using Template.Shared.Interfaces;
namespace Template.Maui
{
@@ -29,17 +31,26 @@ namespace Template.Maui
builder.Services.AddMauiBlazorWebView();
builder.Services.AddMudServices();
builder.Services.AddAutoMapper(typeof(MappingProfile));
builder.Services.AddAuthorizationCore();
builder.Services.AddScoped<AppAuthenticationStateProvider>();
builder.Services.AddScoped<AuthenticationStateProvider>(provider =>
provider.GetRequiredService<AppAuthenticationStateProvider>());
builder.Services.AddScoped<INetworkService, NetworkService>();
builder.Services.AddScoped<IIntegryApiService, IntegryApiService>();
builder.Services.AddScoped<ISyncDbService, SyncDbService>();
builder.Services.AddScoped<IManageDataService, ManageDataService>();
builder.Services.AddScoped<BackNavigationService>();
#if DEBUG
builder.Services.AddBlazorWebViewDeveloperTools();
builder.Logging.AddDebug();
#endif
builder.Services.AddSingleton<IFormFactor, FormFactor>();
builder.Services.AddSingleton<LocalDbService>();
return builder.Build();
}

View File

@@ -1,6 +1,6 @@
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
<application android:allowBackup="true" android:icon="@mipmap/appicon" android:roundIcon="@mipmap/appicon_round" android:supportsRtl="true"></application>
<application android:allowBackup="true" android:icon="@mipmap/appicon" android:usesCleartextTraffic="true" android:supportsRtl="true"></application>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.INTERNET" />
</manifest>

View File

@@ -1,10 +1,12 @@
using Android.App;
using Android.Content.PM;
using Android.OS;
namespace Template.Maui
{
[Activity(Theme = "@style/Maui.SplashTheme", MainLauncher = true, ConfigurationChanges = ConfigChanges.ScreenSize | ConfigChanges.Orientation | ConfigChanges.UiMode | ConfigChanges.ScreenLayout | ConfigChanges.SmallestScreenSize | ConfigChanges.Density)]
[Activity(Theme = "@style/Maui.SplashTheme",
MainLauncher = true,
ConfigurationChanges = ConfigChanges.ScreenSize | ConfigChanges.Orientation | ConfigChanges.UiMode |
ConfigChanges.ScreenLayout | ConfigChanges.SmallestScreenSize | ConfigChanges.Density)]
public class MainActivity : MauiAppCompatActivity
{
}

View File

@@ -28,5 +28,12 @@
</array>
<key>XSAppIconAssets</key>
<string>Assets.xcassets/appicon.appiconset</string>
<key>NSLocalNetworkUsageDescription</key>
<string>This app requires access to the local network to communicate with the server.</string>
<key>NSAppTransportSecurity</key>
<dict>
<key>NSAllowsArbitraryLoads</key>
<true/>
</dict>
</dict>
</plist>

View File

@@ -77,7 +77,7 @@
</PropertyGroup>
<PropertyGroup Condition="'$(TargetFramework)'=='net9.0-ios'">
<CodesignKey>Apple Development: Massimo Fausto Morelli (6C2CUM53BT)</CodesignKey>
<CodesignKey>Apple Development: Created via API (5B7B69P4JY)</CodesignKey>
<CodesignProvision>VS: WildCard Development</CodesignProvision>
</PropertyGroup>
@@ -111,12 +111,14 @@
<ItemGroup>
<PackageReference Include="CommunityToolkit.Maui" Version="11.2.0" />
<PackageReference Include="CommunityToolkit.Mvvm" Version="8.4.0" />
<PackageReference Include="IntegryApiClient.MAUI" Version="1.1.3" />
<PackageReference Include="Microsoft.Extensions.Logging" Version="9.0.4" />
<PackageReference Include="Microsoft.Maui.Controls" Version="9.0.60" />
<PackageReference Include="Microsoft.Maui.Controls.Compatibility" Version="9.0.60" />
<PackageReference Include="Microsoft.AspNetCore.Components.WebView.Maui" Version="9.0.60" />
<PackageReference Include="Microsoft.Extensions.Logging.Debug" Version="9.0.4" />
<PackageReference Include="sqlite-net-pcl" Version="1.9.172" />
</ItemGroup>
<ItemGroup>

View File

@@ -10,8 +10,7 @@
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=Nunito:ital,wght@0,200..1000;1,200..1000&display=swap" rel="stylesheet">
<link href="_content/Template.Shared/css/bootstrap/bootstrap.min.css" rel="stylesheet" integrity="sha384-T3c6CoIi6uLrA9TneNEoa7RxnatzjcDSCmG1MXxSR1GAsXEV/Dwwykc2MPK8M2HN" crossorigin="anonymous">
<link href="_content/Template.Shared/css/bootstrap/bootstrap.min.css" rel="stylesheet">
<link href="_content/Template.Shared/css/bootstrap/bootstrap-icons.min.css" rel="stylesheet" />
<link href="_content/MudBlazor/MudBlazor.min.css" rel="stylesheet" />

View File

@@ -1,10 +1,43 @@
@inject IJSRuntime JS
<div class="header">
<div class="header-content">
<div class="header-content @(Back ? "with-back" : "no-back")">
@if (Back)
{
<div class="left-section">
<MudButton StartIcon="@Icons.Material.Outlined.ArrowBackIosNew"
OnClick="GoBack"
Color="Color.Info"
Style="text-transform: none"
Variant="Variant.Text">@BackTo</MudButton>
</div>
}
<h3 class="page-title">@Title</h3>
<MudIconButton Icon="@Icons.Material.Filled.FilterAlt" Color="Color.Dark" />
<div class="right-section">
@if (ShowFilter)
{
<MudIconButton Icon="@Icons.Material.Outlined.FilterAlt" Color="Color.Dark" />
}
@if (ShowNotifications)
{
<MudIconButton Icon="@Icons.Material.Filled.Notifications" Color="Color.Dark" />
}
</div>
</div>
</div>
@code{
[Parameter] public string? Title { get; set; }
[Parameter] public bool ShowFilter { get; set; }
[Parameter] public bool ShowNotifications { get; set; } = true;
[Parameter] public bool Back { get; set; }
[Parameter] public string BackTo { get; set; } = "";
private async Task GoBack()
{
await JS.InvokeVoidAsync("goBack");
}
}

View File

@@ -1,7 +1,29 @@
.header-content {
line-height: normal;
display: flex;
justify-content: space-between;
color: var(--lighter-color);
align-items: center;
padding-top: .5rem;
position: relative;
}
.header-content.with-back { margin: .6rem 0 0 0; }
.header-content.with-back .page-title {
position: absolute;
left: 50%;
transform: translateX(-50%);
margin: 0;
font-size: larger;
}
.left-section ::deep button {
font-size: 1rem;
}
.left-section ::deep .mud-button-icon-start {
margin-right: 3px !important;
}
.header-content.no-back .page-title {
margin: 0;
}

View File

@@ -1,6 +1,9 @@
@inherits LayoutComponentBase
@using Template.Shared.Core.Messages
@inherits LayoutComponentBase
@inject IJSRuntime JS
@inject BackNavigationService BackService
<MudThemeProvider />
<MudThemeProvider Theme="_currentTheme" />
<MudPopoverProvider />
<MudDialogProvider />
<MudSnackbarProvider />
@@ -15,3 +18,24 @@
</main>
</div>
@code {
private readonly MudTheme _currentTheme = new()
{
PaletteLight = new PaletteLight()
{
Primary = "#ABA9BF",
Secondary = "#BEB7DF",
Tertiary = "#B2FDAD"
}
};
protected override void OnInitialized()
{
BackService.OnHardwareBack += async () =>
{
await JS.InvokeVoidAsync("goBack");
};
}
}

View File

@@ -7,7 +7,7 @@
<li class="nav-item">
<NavLink class="nav-link" href="Users" Match="NavLinkMatch.All">
<div class="d-flex flex-column">
<i class="ri-group-fill"></i>
<i class="ri-group-line"></i>
<span>Contatti</span>
</div>
</NavLink>
@@ -15,7 +15,7 @@
<li class="nav-item">
<NavLink class="nav-link" href="Calendar" Match="NavLinkMatch.All">
<div class="d-flex flex-column">
<i class="ri-calendar-todo-fill"></i>
<i class="ri-calendar-todo-line"></i>
<span>Agenda</span>
</div>
</NavLink>
@@ -23,7 +23,7 @@
<li class="nav-item">
<NavLink class="nav-link" href="PersonalInfo" Match="NavLinkMatch.All">
<div class="d-flex flex-column">
<i class="ri-user-fill"></i>
<i class="ri-user-line"></i>
<span>Profilo</span>
</div>
</NavLink>

View File

@@ -1,8 +1,10 @@
.navbar {
background: var(--mud-palette-background-gray);
background: var(--mud-palette-surface);
position: fixed;
bottom: 0;
width: 100%;
z-index: 1001;
border-top: 1px solid var(--card-border-color);
}
.navbar-expand { padding: 0 !important; }
@@ -12,7 +14,7 @@
.nav-item ::deep a {
display: flex;
align-items: center;
line-height: 1.4;
line-height: 1.2;
justify-content: center;
}
@@ -22,7 +24,7 @@
min-width: 60px;
}
.nav-item ::deep a.active > div { color: var(--mud-palette-primary); }
.nav-item ::deep a.active > div { color: var(--mud-palette-secondary-darken); }
.nav-item ::deep a.active > div > i {
/*background-color: color-mix(in srgb, var(--mud-palette-primary) 20%, transparent);*/

View File

@@ -0,0 +1,20 @@
@if (Elements is not null)
{
<div class="container-loader">
<span>Download risorse in corso</span>
<div>
@foreach (var element in Elements)
{
<div class="progress-content">
<span>@element.Key</span>
<MudProgressLinear Indeterminate="@(!element.Value)" Value="100" Rounded="true" Color="@(element.Value ? Color.Tertiary : Color.Secondary)" Size="Size.Large" />
</div>
}
</div>
</div>
}
@code
{
[Parameter] public Dictionary<string, bool>? Elements { get; set; }
}

View File

@@ -0,0 +1,27 @@
.container-loader {
display: flex;
height: 95vh;
flex-direction: column;
justify-content: center;
padding: 0 1rem;
align-items: center;
gap: 5vh;
}
.container-loader > div {
width: 100%;
}
.container-loader > span {
font-weight: 900;
font-size: large;
color: var(--mud-palette-primary);
}
.progress-content > span {
font-weight: 700;
}
.progress-content:nth-last-child(2) {
margin: 10px 0;
}

View File

@@ -1,39 +1,67 @@
@page "/Calendar"
@attribute [Authorize]
@using Template.Shared.Components.Layout
@using Template.Shared.Components.SingleElements.Calendar
<HeaderLayout Title="Agenda" />
<HeaderLayout Title="Agenda" ShowFilter="true"/>
<div class="content">
<MudButtonGroup Size="Size.Small" Color="Color.Surface" OverrideStyles="true" Variant="Variant.Filled">
<MudButton>Giorno</MudButton>
<MudButton Disabled="true">Settimana</MudButton>
<MudButton Disabled="true">Mese</MudButton>
<MudButtonGroup Size="Size.Small" Class="custom-mudButtonGroup" Color="Color.Surface" OverrideStyles="true" Variant="Variant.Outlined" DropShadow="true">
<MudButton StartIcon="@Icons.Material.Filled.ViewStream" Class="@(FilterByDay ? "custom-button-active" : "")" OnClick="SelectDay">Giorno</MudButton>
<MudButton StartIcon="@Icons.Material.Filled.CalendarViewDay" Class="@(FilterByWeek ? "custom-button-active" : "")" OnClick="SelectWeek">Settimana</MudButton>
<MudButton StartIcon="@Icons.Material.Filled.CalendarViewMonth" Class="@(FilterByMonth ? "custom-button-active" : "")" OnClick="SelectMonth">Mese</MudButton>
</MudButtonGroup>
<div class="activity-filter">
<div class="date-controller">
<MudIconButton Icon="@Icons.Material.Filled.ChevronLeft" @onclick="() => DateFilter = DateFilter.AddDays(-1)" Color="Color.Surface"/>
<MudIconButton Icon="@Icons.Material.Filled.ChevronLeft" @onclick="() => ChangeDate(-1)" Color="Color.Surface"/>
<MudButton Variant="Variant.Text" Color="Color.Surface" OnClick="OpenCalendar">
@if (FilterByDay)
{
@($"{DateFilter:M}")
}
else if (FilterByWeek)
{
@($"{(DateRangeFilter.Start!.Value.Month == DateRangeFilter.End!.Value.Month ? DateRangeFilter.Start!.Value.Day : DateRangeFilter.Start!.Value.ToString("M"))} - {DateRangeFilter.End!.Value:M}")
}
else if (FilterByMonth)
{
@($"{DateFilter:Y}")
}
</MudButton>
<MudIconButton Icon="@Icons.Material.Filled.ChevronRight" @onclick="() => DateFilter = DateFilter.AddDays(1)" Color="Color.Surface" />
<MudIconButton Icon="@Icons.Material.Filled.ChevronRight" @onclick="() => ChangeDate(1)" Color="Color.Surface"/>
</div>
<MudOverlay @bind-Visible="_isVisible" DarkBackground="true" AutoClose="true">
<MudDatePicker PickerVariant="PickerVariant.Static" Date="DateFilter" />
<MudDatePicker @bind-Date:after="CloseDatePicker" @bind-Date="DateFilter" PickerVariant="PickerVariant.Static">
<PickerActions>
@if (DateFilter != DateTime.Today)
{
<MudButton Class="mr-auto align-self-start" OnClick="() => DateFilter = DateTime.Today">Oggi</MudButton>
}
</PickerActions>
</MudDatePicker>
</MudOverlay>
</div>
<div class="card-container">
<ActivityCard Type="memo" />
<ActivityCard Type="commessa"/>
<ActivityCard Type="interna"/>
@if (FilterByDay)
{
<DayView @bind-Date="DateFilter"/>
}
else if (FilterByWeek)
{
<WeekView @bind-Date="DateRangeFilter" />
}
else if (FilterByMonth)
{
<MonthView @bind-Date="DateTimeForMonthView"/>
}
</div>
<MudMenu PopoverClass="custom_popover" Class="custom-mudfab" AnchorOrigin="Origin.TopLeft" TransformOrigin="Origin.BottomRight">
<ActivatorContent>
<MudFab Color="Color.Primary" Size="Size.Small" StartIcon="@Icons.Material.Filled.Add" />
<MudFab Color="Color.Primary" Size="Size.Small" StartIcon="@Icons.Material.Filled.Add"/>
</ActivatorContent>
<ChildContent>
<MudMenuItem>Nuovo contatto</MudMenuItem>
@@ -43,14 +71,110 @@
</div>
@code {
private DateTime DateFilter { get; set; } = DateTime.Today;
private bool FilterByDay { get; set; } = true;
private bool FilterByWeek { get; set; }
private bool FilterByMonth { get; set; }
private DateTime? DateFilter { get; set; } = DateTime.Today;
private DateRange DateRangeFilter { get; set; } = new();
private DateTime DateTimeForMonthView { get; set; }
private bool _isVisible;
protected override void OnInitialized()
{
CalcDateRange();
}
public void OpenCalendar()
{
_isVisible = true;
StateHasChanged();
}
private void SelectDay()
{
ResetFilterCalendar();
FilterByDay = !FilterByDay;
StateHasChanged();
}
private void SelectWeek()
{
ResetFilterCalendar();
FilterByWeek = !FilterByWeek;
CalcDateRange();
StateHasChanged();
}
private void SelectMonth()
{
ResetFilterCalendar();
FilterByMonth = !FilterByMonth;
DateTimeForMonthView = new DateTime(DateFilter!.Value.Year, DateFilter!.Value.Month, 1);
StateHasChanged();
}
private void ResetFilterCalendar(bool forceSelectDay = false)
{
FilterByDay = false;
FilterByWeek = false;
FilterByMonth = false;
}
private void ChangeDate(int value)
{
var date = DateFilter!.Value;
if (FilterByDay)
{
DateFilter = date.AddDays(value);
}
else if (FilterByWeek)
{
DateFilter = DateRangeFilter.Start!.Value.AddDays(value > 0 ? 7 : -7);
}
else if (FilterByMonth)
{
var year = date.Year;
var month = value > 0 ? date.Month + 1 : date.Month - 1;
switch (month)
{
case > 12:
year++;
month = 1;
break;
case < 1:
year--;
month = 12;
break;
}
DateFilter = new DateTime(year, month, 1);
DateTimeForMonthView = DateFilter.Value;
}
CalcDateRange();
StateHasChanged();
}
private void CalcDateRange()
{
var giornoSettimana = DateFilter!.Value.DayOfWeek;
var diffInizio = (7 + (giornoSettimana - DayOfWeek.Monday)) % 7;
DateRangeFilter.Start = DateFilter!.Value.AddDays(-diffInizio).Date;
DateRangeFilter.End = DateRangeFilter.Start.Value.AddDays(6);
}
private async Task CloseDatePicker()
{
DateTimeForMonthView = new DateTime(DateFilter!.Value.Year, DateFilter!.Value.Month, 1);
CalcDateRange();
await Task.Delay(150);
_isVisible = false;
StateHasChanged();
}
}

View File

@@ -1,17 +1,32 @@
.activity-filter {
margin-top: .5rem;
}
.activity-filter { margin-top: .2rem; }
.card-container {
margin-top: .5rem;
margin-top: .2rem;
width: 100%;
display: flex;
flex-direction: column;
flex-wrap: nowrap;
gap: 1rem;
overflow: hidden;
}
.date-controller {
display: flex;
align-items: center;
}
.content ::deep > .custom-mudButtonGroup {
width: 100%;
}
.content ::deep > .custom-mudButtonGroup .mud-button-root {
border-radius: 12px;
padding: .2rem 1.5rem;
text-transform: none !important;
font-size: .985rem;
border: 1px solid var(--mud-palette-gray-light);
}
.content ::deep > .custom-mudButtonGroup .custom-button-active {
background-color: hsl(from var(--mud-palette-primary) h s 95%);
}

View File

@@ -1,10 +1,21 @@
@page "/"
@using Template.Shared.Core.Interface
@attribute [Authorize]
@inject IFormFactor FormFactor
@inject INetworkService NetworkService
@code
{
protected override Task OnInitializedAsync()
{
var lastSyncDate = LocalStorage.Get<DateTime>("last-sync");
if (!FormFactor.IsWeb() && NetworkService.IsNetworkAvailable() && lastSyncDate.Equals(DateTime.MinValue))
{
NavigationManager.NavigateTo("/sync");
return base.OnInitializedAsync();
}
NavigationManager.NavigateTo("/Calendar");
return base.OnInitializedAsync();
}

View File

@@ -11,7 +11,7 @@
else
{
<div class="center-box container d-flex justify-content-center align-items-center min-vh-100">
<div class="row border rounded-4 bg-white shadow box-area">
<div class="row rounded-4 bg-white">
<div class="appName rounded-4 d-flex justify-content-center align-items-center flex-column">
<span>Nome App</span>
@@ -23,7 +23,7 @@ else
<MudTextField @bind-Value="UserData.Username" Label="Username" Variant="Variant.Text"/>
</div>
<div class="input-group mb-2">
<MudTextField @bind-Value="UserData.Password" Label="Password" Variant="Variant.Text"/>
<MudTextField InputType="@_passwordInput" @bind-Value="UserData.Password" Label="Password" Variant="Variant.Text" Adornment="Adornment.End" AdornmentIcon="@_passwordInputIcon" OnAdornmentClick="ShowPassword" AdornmentAriaLabel="Show Password" />
</div>
<div class="input-group mb-4">
<MudTextField @bind-Value="UserData.CodHash" Label="Profilo azienda" Variant="Variant.Text"/>
@@ -55,6 +55,26 @@ else
private string ErrorMessage { get; set; } = "";
private bool _attemptFailed;
private bool _isShow;
private InputType _passwordInput = InputType.Password;
private string _passwordInputIcon = Icons.Material.Rounded.VisibilityOff;
private void ShowPassword()
{
@if (_isShow)
{
_isShow = false;
_passwordInputIcon = Icons.Material.Rounded.VisibilityOff;
_passwordInput = InputType.Password;
}
else
{
_isShow = true;
_passwordInputIcon = Icons.Material.Rounded.Visibility;
_passwordInput = InputType.Text;
}
}
protected override void OnInitialized()
{
UserData.CodHash = LocalStorage.GetString("codHash");

View File

@@ -35,9 +35,8 @@
.button-login {
text-align: center;
border: 2px solid var(--mud-palette-primary);
background-color: var(--mud-palette-primary);
border-radius: 25px;
border-radius: 6px;
padding: .3rem 2rem;
width: 100%;
font-weight: 700;
@@ -59,3 +58,8 @@
height: 15px;
margin-left: 4px;
}
.container > .bg-white {
box-shadow: var(--card-shadow);
border: 1px solid var(--card-border-color);
}

View File

@@ -1,9 +1,120 @@
@page "/PersonalInfo"
@attribute [Authorize]
@using Template.Shared.Components.Layout
@using Template.Shared.Core.Authorization.Enum
@using Template.Shared.Core.Interface
@using Template.Shared.Core.Services
@using Template.Shared.Core.Utility
@inject AppAuthenticationStateProvider AuthenticationStateProvider
@inject INetworkService NetworkService
@inject IFormFactor FormFactor
<HeaderLayout Title="Profilo" />
<div class="content">
<div class="section-primary-info">
<MudAvatar Style="height:85px; width:85px; font-size:2rem;">
<MudImage Src="@($"https://ui-avatars.com/api/?name={UserSession.User.Username}&size=80&background={UtilityColor.CalcHexColor(UserSession.User.Username)}&bold=true")"></MudImage>
</MudAvatar>
<div class="personal-info">
<span class="info-nome">@UserSession.User.Fullname</span>
@if (UserSession.User.KeyGroup is not null)
{
<span class="info-section">@(((KeyGroupEnum)UserSession.User.KeyGroup).ConvertToHumanReadable())</span>
}
</div>
</div>
<div class="section-info">
<div class="section-personal-info">
<div>
<span class="info-title">Telefono</span>
<span class="info-text">000 0000000</span> @*Todo: to implement*@
</div>
<div>
<span class="info-title">Status</span>
@if (NetworkService.IsNetworkAvailable())
{
<div class="status online">
<i class="ri-wifi-line"></i>
<span>Online</span>
</div>
}
else
{
<div class="status offline">
<i class="ri-wifi-off-line"></i>
<span>Offline</span>
</div>
}
</div>
</div>
<div class="section-personal-info">
<div>
<span class="info-title">E-mail</span>
<span class="info-text">
@if (string.IsNullOrEmpty(UserSession.User.Email))
{
@("Nessuna mail configurata")
}
else
{
@UserSession.User.Email
}
</span>
</div>
<div>
<span class="info-title">Ultima sincronizzazione</span>
<span class="info-text">@LastSync.ToString("g")</span>
</div>
</div>
</div>
<MudButton Class="user-button"
FullWidth="true"
Size="Size.Medium"
StartIcon="@Icons.Material.Outlined.Settings"
OnClick="OpenSettings"
Variant="Variant.Outlined">Impostazioni</MudButton>
<div class="divider"></div>
<MudButton FullWidth="true"
StartIcon="@Icons.Material.Outlined.Logout"
Color="Color.Error"
Size="Size.Medium"
OnClick="Logout"
Variant="Variant.Outlined">Esci</MudButton>
</div>
@code {
private bool Unavailable { get; set; }
private DateTime LastSync { get; set; }
protected override async Task OnInitializedAsync()
{
await LoadData();
}
private async Task LoadData()
{
await Task.Run(() =>
{
Unavailable = FormFactor.IsWeb() || !NetworkService.IsNetworkAvailable();
LastSync = LocalStorage.Get<DateTime>("last-sync");
});
StateHasChanged();
}
private void OpenSettings() =>
NavigationManager.NavigateTo("/settings/Profilo");
private void Logout() =>
AuthenticationStateProvider.SignOut();
}

View File

@@ -0,0 +1,83 @@
.section-primary-info {
display: flex;
flex-direction: column;
align-items: center;
}
.personal-info {
display: flex;
flex-direction: column;
align-items: center;
line-height: normal;
margin: .2rem 0 1rem 0;
}
.info-nome {
color: var(--mud-palette-text-primary);
font-weight: 800;
font-size: x-large;
}
.info-section {
color: var(--mud-palette-gray-default);
font-size: medium;
font-weight: 600;
}
.section-info {
width: 100%;
margin-bottom: 1.5rem;
border-radius: 12px;
display: flex;
justify-content: space-between;
flex-direction: row;
padding: .8rem 1.2rem;
border: 1px solid var(--card-border-color);
box-shadow: var(--card-shadow);
}
.section-personal-info {
display: flex;
flex-direction: column;
}
.section-personal-info > div {
display: flex;
flex-direction: column;
line-height: normal;
margin: .25rem 0;
}
.info-title {
color: var(--mud-palette-gray-darker);
font-weight: 800;
}
.info-text {
color: var(--mud-palette-text-secondary);
font-weight: 700;
font-size: small;
}
.content ::deep .user-button {
border: 1px solid var(--card-border-color) !important;
}
.user-button > i { font-size: large; }
.user-button > span {
font-size: medium;
font-weight: 600;
}
.status {
font-weight: 700;
}
.status.online {
color: var(--mud-palette-success);
}
.status.offline {
color: var(--mud-palette-error);
}

View File

@@ -0,0 +1,28 @@
@page "/settings"
@page "/settings/{BackTo}"
@using Template.Shared.Components.Layout
<HeaderLayout BackTo="@BackTo" ShowNotifications="false" Back="true" Title="Impostazioni" />
<div class="content">
<MudButton Class="user-button"
FullWidth="true"
Size="Size.Medium"
StartIcon="@Icons.Material.Outlined.Sync"
OnClick="UpdateDb"
Variant="Variant.Outlined">Sincronizza</MudButton>
</div>
@code {
[Parameter] public string BackTo { get; set; } = "";
private void UpdateDb()
{
var absoluteUri = NavigationManager.ToAbsoluteUri(NavigationManager.Uri);
var pathAndQuery = absoluteUri.Segments.Length > 1 ? absoluteUri.PathAndQuery : null;
var path = pathAndQuery == null ? $"/sync/{DateTime.Today:yyyy-MM-dd}" : $"/sync/{DateTime.Today:yyyy-MM-dd}?path=" + System.Web.HttpUtility.UrlEncode(pathAndQuery);
NavigationManager.NavigateTo(path);
}
}

View File

@@ -0,0 +1,57 @@
@page "/sync"
@page "/sync/{DateFilter}"
@using Template.Shared.Components.Layout.Spinner
@using Template.Shared.Core.Interface
@inject ISyncDbService syncDb
<SyncSpinner Elements="@Elements"/>
@code {
[Parameter] public string? DateFilter { get; set; }
private Dictionary<string, bool> Elements { get; set; } = new();
protected override async Task OnInitializedAsync()
{
Elements.Add("Attività", false);
Elements.Add("Clienti", false);
Elements.Add("Commesse", false);
StateHasChanged();
await Task.WhenAll(SetActivity(), SetClienti(), SetCommesse());
LocalStorage.Set("last-sync", DateTime.Now);
var pathQuery = System.Web.HttpUtility.ParseQueryString(new UriBuilder(NavigationManager.Uri).Query);
var originalPath = pathQuery["path"] ?? null;
var path = originalPath ?? "/Calendar";
NavigationManager.NavigateTo(path);
}
private async Task SetActivity()
{
await syncDb.GetAndSaveActivity(DateFilter);
Elements["Attività"] = true;
StateHasChanged();
}
private async Task SetClienti()
{
await syncDb.GetAndSaveClienti(DateFilter);
await syncDb.GetAndSaveProspect(DateFilter);
Elements["Clienti"] = true;
StateHasChanged();
}
private async Task SetCommesse()
{
await syncDb.GetAndSaveCommesse(DateFilter);
Elements["Commesse"] = true;
StateHasChanged();
}
}

View File

@@ -0,0 +1,61 @@
@using ConSegna.Shared.Core.Helpers
@using Template.Shared.Core.Dto
@using Template.Shared.Core.Interface
@inject IManageDataService manageData
<div class="calendar">
@if (!Activities.IsNullOrEmpty())
{
@foreach (var activity in Activities!)
{
<ActivityCard Activity="activity"/>
}
}
else
{
<NoDataAvailable Text="Nessuna attività trovata" ImageSource="_content/Template.Shared/images/undraw_file-search_cbur.svg"/>
}
</div>
@code
{
[Parameter] public required DateTime? Date { get; set; }
[Parameter] public EventCallback<DateTime?> DateChanged { get; set; }
private List<ActivityDTO>? Activities { get; set; } = null;
protected override async Task OnAfterRenderAsync(bool firstRender)
{
if (firstRender)
{
await LoadData();
}
}
protected override async Task OnParametersSetAsync()
{
await LoadData();
}
private async Task LoadData()
{
await Task.Delay(1000);
var refreshActivity = await RefreshActivity();
Activities = refreshActivity;
StateHasChanged();
}
private async Task<List<ActivityDTO>> RefreshActivity()
{
var activityDto = await Task.Run(async () =>
{
return (await manageData.GetActivity(x =>
(x.EffectiveDate == null && x.EstimatedDate.Equals(Date)) || x.EffectiveDate.Equals(Date)))
.OrderBy(x => x.EffectiveDate ?? x.EstimatedDate)
.ToList();
});
return activityDto;
}
}

View File

@@ -0,0 +1,18 @@
.calendar {
width: 100%;
display: flex;
flex-direction: column;
flex-wrap: nowrap;
gap: 1rem;
overflow-y: auto;
overflow-x: hidden;
padding-bottom: 1rem;
}
.calendar::-webkit-scrollbar { display: none; }
.calendar {
-ms-overflow-style: none;
scrollbar-width: none;
}

View File

@@ -0,0 +1,96 @@
<div class="calendar">
@foreach (var nomeGiorno in _giorniSettimana)
{
<div class="calendar-header">@nomeGiorno</div>
}
@for (var i = 0; i < StartDays; i++)
{
<div class="calendar-day disabled @(i == 0 ? "radiusTopLeft" : "")"></div>
}
@for (var day = 1; day <= DaysInMonth; day++)
{
var currentDate = new DateTime(Date.Year, Date.Month, day);
var events = GetEventsForDay(currentDate);
var isToday = currentDate == DateTime.Today;
var topRight = StartDays == 0 ? 7 : 7 - StartDays;
var bottomLeft = DaysInMonth - (6 - EndDays);
<div class="calendar-day @(isToday ? "today" : "")
@(StartDays == 0 && day == 1 ? "radiusTopLeft" : "")
@(EndDays == 0 && day == DaysInMonth ? "radiusBottomRight" : "")
@(bottomLeft == day ? "radiusBottomLeft" : "")
@(topRight == day ? "radiusTopRight" : "")">
<div class="calendar-day-wrapper">
<span class="titleDay">@day</span>
@if (events.Any())
{
<div class="event-dot"></div>
}
</div>
</div>
}
@for (var i = 0; i < EndDays; i++)
{
<div class="calendar-day disabled @(i + 1 == EndDays ? "radiusBottomRight" : "")"></div>
}
</div>
@code
{
[Parameter] public required DateTime Date { get; set; }
[Parameter] public EventCallback<DateTime> DateChanged { get; set; }
private List<CalendarEvent> Events { get; set; }
private int DaysInMonth { get; set; }
private int StartDays { get; set; }
private int EndDays { get; set; }
readonly string[] _giorniSettimana = ["Lu", "Ma", "Me", "Gi", "Ve", "Sa", "Do"];
protected override void OnInitialized()
{
ChangeMonth();
}
protected override void OnParametersSet()
{
ChangeMonth();
}
private void ChangeMonth()
{
var firstDay = Date;
DaysInMonth = DateTime.DaysInMonth(firstDay.Year, firstDay.Month);
var dayOfWeek = (int)firstDay.DayOfWeek;
StartDays = dayOfWeek == 0 ? 6 : dayOfWeek - 1;
var tempTotalCell = (int)Math.Ceiling((double)(DaysInMonth + StartDays) / 7);
var totalCell = tempTotalCell * 7;
EndDays = totalCell - (DaysInMonth + StartDays);
Events =
[
new CalendarEvent { Date = DateTime.Today, Title = "Meeting", Time = "10:00" },
new CalendarEvent { Date = DateTime.Today.AddDays(2), Title = "Dentista", Time = "15:30" },
new CalendarEvent { Date = DateTime.Today.AddDays(5), Title = "Scadenza", Time = "Tutto il giorno" }
];
}
private List<CalendarEvent> GetEventsForDay(DateTime day)
{
return Events.Where(e => e.Date.Date == day.Date).ToList();
}
public class CalendarEvent
{
public DateTime Date { get; set; }
public string Title { get; set; } = "";
public string Time { get; set; } = "";
}
}

View File

@@ -0,0 +1,64 @@
.calendar {
display: grid;
grid-template-columns: repeat(7, 1fr);
/*border: 1px solid #ccc;*/
}
.calendar-header, .calendar-day {
display: flex;
flex-direction: column;
align-items: center;
justify-content: flex-start;
min-height: 65px;
font-size: 0.85rem;
padding: 4px;
}
.calendar-day { border: 1px solid var(--mud-palette-gray-light); }
.calendar-day.disabled { border: 1px solid hsl(from var(--mud-palette-gray-light) h s 88%); }
.calendar-header {
font-weight: bold;
min-height: 25px;
display: flex;
justify-content: end;
}
.today > .calendar-day-wrapper > .titleDay {
background-color: var(--mud-palette-primary);
color: var(--mud-palette-appbar-text);
font-weight: 700;
}
.calendar-day-wrapper > .titleDay {
padding: 6px;
border-radius: 50%;
position: absolute;
line-height: normal;
}
.event-dot {
width: 100%;
height: 6px;
border-radius: 4px;
background-color: var(--mud-palette-secondary);
position: absolute;
bottom: 0;
}
.calendar-day:hover .event-popup { display: block; }
.calendar-day-wrapper {
position: relative;
width: 100%;
height: 100%;
}
.radiusTopLeft { border-top-left-radius: 12px; }
.radiusTopRight { border-top-right-radius: 12px; }
.radiusBottomLeft { border-bottom-left-radius: 12px; }
.radiusBottomRight { border-bottom-right-radius: 12px; }

View File

@@ -0,0 +1,76 @@
@using ConSegna.Shared.Core.Helpers
@using Template.Shared.Core.Dto
@using Template.Shared.Core.Interface
@inject IManageDataService manageData
<div class="calendar">
@{
DateTime? currentDate = null;
}
@if (!Activities.IsNullOrEmpty())
{
foreach (var activity in Activities!)
{
var dateToShow = activity.EffectiveDate ?? activity.EstimatedDate;
if (currentDate != dateToShow?.Date)
{
currentDate = dateToShow?.Date;
<div class="week-info">
<span>@($"{currentDate:D}")</span>
</div>
}
<ActivityCard Activity="activity"/>
}
}
else
{
<NoDataAvailable Text="Nessuna attività trovata" ImageSource="_content/Template.Shared/images/undraw_file-search_cbur.svg"/>
}
</div>
@code
{
[Parameter] public required DateRange Date { get; set; }
[Parameter] public EventCallback<DateRange> DateChanged { get; set; }
private List<ActivityDTO>? Activities { get; set; }
protected override async Task OnAfterRenderAsync(bool firstRender)
{
if (firstRender)
{
await LoadData();
}
}
protected override async Task OnParametersSetAsync()
{
await LoadData();
}
private async Task LoadData()
{
await Task.Delay(1000);
var refreshActivity = await RefreshActivity();
Activities = refreshActivity;
StateHasChanged();
}
private async Task<List<ActivityDTO>> RefreshActivity()
{
var activityDto = await Task.Run(async () =>
{
return Activities = (await manageData.GetActivity(x =>
(x.EffectiveDate == null && x.EstimatedDate >= Date.Start && x.EstimatedDate <= Date.End) ||
(x.EffectiveDate >= Date.Start && x.EffectiveDate <= Date.End)
))
.OrderBy(x => x.EffectiveDate ?? x.EstimatedDate)
.ToList();
});
return activityDto;
}
}

View File

@@ -0,0 +1,26 @@
.calendar {
width: 100%;
display: flex;
flex-direction: column;
flex-wrap: nowrap;
gap: 1rem;
overflow-y: auto;
overflow-x: hidden;
padding-bottom: 1rem;
}
.calendar::-webkit-scrollbar { display: none; }
.calendar {
-ms-overflow-style: none;
scrollbar-width: none;
}
.week-info {
background: var(--mud-palette-action-disabled-background);
width: 100%;
padding: .3rem .5rem;
border-radius: 8px;
text-transform: capitalize;
font-weight: 700;
}

View File

@@ -1,22 +1,52 @@
<div class="activity-card @Type shadow box-area">
@using Template.Shared.Core.Dto
<div class="activity-card @Activity.Category.ConvertToHumanReadable()">
<div class="activity-left-section">
<div class="activity-hours-section">
<span class="activity-hours">14:00</span>
<MudChip T="string" Icon="@IconConstants.Chip.Time" Color="Color.Dark" Size="Size.Small">1h</MudChip>
<span class="activity-hours">
@if (Activity.EffectiveTime is null)
{
@($"{Activity.EstimatedTime:t}")
}
else
{
@($"{Activity.EffectiveTime:t}")
}
</span>
@if (Durata != null)
{
<MudChip T="string" Icon="@IconConstants.Chip.Time" Color="Color.Dark" Size="Size.Small">@($"{Durata.Value.TotalHours:####}h")</MudChip>
}
</div>
<div class="activity-body-section">
<span class="activity-title">Format</span>
<span class="activity-subtitle">Preparazione preventivo</span>
<MudText Class="activity-title" Typo="Typo.button" HtmlTag="h3">@Activity.Commessa</MudText>
<MudText Class="activity-subtitle" Typo="Typo.caption">@Activity.ActivityDescription</MudText>
</div>
</div>
<div class="activity-info-section">
<MudChip T="string" Icon="@IconConstants.Chip.Stato" Size="Size.Small" Color="Color.Success">Completata</MudChip>
<MudChip T="string" Icon="@IconConstants.Chip.User" Size="Size.Small">GMANCINI</MudChip>
@if (Activity.ActivityResultId != null)
{
<MudChip T="string" Icon="@IconConstants.Chip.Stato" Size="Size.Small" Color="Color.Success">@Activity.ActivityResultId</MudChip>
}
<MudChip T="string" Icon="@IconConstants.Chip.User" Size="Size.Small">@Activity.UserName</MudChip>
</div>
</div>
@code {
[Parameter] public string Type { get; set; } = "";
[Parameter] public ActivityDTO Activity { get; set; } = new();
private TimeSpan? Durata { get; set; }
private Color ColorStatus { get; set; }
protected override void OnInitialized()
{
Durata = Activity switch
{
{ EffectiveTime: not null, EffectiveEndtime: not null } => Activity.EffectiveEndtime.Value - Activity.EffectiveTime.Value,
{ EstimatedTime: not null, EstimatedEndtime: not null } => Activity.EstimatedEndtime.Value - Activity.EstimatedTime.Value,
_ => Durata
};
}
}

View File

@@ -7,6 +7,8 @@
padding: .5rem .7rem;
border-radius: 12px;
line-height: normal;
border: 1px solid var(--card-border-color);
box-shadow: var(--card-shadow);
}
.activity-card.memo { border-left: 5px solid var(--mud-palette-info-darken); }
@@ -38,14 +40,16 @@
flex-direction: column;
}
.activity-title {
font-weight: 800;
font-size: medium;
.activity-body-section ::deep > .activity-title {
font-weight: 800 !important;
margin: 0 0 .2rem 0 !important;
line-height: normal !important;
}
.activity-subtitle {
.activity-body-section ::deep > .activity-subtitle {
font-size: smaller;
color: var(--mud-palette-gray-darker)
color: var(--mud-palette-gray-darker);
line-height: normal !important;
}
.activity-info-section { width: min-content; }

View File

@@ -1,6 +1,5 @@
<div class="no-data opacity-75 d-flex flex-column align-items-center">
<img
src="@ImageSource"/>
<img src="@ImageSource"/>
<p class="mt-3">@Text</p>
</div>

View File

@@ -1,7 +1,7 @@
.no-data {
position: fixed;
top: 35%;
width: calc(100% - 3rem); /* remove page padding */
width: calc(100vw - (var(--bs-gutter-x) * .5) * 2);
}
.no-data img {

View File

@@ -0,0 +1,8 @@
namespace Template.Shared.Core.Authorization.Enum;
public enum KeyGroupEnum
{
UtenteAziendale = 2,
Agenti = 5,
Tecnico = 22
}

View File

@@ -0,0 +1,10 @@
using Template.Shared.Core.Entity;
using Template.Shared.Core.Helpers.Enum;
namespace Template.Shared.Core.Dto;
public class ActivityDTO : StbActivity
{
public string? Commessa { get; set; }
public ActivityCategoryEnum Category { get; set; }
}

View File

@@ -0,0 +1,12 @@
using Template.Shared.Core.Entity;
namespace Template.Shared.Core.Dto;
public class TaskSyncResponseDTO
{
public List<AnagClie>? AnagClie { get; set; }
public List<VtbDest>? VtbDest { get; set; }
public List<VtbCliePersRif>? VtbCliePersRif { get; set; }
public List<PtbPros>? PtbPros { get; set; }
public List<PtbProsRif>? PtbProsRif { get; set; }
}

View File

@@ -0,0 +1,83 @@
using SQLite;
using System.Text.Json.Serialization;
namespace Template.Shared.Core.Entity;
[Table("anag_clie")]
public class AnagClie
{
[PrimaryKey, Column("cod_anag"), JsonPropertyName("codAnag")]
public string CodAnag { get; set; }
[Column("cod_vtip"), JsonPropertyName("codVtip")]
public string? CodVtip { get; set; }
[Column("cod_vage"), JsonPropertyName("codVage")]
public string? CodVage { get; set; }
[Column("rag_soc"), JsonPropertyName("ragSoc")]
public string RagSoc { get; set; }
[Column("indirizzo"), JsonPropertyName("indirizzo")]
public string Indirizzo { get; set; }
[Column("cap"), JsonPropertyName("cap")]
public string Cap { get; set; }
[Column("citta"), JsonPropertyName("citta")]
public string Citta { get; set; }
[Column("prov"), JsonPropertyName("prov")]
public string Prov { get; set; }
[Column("nazione"), JsonPropertyName("nazione")]
public string Nazione { get; set; }
[Column("telefono"), JsonPropertyName("telefono")]
public string Telefono { get; set; }
[Column("fax"), JsonPropertyName("fax")]
public string Fax { get; set; }
[Column("part_iva"), JsonPropertyName("partIva")]
public string PartIva { get; set; }
[Column("cod_fisc"), JsonPropertyName("codFisc")]
public string CodFisc { get; set; }
[Column("note"), JsonPropertyName("note")]
public string Note { get; set; }
[Column("persona_rif"), JsonPropertyName("personaRif")]
public string PersonaRif { get; set; }
[Column("e_mail"), JsonPropertyName("eMail")]
public string EMail { get; set; }
[Column("e_mail_pec"), JsonPropertyName("eMailPec")]
public string EMailPec { get; set; }
[Column("nome"), JsonPropertyName("nome")]
public string Nome { get; set; }
[Column("data_ins"), JsonPropertyName("dataIns")]
public DateTime? DataIns { get; set; } = DateTime.Now;
[Column("num_cell"), JsonPropertyName("numCell")]
public string NumCell { get; set; }
[Column("cognome"), JsonPropertyName("cognome")]
public string Cognome { get; set; }
[Column("diacod"), JsonPropertyName("diacod")]
public string Diacod { get; set; }
[Column("lat"), JsonPropertyName("lat")]
public decimal? Lat { get; set; }
[Column("lng"), JsonPropertyName("lng")]
public decimal? Lng { get; set; }
[Column("data_mod"), JsonPropertyName("dataMod")]
public DateTime? DataMod { get; set; } = DateTime.Now;
}

View File

@@ -0,0 +1,110 @@
using System.Text.Json.Serialization;
using SQLite;
namespace Template.Shared.Core.Entity;
[Table("jtb_comt")]
public class JtbComt
{
[PrimaryKey, Column("cod_jcom"), JsonPropertyName("codJcom")]
public string CodJcom { get; set; }
[Column("cod_jfas"), JsonPropertyName("codJfas")]
public string CodJfas { get; set; }
[Column("cod_jflav"), JsonPropertyName("codJflav")]
public string CodJflav { get; set; }
[Column("descrizione"), JsonPropertyName("descrizione")]
public string Descrizione { get; set; }
[Column("importo"), JsonPropertyName("importo")]
public decimal Importo { get; set; } = 0;
[Column("data_inizi_lav"), JsonPropertyName("dataIniziLav")]
public DateTime? DataIniziLav { get; set; }
[Column("cod_mart"), JsonPropertyName("codMart")]
public string CodMart { get; set; }
[Column("data_cons"), JsonPropertyName("dataCons")]
public DateTime? DataCons { get; set; }
[Column("manuali"), JsonPropertyName("manuali")]
public string Manuali { get; set; }
[Column("note"), JsonPropertyName("note")]
public string Note { get; set; }
[Column("cod_anag"), JsonPropertyName("codAnag")]
public string CodAnag { get; set; }
[Column("cod_divi"), JsonPropertyName("codDivi")]
public string CodDivi { get; set; } = "EURO";
[Column("cambio_divi"), JsonPropertyName("cambioDivi")]
public decimal CambioDivi { get; set; } = 1;
[Column("cod_divi_cont"), JsonPropertyName("codDiviCont")]
public string CodDiviCont { get; set; }
[Column("cambio_divi_cont"), JsonPropertyName("cambioDiviCont")]
public decimal CambioDiviCont { get; set; }
[Column("responsabile_com"), JsonPropertyName("responsabileCom")]
public string ResponsabileCom { get; set; }
[Column("stato_commessa"), JsonPropertyName("statoCommessa")]
public string StatoCommessa { get; set; }
[Column("tipo_commessa"), JsonPropertyName("tipoCommessa")]
public string TipoCommessa { get; set; }
[Column("descrizione_estesa"), JsonPropertyName("descrizioneEstesa")]
public string DescrizioneEstesa { get; set; }
[Column("perc_comp"), JsonPropertyName("percComp")]
public decimal PercComp { get; set; } = 0;
[Column("cod_vdes"), JsonPropertyName("codVdes")]
public string CodVdes { get; set; }
[Column("gestione"), JsonPropertyName("gestione")]
public string Gestione { get; set; }
[Column("data_ord"), JsonPropertyName("dataOrd")]
public DateTime? DataOrd { get; set; }
[Column("num_ord"), JsonPropertyName("numOrd")]
public int? NumOrd { get; set; }
[Column("matricola"), JsonPropertyName("matricola")]
public string Matricola { get; set; }
[Column("tipo_anag"), JsonPropertyName("tipoAnag")]
public string TipoAnag { get; set; }
[Column("flag_pubblica"), JsonPropertyName("flagPubblica")]
public string FlagPubblica { get; set; } = "N";
[Column("cig"), JsonPropertyName("cig")]
public string Cig { get; set; }
[Column("cup"), JsonPropertyName("cup")]
public string Cup { get; set; }
[Column("indirizzo_ente"), JsonPropertyName("indirizzoEnte")]
public string IndirizzoEnte { get; set; }
[Column("note_cons"), JsonPropertyName("noteCons")]
public string NoteCons { get; set; }
[Column("cod_vage"), JsonPropertyName("codVage")]
public string CodVage { get; set; }
[Column("cod_jflav_tec"), JsonPropertyName("codJflavTec")]
public string CodJflavTec { get; set; }
[Column("note_tecniche"), JsonPropertyName("noteTecniche")]
public string NoteTecniche { get; set; }
}

View File

@@ -0,0 +1,131 @@
using SQLite;
using System.Text.Json.Serialization;
namespace Template.Shared.Core.Entity;
[Table("ptb_pros")]
public class PtbPros
{
[PrimaryKey, Column("cod_ppro"), JsonPropertyName("codPpro")]
public string CodPpro { get; set; }
[Column("agenzia_banca"), JsonPropertyName("agenziaBanca")]
public string AgenziaBanca { get; set; }
[Column("cap"), JsonPropertyName("cap")]
public string Cap { get; set; }
[Column("citta"), JsonPropertyName("citta")]
public string Citta { get; set; }
[Column("cod_abi"), JsonPropertyName("codAbi")]
public string CodAbi { get; set; }
[Column("cod_aliq"), JsonPropertyName("codAliq")]
public string CodAliq { get; set; }
[Column("cod_anag"), JsonPropertyName("codAnag")]
public string CodAnag { get; set; }
[Column("cod_banc"), JsonPropertyName("codBanc")]
public string CodBanc { get; set; }
[Column("cod_cab"), JsonPropertyName("codCab")]
public string CodCab { get; set; }
[Column("cod_fisc"), JsonPropertyName("codFisc")]
public string CodFisc { get; set; }
[Column("cod_paga"), JsonPropertyName("codPaga")]
public string CodPaga { get; set; }
[Column("cod_vage"), JsonPropertyName("codVage")]
public string CodVage { get; set; }
[Column("cod_vatt"), JsonPropertyName("codVatt")]
public string CodVatt { get; set; }
[Column("cod_vlis"), JsonPropertyName("codVlis")]
public string CodVlis { get; set; }
[Column("cod_vseg"), JsonPropertyName("codVseg")]
public string CodVseg { get; set; }
[Column("cod_vset"), JsonPropertyName("codVset")]
public string CodVset { get; set; }
[Column("cod_vtip"), JsonPropertyName("codVtip")]
public string CodVtip { get; set; }
[Column("cod_vzon"), JsonPropertyName("codVzon")]
public string CodVzon { get; set; }
[Column("data_ins"), JsonPropertyName("dataIns")]
public DateTime? DataIns { get; set; } = DateTime.Now;
[Column("descrizione_pag"), JsonPropertyName("descrizionePag")]
public string DescrizionePag { get; set; }
[Column("e_mail"), JsonPropertyName("eMail")]
public string EMail { get; set; }
[Column("fax"), JsonPropertyName("fax")]
public string Fax { get; set; }
[Column("flag_riv_clie"), JsonPropertyName("flagRivClie")]
public string FlagRivClie { get; set; } = "C";
[Column("fonte"), JsonPropertyName("fonte")]
public string Fonte { get; set; }
[Column("gg_chiusura"), JsonPropertyName("ggChiusura")]
public string GgChiusura { get; set; }
[Column("indirizzo"), JsonPropertyName("indirizzo")]
public string Indirizzo { get; set; }
[Column("nazione"), JsonPropertyName("nazione")]
public string Nazione { get; set; }
[Column("note"), JsonPropertyName("note")]
public string Note { get; set; }
[Column("part_iva"), JsonPropertyName("partIva")]
public string PartIva { get; set; }
[Column("persona_rif"), JsonPropertyName("personaRif")]
public string PersonaRif { get; set; }
[Column("prov"), JsonPropertyName("prov")]
public string Prov { get; set; }
[Column("rag_soc"), JsonPropertyName("ragSoc")]
public string RagSoc { get; set; }
[Column("rag_soc2"), JsonPropertyName("ragSoc2")]
public string RagSoc2 { get; set; }
[Column("sconto1"), JsonPropertyName("sconto1")]
public decimal Sconto1 { get; set; } = 0;
[Column("sconto2"), JsonPropertyName("sconto2")]
public decimal Sconto2 { get; set; } = 0;
[Column("telefono"), JsonPropertyName("telefono")]
public string Telefono { get; set; }
[Column("cuu_pa"), JsonPropertyName("cuuPa")]
public string CuuPa { get; set; }
[Column("e_mail_pec"), JsonPropertyName("eMailPec")]
public string EMailPec { get; set; }
[Column("flag_informativa"), JsonPropertyName("flagInformativa")]
public string FlagInformativa { get; set; } = "N";
[Column("flag_consenso"), JsonPropertyName("flagConsenso")]
public string FlagConsenso { get; set; } = "N";
[Column("username"), JsonPropertyName("userName")]
public string UserName { get; set; }
}

View File

@@ -0,0 +1,32 @@
using SQLite;
using System.Text.Json.Serialization;
namespace Template.Shared.Core.Entity;
[Table("ptb_pros_rif")]
public class PtbProsRif
{
[PrimaryKey, Column("cod_ppro"), JsonPropertyName("codPpro")]
public string CodPpro { get; set; }
[PrimaryKey, Column("id_pers_rif"), JsonPropertyName("idPersRif")]
public int IdPersRif { get; set; }
[Column("persona_rif"), JsonPropertyName("personaRif")]
public string PersonaRif { get; set; }
[Column("e_mail"), JsonPropertyName("eMail")]
public string EMail { get; set; }
[Column("fax"), JsonPropertyName("fax")]
public string Fax { get; set; }
[Column("mansione"), JsonPropertyName("mansione")]
public string Mansione { get; set; }
[Column("num_cellulare"), JsonPropertyName("numCellulare")]
public string NumCellulare { get; set; }
[Column("telefono"), JsonPropertyName("telefono")]
public string Telefono { get; set; }
}

View File

@@ -0,0 +1,176 @@
using SQLite;
using System.Text.Json.Serialization;
namespace Template.Shared.Core.Entity;
[Table("stb_activity")]
public class StbActivity
{
[PrimaryKey, Column("activity_id"), JsonPropertyName("activityId")]
public string ActivityId { get; set; }
[Column("activity_result_id"), JsonPropertyName("activityResultId")]
public string? ActivityResultId { get; set; }
[Column("activity_type_id"), JsonPropertyName("activityTypeId")]
public string? ActivityTypeId { get; set; }
[Column("data_ins_act"), JsonPropertyName("dataInsAct")]
public DateTime DataInsAct { get; set; } = DateTime.Now;
[Column("activity_description"), JsonPropertyName("activityDescription")]
public string? ActivityDescription { get; set; }
[Column("parent_activity_id"), JsonPropertyName("parentActivityId")]
public string? ParentActivityId { get; set; }
[Column("tipo_anag"), JsonPropertyName("tipoAnag")]
public string? TipoAnag { get; set; }
[Column("cod_anag"), JsonPropertyName("codAnag")]
public string? CodAnag { get; set; }
[Column("cod_jcom"), JsonPropertyName("codJcom")]
public string? CodJcom { get; set; }
[Column("cod_jfas"), JsonPropertyName("codJfas")]
public string? CodJfas { get; set; }
[Column("estimated_date"), JsonPropertyName("estimatedDate")]
public DateTime? EstimatedDate { get; set; }
[Column("estimated_time"), JsonPropertyName("estimatedTime")]
public DateTime? EstimatedTime { get; set; }
[Column("alarm_date"), JsonPropertyName("alarmDate")]
public DateTime? AlarmDate { get; set; }
[Column("alarm_time"), JsonPropertyName("alarmTime")]
public DateTime? AlarmTime { get; set; }
[Column("effective_date"), JsonPropertyName("effectiveDate")]
public DateTime? EffectiveDate { get; set; }
[Column("effective_time"), JsonPropertyName("effectiveTime")]
public DateTime? EffectiveTime { get; set; }
[Column("result_description"), JsonPropertyName("resultDescription")]
public string? ResultDescription { get; set; }
[Column("estimated_enddate"), JsonPropertyName("estimatedEnddate")]
public DateTime? EstimatedEnddate { get; set; }
[Column("estimated_endtime"), JsonPropertyName("estimatedEndtime")]
public DateTime? EstimatedEndtime { get; set; }
[Column("effective_enddate"), JsonPropertyName("effectiveEnddate")]
public DateTime? EffectiveEnddate { get; set; }
[Column("effective_endtime"), JsonPropertyName("effectiveEndtime")]
public DateTime? EffectiveEndtime { get; set; }
[Column("user_creator"), JsonPropertyName("userCreator")]
public string? UserCreator { get; set; }
[Column("user_name"), JsonPropertyName("userName")]
public string? UserName { get; set; }
[Column("perc_comp"), JsonPropertyName("percComp")]
public double? PercComp { get; set; } = 0;
[Column("estimated_hours"), JsonPropertyName("estimatedHours")]
public double? EstimatedHours { get; set; } = 0;
[Column("cod_mart"), JsonPropertyName("codMart")]
public string? CodMart { get; set; }
[Column("partita_mag"), JsonPropertyName("partitaMag")]
public string? PartitaMag { get; set; }
[Column("matricola"), JsonPropertyName("matricola")]
public string? Matricola { get; set; }
[Column("priorita"), JsonPropertyName("priorita")]
public int? Priorita { get; set; } = 0;
[Column("activity_play_counter"), JsonPropertyName("activityPlayCounter")]
public double? ActivityPlayCounter { get; set; } = 0;
[Column("activity_event"), JsonPropertyName("activityEvent")]
public string? ActivityEvent { get; set; }
[Column("guarantee"), JsonPropertyName("guarantee")]
public string? Guarantee { get; set; }
[Column("note"), JsonPropertyName("note")]
public string? Note { get; set; }
[Column("rfid"), JsonPropertyName("rfid")]
public string? Rfid { get; set; }
[Column("id_lotto"), JsonPropertyName("idLotto")]
public int? IdLotto { get; set; }
[Column("persona_rif"), JsonPropertyName("personaRif")]
public string? PersonaRif { get; set; }
[Column("hr_num"), JsonPropertyName("hrNum")]
public int? HrNum { get; set; }
[Column("gestione"), JsonPropertyName("gestione")]
public string? Gestione { get; set; }
[Column("data_ord"), JsonPropertyName("dataOrd")]
public DateTime? DataOrd { get; set; }
[Column("num_ord"), JsonPropertyName("numOrd")]
public int? NumOrd { get; set; }
[Column("id_step"), JsonPropertyName("idStep")]
public int? IdStep { get; set; }
[Column("id_riga"), JsonPropertyName("idRiga")]
public int? IdRiga { get; set; }
[Column("ora_ins_act"), JsonPropertyName("oraInsAct")]
public DateTime? OraInsAct { get; set; }
[Column("indice_gradimento"), JsonPropertyName("indiceGradimento")]
public decimal? IndiceGradimento { get; set; } = 0;
[Column("note_gradimento"), JsonPropertyName("noteGradimento")]
public string? NoteGradimento { get; set; }
[Column("flag_risolto"), JsonPropertyName("flagRisolto")]
public string? FlagRisolto { get; set; } = "N";
[Column("flag_tipologia"), JsonPropertyName("flagTipologia")]
public string? FlagTipologia { get; set; }
[Ignore, JsonPropertyName("oreRapportino")]
public decimal? OreRapportino { get; set; }
[Column("user_modifier"), JsonPropertyName("userModifier")]
public string? UserModifier { get; set; }
[Column("ora_mod_act"), JsonPropertyName("oraModAct")]
public DateTime? OraModAct { get; set; } = DateTime.Now;
[Column("ora_view_act"), JsonPropertyName("oraViewAct")]
public DateTime? OraViewAct { get; set; }
[Column("cod_vdes"), JsonPropertyName("codVdes")]
public string? CodVdes { get; set; }
[Column("cod_cmac"), JsonPropertyName("codCmac")]
public string? CodCmac { get; set; }
[Column("wrike_id"), JsonPropertyName("wrikeId")]
public string? WrikeId { get; set; }
[Column("cod_mgrp"), JsonPropertyName("codMgrp")]
public string? CodMgrp { get; set; }
[Column("plan_id"), JsonPropertyName("planId")]
public long? PlanId { get; set; }
}

View File

@@ -0,0 +1,41 @@
using SQLite;
using System.Text.Json.Serialization;
namespace Template.Shared.Core.Entity;
[Table("vtb_clie_pers_rif")]
public class VtbCliePersRif
{
[PrimaryKey, Column("id_pers_rif"), JsonPropertyName("idPersRif")]
public int IdPersRif { get; set; }
[PrimaryKey, Column("cod_anag"), JsonPropertyName("codAnag")]
public string CodAnag { get; set; }
[Column("persona_rif"), JsonPropertyName("personaRif")]
public string PersonaRif { get; set; }
[Column("mansione"), JsonPropertyName("mansione")]
public string Mansione { get; set; }
[Column("telefono"), JsonPropertyName("telefono")]
public string Telefono { get; set; }
[Column("fax"), JsonPropertyName("fax")]
public string Fax { get; set; }
[Column("e_mail"), JsonPropertyName("eMail")]
public string EMail { get; set; }
[Column("num_cellulare"), JsonPropertyName("numCellulare")]
public string NumCellulare { get; set; }
[Column("tipo_indirizzo"), JsonPropertyName("tipoIndirizzo")]
public string TipoIndirizzo { get; set; }
[Column("cod_vdes"), JsonPropertyName("codVdes")]
public string CodVdes { get; set; }
[Column("data_ult_agg"), JsonPropertyName("dataUltAgg")]
public DateTime? DataUltAgg { get; set; } = DateTime.Now;
}

View File

@@ -0,0 +1,197 @@
using SQLite;
using System.Text.Json.Serialization;
namespace Template.Shared.Core.Entity;
[Table("vtb_dest")]
public class VtbDest
{
[PrimaryKey, Column("cod_anag"), JsonPropertyName("codAnag")]
public string CodAnag { get; set; }
[PrimaryKey, Column("cod_vdes"), JsonPropertyName("codVdes")]
public string CodVdes { get; set; }
[Column("destinatario"), JsonPropertyName("destinatario")]
public string Destinatario { get; set; }
[Column("indirizzo"), JsonPropertyName("indirizzo")]
public string Indirizzo { get; set; }
[Column("cap"), JsonPropertyName("cap")]
public string Cap { get; set; }
[Column("citta"), JsonPropertyName("citta")]
public string Citta { get; set; }
[Column("prov"), JsonPropertyName("prov")]
public string Prov { get; set; }
[Column("nazione"), JsonPropertyName("nazione")]
public string Nazione { get; set; }
[Column("tel"), JsonPropertyName("tel")]
public string Tel { get; set; }
[Column("fax"), JsonPropertyName("fax")]
public string Fax { get; set; }
[Column("note"), JsonPropertyName("note")]
public string Note { get; set; }
[Column("fonte"), JsonPropertyName("fonte")]
public string Fonte { get; set; }
[Column("cod_centro_azi"), JsonPropertyName("codCentroAzi")]
public string CodCentroAzi { get; set; }
[Column("gg_cons"), JsonPropertyName("ggCons")]
public int GgCons { get; set; } = 0;
[Column("cod_aliq_out"), JsonPropertyName("codAliqOut")]
public string CodAliqOut { get; set; }
[Column("cod_aliq_in"), JsonPropertyName("codAliqIn")]
public string CodAliqIn { get; set; }
[Column("descriz_aliq_out"), JsonPropertyName("descrizAliqOut")]
public string DescrizAliqOut { get; set; }
[Column("cod_vzon"), JsonPropertyName("codVzon")]
public string CodVzon { get; set; }
[Column("cod_vlis"), JsonPropertyName("codVlis")]
public string CodVlis { get; set; }
[Column("cod_vage"), JsonPropertyName("codVage")]
public string CodVage { get; set; }
[Column("persona_rif"), JsonPropertyName("personaRif")]
public string PersonaRif { get; set; }
[Column("part_iva"), JsonPropertyName("partIva")]
public string PartIva { get; set; }
[Column("cod_affiliazione"), JsonPropertyName("codAffiliazione")]
public string CodAffiliazione { get; set; }
[Column("indirizzo_legale"), JsonPropertyName("indirizzoLegale")]
public string IndirizzoLegale { get; set; }
[Column("cap_legale"), JsonPropertyName("capLegale")]
public string CapLegale { get; set; }
[Column("citta_legale"), JsonPropertyName("cittaLegale")]
public string CittaLegale { get; set; }
[Column("prov_legale"), JsonPropertyName("provLegale")]
public string ProvLegale { get; set; }
[Column("nazione_legale"), JsonPropertyName("nazioneLegale")]
public string NazioneLegale { get; set; }
[Column("cod_mdep"), JsonPropertyName("codMdep")]
public string CodMdep { get; set; }
[Column("flag_domic_riba"), JsonPropertyName("flagDomicRiba")]
public string FlagDomicRiba { get; set; }
[Column("flag_attivo"), JsonPropertyName("flagAttivo")]
public string FlagAttivo { get; set; } = "S";
[Column("flag_esponi"), JsonPropertyName("flagEsponi")]
public string FlagEsponi { get; set; } = "S";
[Column("rag_soc_legale"), JsonPropertyName("ragSocLegale")]
public string RagSocLegale { get; set; }
[Column("cod_alis"), JsonPropertyName("codAlis")]
public string CodAlis { get; set; }
[Column("cod_vpre"), JsonPropertyName("codVpre")]
public string CodVpre { get; set; }
[Column("cod_vcom"), JsonPropertyName("codVcom")]
public string CodVcom { get; set; }
[Column("cod_sco_cli"), JsonPropertyName("codScoCli")]
public string CodScoCli { get; set; }
[Column("e_mail"), JsonPropertyName("eMail")]
public string EMail { get; set; }
[Column("data_cessazione"), JsonPropertyName("dataCessazione")]
public DateTime? DataCessazione { get; set; }
[Column("data_attivazione"), JsonPropertyName("dataAttivazione")]
public DateTime? DataAttivazione { get; set; }
[Column("cod_vvet"), JsonPropertyName("codVvet")]
public string CodVvet { get; set; }
[Column("gg_chiusura"), JsonPropertyName("ggChiusura")]
public string GgChiusura { get; set; }
[Column("tipo_negozio"), JsonPropertyName("tipoNegozio")]
public string TipoNegozio { get; set; }
[Column("cod_ean"), JsonPropertyName("codEan")]
public string CodEan { get; set; }
[Column("flag_stampa_prezzi"), JsonPropertyName("flagStampaPrezzi")]
public string FlagStampaPrezzi { get; set; } = "S";
[Column("cod_aliq"), JsonPropertyName("codAliq")]
public string CodAliq { get; set; }
[Column("cod_griglia"), JsonPropertyName("codGriglia")]
public string CodGriglia { get; set; }
[Column("cod_acc"), JsonPropertyName("codAcc")]
public string CodAcc { get; set; }
[Column("cod_vtip"), JsonPropertyName("codVtip")]
public string CodVtip { get; set; }
[Column("cod_vset"), JsonPropertyName("codVset")]
public string CodVset { get; set; }
[Column("cod_vseg"), JsonPropertyName("codVseg")]
public string CodVseg { get; set; }
[Column("cod_vatt"), JsonPropertyName("codVatt")]
public string CodVatt { get; set; }
[Column("cod_fisc"), JsonPropertyName("codFisc")]
public string CodFisc { get; set; }
[Column("cuu_pa"), JsonPropertyName("cuuPa")]
public string CuuPa { get; set; }
[Column("e_mail_pec"), JsonPropertyName("eMailPec")]
public string EMailPec { get; set; }
[Column("flag_stabile_org"), JsonPropertyName("flagStabileOrg")]
public string FlagStabileOrg { get; set; }
[Column("lat"), JsonPropertyName("lat")]
public decimal? Lat { get; set; }
[Column("lng"), JsonPropertyName("lng")]
public decimal? Lng { get; set; }
[Column("term_cons"), JsonPropertyName("termCons")]
public string TermCons { get; set; }
[Column("itinerario"), JsonPropertyName("itinerario")]
public string Itinerario { get; set; }
[Column("imp_min_ord"), JsonPropertyName("impMinOrd")]
public decimal ImpMinOrd { get; set; } = 0;
[Column("part_iva_legale"), JsonPropertyName("partIvaLegale")]
public string PartIvaLegale { get; set; }
[Column("cod_fisc_legale"), JsonPropertyName("codFiscLegale")]
public string CodFiscLegale { get; set; }
}

View File

@@ -0,0 +1,17 @@
using Template.Shared.Core.Helpers.Enum;
namespace Template.Shared.Core.Helpers;
public static class ActivityCategoryHelper
{
public static string ConvertToHumanReadable(this ActivityCategoryEnum activityType)
{
return activityType switch
{
ActivityCategoryEnum.Memo => "memo",
ActivityCategoryEnum.Interna => "inerna",
ActivityCategoryEnum.Commessa => "commessa",
_ => throw new ArgumentOutOfRangeException(nameof(activityType), activityType, null)
};
}
}

View File

@@ -0,0 +1,8 @@
namespace Template.Shared.Core.Helpers.Enum;
public enum ActivityCategoryEnum
{
Memo = 0,
Interna = 1,
Commessa = 2
}

View File

@@ -0,0 +1,6 @@
namespace Template.Shared.Core.Helpers.Enum;
public enum ActivityStatusEnum
{
}

View File

@@ -0,0 +1,17 @@
using Template.Shared.Core.Authorization.Enum;
namespace Template.Shared.Core.Helpers;
public static class KeyGroupHelper
{
public static string ConvertToHumanReadable(this KeyGroupEnum keyGroup)
{
return keyGroup switch
{
KeyGroupEnum.Agenti => "Agenti",
KeyGroupEnum.Tecnico => "Tecnico",
KeyGroupEnum.UtenteAziendale => "Utente Aziendale",
_ => throw new ArgumentOutOfRangeException(nameof(keyGroup), keyGroup, null)
};
}
}

View File

@@ -0,0 +1,13 @@
using AutoMapper;
using Template.Shared.Core.Dto;
using Template.Shared.Core.Entity;
namespace Template.Shared.Core.Helpers;
public class MappingProfile : Profile
{
public MappingProfile()
{
CreateMap<StbActivity, ActivityDTO>();
}
}

View File

@@ -0,0 +1,13 @@
using System.Collections;
namespace ConSegna.Shared.Core.Helpers;
public static class ObjectExtensions
{
public static bool IsNullOrEmpty(this IEnumerable? obj) =>
obj == null || obj.GetEnumerator().MoveNext() == false;
public static bool IsNullOrEmpty(this string? obj) =>
string.IsNullOrEmpty(obj);
}

View File

@@ -0,0 +1,13 @@
namespace Template.Shared.Core.Interface;
public interface IFormFactor
{
public string GetFormFactor();
public string GetPlatform();
public bool IsWeb()
{
var formFactor = GetFormFactor();
return formFactor == "Web";
}
}

View File

@@ -0,0 +1,12 @@
using Template.Shared.Core.Dto;
using Template.Shared.Core.Entity;
namespace Template.Shared.Core.Interface;
public interface IIntegryApiService
{
Task<List<StbActivity>?> GetActivity(string? dateFilter = null);
Task<List<JtbComt>?> GetAllCommesse(string? dateFilter = null);
Task<TaskSyncResponseDTO> GetAnagClie(string? dateFilter = null);
Task<TaskSyncResponseDTO> GetProspect(string? dateFilter = null);
}

View File

@@ -0,0 +1,18 @@
using System.Linq.Expressions;
using Template.Shared.Core.Dto;
using Template.Shared.Core.Entity;
namespace Template.Shared.Core.Interface;
public interface IManageDataService
{
Task<List<AnagClie>> GetAnagClie(Expression<Func<AnagClie, bool>>? whereCond = null);
Task<List<JtbComt>> GetJtbComt(Expression<Func<JtbComt, bool>>? whereCond = null);
Task<List<PtbPros>> GetPtbPros(Expression<Func<PtbPros, bool>>? whereCond = null);
Task<List<PtbProsRif>> GetPtbProsRif(Expression<Func<PtbProsRif, bool>>? whereCond = null);
Task<List<StbActivity>> GetStbActivity(Expression<Func<StbActivity, bool>>? whereCond = null);
Task<List<VtbCliePersRif>> GetVtbCliePersRif(Expression<Func<VtbCliePersRif, bool>>? whereCond = null);
Task<List<VtbDest>> GetVtbDest(Expression<Func<VtbDest, bool>>? whereCond = null);
Task<List<ActivityDTO>> GetActivity(Expression<Func<StbActivity, bool>>? whereCond = null);
}

View File

@@ -0,0 +1,6 @@
namespace Template.Shared.Core.Interface;
public interface INetworkService
{
public bool IsNetworkAvailable();
}

View File

@@ -0,0 +1,9 @@
namespace Template.Shared.Core.Interface;
public interface ISyncDbService
{
Task GetAndSaveActivity(string? dateFilter = null);
Task GetAndSaveCommesse(string? dateFilter = null);
Task GetAndSaveProspect(string? dateFilter = null);
Task GetAndSaveClienti(string? dateFilter = null);
}

View File

@@ -0,0 +1,16 @@
using CommunityToolkit.Mvvm.Messaging;
namespace Template.Shared.Core.Messages;
public class BackNavigationService
{
public event Action? OnHardwareBack;
public BackNavigationService()
{
WeakReferenceMessenger.Default.Register<HardwareBackMessage>(this, (r, m) =>
{
OnHardwareBack?.Invoke();
});
}
}

View File

@@ -0,0 +1,5 @@
using CommunityToolkit.Mvvm.Messaging.Messages;
namespace Template.Shared.Core.Messages;
public class HardwareBackMessage(string value) : ValueChangedMessage<string>(value);

View File

@@ -0,0 +1,54 @@
using IntegryApiClient.Core.Domain.Abstraction.Contracts.Account;
using IntegryApiClient.Core.Domain.RestClient.Contacts;
using Template.Shared.Core.Dto;
using Template.Shared.Core.Entity;
using Template.Shared.Core.Interface;
namespace Template.Shared.Core.Services;
public class IntegryApiService(IIntegryApiRestClient integryApiRestClient, IUserSession userSession)
: IIntegryApiService
{
public Task<List<StbActivity>?> GetActivity(string? dateFilter)
{
var queryParams = new Dictionary<string, object> { { "dateFilter", dateFilter ?? "2020-01-01" } };
return integryApiRestClient.AuthorizedGet<List<StbActivity>?>("task/getActivity", queryParams);
}
public Task<List<JtbComt>?> GetAllCommesse(string? dateFilter)
{
var queryParams = new Dictionary<string, object>();
if (dateFilter != null)
{
queryParams.Add("dateFilter", dateFilter);
}
return integryApiRestClient.AuthorizedGet<List<JtbComt>?>("task/getCommesse", queryParams);
}
public Task<TaskSyncResponseDTO> GetAnagClie(string? dateFilter)
{
var queryParams = new Dictionary<string, object>();
if (dateFilter != null)
{
queryParams.Add("dateFilter", dateFilter);
}
return integryApiRestClient.AuthorizedGet<TaskSyncResponseDTO>("task/getAnagClie", queryParams)!;
}
public Task<TaskSyncResponseDTO> GetProspect(string? dateFilter)
{
var queryParams = new Dictionary<string, object>();
if (dateFilter != null)
{
queryParams.Add("dateFilter", dateFilter);
}
return integryApiRestClient.AuthorizedGet<TaskSyncResponseDTO>("task/getProspect", queryParams)!;
}
}

View File

@@ -0,0 +1,118 @@
namespace Template.Shared.Core.Utility;
public static class UtilityColor
{
public static string CalcHexColor(string input)
{
try
{
var hue = (int)(Math.Abs(input.GetHashCode()) * 137.508 % 360);
var data = new HSL(hue, 0.90f, 0.85f);
var myColor = HSLToRGB(data);
return myColor.R.ToString("X2") + myColor.G.ToString("X2") + myColor.B.ToString("X2");
}
catch (Exception e)
{
Console.WriteLine(e.Message);
return "dddddd";
}
}
private struct RGB(byte r, byte g, byte b)
{
public byte R
{
get => r;
set => r = value;
}
public byte G
{
get => g;
set => g = value;
}
public byte B
{
get => b;
set => b = value;
}
public bool Equals(RGB rgb)
{
return (this.R == rgb.R) && (this.G == rgb.G) && (this.B == rgb.B);
}
}
private struct HSL(int h, float s, float l)
{
public int H
{
get => h;
set => h = value;
}
public float S
{
get => s;
set => s = value;
}
public float L
{
get => l;
set => l = value;
}
public bool Equals(HSL hsl)
{
return H == hsl.H && (this.S == hsl.S) && (this.L == hsl.L);
}
}
private static RGB HSLToRGB(HSL hsl)
{
byte r;
byte g;
byte b;
var hue = (float)hsl.H / 360;
if (hsl.S == 0)
{
r = g = b = (byte)(hsl.L * 255);
}
else
{
var v2 = hsl.L < 0.5 ? hsl.L * (1 + hsl.S) : hsl.L + hsl.S - hsl.L * hsl.S;
var v1 = 2 * hsl.L - v2;
r = (byte)(255 * HueToRGB(v1, v2, hue + 1.0f / 3));
g = (byte)(255 * HueToRGB(v1, v2, hue));
b = (byte)(255 * HueToRGB(v1, v2, hue - 1.0f / 3));
}
return new RGB(r, g, b);
}
private static float HueToRGB(float v1, float v2, float vH)
{
if (vH < 0)
vH += 1;
if (vH > 1)
vH -= 1;
if (6 * vH < 1)
return v1 + (v2 - v1) * 6 * vH;
if (2 * vH < 1)
return v2;
if (3 * vH < 2)
return v1 + (v2 - v1) * (2.0f / 3 - vH) * 6;
return v1;
}
}

View File

@@ -0,0 +1,11 @@
namespace Template.Shared.Core.Utility;
public static class UtilityString
{
public static string ExtractInitials(string fullname)
{
return string.Concat(fullname
.Split(' ', StringSplitOptions.RemoveEmptyEntries)
.Select(word => char.ToUpper(word[0])));
}
}

View File

@@ -1,7 +0,0 @@
namespace Template.Shared.Interfaces;
public interface IFormFactor
{
public string GetFormFactor();
public string GetPlatform();
}

View File

@@ -11,8 +11,11 @@
</ItemGroup>
<ItemGroup>
<PackageReference Include="AutoMapper" Version="14.0.0" />
<PackageReference Include="CommunityToolkit.Mvvm" Version="8.4.0" />
<PackageReference Include="IntegryApiClient.Core" Version="1.1.3" />
<PackageReference Include="Microsoft.AspNetCore.Components.Authorization" Version="9.0.4" />
<PackageReference Include="sqlite-net-pcl" Version="1.9.172" />
<PackageReference Include="System.IdentityModel.Tokens.Jwt" Version="8.9.0" />
<PackageReference Include="Microsoft.AspNetCore.Components.Web" Version="9.0.4" />
<PackageReference Include="MudBlazor" Version="8.6.0" />
@@ -20,7 +23,6 @@
</ItemGroup>
<ItemGroup>
<Folder Include="Core\Services\" />
<Folder Include="wwwroot\css\lineicons\" />
<Folder Include="wwwroot\js\bootstrap\" />
</ItemGroup>

View File

@@ -29,6 +29,7 @@ a, .btn-link {
display: flex;
align-items: center;
flex-direction: column;
height: 84vh;
}
h1:focus { outline: none; }
@@ -71,6 +72,8 @@ h1:focus { outline: none; }
.page-title {
font-size: x-large;
font-weight: 800;
margin: 0;
line-height: normal;
color: var(--mud-palette-text-primary);
}
@@ -101,6 +104,13 @@ h1:focus { outline: none; }
padding-right: 12px !important;
}
.divider {
display: block;
width: 100%;
border: 1px solid var(--card-border-color);
margin: 1rem 0;
}
@supports (-webkit-touch-callout: none) {
.status-bar-safe-area {
display: flex;
@@ -120,3 +130,14 @@ h1:focus { outline: none; }
.flex-column, .navbar-brand { padding-left: env(safe-area-inset-left); }
}
/*MudBlazor Personalization*/
.mud-button-group-horizontal:not(.mud-button-group-rtl) > .mud-button-root:not(:last-child), .mud-button-group-horizontal:not(.mud-button-group-rtl) > :not(:last-child) .mud-button-root {
border-top-right-radius: 0 !important;
border-bottom-right-radius: 0 !important;
}
.mud-button-group-horizontal:not(.mud-button-group-rtl) > .mud-button-root:not(:first-child), .mud-button-group-horizontal:not(.mud-button-group-rtl) > :not(:first-child) .mud-button-root {
border-top-left-radius: 0 !important;
border-bottom-left-radius: 0 !important;
}

View File

@@ -1,5 +1,7 @@
:root {
--primary-color: #5352ed;
--ligther-color: #f7f7ff;
--darker-color: hsl(240, 81%, 30%);
/*Color*/
--card-border-color: hsl(from var(--mud-palette-gray-light) h s 86%);
--gray-for-shadow: hsl(from var(--mud-palette-gray-light) h s 95%);
/*Utility*/
--card-shadow: 5px 5px 10px 0 var(--gray-for-shadow);
}

View File

@@ -0,0 +1,43 @@
<svg xmlns="http://www.w3.org/2000/svg" width="748.974" height="457.275" viewBox="0 0 748.974 457.275" xmlns:xlink="http://www.w3.org/1999/xlink" role="img" artist="Katerina Limpitsouni" source="https://undraw.co/">
<g id="Group_201" data-name="Group 201" transform="translate(-382.003 -195.455)">
<g id="Group_200" data-name="Group 200" transform="translate(382.003 195.455)">
<path id="Path_3120-1952" data-name="Path 3120" d="M695.225,508.82,433.394,576.244a34.622,34.622,0,0,1-42.114-24.866L312.1,243.879a34.622,34.622,0,0,1,24.866-42.114l243.591-62.727L642.9,166.948l77.191,299.757A34.622,34.622,0,0,1,695.225,508.82Z" transform="translate(-311.003 -139.037)" fill="#f2f2f2"/>
<path id="Path_3121-1953" data-name="Path 3121" d="M338.989,210.925a24.655,24.655,0,0,0-17.708,29.99l79.185,307.5a24.655,24.655,0,0,0,29.99,17.708L692.287,498.7a24.655,24.655,0,0,0,17.708-29.99L634,173.595l-54.792-24.529Z" transform="translate(-310.548 -138.556)" fill="#fff"/>
<path id="Path_3122-1954" data-name="Path 3122" d="M629.927,168.5l-40.522,10.435a11.518,11.518,0,0,1-14.026-8.282l-7.707-29.929a.72.72,0,0,1,.989-.837l61.379,27.258a.72.72,0,0,1-.113,1.355Z" transform="translate(-298.695 -139)" fill="#f2f2f2"/>
<path id="Path_3123-1955" data-name="Path 3123" d="M612.519,418.284l-119.208,30.7a5.759,5.759,0,0,1-2.872-11.154l119.208-30.7a5.759,5.759,0,1,1,2.872,11.154Z" transform="translate(-302.605 -126.189)" fill="#ccc"/>
<path id="Path_3124-1956" data-name="Path 3124" d="M640.149,430.592,497.936,467.214a5.759,5.759,0,1,1-2.872-11.154l142.213-36.622a5.759,5.759,0,0,1,2.872,11.154Z" transform="translate(-302.384 -125.599)" fill="#ccc"/>
<circle id="Ellipse_44" data-name="Ellipse 44" cx="20.355" cy="20.355" r="20.355" transform="translate(121.697 319.055)" fill="#ABA9BF"/>
<path id="Path_3125-1957" data-name="Path 3125" d="M604.421,374.437,446.1,415.191a17.835,17.835,0,0,1-21.694-12.812L391.229,273.49A17.835,17.835,0,0,1,404.041,251.8l158.32-40.754a17.835,17.835,0,0,1,21.694,12.812l33.178,128.889A17.835,17.835,0,0,1,604.421,374.437Z" transform="translate(-307.183 -135.611)" fill="#fff"/>
<path id="Path_3126-1958" data-name="Path 3126" d="M604.421,374.437,446.1,415.191a17.835,17.835,0,0,1-21.694-12.812L391.229,273.49A17.835,17.835,0,0,1,404.041,251.8l158.32-40.754a17.835,17.835,0,0,1,21.694,12.812l33.178,128.889A17.835,17.835,0,0,1,604.421,374.437ZM404.563,253.826a15.737,15.737,0,0,0-11.3,19.142l33.178,128.889a15.737,15.737,0,0,0,19.142,11.3L603.9,372.407a15.737,15.737,0,0,0,11.3-19.142L582.025,224.376a15.737,15.737,0,0,0-19.142-11.3Z" transform="translate(-307.183 -135.611)" fill="#e6e6e6"/>
<path id="Path_411-1959" data-name="Path 411" d="M550.66,252.63l-79.9,20.568a2.862,2.862,0,0,1-3.467-1.8,2.757,2.757,0,0,1,1.942-3.5l81.335-20.937c3.286,1.665,2.421,5.07.091,5.67Z" transform="translate(-303.514 -133.861)" fill="#f2f2f2"/>
<path id="Path_412-1960" data-name="Path 412" d="M554.1,266l-79.9,20.568a2.862,2.862,0,0,1-3.467-1.8,2.757,2.757,0,0,1,1.942-3.5l81.335-20.937c3.286,1.665,2.421,5.07.091,5.67Z" transform="translate(-303.349 -133.22)" fill="#f2f2f2"/>
<path id="Path_413-1961" data-name="Path 413" d="M461.146,298.825,436.761,305.1a3.1,3.1,0,0,1-3.776-2.23L425.577,274.1a3.1,3.1,0,0,1,2.23-3.776l24.385-6.277a3.105,3.105,0,0,1,3.776,2.23l7.408,28.777a3.1,3.1,0,0,1-2.23,3.776Z" transform="translate(-305.513 -133.047)" fill="#ABA9BF"/>
<path id="Path_414-1962" data-name="Path 414" d="M562.854,293.445,440.909,324.835a2.862,2.862,0,0,1-3.467-1.8,2.757,2.757,0,0,1,1.942-3.5l123.38-31.76c3.286,1.665,2.421,5.07.091,5.67Z" transform="translate(-304.946 -131.904)" fill="#f2f2f2"/>
<path id="Path_415-1963" data-name="Path 415" d="M566.3,306.822,444.353,338.213a2.862,2.862,0,0,1-3.467-1.8,2.757,2.757,0,0,1,1.942-3.5l123.38-31.76c3.286,1.665,2.421,5.07.091,5.67Z" transform="translate(-304.781 -131.263)" fill="#f2f2f2"/>
<path id="Path_416-1964" data-name="Path 416" d="M569.739,320.192,447.794,351.582a2.862,2.862,0,0,1-3.467-1.8,2.757,2.757,0,0,1,1.942-3.5l123.379-31.76c3.286,1.665,2.421,5.07.091,5.67Z" transform="translate(-304.616 -130.621)" fill="#f2f2f2"/>
<path id="Path_417-1965" data-name="Path 417" d="M573.183,333.569,451.237,364.959a2.862,2.862,0,0,1-3.467-1.8,2.757,2.757,0,0,1,1.942-3.5l123.38-31.76C576.377,329.564,575.513,332.969,573.183,333.569Z" transform="translate(-304.45 -129.98)" fill="#f2f2f2"/>
<path id="Path_418-1966" data-name="Path 418" d="M576.624,346.939,454.679,378.329a2.862,2.862,0,0,1-3.467-1.8,2.757,2.757,0,0,1,1.942-3.5l123.38-31.76C579.819,342.934,578.954,346.339,576.624,346.939Z" transform="translate(-304.285 -129.339)" fill="#f2f2f2"/>
<path id="Path_395-1967" data-name="Path 395" d="M448.363,470.511a2.111,2.111,0,0,1-1.335-.092l-.026-.011-5.545-2.351a2.126,2.126,0,1,1,1.664-3.913l3.593,1.528,4.708-11.076a2.125,2.125,0,0,1,2.787-1.124h0l-.028.072.029-.073a2.127,2.127,0,0,1,1.124,2.788l-5.539,13.023a2.126,2.126,0,0,1-1.431,1.224Z" transform="translate(-304.809 -123.966)" fill="#fff"/>
</g>
<g id="Group_199" data-name="Group 199" transform="translate(673.007 225.872) rotate(-8)">
<g id="Group_198" data-name="Group 198" transform="translate(125.896 0) rotate(19)">
<path id="Path_3127-1968" data-name="Path 3127" d="M304.956,386.7H34.583A34.622,34.622,0,0,1,0,352.114V34.583A34.622,34.622,0,0,1,34.583,0H286.121l53.418,42.577V352.114A34.622,34.622,0,0,1,304.956,386.7Z" transform="translate(0 0)" fill="#e6e6e6"/>
<path id="Path_3128-1969" data-name="Path 3128" d="M24.627,0A24.655,24.655,0,0,0,0,24.627V342.158a24.655,24.655,0,0,0,24.627,24.627H295a24.655,24.655,0,0,0,24.627-24.627V37.418L272.683,0Z" transform="translate(9.956 9.956)" fill="#fff"/>
<path id="Path_3129-1970" data-name="Path 3129" d="M128.856,11.518H5.759A5.759,5.759,0,0,1,5.759,0h123.1a5.759,5.759,0,0,1,0,11.518Z" transform="translate(123.512 90.767)" fill="#ABA9BF"/>
<path id="Path_3130-1971" data-name="Path 3130" d="M152.612,11.518H5.759A5.759,5.759,0,0,1,5.759,0H152.612a5.759,5.759,0,1,1,0,11.518Z" transform="translate(123.512 110.204)" fill="#ABA9BF"/>
<path id="Path_3131-1972" data-name="Path 3131" d="M128.852,0H5.758a5.758,5.758,0,1,0,0,11.517H128.852a5.759,5.759,0,0,0,0-11.517Z" transform="translate(123.517 177.868)" fill="#ccc"/>
<path id="Path_3132-1973" data-name="Path 3132" d="M152.609,0H5.758a5.759,5.759,0,1,0,0,11.517h146.85a5.759,5.759,0,1,0,0-11.517Z" transform="translate(123.517 197.307)" fill="#ccc"/>
<path id="Path_3133-1974" data-name="Path 3133" d="M128.856,11.518H5.759A5.759,5.759,0,0,1,5.759,0h123.1a5.759,5.759,0,0,1,0,11.518Z" transform="translate(123.512 264.975)" fill="#ccc"/>
<path id="Path_3134-1975" data-name="Path 3134" d="M152.612,11.518H5.759A5.759,5.759,0,0,1,5.759,0H152.612a5.759,5.759,0,1,1,0,11.518Z" transform="translate(123.512 284.411)" fill="#ccc"/>
<circle id="Ellipse_44-2" data-name="Ellipse 44" cx="20.355" cy="20.355" r="20.355" transform="translate(57.655 85.89)" fill="#ABA9BF"/>
<path id="Path_395-2-1976" data-name="Path 395" d="M6.909,15.481a2.111,2.111,0,0,1-1.27-.422l-.023-.017L.832,11.382A2.126,2.126,0,0,1,3.419,8.008l3.1,2.376L13.839.832A2.125,2.125,0,0,1,16.819.439h0L16.774.5l.047-.063a2.127,2.127,0,0,1,.393,2.98L8.6,14.649a2.126,2.126,0,0,1-1.691.829Z" transform="translate(69.085 98.528)" fill="#fff"/>
<path id="Path_3135-1977" data-name="Path 3135" d="M40.707,20.359A20.354,20.354,0,0,1,20.356,40.721a4.372,4.372,0,0,1-.524-.021A20.353,20.353,0,1,1,40.707,20.359Z" transform="translate(59.75 172.987)" fill="#ABA9BF"/>
<circle id="Ellipse_44-3" data-name="Ellipse 44" cx="20.355" cy="20.355" r="20.355" transform="translate(57.655 260.097)" fill="#ABA9BF"/>
<path id="Path_3136-1978" data-name="Path 3136" d="M53.362,43.143H11.518A11.518,11.518,0,0,1,0,31.625V.72A.72.72,0,0,1,1.167.156l52.642,41.7a.72.72,0,0,1-.447,1.284Z" transform="translate(285.137 0.805)" fill="#ccc"/>
</g>
</g>
<path id="Path_3140-1979" data-name="Path 3140" d="M754.518,518.049a9.158,9.158,0,0,1-12.587,3.05L635.078,455.923a9.158,9.158,0,0,1,9.538-15.637l106.852,65.176a9.158,9.158,0,0,1,3.049,12.587Z" transform="translate(123.58 101.359)" fill="#3f3d56"/>
<path id="Path_3141-1980" data-name="Path 3141" d="M688.648,486.5a73.265,73.265,0,1,1-24.4-100.7A73.265,73.265,0,0,1,688.648,486.5ZM579.19,419.73a54.949,54.949,0,1,0,75.524-18.3,54.949,54.949,0,0,0-75.524,18.3Z" transform="translate(82.597 67.737)" fill="#3f3d56"/>
<circle id="Ellipse_44-4" data-name="Ellipse 44" cx="57.007" cy="57.007" r="57.007" transform="translate(672.542 442.858) rotate(19)" fill="#ABA9BF"/>
</g>
</svg>

After

Width:  |  Height:  |  Size: 8.5 KiB

View File

@@ -1 +1,3 @@

window.goBack = function () {
history.back();
};

View File

@@ -1,6 +1,6 @@
using Template.Shared.Interfaces;
using Template.Shared.Core.Interface;
namespace Template.Web.Services;
namespace Template.Web.Core.Services;
public class FormFactor : IFormFactor
{

View File

@@ -0,0 +1,49 @@
using System.Linq.Expressions;
using Template.Shared.Core.Dto;
using Template.Shared.Core.Entity;
using Template.Shared.Core.Interface;
namespace Template.Web.Core.Services;
public class ManageDataService : IManageDataService
{
public Task<List<AnagClie>> GetAnagClie(Expression<Func<AnagClie, bool>>? whereCond = null)
{
throw new NotImplementedException();
}
public Task<List<JtbComt>> GetJtbComt(Expression<Func<JtbComt, bool>>? whereCond = null)
{
throw new NotImplementedException();
}
public Task<List<PtbPros>> GetPtbPros(Expression<Func<PtbPros, bool>>? whereCond = null)
{
throw new NotImplementedException();
}
public Task<List<PtbProsRif>> GetPtbProsRif(Expression<Func<PtbProsRif, bool>>? whereCond = null)
{
throw new NotImplementedException();
}
public Task<List<StbActivity>> GetStbActivity(Expression<Func<StbActivity, bool>>? whereCond = null)
{
throw new NotImplementedException();
}
public Task<List<VtbCliePersRif>> GetVtbCliePersRif(Expression<Func<VtbCliePersRif, bool>>? whereCond = null)
{
throw new NotImplementedException();
}
public Task<List<VtbDest>> GetVtbDest(Expression<Func<VtbDest, bool>>? whereCond = null)
{
throw new NotImplementedException();
}
public Task<List<ActivityDTO>> GetActivity(Expression<Func<StbActivity, bool>>? whereCond = null)
{
throw new NotImplementedException();
}
}

View File

@@ -0,0 +1,12 @@
using Template.Shared.Core.Interface;
namespace Template.Web.Core.Services;
public class NetworkService : INetworkService
{
public bool IsNetworkAvailable()
{
return true;
}
}

View File

@@ -0,0 +1,26 @@
using Template.Shared.Core.Interface;
namespace Template.Web.Core.Services;
public class SyncDbService : ISyncDbService
{
public Task GetAndSaveActivity(string? dateFilter = null)
{
throw new NotImplementedException();
}
public Task GetAndSaveCommesse(string? dateFilter = null)
{
throw new NotImplementedException();
}
public Task GetAndSaveProspect(string? dateFilter = null)
{
throw new NotImplementedException();
}
public Task GetAndSaveClienti(string? dateFilter = null)
{
throw new NotImplementedException();
}
}

View File

@@ -4,9 +4,9 @@ using Microsoft.AspNetCore.Components.Web;
using Microsoft.AspNetCore.Components.WebAssembly.Hosting;
using MudBlazor.Services;
using Template.Shared.Components;
using Template.Shared.Core.Interface;
using Template.Shared.Core.Services;
using Template.Shared.Interfaces;
using Template.Web.Services;
using Template.Web.Core.Services;
var builder = WebAssemblyHostBuilder.CreateDefault(args);
@@ -14,6 +14,10 @@ builder.Services.AddMudServices();
builder.Services.AddAuthorizationCore();
builder.Services.AddScoped<IFormFactor, FormFactor>();
builder.Services.AddScoped<INetworkService, NetworkService>();
builder.Services.AddScoped<IIntegryApiService, IntegryApiService>();
builder.Services.AddScoped<ISyncDbService, SyncDbService>();
builder.Services.AddScoped<IManageDataService, ManageDataService>();
builder.Services.AddScoped<AppAuthenticationStateProvider>();
builder.Services.AddScoped<AuthenticationStateProvider>(provider => provider.GetRequiredService<AppAuthenticationStateProvider>());

View File

@@ -18,6 +18,16 @@
"ASPNETCORE_ENVIRONMENT": "Development"
}
},
"http debugger": {
"commandName": "Project",
"dotnetRunMessages": true,
"launchBrowser": true,
"inspectUri": "{wsProtocol}://{url.hostname}:{url.port}/_framework/debug/ws-proxy?browser={browserInspectUri}",
"applicationUrl": "http://localhost:5154;http://0.0.0.0:5154",
"environmentVariables": {
"ASPNETCORE_ENVIRONMENT": "Development"
}
},
"https": {
"commandName": "Project",
"dotnetRunMessages": true,

View File

@@ -18,6 +18,7 @@
</ItemGroup>
<ItemGroup>
<Folder Include="Services\" />
<Folder Include="wwwroot\" />
</ItemGroup>