You need to enable JavaScript to run this app. Odoo12 POS下OrderWidget重写set_value方法不生效 拟加自定义numpad模式求助
优惠活动
大模型
产品
解决方案
定价
更多

Odoo12 POS下OrderWidget重写set_value方法不生效 拟加自定义numpad模式求助

Odoo POS 重写 OrderWidget.set_value 不生效问题排查

核心根因

你遇到的“修改任意内容、甚至故意写错误代码都没有反应”的问题,本质是扩展的目标对象引用错误:你代码里使用的POSScreen.OrderWidget并不是POS系统里真实存在的OrderWidget组件引用,对未定义的对象执行include操作时,脚本会在初始化阶段直接中断,你写在include块内的所有自定义逻辑根本没有被解析执行,自然不会触发任何报错、也不会产生任何运行效果。

分场景正确扩展写法

Odoo 14 及以上版本(Owl组件架构)

全局POSScreen挂载点已经被废弃,OrderWidget是独立的Owl组件,需要从核心组件注册表获取真实引用后再扩展:

odoo.define('your_module_name.CustomOrderWidget', function(require) {
    'use strict';
    // 从核心模块导入真实的OrderWidget类
    const OrderWidget = require('point_of_sale.OrderWidget');
    const Registries = require('point_of_sale.Registries');

    // 类式继承扩展原有组件
    const ExtendOrderWidget = (OriginalOrderWidget) => class extends OriginalOrderWidget {
        async set_value(val) {
            // 先执行原有原生方法的全部逻辑
            await super.set_value(val);
            // 在这里写入你新增的自定义numpad模式处理逻辑
            const currentOrder = this.env.pos.get_order();
            const selectedLine = currentOrder?.get_selected_orderline();
            if (!selectedLine) return;
            
            const currentMode = this.numpad_state?.get('mode');
            if (currentMode === 'discount') {
                console.log('自定义折扣模式处理逻辑已触发');
                selectedLine.set_discount(val);
            }
        }
    }
    // 把扩展后的组件重新注册回POS核心注册表,覆盖原有组件
    Registries.Component.add(ExtendOrderWidget(OrderWidget));
});

Odoo 12/13 版本(Backbone架构)

这个版本的OrderWidget是挂在point_of_sale.screens模块下的,不能直接用全局POSScreen当挂载点:

odoo.define('your_module_name.CustomOrderWidget', function(require) {
    'use strict';
    // 从screens模块获取真实的OrderWidget引用
    const screens = require('point_of_sale.screens');

    screens.OrderWidget.include({
        set_value: function(val) {
            // 执行原有原生方法逻辑
            this._super(val);
            const currentOrder = this.pos.get_order();
            const selectedLine = currentOrder.get_selected_orderline();
            if (!selectedLine) return;

            const currentMode = this.numpad_state.get('mode');
            if (currentMode === 'discount') {
                console.log('自定义折扣模式处理逻辑已触发');
                selectedLine.set_discount(val);
            }
        }
    })
});

必做的校验步骤

  • 确认在模块的__manifest__.py配置里,自定义JS文件的加载顺序排在point_of_sale核心模块的JS资源之后,避免自定义代码先于核心组件定义执行,导致扩展被后续的原生组件覆盖。
  • 打开浏览器开发者工具的网络面板,确认你的自定义JS文件没有出现404加载失败的问题。
  • 在自定义set_value方法的第一行加上console.trace('进入自定义set_value'),点击POS的数字键盘按键,如果控制台没有输出这条日志,就说明扩展逻辑没有触达真实的组件实例。

内容的提问来源于stack exchange,提问作者user9523333

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.11.06 19:06:04