۱. ورودی‌ها و پارامترهای قابل تنظیم

مشتری در ماشین‌حساب ابتدا از منوی دکمه‌ای دسته‌بندی و سپس محصول (نوع جعبه) انتخاب می‌کند؛ سپس ابعاد، تیراژ و مواد را تکمیل می‌کند:

ورودینمادواحد
دسته‌بندیboxCategoryIdانتخاب از منو
نوع جعبه / محصولboxTypeIdانتخاب از لیست همان دسته
طول جعبهLسانتی‌متر
عرض جعبهWسانتی‌متر
ارتفاع جعبهHسانتی‌متر
تعداد سفارشQعدد
نوع کاغذانتخاب از لیست
روکش UVhasUVبله / خیر
طلاکوبhasGoldبله / خیر

از هر کاغذ: ابعاد ورق (sheetLength، sheetWidth)، گرماژ، قیمت بند (bundle). از پنل: چاپ، دایکات، UV، طلاکوب، سود، مالیات، چسباندن، طراحی و بسته‌بندی.

۲. کاتالوگ دسته‌بندی و محصول

محصولات در پنل مدیر در دو سطح مدیریت می‌شوند:

  • دسته‌ها (box_categories): کیبوردی، لمینتی، کشویی، دسته‌دار، سروته شربتی، سفره‌ای، درب و زیره، خاص — با sort_order برای ترتیب نمایش (کیبوردی اول، خاص آخر).
  • انواع جعبه (box_types): هر محصول به یک دسته وصل است؛ می‌تواند uses_custom_dimensions داشته باشد یا سایز ثابت (length_cm, width_cm, height_cm).
  • تصویر محصول (image_path): در ماشین‌حساب بلافاصله زیر دسته‌ها و بالای انتخاب محصول نمایش داده می‌شود (در موبایل تصویر قبل از فیلد select قرار می‌گیرد تا نیاز به اسکرول طولانی نباشد).

پیش‌فرض ماشین‌حساب: اولین دسته بر اساس sort_order (معمولاً کیبوردی) انتخاب می‌شود، نه اولین دسته‌ای که محصول دارد.

برای نمایش تصاویر در مرورگر، یک‌بار php artisan storage:link اجرا شود.

۳. نوع جعبه و اجزای آن

مدل جعبه شبیه جعبه دارو است:

  • پشت ↔ رو — دو وجه مقابل L×W (پشت در وسط دایکات، رو در بالا).
  • ته ↔ درب — ته چسب‌خورده W×H (پایین دایکات)؛ درب جلو + لبه‌تا (بازشدنی).
  • چپ و راست — دو پهلو H×L.
در مدل سه‌بعدی: بالا/پایین = رو/پشت (L×W)، جلو/عقب = درب/ته (L×H).

۴. ابعاد گسترده (الگوی تخت — ایفلوت و مقوایی)

برای هر دو نوع جعبه یک فرمول واحد است. marginCm، pattern (tuck_end، rsc، mailer و …) و ابعاد شیت SVG در محاسبه گسترده استفاده نمی‌شوند.

flatWidth = (4 × H) + L + 0.5 + 0.5
flatLength = (2 × W) + (3 × H) + 0.5

۰٫۵ اول = عطف لب برگردان، ۰٫۵ دوم = پرتی برش. ایفلوت: چیدمان رول با EfluteRollLayout::optimize(flatWidth). مقوایی: چیدمان روی ورق ثابت با همان ابعاد.

مثال: L=35.5, W=25, H=4.5 → گسترده 54.5 × 64.0 cm.

انتخاب سایز استاندارد دایکات

پس از محاسبه flatLength و flatWidth، بین سایزهای استاندارد زیر (DieCutSheetLayout::optimize) شیت با کمترین پرتی انتخاب می‌شود (هر سایز در هر دو جهت چرخیده امتحان می‌شود).

مثال: گسترده 54.5×64 cm → سایز 60×90 با کمترین پرتی.

سایز دایکات (cm)ابعاد شیت (طول × عرض)
50×7050 × 70
100×70100 × 70
45×6045 × 60
60×9060 × 90

۵. چیدمان روی ورق و تعداد ورق مصرفی

ورق کاغذ ابعاد ثابت دارد (sheetLength × sheetWidth بر حسب سانتی‌متر). دو حالت چرخش الگوی گسترده مقایسه می‌شود:

چیدمان افقی

horizontalTotal = floor(sheetLength / flatLength) × floor(sheetWidth / flatWidth)

چیدمان عمودی (چرخش ۹۰° الگو)

verticalTotal = floor(sheetLength / flatWidth) × floor(sheetWidth / flatLength)

انتخاب و تعداد ورق

