lab_formularios
This commit is contained in:
@@ -17,11 +17,15 @@ try {
|
|||||||
if (!empty($_GET['paciente_id'])) $filtros['paciente_id'] = (int)$_GET['paciente_id'];
|
if (!empty($_GET['paciente_id'])) $filtros['paciente_id'] = (int)$_GET['paciente_id'];
|
||||||
if (!empty($_GET['estado'])) $filtros['estado'] = $_GET['estado'];
|
if (!empty($_GET['estado'])) $filtros['estado'] = $_GET['estado'];
|
||||||
if (!empty($_GET['fecha_desde'])) $filtros['fecha_desde'] = $_GET['fecha_desde'];
|
if (!empty($_GET['fecha_desde'])) $filtros['fecha_desde'] = $_GET['fecha_desde'];
|
||||||
|
if (!empty($_GET['fecha_hasta'])) $filtros['fecha_hasta'] = $_GET['fecha_hasta'];
|
||||||
|
if (!empty($_GET['paciente'])) $filtros['paciente'] = trim($_GET['paciente']);
|
||||||
// Enfermero solo ve los suyos
|
// Enfermero solo ve los suyos
|
||||||
if (userRole() === 'enfermero') {
|
if (userRole() === 'enfermero') {
|
||||||
$filtros['enviado_por'] = adminId();
|
$filtros['enviado_por'] = adminId();
|
||||||
}
|
}
|
||||||
jsonOk(['data' => $form->listarEnvios($filtros)]);
|
$pagina = max(1, (int)($_GET['page'] ?? 1));
|
||||||
|
$porPagina = !empty($_GET['export']) ? 9999 : max(1, min(100, (int)($_GET['limit'] ?? 20)));
|
||||||
|
jsonOk($form->listarEnvios($filtros, $pagina, $porPagina));
|
||||||
}
|
}
|
||||||
|
|
||||||
// Plantilla específica
|
// Plantilla específica
|
||||||
|
|||||||
@@ -173,7 +173,7 @@ class Formulario {
|
|||||||
/**
|
/**
|
||||||
* Listar envíos (admin/enfermero).
|
* Listar envíos (admin/enfermero).
|
||||||
*/
|
*/
|
||||||
public function listarEnvios(array $filtros = []): array {
|
public function listarEnvios(array $filtros = [], int $pagina = 1, int $porPagina = 20): array {
|
||||||
$where = ['1=1'];
|
$where = ['1=1'];
|
||||||
$params = [];
|
$params = [];
|
||||||
if (!empty($filtros['formulario_id'])) { $where[] = 'e.formulario_id = ?'; $params[] = $filtros['formulario_id']; }
|
if (!empty($filtros['formulario_id'])) { $where[] = 'e.formulario_id = ?'; $params[] = $filtros['formulario_id']; }
|
||||||
@@ -181,8 +181,22 @@ class Formulario {
|
|||||||
if (!empty($filtros['enviado_por'])) { $where[] = 'e.enviado_por = ?'; $params[] = $filtros['enviado_por']; }
|
if (!empty($filtros['enviado_por'])) { $where[] = 'e.enviado_por = ?'; $params[] = $filtros['enviado_por']; }
|
||||||
if (!empty($filtros['estado'])) { $where[] = 'e.estado = ?'; $params[] = $filtros['estado']; }
|
if (!empty($filtros['estado'])) { $where[] = 'e.estado = ?'; $params[] = $filtros['estado']; }
|
||||||
if (!empty($filtros['fecha_desde'])) { $where[] = 'DATE(e.created_at) >= ?'; $params[] = $filtros['fecha_desde']; }
|
if (!empty($filtros['fecha_desde'])) { $where[] = 'DATE(e.created_at) >= ?'; $params[] = $filtros['fecha_desde']; }
|
||||||
$w = implode(' AND ', $where);
|
if (!empty($filtros['fecha_hasta'])) { $where[] = 'DATE(e.created_at) <= ?'; $params[] = $filtros['fecha_hasta']; }
|
||||||
return $this->db->fetchAll("
|
if (!empty($filtros['paciente'])) { $where[] = 'p.nombre_completo LIKE ?'; $params[] = '%' . $filtros['paciente'] . '%'; }
|
||||||
|
$w = implode(' AND ', $where);
|
||||||
|
$offset = ($pagina - 1) * $porPagina;
|
||||||
|
|
||||||
|
$total = $this->db->fetch(
|
||||||
|
"SELECT COUNT(*) AS n
|
||||||
|
FROM lab_form_envios e
|
||||||
|
JOIN lab_formularios f ON f.id = e.formulario_id
|
||||||
|
LEFT JOIN lab_pacientes p ON p.id = e.paciente_id
|
||||||
|
LEFT JOIN admin_users u ON u.id = e.enviado_por
|
||||||
|
WHERE $w",
|
||||||
|
$params
|
||||||
|
)['n'] ?? 0;
|
||||||
|
|
||||||
|
$rows = $this->db->fetchAll("
|
||||||
SELECT e.*, f.nombre AS form_nombre, f.categoria, f.esquema,
|
SELECT e.*, f.nombre AS form_nombre, f.categoria, f.esquema,
|
||||||
p.nombre_completo AS paciente_nombre,
|
p.nombre_completo AS paciente_nombre,
|
||||||
u.full_name AS enviado_por_nombre
|
u.full_name AS enviado_por_nombre
|
||||||
@@ -192,8 +206,16 @@ class Formulario {
|
|||||||
LEFT JOIN admin_users u ON u.id = e.enviado_por
|
LEFT JOIN admin_users u ON u.id = e.enviado_por
|
||||||
WHERE $w
|
WHERE $w
|
||||||
ORDER BY e.created_at DESC
|
ORDER BY e.created_at DESC
|
||||||
LIMIT 200
|
LIMIT ? OFFSET ?
|
||||||
", $params);
|
", array_merge($params, [$porPagina, $offset]));
|
||||||
|
|
||||||
|
return [
|
||||||
|
'data' => $rows,
|
||||||
|
'total' => (int)$total,
|
||||||
|
'pagina' => $pagina,
|
||||||
|
'por_pagina' => $porPagina,
|
||||||
|
'paginas' => (int)ceil($total / max(1, $porPagina)),
|
||||||
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
// ─────────────────────────────────────────────────────────────────────────
|
// ─────────────────────────────────────────────────────────────────────────
|
||||||
|
|||||||
+115
-178
@@ -29,6 +29,10 @@ $puedeEscribir = $esAdmin && hasModuleWrite('lab_formularios');
|
|||||||
transition:box-shadow .2s; }
|
transition:box-shadow .2s; }
|
||||||
.form-card:hover { box-shadow:0 3px 12px rgba(0,0,0,.1); }
|
.form-card:hover { box-shadow:0 3px 12px rgba(0,0,0,.1); }
|
||||||
|
|
||||||
|
/* ── Altura uniforme filtros ─────────────────────── */
|
||||||
|
#panel-envios .form-control-sm,
|
||||||
|
#panel-envios .form-select-sm { height:31px; padding-top:.25rem; padding-bottom:.25rem; }
|
||||||
|
|
||||||
/* ── Colores estado envío ───────────────────────── */
|
/* ── Colores estado envío ───────────────────────── */
|
||||||
.badge-pendiente { background:#6c757d; }
|
.badge-pendiente { background:#6c757d; }
|
||||||
.badge-completado { background:#0d6efd; }
|
.badge-completado { background:#0d6efd; }
|
||||||
@@ -401,7 +405,7 @@ const tabs = {
|
|||||||
document.querySelectorAll('#formTabs .nav-link').forEach((a,i) =>
|
document.querySelectorAll('#formTabs .nav-link').forEach((a,i) =>
|
||||||
a.classList.toggle('active', (tab==='lista') === (i===0))
|
a.classList.toggle('active', (tab==='lista') === (i===0))
|
||||||
);
|
);
|
||||||
if (tab === 'envios') envios.cargar();
|
if (tab === 'envios') { envios.poblarSelectFormulario(); envios.cargar(1); }
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -508,182 +512,130 @@ const ESTADO_ENV = {
|
|||||||
firmado: { cls:'badge-firmado', icon:'✍️' },
|
firmado: { cls:'badge-firmado', icon:'✍️' },
|
||||||
expirado: { cls:'badge-expirado', icon:'⏰' },
|
expirado: { cls:'badge-expirado', icon:'⏰' },
|
||||||
};
|
};
|
||||||
const POR_PAGINA = 15;
|
const POR_PAGINA = 20;
|
||||||
const envios = {
|
const envios = {
|
||||||
_data: [],
|
_pagina: 1,
|
||||||
_filtrado: [],
|
_total: 0,
|
||||||
_pagina: 1,
|
_paginas: 1,
|
||||||
|
_paginaData: [],
|
||||||
|
_debTimer: null,
|
||||||
|
|
||||||
async cargar() {
|
_params() {
|
||||||
// Mostrar spinner, ocultar tabla
|
return new URLSearchParams({
|
||||||
|
envios: 1,
|
||||||
|
page: this._pagina,
|
||||||
|
limit: POR_PAGINA,
|
||||||
|
fecha_desde: $('env-f-desde').value || '',
|
||||||
|
fecha_hasta: $('env-f-hasta').value || '',
|
||||||
|
paciente: $('env-f-paciente').value.trim() || '',
|
||||||
|
formulario_id: $('env-f-formulario').value || '',
|
||||||
|
estado: $('env-f-estado').value || '',
|
||||||
|
});
|
||||||
|
},
|
||||||
|
|
||||||
|
async cargar(pag = 1) {
|
||||||
|
this._pagina = pag;
|
||||||
const spinner = $('env-spinner');
|
const spinner = $('env-spinner');
|
||||||
const tabla = $('env-tabla-wrap');
|
const wrap = $('env-tabla-wrap');
|
||||||
if (spinner) spinner.style.display = '';
|
if (spinner) spinner.style.display = '';
|
||||||
if (tabla) tabla.style.display = 'none';
|
if (wrap) wrap.style.display = 'none';
|
||||||
|
try {
|
||||||
const r = await fetch('api/lab/get_formularios.php?envios=1');
|
const r = await fetch('api/lab/get_formularios.php?' + this._params());
|
||||||
const d = await r.json();
|
const d = await r.json();
|
||||||
this._data = d.data || [];
|
this._paginaData = d.data || [];
|
||||||
this._pagina = 1;
|
this._total = d.total || 0;
|
||||||
this._poblarSelectFormulario();
|
this._paginas = d.paginas || 1;
|
||||||
this._aplicarFiltros();
|
this._render();
|
||||||
|
} catch(e) {
|
||||||
if (spinner) spinner.style.display = 'none';
|
const tb = $('tbody-envios');
|
||||||
if (tabla) tabla.style.display = '';
|
if (tb) tb.innerHTML = '<tr><td colspan="6" class="text-center text-danger py-4">Error al cargar envíos</td></tr>';
|
||||||
|
} finally {
|
||||||
|
if (spinner) spinner.style.display = 'none';
|
||||||
|
if (wrap) wrap.style.display = '';
|
||||||
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
filtrar() {
|
filtrar() {
|
||||||
this._pagina = 1;
|
clearTimeout(this._debTimer);
|
||||||
this._aplicarFiltros();
|
this._debTimer = setTimeout(() => this.cargar(1), 350);
|
||||||
},
|
},
|
||||||
|
|
||||||
limpiarFiltros() {
|
limpiarFiltros() {
|
||||||
$('env-f-desde').value = '';
|
$('env-f-desde').value = '';
|
||||||
$('env-f-hasta').value = '';
|
$('env-f-hasta').value = '';
|
||||||
$('env-f-paciente').value = '';
|
$('env-f-paciente').value = '';
|
||||||
$('env-f-formulario').value = '';
|
$('env-f-formulario').value = '';
|
||||||
$('env-f-estado').value = '';
|
$('env-f-estado').value = '';
|
||||||
this.filtrar();
|
this.cargar(1);
|
||||||
},
|
},
|
||||||
|
|
||||||
_poblarSelectFormulario() {
|
poblarSelectFormulario() {
|
||||||
const sel = $('env-f-formulario');
|
const sel = $('env-f-formulario');
|
||||||
if (!sel) return;
|
if (!sel || sel.options.length > 1) return;
|
||||||
const valorActual = sel.value;
|
(_formularios || []).forEach(f => {
|
||||||
sel.innerHTML = '<option value="">Todos los formularios</option>';
|
const opt = document.createElement('option');
|
||||||
const vistos = new Set();
|
opt.value = f.id;
|
||||||
this._data.forEach(e => {
|
opt.textContent = f.nombre || ('Formulario #' + f.id);
|
||||||
if (e.formulario_id && !vistos.has(e.formulario_id)) {
|
sel.appendChild(opt);
|
||||||
vistos.add(e.formulario_id);
|
|
||||||
const opt = document.createElement('option');
|
|
||||||
opt.value = e.formulario_id;
|
|
||||||
opt.textContent = e.form_nombre || ('Formulario #' + e.formulario_id);
|
|
||||||
sel.appendChild(opt);
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
if (valorActual) sel.value = valorActual;
|
|
||||||
},
|
},
|
||||||
|
|
||||||
_aplicarFiltros() {
|
async exportarExcel() {
|
||||||
const desde = $('env-f-desde').value;
|
const btnExcel = document.querySelector('[onclick="envios.exportarExcel()"]');
|
||||||
const hasta = $('env-f-hasta').value;
|
if (btnExcel) { btnExcel.disabled = true; btnExcel.innerHTML = '<i class="fas fa-spinner fa-spin me-1"></i>Exportando…'; }
|
||||||
const paciente = $('env-f-paciente').value.trim().toLowerCase();
|
let rows = [];
|
||||||
const formId = $('env-f-formulario').value;
|
try {
|
||||||
const estadoFilt = $('env-f-estado').value;
|
const p = this._params();
|
||||||
|
p.set('export', '1'); p.delete('page'); p.delete('limit');
|
||||||
|
const r = await fetch('api/lab/get_formularios.php?' + p);
|
||||||
|
const d = await r.json();
|
||||||
|
rows = d.data || [];
|
||||||
|
} finally {
|
||||||
|
if (btnExcel) { btnExcel.disabled = false; btnExcel.innerHTML = '<i class="fas fa-file-excel me-1"></i><span class="d-none d-md-inline">Excel</span>'; }
|
||||||
|
}
|
||||||
|
if (!rows.length) { showToast('Sin datos para exportar', 'warning'); return; }
|
||||||
|
|
||||||
this._filtrado = this._data.filter(e => {
|
|
||||||
const fecha = (e.created_at || '').slice(0, 10);
|
|
||||||
if (desde && fecha < desde) return false;
|
|
||||||
if (hasta && fecha > hasta) return false;
|
|
||||||
if (paciente && !(e.paciente_nombre || '').toLowerCase().includes(paciente)) return false;
|
|
||||||
if (formId && String(e.formulario_id) !== String(formId)) return false;
|
|
||||||
if (estadoFilt && e.estado !== estadoFilt) return false;
|
|
||||||
return true;
|
|
||||||
});
|
|
||||||
|
|
||||||
// badge de pendientes sobre el total sin filtrar
|
|
||||||
const badgePend = $('badge-envios');
|
|
||||||
const pend = this._data.filter(e => e.estado === 'pendiente').length;
|
|
||||||
if (pend) { badgePend.textContent = pend; badgePend.style.display = ''; }
|
|
||||||
else badgePend.style.display = 'none';
|
|
||||||
|
|
||||||
this._render();
|
|
||||||
},
|
|
||||||
|
|
||||||
exportarExcel() {
|
|
||||||
const rows = this._filtrado;
|
|
||||||
if (!rows.length) { showToast('Sin datos para exportar'); return; }
|
|
||||||
|
|
||||||
// Columnas fijas
|
|
||||||
const fixedCols = ['Formulario','Categoría','Paciente','Estado','Fecha envío','Fecha completado'];
|
const fixedCols = ['Formulario','Categoría','Paciente','Estado','Fecha envío','Fecha completado'];
|
||||||
|
const fieldMap = new Map();
|
||||||
// Recolectar todas las columnas dinámicas (campos del esquema) en orden de aparición
|
|
||||||
const fieldMap = new Map(); // label → id (primer visto)
|
|
||||||
rows.forEach(e => {
|
rows.forEach(e => {
|
||||||
try {
|
try { JSON.parse(e.esquema||'[]').forEach(c => {
|
||||||
const esquema = JSON.parse(e.esquema || '[]');
|
if (!['separador','firma','firma_profesional','parrafo','parrafo_inline','lista_marcable'].includes(c.tipo)
|
||||||
esquema.forEach(c => {
|
&& c.id && c.label && !fieldMap.has(c.label)) fieldMap.set(c.label, c.id);
|
||||||
if (!['separador','firma','firma_profesional','parrafo',
|
}); } catch(_) {}
|
||||||
'parrafo_inline','lista_marcable'].includes(c.tipo)
|
|
||||||
&& c.id && c.label && !fieldMap.has(c.label)) {
|
|
||||||
fieldMap.set(c.label, c.id);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
} catch(_) {}
|
|
||||||
});
|
});
|
||||||
|
const fieldCols = [...fieldMap.entries()];
|
||||||
const fieldCols = [...fieldMap.entries()]; // [[label, id], ...]
|
const csvRows = [[...fixedCols, ...fieldCols.map(([l])=>l)]];
|
||||||
const allCols = [...fixedCols, ...fieldCols.map(([l]) => l)];
|
|
||||||
|
|
||||||
const csvRows = [allCols];
|
|
||||||
|
|
||||||
rows.forEach(e => {
|
rows.forEach(e => {
|
||||||
let cliente = {}, prefill = {};
|
let cliente={}, prefill={};
|
||||||
try { cliente = JSON.parse(e.datos_cliente || '{}'); } catch(_) {}
|
try { cliente=JSON.parse(e.datos_cliente||'{}'); } catch(_) {}
|
||||||
try { prefill = JSON.parse(e.datos_prefilled || '{}'); } catch(_) {}
|
try { prefill=JSON.parse(e.datos_prefilled||'{}'); } catch(_) {}
|
||||||
const todos = { ...prefill, ...cliente };
|
const todos = {...prefill,...cliente};
|
||||||
|
const lmap = new Map();
|
||||||
// Para este envío construir mapa label → id
|
try { JSON.parse(e.esquema||'[]').forEach(c=>{if(c.id&&c.label)lmap.set(c.label,c.id);}); } catch(_) {}
|
||||||
const labelToId = new Map();
|
csvRows.push([
|
||||||
try {
|
e.form_nombre||'', e.categoria||'', e.paciente_nombre||'', e.estado||'',
|
||||||
JSON.parse(e.esquema || '[]').forEach(c => {
|
(e.created_at||'').slice(0,16).replace('T',' '), (e.completado_en||'').slice(0,16).replace('T',' '),
|
||||||
if (c.id && c.label) labelToId.set(c.label, c.id);
|
...fieldCols.map(([l,d])=>{ const v=todos[lmap.get(l)||d]; return v==null?'':(Array.isArray(v)?v.join('; '):String(v)); }),
|
||||||
});
|
]);
|
||||||
} catch(_) {}
|
|
||||||
|
|
||||||
const fixed = [
|
|
||||||
e.form_nombre || '',
|
|
||||||
e.categoria || '',
|
|
||||||
e.paciente_nombre || '',
|
|
||||||
e.estado || '',
|
|
||||||
(e.created_at || '').slice(0, 16).replace('T', ' '),
|
|
||||||
(e.completado_en || '').slice(0, 16).replace('T', ' '),
|
|
||||||
];
|
|
||||||
|
|
||||||
const campos = fieldCols.map(([label, defaultId]) => {
|
|
||||||
const id = labelToId.get(label) || defaultId;
|
|
||||||
const val = todos[id];
|
|
||||||
if (val === undefined || val === null) return '';
|
|
||||||
return Array.isArray(val) ? val.join('; ') : String(val);
|
|
||||||
});
|
|
||||||
|
|
||||||
csvRows.push([...fixed, ...campos]);
|
|
||||||
});
|
});
|
||||||
|
const csv = '\uFEFF' + csvRows.map(r=>r.map(v=>'"'+String(v).replace(/"/g,'""')+'"').join(',')).join('\r\n');
|
||||||
// Generar CSV con BOM UTF-8 para Excel
|
const blob = new Blob([csv],{type:'text/csv;charset=utf-8;'});
|
||||||
const csv = '\uFEFF' + csvRows.map(row =>
|
|
||||||
row.map(v => '"' + String(v).replace(/"/g, '""') + '"').join(',')
|
|
||||||
).join('\r\n');
|
|
||||||
|
|
||||||
const blob = new Blob([csv], { type: 'text/csv;charset=utf-8;' });
|
|
||||||
const url = URL.createObjectURL(blob);
|
const url = URL.createObjectURL(blob);
|
||||||
const a = document.createElement('a');
|
const a = Object.assign(document.createElement('a'),{href:url,download:'envios_formularios_'+new Date().toISOString().slice(0,10)+'.csv'});
|
||||||
a.href = url;
|
document.body.appendChild(a); a.click(); document.body.removeChild(a); URL.revokeObjectURL(url);
|
||||||
a.download = 'envios_formularios_' + new Date().toISOString().slice(0, 10) + '.csv';
|
|
||||||
document.body.appendChild(a);
|
|
||||||
a.click();
|
|
||||||
document.body.removeChild(a);
|
|
||||||
URL.revokeObjectURL(url);
|
|
||||||
showToast('✅ Excel descargado — ' + rows.length + ' registro(s)', 'success', 4000);
|
showToast('✅ Excel descargado — ' + rows.length + ' registro(s)', 'success', 4000);
|
||||||
},
|
},
|
||||||
|
|
||||||
_render() {
|
_render() {
|
||||||
const tb = $('tbody-envios');
|
const tb = $('tbody-envios');
|
||||||
const total = this._filtrado.length;
|
if (!this._paginaData.length) {
|
||||||
|
|
||||||
if (!total) {
|
|
||||||
tb.innerHTML = '<tr><td colspan="6" class="text-center text-muted py-4">Sin envíos para los filtros seleccionados</td></tr>';
|
tb.innerHTML = '<tr><td colspan="6" class="text-center text-muted py-4">Sin envíos para los filtros seleccionados</td></tr>';
|
||||||
$('env-pag-info').textContent = '';
|
$('env-pag-info').textContent = '';
|
||||||
$('env-paginacion').innerHTML = '';
|
$('env-paginacion').innerHTML = '';
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const totalPag = Math.ceil(total / POR_PAGINA);
|
|
||||||
if (this._pagina > totalPag) this._pagina = totalPag;
|
|
||||||
const inicio = (this._pagina - 1) * POR_PAGINA;
|
const inicio = (this._pagina - 1) * POR_PAGINA;
|
||||||
const pagina = this._filtrado.slice(inicio, inicio + POR_PAGINA);
|
tb.innerHTML = this._paginaData.map(e => {
|
||||||
|
|
||||||
tb.innerHTML = pagina.map(e => {
|
|
||||||
const info = ESTADO_ENV[e.estado] || {};
|
const info = ESTADO_ENV[e.estado] || {};
|
||||||
return `<tr>
|
return `<tr>
|
||||||
<td><span class="fw-semibold">${esc(e.form_nombre)}</span>
|
<td><span class="fw-semibold">${esc(e.form_nombre)}</span>
|
||||||
@@ -694,54 +646,39 @@ const envios = {
|
|||||||
<td><small class="text-muted">${esc((e.expira_en||'').slice(0,10))}</small></td>
|
<td><small class="text-muted">${esc((e.expira_en||'').slice(0,10))}</small></td>
|
||||||
<td>
|
<td>
|
||||||
<button class="btn btn-xs btn-outline-secondary" title="Copiar link"
|
<button class="btn btn-xs btn-outline-secondary" title="Copiar link"
|
||||||
onclick="envios.copiarTokenLink('${esc(e.token)}')">
|
onclick="envios.copiarTokenLink('${esc(e.token)}')">
|
||||||
<i class="fas fa-copy"></i>
|
<i class="fas fa-copy"></i>
|
||||||
</button>
|
</button>
|
||||||
${['completado','firmado'].includes(e.estado)
|
${['completado','firmado'].includes(e.estado)
|
||||||
? `<button class="btn btn-xs btn-outline-primary ms-1" title="Ver respuesta"
|
? `<button class="btn btn-xs btn-outline-primary ms-1" onclick="verRespuesta.abrir(${e.id})"><i class="fas fa-eye"></i></button>
|
||||||
onclick="verRespuesta.abrir(${e.id})">
|
<a class="btn btn-xs btn-outline-danger ms-1" href="ver_formulario_enviado.php?id=${e.id}" target="_blank"><i class="fas fa-file-pdf"></i></a>`
|
||||||
<i class="fas fa-eye"></i></button>
|
|
||||||
<a class="btn btn-xs btn-outline-danger ms-1" title="Descargar PDF"
|
|
||||||
href="ver_formulario_enviado.php?id=${e.id}" target="_blank">
|
|
||||||
<i class="fas fa-file-pdf"></i></a>`
|
|
||||||
: ''}
|
: ''}
|
||||||
</td>
|
</td>
|
||||||
</tr>`;
|
</tr>`;
|
||||||
}).join('');
|
}).join('');
|
||||||
|
|
||||||
// Info
|
|
||||||
$('env-pag-info').textContent =
|
$('env-pag-info').textContent =
|
||||||
`Mostrando ${inicio + 1}–${Math.min(inicio + POR_PAGINA, total)} de ${total} envíos`;
|
`Mostrando ${inicio+1}–${inicio+this._paginaData.length} de ${this._total} envío(s)`;
|
||||||
|
|
||||||
// Paginación
|
const ul = $('env-paginacion');
|
||||||
const ul = $('env-paginacion');
|
const pag = this._pagina, tot = this._paginas;
|
||||||
ul.innerHTML = '';
|
ul.innerHTML = '';
|
||||||
const agregar = (label, pag, disabled, active) => {
|
if (tot <= 1) return;
|
||||||
const li = document.createElement('li');
|
const li = (lbl, p, dis, act) => {
|
||||||
li.className = `page-item${disabled?' disabled':''}${active?' active':''}`;
|
const el = document.createElement('li');
|
||||||
li.innerHTML = `<a class="page-link" href="#" onclick="event.preventDefault();${!disabled?`envios.irAPagina(${pag})`:''}">${label}</a>`;
|
el.className = `page-item${dis?' disabled':''}${act?' active':''}`;
|
||||||
ul.appendChild(li);
|
el.innerHTML = `<a class="page-link" href="#" onclick="event.preventDefault();${!dis?`envios.cargar(${p})`:''}">${lbl}</a>`;
|
||||||
|
ul.appendChild(el);
|
||||||
};
|
};
|
||||||
agregar('«', 1, this._pagina === 1, false);
|
li('«',1,pag===1,false); li('‹',pag-1,pag===1,false);
|
||||||
agregar('‹', this._pagina-1, this._pagina === 1, false);
|
const pMin=Math.max(1,pag-2), pMax=Math.min(tot,pag+2);
|
||||||
|
if(pMin>1){li('1',1,false,false);if(pMin>2)li('…',null,true,false);}
|
||||||
// páginas con ventana deslizante ±2
|
for(let p=pMin;p<=pMax;p++) li(p,p,false,p===pag);
|
||||||
const rango = 2;
|
if(pMax<tot){if(pMax<tot-1)li('…',null,true,false);li(tot,tot,false,false);}
|
||||||
const pMin = Math.max(1, this._pagina - rango);
|
li('›',pag+1,pag===tot,false); li('»',tot,pag===tot,false);
|
||||||
const pMax = Math.min(totalPag, this._pagina + rango);
|
|
||||||
if (pMin > 1) { agregar('1', 1, false, false); if (pMin > 2) agregar('…', null, true, false); }
|
|
||||||
for (let p = pMin; p <= pMax; p++) agregar(p, p, false, p === this._pagina);
|
|
||||||
if (pMax < totalPag) { if (pMax < totalPag-1) agregar('…', null, true, false); agregar(totalPag, totalPag, false, false); }
|
|
||||||
|
|
||||||
agregar('›', this._pagina+1, this._pagina === totalPag, false);
|
|
||||||
agregar('»', totalPag, this._pagina === totalPag, false);
|
|
||||||
},
|
},
|
||||||
|
|
||||||
irAPagina(p) {
|
irAPagina(p) { this.cargar(p); $('panel-envios').scrollIntoView({behavior:'smooth',block:'start'}); },
|
||||||
this._pagina = p;
|
|
||||||
this._render();
|
|
||||||
$('panel-envios').scrollIntoView({ behavior:'smooth', block:'start' });
|
|
||||||
},
|
|
||||||
|
|
||||||
copiarTokenLink(token) {
|
copiarTokenLink(token) {
|
||||||
const url = window.location.origin + window.location.pathname.replace(/\/[^/]+$/, '')
|
const url = window.location.origin + window.location.pathname.replace(/\/[^/]+$/, '')
|
||||||
@@ -919,7 +856,7 @@ const verRespuesta = {
|
|||||||
|
|
||||||
async abrir(envioId) {
|
async abrir(envioId) {
|
||||||
this._envioId = envioId;
|
this._envioId = envioId;
|
||||||
const e = envios._data.find(x => x.id == envioId);
|
const e = envios._paginaData.find(x => x.id == envioId);
|
||||||
if (!e) return;
|
if (!e) return;
|
||||||
|
|
||||||
const cliente = JSON.parse(e.datos_cliente || '{}');
|
const cliente = JSON.parse(e.datos_cliente || '{}');
|
||||||
|
|||||||
Reference in New Issue
Block a user