@if ($orderItemsCount > 0 && user_can('Update Order') && $order->status !== 'paid')
@if (user_can('Add Discount on POS'))
@lang('modules.order.addDiscount')
@endif
@endif
@lang('modules.order.totalItem')
{{ $orderItemsCount }}
@lang('modules.order.subTotal')
@php
$stampDiscountAmount = (float)($order->stamp_discount_amount ?? 0);
$hasFreeStampItems = $order->items()->where('is_free_item_from_stamp', true)->exists();
@endphp
@if($stampDiscountAmount > 0 || $hasFreeStampItems)
@lang('app.stampDiscount')
@if($stampDiscountAmount > 0)
(-{{ currency_format($stampDiscountAmount, $currencyId ?? restaurant()->currency_id) }})
@elseif($hasFreeStampItems)
(@lang('app.freeItem'))
@endif
@endif
{{ currency_format($order->sub_total, $currencyId) }}
@if ($order->loyalty_points_redeemed > 0 && $order->loyalty_discount_amount > 0)
@lang('app.loyaltyDiscount') ({{ number_format($order->loyalty_points_redeemed) }} @lang('app.points'))
-{{ currency_format($order->loyalty_discount_amount, $currencyId ?? restaurant()->currency_id) }}
@endif
@php
$_odDiscDecimals = (int) (optional(currency_format_setting($currencyId ?? null))->no_of_decimal ?? 2);
$_odShowOrderDiscount = (int) ($order->loyalty_points_redeemed ?? 0) === 0
&& round((float) ($order->discount_amount ?? 0), $_odDiscDecimals) > 0;
@endphp
@if ($_odShowOrderDiscount)
@lang('modules.order.discount') @if ($order->discount_type == 'percent')
({{ rtrim(rtrim(number_format($order->discount_value, 2), '0'), '.') }}%)
@endif
@if(user_can('Update Order') && $order->status !== 'paid')
@endif
-{{ currency_format($order->discount_amount, $currencyId) }}
@endif
@php
// Calculate net for charges
$net = $order->sub_total - ($order->discount_amount ?? 0);
@endphp
@foreach ($order->charges as $item)
{{ $item->charge->charge_name }}
@if ($item->charge->charge_type == 'percent')
({{ $item->charge->charge_value }}%)
@endif
@if (!in_array($order->status, ['paid', 'payment_due', 'canceled']))
@endif
@php
// Calculate discounted subtotal for charges (after both regular and loyalty discounts)
$chargeBase = $order->sub_total
- ($order->discount_amount ?? 0)
- ($order->loyalty_discount_amount ?? 0);
@endphp
{{ currency_format($item->charge->getAmount($chargeBase), $currencyId) }}
@endforeach
@if ($order->tip_amount > 0)
@lang('modules.order.tip')
{{ currency_format($order->tip_amount, $currencyId) }}
@endif
@if ($order->order_type === 'delivery' && !is_null($order->delivery_fee))
@lang('modules.delivery.deliveryFee')
@if($order->delivery_fee > 0)
{{ currency_format($order->delivery_fee, $currencyId) }}
@else
@lang('modules.delivery.freeDelivery')
@endif
@endif
@if ($taxMode == 'order')
@php
// Calculate net for display
$net = $order->sub_total - ($order->discount_amount ?? 0);
// Use saved tax_base from database
$taxBase = $order->tax_base ?? ($net + $order->charges->sum(fn($charge) => $charge->charge->getAmount($net)));
@endphp
@foreach ($order->taxes as $item)
@if($item->tax)
{{ $item->tax->tax_name }} ({{ $item->tax->tax_percent }}%)
@php
// Step 1: Calculate discounted subtotal (after both regular and loyalty discounts)
// Loyalty points are always removed from subtotal before calculating tax
$discountedSubtotal = $order->sub_total
- ($order->discount_amount ?? 0)
- ($order->loyalty_discount_amount ?? 0);
// Step 2: Calculate service charges on discounted subtotal
$serviceTotal = 0;
if ($order->charges && $order->charges->count() > 0) {
foreach ($order->charges as $chargeRelation) {
$charge = $chargeRelation->charge;
if ($charge) {
$chargeAmount = $charge->getAmount((float)$discountedSubtotal);
$serviceTotal += (float)$chargeAmount;
}
}
}
// Step 3: Calculate tax_base based on Tax Calculation Base setting
// Check if service charges should be included in tax base
$restaurant = restaurant();
$includeChargesInTaxBase = false;
if ($restaurant && isset($restaurant->include_charges_in_tax_base)) {
$includeChargesInTaxBase = (bool)$restaurant->include_charges_in_tax_base;
}
// Tax base = (subtotal - discounts) + service charges (if enabled)
$taxBase = $includeChargesInTaxBase
? ($discountedSubtotal + $serviceTotal)
: $discountedSubtotal;
$taxBase = max(0, (float)$taxBase);
// Step 4: Calculate tax on tax_base
$taxAmount = ($item->tax->tax_percent / 100) * $taxBase;
@endphp
{{ currency_format($taxAmount, restaurant()->currency_id) }}
@endif
@endforeach
@else
@if($order->total_tax_amount > 0)
@php
$taxTotals = [];
$totalTax = 0;
foreach ($order->items as $item) {
$qty = $item->quantity ?? 1;
$taxBreakdown = is_array($item->tax_breakup) ? $item->tax_breakup : (json_decode($item->tax_breakup, true) ?? []);
if (is_array($taxBreakdown) && !empty($taxBreakdown)) {
foreach ($taxBreakdown as $taxName => $taxInfo) {
// Support both keyed tax format and indexed legacy format.
if (is_array($taxInfo) && array_key_exists('name', $taxInfo)) {
$name = $taxInfo['name'] ?? __('modules.order.tax');
$percent = $taxInfo['percent'] ?? ($taxInfo['rate'] ?? 0);
$amount = (float) ($taxInfo['amount'] ?? 0);
} else {
$name = is_string($taxName) ? $taxName : __('modules.order.tax');
$percent = is_array($taxInfo) ? (float) ($taxInfo['percent'] ?? 0) : 0;
$amount = is_array($taxInfo) ? (float) ($taxInfo['amount'] ?? 0) : 0;
}
if (!isset($taxTotals[$name])) {
$taxTotals[$name] = [
'percent' => $percent,
'amount' => 0,
];
}
$taxTotals[$name]['amount'] += ($amount * $qty);
}
}
// Fallback for records where tax_breakup is missing but tax amount exists.
if (empty($taxBreakdown) && ($item->tax_amount ?? 0) > 0) {
$fallbackPercent = (float) ($item->tax_percentage ?? 0);
$fallbackName = __('modules.order.tax') . ' ' . number_format($fallbackPercent, 2);
if (!isset($taxTotals[$fallbackName])) {
$taxTotals[$fallbackName] = [
'percent' => $fallbackPercent,
'amount' => 0,
];
}
$taxTotals[$fallbackName]['amount'] += (float) $item->tax_amount;
}
$totalTax += $item->tax_amount ?? 0;
}
@endphp
@foreach ($taxTotals as $taxName => $taxInfo)
{{ $taxName }} ({{ $taxInfo['percent'] }}%)
{{ currency_format($taxInfo['amount'], $currencyId) }}
@endforeach
@lang('modules.order.totalTax')
{{ currency_format($totalTax, $currencyId) }}
@endif
@endif
@lang('modules.order.total')
{{ currency_format($order->total, $currencyId) }}
@lang('modules.order.balanceReturn')
@php
$totalBalance = $order->payments->sum('balance');
@endphp
{{ currency_format($totalBalance > 0 ? $totalBalance : 0, $currencyId) }}
@php
$cashCollection = $order->order_type === 'delivery' ? $order->orderCashCollection : null;
@endphp
@if ($cashCollection)
@php
$cashCollectionStatus = $cashCollection->status;
$isCustomerPaid = in_array($cashCollectionStatus, ['collected', 'submitted', 'settled'], true)
|| (float) ($order->amount_paid ?? 0) > 0;
$displayAmount = $isCustomerPaid
? (float) ($order->amount_paid ?? $cashCollection->collected_amount ?? 0)
: (float) ($cashCollection->expected_amount ?? $order->remainingAmount());
$bannerClasses = $isCustomerPaid
? 'border-emerald-200 bg-emerald-50 dark:border-emerald-800 dark:bg-emerald-950/30'
: 'border-amber-200 bg-amber-50 dark:border-amber-800 dark:bg-amber-950/30';
$titleClasses = $isCustomerPaid
? 'text-emerald-800 dark:text-emerald-200'
: 'text-amber-800 dark:text-amber-200';
$descriptionClasses = $isCustomerPaid
? 'text-emerald-700 dark:text-emerald-300'
: 'text-amber-700 dark:text-amber-300';
$labelClasses = $isCustomerPaid
? 'text-emerald-700 dark:text-emerald-300'
: 'text-amber-700 dark:text-amber-300';
$badgeClasses = $isCustomerPaid
? 'border-emerald-300 bg-white text-emerald-700 dark:border-emerald-700 dark:bg-emerald-900/40 dark:text-emerald-200'
: 'border-amber-300 bg-white text-amber-700 dark:border-amber-700 dark:bg-amber-900/40 dark:text-amber-200';
@endphp
@lang($isCustomerPaid ? 'modules.delivery.customerPaymentCollected' : 'modules.delivery.customerPaymentPending')
@lang(
$isCustomerPaid
? 'modules.delivery.customerPaymentCollectedMessage'
: 'modules.delivery.customerPaymentPendingMessage',
['amount' => currency_format($displayAmount, $currencyId)]
)
@lang('modules.delivery.executiveCollectionStatus')
{{ match ($cashCollectionStatus) {
'pending_collection' => __('modules.delivery.pendingCollection'),
'collected' => __('modules.delivery.collected'),
'submitted' => __('modules.delivery.submitted'),
'settled' => __('modules.delivery.settled'),
'rejected' => __('modules.delivery.rejected'),
'not_collected' => __('modules.delivery.not_collected'),
default => Str::headline((string) $cashCollectionStatus),
} }}
@endif
@if ($order->status == 'kot' && !is_null($order->table_id))
@lang('modules.order.addItems')
@lang('modules.order.bill')
@endif
@if (($order->status == 'billed' || $order->status == 'payment_due') && user_can('Update Order'))
@lang('modules.order.addPayment')
@endif
@if($order->split_type && $order->splitOrders->count() > 0)
@lang('modules.order.printSplits')
@else
@lang('app.print')
@endif
@if (in_array($order->status, ['billed', 'payment_due', 'paid']) && user_can('Update Order'))
@lang('app.cancel')
@endif
@if (!in_array($order->status, ['paid', 'payment_due', 'canceled']) && user()->hasRole('Admin_'. user()->restaurant_id))
@lang('app.delete')
@endif
{{ __('app.close') }}