boxesPerSheet = max(1 , max(horizontalTotal , verticalTotal))
sheetsNeeded = ceil(Q / boxesPerSheet)
چیدمان «افقی» یا «عمودی» بر اساس بیشترین تعداد جعبه روی هر ورق انتخاب و در خروجی گزارش می‌شود.

۶. هزینه کاغذ

هزینه هر ورق از قیمت بند کاغذ و تعداد برگ در بند محاسبه می‌شود (نه مستقیم از pricePerKg در این مرحله):

sheetCost = bundlePrice / paperPerBundle
totalSheetsCost = sheetCost × sheetsNeeded
bundlesNeeded = ceil(sheetsNeeded / paperPerBundle)

در نتیجه محاسبه، بند مصرفی برای سفارش کاغذ از فروشنده نمایش داده می‌شود (گرد به بالا؛ ممکن است چند ورق بیشتر از مصرف چاپ در بند آخر باشد).

برای نمایش و ثبت کاغذ، pricePerKg از روی وزن تقریبی هر برگ و قیمت بند مشتق می‌شود؛ ولی در فرمول قیمت نهایی سفارش، مبنای هزینه ورق همان sheetCost بالاست.

sheetAreaM2 = (sheetLength × sheetWidth) / 10000

مساحت ورق (متر مربع) در هزینه چاپ استفاده می‌شود.

۷. چاپ افست (دور چاپ + زینک)

هزینه دایکات در بخش ۷-۱ جدا توضیح داده شده است.

هزینه چاپ دیگر بر اساس متر مربع نیست. بر اساس دور چاپ (تعداد ورق قابل‌صورتحساب، گرد به بالا و مضرب ۱۰۰۰) و پلکان‌های تعریف‌شده در پنل مدیر محاسبه می‌شود.

billableImpressions = max( ceil(sheetsNeeded/1000)×1000 , ceil(quantity/1000)×1000 ) — هر کدام حداقل ۱۰۰۰

اگر تیراژ سفارش (مثلاً ۲۸۰۰ عدد) پلکان بالاتری از ورق مصرفی بخواهد، همان تیراژ مبنای انتخاب پلکان است (مثلاً ۳۰۰۰ دور، نه ۲۰۰۰).

ورق مصرفیدور چاپ
۱ تا ۹۹۹۱۰۰۰
۱۰۰۰۱۰۰۰
۱۲۰۰۲۰۰۰
۲۵۰۱۳۰۰۰

در پنل هزینه چاپ افست و هزینه زینک برای هر پلکان ۱۰۰۰ تا ۵۰۰۰ دور فقط printCost (هزینه چاپ) وارد می‌شود.

اگر billable ≤ 5000 → کوچک‌ترین پلکان ≥ billable
اگر billable > 5000 → printCost = پلکان ۵۰۰۰ × ceil(billable / 5000)

زینک (یک‌بار برای سفارش)

هزینه زینک با افزایش دور چاپ ضرب نمی‌شود؛ همان زینک تا پنج هزار دور (و بیشتر) برای یک سفارش کافی است.

zincCost = zincPlatePrice

هر سفارش فقط یک زینک دارد؛ مبلغ آن در پنل مدیر یک‌بار وارد می‌شود.

طلاکوب بر اساس پلکان تیراژ و سایز طرح است (بخش ۱۱).

۷-۱. دایکات — سایز استاندارد و قیمت

برای هر سایز، هزینهٔ یک‌بار قالب‌زنی / دایکات برای کل سفارش است (نه به ازای هر جعبه). سایز از ابعاد گسترده با کمترین پرتی انتخاب می‌شود (بخش ۴. ابعاد گسترده).

totalDieCutCost = dieCutCostsBySize[sizeLabel]

sizeLabel یکی از برچسب‌های جدول زیر است (مثلاً 60×90). ویرایش قیمت‌ها: پنل دایکات · نمای زنده: داشبورد قیمت‌ها.

سایزهای استاندارد دایکات

برای هر سایز، هزینهٔ یک‌بار قالب‌زنی / دایکات برای کل سفارش را در پنل وارد کنید. مثال: گستردهٔ 54.5×64 cm → سایز 60×90 با کمترین پرتی انتخاب می‌شود.

سایز دایکات (cm) هزینه (تومان) توضیح
50×70 1,800,000 یک‌بار برای کل سفارش
100×70 2,500,000 یک‌بار برای کل سفارش
45×60 1,800,000 یک‌بار برای کل سفارش
60×90 2,500,000 یک‌بار برای کل سفارش
این قیمت‌ها برای جعبه مقوایی در ماشین‌حساب استفاده می‌شوند. برای ایفلوتی هم همان سایزها و همان جدول قیمت (پس از ذخیره در پنل دایکات) اعمال می‌شود.

۸. چسباندن و دستمزد

