feat(configurator): OWL widgets + Express form polish to match mockup
NEW OWL widgets: - FpExpressPartCell (static/src/js/express_part_cell.js + .xml) — multi-row Part cell. Wraps Many2OneField for the part picker (row 1: part# / rev, bold). Below it: row 2 part description (italic muted), row 3 serial #s joined + '+ bulk' button that triggers the existing bulk-add wizard. - FpExpressBakePill (static/src/js/express_bake_pill.js + .xml) — click- to-edit Bake pill. Renders amber pill when set, italic muted 'no bake' when empty. Click swaps to inline textarea + Save / Clear / Cancel. NEW fields: - fp.direct.order.line.part_number_display / part_revision_display / part_name_display (related Char from fp.part.catalog) — fed to the Part cell widget so it can render multi-row without RPC. - fp.direct.order.wizard.tooling_charge (Monetary) — surfaced in the Totals card on the Express form. - fp.direct.order.wizard.po_status (computed Selection received/pending/missing) — drives the PO Block status badge. - sale.order.x_fc_tooling_charge (Monetary) — receives wizard.tooling_charge at confirm. View updates (fp_express_order_views.xml): - PO block header now shows the PO status pill (green Received, amber Pending, red Missing) - Order Lines legend bar (Mask / Bake pill / DWG / OPEN explainers) - Part Number column uses widget='fp_express_part_cell' — single cell with 3 internal rows - Bake column uses widget='fp_express_bake_pill' — interactive pill - Totals card now has Subtotal / Tooling Charge / Total Lines / Total Quantity / Grand Total + currency pill SCSS adds: - Multi-row part cell styles (internal borders, bold/italic/muted rows) - Bake pill (has-bake amber, no-bake italic muted) + inline editor - Legend bar (section background, gap-spaced explainer chips) - PO status pill colour scheme - Bulk button styling Wizard's action_create_order now carries tooling_charge to the SO at confirm so it persists on the resulting sale.order.
This commit is contained in:
@@ -460,6 +460,24 @@ class FpDirectOrderLine(models.Model):
|
||||
)
|
||||
|
||||
# ---- Express Orders per-line flags (2026-05-26) ----
|
||||
# Related read-only fields so the FpExpressPartCell OWL widget can
|
||||
# render the multi-row Part cell (part# / revision / name / serials)
|
||||
# without needing extra RPCs.
|
||||
part_number_display = fields.Char(
|
||||
related='part_catalog_id.part_number',
|
||||
string='Part # (display)',
|
||||
readonly=True,
|
||||
)
|
||||
part_revision_display = fields.Char(
|
||||
related='part_catalog_id.revision',
|
||||
string='Revision (display)',
|
||||
readonly=True,
|
||||
)
|
||||
part_name_display = fields.Char(
|
||||
related='part_catalog_id.name',
|
||||
string='Part Name (display)',
|
||||
readonly=True,
|
||||
)
|
||||
customer_line_ref = fields.Char(
|
||||
string='Customer Line Job #',
|
||||
help='Per-line customer sub-reference (e.g. ABC, DEF). Distinct from '
|
||||
|
||||
@@ -274,6 +274,34 @@ class FpDirectOrderWizard(models.Model):
|
||||
help='Which view created this draft. Drafts list routes click-action '
|
||||
'to the matching form. Dropped at phase-out Phase 4.',
|
||||
)
|
||||
tooling_charge = fields.Monetary(
|
||||
string='Tooling Charge',
|
||||
currency_field='currency_id',
|
||||
help='Optional one-time tooling fee added to the order total. '
|
||||
'Carried to the SO and appears as a separate line on the '
|
||||
'customer invoice.',
|
||||
)
|
||||
|
||||
# ---- PO status pill (computed, display-only) ----
|
||||
po_status = fields.Selection(
|
||||
[('received', 'Received'),
|
||||
('pending', 'Pending'),
|
||||
('missing', 'Missing')],
|
||||
string='PO Status',
|
||||
compute='_compute_po_status',
|
||||
help='Computed: Received if PDF attached, Pending if po_pending=True, '
|
||||
'Missing otherwise.',
|
||||
)
|
||||
|
||||
@api.depends('po_attachment_file', 'po_pending')
|
||||
def _compute_po_status(self):
|
||||
for rec in self:
|
||||
if rec.po_attachment_file:
|
||||
rec.po_status = 'received'
|
||||
elif rec.po_pending:
|
||||
rec.po_status = 'pending'
|
||||
else:
|
||||
rec.po_status = 'missing'
|
||||
|
||||
# ---- Lines ----
|
||||
line_ids = fields.One2many(
|
||||
@@ -674,6 +702,7 @@ class FpDirectOrderWizard(models.Model):
|
||||
# Express Orders header (2026-05-26)
|
||||
'x_fc_internal_notes': self.internal_notes or False,
|
||||
'x_fc_material_process': self.material_process or False,
|
||||
'x_fc_tooling_charge': self.tooling_charge or 0.0,
|
||||
'pricelist_id': self.pricelist_id.id if self.pricelist_id else False,
|
||||
'validity_date': self.validity_date or False,
|
||||
'order_line': [],
|
||||
|
||||
Reference in New Issue
Block a user