Actualizar servicios.html
This commit is contained in:
119
servicios.html
119
servicios.html
@@ -572,70 +572,73 @@ async function searchClientByPhone(phone) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function buildGridCard(s) {
|
function buildGridCard(s) {
|
||||||
const raw = s.raw_data || {};
|
const raw = s.raw_data || {};
|
||||||
const name = raw["Nombre Cliente"] || raw["CLIENTE"] || "Asegurado Sin Nombre";
|
const name = raw["Nombre Cliente"] || raw["CLIENTE"] || "Asegurado Sin Nombre";
|
||||||
const addr = raw["Dirección"] || raw["DOMICILIO"] || "---";
|
const addr = raw["Dirección"] || raw["DOMICILIO"] || "---";
|
||||||
const pop = raw["Población"] || raw["POBLACION-PROVINCIA"] || "";
|
const pop = raw["Población"] || raw["POBLACION-PROVINCIA"] || "";
|
||||||
const fullAddr = `${addr} ${pop}`.trim();
|
const fullAddr = `${addr} ${pop}`.trim();
|
||||||
const cita = raw.scheduled_date ? `${raw.scheduled_date} | ${raw.scheduled_time}` : 'Pendiente Cita';
|
const cita = raw.scheduled_date ? `${raw.scheduled_date.split('-').reverse().slice(0,2).join('/')} | ${raw.scheduled_time}` : 'Pte. Cita';
|
||||||
const companyName = raw['Compañía'] || raw['COMPAÑIA'] || raw['Procedencia'] || (s.provider === 'MANUAL' ? 'PARTICULAR' : 'ASEGURADORA');
|
const companyName = raw['Compañía'] || raw['COMPAÑIA'] || raw['Procedencia'] || (s.provider === 'MANUAL' ? 'PARTICULAR' : 'ASEGURADORA');
|
||||||
|
|
||||||
|
const isUrgent = s.is_urgent === true || (raw['Urgente'] && raw['Urgente'].toLowerCase() === 'sí') || (raw['URGENTE'] && raw['URGENTE'].toLowerCase() === 'si');
|
||||||
|
|
||||||
|
const stateInfo = s._stateInfo;
|
||||||
|
const colorData = colorDict[stateInfo.color] || colorDict['gray'];
|
||||||
|
|
||||||
|
let iconEstado = 'tag';
|
||||||
|
if(raw.scheduled_date) iconEstado = 'calendar';
|
||||||
|
if(stateInfo.name.toLowerCase().includes('camino')) iconEstado = 'car';
|
||||||
|
if(stateInfo.name.toLowerCase().includes('reparaci') || stateInfo.name.toLowerCase().includes('trabaja')) iconEstado = 'wrench';
|
||||||
|
if(stateInfo.name.toLowerCase().includes('incidencia') || stateInfo.name.toLowerCase().includes('pausado')) iconEstado = 'alert-triangle';
|
||||||
|
|
||||||
|
const inProgressBadge = s.automation_status === 'in_progress' ? `<span class="absolute -top-3 -right-3 bg-amber-400 text-white px-3 py-1 rounded-full text-[10px] font-black uppercase shadow-lg border-2 border-white flex items-center gap-1 animate-pulse z-10"><i data-lucide="bot" class="w-3 h-3"></i> En Bolsa</span>` : '';
|
||||||
|
|
||||||
|
return `
|
||||||
|
<div class="bg-white p-5 rounded-3xl border border-slate-200 shadow-sm card-hover text-left flex flex-col justify-between relative cursor-pointer" onclick="openDetail(${s.id})">
|
||||||
|
${inProgressBadge}
|
||||||
|
<div class="space-y-3">
|
||||||
|
<div class="flex items-start justify-between w-full gap-2">
|
||||||
|
<span class="text-[9px] font-black ${colorData.bg} ${colorData.text} px-2.5 py-1.5 rounded-lg uppercase tracking-wider flex items-center gap-1.5 truncate border ${colorData.border}">
|
||||||
|
<div class="w-2 h-2 rounded-full ${colorData.dot}"></div>
|
||||||
|
<span class="truncate">${stateInfo.name}</span>
|
||||||
|
</span>
|
||||||
|
${isUrgent ? `<span class="bg-red-500 text-white px-2 py-1 rounded-lg text-[9px] font-black uppercase shadow-sm animate-pulse shrink-0">🔥 URGENTE</span>` : `<span class="text-[10px] text-slate-400 font-bold uppercase bg-slate-50 border border-slate-100 px-2.5 py-1 rounded-lg shrink-0">#${s.service_ref}</span>`}
|
||||||
|
</div>
|
||||||
|
|
||||||
const isUrgent = s.is_urgent === true || (raw['Urgente'] && raw['Urgente'].toLowerCase() === 'sí') || (raw['URGENTE'] && raw['URGENTE'].toLowerCase() === 'si');
|
<div>
|
||||||
|
<p class="text-[9px] font-black text-blue-500 uppercase tracking-widest mb-0.5 truncate">${companyName}</p>
|
||||||
const stateInfo = s._stateInfo;
|
<h4 class="font-black text-slate-800 uppercase text-base leading-tight line-clamp-2" title="${name}">${name}</h4>
|
||||||
const colorData = colorDict[stateInfo.color] || colorDict['gray'];
|
</div>
|
||||||
|
|
||||||
let iconEstado = 'tag';
|
<div class="bg-slate-50/50 p-3 rounded-xl border border-slate-100">
|
||||||
if(raw.scheduled_date) iconEstado = 'calendar';
|
<p class="text-[10px] text-slate-600 font-medium uppercase line-clamp-2 flex items-start gap-1.5" title="${fullAddr}">
|
||||||
if(stateInfo.name.toLowerCase().includes('camino')) iconEstado = 'car';
|
<i data-lucide="map-pin" class="w-3.5 h-3.5 mt-0.5 text-slate-400 shrink-0"></i> ${fullAddr}
|
||||||
if(stateInfo.name.toLowerCase().includes('reparaci') || stateInfo.name.toLowerCase().includes('trabaja')) iconEstado = 'wrench';
|
</p>
|
||||||
if(stateInfo.name.toLowerCase().includes('incidencia') || stateInfo.name.toLowerCase().includes('pausado')) iconEstado = 'alert-triangle';
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
const inProgressBadge = s.automation_status === 'in_progress' ? `<span class="absolute -top-3 -right-3 bg-amber-400 text-white px-3 py-1 rounded-full text-[10px] font-black uppercase shadow-lg border-2 border-white flex items-center gap-1 animate-pulse z-10"><i data-lucide="bot" class="w-3 h-3"></i> En Bolsa</span>` : '';
|
<div class="flex items-center justify-between mt-4 pt-4 border-t border-slate-100 gap-2">
|
||||||
|
<div class="flex items-center gap-1 min-w-0 flex-1">
|
||||||
return `
|
<div class="bg-slate-100 p-1 rounded-lg text-slate-500 shrink-0"><i data-lucide="hard-hat" class="w-3 h-3"></i></div>
|
||||||
<div class="bg-white p-5 rounded-3xl border border-slate-200 shadow-sm card-hover text-left flex flex-col justify-between relative cursor-pointer" onclick="openDetail(${s.id})">
|
<span class="text-[10px] font-black text-slate-600 uppercase truncate flex-1" style="max-width: 70px;" title="${s.assigned_name || 'Sin asignar'}">${s.assigned_name || 'Sin asignar'}</span>
|
||||||
${inProgressBadge}
|
|
||||||
<div class="space-y-3">
|
|
||||||
<div class="flex items-start justify-between w-full gap-2">
|
|
||||||
<span class="text-[9px] font-black ${colorData.bg} ${colorData.text} px-2.5 py-1.5 rounded-lg uppercase tracking-wider flex items-center gap-1.5 truncate border ${colorData.border}">
|
|
||||||
<div class="w-2 h-2 rounded-full ${colorData.dot}"></div>
|
|
||||||
<span class="truncate">${stateInfo.name}</span>
|
|
||||||
</span>
|
|
||||||
${isUrgent ? `<span class="bg-red-500 text-white px-2 py-1 rounded-lg text-[9px] font-black uppercase shadow-sm animate-pulse shrink-0">🔥 URGENTE</span>` : `<span class="text-[10px] text-slate-400 font-bold uppercase bg-slate-50 border border-slate-100 px-2.5 py-1 rounded-lg shrink-0">#${s.service_ref}</span>`}
|
|
||||||
|
|
||||||
</div>
|
<div class="flex items-center gap-0.5 shrink-0">
|
||||||
|
<button onclick="event.stopPropagation(); window.location.href='trazabilidad.html?id=${s.id}'" class="p-1.5 text-slate-300 hover:text-blue-600 transition-colors" title="Ver Historial">
|
||||||
<div>
|
<i data-lucide="history" class="w-4 h-4"></i>
|
||||||
<p class="text-[9px] font-black text-blue-500 uppercase tracking-widest mb-0.5 truncate">${companyName}</p>
|
</button>
|
||||||
<h4 class="font-black text-slate-800 uppercase text-base leading-tight line-clamp-2" title="${name}">${name}</h4>
|
<button onclick="event.stopPropagation(); openDetail(${s.id}, true)" class="p-1.5 text-slate-300 hover:text-amber-600 transition-colors" title="Editar Ficha">
|
||||||
</div>
|
<i data-lucide="edit-3" class="w-4 h-4"></i>
|
||||||
|
</button>
|
||||||
<div class="bg-slate-50/50 p-3 rounded-xl border border-slate-100">
|
|
||||||
<p class="text-[10px] text-slate-600 font-medium uppercase line-clamp-2 flex items-start gap-1.5" title="${fullAddr}">
|
|
||||||
<i data-lucide="map-pin" class="w-3.5 h-3.5 mt-0.5 text-slate-400 shrink-0"></i> ${fullAddr}
|
|
||||||
</p>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="flex items-center justify-between mt-4 pt-4 border-t border-slate-100">
|
<div class="flex items-center gap-1 text-blue-600 shrink-0 bg-blue-50 px-2 py-1 rounded-md border border-blue-100">
|
||||||
<div class="flex items-center gap-2 min-w-0">
|
<i data-lucide="${iconEstado}" class="w-3 h-3"></i>
|
||||||
<div class="bg-slate-100 p-1.5 rounded-lg text-slate-500 shrink-0"><i data-lucide="hard-hat" class="w-3.5 h-3.5"></i></div>
|
<span class="text-[9px] font-black uppercase whitespace-nowrap">${raw.scheduled_date ? cita.split('|')[0] : 'Pte. Cita'}</span>
|
||||||
<span class="text-[10px] font-black text-slate-600 uppercase truncate" title="${s.assigned_name || 'Sin asignar'}">${s.assigned_name || 'Sin asignar'}</span>
|
</div>
|
||||||
<button onclick="event.stopPropagation(); window.location.href='trazabilidad.html?id=${s.id}'" class="p-1.5 bg-slate-50 text-slate-400 hover:text-blue-600 rounded-lg transition-colors border border-slate-100" title="Ver Historial">
|
</div>
|
||||||
<i data-lucide="history" class="w-3.5 h-3.5"></i>
|
</div>`;
|
||||||
</button>
|
}
|
||||||
|
|
||||||
|
|
||||||
</div>
|
|
||||||
${raw.scheduled_date ? `
|
|
||||||
<div class="flex items-center gap-1.5 text-blue-600 shrink-0 ml-2 bg-blue-50 px-2 py-1 rounded-md border border-blue-100">
|
|
||||||
<i data-lucide="${iconEstado}" class="w-3.5 h-3.5"></i>
|
|
||||||
<span class="text-[9px] font-black uppercase">${cita}</span>
|
|
||||||
</div>` : ''}
|
|
||||||
</div>
|
|
||||||
</div>`;
|
|
||||||
}
|
|
||||||
|
|
||||||
function shakeCard(element, status) {
|
function shakeCard(element, status) {
|
||||||
element.classList.add('shake');
|
element.classList.add('shake');
|
||||||
|
|||||||
Reference in New Issue
Block a user