assemblyQuantity = max(Q , assemblyMinQuantity)
totalAssemblyCost = assemblyLaborCost × assemblyQuantity
مثال: سفارش ۳۰۰ عدد، حداقل ۱۰۰۰ → هزینه چسباندن برای ۱۰۰۰ جعبه؛ سهم هر جعبه در قیمت واحد: تقسیم بر Q.

۹. هزینه طراحی

مشتری ساعت طراحی وارد نمی‌کند؛ همیشه از حداقل ساعت طراحی تنظیم‌شده توسط مدیر استفاده می‌شود.

designBillableHours = designMinHours
totalDesignCost = round(designHourlyRate × designBillableHours)

۱۰. بسته‌بندی نهایی

packagingQuantity = max(Q , packagingMinQuantity)
totalPackagingCost = packagingCost × packagingQuantity

۱۱. UV و طلاکوب (اختیاری — مقوایی)

روکش UV

سایز ورق مثل دایکات از گسترده با کمترین پرتی انتخاب می‌شود (sizeLabel — بخش ۷-۱).

uvQuantityForPricing = max(Q , cardboardUvMinQuantity)
totalUVCost = hasUV ? uvCostsBySize[sizeLabel] × uvQuantityForPricing : 0

مثل چسباندن: اگر تیراژ کمتر از حداقل باشد، هزینه با همان حداقل محاسبه می‌شود.

حداقل تیراژ: 1,000 · ویرایش در پنل روکش UV.

سایز ورق (cm)هزینه UV هر جعبه (تومان)
50×70 5,000
100×70 8,000
45×60 5,000
60×90 8,000

طلاکوب

goldStampCost = costPerStroke(پلکان، سایز طرح) × تعداد ضرب
totalGoldCost = hasGold ? goldStampCost : 0

۱۲. جمع، سود و مالیات

totalCostOrder = totalSheetsCost + printCost + zincCost + totalDieCutCost + totalAssemblyCost + totalPackagingCost + totalDesignCost + totalUVCost + totalGoldCost
costPerBox = totalCostOrder / Q
priceWithProfit = costPerBox × (1 + profitPercent / 100)
preliminaryTotal = round(priceWithProfit × (1 + taxPercent / 100) × Q)
totalOrderPrice = ceil(preliminaryTotal / 1٬000٬۰۰۰) × 1٬000٬۰۰۰
pricePerBox = ceil(ceil(totalOrderPrice / Q) / 100) × 100
سود و مالیات مرکب؛ قیمت کل سفارش همیشه به بالا تا نزدیک‌ترین میلیون گرد می‌شود (مثلاً ۷۷٬۴۰۰٬۷۹۱ → ۷۸٬۰۰۰٬۰۰۰). قیمت هر جعبه نیز همیشه به بالا تا مضرب ۱۰۰ تومان. جمع نهایی = قیمت هر جعبه × تیراژ.

۱۳. نمایش در ماشین‌حساب مشتری

بارگذاری صفحه: HTML ماشین‌حساب سبک است؛ دادهٔ قیمت‌ها با GET /api/calculator-data (قابل کش ۵ دقیقه) و اسکریپت calculator.js با defer بارگذاری می‌شوند.

دو رابط: /calculator (ویزارد گام‌به‌گام) و /calculator/single-page (همهٔ ۷ مرحله در یک صفحه با همان منطق محاسبه).

ویزارد گام‌به‌گام (۷ مرحله):

  1. نوع جعبه — مقوایی یا ایفلوتی (فیلتر دسته‌ها و کاغذها)
  2. دسته‌بندی — منوی دکمه‌ای دسته‌های همان نوع
  3. نوع سفارش — «محصول آماده (سایز ثابت)» یا «سایز دلخواه»؛ سپس انتخاب محصول همان دسته
  4. انتخاب محصول — در حالت آماده: محصولات با ابعاد ثبت‌شده؛ در حالت دلخواه: محصولات با فلگ ابعاد دلخواه (پیش‌نمایش در گام ۳)
  5. ابعاد و تیراژ — برای محصول سفارشی: ابعاد داخلی + تیراژ + پیش‌نمایش؛ برای محصول ثابت: فقط تیراژ (پیش‌نمایش در گام قبل است)
  6. پوشش (اختیاری) — روکش UV و طلاکوب
  7. ورق — انتخاب نوع کاغذ / ورق
  8. محاسبه و نتیجه — دکمهٔ «محاسبه قیمت»؛ نمایش قیمت هر جعبه (با سود و مالیات) و جزئیات فنی

در هر گام فقط همان بخش نمایش داده می‌شود؛ دکمه‌های «مرحله قبل» و «ادامه» (در گام ۶: «محاسبه قیمت») جابه‌جایی را کنترل می‌کنند.

