diff --git a/CHANGELOG.md b/CHANGELOG.md index 27274ce..a10aad2 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,9 @@ +v 2.3.0 [01-Abr-2024] + - Mejora: Soporte para complemento Carta Porte 3.0 + - **IMPORTANTE**: Aunque no lo uses, esto afecta al JS de facturación, por + lo que tienes que forzar el refresco (CTRL+F5) si tienes algún problema. + + v 2.2.0 [24-Ene-2024] - Mejora: Soporte para complemento Comercio Exterior 2.0 - **IMPORTANTE**: Aunque no lo uses, esto afecta al JS de facturación, por diff --git a/VERSION b/VERSION index ccbccc3..276cbf9 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -2.2.0 +2.3.0 diff --git a/source/app/controllers/cfdi_xml.py b/source/app/controllers/cfdi_xml.py index ee3d961..90abbce 100644 --- a/source/app/controllers/cfdi_xml.py +++ b/source/app/controllers/cfdi_xml.py @@ -111,10 +111,10 @@ SAT = { 'schema': ' http://www.sat.gob.mx/leyendasFiscales http://www.sat.gob.mx/sitio_internet/cfd/leyendasFiscales/leyendasFisc.xsd', }, 'cartaporte': { - 'version': '2.0', - 'prefix': 'cartaporte20', - 'xmlns': 'http://www.sat.gob.mx/CartaPorte20', - 'schema': ' http://www.sat.gob.mx/CartaPorte20 http://www.sat.gob.mx/sitio_internet/cfd/CartaPorte/CartaPorte20.xsd', + 'version': '3.0', + 'prefix': 'cartaporte30', + 'xmlns': 'http://www.sat.gob.mx/CartaPorte30', + 'schema': ' http://www.sat.gob.mx/CartaPorte30 http://www.sat.gob.mx/sitio_internet/cfd/CartaPorte/CartaPorte30.xsd', }, 'comercioe': { 'version': '2.0', @@ -575,6 +575,11 @@ class CFDI(object): mercancias = datos.pop('mercancias', ()) tiposfigura = datos.pop('tiposfigura', ()) + autotransporte = datos.pop('autotransporte', {}) + identificacion = autotransporte.pop('identificacion') + seguros = autotransporte.pop('seguros') + remolques = autotransporte.pop('remolques') + atributos = {'Version': SAT['cartaporte']['version']} atributos.update(datos) @@ -592,10 +597,6 @@ class CFDI(object): attr = mercancias mercancias = attr.pop('mercancias') - autotransporte = attr.pop('autotransporte') - identificacion = autotransporte.pop('identificacion') - seguros = autotransporte.pop('seguros') - remolque = autotransporte.pop('remolque') node = ET.SubElement(node_carta, f'{prefix}:Mercancias', attr) for mercancia in mercancias: @@ -604,10 +605,10 @@ class CFDI(object): sub_node = ET.SubElement(node, f'{prefix}:Autotransporte', autotransporte) ET.SubElement(sub_node, f'{prefix}:IdentificacionVehicular', identificacion) ET.SubElement(sub_node, f'{prefix}:Seguros', seguros) - if 'SubTipoRem' in remolque and 'Placa' in remolque \ - and remolque['SubTipoRem'] and remolque['Placa']: - tmp = ET.SubElement(sub_node, f'{prefix}:Remolques') - ET.SubElement(tmp, f'{prefix}:Remolque', remolque) + if remolques: + node_remolques = ET.SubElement(sub_node, f'{prefix}:Remolques') + for remolque in remolques: + ET.SubElement(node_remolques, f'{prefix}:Remolque', remolque) if tiposfigura: sub_node = ET.SubElement(node_carta, f'{prefix}:FiguraTransporte') @@ -630,7 +631,9 @@ class CFDI(object): atributos.update(datos['ine']) node_ine = ET.SubElement(self._complemento, 'ine:INE', atributos) if ine_key_entidad: - attr = {'ClaveEntidad': ine_key_entidad, 'Ambito': ine_ambito} + attr = {'ClaveEntidad': ine_key_entidad} + if ine_ambito: + attr['Ambito'] = ine_ambito node_entidad = ET.SubElement(node_ine, 'ine:Entidad', attr) attr = {'IdContabilidad': ine_id_conta} ET.SubElement(node_entidad, 'ine:Contabilidad', attr) diff --git a/source/app/controllers/util.py b/source/app/controllers/util.py index f1cfb29..87944ea 100644 --- a/source/app/controllers/util.py +++ b/source/app/controllers/util.py @@ -30,6 +30,7 @@ import requests import sqlite3 import socket import subprocess +import sys import tempfile import textwrap import threading @@ -44,7 +45,6 @@ from pathlib import Path from xml.etree import ElementTree as ET from xml.dom.minidom import parseString - try: import uno from com.sun.star.beans import PropertyValue @@ -52,9 +52,20 @@ try: from com.sun.star.view.PaperFormat import LETTER APP_LIBO = True except ImportError: - APP_LIBO = False + path_fun = '/usr/lib/libreoffice/program/fundamentalrc' + path_uno = '/usr/lib/libreoffice/program/' + os.environ['URE_BOOTSTRAP'] = f'vnd.sun.star.pathname:{path_fun}' + os.environ['UNO_PATH'] = path_uno + sys.path.append(path_uno) + try: + import uno + from com.sun.star.beans import PropertyValue + from com.sun.star.awt import Size + from com.sun.star.view.PaperFormat import LETTER + APP_LIBO = True + except ImportError: + APP_LIBO = False -# ~ import pyqrcode from dateutil import parser from lxml import etree @@ -69,7 +80,6 @@ from settings import DEBUG, MV, log, template_lookup, COMPANIES, DB_SAT, \ PATH_XMLSEC, TEMPLATE_CANCEL, DEFAULT_SAT_PRODUCTO, DECIMALES, DIR_FACTURAS from settings import USAR_TOKEN, API, DECIMALES_TAX -# ~ from .configpac import AUTH from .utils import get_qr @@ -951,6 +961,7 @@ class LIBO(object): return # ~ print(data) + qr = data.pop('qr', False) figuras = data.pop('figuras') mercancias = data.pop('mercancias') detalle = mercancias.pop('detalle') @@ -1019,7 +1030,27 @@ class LIBO(object): cell_3 = self._set_cell(v=unidad, cell=cell_3) cell_4 = self._set_cell(v=cantidad, cell=cell_4) cell_5 = self._set_cell(v=peso, cell=cell_5) + if qr: + self._timbre_carta(qr) + return + def _timbre_carta(self, qr): + pd = self._sheet.getDrawPage() + image = self._template.createInstance('com.sun.star.drawing.GraphicObjectShape') + gp = self._create_instance('com.sun.star.graphic.GraphicProvider') + pd.add(image) + + instance = 'com.sun.star.io.SequenceInputStream' + stream = self._create_instance(instance) + stream.initialize((uno.ByteSequence(qr.getvalue()),)) + properties = self._set_properties({'InputStream': stream}) + image.Graphic = gp.queryGraphic(properties) + + s = Size() + s.Width = 4000 + s.Height = 4000 + image.setSize(s) + image.Anchor = self._set_cell('{cp.qr}') return def _comercio_exterior(self, data): @@ -1355,6 +1386,7 @@ class LIBO(object): except KeyError: msg = 'Hoja no existe' return (), msg + return cursor.getDataArray(), '' def products(self, path): @@ -1615,6 +1647,7 @@ class LIBO(object): return (), msg rows = tuple(data[1:]) + return rows, '' def _data_to_dict(self, rows): @@ -1688,7 +1721,7 @@ def to_pdf(data, emisor_rfc, ods=False, pdf_from='1'): version = f'{version}_cn_{version_nomina}' if 'carta_porte' in data: - default = 'plantilla_factura_ccp.ods' + default = 'plantilla_ccp.ods' version = '{}_ccp_{}'.format(version, data['carta_porte']['version']) if data.get('pagos', False): @@ -1842,24 +1875,6 @@ def to_letters(value, currency): return NumLet(value, currency).letras -# ~ def get_qr(data, p=True): - # ~ qr = pyqrcode.create(data, mode='binary') - # ~ if p: - # ~ path = get_path_temp('.qr') - # ~ qr.png(path, scale=7) - # ~ return path - - # ~ buffer = io.BytesIO() - # ~ qr.png(buffer, scale=8) - # ~ return base64.b64encode(buffer.getvalue()).decode() - - -# ~ def get_qr2(data, kind='svg'): - # ~ buffer = io.BytesIO() - # ~ segno.make(data).save(buffer, kind=kind, scale=8, border=2) - # ~ return buffer - - def _get_relacionados(doc, version): node = doc.find('{}CfdiRelacionados'.format(PRE[version])) if node is None: @@ -2420,6 +2435,7 @@ def upload_file(rfc, opt, file_obj): '_4.0_cn_1.2.ods', '_4.0_cp_2.0.ods', '_4.0_ccp_2.0.ods', + '_4.0_ccp_3.0.ods', '_4.0_cd_1.1.ods', '_4.0_cce_2.0.ods', '_4.0.json', @@ -3142,4 +3158,9 @@ def parse_xml2(xml_str): return etree.fromstring(xml_str.encode('utf-8')) +def get_idccp(): + uuid4 = str(uuid.uuid4()).upper() + custom_uuid_str = f'CCC{uuid4[3:]}' + # ~ custom_uuid_str = f"CCC{uuid_v4.hex[3:8].upper()}-{uuid_v4.hex[8:12].upper()}-{uuid_v4.hex[12:16].upper()}-{uuid_v4.hex[16:20].upper()}-{uuid_v4.hex[20:32].upper()}" + return custom_uuid_str diff --git a/source/app/controllers/utils.py b/source/app/controllers/utils.py index 313a788..5ef7bb1 100644 --- a/source/app/controllers/utils.py +++ b/source/app/controllers/utils.py @@ -261,9 +261,11 @@ class CfdiToDict(object): 'cfdi4.0': 'http://www.sat.gob.mx/cfd/4', } NS = { + 'tfd': 'http://www.sat.gob.mx/TimbreFiscalDigital', 'divisas': 'http://www.sat.gob.mx/divisas', 'leyendasFisc': 'http://www.sat.gob.mx/leyendasFiscales', 'cartaporte20': 'http://www.sat.gob.mx/CartaPorte20', + 'cartaporte30': 'http://www.sat.gob.mx/CartaPorte30', 'nomina12': 'http://www.sat.gob.mx/nomina12', 'cce20': 'http://www.sat.gob.mx/ComercioExterior20', } @@ -397,11 +399,23 @@ class CfdiToDict(object): self.version = self._root.attrib['Version'] ns = f'cfdi{self.version}' self.NS['cfdi'] = self.NS_VERSION[ns] + self._timbre_fiscal() self._informacion_global() self._receptor() self._complementos() return + def _timbre_fiscal(self): + path = '//tfd:TimbreFiscalDigital' + data = self._root.xpath(path, namespaces=self.NS) + if not data: + return + + data = data[0] + attr = CaseInsensitiveDict(data.attrib) + self._fecha_timbrado = attr['FechaTimbrado'] + return + def _informacion_global(self): self._values['informacion_global'] = {} @@ -514,10 +528,75 @@ class CfdiToDict(object): self._values['carta_porte'] = values + self._complemento_carta_porte(complemento) self._complemento_comercio_exterior(complemento) return + def _complemento_carta_porte(self, complemento): + path = '//cartaporte30:CartaPorte' + carta_porte = complemento.xpath(path, namespaces=self.NS) + if carta_porte: + self._get_carta_porte_3(carta_porte) + return + + def _get_carta_porte_3(self, carta_porte): + URL = 'https://verificacfdi.facturaelectronica.sat.gob.mx/verificaccp/default.aspx' + PRE = '//cartaporte30' + values = CaseInsensitiveDict(carta_porte[0].attrib) + idccp = values['idccp'] + for node in carta_porte[0]: + if 'FiguraTransporte' in node.tag: + figuras = CaseInsensitiveDict(node[0].attrib) + figuras['TipoFigura'] = self.tipo_figura[figuras['TipoFigura']] + values['figuras'] = figuras + elif 'Mercancias' in node.tag: + mercancias = CaseInsensitiveDict(node.attrib) + detalle = [CaseInsensitiveDict(n.attrib) + for n in node if 'Mercancia' in n.tag] + values['mercancias'] = { + 'mercancias': mercancias, + 'detalle': detalle, + } + + path = f'{PRE}:Autotransporte' + node_auto = node.xpath(path, namespaces=self.NS)[0] + values_auto = CaseInsensitiveDict(node_auto.attrib) + values['autotransporte'] = values_auto + + path = f'{PRE}:IdentificacionVehicular' + node_tmp = node_auto.xpath(path, namespaces=self.NS)[0] + values_auto = CaseInsensitiveDict(node_tmp.attrib) + values['autotransporte'].update(values_auto) + + path = f'{PRE}:Seguros' + node_tmp = node_auto.xpath(path, namespaces=self.NS)[0] + values_auto = CaseInsensitiveDict(node_tmp.attrib) + values['autotransporte'].update(values_auto) + + path = f'{PRE}:Remolques' + try: + node_tmp = node_auto.xpath(path, namespaces=self.NS)[0][0] + values_auto = CaseInsensitiveDict(node_tmp.attrib) + values['autotransporte'].update(values_auto) + except IndexError: + pass + elif 'Ubicaciones' in node.tag: + ubicaciones = [] + for n in node: + ubicacion = CaseInsensitiveDict(n.attrib) + if ubicacion['TipoUbicacion'] == 'Origen': + fecha_origen = ubicacion['FechaHoraSalidaLlegada'] + ubicacion['domicilio'] = self._set_carta_porte_domicilio( + CaseInsensitiveDict(n[0].attrib)) + ubicaciones.append(ubicacion) + values['FechaOrigen'] = fecha_origen + values['ubicaciones'] = ubicaciones + qr_data = f'{URL}?IdCCP={idccp}&FechaOrig={fecha_origen}&FechaTimb={self._fecha_timbrado}' + values['qr'] = get_qr(qr_data, 'png') + self._values['carta_porte'] = values + return + def _complemento_comercio_exterior(self, complemento): path = '//cce20:ComercioExterior' comercio_exterior = complemento.xpath(path, namespaces=self.NS) diff --git a/source/app/models/main.py b/source/app/models/main.py index ed75c0f..072ca1a 100644 --- a/source/app/models/main.py +++ b/source/app/models/main.py @@ -79,7 +79,6 @@ def conectar(opt): db = { 'sqlite': SqliteDatabase, 'postgres': PostgresqlDatabase, - 'mysql': MySQLDatabase, } db_type = opt.pop('type') db_name = opt.pop('name') @@ -4824,16 +4823,6 @@ class Facturas(BaseModel): obj = SATTipoRelacion.get(SATTipoRelacion.key==invoice.tipo_relacion) values['tiporelacion'] = str(obj) - # ~ use_packing = Configuracion.get_bool('chk_use_packing') - # ~ if use_packing: - # ~ w = FacturasDetalle.factura == invoice - # ~ q = (FacturasDetalle - # ~ .select(FacturasDetalle.empaques) - # ~ .where(w) - # ~ .order_by(FacturasDetalle.id.asc()) - # ~ .tuples()) - # ~ values['pakings'] = [str(int(r[0])) for r in q] - return values def _get_not_in_xml2(self, invoice, data): @@ -5576,16 +5565,37 @@ class Facturas(BaseModel): if not valores: return + info = {} values = utils.loads(valores) + info['IdCCP'] = util.get_idccp() + info['TranspInternac'] = values['TranspInternac'] + autotransporte = { + 'PermSCT': values['autotransporte'].pop('PermSCT'), + 'NumPermisoSCT': values['autotransporte'].pop('NumPermisoSCT'), + } + identificacion = values['autotransporte'] + if 'PesoBrutoVehicular' in identificacion \ + and isinstance(identificacion['PesoBrutoVehicular'], float): + identificacion['PesoBrutoVehicular'] = f"{identificacion['PesoBrutoVehicular']:.2f}" + info['autotransporte'] = autotransporte + info['autotransporte']['identificacion'] = identificacion + info['autotransporte']['seguros'] = values['seguros'] + info['autotransporte']['remolques'] = values['remolques'] total_distance = 0.00 total_weight = 0.00 mercancias = values['mercancias'] - for mercancia in mercancias['mercancias']: + for mercancia in mercancias: total_weight += float(mercancia['PesoEnKg']) if isinstance(mercancia['PesoEnKg'], (int, float)): mercancia['PesoEnKg'] = f"{mercancia['PesoEnKg']:.2f}" - mercancias['PesoBrutoTotal'] = f"{total_weight:.2f}" + mercancia['Cantidad'] = f"{mercancia['Cantidad']:.2f}" + + info['mercancias'] = {} + info['mercancias']['UnidadPeso'] = values['unidad_peso'] + info['mercancias']['PesoBrutoTotal'] = f"{total_weight:.2f}" + info['mercancias']['NumTotalMercancias'] = f"{len(mercancias):,}" + info['mercancias']['mercancias'] = mercancias ubicaciones = values['ubicaciones'] for ubicacion in ubicaciones: @@ -5609,12 +5619,15 @@ class Facturas(BaseModel): 'CodigoPostal': cp, } - values['TotalDistRec'] = f"{total_distance:.2f}" - # ~ print(2, values) + info['TotalDistRec'] = f"{total_distance:.2f}" + info['ubicaciones'] = ubicaciones + info['tiposfigura'] = values['tiposfigura'] + + # ~ print(2, info) data = { 'factura': invoice, 'nombre': 'cartaporte', - 'valores': utils.dumps(values), + 'valores': utils.dumps(info), } FacturasComplementos.create(**data) return diff --git a/source/app/settings.py b/source/app/settings.py index a2458d9..190833e 100644 --- a/source/app/settings.py +++ b/source/app/settings.py @@ -39,7 +39,7 @@ except ImportError: DEBUG = DEBUG -VERSION = '2.2.0' +VERSION = '2.3.0' EMAIL_SUPPORT = ('soporte@empresalibre.mx',) TITLE_APP = '{} v{}'.format(TITLE_APP, VERSION) diff --git a/source/static/js/controller/invoices.js b/source/static/js/controller/invoices.js index 74aca5f..67db55a 100644 --- a/source/static/js/controller/invoices.js +++ b/source/static/js/controller/invoices.js @@ -97,12 +97,18 @@ var invoices_controllers = { tv_invoice = $$('tv_invoice').getTabbar() tv_invoice.attachEvent('onChange', tv_invoice_change) - $$('grid_carta_mercancias').attachEvent('onItemClick', grid_carta_mercancias_click) - $$('grid_carta_ubicaciones').attachEvent('onBeforeEditStop', grid_carta_ubicaciones_before_edit_stop) - $$('cmd_carta_add_product').attachEvent('onItemClick', cmd_carta_add_product_click) - $$('cmd_carta_copy_from_invoice').attachEvent('onItemClick', cmd_carta_copy_from_invoice_click) + //~ CartaPorte + $$('grid_ccp_ubicaciones').attachEvent('onBeforeEditStop', grid_ccp_ubicaciones_before_edit_stop) + $$('grid_ccp_ubicaciones').attachEvent('onItemClick', grid_ccp_ubicaciones_click) + $$('grid_ccp_mercancias').attachEvent('onItemClick', grid_ccp_mercancias_click) + $$('grid_ccp_remolques').attachEvent('onItemClick', grid_ccp_remolques_click) + $$('cmd_ccp_agregar_ubicacion').attachEvent('onItemClick', cmd_ccp_agregar_ubicacion_click) + $$('cmd_ccp_add_product').attachEvent('onItemClick', cmd_ccp_add_product_click) + $$('cmd_ccp_agregar_remolque').attachEvent('onItemClick', cmd_ccp_agregar_remolque_click) + //~ $$('cmd_carta_copy_from_invoice').attachEvent('onItemClick', cmd_carta_copy_from_invoice_click) $$('cmd_carta_import_json').attachEvent('onItemClick', cmd_carta_import_json_click) + //~ ComercioExterior $$('cmd_import_json_comercioe').attachEvent('onItemClick', cmd_import_json_comercioe_click) $$('cmd_ce_import_ods').attachEvent('onItemClick', cmd_ce_import_ods_click) $$('cmd_ce_tipo_cambio').attachEvent('onItemClick', cmd_ce_tipo_cambio_click) @@ -397,16 +403,6 @@ function validate_invoice(values){ return false } - var usar_cartaporte = $$('chk_cfdi_usar_cartaporte').getValue() - if(usar_cartaporte){ - value = $$('lst_carta_UnidadPeso').getValue() - if(!value){ - msg = 'Es necesario seleccionar una Unidad de Peso' - msg_error(msg) - return false - } - } - var tipo_comprobante = $$('lst_tipo_comprobante').getValue() if(tipo_comprobante != 'T'){ if(values.id_partner == 0){ @@ -589,10 +585,99 @@ function validate_invoice(values){ var values = _get_values_comercio_exterior() } + //~ validate carta porte + var usar_cartaporte = $$('chk_cfdi_usar_cartaporte').getValue() + if(usar_cartaporte){ + var result = _get_values_carta_porte() + if(!result.ok){ + return false + } + } + return true } +function _get_values_carta_porte(){ + var ok = false + var values = new Object() + + unidad_peso = $$('lst_carta_UnidadPeso').getValue() + if(!unidad_peso){ + msg = 'Es necesario seleccionar una Unidad de Peso' + msg_error(msg) + return {ok: ok, values: values} + } + + var ubicaciones = $$('grid_ccp_ubicaciones').data.getRange() + if (ubicaciones.length < 2){ + msg = 'Se requieren al menos dos ubicaciones' + msg_error(msg) + return {ok: ok, values: values} + } + ubicaciones.forEach(function(row, index){ + delete row['id'] + delete row['delete'] + //~ delete row['IDUbicacion'] + }) + + var mercancias = $$('grid_ccp_mercancias').data.getRange() + if (mercancias.length < 1){ + msg = 'Se requieren al menos una mercancía' + msg_error(msg) + return {ok: ok, values: values} + } + mercancias.forEach(function(row, index){ + delete row['id'] + delete row['delete'] + }) + + var autotransporte = $$('grid_ccp_autotransporte').data.getRange()[0] + delete autotransporte['id'] + if(autotransporte['PermSCT'] === undefined){ + msg = 'El campo PermSCT es requerido' + msg_error(msg) + return {ok: ok, values: values} + } + + var remolques = $$('grid_ccp_remolques').data.getRange() + remolques.forEach(function(row, index){ + delete row['id'] + }) + + var seguros = $$('grid_ccp_seguros').data.getRange()[0] + delete seguros['id'] + if(seguros['AseguraRespCivil'] === undefined){ + msg = 'El campo AseguraRespCivil es requerido' + msg_error(msg) + return {ok: ok, values: values} + } + if(seguros['PolizaRespCivil'] === undefined){ + msg = 'El campo PolizaRespCivil es requerido' + msg_error(msg) + return {ok: ok, values: values} + } + + var tipos_figuras = $$('grid_ccp_tipos_figuras').data.getRange() + tipos_figuras.forEach(function(row, index){ + delete row['id'] + }) + + values['TranspInternac'] = $$('lst_cp_TranspInternac').getValue() + values['unidad_peso'] = unidad_peso + values['ubicaciones'] = ubicaciones + values['mercancias'] = mercancias + values['autotransporte'] = autotransporte + values['remolques'] = remolques + values['seguros'] = seguros + values['tiposfigura'] = tipos_figuras + + ok = true + + return {ok: ok, values: values} +} + + function update_grid_invoices(values){ if(values.new){ gi.add(values.row) @@ -797,68 +882,9 @@ function guardar_y_timbrar(values){ var usar_cartaporte = $$('chk_cfdi_usar_cartaporte').getValue() if(usar_cartaporte){ - //~ var total_distance = 0.00 - //~ var total_weight = 0.00 - var cartaporte = { - TranspInternac: $$('lst_carta_TranspInternac').getValue(), - //~ TotalDistRec: total_distance, - } - var ubicaciones = $$('grid_carta_ubicaciones').data.getRange() - ubicaciones.forEach(function(row, index){ - delete row['id'] - delete row['delete'] - //~ if(row['DistanciaRecorrida']){ - //~ total_distance += parseFloat(row['DistanciaRecorrida']) - //~ } - }) - //~ cartaporte['TotalDistRec'] = total_distance - cartaporte['ubicaciones'] = ubicaciones - - var row = $$('grid_carta_autotransporte').data.getRange()[0] - var autotransporte = { - PermSCT: row['PermSCT'], - NumPermisoSCT: row['NumPermisoSCT'], - identificacion: { - ConfigVehicular: row['ConfigVehicular'], - PlacaVM: row['PlacaVM'], - AnioModeloVM: row['AnioModeloVM'], - }, - seguros: { - AseguraRespCivil: row['AseguraRespCivil'], - PolizaRespCivil: row['PolizaRespCivil'], - }, - remolque: { - SubTipoRem: row['SubTipoRem'], - Placa: row['Placa'], - } - } - - var mercancias = $$('grid_carta_mercancias').data.getRange() - mercancias.forEach(function(row, index){ - delete row['id'] - delete row['delete'] - row['Cantidad'] = String(row['Cantidad']) - //~ row['ValorMercancia'] = String(row['ValorMercancia']) - //~ if(row['PesoEnKg']){ - //~ total_weight += parseFloat(row['PesoEnKg']) - //~ } - }) - var mercancias = { - 'PesoBrutoTotal': 0.00, - 'UnidadPeso': $$('lst_carta_UnidadPeso').getValue(), - 'NumTotalMercancias': String(mercancias.length), - mercancias: mercancias, - autotransporte: autotransporte, - } - cartaporte['mercancias'] = mercancias - - var tiposfigura = $$('grid_carta_tipos_figuras').data.getRange() - tiposfigura.forEach(function(row, index){ - delete row['id'] - }) - cartaporte['tiposfigura'] = tiposfigura - - data['cartaporte'] = cartaporte + var result = _get_values_carta_porte() + data['cartaporte'] = result.values + $$('chk_cfdi_usar_cartaporte').setValue(false) } var usar_comercioe = $$('chk_cfdi_usar_comercioe').getValue() @@ -929,6 +955,11 @@ function cmd_timbrar_click(id, e, node){ msg += 'Estas usando el complemento:
Comercio Exterior

' } + usar_carta_porte = $$('chk_cfdi_usar_cartaporte').getValue() + if(usar_carta_porte){ + msg += 'Estas usando el complemento:
Carta Porte

' + } + if(tipo_comprobante == 'T'){ msg += 'El Tipo de Comprobante es Traslado, el total será puesto a 0 (Cero), asegurate de que sea el tipo de comprobante correcto

' } @@ -1259,8 +1290,8 @@ function grid_details_before_edit_start(id){ } -function grid_carta_ubicaciones_before_edit_stop(state, editor){ - var g = $$('grid_carta_ubicaciones') +function grid_ccp_ubicaciones_before_edit_stop(state, editor){ + var g = $$('grid_ccp_ubicaciones') var row = g.getItem(editor.row) if(editor.column != 'CodigoPostal'){ @@ -2806,12 +2837,26 @@ function cmd_invoice_ask_cancel_click(){ } -function cmd_carta_add_product_click(){ - var g = $$('grid_carta_mercancias') +function cmd_ccp_agregar_ubicacion_click(){ + var g = $$('grid_ccp_ubicaciones') + g.add({delete: '-', Pais: 'MEX'}) +} + + +function cmd_ccp_add_product_click(){ + var g = $$('grid_ccp_mercancias') g.add({delete: '-'}) } +function cmd_ccp_agregar_remolque_click(){ + var g = $$('grid_ccp_remolques') + if(g.count() < 2){ + g.add({delete: '-'}) + } +} + + function _copy_from_invoice(){ var g1 = $$('grid_details') var g2 = $$('grid_carta_mercancias') @@ -2855,7 +2900,23 @@ function cmd_carta_copy_from_invoice_click(){ } -function grid_carta_mercancias_click(id, e, node){ +function grid_ccp_ubicaciones_click(id, e, node){ + if(id.column != 'delete'){ + return + } + this.remove(id.row) +} + + +function grid_ccp_mercancias_click(id, e, node){ + if(id.column != 'delete'){ + return + } + this.remove(id.row) +} + + +function grid_ccp_remolques_click(id, e, node){ if(id.column != 'delete'){ return } @@ -2876,26 +2937,17 @@ function _set_carta_porte_from_json(data){ return } - var mercancias = values['mercancias'] + $$('lst_cp_TranspInternac').setValue(values['TranspInternac']) + $$('lst_carta_UnidadPeso').setValue(values['UnidadPeso']) + var ubicaciones = values['ubicaciones'] + var mercancias = values['mercancias'] var autotransporte = values['autotransporte'] - var operador = values['operador'] + var remolques = values['remolques'] + var seguros = values['seguros'] + var figura = values['figura'] - $$('lst_carta_UnidadPeso').setValue(values['unidad_de_peso']) - var grid = $$('grid_carta_mercancias') - grid.clearAll() - mercancias.forEach(function(row, index){ - var data = new Object() - data['delete'] = '-' - data['BienesTransp'] = row.clave_sat - data['Descripcion'] = row.descripcion - data['Cantidad'] = row.cantidad - data['ClaveUnidad'] = row.clave_unidad - data['PesoEnKg'] = row.peso_en_kg - grid.add(data) - }) - - var grid = $$('grid_carta_ubicaciones') + var grid = $$('grid_ccp_ubicaciones') grid.clearAll() ubicaciones.forEach(function(row, index){ var data = new Object() @@ -2914,32 +2966,55 @@ function _set_carta_porte_from_json(data){ grid.add(data) }) - var grid = $$('grid_carta_autotransporte') + var grid = $$('grid_ccp_mercancias') + grid.clearAll() + mercancias.forEach(function(row, index){ + var data = new Object() + data['delete'] = '-' + data['BienesTransp'] = row.clave_sat + data['Descripcion'] = row.descripcion + data['Cantidad'] = row.cantidad + data['ClaveUnidad'] = row.clave_unidad + data['PesoEnKg'] = row.peso_en_kg + grid.add(data) + }) + + var grid = $$('grid_ccp_autotransporte') grid.clearAll() var data = new Object() - data['PermSCT'] = autotransporte.tipo_permiso - data['NumPermisoSCT'] = autotransporte.numero - data['ConfigVehicular'] = autotransporte.clave - data['PlacaVM'] = autotransporte.placa - data['AnioModeloVM'] = autotransporte.modelo - if('remolque' in autotransporte){ - data['SubTipoRem'] = autotransporte.remolque - data['Placa'] = autotransporte.placa_remolque - } - data['AseguraRespCivil'] = autotransporte.aseguradora - data['PolizaRespCivil'] = autotransporte.poliza + data['PermSCT'] = autotransporte.PermSCT + data['NumPermisoSCT'] = autotransporte.NumPermisoSCT + data['ConfigVehicular'] = autotransporte.ConfigVehicular + data['PesoBrutoVehicular'] = autotransporte.PesoBrutoVehicular + data['PlacaVM'] = autotransporte.PlacaVM + data['AnioModeloVM'] = autotransporte.AnioModeloVM grid.add(data) - var grid = $$('grid_carta_tipos_figuras') + var grid = $$('grid_ccp_remolques') + //~ if(remolques.length > 0){ + grid.clearAll() + remolques.forEach(function(row, index){ + var data = new Object() + data['SubTipoRem'] = row.SubTipoRem + data['Placa'] = row.Placa + grid.add(data) + }) + //~ } + + var grid = $$('grid_ccp_seguros') grid.clearAll() var data = new Object() - data['TipoFigura'] = '01' - if('tipo' in operador){ - data['TipoFigura'] = operador.tipo - } - data['RFCFigura'] = operador.rfc - data['NombreFigura'] = operador.nombre - data['NumLicencia'] = operador.licencia + data['AseguraRespCivil'] = seguros.AseguraRespCivil + data['PolizaRespCivil'] = seguros.PolizaRespCivil + grid.add(data) + + var grid = $$('grid_ccp_tipos_figuras') + grid.clearAll() + var data = new Object() + data['TipoFigura'] = figura.TipoFigura + data['RFCFigura'] = figura.RFCFigura + data['NumLicencia'] = figura.NumLicencia + data['NombreFigura'] = figura.NombreFigura grid.add(data) $$('chk_cfdi_usar_cartaporte').setValue(1) diff --git a/source/static/js/ui/admin.js b/source/static/js/ui/admin.js index 3c3f04c..43a3c17 100644 --- a/source/static/js/ui/admin.js +++ b/source/static/js/ui/admin.js @@ -604,6 +604,7 @@ var opt_templates_cfdi = [ {id: '_4.0_cn_1.2.ods', value: 'CFDI v4.0 - Nómina v1.2'}, {id: '_4.0_cp_2.0.ods', value: 'CFDI v4.0 - Pagos v2.0'}, {id: '_4.0_ccp_2.0.ods', value: 'CFDI v4.0 - Carta Porte v2.0'}, + {id: '_4.0_ccp_3.0.ods', value: 'CFDI v4.0 - Carta Porte v3.0'}, {id: '_4.0_cd_1.1.ods', value: 'CFDI v4.0 - Donativos v1.1'}, {id: '_4.0_cce_2.0.ods', value: 'CFDI v4.0 - Comercio Exterior v2.0'}, {id: '_4.0.json', value: 'CFDI v4.0 - JSON'}, diff --git a/source/static/js/ui/invoices.js b/source/static/js/ui/invoices.js index 790d277..78823a3 100644 --- a/source/static/js/ui/invoices.js +++ b/source/static/js/ui/invoices.js @@ -845,20 +845,66 @@ var controls_leyendas_fiscales = [ ] -var opt_transporte_internacional = [ +var opt_ccp_transporte_internacional = [ {id: 'Sí', value: 'Sí'}, {id: 'No', value: 'No'}, ] -var opt_entrada_salida = [ +var opt_ccp_regimen_aduanero = [ + {id: '', value: ''}, + {id: 'IMD', value: '[IMD] Definitivo de importación.'}, + {id: 'EXD', value: '[EXD] Definitivo de exportación.'}, + {id: 'ITR', value: '[ITR] Temporales de importación para retomar al extranjero en el mismo estado.'}, + {id: 'ITE', value: '[ITE] Temporales de importación para elaboración, transformación o reparación para empresas con programa IMMEX.'}, + {id: 'ETR', value: '[ETR] Temporales de exportación para retornar al país en el mismo estado.'}, + {id: 'ETE', value: '[ETE] Temporales de exportación para elaboración, transformación o reparación.'}, + {id: 'DFI', value: '[DFI] Depósito Fiscal.'}, + {id: 'RFE', value: '[RFE] Elaboración, transformación o reparación en recinto fiscalizado.'}, + {id: 'RFS', value: '[RFS] Recinto fiscalizado estratégico.'}, + {id: 'TRA', value: '[TRA] Tránsitos.'}, +] + + +var opt_ccp_entrada_salida = [ {id: '', value: ''}, {id: 'Entrada', value: 'Entrada'}, {id: 'Salida', value: 'Salida'}, ] -var opt_origen_destino = [ +var opt_ccp_pais_origen = [ + {id: '', value: ''}, +] + + +var opt_ccp_via_entrada = [ + {id: '', value: ''}, + {id: '01', value: '[01] Autotransporte'}, + {id: '02', value: '[02] Marítimo'}, + {id: '03', value: '[03] Aéreo'}, + {id: '04', value: '[04] Ferroviario'}, +] + + +var opt_ccp_ubicacion_polo = [ + {id: '', value: ''}, + {id: '01', value: '[01] Coatzacoalcos I'}, + {id: '02', value: '[02] Coatzacoalcos II'}, + {id: '03', value: '[03] Texistepec'}, + {id: '04', value: '[04] San Juan Evangelista'}, + {id: '05', value: '[05] Salina Cruz'}, + {id: '06', value: '[06] San Blas Atempa'}, +] + + +var opt_ccp_registro_istmo = [ + {id: '', value: ''}, + {id: 'Si', value: 'Sí'}, +] + + +var opt_ccp_origen_destino = [ {id: 'Origen', value: 'Origen'}, {id: 'Destino', value: 'Destino'}, ] @@ -873,12 +919,12 @@ var date_suggest = { } -var opt_countries = [ +var opt_ccp_countries = [ {id: 'MEX', value: 'México'}, ] -var opt_carta_estados = [ +var opt_ccp_carta_estados = [ {id: 'AGU', value: 'Aguascalientes'}, {id: 'BCN', value: 'Baja California'}, {id: 'BCS', value: 'Baja California Sur'}, @@ -915,18 +961,25 @@ var opt_carta_estados = [ ] -var grid_cols_carta_ubicaciones = [ +var grid_cols_ccp_ubicaciones = [ {id: 'id', header: 'ID', hidden: true}, - {id: 'delete', header: '', hidden: true, width: 30, css: 'delete'}, - {id: 'TipoUbicacion', header: 'Tipo de Ubicación', editor: 'select', options: opt_origen_destino, fillspace: 1}, + {id: 'delete', header: '', width: 30, css: 'delete'}, + {id: 'TipoUbicacion', header: 'TipoUbicacion', editor: 'select', options: opt_ccp_origen_destino, fillspace: 1}, + //~ {id: 'IDUbicacion', header: 'IDUbicacion', hidden: true, editor: 'text', fillspace: 1}, {id: 'RFCRemitenteDestinatario', header: 'RFC Rem/Des', editor: 'text', fillspace: 1}, {id: 'NombreRemitenteDestinatario', header: 'Nombre Rem/Des', editor: 'text', fillspace: 1}, + //~ {id: 'NumRegIdTrib', header: 'NumRegIdTrib', hidden: true, editor: 'text', fillspace: 1}, + //~ {id: 'ResidenciaFiscal', header: 'ResidenciaFiscal', hidden: true, editor: 'text', fillspace: 1}, + //~ {id: 'NumEstacion', header: 'NumEstacion', hidden: true, editor: 'text', fillspace: 1}, + //~ {id: 'NombreEstacion', header: 'NombreEstacion', hidden: true, editor: 'text', fillspace: 1}, + //~ {id: 'NavegacionTrafico', header: 'NavegacionTrafico', hidden: true, editor: 'text', fillspace: 1}, {id: 'FechaHoraSalidaLlegada', header: 'Fecha/Hora', editor: 'date', suggest: date_suggest, format: webix.Date.dateToStr("%D, %d-%M-%Y %h:%i"), footer: 'Total distancia:', fillspace: 1}, + //~ {id: 'TipoEstacion', header: 'TipoEstacion', hidden: true, editor: 'text', fillspace: 1}, {id: 'DistanciaRecorrida', header: 'Distancia (KM)', editor: 'text', format: webix.i18n.numberFormat, css: 'right', footer: {content: 'summColumn', css: 'right'}, fillspace: 1}, - {id: 'Municipio', headerd: 'Municipio', editor: 'text', fillspace: 1}, - {id: 'Estado', headerd: 'Estado', editor: 'select', options: opt_carta_estados, fillspace: 1}, - {id: 'Pais', headerd: 'Pais', editor: 'select', options: opt_countries, fillspace: 1}, - {id: 'CodigoPostal', headerd: 'C.P.', editor: 'text', fillspace: 1}, + {id: 'Municipio', header: 'Municipio', editor: 'text', fillspace: 1}, + {id: 'Estado', header: 'Estado', editor: 'select', options: opt_ccp_carta_estados, fillspace: 1}, + {id: 'Pais', header: 'País', editor: 'select', options: opt_ccp_countries, fillspace: 1}, + {id: 'CodigoPostal', header: 'C.P.', editor: 'text', fillspace: 1}, ] //~ Calle //~ NumeroExterior @@ -936,19 +989,29 @@ var grid_cols_carta_ubicaciones = [ //~ Referencia -var grid_cols_carta_mercancias = [ +var grid_cols_ccp_mercancias = [ {id: 'id', header: 'ID', hidden: true}, {id: 'delete', header: '', width: 30, css: 'delete'}, {id: 'BienesTransp', header: 'Clave SAT', editor: 'text', fillspace: 1}, + //~ {id: 'ClaveSTCC', header: 'ClaveSTCC', editor: 'text', fillspace: 1}, {id: 'Descripcion', header: 'Descripción', editor: 'text', fillspace: 1}, {id: 'Cantidad', header: 'Cantidad', editor: 'text', format: webix.i18n.numberFormat, css: 'right', fillspace: 1}, {id: 'ClaveUnidad', header: 'Unidad', editor: 'select', options: 'values/unitbykey', footer: 'Total peso:', fillspace: 1}, - //~ {id: 'ValorMercancia', header: 'Valor Mercancia', format: webix.i18n.priceFormat, css: 'right', footer: 'Total peso:', fillspace: 1}, + //~ {id: 'Unidad', header: 'Unidad', editor: 'text', fillspace: 1}, + //~ {id: 'Dimensiones', header: 'Dimensiones', editor: 'text', fillspace: 1}, + //~ {id: 'MaterialPeligroso', header: 'MaterialPeligroso', editor: 'text', fillspace: 1}, + //~ {id: 'CveMaterialPeligroso', header: 'CveMaterialPeligroso', editor: 'text', fillspace: 1}, + //~ {id: 'Embalaje', header: 'Embalaje', editor: 'text', fillspace: 1}, + //~ {id: 'DescripEmbalaje', header: 'DescripEmbalaje', editor: 'text', fillspace: 1}, + //~ {id: 'SectorCOFEPRIS', header: 'SectorCOFEPRIS', editor: 'text', fillspace: 1}, {id: 'PesoEnKg', header: 'Peso (Kg)', format: webix.i18n.numberFormat, css: 'right', editor: 'text', footer: {content: 'summColumn', css: 'right'}, fillspace: 1}, + //~ {id: 'ValorMercancia', header: 'Valor Mercancia', format: webix.i18n.priceFormat, css: 'right', footer: 'Total peso:', fillspace: 1}, + //~ {id: 'Moneda', header: 'Moneda', editor: 'text', fillspace: 1}, + //~ {id: 'FraccionArancelaria', header: 'FraccionArancelaria', editor: 'text', fillspace: 1}, ] -var opt_carta_tipo_permiso_sct = [ +var opt_ccp_tipo_permiso_sct = [ {id: 'TPAF01', value: '[TPAF01] Autotransporte Federal de carga general.'}, {id: 'TPAF02', value: '[TPAF02] Transporte privado de carga.'}, {id: 'TPAF03', value: '[TPAF03] Autotransporte Federal de Carga Especializada de materiales y residuos peligrosos.'}, @@ -978,7 +1041,7 @@ var opt_carta_tipo_permiso_sct = [ ] -var opt_config_auto = [ +var opt_ccp_config_auto = [ {id: '', value: ''}, {id: 'VL', value: '[VL] Vehículo ligero de carga (2 llantas en el eje delantero y 2 llantas en el eje trasero)'}, {id: 'C2', value: '[C2] Camión Unitario (2 llantas en el eje delantero y 4 llantas en el eje trasero)'}, @@ -1017,7 +1080,7 @@ var opt_config_auto = [ ] -var opt_carta_tipo_remolque = [ +var opt_ccp_tipo_remolque = [ {id: '', value: ''}, {id: 'CTR001', value: '[CTR001] Caballete'}, {id: 'CTR002', value: '[CTR002] Caja'}, @@ -1053,27 +1116,42 @@ var opt_carta_tipo_remolque = [ ] -var opt_carta_aseguradoras = [ - {id: 'General de Seguros', value: 'General de Seguros'}, - {id: 'Qualitas', value: 'Qualitas'}, -] +//~ var opt_carta_aseguradoras = [ + //~ {id: 'General de Seguros', value: 'General de Seguros'}, + //~ {id: 'Qualitas', value: 'Qualitas'}, +//~ ] -var grid_cols_carta_autotransporte = [ +var grid_cols_ccp_autotransporte = [ {id: 'id', header: 'ID', hidden: true}, - {id: 'PermSCT', header: 'Tipo Permiso SCT', editor: 'select', options: opt_carta_tipo_permiso_sct, fillspace: 1}, - {id: 'NumPermisoSCT', header: 'Número Permiso SCT', editor: 'text', fillspace: 1}, - {id: 'ConfigVehicular', header: 'Clave Autotransporte', editor: 'select', options: opt_config_auto, fillspace: 1}, + {id: 'PermSCT', header: 'PermSCT', editor: 'select', options: opt_ccp_tipo_permiso_sct, fillspace: 1}, + {id: 'NumPermisoSCT', header: 'NumPermisoSCT', editor: 'text', fillspace: 1}, + {id: 'ConfigVehicular', header: 'ConfigVehicular', editor: 'select', options: opt_ccp_config_auto, fillspace: 1}, + {id: 'PesoBrutoVehicular', header: 'PesoBrutoVehicular', editor: 'text', format: webix.i18n.numberFormat, css: 'right', fillspace: 1}, {id: 'PlacaVM', header: 'Placa', editor: 'text', fillspace: 1}, {id: 'AnioModeloVM', header: 'Modelo (Año)', editor: 'text', fillspace: 1}, - {id: 'SubTipoRem', header: 'ST Remolque', editor: 'select', options: opt_carta_tipo_remolque, fillspace: 1}, + //~ {id: 'SubTipoRem', header: 'ST Remolque', editor: 'select', options: opt_ccp_tipo_remolque, fillspace: 1}, + //~ {id: 'Placa', header: 'Placa', editor: 'text', fillspace: 1}, +] +var grid_cols_ccp_remolques = [ + {id: 'id', header: 'ID', hidden: true}, + {id: 'delete', header: '', width: 30, css: 'delete'}, + {id: 'SubTipoRem', header: 'SubTipo Remolque', editor: 'select', options: opt_ccp_tipo_remolque, fillspace: 1}, {id: 'Placa', header: 'Placa', editor: 'text', fillspace: 1}, +] +var grid_cols_ccp_seguros = [ + {id: 'id', header: 'ID', hidden: true}, {id: 'AseguraRespCivil', header: 'Aseguradora', editor: 'text', fillspace: 1}, {id: 'PolizaRespCivil', header: 'Póliza', editor: 'text', fillspace: 1}, + //~ {id: 'AseguraMedAmbiente', header: 'AseguraMedAmbiente', editor: 'text', fillspace: 1}, + //~ {id: 'PolizaMedAmbiente', header: 'PolizaMedAmbiente', editor: 'text', fillspace: 1}, + //~ {id: 'AseguraCarga', header: 'AseguraCarga', editor: 'text', fillspace: 1}, + //~ {id: 'PolizaCarga', header: 'PolizaCarga', editor: 'text', fillspace: 1}, + //~ {id: 'PrimaSeguro', header: 'PrimaSeguro', editor: 'text', format: webix.i18n.numberFormat, css: 'right', fillspace: 1}, ] -var opt_tipos_figura = [ +var opt_ccp_tipos_figura = [ {id: '', value: ''}, {id: '01', value: '[01] Operador'}, {id: '02', value: '[02] Propietario'}, @@ -1082,101 +1160,167 @@ var opt_tipos_figura = [ ] -var grid_cols_carta_tipos_figuras = [ +var grid_cols_ccp_tipos_figuras = [ {id: 'id', header: 'ID', hidden: true}, - {id: 'TipoFigura', header: 'Tipo Figura', editor: 'select', options: opt_tipos_figura, fillspace: 1}, - {id: 'RFCFigura', header: 'RFC Figura', editor: 'text', fillspace: 1}, - {id: 'NombreFigura', header: 'Nombre Figura', editor: 'text', fillspace: 1}, - {id: 'NumLicencia', header: 'Número de Licencia', editor: 'text', fillspace: 1}, + {id: 'TipoFigura', header: 'TipoFigura', editor: 'select', options: opt_ccp_tipos_figura, fillspace: 1}, + {id: 'RFCFigura', header: 'RFCFigura', editor: 'text', fillspace: 1}, + {id: 'NumLicencia', header: 'NumLicencia', editor: 'text', fillspace: 1}, + {id: 'NombreFigura', header: 'NombreFigura', editor: 'text', fillspace: 1}, + //~ {id: 'NumRegIdTribFigura', header: 'NumRegIdTribFigura', editor: 'text', fillspace: 1}, + //~ {id: 'ResidenciaFiscalFigura', header: 'ResidenciaFiscalFigura', editor: 'text', fillspace: 1}, + //~ {id: 'Municipio', header: 'Municipio', editor: 'text', fillspace: 1}, + //~ {id: 'Estado', header: 'Estado', editor: 'select', options: opt_ccp_carta_estados, fillspace: 1}, + //~ {id: 'Pais', header: 'País', editor: 'select', options: opt_ccp_countries, fillspace: 1}, + //~ {id: 'CodigoPostal', header: 'C.P.', editor: 'text', fillspace: 1}, ] -var grid_carta_ubicaciones = { +var grid_ccp_ubicaciones = { view: 'datatable', - id: 'grid_carta_ubicaciones', + id: 'grid_ccp_ubicaciones', multiselect: false, adjust: true, autoheight: true, headermenu: true, editable: true, footer: true, - columns: grid_cols_carta_ubicaciones, - //~ data: data_tmp1, - data: [ - {delete: '-', TipoUbicacion: 'Origen', Pais: 'MEX'}, - {delete: '-', TipoUbicacion: 'Destino', Pais: 'MEX'}, - ] + columns: grid_cols_ccp_ubicaciones, } -var grid_carta_mercancias = { +var grid_ccp_mercancias = { view: 'datatable', - id: 'grid_carta_mercancias', + id: 'grid_ccp_mercancias', multiselect: false, adjust: true, autoheight: true, headermenu: true, editable: true, footer: true, - columns: grid_cols_carta_mercancias, + columns: grid_cols_ccp_mercancias, } -var grid_carta_autotransporte = { +var grid_ccp_autotransporte = { view: 'datatable', - id: 'grid_carta_autotransporte', + id: 'grid_ccp_autotransporte', multiselect: false, adjust: true, autoheight: true, headermenu: true, editable: true, - columns: grid_cols_carta_autotransporte, + columns: grid_cols_ccp_autotransporte, data: [{id: 0}], - //~ data: data_tmp2, } - - -var grid_carta_tipos_figuras = { +var grid_ccp_remolques = { view: 'datatable', - id: 'grid_carta_tipos_figuras', + id: 'grid_ccp_remolques', multiselect: false, adjust: true, autoheight: true, headermenu: true, editable: true, - columns: grid_cols_carta_tipos_figuras, + columns: grid_cols_ccp_remolques, +} +var grid_ccp_seguros = { + view: 'datatable', + id: 'grid_ccp_seguros', + multiselect: false, + adjust: true, + autoheight: true, + headermenu: true, + editable: true, + columns: grid_cols_ccp_seguros, data: [{id: 0}], - //~ data: data_tmp3, } -var body_carta_mercancias = {rows:[ +var grid_ccp_tipos_figuras = { + view: 'datatable', + id: 'grid_ccp_tipos_figuras', + multiselect: false, + adjust: true, + autoheight: true, + headermenu: true, + editable: true, + columns: grid_cols_ccp_tipos_figuras, + data: [{id: 0}], +} + + +var body_ccp_ubicaciones = {rows:[ {cols: [ - {view: 'button', id: 'cmd_carta_add_product', label: 'Agregar Mercancía', icon: 'plus', + {view: 'button', id: 'cmd_ccp_agregar_ubicacion', label: 'Agregar Ubicación', icon: 'plus', type: 'iconButton', autowidth: true, align: 'center'}, - {view: 'button', id: 'cmd_carta_copy_from_invoice', label: 'Copiar de CFDI', icon: 'copy', + {}]}, + {maxHeight: 10}, + grid_ccp_ubicaciones, +]} + + +var body_ccp_mercancias = {rows:[ + {cols: [ + {view: 'button', id: 'cmd_ccp_add_product', label: 'Agregar Mercancía', icon: 'plus', type: 'iconButton', autowidth: true, align: 'center'}, + //~ {view: 'button', id: 'cmd_carta_copy_from_invoice', label: 'Copiar de CFDI', icon: 'copy', + //~ type: 'iconButton', autowidth: true, align: 'center'}, {}, {view: 'richselect', id: 'lst_carta_UnidadPeso', label: 'Unidad de Peso: ', labelWidth: 110, maxWidth: 300, options: '/satunidadespeso?opt=active'} ]}, {maxHeight: 10}, - grid_carta_mercancias, + grid_ccp_mercancias, ]} -var body_carta_ubicaciones = {rows:[ - grid_carta_ubicaciones, +var body_ccp_autotransporte = {rows:[ + grid_ccp_autotransporte, + {minHeight: 10}, + {cols: [ + {view: 'button', id: 'cmd_ccp_agregar_remolque', label: 'Agregar Remolque', icon: 'plus', + type: 'iconButton', autowidth: true, align: 'center'}, + {}]}, + {minHeight: 10}, + grid_ccp_remolques, + {minHeight: 10}, + grid_ccp_seguros, ]} -var body_carta_autotransporte = {rows:[ - grid_carta_autotransporte, +var body_ccp_tipos_figuras = {rows:[ + grid_ccp_tipos_figuras, ]} -var body_carta_tipos_figuras = {rows:[ - grid_carta_tipos_figuras, +var body_cp_datos_generales = {rows:[ + {cols: [{maxWidth: 15}, + {view: 'richselect', id: 'lst_cp_TranspInternac', labelPosition: 'top', + label: 'TranspInternac', options: opt_ccp_transporte_internacional, + value: 'No', readonly: true}, + {view: 'richselect', id: 'lst_cp_RegimenAduanero', labelPosition: 'top', + label: 'RegimenAduanero', options: opt_ccp_regimen_aduanero, + value: '', disabled: true}, + {view: 'richselect', id: 'lst_cp_EntradaSalidaMerc', labelPosition: 'top', + label: 'EntradaSalidaMerc', options: opt_ccp_entrada_salida, + value: '', disabled: true}, + {view: 'richselect', id: 'lst_cp_PaisOrigenDestino', labelPosition: 'top', + label: 'PaisOrigenDestino', options: opt_ccp_pais_origen, + value: '', disabled: true}, + {view: 'richselect', id: 'lst_cp_ViaEntradaSalida', labelPosition: 'top', + label: 'ViaEntradaSalida', options: opt_ccp_via_entrada, + value: '', disabled: true}, + ]}, + {cols: [{maxWidth: 15}, + {view: 'richselect', id: 'lst_cp_RegistroISTMO', labelPosition: 'top', + label: 'RegistroISTMO', options: opt_ccp_registro_istmo, + value: '', readonly: false}, + {view: 'richselect', id: 'lst_cp_UbicacionPoloOrigen', labelPosition: 'top', + label: 'UbicacionPoloOrigen', options: opt_ccp_ubicacion_polo, + value: '', disabled: true}, + {view: 'richselect', id: 'lst_cp_UbicacionPoloDestino', labelPosition: 'top', + label: 'UbicacionPoloDestino', options: opt_ccp_ubicacion_polo, + value: '', disabled: true}, + {}]}, ]} @@ -1189,24 +1333,11 @@ var controls_carta_porte = [ {view: 'button', id: 'cmd_carta_import_ods', label: 'Importar ODS', icon: 'upload', type: 'iconButton', autowidth: true, align: 'center'}, {maxWidth: 15}]}, - {view: 'fieldset', label: 'Mercancias', body: body_carta_mercancias}, - {cols: [{maxWidth: 15}, - {view: 'richselect', id: 'lst_carta_TranspInternac', labelPosition: 'top', - label: 'Transporte Internacional', options: opt_transporte_internacional, - value: 'No', readonly: true}, - {view: 'richselect', id: 'lst_carta_EntradaSalidaMerc', labelPosition: 'top', - label: 'Entrada o Salida', options: opt_entrada_salida, - value: '', disabled: true}, - {view: 'richselect', id: 'lst_carta_PaisOrigenDestino', labelPosition: 'top', - label: 'País Origen/Destino', options: [], - value: '', disabled: true}, - {view: 'richselect', id: 'lst_carta_ViaEntradaSalida', labelPosition: 'top', - label: 'Vía de Entrada o Salida', options: [], - value: '', disabled: true}, - ]}, - {view: 'fieldset', label: 'Ubicaciones', body: body_carta_ubicaciones}, - {view: 'fieldset', label: 'Autotransporte', body: body_carta_autotransporte}, - {view: 'fieldset', label: 'Tipos Figura', body: body_carta_tipos_figuras}, + {view: 'fieldset', label: 'Datos generales', body: body_cp_datos_generales}, + {view: 'fieldset', label: 'Ubicaciones', body: body_ccp_ubicaciones}, + {view: 'fieldset', label: 'Mercancias', body: body_ccp_mercancias}, + {view: 'fieldset', label: 'Autotransporte', body: body_ccp_autotransporte}, + {view: 'fieldset', label: 'Tipos Figura', body: body_ccp_tipos_figuras}, ] diff --git a/source/templates/plantilla_ccp.ods b/source/templates/plantilla_ccp.ods new file mode 100644 index 0000000..2339002 Binary files /dev/null and b/source/templates/plantilla_ccp.ods differ diff --git a/source/xslt/cadena.xslt b/source/xslt/cadena.xslt index 218d9d2..119e79d 100644 --- a/source/xslt/cadena.xslt +++ b/source/xslt/cadena.xslt @@ -10,7 +10,7 @@ - + diff --git a/source/xslt/cartaporte30.xslt b/source/xslt/cartaporte30.xslt new file mode 100644 index 0000000..d5fe39b --- /dev/null +++ b/source/xslt/cartaporte30.xslt @@ -0,0 +1,744 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +