feat: enhance order submission flow and UI improvements

- Updated categories component to improve loading state and category display.
- Modified order section to handle payment submission with event payload.
- Refactored payment form dialog to emit order response on successful payment.
- Adjusted order response model to enforce required fields.
- Improved root component layout and added success dialog for order submission.
- Enhanced sale invoice card component to use new TSP API methods.
- Updated API routes for sale invoices to reflect TSP changes.
- Improved user interface for business activities and partners sections.
- Added card shadow styling for better visual hierarchy.
- Introduced new order submitted dialog component for post-order actions.
- Cleaned up console logs and improved code readability across components.
This commit is contained in:
2026-05-08 18:08:57 +03:30
parent ce40bd8c75
commit a138034c06
40 changed files with 375 additions and 212 deletions
@@ -1,7 +1,5 @@
<ng-template #topbarStart>
<p-button (click)="toggleMenu()" icon="pi pi-bars" outlined size="large" />
<p-button (click)="refresh()" icon="pi pi-bars" outlined size="large" />
<p-button (click)="doPay()" icon="pi pi-bars" outlined size="large" />
</ng-template>
<ng-template #topbarCenter>
@@ -26,11 +24,34 @@
</div>
</ng-template>
@if (loading()) {
<shared-page-loading />
} @else {
<!-- <div class="w-svw h-svh bg-surface-ground flex flex-col gap-4 p-4"> -->
<!-- <div class="w-full flex items-center gap-4 shrink-0 justify-between">
<div
class="h-full relative"
(touchstart)="onTouchStart($event)"
(touchmove)="onTouchMove($event)"
(touchend)="onTouchEnd()"
>
@if (pullDistance() >= 0) {
<div
class="w-full flex justify-center items-center py-2 min-h-10 text-xs text-surface-500 overflow-hidden fixed top-0 inset-x-0 z-1000 translate-y--20px"
[ngStyle]="{ height: pullDistance() + 'px' }"
>
<div
class="inline-flex p-3 rounded-full opacity-0 transition-opacity shadow-xl bg-surface-card"
[ngStyle]="{ opacity: pullDistance() / 100 }"
>
<i
class="pi pi-refresh text-[1.25rem] text-primary"
[ngStyle]="{ fontSize: `${1.25 + pullDistance() * 0.007}rem`, rotate: pullDistance() * 2 + 'deg' }"
></i>
</div>
<!-- [ngStyle]="{ transform: 'scale(1.' + pullDistance() * 10 + ')' }" -->
</div>
}
@if (loading()) {
<shared-page-loading />
} @else {
<!-- <div class="w-svw h-svh bg-surface-ground flex flex-col gap-4 p-4"> -->
<!-- <div class="w-full flex items-center gap-4 shrink-0 justify-between">
<div class="flex gap-2 items-center">
@if (posInfo()) {
<div class="w-10 h-10">
@@ -53,27 +74,28 @@
</div>
</div>
</div> -->
@if (error()) {
@switch (error()?.status) {
@case (412) {
<pos-choose-cards class="h-full" (onChoose)="onChoosePos()" />
}
@default {
<div class="h-full w-full flex items-center justify-center">
<p-card class="border border-surface-border">
<div class="flex flex-col gap-2 items-center justify-between shrink-0">
<i class="pi pi-exclamation-triangle text-6xl! mb-3 text-error" aria-hidden="true"></i>
<span class="text-xl font-semibold mb-2 text-error block"> عدم دسترسی </span>
<p class="inline-block text-base">متاسفانه امکان دسترسی برای کاربر شما فراهم نیست</p>
<button pButton outlined severity="danger" class="mt-5 w-32" (click)="logout()">خروج</button>
</div>
</p-card>
</div>
@if (error()) {
@switch (error()?.status) {
@case (412) {
<pos-choose-cards class="h-full" (onChoose)="onChoosePos()" />
}
@default {
<div class="h-full w-full flex items-center justify-center">
<p-card class="border border-surface-border">
<div class="flex flex-col gap-2 items-center justify-between shrink-0">
<i class="pi pi-exclamation-triangle text-6xl! mb-3 text-error" aria-hidden="true"></i>
<span class="text-xl font-semibold mb-2 text-error block"> عدم دسترسی </span>
<p class="inline-block text-base">متاسفانه امکان دسترسی برای کاربر شما فراهم نیست</p>
<button pButton outlined severity="danger" class="mt-5 w-32" (click)="logout()">خروج</button>
</div>
</p-card>
</div>
}
}
} @else {
<pos-main-menu-sidebar [(visible)]="mainMenuVisible" />
<router-outlet></router-outlet>
}
} @else {
<pos-main-menu-sidebar [(visible)]="mainMenuVisible" />
<router-outlet></router-outlet>
<!-- </div> -->
}
<!-- </div> -->
}
</div>
+34 -20
View File
@@ -3,6 +3,7 @@ import { NativeBridgeService } from '@/core/services';
import { ToastService } from '@/core/services/toast.service';
import { LayoutService } from '@/layout/service/layout.service';
import { PageLoadingComponent } from '@/shared/components/page-loading.component';
import { CommonModule } from '@angular/common';
import {
AfterViewInit,
Component,
@@ -34,6 +35,7 @@ import { PosMainMenuSidebarComponent } from './mainMenuSidebar/main-menu-sidebar
Button,
PosMainMenuSidebarComponent,
Menu,
CommonModule,
],
})
export class PosLayoutComponent implements AfterViewInit {
@@ -84,6 +86,10 @@ export class PosLayoutComponent implements AfterViewInit {
placeholderLogo = images.placeholders.logo;
now = new Date();
private touchStartY = 0;
private pulling = false;
pullDistance = signal(0);
readonly pullThreshold = 80;
getData() {
this.posProfileStore.getData().subscribe({
@@ -101,24 +107,6 @@ export class PosLayoutComponent implements AfterViewInit {
this.getData();
}
doPay() {
// this.nativeBridgeService.pay({
// amount: 10_000,
// id: '1',
// });
this.nativeBridgeService.print({
title: 'salam',
items: [
{
label: 'مجموع قیمت',
value: '10_000',
},
],
});
// @ts-ignore
// window.NativeBridge.pay(12312, 'test');
}
ngOnInit() {
this.layoutService.changeIsFullPage(true);
this.getData();
@@ -137,7 +125,33 @@ export class PosLayoutComponent implements AfterViewInit {
this.layoutService.setTopbarEndSlot(null);
}
refresh() {
window.location.reload();
onTouchStart(event: TouchEvent) {
if (window.scrollY > 0 || event.touches.length !== 1) return;
this.touchStartY = event.touches[0].clientY;
this.pulling = true;
}
onTouchMove(event: TouchEvent) {
if (!this.pulling) return;
const delta = event.touches[0].clientY - this.touchStartY;
if (delta <= 0) {
this.pullDistance.set(0);
return;
}
const damped = Math.min(delta * 0.5, 140);
this.pullDistance.set(damped);
event.preventDefault();
}
onTouchEnd() {
if (!this.pulling) return;
const shouldRefresh = this.pullDistance() >= this.pullThreshold;
this.pulling = false;
this.pullDistance.set(0);
if (shouldRefresh) {
this.layoutService.changeIsFullPage(true);
this.getData();
}
}
}