در موبایل نوار ثابت پایین: «ادامه» (گام ۱–۵) یا «محاسبه قیمت» (گام ۶).

پس از وارد کردن L، W و H، سه نما به‌روز می‌شوند:

نمانوعکاربرد
موکاپ برداری (فنی)SVG ایزومتریکابعاد روی لبه‌ها، لبه تا (گوشه گرد فقط لبه آزاد)
نمای سه‌بعدیمدل CSSدرک حجمی؛ چرخش با ماوس/لمس
الگوی گستردهSVG دایکاتپشت، رو، چپ، راست، ته، لبه‌تا، پوشال

فرمول‌های بخش ۳ منبع هر سه نما هستند؛ تغییر ابعاد ورودی همه را هم‌زمان به‌روز می‌کند.

۱۴. API محاسبه

درخواست: POST /api/calculate

فیلدنوعتوضیح
boxTypeIdintegerشناسه نوع جعبه (اختیاری؛ در صورت ارسال، الگوی همان نوع اعمال می‌شود)
lengthnumberطول L (cm)
widthnumberعرض W (cm)
heightnumberارتفاع H (cm)
quantityintegerتعداد Q
paperIdintegerشناسه کاغذ فعال
hasUVbooleanروکش UV
hasGoldbooleanطلاکوب

خروجی مهم (در data):

فیلدتوضیح
pricePerBoxقیمت هر جعبه با سود و مالیات (تومان)
totalOrderPriceقیمت کل سفارش
flatLengthطول گسترده (cm)
flatWidthعرض گسترده (cm)
tuckFlapDepthعمق لبه تا tuckT (cm)
boxesPerSheetتعداد جعبه روی هر ورق
sheetsNeededتعداد ورق مصرفی
layoutافقی یا عمودی
billablePrintImpressionsدور چاپ قابل‌صورتحساب
printTierKeyپلکان انتخاب‌شده (۱۰۰۰ تا ۵۰۰۰)
printCostهزینه چاپ (پلکان دور چاپ)
zincPlatePrice / zincCostهزینه زینک (یک‌بار برای سفارش)
dieCutCostهزینه دایکات (کل سفارش)
assemblyCostهزینه چسباندن
packagingCostهزینه بسته‌بندی
uvCost / uvUnitCost / uvSizeLabel / uvMinQuantity / uvQuantityForPricing / hasUVهزینه روکش UV (در صورت انتخاب)
goldCost / hasGoldهزینه طلاکوب (در صورت انتخاب)
assemblyQuantityتیراژ مبنای چسباندن
packagingQuantityتیراژ مبنای بسته‌بندی
designBillableHoursساعت طراحی (همان designMinHours مدیر)

۱۵. ارتباط با صفحات پنل

صفحهپارامترها
دسته‌بندی جعبه/admin/box-categories — نام، ترتیب نمایش
انواع جعبه / محصولات/admin/box-types — دسته، ابعاد ثابت، تصویر، الگوی ساخت
هزینه چاپ افست و هزینه زینکپلکان چاپ افست (۱۰۰۰–۵۰۰۰ دور)، هزینه زینک (یک‌بار)
دایکات/admin/die-cut — قیمت هر سایز استاندارد
روکش UV/admin/uv — قیمت یک‌بار UV به ازای سایز استاندارد
طلاکوب/admin/gold-stamp — پلکان تیراژ × سایز طرح
داشبورد قیمت‌ها/admin/prices-dashboard — نمای زندهٔ همهٔ قیمت‌ها
چسباندنassemblyLaborCost، assemblyMinQuantity
طراحیdesignHourlyRate، designMinHours
بسته‌بندیpackagingCost، packagingMinQuantity
مشخصات شرکت / پیش‌فاکتور/admin/company-profile — لوگو، مهر، آدرس، تلفن، حساب، شبا · در ماشین‌حساب گام ۷: نام و مشخصات مشتری
آرشیو پیش‌فاکتورها/admin/preinvoices — تاریخ، مشتری، مدل جعبه (مقوایی/ایفلوتی/…)، ابعاد، قیمت · جستجو: GET /api/preinvoices?q=
اشتراک پیش‌فاکتورPOST /api/preinvoices/shareGET /preinvoice/{token} (لینک عمومی برای شبکه‌های اجتماعی)
کاغذهاابعاد ورق، gsm، bundlePrice، paperPerBundle
ماشین‌حساب / APIاجرای تمام فرمول‌های این سند

منطق محاسبه در مرورگر (ماشین‌حساب مشتری) و POST /api/calculate یکسان است.

برای مشاهدهٔ همهٔ قیمت‌های ثبت‌شده (زنده از دیتابیس) به داشبورد قیمت‌ها بروید.