diff --git a/addons/point_of_sale/__manifest__.py b/addons/point_of_sale/__manifest__.py index 351ca106e87..c275471a0c9 100644 --- a/addons/point_of_sale/__manifest__.py +++ b/addons/point_of_sale/__manifest__.py @@ -23,6 +23,7 @@ 'views/point_of_sale_view.xml', 'views/pos_order_view.xml', 'views/pos_category_view.xml', + 'views/pos_combo_view.xml', 'views/product_view.xml', 'views/account_journal_view.xml', 'views/pos_payment_method_views.xml', diff --git a/addons/point_of_sale/models/__init__.py b/addons/point_of_sale/models/__init__.py index c71d05f2c84..676f237afe6 100644 --- a/addons/point_of_sale/models/__init__.py +++ b/addons/point_of_sale/models/__init__.py @@ -13,6 +13,8 @@ from . import pos_category from . import pos_config from . import pos_order from . import pos_session +from . import pos_combo +from . import pos_combo_line from . import product from . import res_partner from . import res_company diff --git a/addons/point_of_sale/models/pos_combo.py b/addons/point_of_sale/models/pos_combo.py new file mode 100644 index 00000000000..74e627c4e24 --- /dev/null +++ b/addons/point_of_sale/models/pos_combo.py @@ -0,0 +1,25 @@ +from odoo import api, fields, models, _ +from odoo.exceptions import ValidationError + +class PosCombo(models.Model): + """ + This model is used to allow the pos user to create menus. + This means that products can be grouped together and sold as a combo. + """ + _name = "pos.combo" + _description = "Product combo choices" + + name = fields.Char(string="Name", required=True) + combo_line_ids = fields.One2many("pos.combo.line", "combo_id", string="Products in Combo") + num_of_products = fields.Integer("No of Products", compute="_compute_num_of_products") + + @api.depends("combo_line_ids") + def _compute_num_of_products(self): + # optimization trick to count the number of products in each combo + for rec, num_of_products in self.env["pos.combo.line"]._read_group([("combo_id", "in", self.ids)], groupby=["combo_id"], aggregates=["__count"]): + rec.num_of_products = num_of_products + + @api.constrains("combo_line_ids") + def _check_combo_line_ids_is_not_null(self): + if any(not rec.combo_line_ids for rec in self): + raise ValidationError(_("Please add products in combo.")) diff --git a/addons/point_of_sale/models/pos_combo_line.py b/addons/point_of_sale/models/pos_combo_line.py new file mode 100644 index 00000000000..6293b2a427a --- /dev/null +++ b/addons/point_of_sale/models/pos_combo_line.py @@ -0,0 +1,11 @@ +from odoo import fields, models + + +class PosComboLine(models.Model): + _name = "pos.combo.line" + _description = "Product Combo Items" + + product_id = fields.Many2one("product.product", string="Product") + price = fields.Float("Price Extra", default=0.0) + lst_price = fields.Float("Original Price", related="product_id.lst_price") + combo_id = fields.Many2one("pos.combo") diff --git a/addons/point_of_sale/models/product.py b/addons/point_of_sale/models/product.py index 99f3b0e3869..d694bec80f2 100644 --- a/addons/point_of_sale/models/product.py +++ b/addons/point_of_sale/models/product.py @@ -15,6 +15,7 @@ class ProductTemplate(models.Model): pos_categ_ids = fields.Many2many( 'pos.category', string='Point of Sale Category', help="Category used in the Point of Sale.") + combo_ids = fields.Many2many('pos.combo', string='Combinations') @api.ondelete(at_uninstall=False) def _unlink_except_open_session(self): diff --git a/addons/point_of_sale/security/ir.model.access.csv b/addons/point_of_sale/security/ir.model.access.csv index 41b5594da75..9dbd50ab155 100644 --- a/addons/point_of_sale/security/ir.model.access.csv +++ b/addons/point_of_sale/security/ir.model.access.csv @@ -47,6 +47,10 @@ access_decimal_precision_user,decimal.precision,base.model_decimal_precision,gro access_pos_payment_user,pos.payment user,model_pos_payment,group_pos_user,1,1,1,1 access_pos_payment_method_user,pos.payment.method user,model_pos_payment_method,group_pos_user,1,0,0,0 access_pos_payment_method_manager,pos.payment.method manager,model_pos_payment_method,group_pos_manager,1,1,1,1 +access_pos_combo_manager,pos.combo manager,model_pos_combo,group_pos_manager,1,1,1,1 +access_pos_combo_user,pos.combo user,model_pos_combo,group_pos_user,1,0,0,0 +access_pos_combo_line_manager,pos.combo.line manager,model_pos_combo_line,group_pos_manager,1,1,1,1 +access_pos_combo_line_user,pos.combo.line user,model_pos_combo_line,group_pos_user,1,0,0,0 access_pos_details_wizard,access.pos.details.wizard,model_pos_details_wizard,point_of_sale.group_pos_manager,1,1,1,0 access_pos_make_payment,access.pos.make.payment,model_pos_make_payment,point_of_sale.group_pos_manager,1,1,1,0 access_pos_close_session_wizard,access.pos.close.session.wizard,model_pos_close_session_wizard,point_of_sale.group_pos_user,1,1,1,0 diff --git a/addons/point_of_sale/views/pos_combo_view.xml b/addons/point_of_sale/views/pos_combo_view.xml new file mode 100644 index 00000000000..386e3325b42 --- /dev/null +++ b/addons/point_of_sale/views/pos_combo_view.xml @@ -0,0 +1,41 @@ + + + + pos.combo.form + pos.combo + +
+
+
+ + + + + + + +
+
+
+ + + pos.combo.tree + pos.combo + + + + + + + + + + Combo Choices + pos.combo + tree,form + +
diff --git a/addons/point_of_sale/views/product_view.xml b/addons/point_of_sale/views/product_view.xml index 66003b96b5a..e63cd4bea57 100644 --- a/addons/point_of_sale/views/product_view.xml +++ b/addons/point_of_sale/views/product_view.xml @@ -69,6 +69,7 @@ + @@ -88,6 +89,11 @@ action="product_product_action" groups="product.group_product_variant" sequence="10"/> +