fix factors list and doble factor submit

This commit is contained in:
javad committed 2026-07-18 20:02:12 +03:30
1 parent c33184a996
commit b86ccb373b
3 files changed
+317 -37

No files matched your search

@@ -246,10 +246,14 @@
//دکمه ثبت فاکتور //دکمه ثبت فاکتور
$("#submitFactor").click(function(){ $("#submitFactor").click(function(){
//$("#disablePage").addClass("is-active"); // اگر دکمه قبلاً غیرفعال شده باشد، دیگر کاری انجام ندهد
if ($(this).hasClass("is-loading")) {
return false;
}
$("#prdsList").val(JSON.stringify(orderList)); $("#prdsList").val(JSON.stringify(orderList));
$("#sarResidDate").val( $("#sarResidDateSL").val() ) $("#sarResidDate").val( $("#sarResidDateSL").val() )
$("#payType").val( $("#FpayType").val() ) $("#payType").val( $("#FpayType").val() )
@@ -296,33 +300,34 @@
} }
}) })
//console.log(sumPardakhti)
//sumPardakhti += int(paylist['l_naghd'])
//sumPardakhti += int(paylist['l_kartKhan'])
//sumPardakhti += int(paylist['l_kartbekart'])
//sumPardakhti += int(paylist['l_checkPrice'])
//sumPardakhti += int(paylist['l_nesiye'])
if(nesiyeOk && checkOk && !Object.values(paylist).every(o => o === null) ){ if(nesiyeOk && checkOk && !Object.values(paylist).every(o => o === null) ){
if(sumPardakhti==sumALL_factor){ if(sumPardakhti==sumALL_factor){
//alert("ok")
// --- تغییرات اصلی برای جلوگیری از کلیک مجدد اینجاست ---
var $btn = $("#submitFactor");
// 1. اضافه کردن کلاس لودینگ Bulma و غیرفعال کردن دکمه
$btn.addClass("is-loading").prop("disabled", true).css("pointer-events", "none");
// 2. فعال کردن لایه تاریک روی صفحه که خودتان ساخته بودید (از کامنت خارج شد)
$("#disablePage").addClass("is-active");
// 3. ارسال فرم
$("#subFactor").submit(); $("#subFactor").submit();
// --------------------------------------------------------
}else{ }else{
console.log(sumPardakhti, " ", sumALL_factor) console.log(sumPardakhti, " ", sumALL_factor)
alert("جمع فاکتور با مبالغ پرداختی همخوانی ندارد") alert("جمع فاکتور با مبالغ پرداختی همخوانی ندارد")
} }
//
}else{ }else{
alert("لطفا فرم را کنترل کنید") alert("لطفا فرم را کنترل کنید")
} }
}); });
//پایان دکمه ثبت فاکتور //پایان دکمه ثبت فاکتور
$("#categoryS").change(function(){ $("#categoryS").change(function(){
var cat_id = $(this).val(); var cat_id = $(this).val();
@@ -3,30 +3,251 @@
{% load static %} {% load static %}
{% block BodyCustomer1 %} {% block BodyCustomer1 %}
<div id="factorha" class="column is-12-mobile is-12-desktop"> <div id="factorha" class="column is-12-mobile is-12-desktop p-3">
<span class="button mb-3 is-info is-hidden">ایجاد فاکتور</span>
<div class="is-flex is-justify-content-space-between is-align-items-center mb-3 pb-2" style="border-bottom: 2px solid #dbdbdb;">
<h2 class="title is-5 m-0 has-text-weight-bold has-text-dark">مدیریت فاکتورهای مشتری</h2>
<a href="{% url 'admin_panel:customerNew' customer.id %}" class="button is-info is-small" style="border-radius: 0px;">
<span>+ ایجاد فاکتور جدید</span>
</a>
</div>
{% for factor in factorha %} <form method="get" action="" class="mb-3 has-background-white-ter p-2" style="border: 1px solid #dbdbdb;">
<a href="{% url 'admin_panel:customerFactor' customer.id factor.id %}"> <div class="columns is-mobile is-multiline is-variable is-1">
<div class="columns m-0 mb-4 is-multiline is-mobile has-text-centered {% if factor.pay_status %}{{ factor.pay_status }}{% endif %}">
<div class="column is-12-mobile is-3-desktop">
<div class="field">
<div class="control">
<input name="search_factor" value="{{ search_query }}" class="input is-small" type="text" placeholder="جستجوی شماره فاکتور یا بابت..." style="border-radius: 0px;">
</div>
</div>
</div>
<div class="column is-4-mobile is-4-desktop"> <div class="column is-6-mobile is-2-desktop">
{{ factor.create_date | toJalali }} <div class="field">
<div class="control">
<div class="select is-small is-fullwidth" style="border-radius: 0px;">
<select name="type" style="border-radius: 0px;">
<option value="all" {% if filter_type == 'all' %}selected{% endif %}>— همه انواع —</option>
<option value="Nasb" {% if filter_type == 'Nasb' %}selected{% endif %}>نصب</option>
<option value="Khadamat" {% if filter_type == 'Khadamat' %}selected{% endif %}>خدمات</option>
<option value="Garranty" {% if filter_type == 'Garranty' %}selected{% endif %}>گارانتی</option>
</select>
</div>
</div>
</div>
</div>
<div class="column is-6-mobile is-2-desktop">
<div class="field">
<div class="control">
<div class="select is-small is-fullwidth" style="border-radius: 0px;">
<select name="status" style="border-radius: 0px;">
<option value="all" {% if filter_status == 'all' %}selected{% endif %}>— همه وضعیت‌ها —</option>
<option value="paid" {% if filter_status == 'paid' %}selected{% endif %}>پرداخت شده</option>
<option value="unpaid" {% if filter_status == 'unpaid' %}selected{% endif %}>پرداخت نشده</option>
<option value="cancell" {% if filter_status == 'cancell' %}selected{% endif %}>لغو شده</option>
<option value="deleted" {% if filter_status == 'deleted' %}selected{% endif %}>باطل شده (حذف نرم)</option>
</select>
</div>
</div>
</div>
</div>
<div class="column is-6-mobile is-2-desktop">
<div class="field">
<div class="control">
<input name="az_tarikh" id="azTarikhFilter" value="{{ az_tarikh }}" class="input is-small ss02" type="text" placeholder="از تاریخ" style="border-radius: 0px;" autocomplete="off">
</div>
</div>
</div>
<div class="column is-6-mobile is-2-desktop">
<div class="field">
<div class="control">
<input name="ta_tarikh" id="taTarikhFilter" value="{{ ta_tarikh }}" class="input is-small ss02" type="text" placeholder="تا تاریخ" style="border-radius: 0px;" autocomplete="off">
</div>
</div>
</div>
<div class="column is-12-mobile is-1-desktop">
<button type="submit" class="button is-dark is-small is-fullwidth" style="border-radius: 0px;">
فیلتر
</button>
</div>
</div> </div>
<div class="column is-4-mobile is-4-desktop"> </form>
{{ factor.user.first_name }} {{ factor.user.last_name }}
{% if search_query or az_tarikh or ta_tarikh or filter_status != 'all' or filter_type != 'all' %}
<div class="is-flex is-justify-content-between is-align-items-center p-2 mb-2 has-background-warning-light" style="border: 1px solid #ffe08a; border-radius: 0px; font-size: 0.8rem;">
<div class="has-text-warning-dark">
<strong>وضعیت:</strong> نتایج در حال حاضر بر اساس فیلترهای انتخابی شما محدود شده‌اند.
</div> </div>
<div class="column is-4-mobile is-4-desktop"> <a href="{% url 'admin_panel:customerFactors' customer.id %}" class="button is-small is-danger is-outlined py-0 px-2" style="border-radius: 0px; height: 22px; font-size: 0.75rem;">
{{ factor.amount }} حذف فیلترها و نمایش همه فاکتورها
</div> </a>
</div>
{% endif %}
<div class="table-container m-0">
<table class="table is-bordered is-striped is-narrow is-fullwidth is-hoverable solution-table">
<thead>
<tr class="has-background-light">
<th style="width: 60px;">شماره</th>
<th style="width: 90px;">نوع فاکتور</th>
<th style="width: 100px;">تاریخ ثبت</th>
<th style="width: 100px;">سررسید</th>
<th style="width: 100px;">مبلغ (تومان)</th>
<th style="width: 100px;">نوع پرداخت</th>
<th>توضیحات / بابت</th>
<th style="width: 110px;">کاربر ثبت کننده</th>
<th style="width: 95px;">وضعیت</th>
<th style="width: 65px;">عملیات</th>
</tr>
</thead>
<tbody>
{% if factorha %}
{% for factor in factorha %}
<tr class="{% if not factor.is_active %}row-deleted-factor{% endif %}">
<td class="has-text-weight-bold">{{ factor.id }}</td>
<td>
{% if factor.FactorType == 'Nasb' %}نصب
{% elif factor.FactorType == 'Khadamat' %}خدمات
{% elif factor.FactorType == 'Garranty' %}گارانتی
{% else %}{{ factor.FactorType }}{% endif %}
</td>
<td class="is-size-7 ss02">{{ factor.create_date | toJalali }}</td>
<td class="is-size-7 ss02">
{% if factor.deadline %}
{{ factor.deadline | toJalali }}
{% else %}
<span class="has-text-grey-light">—</span>
{% endif %}
</td>
<td class="has-text-weight-semibold format-price text-left-dir">{{ factor.amount }}</td>
<td class="is-size-7">
{% if factor.PayType == 'naghd' %}نقدی
{% elif factor.PayType == 'cardToCard' %}کارت به کارت
{% elif factor.PayType == 'kartKhan' %}کارت‌خوان
{% elif factor.PayType == 'nesiye' %}نسیه
{% elif factor.PayType == 'check' %}چک
{% else %}{{ factor.PayType }}{% endif %}
</td>
<td class="has-text-right" style="max-width: 250px; text-overflow: ellipsis; overflow: hidden; white-space: nowrap;" title="{{ factor.desc }}">
{{ factor.desc | default:"—" }}
</td>
<td class="is-size-7">{{ factor.user.first_name }} {{ factor.user.last_name }}</td>
<td>
{% if not factor.is_active %}
<span class="status-badge status-deleted">باطل شده</span>
{% else %}
{% if factor.pay_status == 'paid' %}
<span class="status-badge status-paid">پرداخت شده</span>
{% elif factor.pay_status == 'unpaid' %}
<span class="status-badge status-unpaid">معوق / مانده</span>
{% elif factor.pay_status == 'cancell' %}
<span class="status-badge status-cancelled">لغو شده</span>
{% else %}
<span class="status-badge status-neutral">{{ factor.pay_status }}</span>
{% endif %}
{% endif %}
</td>
<td>
<a href="{% url 'admin_panel:customerFactor' customer.id factor.id %}" class="button is-small is-link is-outlined py-0 px-2" style="height: 20px; border-radius: 0px; font-size: 0.75rem;">
مشاهده
</a>
</td>
</tr>
{% endfor %}
{% else %}
<tr>
<td colspan="10" class="has-text-centered has-text-grey p-4">
هیچ فاکتوری با فیلترهای مشخص شده یافت نشد.
</td>
</tr>
{% endif %}
</tbody>
</table>
</div> </div>
</a>
{% endfor %}
</div> </div>
<style>
.solution-table {
border-radius: 0px !important;
font-size: 0.85rem;
}
.solution-table th, .solution-table td {
border-radius: 0px !important;
text-align: center !important;
vertical-align: middle !important;
padding: 6px 4px !important;
border: 1px solid #dcdcdc !important;
}
.text-left-dir {
text-align: left !important;
padding-left: 8px !important;
}
.row-deleted-factor {
background-color: #fff1f3 !important;
color: #cc2543 !important;
text-decoration: line-through;
}
.row-deleted-factor td a {
text-decoration: none !important;
}
.status-badge {
display: block;
font-size: 0.75rem;
font-weight: bold;
padding: 2px 4px;
border: 1px solid;
text-decoration: none !important;
}
.status-paid { background-color: #ebfffc; border-color: #00d1b2; color: #00796b; }
.status-unpaid { background-color: #fffbeb; border-color: #ffe08a; color: #8a6d00; }
.status-cancelled { background-color: #fafafa; border-color: #dbdbdb; color: #7a7a7a; }
.status-deleted { background-color: #ffebee; border-color: #f14668; color: #c51162; text-decoration: none !important; }
.status-neutral { background-color: #eceff1; border-color: #b0bec5; color: #37474f; }
</style>
{% endblock %} {% endblock %}
{% block BodyCustomer2 %} {% block BodyCustomer2 %}
{% endblock %}
{% block jsEnd %}
{{ block.super }}
<script>
// فعال‌سازی تقویم شمسی روی فیلدهای فیلتر تاریخ جدید
$("#azTarikhFilter, #taTarikhFilter").pDatepicker({
initialValue: false,
initialValueType: 'en',
format: 'YYYY/MM/DD',
autoClose: true,
calendar:{
persian: {
locale: 'fa',
leapYearMode: 'astronomical'
}
}
});
</script>
{% endblock %} {% endblock %}
+60 -6
View File
@@ -693,14 +693,68 @@ def customerNew2(request ,c_id):
@login_required(login_url='/panel/p_login/') @login_required(login_url='/panel/p_login/')
def customerFactors(request ,c_id): def customerFactors(request, c_id):
customer = Customer.objects.get(id=c_id) customer = get_object_or_404(Customer, id=c_id)
categorys = ProductCategory.objects.all() categorys = ProductCategory.objects.all()
factorha = Factor.objects.filter(customer__id = c_id).order_by('-create_date')
#all_prd = serializers.serialize("json", all_prda) # کوئری پایه برای دریافت همه فاکتورهای این مشتری
#return JsonResponse(all_prd,safe = False) factor_qs = Factor.objects.filter(customer=customer)
# دریافت پارامترهای فیلتر و جستجو از آدرس URL
search_query = request.GET.get('search_factor', '').strip()
filter_status = request.GET.get('status', 'all')
filter_type = request.GET.get('type', 'all')
az_tarikh = request.GET.get('az_tarikh', '').strip()
ta_tarikh = request.GET.get('ta_tarikh', '').strip()
# ۱. اعمال فیلتر جستجو (شناسه فاکتور یا متن توضیحات)
if search_query:
if search_query.isdigit():
factor_qs = factor_qs.filter(models.Q(id=int(search_query)) | models.Q(desc__icontains=search_query))
else:
factor_qs = factor_qs.filter(models.Q(desc__icontains=search_query))
# ۲. اعمال فیلتر وضعیت پرداخت و حذف نرم
if filter_status != 'all':
if filter_status == 'deleted':
factor_qs = factor_qs.filter(is_active=False)
else:
factor_qs = factor_qs.filter(pay_status=filter_status, is_active=True)
# ۳. اعمال فیلتر نوع فاکتور (نصب، خدمات، گارانتی)
if filter_type != 'all':
factor_qs = factor_qs.filter(FactorType=filter_type)
# ۴. اعمال فیلتر تاریخ شروع (از تاریخ)
if az_tarikh:
az_gregorian = _parse_jalali_date(az_tarikh)
if az_gregorian:
az_datetime = datetime.datetime.combine(az_gregorian, datetime.time.min)
factor_qs = factor_qs.filter(create_date__gte=az_datetime)
# ۵. اعمال فیلتر تاریخ پایان (تا تاریخ)
if ta_tarikh:
ta_gregorian = _parse_jalali_date(ta_tarikh)
if ta_gregorian:
ta_datetime = datetime.datetime.combine(ta_gregorian, datetime.time.max)
factor_qs = factor_qs.filter(create_date__lte=ta_datetime)
# مرتب‌سازی بر اساس آخرین تاریخ ایجاد
factorha = factor_qs.order_by('-create_date')
dateNow = datetime.datetime.now().date dateNow = datetime.datetime.now().date
data = {'customer': customer, 'categorys': categorys, 'dateNow': dateNow, 'factorha': factorha}
data = {
'customer': customer,
'categorys': categorys,
'dateNow': dateNow,
'factorha': factorha,
'search_query': search_query,
'filter_status': filter_status,
'filter_type': filter_type,
'az_tarikh': az_tarikh,
'ta_tarikh': ta_tarikh
}
return render(request, 'admin_panel/customerIDFactor.html', data) return render(request, 'admin_panel/customerIDFactor.html', data)
@login_required(login_url='/panel/p_login/') @login_required(login_url='/panel/p_login/')