from decimal import Decimal from datetime import datetime from operator import itemgetter, attrgetter from .commons.dialogs import HelpDialog, QuickDialog # from PyQt5.QtCore import Qt, QSize # from PyQt5.QtWidgets import ( # QCheckBox, QTextEdit, QVBoxLayout, QGridLayout, QLineEdit, QPlainTextEdit, # QScrollArea, QHBoxLayout, QDoubleSpinBox, QLabel, QMessageBox # ) from PySide6.QtCore import Qt, QSize from PySide6.QtWidgets import ( QCheckBox, QTextEdit, QVBoxLayout, QGridLayout, QLineEdit, QPlainTextEdit, QScrollArea, QHBoxLayout, QDoubleSpinBox, QLabel, QMessageBox ) from .proxy import Report from .buttonpad import ButtonsFunction from .constants import alignCenter, alignLeft, FRACTIONS, TYPE_VEHICLE, MONEY from .commons.forms import FieldMoney, ComboBox, GridForm from .commons.search_window import SearchWindow from collections import OrderedDict from .manage_tables import ManageTables from app.commons.menu_buttons import GridButtons from app.commons.table import TableView from app.commons.model import TableEdit from .commons.custom_button import CustomButton from .tools import get_icon, get_screen __all__ = [ 'ControlPanel', 'SearchSale', 'SearchParty', 'SearchProduct', 'Position', 'DialogPayment', 'DialogSource', 'DialogSplitSale', 'DialogTaxes', 'Help', 'DialogMoneyCount', 'DialogTableDeliveryParty', 'DialogDeliveryParty', 'DeliveryPartySelected', 'DialogPrintInvoice', 'DialogStock', 'Comment', 'DialogAuthDiscounts', 'DialogSalesmanCode', 'DialogAgent', 'ProductEdit', 'DialogOrder', 'DialogGlobalDiscount', 'DialogVoucher', 'DialogConsumer', 'DialogManageTables', 'DialogHistoricSales', 'DialogSaleForm', 'DialogCancelInvoice', 'DialogForceAssign', 'CombineProduct', 'DialogReports', 'DialogFixedDiscounts', 'DialogFixedDiscountsManual', 'DialogExpenses', 'DialogInfoProduct', 'DialogAdvance', 'DialogDeleteProduct' ] WIZARDS = { 'square_box_report': { 'name': 'sale_pos_frontend.sale_square_box_report', 'fields': [ ('date', { 'name': 'FECHA', 'type': 'date', 'default': datetime.now().strftime("%Y-%m-%d"), }), ('turn', { 'name': 'TURNO', 'type': 'selection', 'values': [('', ''), ('1', '1'), ('2', '2'), ('3', '3')], }), ], }, 'delivery_report': { 'fields': [ ('date', { 'name': 'FECHA', 'type': 'date', 'default': datetime.now().strftime("%Y-%m-%d"), }), ], } } def create_vbox(parent, values, method, columns=4): vbox_ = QVBoxLayout() grid = QGridLayout() grid.setSpacing(2) if isinstance(method, str): method = getattr(parent, method) grid_buttons = GridButtons(parent, values, columns, action=method, style='standard_button') vbox_.setObjectName('grid_buttons') scroll_area = QScrollArea() scroll_area.setWidgetResizable(True) scroll_area.setVerticalScrollBarPolicy(Qt.ScrollBarAlwaysOn) scroll_area.setWidget(grid_buttons) grid.addWidget(scroll_area) vbox_.addLayout(grid) return vbox_ class ControlPanel(QuickDialog): def __init__(self, parent): vbox_ = QVBoxLayout() grid = QGridLayout() values = self.get_control_panel() control_panel = ButtonsFunction(parent, values=values) scroll_area = QScrollArea() scroll_area.setLayout(control_panel) grid.addWidget(scroll_area) vbox_.addLayout(grid) width, height = get_screen() super(ControlPanel, self).__init__(parent, 'action', widgets=[vbox_]) self.setFixedSize(int(width * 0.5), int(height * 0.5)) self.setWindowTitle('PANEL DE CONTROL') def get_control_panel(self): menu_dash = ( ('button_open', 'ABRIR ESTADOS DE CUENTA', 'action_open_statement'), ('button_closed', 'CERRAR ESTADOS DE CUENTA', 'action_close_statement'), ('button_expenses', 'GASTOS', 'action_expenses'), ('button_discount', 'DESCUENTOS AUTORIZADOS', 'action_table_discount'), ('button_delivery_party', 'CREAR DOMICILIARIO', 'action_delivery_party_panel'), ) return menu_dash class DialogReports(QuickDialog): def __init__(self, parent): super(DialogReports, self).__init__(parent, 'action') vbox = QVBoxLayout() grid = QGridLayout() scroll_area = QScrollArea() _reports = ( ('button_square_box', 'CUADRE DE CAJA', 'action_square_box_report'), ('button_terminal_journal', 'PAGOS ELECTRONICOS', 'action_terminal_journal_report'), ('button_delivery_report', 'ENTREGA DOMICILIARIOS', 'action_delivery_report'), ) self.reports = ButtonsFunction(parent, values=_reports) self.parent = parent scroll_area.setLayout(self.reports) grid.addWidget(scroll_area) vbox.addLayout(grid) width, height = get_screen() self.setFixedSize(int(width * 0.5), int(height * 0.5)) self.setWindowTitle('REPORTES') self.add_widget(vbox) def open_wizard(self, report, add_fields=None, open_print=True): vbox = QVBoxLayout() wiz_report = WIZARDS[report] fields = wiz_report['fields'] if add_fields: fields.append(add_fields) fields = OrderedDict(fields) self.form = GridForm(self, fields, col=2) vbox.addLayout(self.form) dialog = QuickDialog(self, 'action', widgets=[vbox]) result = dialog.exec() store = self.form.getStore() values = {} values.update(store) report_name = wiz_report.get('name') if result == 1: if not open_print: return values, report_name else: self.open_report(report_name, values) def open_report(self, report_name, data): report = Report(self.parent.ctx) values = { 'report_name': report_name, 'args': data, } result = report.get(values) report.open(result) class SearchSale(SearchWindow): def __init__(self, parent): self.parent = parent self.screen_size = 'small' headers = OrderedDict() headers['id'] = {'desc': 'ID', 'type': 'char'} headers['number'] = {'desc': 'NUMERO', 'type': 'char'} headers['invoice_number'] = {'desc': 'FACTURA', 'type': 'char'} headers['salesman.rec_name'] = {'desc': 'VENDEDOR', 'type': 'char'} widths = [20, 115, 115, 160] widths_append = widths.append if parent._sale_pos_restaurant: headers['kind'] = {'desc': 'CLASE', 'type': 'char'} widths_append(110) headers['consumer.rec_name'] = {'desc': 'CONSUMIDOR', 'type': 'char'} widths_append(300) headers['table_assigned.rec_name'] = {'desc': 'MESA', 'type': 'char'} widths_append(100) headers['source.name'] = {'desc': 'FUENTE', 'type': 'char'} widths_append(150) headers['create_date'] = {'desc': 'HORA', 'type': 'time'} widths_append(120) else: headers['party.name'] = {'desc': 'CLIENTE', 'type': 'char'} widths_append(160) headers['sale_date'] = {'desc': 'FECHA', 'type': 'char'} widths_append(80) headers['position'] = {'desc': 'POSICION', 'type': 'char'} widths_append(130) headers['total_amount_cache'] = {'desc': 'VALOR TOTAL', 'type': 'number'} widths_append(90) title = ('BUSCAR PEDIDOS...') methods = { 'on_selected_method': 'on_selected_sale', 'on_return_method': 'on_selected_sale' } self.buttons_layout_filter = QHBoxLayout() self.pushButtonCash = CustomButton( id='button_search_sale_cash', parent=self, # icon=get_icon('history'), title='CONTADO', name_style='start', record='cash', method='action_search_sale', size='mini_button', ) self.pushButtonCredit = CustomButton( id='button_search_sale_credit', parent=self, # icon=get_icon('history'), title='CREDITO', name_style='start', record='credit', method='action_search_sale', size='mini_button', ) self.pushButtonReservation = CustomButton( id='button_search_sale_reservation', parent=self, # icon=get_icon('history'), title='RESERVA', name_style='start', record='reservation', method='action_search_sale', size='mini_button', ) self.buttons_layout_filter.addWidget(self.pushButtonCash) self.buttons_layout_filter.addWidget(self.pushButtonCredit) self.buttons_layout_filter.addWidget(self.pushButtonReservation) widgets_to_create = self.buttons_layout_filter super(SearchSale, self).__init__(parent, headers, None, methods, filter_column=(1, 2, 3, 4, 5, 6, 7), cols_width=widths, title=title, fill=True, widgets=[widgets_to_create]) def action_search_sale(self, _type): self.parent.search_sales_by_domain(_type) class SearchParty(SearchWindow): def __init__(self, parent): headers = OrderedDict() headers['id'] = {'desc': 'ID', 'type': 'char'} headers['id_number'] = {'desc': 'NUMERO ID', 'type': 'char'} headers['name'] = {'desc': 'NOMBRE', 'type': 'char'} headers['phone'] = {'desc': 'TELEFONO', 'type': 'char'} headers['street'] = {'desc': 'DIRECCION', 'type': 'char'} show_party_cats = parent._config.get('show_party_categories', None) if show_party_cats: headers['categories_string'] = {'desc': 'CATEGORIA', 'type': 'char'} title = 'BUSCAR CLIENTE' methods = { 'on_selected_method': 'on_selected_party', 'on_return_method': 'on_search_party', # 'street': parent.on_selected_street_party } super(SearchParty, self).__init__(parent, headers, None, methods, filter_column=[], cols_width=[60, 120, 270, 190, 90], title=title, fill=True) class SearchProduct(SearchWindow): def __init__(self, parent): _cols_width = [10, 80] _cols_width_append = _cols_width.append headers = OrderedDict() headers['id'] = {'desc': ('ID'), 'type': 'char'} headers['code'] = {'desc': ('COD'), 'type': 'char'} if parent._config.get('show_stock_pos') in ['icon', 'value']: headers['quantity'] = {'desc': ('STOCK'), 'type': 'char'} if parent._config['show_stock_pos'] == 'icon': headers['quantity']['icon'] = 'stock' headers['quantity']['type'] = 'icon' _cols_width_append(60) if not parent.cache_local: headers['name'] = {'desc': 'NOMBRE', 'type': 'char'} else: headers['template.name'] = {'desc': 'NOMBRE', 'type': 'char'} _cols_width_append(350) if parent._config.get('show_description_pos'): headers['description'] = {'desc': 'DESCRIPCION', 'type': 'char'} _cols_width_append(300) if parent._config.get('show_brand'): headers['template.brand'] = {'desc': 'BRAND', 'type': 'char'} _cols_width_append(100) price = {'desc': ('PRICE'), 'type': 'number'} if not parent._config.get('encoded_sale_price'): headers['template.sale_price_w_tax'] = price else: price['type'] = 'char' headers['encoded_sale_price'] = price _cols_width_append(100) if parent._config.get('show_location_pos'): headers['location.name'] = {'desc': 'BODEGA', 'type': 'char'} _cols_width_append(100) if parent._config['show_product_image']: headers['image'] = {'desc': 'IMAGEN', 'icon': 'image', 'type': 'icon'} _cols_width_append(30) methods = { 'on_selected_method': 'on_selected_product', 'on_return_method': 'on_search_product', 'image': parent.on_selected_icon_product, 'quantity': parent.on_selected_stock_product } fields_names = list(headers.keys()) try: fields_names.remove('image') except: pass self.fields_names = fields_names super(SearchProduct, self).__init__(parent, headers, None, methods, cols_width=_cols_width, fill=True) class DialogManageTables(QuickDialog): def __init__(self, parent): self.parent = parent if not parent._sale_pos_restaurant: return tables = parent.RestTables.find([ ('shop', '=', parent.shop['id']) ]) self.manager = ManageTables(parent, tables) width, height = get_screen() super(DialogManageTables, self).__init__(parent, 'action', widgets=[self.manager]) self.setFixedSize(int(width / 1.5), int(height / 1.5)) def exec(self): self.open_tables() super(DialogManageTables, self).exec() def open_tables(self): tables = self.parent.RestTables.find([ ('shop', '=', self.parent.shop['id']) ]) self.manager.update_records(tables) class DialogConsumer(QuickDialog): def __init__(self, parent): self._parent = parent self._parent._consumer = None vbox_consumer = QVBoxLayout() grid = QGridLayout() self.consumer = {} label_phone = QLabel('TELEFONO:') label_phone.setObjectName('label_phone') grid.addWidget(label_phone, 1, 1) self.form_phone = QLineEdit() self.form_phone.setObjectName('form_consumer_phone') self.form_phone.textChanged.connect( lambda: self.update('phone')) self.form_phone.editingFinished.connect(lambda: self.search()) self.form_phone.returnPressed.connect(lambda: self.search()) grid.addWidget(self.form_phone, 1, 2) label_consumer = QLabel('CONSUMIDOR:') label_consumer.setObjectName('label_consumer') grid.addWidget(label_consumer, 2, 1) self.form_name = QLineEdit() self.form_name.setFocus() self.form_name.setObjectName('form_consumer_name') self.form_name.textChanged.connect( lambda: self.update('name')) grid.addWidget(self.form_name, 2, 2) label_address = QLabel('DIRECCION:') label_address.setObjectName('label_address') grid.addWidget(label_address, 3, 1) self.form_address = QLineEdit() self.form_address.setObjectName('form_consumer_address') self.form_address.textChanged.connect( lambda: self.update('address')) grid.addWidget(self.form_address, 3, 2) label_id_number = QLabel('NUMERO ID:') label_id_number.setObjectName('label_id_number') grid.addWidget(label_id_number, 4, 1) self.form_id_number = QLineEdit() self.form_id_number.setObjectName('form_consumer_id_number') self.form_id_number.textChanged.connect( lambda: self.update('id_number')) grid.addWidget(self.form_id_number, 4, 2) label_delivery = QLabel('DOMICILO:') label_delivery.setObjectName('label_delivery') grid.addWidget(label_delivery, 5, 1) self.form_delivery = QLineEdit() self.form_delivery.setObjectName('form_consumer_delivery') self.form_delivery.textChanged.connect( lambda: self.update('delivery')) grid.addWidget(self.form_delivery, 5, 2) label_notes = QLabel('NOTAS:') label_notes.setObjectName('label_notes') grid.addWidget(label_notes, 6, 1) self.form_notes = QPlainTextEdit() self.form_notes.setObjectName('form_consumer_notes') self.form_notes.textChanged.connect( lambda: self.update('notes') ) grid.addWidget(self.form_notes, 6, 2) grid.setVerticalSpacing(15) self.label_msg = QLabel('Faltan campos requeridos!') grid.addWidget(self.label_msg, 7, 2) self.label_msg.setVisible(False) grid.addWidget(self.get_button(), 8, 1, 1, 2) vbox_consumer.addLayout(grid) super(DialogConsumer, self).__init__(parent, 'form', widgets=[ vbox_consumer]) self.setWindowTitle('CONSUMIDOR') self.ok_button.setDefault(False) width, height = get_screen() self.setGeometry(0, 0, int(width * 0.4), int(height * 0.7)) def get_button(self): self.button_history_customer = CustomButton( id='button_history_customer', parent=self._parent, icon=get_icon('history'), title='HISTORIAL DE VENTAS', name_style='toolbar', method='button_sale_consumer_history' ) self.button_history_customer.setVisible(False) return self.button_history_customer def fill(self, values): self.consumer = values self.form_phone.setText(values['phone']) self.form_name.setText(values['name']) self.form_delivery.setText(values.get('delivery', None)) self.form_address.setText(values['address']) id_number = values.get('id_number', None) if id_number: self.form_id_number.setText(id_number) notes = values.get('notes', None) if not notes: notes = '' self.form_notes.setPlainText(notes) self.button_history_customer.setVisible(True) def update(self, field): self.label_msg.setVisible(False) field_wid = getattr(self, 'form_' + field) if hasattr(field_wid, 'text'): value = field_wid.text() else: value = field_wid.toPlainText() self.consumer[field] = value.upper() def search(self): self.ok_button.setDefault(False) phone = self.form_phone.text() res = self.parent.search_consumer(phone) if res: self.button_history_customer.setVisible(True) def show(self): super(DialogConsumer, self).show() self.form_phone.setFocus() def dialog_accepted(self): if self.consumer and len(self.consumer['phone']) > 6: if self.consumer.get('address') and self.consumer.get('name'): self.parent.save_consumer(self.consumer) else: # Add dialog error missing required fields self.label_msg.setVisible(True) return super(DialogConsumer, self).dialog_accepted() def clear(self): self.consumer = {} self.form_phone.setText('') self.form_name.setText('') self.form_address.setText('') self.form_id_number.setText('') self.form_delivery.setText('') self.form_notes.clear() self.button_history_customer.setVisible(False) self.ok_button.setDefault(False) class DialogHistoricSales(QuickDialog): def __init__(self, parent): width, height = get_screen() col_sizes = (fd['width'] for fd in parent.fields_sales_query) vbox_ = QVBoxLayout() table = TableView( 'model_sale_historic', parent.model_sale_historic, col_sizes, method_selected_row=parent.sale_form_selected ) vbox_.addWidget(table) vbox_.addSpacing(10) super(DialogHistoricSales, self).__init__(parent, 'action', widgets=[vbox_]) self.setWindowTitle('-- VENTA --') self.setFixedSize(int(width * 0.8), int(height * 0.7)) class DialogSaleForm(QuickDialog): def __init__(self, parent): self._parent = parent vbox_ = QVBoxLayout() _fields = [ ('party', { 'name': 'CLIENTE', 'readonly': True, }), ('number', { 'name': 'NUMERO', 'readonly': True, }), ('sale_date', { 'name': 'FECHA', 'readonly': True, }), ('invoice_number', { 'name': 'FACTURA', 'readonly': True, }), ('total_amount_cache', { 'name': 'TOTAL', 'readonly': True, 'type': 'money', }), ] fields = OrderedDict(_fields) self.grid = GridForm(self, fields, col=2) col_sizes = (field['width'] for field in parent.fields_sale_line) self.table = TableView( 'model_sale_lines', parent.model_sale_lines_simple, col_sizes ) self.grid.addWidget(self.table, 4, 1, 1, 4) vbox_.addLayout(self.grid) super(DialogSaleForm, self).__init__(parent, 'action', widgets=[vbox_]) self.grid.addWidget(self.get_button(), 5, 3, 3, 4) width, height = get_screen() self.setFixedSize(int(width * 0.5), int(height * 0.6)) def start(self, data): elements = ( 'id', 'party.', 'number', 'sale_date', 'total_amount_cache', 'invoice_number', 'lines.' ) id, party, number, sale_date, total_amount_cache, invoice_number, lines = itemgetter(*elements)(data) self.sale_customer_selected = id self.field_party.setText(party['name']) self.field_number.setText(number) self.field_sale_date.setText(sale_date) self.field_total_amount_cache.setText(str(total_amount_cache)) self.field_invoice_number.setText(str(invoice_number)) self.table.model.reset() for line in lines: self.table.model.add_record(line) self.exec() def get_button(self): button_duplicate_sale = CustomButton( id='button_duplicate_sale', parent=self, icon=get_icon('duplicate_sale'), title=('DUPLICAR VENTA'), name_style='toolbar', method='button_duplicate_sale' ) return button_duplicate_sale def button_duplicate_sale(self): if self.sale_customer_selected: res = self._parent.Sale.duplicate_sale({ 'sale_id': self.sale_customer_selected, }) self.parent.dialog_consumer.close() self.parent.dialog_historic_sales.close() self.close() return res class DialogAgent(QuickDialog): def __init__(self, parent): view = ( ('agent_ask', { 'name': 'AGENTE', 'type': 'relation', 'model': parent.Agent, 'domain': [], 'fields': [ ('id', 'ID'), ('party.rec_name', 'NOMBRE'), ('party.id_number', 'NUMERO ID'), ] }), ('commission_ask', {'name': 'COMISION'}), ('commission_amount', {'name': 'VALOR', 'readonly': True}), ) super(DialogAgent, self).__init__(parent, 'action', data=view) class DialogCancelInvoice(QuickDialog): def __init__(self, parent): view = ( ('password_for_cancel_ask', { 'name': 'INGRESE LA CONTRASEÑA', 'password': True }), ) super(DialogCancelInvoice, self).__init__(parent, 'action', data=view) class DialogForceAssign(QuickDialog): def __init__(self, parent): field = 'password_force_assign_ask' data = (field, {'name': 'CONTRASEÑA DE FORZAR ASIGNACION'}) super(DialogForceAssign, self).__init__(parent, 'action', data=[data]) class DialogOrder(QuickDialog): def __init__(self, parent): string = 'DESEA CONFIRMAR EL ENVIO DE LA ORDEN?' super(DialogOrder, self).__init__(parent, 'action', string, data=[]) class DialogStock(QuickDialog): def __init__(self, parent): data = { 'name': 'stock', 'values': [], 'heads': ('BODEGA', 'CANTIDAD', 'POSICION'), } label = 'STOCK POR PRODUCTO:' width, height = get_screen() super(DialogStock, self).__init__(parent, 'selection', label, data, readonly=True) self.setFixedSize(int(width * 0.4), int(height * 0.3)) class DialogGlobalDiscount(QuickDialog): def __init__(self, parent): field = 'global_discount_ask' data = (field, {'name': 'DESCUENTO GLOBAL'}) super(DialogGlobalDiscount, self).__init__(parent, 'action', data=[data]) class DialogPrintInvoice(QuickDialog): def __init__(self, parent): view = ( ('invoice_number_ask', {'name': 'ORDEN / FACTURA'}), ('type_ask', { 'name': 'TIPO', 'type': 'selection', 'values': [ ('invoice', 'FACTURA'), ('order', 'ORDEN'), # ('delivery', ('DELIVERY')) ], }), ('printer_ask', { 'name': 'IMPRESORA', 'type': 'selection', 'values': [ (1, 'POS'), (2, 'LASER') ], }), ('resend_dian_ask', { 'name': 'REENVIO DIAN', 'type': 'checkbox', 'placeholder': 'REENVIO DIAN', }), ) super(DialogPrintInvoice, self).__init__(parent, 'action', data=view) class DialogAdvance(QuickDialog): def __init__(self, parent): data = ( ('amount_ask', {'name': 'VALOR'}), ('reservation_ask', { 'name': 'RESERVA', 'type': 'checkbox', 'placeholder': 'RESERVA', }), ) super(DialogAdvance, self).__init__(parent, 'action', data=data) def clean(self): self.parent.field_amount_ask.clear() self.parent.field_reservation_ask.setChecked(False) class DialogVoucher(QuickDialog): def __init__(self, parent): data = ('voucher_ask', {'name': 'NUMERO DE COMPROBANTE'}) super(DialogVoucher, self).__init__(parent, 'action', data=[data]) class DialogDeleteProduct(QuickDialog): def __init__(self, parent): data = ('note_ask', {'name': 'OBSERVACION', 'type': 'text_area'}) super(DialogDeleteProduct, self).__init__(parent, 'action', data=[data]) class DialogAuthDiscounts(QuickDialog): def __init__(self, parent): vbox_discounts = create_vbox( parent, parent.discounts, parent.on_selected_discount ) width, height = get_screen() super(DialogAuthDiscounts, self).__init__(parent, 'action', size=(width * 0.8, height * 0.8), widgets=[vbox_discounts]) self.setWindowTitle('DESCUENTOS AUTORIZADOS') class DialogFixedDiscounts(QuickDialog): def __init__(self, parent): widgets = create_vbox( parent, parent.discounts_fixed, parent.on_selected_discount ) width, height = get_screen() super(DialogFixedDiscounts, self).__init__(parent, 'action', widgets=[widgets]) self.setFixedSize(int(width * 0.8), int(height * 0.7)) self.setWindowTitle('DESCUENTO/BONO') class DialogFixedDiscountsManual(QuickDialog): def __init__(self, parent): field = 'bono_discount_manual' data = (field, {'name': 'BONO ABIERTO'}) super(DialogFixedDiscountsManual, self).__init__(parent, 'action', data=[data]) self.setWindowTitle('BONO ABIERTO') class DialogDeliveryParty(QuickDialog): def __init__(self, parent): vbox_ = create_vbox( parent, parent.delivery_parties, parent.on_selected_delivery_party, ) width, height = get_screen() super(DialogDeliveryParty, self).__init__(parent, 'action', widgets=[vbox_]) self.setWindowTitle('ESCOJE EL DOMICILIARIO') self.setFixedSize(int(width * 0.8), int(height * 0.7)) class DeliveryPartySelected(QuickDialog): def __init__(self, parent): parent.state_delivery_party = {} vbox_ = QVBoxLayout() grid = QGridLayout() label_delivery_party = QLabel('DOMICILIARIO:') label_delivery_party.setAlignment(alignCenter) label_delivery_party.setObjectName('label_delivery_party') grid.addWidget(label_delivery_party, 1, 1) parent.row_delivery_party = QLineEdit() parent.row_delivery_party.setObjectName('row_delivery_party') parent.row_delivery_party.textChanged.connect( lambda: parent.update_delivery_party('delivery_party')) grid.addWidget(parent.row_delivery_party, 1, 2) label_id_number = QLabel('NUMERO ID:') label_id_number.setAlignment(alignCenter) label_id_number.setObjectName('label_id_number') grid.addWidget(label_id_number, 2, 1) parent.row_id_number = QLineEdit() parent.row_id_number.setObjectName('row_id_number') parent.row_id_number.textChanged.connect( lambda: parent.update_delivery_party('id_number')) grid.addWidget(parent.row_id_number, 2, 2) label_number_plate = QLabel('PLACA:') label_number_plate.setAlignment(alignCenter) label_number_plate.setObjectName('label_number_plate') grid.addWidget(label_number_plate, 3, 1) parent.row_number_plate = QLineEdit() parent.row_number_plate.setObjectName('row_number_plate') parent.row_number_plate.textChanged.connect( lambda: parent.update_delivery_party('number_plate')) grid.addWidget(parent.row_number_plate, 3, 2) label_phone = QLabel('TELEFONO:') label_phone.setAlignment(alignCenter) label_phone.setObjectName('label_phone') grid.addWidget(label_phone, 4, 1) parent.row_phone = QLineEdit() parent.row_phone.setObjectName('row_phone') parent.row_phone.textChanged.connect( lambda: parent.update_delivery_party('row_phone')) grid.addWidget(parent.row_phone, 4, 2) label_type_vehicle = QLabel('TIPO DE VEHICULO:') label_type_vehicle.setAlignment(alignCenter) label_type_vehicle.setObjectName('label_type_vehicle') grid.addWidget(label_type_vehicle, 5, 1) parent.row_type_vehicle = ComboBox(parent, 'TIPO DE VEHICULO', {'values': TYPE_VEHICLE}) parent.row_type_vehicle.setObjectName('row_type_vehicle') parent.row_type_vehicle.currentIndexChanged.connect( lambda: parent.update_delivery_party('type_vehicle')) grid.addWidget(parent.row_type_vehicle, 5, 2) label_delivery_party_active = QLabel('ACTIVO:') label_delivery_party_active.setAlignment(alignCenter) label_delivery_party_active.setObjectName('label_delivery_party_active') grid.addWidget(label_delivery_party_active, 6, 1) parent.row_delivery_party_active = QCheckBox() parent.row_delivery_party_active.setObjectName('row_delivery_party_active') parent.row_delivery_party_active.stateChanged.connect( lambda: parent.update_delivery_party('delivery_party_active')) grid.addWidget(parent.row_delivery_party_active, 6, 2) vbox_.addLayout(grid) super(DeliveryPartySelected, self).__init__(parent, 'action', widgets=[vbox_]) self.accepted.connect(parent.dialog_delivery_party_accepted) class DialogTableDeliveryParty(QuickDialog): def __init__(self, parent): self._parent = parent col_sizes_tlines = (field['width'] for field in parent.fields_delivery_party) table = TableView( 'model_delivery_party', parent.model_delivery_party, col_sizes_tlines, method_selected_row=parent.delivery_party_selected ) width, height = get_screen() table.setFixedSize(int(width/2.2), int(height/2.2)) vbox_ = QVBoxLayout() grid = QGridLayout() grid.addWidget(table, 1, 1, 1, 2) grid.setVerticalSpacing(20) grid.addWidget(self.get_button(), 2, 1, 1, 2) grid.setAlignment(alignCenter) vbox_.addLayout(grid) super(DialogTableDeliveryParty, self).__init__(parent, 'action', widgets=[vbox_]) width, height = get_screen() self.setGeometry(0, 0, int(width / 1.8), int(height / 1.5)) self.setWindowTitle('DOMICILIARIO') def get_button(self): self._parent.button_create_delivery_party = CustomButton( id='button_create_delivery_party', parent=self._parent, icon=get_icon('delivery_party'), title='NUEVO DOMICILIARIO', name_style='toolbar', method='button_create_delivery_party' ) return self._parent.button_create_delivery_party class DialogMoneyCount(QuickDialog): def __init__(self, parent): self._parent = parent self.kind = None width, height = get_screen() grid = QGridLayout() _sizes = (160, 120, 240) fields = ( {'label': 'MONEDA', 'type': 'integer', 'readonly': True}, {'label': 'CANTIDAD', 'type': 'integer', 'change': 'set_total'}, {'label': 'SUBTOTAL', 'type': 'integer', 'readonly': True}, ) self.model = TableEdit(self, MONEY, fields) table = TableView('model', self.model, _sizes, editable=True) table.setFixedSize(int(width * 0.35), int(height * 0.4)) grid.addWidget(table, 1, 0, 1, 2) label_total = QLabel('TOTAL DINERO:') label_total.setObjectName('label_total_money') grid.addWidget(label_total, 2, 0) self.field_total_money = FieldMoney(self, 'field_total_money') self.field_total_money.setObjectName('field_total_money') self.field_total_money.setAlignment(alignLeft) grid.addWidget(self.field_total_money, 2, 1) self.screen_size = parent.screen_size self.button_print = CustomButton( self, id='button_print_count_money', size='small', icon=get_icon('print_sale'), title='IMPRIMIR', method='action_print_count_money', name_style='mini_button', ) grid.addWidget(self.button_print, 3, 0) grid.setRowStretch(0, 1) grid.setSpacing(10) super(DialogMoneyCount, self).__init__(parent, 'action', widgets=[grid]) self.setWindowTitle('CONTEO DE DINERO') def exec(self, kind): self.kind = kind self.exec_() def set_total(self, row): _row = self.model._data[row] money, value = _row[0], _row[1] _row[2] = int(value) * int(money) self.field_total_money.setText(str(self.model.get_sum(2))) def dialog_accepted(self): super(DialogMoneyCount, self).dialog_accepted() val = self.field_total_money.text().replace(',', '') if self.kind == 'open': self.parent.open_statement_accepted(val) else: values = self.model._data self.parent.close_statement_accepted(values) def clear(self): self.field_total_money.setText('0') def action_print_count_money(self): kind = 'CIERRE' if self.kind == 'open': kind = 'APERTURA' _data = ((str(d[0]), str(d[1]), str(d[2])) for d in self.model._data) data = { 'type': kind, 'total': self.field_total_money.text(), 'lines': _data, } self.parent.action_print_count_money(data) class DialogExpenses(QuickDialog): def __init__(self, parent): self._parent = parent width, height = get_screen() grid = QGridLayout() self.screen_size = parent.screen_size self.button_add = CustomButton( self, id='button_add_expense', size='small', icon=get_icon('plus'), title='AGREGAR', method='action_add_expense', name_style='mini_button', ) grid.addWidget(self.button_add, 1, 0) # self.button_test = CustomButton( # self, # id='button_add_expense', # size='small', # icon=get_icon('plus'), # title='BORRAR', # method='test_delete', # name_style='mini_button', # ) # grid.addWidget(self.button_test, 1, 1) _sizes = (140, 290, 210, 150) fields = ( {'name': 'id', 'label': 'ID', 'type': 'integer', 'invisible': True}, {'name': 'invoice_number', 'label': 'FACTURA', 'type': 'char'}, {'name': 'description', 'label': 'DESCRIPCION', 'type': 'char'}, {'name': 'reference', 'label': 'REFERENCIA', 'type': 'char'}, {'name': 'amount', 'label': 'VALOR', 'type': 'float', 'change': 'set_total'}, ) self.model = TableEdit(self, [], fields) self.table = TableView('model_expenses', self.model, _sizes, editable=True) self.table.hideColumn(0) grid.addWidget(self.table, 2, 0, 1, 2) label_total = QLabel('TOTAL:') label_total.setObjectName('label_total_expenses') label_total.setAlignment(alignCenter) grid.addWidget(label_total, 3, 0) self.field_total = FieldMoney(self, 'field_total_expenses') self.field_total.setObjectName('field_total_expenses') self.field_total.setAlignment(alignLeft) grid.addWidget(self.field_total, 3, 1) grid.setSpacing(10) super(DialogExpenses, self).__init__(parent, 'action', widgets=[grid]) self.setGeometry(0, 0, int(width * 0.5), int(height * 0.7)) self.setWindowTitle('GASTOS') self.id_count = -1 self.load() def exec(self): self.clear() self.load() super(DialogExpenses, self).exec() def load(self): if not self.parent.data_expenses: return model_add = self.model.add_record for rec in self.parent.data_expenses: data = ( rec['id'], rec['invoice_number'], rec['description'], rec['reference'], rec['amount'] ) model_add(data) self.field_total.setText(str(self.model.get_sum(4))) def set_total(self, args=None): self.field_total.setText(str(self.model.get_sum(4))) def save(self): for d in self.model._data: args = { 'statement': self.parent.statement_cash['id'], 'invoice_number': d[1], 'description': d[2], 'reference': d[3], 'amount': d[4].replace(',', '') if isinstance(d[4], str) else d[4], } obj_id = d[0] if d[0] > 0: self.parent.Expenses.write([obj_id], args) else: args['id'] = obj_id rec = self.parent.Expenses.create(args) for d in self.model._data: if obj_id == d[0]: d[0] = rec[0] def action_add_expense(self): record = [self.id_count, '', '', '', 0] self.id_count += -1 self.model.add_record(record) self.set_total() def dialog_accepted(self): self.save() super(DialogExpenses, self).dialog_accepted() def clear(self): self.model.clearData() self.set_total() class DialogTaxes(QuickDialog): def __init__(self, parent): if parent.shop_taxes: taxes = ((str(e['id']), e['name']) for e in parent.shop_taxes) else: taxes = [] data = { 'name': 'tax', 'values': taxes, 'heads': ['ID', 'VALOR'], } string = 'ESCOJA EL IMPUESTO' super(DialogTaxes, self).__init__(parent, 'selection', string, data) class DialogSource(QuickDialog): def __init__(self, parent): vbox_ = create_vbox(parent, parent.sources, parent.on_selected_source) super(DialogSource, self).__init__(parent, 'action', widgets=[vbox_], buttons=False) self.setWindowTitle('SELECCIONE EL CANAL') width, height = get_screen() self.setFixedSize(int(width * 0.6), int(height * 0.7)) class DialogPaymentTerm(QuickDialog): def __init__(self, parent): vbox_ = create_vbox(parent, parent._payment_terms, parent.on_selected_payment_term) super(DialogPaymentTerm, self).__init__(parent, 'action', widgets=[vbox_]) self.setWindowTitle('PLAZO DE PAGO') class DialogPayment(QuickDialog): def __init__(self, parent): vbox_ = create_vbox(parent, parent._journals, parent.on_selected_payment) width, height = get_screen() super(DialogPayment, self).__init__(parent, 'action', widgets=[vbox_]) self.setWindowTitle('EL MEDIO DE PAGO:') self.setFixedSize(int(width * 0.8), int(height * 0.7)) class Position(QuickDialog): def __init__(self, parent): field = 'position_ask' data = (field, {'name': 'POSICION'}) super(Position, self).__init__(parent, 'action', data=[data]) class Comment(QuickDialog): def __init__(self, parent): field = 'comment' data = (field, {'name': 'COMENTARIO', 'type': 'text'}) super(Comment, self).__init__(parent, 'action', data=[data]) class TipAmount(QuickDialog): def __init__(self, parent): vbox_ = QVBoxLayout() grid = QGridLayout() label_tip_amount_ask = QLabel('VALOR PROPINA:') label_tip_amount_ask.setAlignment(alignCenter) label_tip_amount_ask.setObjectName('label_tip_amount_ask') grid.addWidget(label_tip_amount_ask, 1, 1) parent.field_tip_amount_ask = QLineEdit() parent.field_tip_amount_ask.setObjectName('field_delivery_amount_ask') grid.addWidget(parent.field_tip_amount_ask, 1, 2) vbox_.addLayout(grid) parent.field_tip_amount_invoice = QCheckBox() parent.field_tip_amount_invoice.setText('INCLUIR EN FACTURA') vbox_.addWidget(parent.field_tip_amount_invoice) super(TipAmount, self).__init__(parent, 'action', widgets=[vbox_]) class DeliveryAmount(QuickDialog): def __init__(self, parent): vbox_ = QVBoxLayout() grid = QGridLayout() label_delivery_amount_ask = QLabel('VALOR DEL DOMICILO:') label_delivery_amount_ask.setAlignment(alignCenter) label_delivery_amount_ask.setObjectName('label_delivery_amount_ask') grid.addWidget(label_delivery_amount_ask, 1, 1) parent.field_delivery_amount_ask = QLineEdit() parent.field_delivery_amount_ask.setObjectName('field_delivery_amount_ask') grid.addWidget(parent.field_delivery_amount_ask, 1, 2) vbox_.addLayout(grid) parent.field_delivery_amount_invoice = QCheckBox() parent.field_delivery_amount_invoice.setText('INCLUIR EN FACTURA') vbox_.addWidget(parent.field_delivery_amount_invoice) super(DeliveryAmount, self).__init__(parent, 'action', widgets=[vbox_]) class DialogSalesmanCode(QuickDialog): def __init__(self, parent): field = 'salesman_code_ask' data = (field, {'name': 'CODIGO VENDEDOR', 'password': True}) super(DialogSalesmanCode, self).__init__(parent, 'action', data=[data]) class ProductEdit(QuickDialog): def __init__(self, parent): self._parent = parent self.store = {} self.active_line = {} vbox_product = QVBoxLayout() grid = QGridLayout() width, height = get_screen() self.label_product = QLabel() self.label_product.setAlignment(alignCenter) self.label_product.setObjectName('label_product') vbox_product.addWidget(self.label_product) if parent._config.get('show_fractions'): self.field_description = QLineEdit() self.field_description.setObjectName('field_description') self.field_description.textChanged.connect( lambda: self.update_line('description') ) grid.addWidget(self.field_description, 1, 1, 1, 2) label_fraction = QLabel('FRACCION:') label_fraction.setObjectName('label_fraction') grid.addWidget(label_fraction, 2, 1) self.field_combobox_fraction = ComboBox( parent, 'fraction', {'values': FRACTIONS} ) grid.addWidget(self.field_combobox_fraction, 2, 2) self.field_combobox_fraction.currentIndexChanged.connect( lambda: self.update_line('qty_fraction') ) label_qty = QLabel('CANTIDAD:') label_qty.setObjectName('label_qty') grid.addWidget(label_qty, 3, 1) self.field_qty = QDoubleSpinBox() self.field_qty.setObjectName('field_qty') self.field_qty.setMinimum(0) self.field_qty.setMaximum(100000) decimals = 2 if parent._config.get('decimals_digits_quantity'): decimals = parent._config['decimals_digits_quantity'] self.field_qty.setDecimals(decimals) self.field_qty.setAlignment(alignCenter) grid.addWidget(self.field_qty, 3, 2) self.field_qty.valueChanged.connect( lambda: self.update_line('quantity') ) label_price = QLabel('PRECIO:') label_price.setObjectName('label_price') grid.addWidget(label_price, 4, 1) self.field_price = FieldMoney(self, 'field_price', {}, readonly=False) self.field_price.setObjectName('field_price') grid.addWidget(self.field_price, 4, 2) self.field_price.textChanged.connect( lambda: self.update_line('unit_price') ) self.field_note = QTextEdit('') self.field_note.setObjectName('row_field_note') grid.addWidget(self.field_note, 5, 1, 5, 2) self.field_note.textChanged.connect(lambda: self.update_line('note')) button_delete = CustomButton( parent, id='button_delete', size='small', icon=get_icon('delete_line'), title='ELIMINAR', method='action_delete_line', name_style='mini_button', ) button_discounts = CustomButton( parent, id='button_discount', size='small', icon=get_icon('discount'), title=('DESCUENTO/BONO'), method='action_discount_line', name_style='mini_button', ) button_discounts_bono = CustomButton( parent, id='button_discount_bono', size='small', icon=get_icon('discount'), title=('BONO/ABIERTO'), method='action_discount_bono_line', name_style='mini_button', ) button_addition = CustomButton( parent, id='button_addition', size='small', icon=get_icon('combine_product'), title=('COMBINAR'), method='action_combine_line', name_style='mini_button', ) button_combo = CustomButton( parent, id='button_combo', size='small', icon=get_icon('combo'), title=('ELECCION'), method='action_combo', name_style='mini_button', ) hbox = QHBoxLayout() vbox_product.addLayout(grid, 1) vbox_product.addLayout(hbox, 0) hbox.addWidget(button_delete, 0) hbox.addWidget(button_discounts, 0) hbox_checkbox_base = QHBoxLayout() vbox_product.addLayout(hbox_checkbox_base, 0) self.checkbox_base = QCheckBox() self.checkbox_base.setText('PRECIO BASE') self.checkbox_base.setMaximumSize(120, 0) if parent.enviroment == 'restaurant': hbox.addWidget(button_discounts_bono, 0) hbox.addWidget(button_combo, 0) hbox.addWidget(button_addition, 0) else: hbox.addWidget(self.checkbox_base, 0) super(ProductEdit, self).__init__(parent, 'action', widgets=[vbox_product]) self.setFixedSize(int(width * 0.5), int(height * 0.7)) def get(self): return self.active_line def close(self): super(ProductEdit, self).close() self.clear() def closeEvent(self, event): super(QuickDialog, self).closeEvent(event) self.clear() def clear(self): self.store = {} self.active_line = {} self.checkbox_base.setChecked(False) def dialog_rejected(self): super(ProductEdit, self).dialog_rejected() self.clear() def dialog_accepted(self): super(ProductEdit, self).dialog_accepted() self.parent.dialog_product_edit_accepted(self.store, self.active_line) def set_line(self, record): self.active_line = record self.show() name = record.get('product.template.name', None) if not name: name = record['product.']['template.']['name'] self.label_product.setText(name) if hasattr(self, 'field_description'): self.field_description.setText(record['description']) self.field_qty.setValue(float(record['quantity'])) self.field_price.setText(str(record['unit_price_w_tax'])) self.field_note.setText(str(record['note'])) self.field_note.setFocus() def update_line(self, field): value = None self.store['id'] = self.active_line['id'] if field == 'quantity': value = Decimal(self.field_qty.value()) if field == 'unit_price': value = self.field_price.text() value = value.replace(',', '') if field == 'qty_fraction': qty = self.field_combobox_fraction.get_id() self.field_qty.setValue(float(qty)) value = self.field_combobox_fraction.get_label() self.store['quantity'] = qty price_ = self.parent.get_product_fraction_prices( self.active_line['product']['id'], self.active_line['sale'], qty ) if price_ and price_.get('unit_price_w_tax'): price_list = str(price_['unit_price_w_tax']) self.field_price.setText(price_list) self.store['unit_price'] = price_list if hasattr(self, 'field_description'): if field == 'description': value = self.field_description.text() if field == 'note': value = self.field_note.toPlainText() if value: self.store[field] = value class CombineProduct(QuickDialog): def __init__(self, parent): self.box = QVBoxLayout() width, height = get_screen() self.method_action = getattr(parent, 'on_selected_item_mix') self.parent = parent self.box.setObjectName('grid_buttons') self.filter_field = QLineEdit() self.filter_field.setObjectName('field_filter_addition') self.filter_field.setPlaceholderText('BUSCAR...') self.filter_field.textChanged.connect(self.filter_products) self.box.addWidget(self.filter_field) super(CombineProduct, self).__init__(parent, 'action', widgets=[self.box]) self.setWindowTitle('SELECCIONE LA COMBINACION') self.setFixedSize(int(width * 0.8), int(height * 0.9)) def set_buttons(self, values): self.values = values self.set_products(values) def set_products(self, values): grid_buttons = GridButtons( self.parent, values, 5, action=self.method_action, style='standard_button' ) if hasattr(self, 'scroll_area'): _ = self.box.removeWidget(self.scroll_area) self.scroll_area = QScrollArea() self.scroll_area.setWidgetResizable(True) self.scroll_area.setWidget(grid_buttons) self.box.addWidget(self.scroll_area) def filter_products(self, text): if len(text) == 0: self.set_products(self.values) return if len(text) <= 2: return filtered = [] text_list = text.upper().split(' ') for v in self.values: for t in text_list: if t in v['rec_name']: filtered.append(v) self.set_products(filtered) class DialogComboProduct(QuickDialog): def __init__(self, parent): self.box = QVBoxLayout() self.box.setObjectName('grid_buttons') width, height = get_screen() self.method_action = getattr(parent, 'on_selected_item_combo') self.parent = parent label = QLabel('SELECCIONE LOS PRODUCTOS') label.setObjectName('label_combo_product') self.box.addWidget(label) super(DialogComboProduct, self).__init__( parent, 'action', widgets=[self.box] ) self.setWindowTitle('PRODUCTO EN COMBO') self.setFixedSize(int(width * 0.7), int(height * 0.6)) def set_buttons(self, values): self.values = values self.set_products(values) def set_products(self, values): grid_buttons = GridButtons( self.parent, values, 4, action=self.method_action, style='standard_button' ) if hasattr(self, 'scroll_area'): _ = self.box.removeWidget(self.scroll_area) self.scroll_area = QScrollArea() self.scroll_area.setWidgetResizable(True) self.scroll_area.setWidget(grid_buttons) self.box.addWidget(self.scroll_area) class DialogSplitSale(QuickDialog): def __init__(self, parent): self._parent = parent box = QVBoxLayout() box.setObjectName('box_sale_split') width, height = get_screen() self.parent = parent self.label = QLabel() self.label_number = QLabel() box.addWidget(self.label) box.addWidget(self.label_number) self.label.setAlignment(alignCenter) self.label_number.setAlignment(alignCenter) self.label.setWordWrap(True) self.label_number.setWordWrap(True) super(DialogSplitSale, self).__init__(parent, 'action', widgets=[box]) self.setWindowTitle('DIVIDIR CUENTA') self.setFixedSize(int(width * 0.4), int(height * 0.3)) self.label.setObjectName('label_h2') self.label_number.setObjectName('label_h1') def ask(self): msg = 'DESEA CREAR UN PEDIDO CON LOS PRODUCTOS SELECCIONADOS?' self.label.setText(msg) self.label_number.setText('') return self.exec_() def info(self, number): self.label.setText('PEDIDO CREADO EXITOSAMENTE!') self.label_number.setText(number) self.exec_() class Help(HelpDialog): def __init__(self, parent): super(Help, self).__init__(parent) shortcuts = ( ('PANEL DE CONTROL', 'F1'), ('BUSCAR PRODUCTO', 'F2'), ('MEDIO DE PAGO', 'F3'), ('BUSCAR CLIENTE', 'F4'), ('DESCUENTO GLOBAL', 'F5'), ('ENVIAR ORDEN', 'F6'), ('IMPRIMIR ORDEN/FACTURA', 'F7'), ('PLAZO DE PAGO', 'F8'), ('BUSCAR ORDEN', 'F9'), ('CONSULTAR PRECIO', 'F10'), ('NUEVA VENTA', 'F11'), ('DOMICILIARIO', 'F12'), ('POSICION', 'Insert'), ('FACTURAR', 'End'), ('COMENTARIO', 'Quotation Marks'), ) self.set_shortcuts(shortcuts) class DialogListProduct(QuickDialog): def __init__(self, parent): self._parent = parent vbox = QVBoxLayout() grid = QGridLayout() label_code = QLabel('CODIGO:') label_code.setObjectName('label_info_product_code') grid.addWidget(label_code, 1, 1) self.input_code = QLineEdit() self.input_code.setObjectName('input_info_product_code') self.input_code.returnPressed.connect(lambda: self.search()) grid.addWidget(self.input_code, 1, 2) class DialogInfoProduct(QuickDialog): def __init__(self, parent): self._parent = parent self.products = [] vbox = QVBoxLayout() grid = QGridLayout() label_filter = QLabel('FILTRO:') label_filter.setObjectName('label_info_product_filter') grid.addWidget(label_filter, 1, 1) self.input_filter = QLineEdit() self.input_filter.setObjectName('input_info_product_filter') self.input_filter.returnPressed.connect(lambda: self.search()) grid.addWidget(self.input_filter, 1, 2) label_code = QLabel('CODIGO:') label_code.setObjectName('label_info_product_code') grid.addWidget(label_code, 2, 1) self.input_code = QLineEdit() self.input_code.setReadOnly(True) self.input_code.setObjectName('input_info_product_code') grid.addWidget(self.input_code, 2, 2) label_name = QLabel('NOMBRE:') label_name.setObjectName('label_info_product_name') grid.addWidget(label_name, 3, 1) self.input_name = QLineEdit() self.input_name.setReadOnly(True) self.input_name.setObjectName('input_info_product_name') grid.addWidget(self.input_name, 3, 2) label_price = QLabel('PRECIO:') label_price.setObjectName('label_info_product_price') grid.addWidget(label_price, 4, 1) self.input_price = QLineEdit() self.input_price.setReadOnly(True) self.input_price.setObjectName('input_info_product_price') grid.addWidget(self.input_price, 4, 2) label_quantity = QLabel('CANTIDAD:') label_quantity.setObjectName('label_info_product_quantity') grid.addWidget(label_quantity, 5, 1) self.input_quantity = QLineEdit() self.input_quantity.setReadOnly(True) self.input_quantity.setObjectName('input_info_product_quantity') grid.addWidget(self.input_quantity, 5, 2) vbox.addLayout(grid) super(DialogInfoProduct, self).__init__(parent, 'help', widgets=[vbox]) self.setWindowTitle('INFO. PRODUCT') self.ok_button.setDefault(False) width, height = get_screen() self.setGeometry(0, 0, int(width * 0.4), int(height * 0.7)) self.input_filter.setFocus() def fill(self, values): self.input_code.setText(values['code']) self.input_name.setText(values['name']) extra_tax = values['extra_tax'] if values.get('extra_tax') else 0 sale_price_w_tax = values['template.']['sale_price_w_tax'] sale_price = "{:,}".format(round(sale_price_w_tax + extra_tax, 0)) self.input_price.setText(sale_price) self.input_quantity.setText(str(values['quantity'])) def search(self, values=None): self.ok_button.setDefault(False) filter = self.input_filter.text() if not filter: return domain = [ ('template.salable', '=', True), ('template.account_category', '!=', None), ] domain.append([ 'OR', # ('barcode', 'ilike', '%' + filter + '%'), ('code', 'ilike', '%' + filter + '%'), ('name', 'ilike', '%' + filter + '%') ]) if self._parent.cache_local: clause = [ 'OR', # ('barcode', 'ilike', '%{:}%'.format(filter)), ('code', 'ilike', '%{:}%'.format(filter)), ('code', 'ilike', '%{:}%'.format(filter)), ] domain = [clause] products = self._parent.local_db.find_product_elastic(domain, limit=100) else: products = self._parent.Product.find(domain, ctx=self._parent.stock_context, fields=['name', 'code', 'description', 'id', 'list_price', 'quantity', 'rec_name', 'template', 'extra_tax', 'template.sale_price_w_tax', 'write_date']) if not products: self.message_bar.set('product_not_found') return False elif len(products) > 1: self.products = products self.create_dialog_select_item(products) else: product = products[0] if product: self.fill(product) def on_selected_product(self, row=None): code = row[0] for product in self.products: if product['code'] == code: self.fill(product) self.dialog_select_item.hide() break def create_dialog_select_item(self, products): parent = self._parent width, height = get_screen() grid = QGridLayout() _sizes = (160, 320) fields = ( {'label': 'CODIGO', 'type': 'integer', 'readonly': False}, {'label': 'NOMBRE', 'type': 'char', 'readonly': False}, ) self.model = TableEdit(self, [], fields) self.table = TableView('model_info_product', self.model, _sizes, editable=False, method_selected_row=self.on_selected_product) self.table.setFixedSize(int(width * 0.35), int(height * 0.4)) grid.addWidget(self.table, 1, 0, 1, 2) self.dialog_select_item = QuickDialog(parent, 'action', widgets=[grid], readonly=True, buttons=True) self.dialog_select_item.setWindowTitle('PRODUCTOS') self.load(products) self.dialog_select_item.show() def load(self, products): if not products: return for rec in products: data = [ rec['code'], rec['name'], ] self.model.add_record(data) def show(self): super(DialogInfoProduct, self).show() self.input_filter.setFocus() def clear(self): self.input_filter.setText('') self.input_code.setText('') self.input_name.setText('') self.input_price.setText('') self.input_quantity.setText('') def dialog_accepted(self): self.clear() super(DialogInfoProduct, self).dialog_accepted()