This commit is contained in:
Marwan Alwali 2025-03-04 00:03:29 +03:00
parent 1580e2ad26
commit 9c55bdbe92
85 changed files with 1339 additions and 1357 deletions

View File

@ -25,6 +25,7 @@ from django_ledger.forms.bill import BillModelCreateForm as BillModelCreateFormB
from .models import (
Dealer,
DealersMake,
# Branch,
Vendor,
Schedule,
@ -187,6 +188,7 @@ class CarForm(
"vendor",
]
widgets = {
"id_car_make": forms.Select(attrs={"class": "form-select form-select-sm"}),
"receiving_date": forms.DateTimeInput(attrs={"type": "datetime-local"}),
"remarks": forms.Textarea(attrs={"rows": 2}),
}
@ -930,4 +932,24 @@ class DealerSettingsForm(forms.ModelForm):
fields = "__all__"
class LeadTransferForm(forms.Form):
transfer_to = forms.ModelChoiceField(label="to",queryset=Staff.objects.all())
transfer_to = forms.ModelChoiceField(label="to",queryset=Staff.objects.all())
class DealersMakeForm(forms.Form):
car_makes = forms.ModelMultipleChoiceField(
queryset=CarMake.objects.filter(is_sa_import=True),
widget=forms.CheckboxSelectMultiple(attrs={"class": "car-makes-grid"}),
required=True,
label=_("Select Car Makes")
)
def __init__(self, *args, **kwargs):
self.dealer = kwargs.pop("dealer", None) # Pass dealer instance
super().__init__(*args, **kwargs)
def save(self):
if self.dealer:
DealersMake.objects.filter(dealer=self.dealer).delete()
for car_make in self.cleaned_data["car_makes"]:
DealersMake.objects.create(dealer=self.dealer, car_make=car_make)

View File

@ -0,0 +1,26 @@
# Generated by Django 5.1.6 on 2025-03-03 16:59
import django.db.models.deletion
from django.db import migrations, models
class Migration(migrations.Migration):
dependencies = [
('inventory', '0053_lead_crn_lead_vrn'),
]
operations = [
migrations.CreateModel(
name='DealersMake',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('added_at', models.DateTimeField(auto_now_add=True)),
('car_make', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='car_dealers', to='inventory.carmake')),
('dealer', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='dealer_makes', to='inventory.dealer')),
],
options={
'unique_together': {('dealer', 'car_make')},
},
),
]

View File

@ -53,7 +53,8 @@ class DealerUserManager(UserManager):
return user
# class DealerMakes(models.Model):
# car_make = models.ManyToManyField(CarMake, verbose_name=_("Car Make"), related_name="dealers")
class StaffUserManager(UserManager):
@ -924,6 +925,18 @@ class Dealer(models.Model, LocalizedNameMixin):
# return self.parent_dealer if self.parent_dealer else self
class DealersMake(models.Model):
dealer = models.ForeignKey(Dealer, on_delete=models.CASCADE, related_name="dealer_makes")
car_make = models.ForeignKey(CarMake, on_delete=models.CASCADE, related_name="car_dealers")
added_at = models.DateTimeField(auto_now_add=True)
class Meta:
unique_together = ("dealer", "car_make") # Prevents duplicate entries
def __str__(self):
return f"{self.dealer.name} - {self.car_make.name}"
##############################
# Additional staff types for later

View File

@ -7,7 +7,7 @@ import json
from django_ledger.models import EntityModel
from inventory.utils import get_jwt_token
from inventory.utils import get_jwt_token, get_user_type
from pyvin import VIN
from django.conf import settings
from openai import OpenAI
@ -80,12 +80,3 @@ def elm(vin):
}
print(data)
return data if all([x for x in data.values()]) else None
def get_ledger_data(request):
data = {}
entity = EntityModel.objects.filter(name=request.user.dealer.name).first()
data['bills'] = entity.get_bills()
data['invoices'] = entity.get_invoices()
data['income'] = entity.get_income_statement()
return data

View File

@ -184,7 +184,7 @@ def income_statement_table(context, io_model, from_date=None, to_date=None):
'tx_digest': io_digest.get_io_data()
}
@register.inclusion_tag('django_ledger/financial_statements/tags/cash_flow_statement.html', takes_context=True)
@register.inclusion_tag('ledger/reports/tags/cash_flow_statement.html', takes_context=True)
def cash_flow_statement(context, io_model):
user_model = context['user']
entity_slug = context['view'].kwargs.get('entity_slug')

View File

