2217 lines
80 KiB
Python
2217 lines
80 KiB
Python
from decimal import Decimal
|
|
from datetime import datetime
|
|
from operator import itemgetter
|
|
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
|
|
from PySide6.QtWidgets import (
|
|
QCheckBox, QTextEdit, QVBoxLayout, QGridLayout, QLineEdit, QPlainTextEdit,
|
|
QScrollArea, QHBoxLayout, QDoubleSpinBox, QLabel, QWidget
|
|
)
|
|
|
|
from .proxy import Report
|
|
from .buttonpad import ButtonsFunction
|
|
from .constants import (alignCenter, alignLeft, FRACTIONS, TYPE_VEHICLE,
|
|
MONEY, TYPE_PRINTER, ROW_CHARACTERS)
|
|
from .constants import (alignCenter, alignLeft, FRACTIONS, TYPE_VEHICLE,
|
|
MONEY, TYPE_PRINTER, ROW_CHARACTERS)
|
|
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
|
|
from .reporting import Receipt
|
|
from .reporting import Receipt
|
|
|
|
__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', 'DialogCollection', 'DialogTestPrinter'
|
|
]
|
|
|
|
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['party.name'] = {'desc': 'CLIENTE', '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'] = {'desc': 'VALOR TOTAL', 'type': 'number'}
|
|
widths_append(90)
|
|
|
|
title = ('BUSCAR PEDIDOS...')
|
|
self.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',
|
|
)
|
|
|
|
if self.parent.environment == 'restaurant':
|
|
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',
|
|
)
|
|
else:
|
|
self.pushButtonReservation = CustomButton(
|
|
id='button_search_sale_quote',
|
|
parent=self,
|
|
title='COTIZACION',
|
|
name_style='start',
|
|
record='quotation',
|
|
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, self.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):
|
|
if _type == 'quotation':
|
|
self.on_return_method = 'on_search_sale_by_number'
|
|
else:
|
|
self.on_return_method = 'on_selected_sale'
|
|
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.name'] = {'desc': 'MARCA', 'type': 'char'}
|
|
_cols_width_append(100)
|
|
|
|
if parent.environment == 'retail':
|
|
headers['template.reference'] = {'desc': 'REFERENCIA', 'type': 'char'}
|
|
_cols_width_append(200)
|
|
|
|
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['positions.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 Exception:
|
|
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.2))
|
|
|
|
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.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):
|
|
options_type = [
|
|
('invoice', 'FACTURA'),
|
|
('order', 'ORDEN'),
|
|
]
|
|
if parent.environment == 'restaurant':
|
|
options_type.append(('quotation', 'COTIZACION'))
|
|
view = (
|
|
('invoice_number_ask', {'name': 'ORDEN / FACTURA'}),
|
|
('type_ask', {
|
|
'name': 'TIPO',
|
|
'type': 'selection',
|
|
'values': options_type,
|
|
}),
|
|
('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('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('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('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)
|
|
|
|
parent.field_send_mail = QCheckBox()
|
|
parent.field_send_mail.setText('ENVIAR EMAIL')
|
|
grid.addWidget(parent.field_send_mail, 3, 1)
|
|
|
|
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_tip_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.environment == '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.']['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):
|
|
qwidget = QWidget()
|
|
self.hbox = QHBoxLayout(qwidget)
|
|
qwidget.setFixedHeight(50)
|
|
|
|
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.hbox.addWidget(label)
|
|
|
|
self.label_qty_min = QLabel('CANT. MIN.')
|
|
self.label_qty_min.setObjectName('label_qty_min')
|
|
self.hbox.addWidget(self.label_qty_min)
|
|
|
|
self.label_qty_min_req = QLabel("")
|
|
self.label_qty_min_req.setObjectName('label_qty_min_req')
|
|
self.hbox.addWidget(self.label_qty_min_req)
|
|
|
|
self.label_qty = QLabel('CANT.')
|
|
self.label_qty.setObjectName('label_qty')
|
|
self.hbox.addWidget(self.label_qty)
|
|
|
|
self.label_qty_add = QLabel("")
|
|
self.label_qty_add.setObjectName('label_qty_add')
|
|
self.hbox.addWidget(self.label_qty_add)
|
|
|
|
self.vbox = QVBoxLayout()
|
|
self.vbox.setObjectName('grid_buttons')
|
|
self.vbox.addWidget(qwidget)
|
|
super(DialogComboProduct, self).__init__(
|
|
parent, 'action', widgets=[self.vbox]
|
|
)
|
|
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.vbox.removeWidget(self.scroll_area)
|
|
self.scroll_area = QScrollArea()
|
|
self.scroll_area.setWidgetResizable(True)
|
|
self.scroll_area.setWidget(grid_buttons)
|
|
self.vbox.addWidget(self.scroll_area)
|
|
|
|
def close(self):
|
|
if self.validate_close_dialog():
|
|
self.label_qty_add.setText("")
|
|
self.label_qty_min_req.setText("")
|
|
super(QuickDialog, self).close()
|
|
|
|
def closeEvent(self, event):
|
|
if self.validate_close_dialog():
|
|
super(QuickDialog, self).closeEvent(event)
|
|
|
|
def dialog_rejected(self):
|
|
if self.validate_close_dialog():
|
|
super().dialog_rejected()
|
|
|
|
def dialog_accepted(self):
|
|
if self.validate_close_dialog():
|
|
super().dialog_accepted()
|
|
|
|
def validate_close_dialog(self):
|
|
qty_add = self.label_qty_add.text()
|
|
qty_req = self.label_qty_min_req.text()
|
|
if qty_req:
|
|
if not qty_add or int(qty_req) - int(qty_add) > 0:
|
|
dialog = self.parent.dialog('qty_combo_min_req', extra_message=f"cantidad minima {qty_req} has agregado {qty_add}")
|
|
dialog.exec()
|
|
return False
|
|
return True
|
|
|
|
|
|
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', 'COMILLAS DOBLE (")'),
|
|
('AGENTE', 'PUNTO Y COMA (;)'),
|
|
)
|
|
|
|
self.set_shortcuts(shortcuts)
|
|
|
|
|
|
class DialogListProduct(QuickDialog):
|
|
def __init__(self, parent):
|
|
self._parent = parent
|
|
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 DialogTestPrinter(QuickDialog):
|
|
|
|
def __init__(self, parent):
|
|
self._parent = parent
|
|
width, height = get_screen()
|
|
grid = QGridLayout()
|
|
if parent.environment == 'restaurant':
|
|
_sizes = (100, 210, 210, 100)
|
|
fields = (
|
|
{'name': 'id', 'label': 'ID', 'type': 'integer', 'invisible': True},
|
|
{'name': 'name', 'label': 'NOMBRE', 'type': 'char', 'readonly': True},
|
|
{'name': 'interface', 'label': 'INTERFACE', 'type': 'char', 'readonly': True},
|
|
{'name': 'server', 'label': 'SERVIDOR', 'type': 'char', 'readonly': True},
|
|
{'name': 'row_characters', 'label': 'CARACTERES POR FILA', 'type': 'integer', 'readonly': True},
|
|
)
|
|
self.model = TableEdit(self, [], fields)
|
|
self.table = TableView('model_printers', self.model, _sizes, self.fill_fields)
|
|
self.table.hideColumn(0)
|
|
|
|
grid.addWidget(self.table, 0, 0, 2, 7)
|
|
|
|
label_interface = QLabel('INTERFACE:')
|
|
label_interface.setObjectName('label_interface')
|
|
grid.addWidget(label_interface, 3, 1)
|
|
self.combo_interface = ComboBox(parent, 'type_printer', {'values': TYPE_PRINTER})
|
|
grid.addWidget(self.combo_interface, 3, 2)
|
|
|
|
label_server = QLabel('SERVIDOR:')
|
|
label_server.setObjectName('label_server')
|
|
grid.addWidget(label_server, 3, 3)
|
|
self.input_server = QLineEdit()
|
|
self.input_server.setObjectName('input_server')
|
|
grid.addWidget(self.input_server, 3, 4)
|
|
|
|
label_row_characters = QLabel('CARACTERES POR FILA:')
|
|
label_row_characters.setObjectName('label_row_characters')
|
|
grid.addWidget(label_row_characters, 3, 5)
|
|
self.combo_row_characters = ComboBox(
|
|
parent, 'row_characters', {'values': ROW_CHARACTERS}
|
|
)
|
|
grid.addWidget(self.combo_row_characters, 3, 6)
|
|
|
|
super(DialogTestPrinter, self).__init__(
|
|
parent, 'action', widgets=[grid]
|
|
)
|
|
self.setWindowTitle('TEST IMPRESORA')
|
|
self.setFixedSize(int(width * 0.4), int(height * 0.3))
|
|
|
|
def load(self):
|
|
printers_shop = self.parent.printers_shop
|
|
if getattr(self, 'table', None) and printers_shop:
|
|
model_add = self.model.add_record
|
|
for k, v in printers_shop.items():
|
|
data = [
|
|
k,
|
|
v.get('name', ''),
|
|
v['interface'],
|
|
v['host'],
|
|
v['row_characters'],
|
|
]
|
|
model_add(data)
|
|
|
|
def exec_(self):
|
|
self.clear()
|
|
self.load()
|
|
super(DialogTestPrinter, self).exec_()
|
|
|
|
def clear(self):
|
|
self.model.clearData()
|
|
self.input_server.setText("")
|
|
self.combo_interface.set_from_id("")
|
|
self.combo_row_characters.set_from_id("")
|
|
|
|
def test_printer(self):
|
|
print('configure test')
|
|
server = self.input_server.text()
|
|
interface = self.combo_interface.get_id()
|
|
row_characters = self.combo_row_characters.get_id()
|
|
|
|
printer_test = {
|
|
'interface': interface,
|
|
'device': str(server),
|
|
'profile': 'TM-P80',
|
|
'row_characters': row_characters,
|
|
}
|
|
|
|
ctx_printing = {}
|
|
ctx_printing['company'] = 'OSCORP INC'
|
|
ctx_printing['sale_device'] = 'CAJA-10'
|
|
ctx_printing['shop'] = 'Shop Wall Boulevard'
|
|
ctx_printing['street'] = 'Cll 21 # 172-81. Central Park'
|
|
ctx_printing['user'] = 'Charles Chapplin'
|
|
ctx_printing['city'] = 'Dallas'
|
|
ctx_printing['zip'] = '0876'
|
|
ctx_printing['phone'] = '591 5513 455'
|
|
ctx_printing['id_number'] = '123456789-0'
|
|
ctx_printing['tax_regime'] = 'none'
|
|
receipt = Receipt(ctx_printing)
|
|
receipt.config_printer(printer_test)
|
|
return receipt.test_printer()
|
|
|
|
def dialog_accepted(self):
|
|
result = self.test_printer()
|
|
if result:
|
|
msg = 'Impresion Exitosa ✔'
|
|
else:
|
|
msg = '''\n\n Test de impresión ha fallado,
|
|
es posible que haya un problema con la conexión de energía, USB o red.
|
|
Para solucionar el problema, asegúrese de que la impresora esté conectada
|
|
correctamente a la fuente de alimentación y que el cable USB o Ethernet
|
|
esté conectado correctamente a la impresora y
|
|
al dispositivo desde el que está intentando imprimir.'''
|
|
self._parent.dialog('test_printer', extra_message=msg)
|
|
if result:
|
|
super(DialogTestPrinter, self).dialog_accepted()
|
|
|
|
def fill_fields(self, data):
|
|
self.input_server.setText(data[3])
|
|
self.combo_interface.set_from_id(data[2])
|
|
self.combo_row_characters.set_from_id(str(data[4]))
|
|
|
|
|
|
class DialogTestPrinter(QuickDialog):
|
|
|
|
def __init__(self, parent):
|
|
self._parent = parent
|
|
width, height = get_screen()
|
|
grid = QGridLayout()
|
|
if parent.environment == 'restaurant':
|
|
_sizes = (100, 210, 210, 100)
|
|
fields = (
|
|
{'name': 'id', 'label': 'ID', 'type': 'integer', 'invisible': True},
|
|
{'name': 'name', 'label': 'NOMBRE', 'type': 'char', 'readonly': True},
|
|
{'name': 'interface', 'label': 'INTERFACE', 'type': 'char', 'readonly': True},
|
|
{'name': 'server', 'label': 'SERVIDOR', 'type': 'char', 'readonly': True},
|
|
{'name': 'row_characters', 'label': 'CARACTERES POR FILA', 'type': 'integer', 'readonly': True},
|
|
)
|
|
self.model = TableEdit(self, [], fields)
|
|
self.table = TableView('model_printers', self.model, _sizes, self.fill_fields)
|
|
self.table.hideColumn(0)
|
|
|
|
grid.addWidget(self.table, 0, 0, 2, 7)
|
|
|
|
label_interface = QLabel('INTERFACE:')
|
|
label_interface.setObjectName('label_interface')
|
|
grid.addWidget(label_interface, 3, 1)
|
|
self.combo_interface = ComboBox(parent, 'type_printer', {'values': TYPE_PRINTER})
|
|
grid.addWidget(self.combo_interface, 3, 2)
|
|
|
|
label_server = QLabel('SERVIDOR:')
|
|
label_server.setObjectName('label_server')
|
|
grid.addWidget(label_server, 3, 3)
|
|
self.input_server = QLineEdit()
|
|
self.input_server.setObjectName('input_server')
|
|
grid.addWidget(self.input_server, 3, 4)
|
|
|
|
label_row_characters = QLabel('CARACTERES POR FILA:')
|
|
label_row_characters.setObjectName('label_row_characters')
|
|
grid.addWidget(label_row_characters, 3, 5)
|
|
self.combo_row_characters = ComboBox(
|
|
parent, 'row_characters', {'values': ROW_CHARACTERS}
|
|
)
|
|
grid.addWidget(self.combo_row_characters, 3, 6)
|
|
|
|
super(DialogTestPrinter, self).__init__(
|
|
parent, 'action', widgets=[grid]
|
|
)
|
|
self.setWindowTitle('TEST IMPRESORA')
|
|
self.setFixedSize(int(width * 0.4), int(height * 0.3))
|
|
|
|
def load(self):
|
|
printers_shop = self.parent.printers_shop
|
|
if getattr(self, 'table', None) and printers_shop:
|
|
model_add = self.model.add_record
|
|
for k, v in printers_shop.items():
|
|
data = [
|
|
k,
|
|
v.get('name', ''),
|
|
v['interface'],
|
|
v['host'],
|
|
v['row_characters'],
|
|
]
|
|
model_add(data)
|
|
|
|
def exec(self):
|
|
self.clear()
|
|
self.load()
|
|
super(DialogTestPrinter, self).exec()
|
|
|
|
def clear(self):
|
|
self.model.clearData()
|
|
self.input_server.setText("")
|
|
self.combo_interface.set_from_id("")
|
|
self.combo_row_characters.set_from_id("")
|
|
|
|
def test_printer(self):
|
|
print('configure test')
|
|
server = self.input_server.text()
|
|
interface = self.combo_interface.get_id()
|
|
row_characters = self.combo_row_characters.get_id()
|
|
|
|
printer_test = {
|
|
'interface': interface,
|
|
'device': str(server),
|
|
'profile': 'TM-P80',
|
|
'row_characters': row_characters,
|
|
}
|
|
|
|
ctx_printing = {}
|
|
ctx_printing['company'] = 'OSCORP INC'
|
|
ctx_printing['sale_device'] = 'CAJA-10'
|
|
ctx_printing['shop'] = 'Shop Wall Boulevard'
|
|
ctx_printing['street'] = 'Cll 21 # 172-81. Central Park'
|
|
ctx_printing['user'] = 'Charles Chapplin'
|
|
ctx_printing['city'] = 'Dallas'
|
|
ctx_printing['zip'] = '0876'
|
|
ctx_printing['phone'] = '591 5513 455'
|
|
ctx_printing['id_number'] = '123456789-0'
|
|
ctx_printing['tax_regime'] = 'none'
|
|
receipt = Receipt(ctx_printing)
|
|
receipt.config_printer(printer_test)
|
|
return receipt.test_printer()
|
|
|
|
def dialog_accepted(self):
|
|
result = self.test_printer()
|
|
if result:
|
|
msg = 'Impresion Exitosa ✔'
|
|
else:
|
|
msg = '''\n\n Test de impresión ha fallado,
|
|
es posible que haya un problema con la conexión de energía, USB o red.
|
|
Para solucionar el problema, asegúrese de que la impresora esté conectada
|
|
correctamente a la fuente de alimentación y que el cable USB o Ethernet
|
|
esté conectado correctamente a la impresora y
|
|
al dispositivo desde el que está intentando imprimir.'''
|
|
self._parent.dialog('test_printer', extra_message=msg)
|
|
if result:
|
|
super(DialogTestPrinter, self).dialog_accepted()
|
|
|
|
def fill_fields(self, data):
|
|
self.input_server.setText(data[3])
|
|
self.combo_interface.set_from_id(data[2])
|
|
self.combo_row_characters.set_from_id(str(data[4]))
|
|
|
|
|
|
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',
|
|
('code', 'ilike', '%' + filter + '%'),
|
|
('name', 'ilike', '%' + filter + '%')
|
|
])
|
|
if self.parent._onebarcode_activated:
|
|
domain.append(('barcode', 'ilike', '%' + filter + '%'))
|
|
|
|
|
|
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._parent.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': 'char', '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()
|
|
|
|
|
|
class DialogCollection(QuickDialog):
|
|
def __init__(self, parent):
|
|
self._parent = parent
|
|
self.parties = []
|
|
self.party_id = None
|
|
self.statements = {}
|
|
vbox = QVBoxLayout()
|
|
grid = QGridLayout()
|
|
|
|
label_filter = QLabel('FILTRO:')
|
|
label_filter.setObjectName('label_collection_filter')
|
|
grid.addWidget(label_filter, 1, 1)
|
|
self.input_filter = QLineEdit()
|
|
self.input_filter.setObjectName('input_collection_filter')
|
|
self.input_filter.editingFinished.connect(lambda: self.search())
|
|
self.input_filter.returnPressed.connect(lambda: self.search())
|
|
|
|
grid.addWidget(self.input_filter, 1, 2)
|
|
|
|
label_id_number = QLabel('DOCUMENTO:')
|
|
label_id_number.setObjectName('label_party_id_number')
|
|
grid.addWidget(label_id_number, 2, 1)
|
|
self.input_id_number = QLineEdit()
|
|
self.input_id_number.setReadOnly(True)
|
|
self.input_id_number.setObjectName('input_party_id_number')
|
|
grid.addWidget(self.input_id_number, 2, 2)
|
|
|
|
label_name = QLabel('NOMBRE:')
|
|
label_name.setObjectName('label_party_name')
|
|
grid.addWidget(label_name, 3, 1)
|
|
self.input_name = QLineEdit()
|
|
self.input_name.setReadOnly(True)
|
|
self.input_name.setObjectName('input_party_name')
|
|
grid.addWidget(self.input_name, 3, 2)
|
|
|
|
label_amount = QLabel('VALOR:')
|
|
label_amount.setObjectName('label_collection_amount')
|
|
grid.addWidget(label_amount, 4, 1)
|
|
self.input_amount = QLineEdit()
|
|
self.input_amount.setObjectName('input_collection_amount')
|
|
grid.addWidget(self.input_amount, 4, 2)
|
|
|
|
label_payment_method = QLabel('MODO DE PAGO:')
|
|
label_payment_method.setObjectName('label_collection_payment_method')
|
|
grid.addWidget(label_payment_method, 5, 1)
|
|
self.combobox_payment_method = ComboBox(
|
|
parent, 'payment_method_collection', {'values': self.get_payment_methods()}
|
|
)
|
|
grid.addWidget(self.combobox_payment_method, 5, 2)
|
|
|
|
label_voucher_number = QLabel('NUMERO COMPROBANTE:')
|
|
label_voucher_number.setObjectName('label_collection_voucher_number')
|
|
grid.addWidget(label_voucher_number, 6, 1)
|
|
self.input_voucher_number = QLineEdit()
|
|
self.input_voucher_number.setObjectName('input_collection_voucher_number')
|
|
grid.addWidget(self.input_voucher_number, 6, 2)
|
|
|
|
vbox.addLayout(grid)
|
|
super(DialogCollection, self).__init__(parent, 'help', widgets=[vbox])
|
|
self.setWindowTitle('RECAUDO')
|
|
self.ok_button.setDefault(False)
|
|
width, height = get_screen()
|
|
self.setGeometry(0, 0, int(width * 0.4), int(height * 0.5))
|
|
self.input_filter.setFocus()
|
|
|
|
def fill(self, values):
|
|
self.input_id_number.setText(values['id_number'])
|
|
self.input_name.setText(values['name'])
|
|
self.party_id = values['id']
|
|
|
|
def get_payment_methods(self):
|
|
domain = [
|
|
["sale_device", "=", self._parent.device['id']],
|
|
["state", "=", "draft"]
|
|
]
|
|
statements = self._parent.Statement.find(domain,
|
|
fields=['rec_name', 'journal.require_voucher'])
|
|
records = [('', '')]
|
|
statements_ = {}
|
|
for st in statements:
|
|
statements_[st['id']] = st
|
|
records.append((st['id'], st['rec_name']))
|
|
self.statements = statements_
|
|
return records
|
|
|
|
def search(self, values=None):
|
|
self.ok_button.setDefault(False)
|
|
filter = self.input_filter.text()
|
|
if not filter:
|
|
return
|
|
|
|
domain = ['OR',
|
|
('id_number', 'ilike', '%' + filter + '%'),
|
|
('name', 'ilike', '%' + filter + '%'),
|
|
]
|
|
|
|
parties = self._parent.Party.find(domain,
|
|
fields=['name', 'id_number'])
|
|
|
|
if not parties:
|
|
self.create_dialog_message('TERCERO NO ENCONTRADO..!', 'error')
|
|
return False
|
|
elif len(parties) > 1:
|
|
self.parties = parties
|
|
self.create_dialog_select_item(parties)
|
|
else:
|
|
party = parties[0]
|
|
if party:
|
|
self.fill(party)
|
|
|
|
def on_selected_party(self, row=None):
|
|
id_number = row[0]
|
|
for party in self.parties:
|
|
if party['id_number'] == id_number:
|
|
self.fill(party)
|
|
self.dialog_select_item.hide()
|
|
break
|
|
|
|
def create_dialog_select_item(self, parties):
|
|
parent = self._parent
|
|
width, height = get_screen()
|
|
grid = QGridLayout()
|
|
_sizes = (160, 320)
|
|
fields = (
|
|
{'label': 'DOCUMENTO', 'type': 'char', 'readonly': False},
|
|
{'label': 'NOMBRE', 'type': 'char', 'readonly': False},
|
|
)
|
|
self.model = TableEdit(self, [], fields)
|
|
self.table = TableView('model_party', self.model, _sizes, editable=False, method_selected_row=self.on_selected_party)
|
|
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('TERCEROS')
|
|
self.load(parties)
|
|
self.dialog_select_item.show()
|
|
|
|
def load(self, parties):
|
|
if not parties:
|
|
return
|
|
for rec in parties:
|
|
data = [
|
|
rec['id_number'],
|
|
rec['name'],
|
|
]
|
|
self.model.add_record(data)
|
|
|
|
def show(self):
|
|
super(DialogCollection, self).show()
|
|
self.input_filter.setFocus()
|
|
|
|
def clear(self):
|
|
self.input_filter.setText('')
|
|
self.input_id_number.setText('')
|
|
self.input_name.setText('')
|
|
self.input_amount.setText('')
|
|
self.combobox_payment_method.set_none()
|
|
self.input_voucher_number.setText('')
|
|
self.party_id = None
|
|
|
|
def dialog_accepted(self):
|
|
args = {
|
|
'party': self.party_id,
|
|
'amount': self.input_amount.text(),
|
|
'statement': self.combobox_payment_method.get_id(),
|
|
'voucher_number': self.input_voucher_number.text()
|
|
}
|
|
require_voucher = self.statements[int(args['statement'])]['journal.']['require_voucher']
|
|
if not args.get('voucher_number') and require_voucher:
|
|
self.create_dialog_message('REQUIERE COMPROBANTE', 'info')
|
|
return False
|
|
rec = self._parent.Statement.apply_payment_collection(args)
|
|
if rec.get('status') and rec.get('status') == 'ok':
|
|
self.create_dialog_message(rec['message'], 'info')
|
|
else:
|
|
self.create_dialog_message(rec['message'], 'error')
|
|
|
|
self.clear()
|
|
super(DialogCollection, self).dialog_accepted()
|
|
|
|
def create_dialog_message(self, message, kind):
|
|
parent = self._parent
|
|
width, height = get_screen()
|
|
self.dialog_message = QuickDialog(parent, kind, string=message, readonly=True, buttons=True)
|