@ -45,6 +45,7 @@ urlpatterns = [
# Dashboards
# path("user/<int:pk>/settings/", views.UserSettingsView.as_view(), name="user_settings"),
path("dealer/<int:pk>/settings/", views.DealerSettingsView, name="dealer_settings"),
path("dealer/assign-car-makes/", views.assign_car_makes, name="assign_car_makes"),
path("dashboards/manager/", views.ManagerDashboard.as_view(), name="manager_dashboard"),
path("dashboards/sales/", views.SalesDashboard.as_view(), name="sales_dashboard"),
path("test/", views.TestView.as_view(), name="test"),

View File

@ -846,4 +846,5 @@ def get_local_name(self):
"""
if get_language() == 'ar':
return getattr(self, 'arabic_name', None)
return getattr(self, 'name', None)
return getattr(self, 'name', None)

View File

@ -259,57 +259,57 @@ class HomeView(TemplateView):
return redirect("welcome")
return super().dispatch(request, *args, **kwargs)
def get_context_data(self, **kwargs):
context = super().get_context_data(**kwargs)
dealer = get_user_type(self.request)
try:
# Fetch car-related statistics
total_cars = models.Car.objects.filter(dealer=dealer).count()
total_reservations = models.CarReservation.objects.filter(
reserved_until__gte=timezone.now()
).count()
cars_in_house = models.CarLocation.objects.filter(
owner=dealer,
).count()
cars_outside = total_cars - cars_in_house
# Fetch financial statistics
stats = models.CarFinance.objects.aggregate(
total_cost_price=Sum("cost_price"),
total_selling_price=Sum("selling_price"),
)
total_cost_price = stats.get("total_cost_price", 0) or 0
total_selling_price = stats.get("total_selling_price", 0) or 0
total_profit = total_selling_price - total_cost_price
# Prepare context data
context.update({
"dealer": dealer,
"total_cars": total_cars,
"cars_in_house": cars_in_house,
"cars_outside": cars_outside,
"total_reservations": total_reservations,
"total_cost_price": total_cost_price,
"total_selling_price": total_selling_price,
"total_profit": total_profit,
})
except Exception as e:
# Log the error (you can use Django's logging framework)
print(f"Error fetching data: {e}")
# Provide default values in case of an error
context.update({
"dealer": dealer,
"total_cars": 0,
"cars_in_house": 0,
"cars_outside": 0,
"total_reservations": 0,
"total_cost_price": 0,
"total_selling_price": 0,
"total_profit": 0,
})
return context
# def get_context_data(self, **kwargs):
# context = super().get_context_data(**kwargs)
# dealer = get_user_type(self.request)
#
# try:
# # Fetch car-related statistics
# total_cars = models.Car.objects.filter(dealer=dealer).count()
# total_reservations = models.CarReservation.objects.filter(
# reserved_until__gte=timezone.now()
# ).count()
# cars_in_house = models.CarLocation.objects.filter(
# owner=dealer,
# ).count()
# cars_outside = total_cars - cars_in_house
#
# # Fetch financial statistics
# stats = models.CarFinance.objects.aggregate(
# total_cost_price=Sum("cost_price"),
# total_selling_price=Sum("selling_price"),
# )
# total_cost_price = stats.get("total_cost_price", 0) or 0
# total_selling_price = stats.get("total_selling_price", 0) or 0
# total_profit = total_selling_price - total_cost_price
#
# # Prepare context data
# context.update({
# "dealer": dealer,
# "total_cars": total_cars,
# "cars_in_house": cars_in_house,
# "cars_outside": cars_outside,
# "total_reservations": total_reservations,
# "total_cost_price": total_cost_price,
# "total_selling_price": total_selling_price,
# "total_profit": total_profit,
# })
#
# except Exception as e:
# # Log the error (you can use Django's logging framework)
# print(f"Error fetching data: {e}")
# # Provide default values in case of an error
# context.update({
# "dealer": dealer,
# "total_cars": 0,
# "cars_in_house": 0,
# "cars_outside": 0,
# "total_reservations": 0,
# "total_cost_price": 0,
# "total_selling_price": 0,
# "total_profit": 0,
# })
# return context
class TestView(TemplateView):
template_name = "inventory/cars_list_api.html"
@ -318,9 +318,7 @@ class ManagerDashboard(LoginRequiredMixin, TemplateView):
template_name = "dashboards/manager.html"
def dispatch(self, request, *args, **kwargs):
if (
not request.user.is_authenticated
):
if not request.user.is_authenticated:
return redirect("welcome")
return super().dispatch(request, *args, **kwargs)
@ -358,6 +356,8 @@ class ManagerDashboard(LoginRequiredMixin, TemplateView):
total_leads = models.Lead.objects.filter(dealer=dealer).count()
invoices = entity.get_invoices().count()
customers = entity.get_customers().count()
purchase_orders = entity.get_purchase_orders().count()
estimates = entity.get_estimates().count()
context["dealer"] = dealer
context["total_cars"] = total_cars
@ -377,6 +377,13 @@ class ManagerDashboard(LoginRequiredMixin, TemplateView):
context['damaged_cars'] = damaged_cars
context['transfer_cars'] = transfer_cars
context['car'] = json.dumps(car_by_make)
context['customers'] = customers
context['staff'] = staff
context['total_leads'] = total_leads
context['invoices'] = invoices
context['estimates'] = estimates
context['purchase_orders'] = purchase_orders
return context
@ -428,10 +435,10 @@ class SalesDashboard(LoginRequiredMixin, TemplateView):
context['damaged_cars'] = damaged_cars
context['transfer_cars'] = transfer_cars
context['car'] = json.dumps(car_by_make)
context['customers'] = customers
context['staff'] = staff
context['total_leads'] = total_leads
context['invoices'] = invoices
# context['customers'] = customers
# context['staff'] = staff
# context['total_leads'] = total_leads
# context['invoices'] = invoices
return context
@ -1206,13 +1213,20 @@ class DealerDetailView(LoginRequiredMixin, DetailView):
def get_context_data(self, **kwargs):
context = super().get_context_data(**kwargs)
dealer = self.object
car_makes = models.CarMake.objects.filter(car_dealers__dealer=dealer)
# Fetch current staff count from the annotated queryset
staff_count = dealer.staff_count
cars_count = models.Car.objects.filter(dealer=dealer).count()
# Get the quota value dynamically
quota_dict = get_user_quota(dealer.user)
allowed_users = quota_dict.get("Users", None) # Fetch quota or default to None
allowed_users = quota_dict.get("Users", None)
allowed_cars = quota_dict.get("Cars", None)
context["car_makes"] = car_makes
context["staff_count"] = staff_count
context["cars_count"] = cars_count
context["allowed_users"] = allowed_users
context["allowed_cars"] = allowed_cars
context["quota_display"] = f"{staff_count}/{allowed_users}" if allowed_users is not None else "N/A"
return context
@ -2296,6 +2310,7 @@ class EstimatePreviewView(DetailView):
template_name = "sales/estimates/estimate_preview.html"
def get_context_data(self, **kwargs):
dealer = get_user_type(self.request)
estimate = kwargs.get("object")
if estimate.get_itemtxs_data():
data = get_financial_values(estimate)
@ -2305,6 +2320,7 @@ class EstimatePreviewView(DetailView):
kwargs["discount_amount"] = data["discount_amount"]
kwargs["vat"] = data["vat"]
kwargs["additional_services"] = data["additional_services"]
kwargs["dealer"] = dealer
return super().get_context_data(**kwargs)
@ -2342,6 +2358,7 @@ def estimate_mark_as(request, pk):
messages.error(request, _("Estimate is not ready for cancelation"))
return redirect("estimate_detail", pk=estimate.pk)
estimate.mark_as_canceled()
messages.success(request, _("Estimate canceled successfully."))
estimate.save()
messages.success(request, "Estimate marked as " + mark.upper())
@ -3478,53 +3495,50 @@ class OrderListView(ListView):
# email
@login_required
def send_email_view(request, pk):
dealer = get_user_type(request)
estimate = get_object_or_404(EstimateModel, pk=pk)
if request.method == "POST":
if not estimate.get_itemtxs_data()[0]:
messages.error(request, _("Estimate has no items"))
return redirect("estimate_detail", pk=estimate.pk)
send_email(
"manager@tenhal.com",
request.POST.get("to"),
request.POST.get("subject"),
request.POST.get("message"),
)
estimate.mark_as_review()
messages.success(request, _("Email sent successfully!"))
if not estimate.get_itemtxs_data()[0]:
messages.error(request, _("Quotation has no items"))
return redirect("estimate_detail", pk=estimate.pk)
link = reverse_lazy("estimate_preview", kwargs={"pk": estimate.pk})
link = request.build_absolute_uri(reverse_lazy("estimate_preview", kwargs={"pk": estimate.pk}))
msg = f"""
السلام عليكم
Dear {estimate.customer.customer_name},
أود أن أشارككم تقدير المشروع الذي ناقشناه. يرجى العثور على الوثيقة التفصيلية للمقترح المرفقة.
أود أن أشارككم عرض السعر.
I hope this email finds you well. I wanted to share with you the estimate for the project we discussed. Please find the detailed estimate document attached.
I wanted to share with you the quotation.
يرجى مراجعة المقترح وإعلامي إذا كانت لديك أي أسئلة أو مخاوف. إذا كانت كل شيء يبدو جيدًا، يمكننا المضي قدمًا في المشروع.
يرجى مراجعة عرض السعر وإعلامي إذا كانت لديك أي استفسارات أو ملاحظات. إذا كان كل شيء على ما يرام، يمكننا المتابعة في الإجراءات.
Please review the estimate and let me know if you have any questions or concerns. If everything looks good, we can proceed with the project.
Please review the quotation and let me know if you have any questions or concerns. If everything looks good, we can proceed with the process.
Estimate Link:
رابط عرض السعر:
{link}
شكراً لاهتمامكم بهذا الأمر.
Thank you for your attention to this matter.
تحياتي,
Best regards,
[Your Name]
[Your Position]
[Your Company]
[Your Contact Information]
{dealer.get_local_name}
{dealer.phone_number}
هيكل | Haikal
"""
return render(
request,
"sales/estimates/estimate_send.html",
{"estimate": estimate, "message": msg},
send_email(
settings.DEFAULT_FROM_EMAIL,
estimate.customer.email,
_("Quotation"),
msg,
)
estimate.mark_as_review()
messages.success(request, _("Email sent successfully!"))
return redirect("estimate_detail", pk=estimate.pk)
# errors
def custom_page_not_found_view(request, exception):
@ -3896,4 +3910,20 @@ def schedule_cancel(request,pk):
schedule.save()
response = HttpResponse()
response.status_code = 200
return response
return response
@login_required
def assign_car_makes(request):
dealer = get_user_type(request)
if request.method == "POST":
form = forms.DealersMakeForm(request.POST, dealer=dealer)
if form.is_valid():
form.save()
return redirect("dealer_detail", pk=dealer.pk)
else:
# Pre-fill the form with existing selections
existing_car_makes = models.DealersMake.objects.filter(dealer=dealer).values_list("car_make", flat=True)
form = forms.DealersMakeForm(initial={"car_makes": existing_car_makes}, dealer=dealer)
return render(request, "dealers/assign_car_makes.html", {"form": form})

Binary file not shown.

File diff suppressed because it is too large Load Diff

BIN
static/.DS_Store vendored

Binary file not shown.

Binary file not shown.

View File

@ -1,4 +1,13 @@
@font-face {
font-family: 'SaudiRiyalFont';
src: url('/static/assets/fonts/SaudiRiyalFont.ttf') format('truetype');
font-weight: normal;
font-style: normal;
}
.currency {
font-family: 'SaudiRiyalFont', sans-serif;
}
.color-div {
width: 64px;

View File

@ -1259,6 +1259,7 @@ progress {
font-weight: 600;
}
.display-1 {
font-size: calc(1.6018371582rem + 4.2220458984vw);
font-weight: 400;

Binary file not shown.

After

Width:  |  Height:  |  Size: 109 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 142 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 37 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 16 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 56 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 12 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 64 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 12 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 78 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 77 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 79 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 149 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 23 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 47 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 33 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 31 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 92 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 16 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 76 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 21 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 15 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 38 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 31 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 40 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 64 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 26 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 61 KiB

File diff suppressed because one or more lines are too long

1
static/vendors/zxing/index.min.js vendored Normal file

File diff suppressed because one or more lines are too long

View File

@ -85,9 +85,9 @@
<!-- Currency Field -->
<div class="form-floating mb-3">
<select name="currency" id="id_currency" class="form-select form-control-sm" >
<option value="SAR">{{ CURRENCY }}</option>
<option class="currency" value="SAR">{{ CURRENCY }}</option>
</select>
<label for="id_currency">{{ _("Currency") }}</label>
<label for="id_currency"><span class="currency"> {{ CURRENCY }}</span></label>
{% if form.currency.errors %}
<div class="alert alert-danger mt-2">
{{ form.currency.errors }}

View File

@ -39,7 +39,7 @@
<h3 class="fw-bolder mb-2 line-clamp-1">{{ opportunity.customer.customer_name }}</h3>
<div class="d-flex align-items-center mb-4">
{% if opportunity.car.finances %}
<h5 class="mb-0 me-4">{{ opportunity.car.finances.total }} <span class="fw-light">{{ _("SAR") }}</span></h5>
<h5 class="mb-0 me-4">{{ opportunity.car.finances.total }} <span class="fw-light"><span class="currency">{{ CURRENCY }}</span></span></h5>
{% endif %}
</div>
<div class="d-md-flex d-xl-block align-items-center justify-content-between mb-5">

View File

@ -125,7 +125,7 @@
<p class="fw-semibold mb-0" >{{ _("Quotation") }}-<span class="fs-10 fw-medium">{{ estimate.estimate_number }}</span></p>
</td>
<td class="total align-middle text-end fw-semibold pe-7 text-body-highlight">{{ estimate.revenue_estimate|currency_format }}</td>
<td class="total align-middle text-end fw-semibold pe-7 text-body-highlight">{{ estimate.revenue_estimate|currency_format }} <span class="currency"> {{ CURRENCY }}</span> </td>
<td class="payment_status align-middle white-space-nowrap text-start fw-bold text-body-tertiary">
</td>
@ -147,7 +147,7 @@
<p class="fw-semibold mb-0" >{{ _("Invoice") }}-<span class="fs-10 fw-medium">{{ invoice.invoice_number }}</span></p>
</td>
<td class="total align-middle text-end fw-semibold pe-7 text-body-highlight">{{ invoice.amount_paid|currency_format }}</td>
<td class="total align-middle text-end fw-semibold pe-7 text-body-highlight">{{ invoice.amount_paid|currency_format }}<span class="currency"> {{ CURRENCY }}</span> </td>
<td class="payment_status align-middle white-space-nowrap text-start fw-bold text-body-tertiary">
{% if invoice.is_paid %}
<span class="badge badge-phoenix fs-10 badge-phoenix-success">

View File

@ -2,14 +2,15 @@
{% load i18n static custom_filters django_ledger%}
{% block content %}
<div class="row justify-content-between">
<div class="col-12 col-lg-6">
<div class="row g-2">
<div class="row justify-content-between mb-2">
<h3 class="fs-4 fs-md-4 fs-xl-4 fw-black mb-4">
<span class="text-gradient-info me-3">{{ dealer.get_local_name }}</span>
</h3>
<div class="row justify-content-between">
<span class="text-gradient-info me-3">{{ dealer.get_local_name }}</span>
</h3>
<p><span class="badge badge-phoenix badge-phoenix-success me-2 fs-10">
<span class="fs-10 text-body-secondary me-1">{{ _("As of")}}</span>{% now "SHORT_DATETIME_FORMAT" %}
</span></p>
</div>
<div class="row justify-content-between mb-2">
<div class="col-6 col-md-4 col-xxl-2 text-center border-translucent border-start-xxl border-end-xxl-0 border-bottom-xxl-0 border-end border-bottom pb-4 pb-xxl-0 ">
<span class="uil fs-5 lh-1 uil-users-alt text-success"></span>
<h4 class="fs-6 pt-3">{{ staff }}</h4>
@ -17,7 +18,7 @@
</div>
<div class="col-6 col-md-4 col-xxl-2 text-center border-translucent border-start-xxl border-end-xxl-0 border-bottom-xxl-0 border-end border-bottom pb-4 pb-xxl-0 ">
<span class="uil fs-5 lh-1 uil-bolt-alt text-primary"></span>
<h4 class="fs-6 pt-3">{{ total_leads }}</h4>
<a href="{% url 'lead_list' %}"><h4 class="fs-6 pt-3">{{ total_leads }}</h4></a>
<p class="fs-9 mb-0">{{ _("Leads")}}</p>
</div>
<div class="col-6 col-md-4 col-xxl-2 text-center border-translucent border-start-xxl border-end-xxl-0 border-bottom-xxl-0 border-end border-bottom pb-4 pb-xxl-0 ">
@ -30,7 +31,67 @@
<h4 class="fs-6 pt-3">{{ invoices }}</h4>
<p class="fs-9 mb-0">{{ _("Invoices")}}</p>
</div>
<div class="col-6 col-md-4 col-xxl-2 text-center border-translucent border-start-xxl border-end-xxl-0 border-bottom-xxl-0 border-end border-bottom pb-4 pb-xxl-0 ">
<span class="uil fs-5 lh-1 uil-comment-alt-question text-success-dark"></span>
<h4 class="fs-6 pt-3">{{ estimates }}</h4>
<p class="fs-9 mb-0">{{ _("Quotations")}}</p>
</div>
<div class="col-6 col-md-4 col-xxl-2 text-center border-translucent border-start-xxl border-end-xxl-0 border-bottom-xxl-0 border-end border-bottom pb-4 pb-xxl-0 ">
<span class="uil fs-5 lh-1 uil-receipt-alt text-secondary"></span>
<h4 class="fs-6 pt-3">{{ purchase_orders }}</h4>
<p class="fs-9 mb-0">{{ _("Purchase Orders")}}</p>
</div>
</div>
<div class="row g-3 pe-xxl-3 my-3">
<div class="col-12 col-xl-6 col-xxl-12">
<div class="row">
<div class="col-4 col-xl-12 col-xxl-4 border-end border-end-xl-0 border-end-xxl pb-4 pt-4 pt-xl-0 pt-xxl-4 pe-4 pe-sm-5 pe-xl-0 pe-xxl-5">
<h4 class="text-body mb-4">{% trans 'inventory'|upper %}</h4>
<div class="d-md-flex flex-between-center">
<div id="car-chart-by-make" class="order-sm-0 order-md-1" style="height:64px;width: 128px;"></div>
<div class="mt-4 mt-md-0">
<h1 class="text-body-highlight">{{ total_cars }} <span class="fs-6 text-body-highlight">{{ _("Car") }}</span></h1>
</div>
</div>
</div>
<div class="col-4 col-xl-12 col-xxl-4 border-end border-end-xl-0 border-end-xxl py-4 ps-4 ps-sm-5 ps-xl-0 ps-xxl-5">
<h4 class="text-body mb-4">{% trans 'inventory value'|upper %}</h4>
<div class="d-md-flex flex-between-center">
<div class="d-md-flex align-items-center gap-2">
<span class="fas fa-money-check-alt fs-5 text-success-light dark__text-opacity-75"></span>
<div class="d-flex d-md-block gap-2 align-items-center mt-1 mt-md-0">
<p class="fs-9 mb-0 mb-md-2 text-body-tertiary text-nowrap"></p>
<h4 class="text-body-highlight mb-0"></h4>
</div>
</div>
<div class="mt-3 mt-md-0">
<h3 class="text-body-highlight mb-2">{{ total_selling_price|currency_format }} <span class="currency"> {{ CURRENCY }}</span></h3>
</div>
</div>
</div>
<div class="col-4 col-xl-12 col-xxl-4 border-end border-end-xl-0 border-end-xxl py-4 pe-4 pe-sm-5 pe-xl-0 pe-xxl-5">
<h4 class="text-body mb-4">{% trans "Profits"|upper %}</h4>
<div class="d-md-flex flex-between-center">
<div class="d-md-flex align-items-center gap-2">
<span class="fa-solid fa-money-bill-trend-up fs-5 text-warning-light dark__text-opacity-75" data-bs-theme="light"></span>
<div class="d-flex d-md-block gap-2 align-items-center mt-1 mt-md-0">
<p class="fs-9 mb-0 mb-md-2 text-body-tertiary text-nowrap"></p>
<h4 class="text-body-highlight mb-0"></h4>
</div>
</div>
<div class="mt-3 mt-md-0">
<h3 class="text-body-highlight mb-2">{{ total_profit|currency_format }}<span class="currency"> {{ CURRENCY }}</span></h3>
</div>
</div>
</div>
</div>
</div>
</div>
<div class="row justify-content-between">
<div class="col-12 col-lg-12">
<div class="row">
<div class="card mb-3">
<div class="bg-holder" style="background-image:url({% static 'images/bg/38.png' %});background-position:left bottom;background-size:auto;"></div>
@ -78,194 +139,18 @@
</div>
<div class="col-sm-5 col-md-4 col-xxl-4 my-3 my-sm-0">
<div class="position-relative d-flex flex-center mb-sm-4 mb-xl-0 echart-cars-by-status-container mt-sm-7 mt-lg-4 mt-xl-0">
<div id="echart-cars-by-status" style="min-height:245px;width:100%"></div>
<div class="position-absolute rounded-circle bg-primary-subtle top-50 start-50 translate-middle d-flex flex-center" style="height:100px; width:100px;">
<h3 class="mb-0 text-primary-dark fw-bolder" data-label="data-label"></h3>
</div>
<div id="echart-cars-by-status" class="mx-auto mt-3 mt-md-0 mt-xl-3 mt-xxl-0" style="min-height:245px;width:100%"></div>
</div>
</div>
</div>
</div>
</div>
<div class="row g-2">
<div class="col-12 mb-8">
<div class="mb-3">
<h3>{{ _("New Leads and Customers")}}</h3>
<p class="text-body-tertiary mb-0">{{ _("Payment received across all channels")}}</p>
</div>
<div class="row g-6">
<div class="col-xl-6 mb-2 mb-sm-0">
<div class="d-flex align-items-center"><span class="me-2 text-info" data-feather="users" style="min-height:24px; width:24px"></span>
<h4 class="text-body-tertiary mb-0">{{ _("New Customers")}} :
<span class="text-body-emphasis"> 42</span>
</h4>
<span class="badge badge-phoenix fs-10 badge-phoenix-success d-inline-flex align-items-center ms-2">
<span class="badge-label d-inline-block lh-base">+24.5%</span>
<span class="ms-1 fa-solid fa-caret-up d-inline-block lh-1"></span>
</span>
</div>
<div class="pb-0 pt-4">
<div class="echarts-new-users" style="min-height:110px;width:100%;"></div>
</div>
</div>
<div class="col-md-6">
<div class="d-flex align-items-center"><span class="me-2 text-primary" data-feather="zap" style="height:24px; width:24px"></span>
<h4 class="text-body-tertiary mb-0">{{ _("New Leads")}} :<span class="text-body-emphasis"> 45</span></h4>
<span class="badge badge-phoenix fs-10 badge-phoenix-success d-inline-flex align-items-center ms-2">
<span class="badge-label d-inline-block lh-base">+30.5%</span>
<span class="ms-1 fa-solid fa-caret-up d-inline-block lh-1"></span>
</span>
</div>
<div class="pb-0 pt-4">
<div class="echarts-new-leads" style="min-height:110px;width:100%;"></div>
</div>
</div>
</div>
</div>
</div>
</div>
<div class="col-12 col-lg-6">
<div class="row g-3 pe-xxl-3">
<div class="col-12 col-xl-6 col-xxl-12">
<div class="row">
<div class="col-6 col-xl-12 col-xxl-6 border-bottom border-end border-end-xl-0 border-end-xxl pb-4 pt-4 pt-xl-0 pt-xxl-4 pe-4 pe-sm-5 pe-xl-0 pe-xxl-5">
<h4 class="text-body mb-4">{% trans 'inventory'|upper %}</h4>
<div class="d-md-flex flex-between-center">
<div id="car-chart-by-make" class="order-sm-0 order-md-1" style="height:64px;width: 128px;"></div>
<div class="mt-4 mt-md-0">
<h1 class="text-body-highlight mb-2">{{ total_cars }}</h1>
<span class="badge badge-phoenix badge-phoenix-primary me-2 fs-10"> <span class="fs-10 text-body-secondary me-1">{{ _("As of")}}</span>{% now "SHORT_DATETIME_FORMAT" %}</span>
</div>
</div>
</div>
<div class="col-6 col-xl-12 col-xxl-6 border-bottom py-4 ps-4 ps-sm-5 ps-xl-0 ps-xxl-5">
<h4 class="text-body mb-4">{% trans 'inventory value'|upper %}</h4>
<div class="d-md-flex flex-between-center">
<div class="d-md-flex align-items-center gap-2 order-sm-0 order-md-1 fa-2x align-items-center">
<i class="fas fa-money-check-alt fs-4 text-success-light dark__text-opacity-75"></i>
<div class="d-flex d-md-block gap-2 align-items-center mt-1 mt-md-0">
<p class="fs-9 mb-0 mb-md-2 text-body-tertiary text-nowrap"></p>
<h4 class="text-body-highlight mb-0"></h4>
</div>
</div>
<div class="mt-3 mt-md-0">
<h3 class="text-body-highlight mb-2">{{ total_selling_price|currency_format }} {{ CURRENCY }}</h3>
</div>
</div>
</div>
<div class="col-6 col-xl-12 col-xxl-6 border-bottom-xl border-bottom-xxl-0 border-end border-end-xl-0 border-end-xxl py-4 pe-4 pe-sm-5 pe-xl-0 pe-xxl-5">
<h4 class="text-body mb-4">{% trans "Profits"|upper %}</h4>
<div class="d-md-flex flex-between-center">
<div class="d-md-flex align-items-center gap-2 order-sm-0 order-md-1">
<span class="fa-solid fa-money-bill-trend-up fs-4 text-warning-light dark__text-opacity-75" data-bs-theme="light"></span>
<div class="d-flex d-md-block gap-2 align-items-center mt-1 mt-md-0">
<p class="fs-9 mb-0 mb-md-2 text-body-tertiary text-nowrap"></p>
<h4 class="text-body-highlight mb-0"></h4>
</div>
</div>
<div class="mt-3 mt-md-0">
<h3 class="text-body-highlight mb-2">{{ total_profit|currency_format }} {{ CURRENCY }}</h3>
</div>
</div>
</div>
<div class="col-6 col-xl-12 col-xxl-6 py-4 ps-4 ps-sm-5 ps-xl-0 ps-xxl-5">
<h5 class="text-body mb-4">{{ _("Canceled Invoices")}}</h5>
<div class="d-md-flex flex-between-center">
<div class="chart-cancel-booking order-sm-0 order-md-1" style="height:54px; width:78px"></div>
<div class="mt-3 mt-md-0">
<h3 class="text-body-highlight mb-2">120.00</h3>
<span class="badge badge-phoenix badge-phoenix-danger me-2 fs-10"> <span class="fa-solid fa-plus me-1"></span>5.76%</span>
<span class="fs-9 text-body-secondary d-block d-sm-inline mt-1">{{ _("From last month")}}</span>
</div>
</div>
</div>
</div>
</div>
<div class="col-12 col-xl-6 col-xxl-12 mb-3">
<div class="card h-100">
<div class="card-header pb-3">
<div class="row justify-content-between g-3">
<div class="col-auto">
<h3 class="text-body-highlight">{{ _("Gross Profit")}}</h3>
<p class="mb-0">Annual income according to the board</p>
</div>
</div>
</div>
<div class="card-body">
<div class="row align-items-center h-100 gy-5">
<div class="col-12 col-md-auto col-xl-12 col-xxl-auto order-md-1 order-xl-0 order-xxl-1 px-md-8 px-xl-6">
<div class="echart-gross-profit mx-auto mt-3 mt-md-0 mt-xl-3 mt-xxl-0" style="width: 250px; height: 250px"></div>
</div>
<div class="col-12 col-md-auto col-xl-12 col-xxl-auto flex-1 h-md-100">
<div class="d-flex flex-column justify-content-between h-md-100 h-xl-auto h-xxl-100">
<div class="d-flex align-items-center justify-content-between">
<div class="d-flex gap-2">
<div class="bullet-item bg-primary-light" data-bs-theme="light"></div>
<div>
<h6 class="mb-0 text-body fw-semibold mb-2">Flight</h6>
<h5 class="mb-0 text-body">$162,791,400</h5>
</div>
</div>
<div class="d-flex align-items-center gap-2 text-primary">
<span class="fw-bold" data-feather="trending-up" style="width: 24px; height: 24px"></span>
<p class="mb-0 fw-bold">15.50%</p>
</div>
</div>
<hr />
<div class="d-flex align-items-center justify-content-between">
<div class="d-flex gap-2">
<div class="bullet-item bg-info-light" data-bs-theme="light"></div>
<div>
<h6 class="mb-0 text-body fw-semibold mb-2">Flight (Package)</h6>
<h5 class="mb-0 text-body">$135,659,500</h5>
</div>
</div>
<div class="d-flex align-items-center gap-2 text-danger">
<span class="fw-bold" data-feather="trending-down" style="width: 24px; height: 24px"></span>
<p class="mb-0 fw-bold">11.09%</p>
</div>
</div>
<hr />
<div class="d-flex align-items-center justify-content-between">
<div class="d-flex gap-2">
<div class="bullet-item bg-warning-light" data-bs-theme="light"></div>
<div>
<h6 class="mb-0 text-body fw-semibold mb-2">Hotel</h6>
<h5 class="mb-0 text-body">$271,319,000</h5>
</div>
</div>
<div class="d-flex align-items-center gap-2 text-warning">
<span class="fw-bold" data-feather="trending-up" style="width: 24px; height: 24px"></span>
<p class="mb-0 fw-bold">29.98%</p>
</div>
</div>
<hr />
<div class="d-flex align-items-center justify-content-between">
<div class="d-flex gap-2">
<div class="bullet-item bg-success-light" data-bs-theme="light"></div>
<div>
<h6 class="mb-0 text-body fw-semibold mb-2">Hotel (Package)</h6>
<h5 class="mb-0 text-body">$162,791,400</h5>
</div>
</div>
<div class="d-flex align-items-center gap-2 text-success">
<span class="fw-bold" data-feather="trending-up" style="width: 24px; height: 24px"></span>
<p class="mb-0 fw-bold">03.90%</p>
</div>
</div>
<hr class="d-none" />
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
@ -274,9 +159,7 @@
document.addEventListener("DOMContentLoaded", function () {
/* Car Chart By Make */
const getColor = (name, dom = document.documentElement) => {
return getComputedStyle(dom).getPropertyValue(`--phoenix-${name}`).trim();
};
const { getColor, rgbaColor } = window.phoenix.utils;
const handleTooltipPosition = ([pos, , dom, , size]) => {
// only for mobile device
if (window.innerWidth <= 540) {
@ -348,9 +231,7 @@ document.addEventListener("DOMContentLoaded", function () {
car_chart.setOption(option);
/* Car Status Chart */
const chartElContainer = document.querySelector('.echart-cars-by-status-container');
const car_status = echarts.init(document.getElementById('echart-cars-by-status'));
const chartLabel = chartElContainer.querySelector('[data-label]');
const data = [
{value: {{available_cars}}, name: '{{ _("Available") }}'},
{value: {{sold_cars}}, name: '{{ _("Sold")}}'},
@ -359,24 +240,21 @@ document.addEventListener("DOMContentLoaded", function () {
{value: {{hold_cars}}, name: '{{ _("Hold") }}'},
{value: {{damaged_cars}}, name: '{{ _("Damaged") }}'}
];
const totalCars = data.reduce((acc, val) => val.value + acc, 0);
if (chartLabel) {
chartLabel.innerHTML = totalCars;
}
option = {
color: [
getColor('success'),
getColor('warning'),
getColor('danger'),
getColor('primary'),
getColor('warning-lighter'),
getColor('secondary-dark')
rgbaColor(getColor('success'),0.7),
rgbaColor(getColor('warning'),0.7),
rgbaColor(getColor('danger'),0.7),
rgbaColor(getColor('primary'),0.7),
rgbaColor(getColor('warning-light'),0.7),
rgbaColor(getColor('secondary-light'),0.7),
],
tooltip: {
trigger: 'item',
padding: [7, 10],
backgroundColor: getColor('body-highlight-bg'),
borderColor: getColor('border-color'),
borderColor: getColor('body-bg'),
textStyle: {color: getColor('light-text-emphasis')},
borderWidth: 1,
transitionDuration: 0,

View File

@ -132,7 +132,7 @@
</div>
</div>
<div class="mt-3 mt-md-0">
<h3 class="text-body-highlight mb-2">{{ total_selling_price|currency_format }} {{ CURRENCY }}</h3>
<h3 class="text-body-highlight mb-2">{{ total_selling_price|currency_format }} <span class="currency"> {{ CURRENCY }}</span> </h3>
</div>
</div>
</div>
@ -147,7 +147,7 @@
</div>
</div>
<div class="mt-3 mt-md-0">
<h3 class="text-body-highlight mb-2">{{ total_profit|currency_format }} {{ CURRENCY }}</h3>
<h3 class="text-body-highlight mb-2">{{ total_profit|currency_format }} <span class="currency"> {{ CURRENCY }}</span> </h3>
</div>
</div>
</div>

View File

@ -0,0 +1,25 @@
{% extends "base.html" %}
{% load crispy_forms_filters %}
{% block content %}
<style>
.car-makes-grid {
display: grid;
grid-template-columns: repeat(5, 1fr);
gap: 16px;
}
.car-makes-grid label {
display: flex;
align-items: center;
}
</style>
<h2>{{ _("Select Car Makes You Sell")}}</h2>
<form method="post">
{% csrf_token %}
<div class="car-makes-grid">
{{ form.car_makes }}
</div>
<button class="btn btn-phoenix-success btn-sm" type="submit">{{ _("Save") }}</button>
</form>
{% endblock %}

View File

@ -44,10 +44,7 @@
<h6 class="mb-2 text-body-secondary">{% trans 'last login'|capfirst %}</h6>
<h4 class="fs-7 text-body-highlight mb-0">{{ dealer.user.last_login|date:"D M d, Y H:i" }}</h4>
</div>
<div class="text-end">
<h6 class="mb-2 text-body-secondary">{% trans 'Total users'|capfirst %}</h6>
<h4 class="fs-7 text-body-highlight mb-0">{{ dealer.staff_count }} / {{ allowed_users }}</h4>
</div>
</div>
</div>
</div>
@ -104,7 +101,7 @@
</div>
<p class="fs-9 text-body-tertiary">{% trans 'Active until' %}: {{ dealer.user.userplan.expire}}</p>
<div class="d-flex align-items-end mb-md-5 mb-lg-0">
<h4 class="fw-bolder me-1">{{ dealer.user.userplan.plan.planpricing_set.first.price }} {{ CURRENCY }}</h4>
<h4 class="fw-bolder me-1">{{ dealer.user.userplan.plan.planpricing_set.first.price }}<span class="currency"> {{ CURRENCY }}</span></h4>
<h5 class="fs-9 fw-normal text-body-tertiary ms-1">{{ _("Per month")}}</h5>
</div>
</div>
@ -131,12 +128,42 @@
</div>
</div>
<div class="col-12 col-lg-3">
<div class="card h-100">
<div class="card h-100">
<div class="bg-holder" style="background-image:url({% static 'images/bg/bg-2.png' %});background-position:left bottom;background-size:auto;"></div>
<div class="card-body d-flex flex-column justify-content-between position-relative">
<div class="d-flex justify-content-between">
<div class="mb-5 mb-md-0 mb-lg-5">
<div class="card-body d-flex flex-column justify-content-between position-relative align-items-end">
<div class="d-flex justify-content-between ">
<div class="text-center me-3">
<span class="uil-users-alt fs-4 text-primary-light"></span>
<h6 class="mb-2 text-body-secondary">{% trans 'Total users'|capfirst %}</h6>
<h4 class="fs-7 text-body-highlight mb-0">{{ dealer.staff_count }} / {{ allowed_users }}</h4>
</div>
<div class="text-center">
<span class="uil-car-sideview fs-4 text-success-light"></span>
<h6 class="mb-2 text-body-secondary">{% trans 'Total cars'|capfirst %}</h6>
<h4 class="fs-7 text-body-highlight mb-0">{{ cars_count }} / {{ allowed_cars }}</h4>
</div>
</div>
</div>
</div>
</div>
<div class="col-12 col-lg-3">
<div class="card h-100">
<div class="bg-holder" style="background-image:url({% static 'images/bg/bg-left-20.png' %});background-position:left bottom;background-size:auto;"></div>
<div class="card-body d-flex flex-column justify-content-between position-relative align-items-end">
<div class="d-flex justify-content-between ">
<div class="text-center me-3">
<div class="row">
{% for make in car_makes %}
<div class="col-auto">
{% if make.logo %}
<img src="{{ make.logo.url }}" alt="{{ make.get_local_name }}" class="rounded-circle" style="height: 64px;" />
{% endif %}
<p>{{ make.get_local_name }}</p>
</div>
{% endfor %}
</div>
</div>
</div>
</div>
</div>

View File

@ -1,11 +1,17 @@
{% load i18n %}
<footer class="footer position-absolute">
{% load i18n static %}
<footer class="footer position-absolute fs-9">
<div class="row g-0 justify-content-between align-items-center h-100">
<div class="col-12 col-sm-auto text-center">
<p class="mb-0 mt-2 mt-sm-0 text-body">{% trans 'All right reserved' %}:<span class="d-none d-sm-inline-block"></span><span class="d-none d-sm-inline-block mx-1">|</span><br class="d-sm-none" />2024 &copy;<a class="mx-1" href="https://tenhal.sa">{% trans 'tenhal' %}</a></p>
<span class="text-body"> © 2024-2025 {{ _("All right reserved")}}</span>
<span class="fw-bold">Haikal</span>&nbsp;|&nbsp;<span class="fw-bold">هيكل</span>
</div>
<div class="col-12 col-sm-auto text-center">
<p class="mb-0 text-body-tertiary text-opacity-85">v1.1.9</p>
<span class="fw-light text-body-tertiary text-opacity-85">{{ _("Powered by")}} </span>
<a class="mx-1 text-decoration-none text-body-highlight" href="https://tenhal.sa">
<span>TENHAL</span>&nbsp;|&nbsp;<span>تنحل</span>
</a>
<span class="uil-trademark-circle fs-10 fw-light text-body-tertiary text-opacity-85"></span>
</div>
</div>
</footer>

View File

@ -79,13 +79,13 @@
</a>
<!-- more inner pages-->
</li>
<!--<li class="nav-item">
<li class="nav-item">
<a class="nav-link" href="{% url 'inventory_stats' %}">
<div class="d-flex align-items-center">
<span class="nav-link-icon"><span class="fas fa-car-side"></span></span><span class="nav-link-text">{% trans 'Cars'|capfirst %}</span>
</div>
</a>
</li>-->
</li>
<li class="nav-item">
<a class="nav-link" href="{% url 'car_list' %}">
<div class="d-flex align-items-center">
@ -188,7 +188,7 @@
<span class="nav-link-icon"><span class="fas fa-city"></span></span><span class="nav-link-text">{% trans "Organizations"|capfirst %}</span>
</div>
</a>
<!-- more inner pages-->
<!-- more inner pages
</li>
<li class="nav-item">
<a class="nav-link" href="{% url 'representative_list' %}">
@ -196,7 +196,7 @@
<span class="nav-link-icon"><span class="fas fa-users-cog"></span></span><span class="nav-link-text">{% trans "Representatives"|capfirst %}</span>
</div>
</a>
<!-- more inner pages-->
more inner pages-->
{% comment %} </li>
<li class="nav-item">
<a class="nav-link" href="{% url 'opportunity_list' %}">

View File

@ -2,164 +2,5 @@
{% load i18n static %}
{% block content %}
<script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
<div class="px-3 mb-6">
<div class="row justify-content-between">
<div class="col-12 text-start pb-4 my-3"></div>
</div>
<div class="row justify-content-between">
<div class="col-4 text-center pb-4 pb-xxl-0 align-content-center">
<h1 class="fs-5 pt-3">{{ dealer.get_local_name }}</h1>
</div>
<div class="col-2 text-center border-translucent border-start-xxl border-end-xxl-0 border-bottom-xxl-0 border-end border-bottom pb-4 pb-xxl-0 align-content-center">
<span class="uil fs-5 lh-1 uil-car text-primary"></span>
<h1 class="fs-5 pt-3">{{ total_cars }}</h1>
<p class="fs-9 mb-0">{% trans "Total Cars in Inventory" %}</p>
</div>
<div class="col-2 text-center border-translucent border-start-xxl border-end-xxl-0 border-bottom-xxl-0 border-end-md border-bottom pb-4 pb-xxl-0 align-content-center">
<span class="uil fs-5 lh-1 uil-lock-alt text-info"></span>
<h1 class="fs-5 pt-3">{{ total_reservations }}</h1>
<p class="fs-9 mb-0">{{ _("Reserved")}}</p>
</div>
<div class="col-2 text-center border-translucent border-start-xxl border-bottom-xxl-0 border-bottom border-end border-end-md-0 pb-4 pb-xxl-0 pt-4 pt-md-0 align-content-center">
<span class="uil fs-5 lh-1 uil-car-wash text-success-dark"></span>
<h1 class="fs-5 pt-3">{{ cars_in_house}}</h1>
<p class="fs-9 mb-0">{{ _("In Our Showroom")}}</p>
</div>
<div class="col-2 text-center border-translucent border-start-xxl border-end-md border-end-xxl-0 border-bottom border-bottom-md-0 pb-4 pb-xxl-0 pt-4 pt-xxl-0 align-content-center">
<span class="uil fs-5 lh-1 uil-car-slash text-danger-dark"></span>
<h1 class="fs-5 pt-3">{{ cars_outside }}</h1>
<p class="fs-9 mb-0">{{ _("Outside Showroom")}}</p>
</div>
</div>
</div>
<div class="row gx-3">
<div class="col-xxl-6">
<div class="row gx-7 pe-xxl-3">
<div class="col-12 col-xl-7 col-xxl-12">
<div class="row g-3 mb-3">
<div class="col-sm-6 col-md-4 col-xl-3 col-xxl-4 align-content-center">
<div class="card h-75">
<div class="card-body">
<div class="d-flex d-sm-block justify-content-between">
<div class="border-translucent mb-sm-4">
<div class="d-flex align-items-center">
<div class="d-flex align-items-center icon-wrapper-sm shadow-primary-100" style="transform: rotate(-7.45deg);">
<div class="icon icon-shape bg-gradient-info text-white rounded-circle shadow"></div>
</div>
<p class="text-body-tertiary fs-9 mb-0 ms-2 mt-3">Outgoing call</p>
</div>
<p class="text-primary mt-2 fs-6 fw-bold mb-0 mb-sm-4">3 <span class="fs-8 text-body lh-lg">Leads Today</span></p>
</div>
</div>
</div>
</div>
</div>
<div class="col-sm-6 col-md-4 col-xl-3 col-xxl-4 align-content-center">
<div class="card h-75">
<div class="card-body">
<div class="d-flex d-sm-block justify-content-between">
<div class="border-translucent mb-sm-4">
<div class="d-flex align-items-center">
<div class="d-flex align-items-center icon-wrapper-sm shadow-info-100" style="transform: rotate(-7.45deg);"><span class="fa-solid fa-calendar text-info fs-7 z-1 ms-2"></span></div>
<p class="text-body-tertiary fs-9 mb-0 ms-2 mt-3">Outgoing meeting</p>
</div>
<p class="text-info mt-2 fs-6 fw-bold mb-0 mb-sm-4">12 <span class="fs-8 text-body lh-lg">This Week</span></p>
</div>
</div>
</div>
</div>
</div>
<div class="col-sm-6 col-md-4 col-xl-3 col-xxl-4 align-content-center">
</div>
</div>
<div class="row g-3 mb-3">
<canvas id="pnlChart"></canvas>
</div>
</div>
</div>
</div>
<div class="col-xxl-6 align-content-center">
<div class="row g-0">
<div class="card mb-3">
<div class="bg-holder bg-card" style="background-image: url({% static 'images/spot-illustrations/39.png' %}); background-position: bottom right 0px; background-size: auto;"></div>
<div class="card-body">
<div>
<div class="col-6 col-xl-12 col-xxl-6 py-4 ps-4 ps-sm-5 ps-xl-0 ps-xxl-5">
<h5 class="text-body mb-4">{% trans 'inventory value'|capfirst %}</h5>
<div class="d-md-flex flex-between-center">
<div class="d-md-flex align-items-center gap-2 order-sm-0 order-md-1">
<span class="fa-solid fa-money-bill-trend-up fs-5 text-warning-light dark__text-opacity-75" data-bs-theme="light"></span>
<div class="d-flex d-md-block gap-2 align-items-center mt-1 mt-md-0">
<p class="fs-9 mb-0 mb-md-2 text-body-tertiary text-nowrap">{% trans "Profits"|upper %}</p>
<h4 class="text-body-highlight mb-0">{{ total_profit|floatformat }} {% trans 'SAR' %}</h4>
</div>
</div>
<div class="mt-3 mt-md-0">
<h3 class="text-body-highlight mb-2">{{ total_selling_price|floatformat }} {% trans 'SAR' %}</h3>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
<script>
const url = "{% url 'django_ledger:entity-json-pnl' dealer.entity.slug %}"
async function fetchPnLData() {
try {
const response = await fetch(url); // Update with your API URL
const jsonResponse = await response.json();
const pnlData = jsonResponse.results.pnl_data;
console.log(pnlData);
const labels = Object.keys(pnlData);
const profits = labels.map(label => pnlData[label].GROUP_NET_PROFIT);
const sales = labels.map(label => pnlData[label].GROUP_NET_SALES);
renderChart(labels, profits, sales);
} catch (error) {
console.error("Error fetching PnL data:", error);
}
}
function renderChart(labels, profits, sales) {
const ctx = document.getElementById("pnlChart").getContext("2d");
new Chart(ctx, {
type: "bar",
data: {
labels: labels,
datasets: [
{
label: "Net Profit",
data: profits,
backgroundColor: "#336699"
},
{
label: "Net Sales",
data: sales,
backgroundColor: "blue"
}
]
},
options: {
responsive: true,
scales: {
y: {
beginAtZero: true
}
}
}
});
}
fetchPnLData();
</script>
{% endblock %}

View File

@ -9,8 +9,9 @@
</style>
<!-- JavaScript Section -->
<script src="https://unpkg.com/@zxing/library@latest"></script>
<script src="https://cdn.jsdelivr.net/npm/tesseract.js@5/dist/tesseract.min.js"></script>
<script src="{% static 'vendors/zxing/index.min.js' %}"></script>
<script src="{% static 'vendors/tesseract/tesseract.min.js' %}"></script>
<div class=" container-fluid m-0">
<form method="post" id="carForm" class="form needs-validation" novalidate>
@ -69,7 +70,7 @@
<div class="col-md-6" id="make-row">
<div class="form-floating">
<span class="text-success fw-bold" id="make-check"></span>
{{ form.id_car_make|add_class:"form-select form-select-sm" }}
{{ form.id_car_make|default:'Select' }}
<label for="{{ form.id_car_make.id_for_label }}">{% trans 'make'|capfirst %}</label>
</div>
</div>

View File

@ -10,14 +10,14 @@
<div class="row justify-content-between">
<div class="col-sm-12 ">
<div class="card border h-100 w-100 p-lg-10">
<div class="bg-holder d-block bg-card" style="background-image:url({% static 'images/spot-illustrations/32.png' %});background-position: top right;">
<div class="bg-holder bg-card" style="background-image:url({% static 'images/spot-illustrations/32.png' %});background-position: top right;">
</div>
<div class="d-dark-none me-5">
<div class="bg-holder d-none d-sm-block d-xl-none d-xxl-block bg-card" style="background-image:url({% static 'images/spot-illustrations/dark_21.png' %}); background-position: bottom right; background-size: auto;">
<div class="d-dark-none">
<div class="bg-holder bg-card me-5" style="background-image:url({% static 'images/spot-illustrations/dark_21.png' %}); background-position: bottom right; transform: revert;">
</div>
</div>
<div class="d-light-none me-5">
<div class="bg-holder d-none d-sm-block d-xl-none d-xxl-block bg-card" style="background-image:url({% static 'images/spot-illustrations/21.png' %}); background-position: bottom right; background-size: auto;">
<div class="d-light-none">
<div class="bg-holder bg-card me-5" style="background-image:url({% static 'images/spot-illustrations/21.png' %}); background-position: bottom right; transform: revert;">
</div>
</div>
</div>

View File

@ -78,9 +78,9 @@
<tr>
<td>{{ transfer.car.vin }}</td>
<td>{{ transfer.car }}</td>
<td class="text-center">{{ transfer.car.finances.selling_price }}&nbsp;{{ CURRENCY }}</td>
<td class="text-center">{{ transfer.car.finances.vat_amount }}&nbsp;{{ CURRENCY }}</td>
<td class="text-center">{{ transfer.total_price }}&nbsp;{{ CURRENCY }}</td>
<td class="text-center">{{ transfer.car.finances.selling_price }}&nbsp;<span class="currency"> {{ CURRENCY }}</span></td>
<td class="text-center">{{ transfer.car.finances.vat_amount }}&nbsp;<span class="currency"> {{ CURRENCY }}</span></td>
<td class="text-center">{{ transfer.total_price }}&nbsp;<span class="currency"> {{ CURRENCY }}</span></td>
</tr>
</tbody>
</table>
@ -89,8 +89,8 @@
<!-- Total -->
<div class="transfer-total">
<p><strong>{%trans "Total Amount" %}:</strong> <span class="text-danger-darker fw-bold fs-8">{{transfer.total_price}}&nbsp;{{ CURRENCY }}</span></p>
<p><strong>{%trans "Total Amount written" %}:</strong> <span>{{ transfer.total_price|num_to_words:"ar" }}&nbsp;{{ CURRENCY }} {{ _("only") }}</span></p>
<p><strong>{%trans "Total Amount" %}:</strong> <span class="text-danger-darker fw-bold fs-8">{{transfer.total_price}}&nbsp;<span class="currency"> {{ CURRENCY }}</span></span></p>
<p><strong>{%trans "Total Amount written" %}:</strong> <span>{{ transfer.total_price|num_to_words:"ar" }}&nbsp;<span class="currency"> {{ CURRENCY }}</span> {{ _("only") }}</span></p>
</div>
</div>
<div class="col-12">

View File

@ -84,8 +84,8 @@
<div class="d-flex bg-success-subtle rounded flex-center me-3 mb-sm-3 mb-md-0 mb-xl-3 mb-xxl-0" style="width:32px; height:32px"><span class="text-success-dark" data-feather="dollar-sign" style="width:24px; height:24px"></span></div>
<div>
<p class="fw-bold mb-1">{% trans 'Paid Amount' %}</p>
<h4 class="fw-bolder text-nowrap {% if bill.is_paid %}text-success{% endif %}">{{bill.amount_paid}} {{ CURRENCY }}</h4>
<h6 class="fw-bolder text-nowrap">Owned <span class="fw-semibold text-nowrap text-success">{{bill.get_amount_open}} {{ CURRENCY }}</span></h6>
<h4 class="fw-bolder text-nowrap {% if bill.is_paid %}text-success{% endif %}">{{bill.amount_paid}} <span class="currency"> {{ CURRENCY }}</span></h4>
<h6 class="fw-bolder text-nowrap">Owned <span class="fw-semibold text-nowrap text-success">{{bill.get_amount_open}} <span class="currency"> {{ CURRENCY }}</span></span></h6>
<div class="progress" style="height:17px">
<div class="progress-bar fw-semibold bg-{% if bill.get_progress_percent < 100 %}secondary{% else %}success{% endif %} rounded-2" role="progressbar" style="width: {{bill.get_progress_percent}}%" aria-valuenow="{{bill.get_progress_percent}}" aria-valuemin="0" aria-valuemax="100">{{bill.get_progress_percent}}%</div>
</div>
@ -137,9 +137,9 @@
<div>
<p class="fw-bold mb-1">{% trans 'Due Amount' %}</p>
{% if bill.is_paid %}
<s><h4 class="fw-bolder text-nowrap">{{bill.amount_due}} {{ CURRENCY }}</h4></s>
<h4 class="fw-bolder text-nowrap">{{bill.amount_due}} <span class="currency"> {{ CURRENCY }}</span></h4>
{% else %}
<h4 class="fw-bolder text-nowrap">{{bill.amount_due}} {{ CURRENCY }}</h4>
<h4 class="fw-bolder text-nowrap">{{bill.amount_due}} <span class="currency"> {{ CURRENCY }}</span></h4>
{% endif %}
</div>
</div>

View File

@ -98,8 +98,8 @@
<tr class="has-text-weight-bold">
<td></td>
<td class="has-text-right"><span class="fw-bold fs-8">{{ _("Total") }}</span></td>
<td class="has-text-centered"><span class="fw-bold fs-8 text-success">{{ total_debits }} {{ _("SAR") }}</span></td>
<td class="has-text-centered"><span class="fw-bold fs-8 text-danger">{{ total_credits }} {{ _("SAR") }}</span></td>
<td class="has-text-centered"><span class="fw-bold fs-8 text-success">{{ total_debits }} <span class="currency">{{ CURRENCY }}</span></span></td>
<td class="has-text-centered"><span class="fw-bold fs-8 text-danger">{{ total_credits }} <span class="currency">{{ CURRENCY }}</span></span></td>
<td></td>
<td></td>
<td></td>

View File

@ -16,19 +16,19 @@
<div class="px-3 mb-6">
<div class="row justify-content-between">
<div class="col-6 col-md-4 col-xxl-2 text-center border-translucent border-start-xxl border-end-xxl-0 border-bottom-xxl-0 border-end border-bottom pb-4 pb-xxl-0 "><i class="fa-solid fa-landmark-dome fs-5 lh-1 text-primary"></i>
<h1 class="fs-5 pt-3">{% currency_symbol %}{{ tx_digest.group_balance.GROUP_ASSETS | currency_format }}</h1>
<p class="fs-9 mb-0">{{ _("Assets") }}nmnmnmnmnmnm</p>
<h1 class="fs-5 pt-3"><span class="currency">{% currency_symbol %}</span>{{ tx_digest.group_balance.GROUP_ASSETS | currency_format }}</h1>
<p class="fs-9 mb-0">{{ _("Assets") }}</p>
</div>
<div class="col-6 col-md-4 col-xxl-2 text-center border-translucent border-start-xxl border-end-xxl-0 border-bottom-xxl-0 border-end-md border-bottom pb-4 pb-xxl-0"><i class="fa-solid fa-weight-hanging fs-5 lh-1 text-primary"></i>
<h1 class="fs-5 pt-3">{% currency_symbol %}{{ tx_digest.group_balance.GROUP_LIABILITIES | currency_format }}</h1>
<h1 class="fs-5 pt-3"><span class="currency">{% currency_symbol %}</span>{{ tx_digest.group_balance.GROUP_LIABILITIES | currency_format }}</h1>
<p class="fs-9 mb-0">{{ _("Liabilities") }}</p>
</div>
<div class="col-6 col-md-4 col-xxl-2 text-center border-translucent border-start-xxl border-bottom-xxl-0 border-bottom border-end border-end-md-0 pb-4 pb-xxl-0 pt-4 pt-md-0"><i class="fa-solid fa-scale-balanced fs-5 lh-1 text-primary"></i>
<h1 class="fs-5 pt-3">{% currency_symbol %}{{ tx_digest.group_balance.GROUP_EQUITY | currency_format }}</h1>
<h1 class="fs-5 pt-3"><span class="currency">{% currency_symbol %}</span>{{ tx_digest.group_balance.GROUP_EQUITY | currency_format }}</h1>
<p class="fs-9 mb-0">{{ _("Equity") }}</p>
</div>
<div class="col-6 col-md-4 col-xxl-2 text-center border-translucent border-start-xxl border-end-md border-end-xxl-0 border-bottom border-bottom-md-0 pb-4 pb-xxl-0 pt-4 pt-xxl-0"><i class="fa-solid fs-5 lh-1 text-success fa-money-bill"></i>
<h1 class="fs-5 pt-3">{% currency_symbol %}{{ tx_digest.role_balance.ASSET_CA_CASH | currency_format }}</h1>
<h1 class="fs-5 pt-3"><span class="currency">{% currency_symbol %}</span>{{ tx_digest.role_balance.ASSET_CA_CASH | currency_format }}</h1>
<p class="fs-9 mb-0">{{ _("Cash") }}</p>
</div>
</div>
@ -40,15 +40,15 @@
<div class="px-3 mb-6">
<div class="row justify-content-between">
<div class="col-6 col-md-4 col-xxl-2 text-center border-translucent border-start-xxl border-end-xxl-0 border-bottom-xxl-0 border-end border-bottom pb-4 pb-xxl-0 "><i class="fa-solid fa-coins fs-5 lh-1 text-primary"></i>
<h1 class="fs-5 pt-3">{% currency_symbol %}{{ tx_digest.group_balance.GROUP_INCOME | currency_format }}</h1>
<h1 class="fs-5 pt-3"><span class="currency">{% currency_symbol %}</span>{{ tx_digest.group_balance.GROUP_INCOME | currency_format }}</h1>
<p class="fs-9 mb-0">{{ _("Revenue") }}</p>
</div>
<div class="col-6 col-md-4 col-xxl-2 text-center border-translucent border-start-xxl border-end-xxl-0 border-bottom-xxl-0 border-end-md border-bottom pb-4 pb-xxl-0"><i class="fa-solid fa-hand-holding-dollar fs-5 lh-1 text-danger"></i>
<h1 class="fs-5 pt-3">{% currency_symbol %}{{ tx_digest.group_balance.GROUP_EXPENSES | reverse_sign | currency_format }}</h1>
<h1 class="fs-5 pt-3"><span class="currency">{% currency_symbol %}</span>{{ tx_digest.group_balance.GROUP_EXPENSES | reverse_sign | currency_format }}</h1>
<p class="fs-9 mb-0">{{ _("Expenses") }}</p>
</div>
<div class="col-6 col-md-4 col-xxl-2 text-center border-translucent border-start-xxl border-bottom-xxl-0 border-bottom border-end border-end-md-0 pb-4 pb-xxl-0 pt-4 pt-md-0"><i class="fa-solid fa-sack-dollar fs-5 lh-1 text-primary"></i>
<h1 class="fs-5 pt-3">{% currency_symbol %}{{ tx_digest.group_balance.GROUP_EARNINGS | currency_format }}</h1>
<h1 class="fs-5 pt-3"><span class="currency">{% currency_symbol %}</span>{{ tx_digest.group_balance.GROUP_EARNINGS | currency_format }}</h1>
<p class="fs-9 mb-0">{{ _("Earnings (Loss)")}}</p>
</div>
<div class="col-6 col-md-4 col-xxl-2 text-center border-translucent border-start-xxl border-end-md border-end-xxl-0 border-bottom border-bottom-md-0 pb-4 pb-xxl-0 pt-4 pt-xxl-0"></div>

View File

@ -33,7 +33,7 @@
<td>{{ acc.unit_name|default:"" }}</td>
{% endif %}
<td>{{ acc.balance_type.0 | upper }}</td>
<td class="has-text-right">{% currency_symbol %}{{ acc.balance | currency_format }}</td>
<td class="has-text-right"><span class="currency">{% currency_symbol %}</span>{{ acc.balance | currency_format }}</td>
<td></td>
</tr>
{% endfor %}
@ -45,7 +45,7 @@
{% if tx_digest.by_unit %}
<td></td>
{% endif %}
<td class="has-text-right">{% currency_symbol %}{{ acc_data.total_balance | currency_format }}</td>
<td class="has-text-right"><span class="currency">{% currency_symbol %}</span>{{ acc_data.total_balance | currency_format }}</td>
<td></td>
</tr>
{% endfor %}
@ -58,7 +58,7 @@
<td></td>
{% endif %}
<td></td>
<td class="has-text-right">{% currency_symbol %}{{ bs_role_data.total_balance | currency_format }}</td>
<td class="has-text-right"><span class="currency">{% currency_symbol %}</span>{{ bs_role_data.total_balance | currency_format }}</td>
<td></td>
</tr>
{% endif %}
@ -72,7 +72,7 @@
<td></td>
{% endif %}
<td></td>
<td class="has-text-right">{% currency_symbol %}{{ tx_digest.group_balance.GROUP_EARNINGS | currency_format }}</td>
<td class="has-text-right"><span class="currency">{% currency_symbol %}</span>{{ tx_digest.group_balance.GROUP_EARNINGS | currency_format }}</td>
<td></td>
</tr>
@ -83,7 +83,7 @@
<td></td>
{% endif %}
<td></td>
<td class="has-text-right">{% currency_symbol %}{{ tx_digest.group_balance.GROUP_EQUITY | currency_format }}</td>
<td class="has-text-right"><span class="currency">{% currency_symbol %}</span>{{ tx_digest.group_balance.GROUP_EQUITY | currency_format }}</td>
<td></td>
</tr>
@ -94,7 +94,7 @@
<td></td>
{% endif %}
<td></td>
<td class="has-text-right">{% currency_symbol %}{{ tx_digest.group_balance.GROUP_LIABILITIES_EQUITY | currency_format }}</td>
<td class="has-text-right"><span class="currency">{% currency_symbol %}</span>{{ tx_digest.group_balance.GROUP_LIABILITIES_EQUITY | currency_format }}</td>
<td></td>
</tr>
</tbody>

View File

@ -0,0 +1,208 @@
{% load django_ledger %}
{% load i18n %}
<div class="table-container">
{# OPERATING ACTIVITIES #}
<table class="table is-fullwidth is-narrow is-striped">
<thead>
<tr>
<td class="has-text-weight-light is-size-3">{% trans 'Cash from Operating Activities' %}</td>
<td class="has-text-right has-text-weight-bold">{% trans 'Total' %}</td>
</tr>
</thead>
<tbody>
<tr>
<td class="has-text-weight-bold is-size-5">
{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_NET_INCOME.description }}
</td>
<td class="has-text-weight-bold has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_NET_INCOME.balance | currency_format }}</td>
</tr>
{# Non-cash Charges to Non-current Accounts #}
<tr>
<td class="is-size-5 has-text-weight-light has-text-centered">{% trans 'Noncash Charges to Non-current Accounts' %}</td>
<td></td>
</tr>
<tr>
<td class="has-text-right has-text-weight-light">
{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_OP_DEPRECIATION_AMORTIZATION.description }}
</td>
<td class="has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_OP_DEPRECIATION_AMORTIZATION.balance | currency_format }}</td>
</tr>
<tr>
<td class="has-text-right has-text-weight-light">
{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_OP_INVESTMENT_GAINS.description }}
</td>
<td class="has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_OP_INVESTMENT_GAINS.balance | currency_format }}</td>
</tr>
{# Non-cash Charges to Current Accounts #}
<tr>
<td class="is-size-5 has-text-weight-light has-text-centered">{% trans 'Non cash Charges to Current Accounts' %}</td>
<td></td>
</tr>
<tr>
<td class="has-text-right has-text-weight-light">
{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_OP_ACCOUNTS_RECEIVABLE.description }}
</td>
<td class="has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_OP_ACCOUNTS_RECEIVABLE.balance | currency_format }}</td>
</tr>
<tr>
<td class="has-text-right has-text-weight-light">
{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_OP_INVENTORY.description }}
</td>
<td class="has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_OP_INVENTORY.balance | currency_format }}</td>
</tr>
<tr>
<td class="has-text-right has-text-weight-light">
{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_OP_ACCOUNTS_PAYABLE.description }}
</td>
<td class="has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_OP_ACCOUNTS_PAYABLE.balance | currency_format }}</td>
</tr>
<tr>
<td class="has-text-right has-text-weight-light">
{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_OP_OTHER_CURRENT_ASSETS_ADJUSTMENT.description }}
</td>
<td class="has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_OP_OTHER_CURRENT_ASSETS_ADJUSTMENT.balance | currency_format }}</td>
</tr>
<tr>
<td class="has-text-right has-text-weight-light">
{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_OP_OTHER_CURRENT_LIABILITIES_ADJUSTMENT.description }}
</td>
<td class="has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.operating.GROUP_CFS_OP_OTHER_CURRENT_LIABILITIES_ADJUSTMENT.balance | currency_format }}</td>
</tr>
</tbody>
<tfoot>
<tr>
<td class="has-text-weight-bold is-size-5">{% trans 'Net Cash Provided by Operating Activities' %}</td>
<td class="has-text-weight-bold has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.net_cash_by_activity.OPERATING | currency_format }}</td>
</tr>
</tfoot>
</table>
{# FINANCING ACTIVITIES #}
<table class="table is-fullwidth is-narrow is-striped">
<thead>
<tr>
<td class="has-text-weight-light is-size-3">{% trans 'Cash from Financing Activities' %}</td>
<td></td>
</tr>
</thead>
<tbody>
<tr>
<td class="has-text-right has-text-weight-light">
{{ tx_digest.cash_flow_statement.financing.GROUP_CFS_FIN_ISSUING_EQUITY.description }}
</td>
<td class="has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.financing.GROUP_CFS_FIN_ISSUING_EQUITY.balance | currency_format }}</td>
</tr>
<tr>
<td class="has-text-right has-text-weight-light">
{{ tx_digest.cash_flow_statement.financing.GROUP_CFS_FIN_DIVIDENDS.description }}
</td>
<td class="has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.financing.GROUP_CFS_FIN_DIVIDENDS.balance | currency_format }}</td>
</tr>
<tr>
<td class="has-text-right has-text-weight-light">
{{ tx_digest.cash_flow_statement.financing.GROUP_CFS_FIN_ST_DEBT_PAYMENTS.description }}
</td>
<td class="has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.financing.GROUP_CFS_FIN_ST_DEBT_PAYMENTS.balance | currency_format }}</td>
</tr>
<tr>
<td class="has-text-right has-text-weight-light">
{{ tx_digest.cash_flow_statement.financing.GROUP_CFS_FIN_LT_DEBT_PAYMENTS.description }}
</td>
<td class="has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.financing.GROUP_CFS_FIN_LT_DEBT_PAYMENTS.balance | currency_format }}</td>
</tr>
</tbody>
<tfoot>
<tr>
<td class="has-text-weight-bold is-size-5">{% trans 'Net Cash Provided by Financing Activities' %}</td>
<td class="has-text-weight-bold has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.net_cash_by_activity.FINANCING | currency_format }}</td>
</tr>
</tfoot>
</table>
{# INVESTING ACTIVITIES #}
<table class="table is-fullwidth is-narrow is-striped">
<thead>
<tr>
<td class="has-text-weight-light is-size-3">{% trans 'Cash from Investing Activities' %}</td>
<td></td>
</tr>
</thead>
<tbody>
<tr>
<td class="has-text-right has-text-weight-light">
{{ tx_digest.cash_flow_statement.investing.GROUP_CFS_INVESTING_PPE.description }}
</td>
<td class="has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.investing.GROUP_CFS_INVESTING_PPE.balance | currency_format }}</td>
</tr>
<tr>
<td class="has-text-right has-text-weight-light">
{{ tx_digest.cash_flow_statement.investing.GROUP_CFS_INVESTING_SECURITIES.description }}
</td>
<td class="has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.investing.GROUP_CFS_INVESTING_SECURITIES.balance | currency_format }}</td>
</tr>
</tbody>
<tfoot>
<tr>
<td class="has-text-weight-bold is-size-5">{% trans 'Net Cash Provided by Investing Activities' %}</td>
<td class="has-text-weight-bold has-text-right">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.net_cash_by_activity.INVESTING | currency_format }}</td>
</tr>
</tfoot>
</table>
{# NET CASH #}
<table class="table is-fullwidth is-narrow is-stripped">
<thead>
<tr>
<td class="has-text-weight-light is-size-3">{% trans 'Net Cashflow' %}</td>
<td></td>
</tr>
</thead>
<tbody>
<tr>
<td class="has-text-right has-text-weight-light">
{% trans 'Net Cash From' %} {{ tx_digest.from_date }} -> {{ tx_digest.to_date }}
</td>
<td class="has-text-weight-bold has-text-right is-size-5">
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.cash_flow_statement.net_cash | currency_format }}</td>
</tr>
</tbody>
</table>
</div>

View File

@ -41,7 +41,7 @@
<span class="icon">{% icon 'bi:arrow-bar-up' 24 %}</span>
{% endif %}
</td>
<td>{% currency_symbol %}{{ acc.balance | currency_format }}</td>
<td><span class="currency">{% currency_symbol %}</span>{{ acc.balance | currency_format }}</td>
<td>
</td>
@ -56,7 +56,7 @@
<td></td>
<td><h2 class="is-size-5 has-text-right">{% trans 'Net Operating Revenues' %}</h2></td>
<td class="is-size-5 has-text-weight-bold">
{% currency_symbol %}{{ tx_digest.income_statement.operating.net_operating_revenue | currency_format }}</td>
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.income_statement.operating.net_operating_revenue | currency_format }}</td>
<td></td>
</tr>
@ -85,7 +85,7 @@
<span class="icon">{% icon 'bi:arrow-bar-up' 24 %}</span>
{% endif %}
</td>
<td>{% currency_symbol %}{{ acc.balance | reverse_sign | currency_format }}</td>
<td><span class="currency">{% currency_symbol %}</span>{{ acc.balance | reverse_sign | currency_format }}</td>
<td>
</td>
@ -100,7 +100,7 @@
<td></td>
<td><h2 class="is-size-5 has-text-right">{% trans 'Net COGS' %}</h2></td>
<td class="is-size-5 has-text-weight-bold">
{% currency_symbol %}{{ tx_digest.income_statement.operating.net_cogs | currency_format }}</td>
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.income_statement.operating.net_cogs | currency_format }}</td>
<td></td>
</tr>
@ -113,7 +113,7 @@
<td></td>
<td><h2 class="is-size-4 has-text-right">{% trans 'Gross Profit' %}</h2></td>
<td class="is-size-4 has-text-weight-bold">
{% currency_symbol %}{{ tx_digest.income_statement.operating.gross_profit | currency_format }}</td>
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.income_statement.operating.gross_profit | currency_format }}</td>
<td></td>
</tr>
@ -142,7 +142,7 @@
<span class="icon">{% icon 'bi:arrow-bar-up' 24 %}</span>
{% endif %}
</td>
<td>{% currency_symbol %}{{ acc.balance | reverse_sign | currency_format }}</td>
<td><span class="currency">{% currency_symbol %}</span>{{ acc.balance | reverse_sign | currency_format }}</td>
<td>
</td>
@ -156,7 +156,7 @@
<td></td>
<td><h2 class="is-size-5 has-text-right">{% trans 'Net Operating Expenses' %}</h2></td>
<td class="is-size-5 has-text-weight-bold">
{% currency_symbol %}{{ tx_digest.income_statement.operating.net_operating_expenses | reverse_sign | currency_format }}</td>
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.income_statement.operating.net_operating_expenses | reverse_sign | currency_format }}</td>
<td></td>
</tr>
@ -170,7 +170,7 @@
<td></td>
<td><h2 class="is-size-4 has-text-right">{% trans 'Net Operating Income (Loss)' %}</h2></td>
<td class="is-size-3">
{% currency_symbol %}{{ tx_digest.income_statement.operating.net_operating_income| currency_format }}</td>
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.income_statement.operating.net_operating_income| currency_format }}</td>
<td></td>
</tr>
@ -199,7 +199,7 @@
<span class="icon">{% icon 'bi:arrow-bar-up' 24 %}</span>
{% endif %}
</td>
<td class="is-size-5">{% currency_symbol %}{{ acc.balance | currency_format }}</td>
<td class="is-size-5"><span class="currency">{% currency_symbol %}</span>{{ acc.balance | currency_format }}</td>
<td>
</td>
@ -213,7 +213,7 @@
<td></td>
<td><h2 class="is-size-5 has-text-right">{% trans 'Net Other Revenues' %}</h2></td>
<td class="is-size-5 has-text-weight-bold">
{% currency_symbol %}{{ tx_digest.income_statement.other.net_other_revenues | currency_format }}</td>
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.income_statement.other.net_other_revenues | currency_format }}</td>
<td></td>
</tr>
@ -243,7 +243,7 @@
<span class="icon">{% icon 'bi:arrow-bar-up' 24 %}</span>
{% endif %}
</td>
<td class="is-size-5">{% currency_symbol %}{{ acc.balance | reverse_sign | currency_format }}</td>
<td class="is-size-5"><span class="currency">{% currency_symbol %}</span>{{ acc.balance | reverse_sign | currency_format }}</td>
<td>
</td>
@ -257,7 +257,7 @@
<td></td>
<td><h2 class="is-size-5 has-text-right">{% trans 'Net Other Expenses' %}</h2></td>
<td class="is-size-5 has-text-weight-bold">
{% currency_symbol %}{{ tx_digest.income_statement.other.net_other_expenses | currency_format }}</td>
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.income_statement.other.net_other_expenses | currency_format }}</td>
<td></td>
</tr>
@ -270,7 +270,7 @@
<td></td>
<td><h2 class="is-size-4 has-text-right">{% trans 'Net Other Income (Loss)' %}</h2></td>
<td class="is-size-3">
{% currency_symbol %}{{ tx_digest.income_statement.other.net_other_income | currency_format }}</td>
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.income_statement.other.net_other_income | currency_format }}</td>
<td></td>
</tr>
@ -286,7 +286,7 @@
</td>
<td><h2 class="is-size-3 has-text-right">{% trans 'Net Income' %}</h2></td>
<td class="is-size-3 has-text-weight-bold">
{% currency_symbol %}{{ tx_digest.income_statement.net_income| currency_format }}</td>
<span class="currency">{% currency_symbol %}</span>{{ tx_digest.income_statement.net_income| currency_format }}</td>
<td></td>
</tr>

View File

@ -1,354 +1,270 @@
{% load static i18n %}
{% load i18n static custom_filters num2words_tags %}
<!DOCTYPE html>
<html lang="en">
<html lang="ar">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Estimate</title>
<!-- Bootstrap CSS -->
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/css/bootstrap.min.css" rel="stylesheet">
<title>Invoice</title>
<!-- CSS -->
<link href="{% static 'css/theme.min.css' %}" type="text/css" rel="stylesheet" id="style-default">
<link href="{% static 'css/user.min.css' %}" type="text/css" rel="stylesheet" id="user-style-default">
<link href="{% static 'css/custom.css' %}" type="text/css" rel="stylesheet">
<!-- Google Fonts - Roboto -->
<link href="https://fonts.googleapis.com/css2?family=Roboto:wght@300;400;500;700&display=swap" rel="stylesheet">
<!-- Custom CSS -->
<style>
body {
background-color: #f8f9fa;
font-family: 'Roboto', sans-serif;
margin: 0;
padding: 0;
}
.estimate-row {
background: #fff;
border-radius: 12px;
box-shadow: 0 6px 12px rgba(0, 0, 0, 0.1);
padding: 3rem;
margin: 3rem auto;
max-width: 1000px;
}
.estimate-header {
border-bottom: 2px solid #dee2e6;
padding-bottom: 1.5rem;
margin-bottom: 2.5rem;
text-align: center;
}
.estimate-header h1 {
font-size: 2.5rem;
font-weight: 700;
color: #333;
margin-bottom: 0.5rem;
}
.estimate-header p {
font-size: 1.1rem;
color: #666;
font-weight: 400;
}
.estimate-details {
margin-bottom: 2.5rem;
}
.estimate-details p {
margin: 0.75rem 0;
color: #555;
font-size: 1rem;
font-weight: 400;
}
.estimate-table {
margin-bottom: 2.5rem;
}
.estimate-table th {
padding: 10mm;
background-color: #f8f9fa;
font-weight: 500;
color: #333;
}
.estimate-table td {
color: #555;
font-weight: 400;
.invoice-container {
width: 210mm;
min-height: 297mm;
padding: 10mm;
margin: auto;
background: white;
border-radius: 5px;
box-shadow: 0 0 5px rgba(0, 0, 0, 0.1);
position: relative;
}
.additional-charges {
margin-top: 2rem;
margin-bottom: 1.5rem;
.invoice-header {
text-align: center;
border-bottom: 2px solid #dee2e6;
padding-bottom: 10px;
margin-bottom: 20px;
}
.additional-charges p {
margin: 0.5rem 0;
color: #555;
font-size: 1rem;
font-weight: 400;
.qr-code {
text-align: center;
margin-top: 10px;
}
.estimate-total {
.qr-code img {
width: 3cm;
height: 3cm;
border-radius: 0.3333333333rem;
}
.invoice-details, .invoice-table {
font-size: 12px;
}
.invoice-table th {
background-color: #f8f9fa;
font-weight: 600;
}
.invoice-total {
text-align: right;
font-size: 1.5rem;
font-weight: 500;
color: #333;
margin-top: 1rem;
font-size: 13px;
font-weight: 600;
margin-top: 10px;
}
.footer-note {
position: absolute;
text-align: center;
color: #777;
margin-left: 0;
margin-top: 0;
font-size: 1rem;
font-weight: 400;
}
.logo {
max-width: 150px;
margin-bottom: 1.5rem;
}
.highlight {
color: #007bff;
font-weight: 500;
}
.btn-primary {
background-color: #007bff;
border-color: #007bff;
font-weight: 500;
padding: 0.75rem 1.5rem;
font-size: 1rem;
}
.btn-primary:hover {
background-color: #0056b3;
border-color: #0056b3;
}
.button-row {
bottom: 10mm;
left: 10mm;
right: 10mm;
font-size: 10px;
display: flex;
justify-content: center;
gap: 10px;
margin-top: 2rem;
justify-content: space-between;
align-items: center;
}
.logo-img img {
width: 10mm;
height: 10mm;
}
</style>
{% if LANGUAGE_CODE == 'en' %}
<link href="{% static 'css/theme.min.css' %}" type="text/css" rel="stylesheet" id="style-default">
<link href="{% static 'css/user.min.css' %}" type="text/css" rel="stylesheet" id="user-style-default">
{% else %}
<link href="{% static 'css/theme-rtl.min.css' %}" type="text/css" rel="stylesheet" id="style-rtl">
<link href="{% static 'css/user-rtl.min.css' %}" type="text/css" rel="stylesheet" id="user-style-rtl">
{% endif %}
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.0.0-beta3/css/all.min.css">
</head>
<body>
{% if estimate.status != "in_review" %}
<main class="main" id="top">
<div class="px-3">
<div class="row min-vh-100 flex-center p-5">
<div class="col-12 col-xl-10 col-xxl-8">
<div class="row justify-content-center align-items-center g-5">
<div class="col-12 col-lg-6 text-center order-lg-1"><img class="img-fluid w-lg-100 d-dark-none" src="{% static 'images/spot-illustrations/404-illustration.png' %}" alt="" width="400" /><img class="img-fluid w-md-50 w-lg-100 d-light-none" src="../../assets/img/spot-illustrations/dark_404-illustration.png" alt="" width="540" /></div>
<div class="col-12 col-lg-6 text-center text-lg-start"><img class="img-fluid mb-6 w-50 w-lg-75 d-dark-none" src="{% static 'images/spot-illustrations/404.png' %}" alt="" /><img class="img-fluid mb-6 w-50 w-lg-75 d-light-none" src="../../assets/img/spot-illustrations/dark_404.png" alt="" />
<h2 class="text-body-secondary fw-bolder mb-3">Page Missing!</h2>
<p class="text-body mb-5">But no worries! Our ostrich is looking everywhere <br class="d-none d-sm-block" />
</div>
</div>
</div>
</div>
</div>
<script>
var navbarTopStyle = window.config.config.phoenixNavbarTopStyle;
var navbarTop = document.querySelector('.navbar-top');
if (navbarTopStyle === 'darker') {
navbarTop.setAttribute('data-navbar-appearance', 'darker');
}
var navbarVerticalStyle = window.config.config.phoenixNavbarVerticalStyle;
var navbarVertical = document.querySelector('.navbar-vertical');
if (navbarVertical && navbarVerticalStyle === 'darker') {
navbarVertical.setAttribute('data-navbar-appearance', 'darker');
}
</script>
<div class="support-chat-row">
<div class="row-fluid support-chat">
<div class="card bg-body-emphasis">
<div class="card-header d-flex flex-between-center px-4 py-3 border-bottom border-translucent">
<h5 class="mb-0 d-flex align-items-center gap-2">Demo widget<span class="fa-solid fa-circle text-success fs-11"></span></h5>
<div class="btn-reveal-trigger">
<button class="btn btn-link p-0 dropdown-toggle dropdown-caret-none transition-none d-flex" type="button" id="support-chat-dropdown" data-bs-toggle="dropdown" data-boundary="window" aria-haspopup="true" aria-expanded="false" data-bs-reference="parent"><span class="fas fa-ellipsis-h text-body"></span></button>
<div class="dropdown-menu dropdown-menu-end py-2" aria-labelledby="support-chat-dropdown"><a class="dropdown-item" href="#!">Request a callback</a><a class="dropdown-item" href="#!">Search in chat</a><a class="dropdown-item" href="#!">Show history</a><a class="dropdown-item" href="#!">Report to Admin</a><a class="dropdown-item btn-support-chat" href="#!">Close Support</a></div>
</div>
</div>
<div class="card-body chat p-0">
<div class="d-flex flex-column-reverse scrollbar h-100 p-3">
<div class="text-end mt-6"><a class="mb-2 d-inline-flex align-items-center text-decoration-none text-body-emphasis bg-body-hover rounded-pill border border-primary py-2 ps-4 pe-3" href="#!">
<p class="mb-0 fw-semibold fs-9">I need help with something</p><span class="fa-solid fa-paper-plane text-primary fs-9 ms-3"></span>
</a><a class="mb-2 d-inline-flex align-items-center text-decoration-none text-body-emphasis bg-body-hover rounded-pill border border-primary py-2 ps-4 pe-3" href="#!">
<p class="mb-0 fw-semibold fs-9">I cant reorder a product I previously ordered</p><span class="fa-solid fa-paper-plane text-primary fs-9 ms-3"></span>
</a><a class="mb-2 d-inline-flex align-items-center text-decoration-none text-body-emphasis bg-body-hover rounded-pill border border-primary py-2 ps-4 pe-3" href="#!">
<p class="mb-0 fw-semibold fs-9">How do I place an order?</p><span class="fa-solid fa-paper-plane text-primary fs-9 ms-3"></span>
</a><a class="false d-inline-flex align-items-center text-decoration-none text-body-emphasis bg-body-hover rounded-pill border border-primary py-2 ps-4 pe-3" href="#!">
<p class="mb-0 fw-semibold fs-9">My payment method not working</p><span class="fa-solid fa-paper-plane text-primary fs-9 ms-3"></span>
</a>
</div>
<div class="text-center mt-auto">
<div class="avatar avatar-3xl status-online"><img class="rounded-circle border border-3 border-light-subtle" src="../../assets/img/team/30.webp" alt="" /></div>
<h5 class="mt-2 mb-3">Eric</h5>
<p class="text-center text-body-emphasis mb-0">Ask us anything well get back to you here or by email within 24 hours.</p>
</div>
</div>
</div>
<div class="card-footer d-flex align-items-center gap-2 border-top border-translucent ps-3 pe-4 py-3">
<div class="d-flex align-items-center flex-1 gap-3 border border-translucent rounded-pill px-4">
<input class="form-control outline-none border-0 flex-1 fs-9 px-0" type="text" placeholder="Write message" />
<label class="btn btn-link d-flex p-0 text-body-quaternary fs-9 border-0" for="supportChatPhotos"><span class="fa-solid fa-image"></span></label>
<input class="d-none" type="file" accept="image/*" id="supportChatPhotos" />
<label class="btn btn-link d-flex p-0 text-body-quaternary fs-9 border-0" for="supportChatAttachment"> <span class="fa-solid fa-paperclip"></span></label>
<input class="d-none" type="file" id="supportChatAttachment" />
</div>
<button class="btn p-0 border-0 send-btn"><span class="fa-solid fa-paper-plane fs-9"></span></button>
</div>
<div class="row p-2">
<div class="col-2">
<button class="btn btn-sm btn-danger w-100" onclick="window.history.back()">الرجوع&nbsp;/&nbsp;Back</button>
</div>
</div>
<button class="btn btn-support-chat p-0 border border-translucent"><span class="fs-8 btn-text text-primary text-nowrap">Chat demo</span><span class="ping-icon-wrapper mt-n4 ms-n6 mt-sm-0 ms-sm-2 position-absolute position-sm-relative"><span class="ping-icon-bg"></span><span class="fa-solid fa-circle ping-icon"></span></span><span class="fa-solid fa-headset text-primary fs-8 d-sm-none"></span><span class="fa-solid fa-chevron-down text-primary fs-7"></span></button>
</div>
</main>
{% else%}
<div class="button-row">
<button id="download-pdf" class="btn btn-primary">
<i class="fas fa-download"></i> {% trans 'Download Estimate' %}
</button>
<button id="accept" class="btn btn-success" data-bs-toggle="modal" data-bs-target="#acceptModal">
<i class="fas fa-check-circle"></i> {% trans 'Accept Estimate' %}
</button>
<button id="reject" class="btn btn-danger" data-bs-toggle="modal" data-bs-target="#rejectModal">
<i class="fas fa-times-circle"></i> {% trans 'Reject Estimate' %}
</button>
<div class="col-2">
<button class="btn btn-sm btn-primary w-100" id="download-pdf">تحميل&nbsp;/&nbsp;Download</button>
</div>
<div class="col-8"></div>
</div>
<!-- Accept Modal -->
<div class="modal fade" id="acceptModal" tabindex="-1" aria-labelledby="acceptModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="acceptModalLabel">{% trans 'Accept Estimate' %}</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
{% trans 'Are you sure you want to accept this estimate?' %}
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">{% trans 'Cancel' %}</button>
<a href="{% url 'estimate_mark_as' estimate.pk %}?mark=accepted" type="button" class="btn btn-success" id="confirmAccept">{% trans 'Accept' %}</a>
</div>
</div>
<div class="invoice-container" id="invoice-content">
<div class="invoice-header">
<h5 class="fs-5"><span>Quotation</span>&nbsp;/&nbsp;<span>عرض سعر</span></h5>
</div>
</div>
<div class="invoice-details p-1">
<table class="table table-sm table-responsive border-gray-50">
<tr>
<td>
<!-- Reject Modal -->
<div class="modal fade" id="rejectModal" tabindex="-1" aria-labelledby="rejectModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="rejectModalLabel">{% trans 'Reject Estimate' %}</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
{% trans 'Are you sure you want to reject this estimate?' %}
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">{% trans 'Cancel' %}</button>
<a href="{% url 'estimate_mark_as' estimate.pk %}?mark=rejected" type="button" class="btn btn-danger" id="confirmReject">{% trans 'Reject' %}</a>
</div>
</div>
</td>
<td></td>
<td>
<div class="qr-code">
<img class="rounded-soft" src="{{ dealer.logo.url|default:'' }}" alt="Dealer Logo"/>
</div>
</td>
</tr>
<tr>
<td><strong>{{ dealer.name }}</strong></td>
<td></td>
<td class="text-end"><strong>{{ dealer.arabic_name }}</strong></td>
</tr>
<tr>
<td><strong>Address</strong></td>
<td>{{ dealer.address }}</td>
<td class="text-end"> <strong>العنوان</strong></td>
</tr>
<tr>
<td><strong>Phone</strong></td>
<td>{{ dealer.phone_number }}</td>
<td class="text-end"><strong>جوال</strong></td>
</tr>
<tr>
<td><strong>VAT Number</strong></td>
<td>{{ dealer.vrn }}</td>
<td class="text-end"><strong>الرقم الضريبي</strong></td>
</tr>
</table>
<table class="table table-sm table-bordered border-gray-50">
<tr>
<td class="ps-1"><strong>Quotation&nbsp;Number</strong></td>
<td class="text-center">{{ estimate.estimate_number }}</td>
<td class="text-end p-1"><strong>رقم عرض السعر</strong></td>
</tr>
<tr>
<td class="ps-1"><strong>Date</strong></td>
<td class="text-center">{{ estimate.date_approved| date:"Y/m/d" }}</td>
<td class="text-end p-1"><strong>التاريخ</strong></td>
</tr>
<tr>
<td class="ps-1"><strong>Customer</strong></td>
<td class="text-center">{{ estimate.customer.customer_name }}</td>
<td class="text-end p-1"><strong>العميل</strong></td>
</tr>
<tr>
<td class="ps-1"><strong>VAT&nbsp;ID</strong></td>
<td class="text-center">{{ estimate.customer.vrn|default:"-" }}</td>
<td class="text-end p-1"><strong>الرقم الضريبي</strong></td>
</tr>
<tr>
<td class="ps-1"><strong>Email</strong></td>
<td class="text-center">{{ estimate.customer.email |default:"N/A" }} </td>
<td class="text-end p-1"><strong>البريد الإلكتروني</strong></td>
</tr>
<tr>
<td class="ps-1"><strong>Terms</strong></td>
<td class="text-center">{{ estimate.get_terms_display }}</td>
<td class="text-end p-1"><strong>طريقة&nbsp;الدفع</strong></td>
</tr>
</table>
</div>
</div>
<div class="estimate-row" id="estimate-content">
<!-- Header -->
<div class="estimate-header">
<svg width="101" height="24" viewBox="0 0 101 24" fill="none" xmlns="http://www.w3.org/2000/svg">
<!-- SVG Paths -->
</svg>
<h1 style="margin-top: 10px;"><b>{% trans "Estimate" %}</b></h1>
<p>{% trans "Thank you for choosing us. We appreciate your business" %}</p>
<div class="d-flex justify-content-between">
<span class="fs-9 fw-thin">Car Details</span>
<span class="fs-9 fw-thin">تفاصيل السيارة</span>
</div>
<div class="invoice-table p-1">
<table class="table table-sm table-bordered m-1">
<thead>
<tr>
<th class="text-wrap text-center align-content-center"><span class="fs-10">Make</span> / <span class="fs-10">الصانع</span></th>
<th class="text-wrap text-center align-content-center"><span class="fs-10">Model</span> / <span class="fs-10">الموديل</span></th>
<th class="text-wrap text-center align-content-center"><span class="fs-10">Trim</span> / <span class="fs-10">الفئة</span></th>
<th class="text-wrap text-center align-content-center"><span class="fs-10">Year</span> / <span class="fs-10">السنة</span></th>
<th class="text-wrap text-center align-content-center"><span class="fs-10">VIN</span> / <span class="fs-10">الهيكل</span></th>
<th class="text-wrap text-center align-content-center"><span class="fs-10">Quantity</span> / <span class="fs-10">الكمية</span></th>
<th class="text-wrap text-center align-content-center"><span class="fs-10">Unit Price</span> / <span class="fs-10">سعر الوحدة</span></th>
<th class="text-wrap text-center align-content-center"><span class="fs-10">Including VAT</span> / <span class="fs-10">شامل الضريبة</span></th>
</tr>
</thead>
<tbody>
{% for item in data.cars %}
<tr>
<td class="ps-1 fs-10 align-content-center" colspan="3">{{ item.make }} - {{ item.model }} - {{ item.trim }}</td>
<td class="text-center fs-10 align-content-center">{{ item.year }}</td>
<td class="ps-1 fs-10 align-content-center">{{ item.vin }}</td>
<td class="text-center fs-10 align-content-center">{{ item.quantity|floatformat:-1 }}</td>
<td class="text-center fs-10 align-content-center">{{ item.unit_price|floatformat:2 }}</td>
<td class="text-center fs-10 align-content-center">{{ item.total_vat|floatformat:2 }}</td>
</tr>
{% endfor %}
<tr>
<td class="ps-1 fs-10 align-content-center" colspan="5"></td>
<td class="text-center fs-10 align-content-center">{{ data.quantity|floatformat:-1 }}</td>
<td class="text-center fs-10 align-content-center">{{ data.total_price|floatformat:2 }}</td>
<td class="text-center fs-10 align-content-center">{{ data.total_vat|floatformat:2 }}</td>
</tr>
</tbody>
</table>
</div>
<!-- Details -->
<div class="estimate-details">
<p><strong>{% trans "Estimate Number" %} :</strong> <span class="highlight">#{{estimate.estimate_number}}</span></p>
<p><strong>{% trans "Date" %} :</strong> {{estimate.date_in_review}}</p>
<p><strong>{% trans "Customer" %} :</strong> {{estimate.customer.customer_name}}</p>
<p><strong>{% trans "Email" %} :</strong> {{estimate.customer.email}}</p>
<p><strong>{% trans "Terms" %} :</strong> {{estimate.terms|title}}</p>
<div class="d-flex justify-content-between">
<span class="fs-9 fw-thin">Additional&nbsp;Services</span>
<span class="fs-9 fw-thin">الخدمات&nbsp;الإضافية</span>
</div>
<!-- Items Table -->
<div class="estimate-table">
<table class="table table-bordered">
{% if data.additionals %}
<div class="invoice-table p-1">
<table class="table table-sm table-bordered m-1">
<thead>
<tr>
<th>{% trans "Item" %}</th>
<th class="text-center">{% trans "Quantity" %}</th>
<th class="text-center">{% trans "Unit Price" %}</th>
<th class="text-center">{% trans "Total" %}</th>
<th class="text-center fs-10 align-content-center">Type&nbsp;/&nbsp;النوع</th>
<th class="text-center fs-10 align-content-center">Price&nbsp;/&nbsp;القيمة</th>
<th class="text-center fs-10 align-content-center"><span class="fs-10">Including VAT</span> / <span class="fs-10">شامل الضريبة</span></th>
</tr>
</thead>
<tbody>
{% for item in car_and_item_info %}
{% for item in data.additionals %}
<tr>
<td class="">{{item.info.make}}</td>
<td class="align-middle">{{item.quantity}}</td>
<td class="align-middle ps-5">{{item.finances.selling_price}}</td>
<td class="align-middle text-body-tertiary fw-semibold">{{item.total}}</td>
<td class="ps-1 text-start fs-10 align-content-center">{{ item.name }}</td>
<td class="ps-1 text-center fs-10 align-content-center">{{ item.price|floatformat:2 }}</td>
<td class="ps-1 text-center fs-10 align-content-center">{{ item.price_|floatformat:2 }}</td>
</tr>
{% endfor %}
</tbody>
</table>
</div>
<!-- Additional Charges (VAT and Services) -->
<div class="additional-charges">
<p><strong>{% trans "VAT" %} ({{vat}}%):</strong> <span class="highlight">${{vat_amount}}</span></p>
<p><strong>{% trans "Additional Services" %}:</strong>
<br>
{% for service in additional_services %}
<span class="highlight">{{service.name}} - ${{service.price}}</span><br>
{% endfor %}
</p>
{% endif %}
<div class="invoice-total d-flex justify-content-end">
<div class="table-responsive">
<table class="table table-sm table-responsive">
<tr>
<td class="text-start ps-1"><strong class="fs-9">VAT</strong></td>
<td class="text-center"><span class="fs-9">{{ data.total_vat_amount|floatformat:2 }} <span class="currency">{{ CURRENCY }}</span></span></td>
<td class="text-end"><strong class="fs-9">ضريبة&nbsp;القيمة&nbsp;المضافة</strong></td>
</tr>
<tr>
<td class="text-start ps-1"><strong class="fs-9">Total</strong></td>
<td class="text-center"><span class="fs-9">{{ data.grand_total|floatformat:2 }}&nbsp;<span class="currency">{{ CURRENCY }}</span></span></td>
<td class="text-end"><strong class="fs-9">الإجمالي</strong></td>
</tr>
<tr>
<td class="text-end" colspan="3"><span class="fs-9 fw-bold">كتابةً:&nbsp;</span><span class="fs-9">{{ data.grand_total|num_to_words }}&nbsp;<span class="currency">{{ CURRENCY }}</span></span></td>
</tr>
</table>
</div>
</div>
<!-- Total -->
<div class="estimate-total">
<p><strong>{%trans "Total Amount" %}:</strong> <span class="highlight">${{total}}</span></p>
</div>
<!-- Footer Note -->
<br><br>
<br><br>
<br><br>
<div class="footer-note">
<p>{% trans "If you have any questions, feel free to contact us at" %} <a href="mailto:support@example.com">support@example.com</a>.</p>
<p>{% trans "Thank you for your business" %}</p>
<div class="logo-img text-center">
<img src="{% static 'images/logos/logo-d-pdf.png' %}" alt="Logo"/>
<p class="fs-11 fw-bold"><span>Haikal</span>&nbsp;|&nbsp;<span>هيكل</span></p>
</div>
<p class="fs-11"><span class="fw-thin">Powered&nbsp;by&nbsp;</span><a class="text-decoration-none" href="https://tenhal.sa" style="color: #112e40;"><span>TENHAL</span>&nbsp;|&nbsp;<span>تنحل</span></a></p>
</div>
</div>
{% endif %}
<!-- Bootstrap JS (Optional) -->
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/js/bootstrap.bundle.min.js"></script>
<!-- jsPDF Library -->
<script src="https://cdnjs.cloudflare.com/ajax/libs/jspdf/2.5.1/jspdf.umd.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/html2pdf.js/0.10.1/html2pdf.bundle.min.js"></script>
<script src="{% static 'vendors/bootstrap/bootstrap.min.js' %}"></script>
<script src="{% static 'js/html2pdf.bundle.min.js' %}"></script>
<script>
document.getElementById('download-pdf').addEventListener('click', function () {
const element = document.getElementById('estimate-content');
// Options for html2pdf.js
const options = {
margin: 0, // No margin
filename: 'estimate.pdf', // Name of the downloaded file
image: { type: 'jpeg', quality: 0.98 }, // Image quality
html2canvas: {
scale: 2, // Increase scale for better quality
scrollX: 0, // Ensure no horizontal scroll offset
scrollY: 0, // Ensure no vertical scroll offset
useCORS: true, // Enable CORS for external resources
},
jsPDF: { unit: 'mm', format: 'a4', orientation: 'portrait' } // PDF settings
};
// Generate and download the PDF
html2pdf().from(element).set(options).save();
});
document.getElementById('confirmAccept').addEventListener('click', function () {
// Handle the accept action here
$('#acceptModal').modal('hide');
});
document.getElementById('confirmReject').addEventListener('click', function () {
// Handle the reject action here
$('#rejectModal').modal('hide');
html2pdf().from(document.getElementById('invoice-content')).set({
margin: 0,
filename: "{{ invoice.invoice_number }}_{{ invoice.customer.customer_name }}_{{ invoice.date_in_review|date:'Y-m-d' }}.pdf",
image: { type: 'jpeg', quality: 0.98 },
html2canvas: { scale: 3 },
jsPDF: { unit: 'mm', format: 'a3', orientation: 'portrait' }
}).save();
});
</script>
</body>

View File

@ -15,7 +15,7 @@
<input class="form-control" name="to" type="text" placeholder="To" value="{{estimate.customer.email}}" />
</div>
<div class="col-12">
<input class="form-control" name="subject" type="text" placeholder="Subject" value="Estimate {{estimate.estimate_number}}" />
<input class="form-control" name="subject" type="text" placeholder="Subject" value="Quotation {{estimate.estimate_number}}" />
</div>
</div>
<div class="mb-3 flex-1">
@ -23,8 +23,8 @@
</div>
<div class="d-flex justify-content-between align-items-center">
<div class="d-flex">
<a href="{% url 'estimate_detail' estimate.pk %}" class="btn btn-link text-body fs-10 text-decoration-none">Discard</a>
<button class="btn btn-primary fs-10" type="submit">Send<span class="fa-solid fa-paper-plane ms-1"></span></button>
<a href="{% url 'estimate_detail' estimate.pk %}" class="btn btn-sm btn-phoenix-secondary text-body fs-10 me-1">{{ _("Cancel") }}</a>
<button class="btn btn-sm btn-phoenix-primary fs-10" type="submit">{{ _("Send") }}<span class="fa-solid fa-paper-plane ms-1"></span></button>
</div>
</div>
</form>

View File

@ -103,8 +103,8 @@
<div class="d-flex bg-success-subtle rounded flex-center me-3 mb-sm-3 mb-md-0 mb-xl-3 mb-xxl-0" style="width:32px; height:32px"><span class="text-success-dark" data-feather="dollar-sign" style="width:24px; height:24px"></span></div>
<div>
<p class="fw-bold mb-1">{% trans 'Paid Amount' %}</p>
<h4 class="fw-bolder text-nowrap {% if invoice.is_paid %}text-success{% endif %}">{{invoice.amount_paid}}&nbsp;{{ CURRENCY }}</h4>
<h6 class="fw-bolder text-nowrap">{{ _("Owned") }} <span class="fw-semibold text-nowrap text-success">{{invoice.get_amount_open|floatformat}}&nbsp;{{ _("SAR") }}</span></h6>
<h4 class="fw-bolder text-nowrap {% if invoice.is_paid %}text-success{% endif %}">{{invoice.amount_paid}}&nbsp;<span class="currency">{{ CURRENCY }}</span></h4>
<h6 class="fw-bolder text-nowrap">{{ _("Owned") }} <span class="fw-semibold text-nowrap text-success">{{invoice.get_amount_open|floatformat}}&nbsp;<span class="currency">{{ CURRENCY }}</span></span></h6>
<div class="progress" style="height:17px">
<div class="progress-bar fw-semibold bg-{% if invoice.get_progress_percent < 100 %}secondary{% else %}success{% endif %} rounded-2" role="progressbar" style="width: {{invoice.get_progress_percent}}%" aria-valuenow="{{invoice.get_progress_percent}}" aria-valuemin="0" aria-valuemax="100">{{invoice.get_progress_percent}}%</div>
</div>
@ -156,9 +156,9 @@
<div>
<p class="fw-bold mb-1">{% trans 'Due Amount' %}</p>
{% if invoice.is_paid %}
<s><h4 class="fw-bolder text-nowrap">{{invoice.amount_due}}&nbsp;{{ _("SAR") }}</h4></s>
<s><h4 class="fw-bolder text-nowrap">{{invoice.amount_due}}&nbsp;<span class="currency">{{ CURRENCY }}</span></h4></s>
{% else %}
<h4 class="fw-bolder text-nowrap">{{invoice.amount_due}}&nbsp;{{ _("SAR") }}</h4>
<h4 class="fw-bolder text-nowrap">{{invoice.amount_due}}&nbsp;<span class="currency">{{ CURRENCY }}</span></h4>
{% endif %}
</div>
</div>

View File

@ -8,6 +8,7 @@
<!-- CSS -->
<link href="{% static 'css/theme.min.css' %}" type="text/css" rel="stylesheet" id="style-default">
<link href="{% static 'css/user.min.css' %}" type="text/css" rel="stylesheet" id="user-style-default">
<link href="{% static 'css/custom.css' %}" type="text/css" rel="stylesheet">
<!-- Google Fonts - Roboto -->
<link href="https://fonts.googleapis.com/css2?family=Roboto:wght@300;400;500;700&display=swap" rel="stylesheet">
<!-- Custom CSS -->
@ -70,9 +71,7 @@
width: 10mm;
height: 10mm;
}
.table-responsive {
overflow-x: auto;
}
</style>
</head>
<body>
@ -91,8 +90,8 @@
<div class="invoice-header">
<h5 class="fs-5">Tax&nbsp;Invoice&nbsp;&nbsp;/&nbsp;&nbsp;فاتورة&nbsp;ضريبية</h5>
</div>
<div class="invoice-details">
<table class="table table-sm table-responsive">
<div class="invoice-details p-1">
<table class="table table-sm table-responsive border-gray-50">
<tr>
<td>
<div class="qr-code">
@ -127,9 +126,8 @@
<td class="text-end"><strong>الرقم الضريبي</strong></td>
</tr>
</table>
</div>
<div class="invoice-details">
<table class="table table-sm table-bordered">
<table class="table table-sm table-bordered border-gray-50">
<tr>
<td class="ps-1"><strong>Invoice&nbsp;Number</strong></td>
<td class="text-center">{{ invoice.invoice_number }}</td>
@ -166,8 +164,8 @@
<span class="fs-9 fw-thin">Car&nbsp;Details</span>
<span class="fs-9 fw-thin">تفاصيل&nbsp;السيارة</span>
</div>
<div class="invoice-table">
<table class="table table-sm table-bordered">
<div class="invoice-table p-1">
<table class="table table-sm table-bordered m-1">
<thead>
<tr>
<th class="text-wrap text-center align-content-center"><span class="fs-10">Make</span> / <span class="fs-10">الصانع</span></th>
@ -207,13 +205,13 @@
</div>
{% if data.additionals %}
<div class="invoice-table">
<table class="table table-sm table-bordered">
<div class="invoice-table p-1">
<table class="table table-sm table-bordered m-1">
<thead>
<tr>
<th class="text-center fs-10 align-content-center">Type&nbsp;/&nbsp;النوع</th>
<th class="text-center fs-10 align-content-center">Price&nbsp;/&nbsp;القيمة</th>
<th class="text-center fs-10 align-content-center">Taxable&nbsp;/&nbsp;خاضع للضريبة</th>
<th class="text-center fs-10 align-content-center"><span class="fs-10">Including VAT</span> / <span class="fs-10">شامل الضريبة</span></th>
</tr>
</thead>
<tbody>
@ -221,33 +219,35 @@
<tr>
<td class="ps-1 text-start fs-10 align-content-center">{{ item.name }}</td>
<td class="ps-1 text-center fs-10 align-content-center">{{ item.price|floatformat:2 }}</td>
<td class="ps-1 text-center fs-10 align-content-center">{{ item.taxable|yesno:"نعم,لا" }}</td>
<td class="ps-1 text-center fs-10 align-content-center">{{ item.price_|floatformat:2 }}</td>
</tr>
{% endfor %}
</tbody>
</table>
</div>
{% endif %}
<div class="d-flex justify-content-end">
<div class="invoice-total d-flex justify-content-end">
<div class="table-responsive">
<table class="table table-sm table-responsive">
<tr>
<td class="text-start ps-1"><strong class="fs-9">VAT</strong></td>
<td class="text-center"><span class="fs-9">{{ data.total_vat_amount|floatformat:2 }} {{ CURRENCY }}</span></td>
<td class="text-center"><span class="fs-9">{{ data.total_vat_amount|floatformat:2 }} <span class="currency">{{ CURRENCY }}</span></span></td>
<td class="text-end"><strong class="fs-9">ضريبة&nbsp;القيمة&nbsp;المضافة</strong></td>
</tr>
<tr>
<td class="text-start ps-1"><strong class="fs-9">Total</strong></td>
<td class="text-center"><span class="fs-9">{{ data.grand_total|floatformat:2 }}&nbsp;{{ CURRENCY }}</span></td>
<td class="text-center"><span class="fs-9">{{ data.grand_total|floatformat:2 }}&nbsp;<span class="currency">{{ CURRENCY }}</span></span></td>
<td class="text-end"><strong class="fs-9">الإجمالي</strong></td>
</tr>
<tr>
<td class="text-end" colspan="3"><span class="fs-9 fw-bold">كتابةً:&nbsp;</span><span class="fs-9">{{ data.grand_total|num_to_words }}&nbsp;{{ CURRENCY }}</span></td>
<td class="text-end" colspan="3"><span class="fs-9 fw-bold">كتابةً:&nbsp;</span><span class="fs-9">{{ data.grand_total|num_to_words }}&nbsp;<span class="currency">{{ CURRENCY }}</span></span></td>
</tr>
</table>
</div>
</div>
<br><br>
<br><br>
<br><br>
<div class="footer-note">
<div class="logo-img text-center">
<img src="{% static 'images/logos/logo-d-pdf.png' %}" alt="Logo"/>

View File

@ -38,7 +38,7 @@
<br> in giving it a shot first.
</p>
<div class="d-flex align-items-end mb-md-5 mb-lg-0">
<h4 class="fw-bolder me-1">{{ plan.price|floatformat }} {% trans 'SAR' %}</h4>
<h4 class="fw-bolder me-1">{{ plan.price|floatformat }} <span class="currency">{{ CURRENCY }}</span></h4>
<h5 class="fs-9 fw-normal text-body-tertiary ms-1">{{ _("Per month")}}</h5>
</div>
</div>