production/Vue/Ficheadherent/index.php
2025-12-01 16:12:12 +00:00

928 lines
34 KiB
PHP
Executable File

<?php
$this->titre = "INTER SANTE - Fiche Adhérent";
$codeTypeAvenant = $_SESSION['codeTypeAvenant_C'];
$estsupprimable_0 = ($codeTypeAvenant=="AFN" or $codeTypeAvenant=="REN");
$garantieArchive = $_SESSION['garantieArchive_C'];
$estsupprimable = ($estsupprimable_0 && ($garantieArchive=="0"));
$primeArchiveAdh =$this->nettoyer($adherent['primeArchive']);
$estsupprimableAdh = ($primeArchiveAdh=="0");
$superUser = $_SESSION['superUser'];
$idAdherent = $this->nettoyer($adherent['idAdherent']);
$adherentRetire = $adherent['sorti'];
$dateSortieAdherent = $adherent['dateSortieAdherent'];
$controlerPlafondAdherent = ($_SESSION['controlerPlafondAdherent']>0);
$prestationParLienParente = $_SESSION['prestationParLienParente'];
$vip = $adherent['vip'];
$idBaremePriseEnCharge = $adherent['idBaremePriseEnCharge'];
$niveauGlobalConsoFamille = 0;
if($limite_adherent['plafond']>0)
{
$niveauGlobalConsoFamille = ($limite_adherent['consommation']/$limite_adherent['plafond'])*100;
}
$niveauGlobalConsoFamille = number_format($niveauGlobalConsoFamille, 2, ',', ' ');
?>
<script type="text/javascript">
</script>
<INPUT class="sr-only" TYPE="text" id="garantieArchive_C" name="garantieArchive_C" value="<?= $_SESSION['garantieArchive_C'] ?>">
<INPUT class="sr-only" TYPE="text" id="primeArchive" name="primeArchive" value="<?= $adherent['primeArchive'] ?>" >
<INPUT class="sr-only" TYPE="text" id="remplacementAdherent" name="remplacementAdherent" value="<?= $adherent['remplacementAdherent'] ?>" >
<INPUT class="sr-only" TYPE="text" id="remplace" name="remplace" value="<?= $adherent['remplace'] ?>" >
<INPUT class="sr-only" TYPE="text" id="remplacant" name="remplace" value="<?= $adherent['remplacant'] ?>" >
<INPUT class="sr-only" TYPE="text" id="idAdherent" name="idAdherent" value="<?= $idAdherent ?>" >
<INPUT class="sr-only" TYPE="text" id="numeroAdherent" name="numeroAdherent" value="<?= $adherent['numeroAdherent'] ?>" >
<INPUT class="sr-only" TYPE="text" id="nomForm" name="nomForm" value="ficheAdherent" >
<div id="div_patienter" ></div>
<FORM name = "formficheadehrent" id = "formficheadehrent" method="POST">
<INPUT class="sr-only" TYPE="text" id="codeEtatFacturation" name="codeEtatFacturation" value="<?=$adherent['codeEtatFacturation']?>" >
<INPUT class="sr-only" TYPE="text" id="numeroBeneficiaire" name="numeroBeneficiaire" value="<?=$adherent['numeroBeneficiaire']?>" >
<legend ><?= _("Informations sur l'adhérent") . " : (" . $this->nettoyer($adherent['numeroAdherent']).") => "._("Date Effet")." : ".dateLang($_SESSION['dateEffetAdherent_C'], $_SESSION['lang']) ?></legend>
<table class="table table-responsive table-condensed">
<tbody>
<tr>
<td colspan="6">
<?php if($vip=="1"): ?>
<INPUT class="form-control vip" TYPE="text" id="vip" name="vip" value="<?= _("ASSURE VIP") ?>">
<?php endif; ?>
</td >
</tr>
<tr>
<td width="10%" > <?= _("Nom Adhérent") ?> </td>
<td><INPUT class="form-control gras" TYPE="text" id="nom" NAME="nom" value="<?=$this->nettoyer($adherent['nom'])?>" readonly ></td>
<td width="10%" align="center"> <?= _("Prénoms") ?> </td>
<td><INPUT class="form-control gras" TYPE="text" id="prenoms" NAME="prenoms" value="<?=$this->nettoyer($adherent['prenoms'])?>" readonly ></td>
<td width="10%" align="center"> <?= _("Collège") ?> </td>
<td ><INPUT class="form-control gras" TYPE="text" value="<?=$this->nettoyer($adherent['libelleCollege'])?>" readonly ></td>
</tr>
<tr>
<td> <?= _("Tél Portable") ?> </td>
<td><INPUT class="form-control gras" TYPE="text" id="telephonePortable" NAME="telephonePortable" value="<?=$this->nettoyer($adherent['telephonePortable'])?>" readonly ></td>
<td align="center">E-mail</td>
<td colspan="2"><INPUT class="form-control gras" TYPE="text" id="email" NAME="email" value="<?=$this->nettoyer($adherent['email'])?>" readonly ></td>
<td>
<?php if($estsupprimableAdh==false): ?>
<?php if ($superUser=="1"): ?>
<input class = "form-control btn btn-warning" type="button" value="<?= _("Désarchiver toute la famille") ?>" onClick="javascript:de_archiver_adherent_fiche('<?= $idAdherent ?>');">
<?php endif; ?>
<?php else: ?>
<input class = "form-control btn btn-info" type="button" value="<?= _("Archiver toute la famille") ?>" onClick="javascript:archiver_adherent_fiche('<?= $idAdherent ?>');">
<?php endif; ?>
</tr>
<tr>
<td> <?= _("Pays") ?> </td>
<td><INPUT class="form-control gras" TYPE="text" value="<?=$this->nettoyer($adherent['pays'])?>" readonly ></td>
<td align="center"> <?= (isset($_SESSION['affichagedynamique']['Région'])) ? _($_SESSION['affichagedynamique']['Région']) : _("Région") ?> </td>
<td><INPUT class="form-control gras" TYPE="text" value="<?=$this->nettoyer($adherent['ville'])?>" readonly ></td>
<td align="center"> <?= (isset($_SESSION['affichagedynamique']['Commune'])) ? _($_SESSION['affichagedynamique']['Commune']) : _("Commune") ?> </td>
<td><INPUT class="form-control gras" TYPE="text" value="<?=$this->nettoyer($adherent['localite'])?>" readonly ></td>
</tr>
<tr>
<td ><?= _("Date Naissance") ?></td>
<td >
<INPUT class="form-control gras" TYPE="text" value="<?= datefr($this->nettoyer($adherent['dateNaissance']))?>" readonly >
</td>
<td align="center"><?= _("Date Entrée") ?></td>
<td ><INPUT class="form-control gras" TYPE="text" value="<?= datefr($this->nettoyer($adherent['dateEntree']))?>" readonly ></td>
<td align="center"><?= _("Type Remboursement") ?></td>
<td ><INPUT class="form-control gras" TYPE="text" value="<?= $this->nettoyer($adherent['codeTypeRemboursement'])?>" readonly ></td>
</tr>
<tr>
<td ><?= _("Tarif Actes") ?></td>
<td >
<select class="form-select gras" name="codeTarifActe" id="codeTarifActe" disabled >
<?= liste_options($tarifActe, $adherent['codeTarifActe'], false) ?>
</select>
</td>
<td align="center"><?= _("Date Souscription") ?></td>
<td ><INPUT class="form-control gras" TYPE="text" value="<?= datefr($this->nettoyer($adherent['dateSouscription']))?>" readonly ></td>
<td align="center"><?= _("Seuil RD (%)") ?></td>
<td ><INPUT class="form-control gras" TYPE="text" value="<?= $this->nettoyer($adherent['seuilRdAdherent'])?>" readonly ></td>
</tr>
<tr>
<td> <?= _("Plafond Famille") ?> </td>
<td>
<button class="form-control gras btn btn-primary" TYPE="button" onclick="javascript:limiteadherent();" title="Cliquez pour modifier le plafond famille...">
<?= format_N($this->nettoyer($limite_adherent['plafond'])) ?>
</button>
</td>
<td align="center"> <?= _("Conso. Famille") ?> </td>
<td>
<button class="form-control gras btn btn-primary" TYPE="button" onclick="javascript:consosadherent();" title="Cliquez pour voir le détail des consommations de l'adhérent...">
<?= format_N($this->nettoyer($limite_adherent['consommation'])) ?>
</button>
</td>
<td align="center"> <?= _("Solde Famille") ?> </td>
<td>
<INPUT style='text-align:center; color:red !important; font-weight:bold; font-size:10pt;' class="form-control" TYPE="text" value="<?= format_N($this->nettoyer($limite_adherent['soldeConsommation'])) ?>" readonly >
</td>
</tr>
<tr>
<td ></td>
<td >
<button class="form-control gras btn btn-info" TYPE="button" id="produit" name="produit" onclick="javascript:consulter_detail_bareme_college(<?=$idBaremePriseEnCharge?>);" title="<?= _("Afficher le barème de prise en charge")?>">
<?= _("Consulter Barème prise en charge") ?>
</button>
</td>
<td ></td>
<td >
<button class="form-control gras btn btn-success" TYPE="button" onclick="javascript:affiche_historique_prestations_famille();" title="<?= _("Afficher les prestations")?>">
<?= _("Historique prestations") ?>
</button>
</td>
<td style="font-size:12pt; text-align:center; font-weight:bold;"> % </td>
<td width="8%">
<INPUT style="font-size:10pt; text-align:center; font-weight:bold; color:red;" class="form-control" TYPE="text" value="<?= $niveauGlobalConsoFamille; ?>" readonly >
</td>
</tr>
</tbody>
</table>
</FORM>
<div id="div_patienter">
</div>
<div id="div_limite_adherent" class="modal fade">
</div>
<div id="div_consos_adherent" class="modal fade">
</div>
<?php if ($adherentRetire=="1") : ?>
<div class="alert alert-danger" style="height:30px; padding:5px; margin-bottom:5px; text-align:center;" >
<H4><?= _("Date sortie") . " : " . dateLang($dateSortieAdherent) ?></H4>
</div>
<?php endif; ?>
<fieldset>
<legend> <?= _('Détail les membres de sa famille') ?> </legend>
<table class="table table-striped table-bordered table-hover table-condensed table-responsive" style="font-size:9pt;">
<thead>
<tr>
<th style='text-align:center'> <?= _("No") ?> </th>
<th class="text-center"> <?= _("Photo") ?> </th>
<th> <?= _("Nom") ?> </th>
<th> <?= _("Prénoms") ?> </th>
<th style='text-align:center'> <?= _("Genre") ?> </th>
<th style='text-align:center'> <?= _("Lien Parenté") ?> </th>
<th style='text-align:center'> <?= _("Naissance") ?> </th>
<th style='text-align:center'> Age </th>
<th style='text-align:center'> <?= _("P Base") ?> </th>
<th style='text-align:center'> <?= _("P Nette") ?> </th>
<th style='text-align:center'> <?= (isset($_SESSION['composanteprime']['Taxes'])) ? _($_SESSION['composanteprime']['Taxes']) : _("Taxes") ?> </th>
<th style='text-align:center'> <?= (isset($_SESSION['composanteprime']['Cartes'])) ? _($_SESSION['composanteprime']['Cartes']) : _("Cartes") ?> </th>
<th style='text-align:center'> <?= _("PRIME TTC") ?> </th>
<th style='text-align:center'> <?= _("Fact") ?> </th>
<th width="5%" style='text-align:center'> <?= _("Archiver") ?> </th>
<th style='text-align:center'> <?= _("Etat") ?> </th>
<th style='text-align:center'> Suppr </th>
</tr>
</thead>
<tfoot>
<tr>
<td colspan="9" style='text-align:center'> Total </td>
<td align='center'><?= format_N($this->nettoyer($totalbeneficiaires['primeHt'])) ?></td>
<td align='center'><?= format_N($this->nettoyer($totalbeneficiaires['taxe'])) ?></td>
<td align='center'><?= format_N($this->nettoyer($totalbeneficiaires['fraisCarte'])) ?></td>
<td align='center'><?= format_N($this->nettoyer($totalbeneficiaires['primeTtc'])) ?></td>
<td colspan='4'> </td>
</tr>
</tfoot>
<tbody>
<?php foreach ($beneficiaires as $beneficiaire):
$idBeneficiaire = $this->nettoyer($beneficiaire['idBeneficiaire']);
$numeroBeneficiaire = $this->nettoyer($beneficiaire['numeroBeneficiaire']);
$primeArchive = $this->nettoyer($beneficiaire['primeArchive']);
$estsupprimable = ($primeArchive=="0");
if (est_anglophone())
{
$lienParente = $this->nettoyer($beneficiaire['LienParenteEng']);
}
else
{
$lienParente = $this->nettoyer($beneficiaire['LienParente']);
}
$vipben = $this->nettoyer($beneficiaire['vip']);
$faceRegistered = $this->nettoyer($beneficiaire['faceRegistered']);
$lienPhoto = $this->nettoyer($beneficiaire['lienPhoto']);
// vérifier que la photo du bénéficiaire existe
$photo = "";
$photoAssureCrypte = "";
if($faceRegistered == "1" && $lienPhoto>" ")
{
$photo = $_SESSION['lienPhotoFace'] . $lienPhoto;
if(!file_exists($photo))
{
$photoAssureCrypte = "";
}
else
{
$photoAssureCrypte = decryptImage($photo);
}
}
?>
<?php if($vipben=='1'): ?>
<tr style="color: red;" onclick="javascript:selectionner_beneficiaire(<?= $idBeneficiaire ?>,'<?= $numeroBeneficiaire ?>');" ondblclick="javascript:afficher_beneficiaire_id();" valign="top">
<?php else: ?>
<tr onclick="javascript:selectionner_beneficiaire(<?= $idBeneficiaire ?>,'<?= $numeroBeneficiaire ?>');" ondblclick="javascript:afficher_beneficiaire_id();" valign="top">
<?php endif; ?>
<?php if($vipben=='1'): ?>
<td align='center'><a href="javascript:selectionner_beneficiaire(<?= $idBeneficiaire ?>,'<?= $numeroBeneficiaire ?>');afficher_beneficiaire_id();"><span style="font-size:10pt; color:red;background-color:#eeeeee; border:1px solid #000; border-radius:3px;"><?= $numeroBeneficiaire ?></span></a></td>
<?php else: ?>
<td align='center'><a href="javascript:selectionner_beneficiaire(<?= $idBeneficiaire ?>,'<?= $numeroBeneficiaire ?>');afficher_beneficiaire_id();"><span style="font-size:10pt; color:blue;background-color:#eeeeee; border:1px solid #000; border-radius:3px;"><?= $numeroBeneficiaire ?></span></a></td>
<?php endif; ?>
<td align="center" style="position: relative; z-index: 1;">
<?php if($faceRegistered == "1"): ?>
<div class="photo-container" style="display: inline-block;">
<img class="photoId rounded-circle photo-zoom"
src="data:image/jpg;base64,<?=$photoAssureCrypte?>"
alt="<?= _("Photo Bénéficiaire") ?>"
style="width: 20px;">
</div>
<?php else: ?>
<div class="photo-container" style="display: inline-block;">
<i class="fas fa-user-circle photo-zoom"
style="color: #ccc; font-size: 20px;"></i>
</div>
<?php endif; ?>
</td>
<td><?= $this->nettoyer($beneficiaire['nomBeneficiaire']) ?></td>
<td><?= $this->nettoyer($beneficiaire['prenomsBeneficiaire']) ?></td>
<td align='center'><?= $this->nettoyer($beneficiaire['sexe']) ?></td>
<td align='center'><?= $lienParente ?></td>
<td align='center'><?= dateLang($this->nettoyer($beneficiaire['dateNaissance'])) ?></td>
<td align='center'><?= $this->nettoyer($beneficiaire['age']) ?></td>
<td align='center'><?= format_N($this->nettoyer($beneficiaire['primeFamille'])) ?></td>
<td align='center'><?= format_N($this->nettoyer($beneficiaire['primeHt'])) ?></td>
<td align='center'><?= format_N($this->nettoyer($beneficiaire['taxe'])) ?></td>
<td align='center'><?= format_N($this->nettoyer($beneficiaire['fraisCarte'])) ?></td>
<?php if($beneficiaire['codeEtatFacturation']=='1'): ?>
<td align='center'><?= format_N($this->nettoyer($beneficiaire['primeTtc'])) ?></td>
<td align='center'> <input type="checkbox" checked value="<? $beneficiaire['codeEtatFacturation']; ?>" disabled></td>
<td> </td>
<td align='center'><?= $this->nettoyer($beneficiaire['codeEtatBeneficiaire']) ?></td>
<td> </td>
<?php else: ?>
<?php if($estsupprimable) : ?>
<td align='center'> <input class = "form-control btn btn-primary" type="button"
value="<?= format_N($this->nettoyer($beneficiaire['primeTtc'])) ?>"
onClick="javascript:selectionner_beneficiaire(<?= $idBeneficiaire ?>, '<?= $numeroBeneficiaire ?>');
modifier_prime_beneficiaire(<?= $idBeneficiaire ?>)"> </td>
<td align='center'> <input type="checkbox" value="<? $beneficiaire['codeEtatFacturation']; ?>" disabled></td>
<td> <input class = "form-control btn btn-info" type="button" value="<?= _("Archiver") ?>" onClick="javascript:archiver_beneficiaire('<?= $idBeneficiaire ?>');"></td>
<td align='center'><?= $this->nettoyer($beneficiaire['codeEtatBeneficiaire']) ?></td>
<td align='center'> <input type="button" value="X" onClick="javascript:supprimer_beneficiaire_id('<?= $idBeneficiaire ?>');"></td>
<?php else: ?>
<td align='center'><?= format_N($this->nettoyer($beneficiaire['primeTtc'])) ?></td>
<td align='center'> <input type="checkbox" value="<? $beneficiaire['codeEtatFacturation']; ?>" disabled></td>
<?php if ($superUser=="1"): ?>
<td> <input class = "form-control btn btn-warning" type="button" value="<?= _("Désarchiver") ?>" onClick="javascript:de_archiver_beneficiaire('<?= $idBeneficiaire ?>');"></td>
<?php else : ?>
<td> </td>
<?php endif; ?>
<td align='center'><?= $this->nettoyer($beneficiaire['codeEtatBeneficiaire']) ?></td>
<td> </td>
<?php endif; ?>
<?php endif; ?>
</tr>
<?php endforeach; ?>
<tr style='background-color:white'>
<td colspan="16" height="1"></td>
</tr>
</tbody>
</table>
</fieldset>
<!-- Responsive Area Chart -->
<div class="row mt-4">
<div class="col-xl-8 col-lg-7 mb-4">
<div class="card shadow h-100">
<div class="card-header py-3 d-flex flex-column flex-md-row justify-content-between align-items-center">
<h6 class="m-0 font-weight-bold text-primary"><?= _("Dépenses mensuelles") ?></h6>
<div class="mt-2 mt-md-0">
<button id="exportTrendBtn" class="btn btn-sm btn-danger mr-2">
<i class="fas fa-download"></i> PDF
</button>
<small class="text-muted"><?= _("Évolution sur 12 mois") ?></small>
</div>
</div>
<div class="card-body">
<div class="chart-container" style="position: relative; height:300px; width:100%">
<canvas id="expenseTrendChart"></canvas>
</div>
</div>
</div>
</div>
<!-- Responsive Pie Chart -->
<div class="col-xl-4 col-lg-5 mb-4">
<div class="card shadow h-100">
<div class="card-header py-3 d-flex justify-content-between align-items-center">
<h6 class="m-0 font-weight-bold text-primary"><?= _("Dépenses par lien parenté") ?></h6>
<button id="exportPieBtn" class="btn btn-sm btn-danger">
<i class="fas fa-download"></i> PDF
</button>
</div>
<div class="card-body d-flex flex-column">
<div class="chart-container" style="position: relative; height:250px; width:100%">
<canvas id="expenseDistributionChart"></canvas>
</div>
<div id="pieChartLegend" class="mt-3 text-center"></div>
<div class="mt-auto pt-3">
<small class="text-muted"><?= _("Répartition en pourcentage") ?></small>
</div>
</div>
</div>
</div>
</div>
<!-- Bar Chart Section -->
<div class="row mt-4">
<div class="col-12 mb-4">
<div class="card shadow h-100">
<div class="card-header py-3 d-flex justify-content-between align-items-center">
<h6 class="m-0 font-weight-bold text-primary"><?= _("Dépenses par garantie") ?></h6>
<button id="exportBarBtn" class="btn btn-sm btn-danger">
<i class="fas fa-download"></i> PDF
</button>
</div>
<div class="card-body">
<div class="chart-container" style="position: relative; height:400px; width:100%">
<canvas id="depensesChart"></canvas>
</div>
</div>
</div>
</div>
</div>
<script>
// Configuration commune
(function() {
// Récupération de la devise depuis PHP
const userCurrency = '<?= isset($_SESSION['devise_C']) ? $_SESSION['devise_C'] : 'F CFA' ?>';
// Configuration des devises
const currencyFormats = {
'F CFA': {
symbol: 'F CFA',
format: (value) => new Intl.NumberFormat('fr-FR').format(value) + ' F CFA'
},
'€': {
symbol: '€',
format: (value) => new Intl.NumberFormat('fr-FR', {style: 'currency', currency: 'EUR'}).format(value)
},
'$': {
symbol: '$',
format: (value) => new Intl.NumberFormat('fr-FR', {style: 'currency', currency: 'USD'}).format(value)
},
'XOF': {
symbol: 'F CFA',
format: (value) => new Intl.NumberFormat('fr-FR').format(value) + ' F CFA'
}
};
// Format monétaire dynamique
const formatMoney = (value) => {
const currencyConfig = currencyFormats[userCurrency] || currencyFormats['F CFA'];
return currencyConfig.format(value);
};
// Format pourcentage
const formatPercentage = (value, total) => {
const percentage = (value * 100 / total).toFixed(1);
return percentage + '%';
};
// Détection mobile
const isMobile = window.matchMedia("(max-width: 768px)").matches;
// Génération des couleurs
const generateColors = (count) => {
const palette = [
'#4e73df', '#1cc88a', '#36b9cc', '#f6c23e',
'#e74a3b', '#858796', '#5a5c69', '#3a3b45',
'#2e59a9', '#17a673', '#2c9faf', '#dda20a'
];
return palette.slice(0, count).concat(
Array.from({length: Math.max(0, count - palette.length)}, (_, i) => {
const hue = Math.floor(360 * (i / Math.max(1, count - palette.length)));
return `hsl(${hue}, 70%, 60%)`;
})
);
};
// Fonction pour générer une légende personnalisée
function generateCustomLegend(chart, containerId) {
const legendContainer = document.getElementById(containerId);
legendContainer.innerHTML = '';
const items = chart.data.datasets[0].data.map((value, i) => {
const total = chart.data.datasets[0].data.reduce((a, b) => a + b, 0);
const percentage = formatPercentage(value, total);
return `
<div class="d-inline-block mx-2 my-1">
<span class="legend-color" style="
display: inline-block;
width: 12px;
height: 12px;
background-color: ${chart.data.datasets[0].backgroundColor[i]};
border: 1px solid #fff;
vertical-align: middle;
"></span>
<span class="legend-text small ml-1">
${chart.data.labels[i]}: ${formatMoney(value)} (${percentage})
</span>
</div>
`;
});
legendContainer.innerHTML = items.join('');
}
// Fonction pour exporter un graphique en PDF
function exportChartToPDF(chartId, fileName) {
const { jsPDF } = window.jspdf;
const canvas = document.getElementById(chartId);
html2canvas(canvas).then(canvasImage => {
const imgData = canvasImage.toDataURL('image/png');
const pdf = new jsPDF({
orientation: canvasImage.width > canvasImage.height ? 'landscape' : 'portrait'
});
const pageWidth = pdf.internal.pageSize.getWidth();
const pageHeight = pdf.internal.pageSize.getHeight();
const ratio = canvasImage.height / canvasImage.width;
let imgWidth = pageWidth - 20;
let imgHeight = imgWidth * ratio;
if (imgHeight > pageHeight - 20) {
imgHeight = pageHeight - 20;
imgWidth = imgHeight / ratio;
}
pdf.addImage(imgData, 'PNG',
(pageWidth - imgWidth) / 2,
(pageHeight - imgHeight) / 2,
imgWidth,
imgHeight
);
pdf.save(fileName + '.pdf');
});
}
// Graphique d'évolution des dépenses
const dataMois = <?= $dataConsoParMois ?>;
const trendCtx = document.getElementById('expenseTrendChart').getContext('2d');
const trendChart = new Chart(trendCtx, {
type: 'line',
data: {
labels: dataMois.mois,
datasets: [{
label: '<?= _("Montant dépensé") ?>',
data: dataMois.consos,
backgroundColor: 'rgba(78, 115, 223, 0.05)',
borderColor: 'rgba(78, 115, 223, 1)',
borderWidth: 2,
pointBackgroundColor: 'rgba(78, 115, 223, 1)',
pointRadius: isMobile ? 3 : 4,
pointHoverRadius: 6,
fill: true,
tension: 0.3
}]
},
options: {
responsive: true,
maintainAspectRatio: false,
plugins: {
legend: {
display: false
},
tooltip: {
mode: 'index',
intersect: false,
callbacks: {
label: function(context) {
return context.dataset.label + ': ' + formatMoney(context.parsed.y);
}
}
}
},
scales: {
x: {
grid: {
display: false
},
ticks: {
maxRotation: isMobile ? 45 : 0,
autoSkip: true,
maxTicksLimit: isMobile ? 6 : 12
}
},
y: {
beginAtZero: false,
ticks: {
callback: function(value) {
return formatMoney(value);
}
},
grid: {
color: 'rgba(0, 0, 0, 0.05)'
}
}
},
interaction: {
mode: 'nearest',
axis: 'x',
intersect: false
}
}
});
// Graphique de répartition
const dataLiens = <?= $dataConsoParLiens ?>;
const distributionCtx = document.getElementById('expenseDistributionChart').getContext('2d');
const distributionChart = new Chart(distributionCtx, {
type: 'pie',
data: {
labels: dataLiens.lienparente,
datasets: [{
data: dataLiens.consos_liens,
backgroundColor: generateColors(<?= $nbreLienParente; ?>),
borderColor: '#fff',
borderWidth: 2
}]
},
options: {
responsive: true,
maintainAspectRatio: false,
plugins: {
legend: {
display: false,
},
datalabels: {
formatter: (value, ctx) => {
const sum = ctx.chart.data.datasets[0].data.reduce((a, b) => a + b, 0);
return formatPercentage(value, sum);
},
color: '#fff',
font: {
weight: 'bold',
size: isMobile ? 10 : 12
}
},
tooltip: {
callbacks: {
label: function(context) {
const label = context.label || '';
const value = context.raw || 0;
const sum = context.dataset.data.reduce((a, b) => a + b, 0);
const percentage = formatPercentage(value, sum);
return `${label}: ${formatMoney(value)} (${percentage})`;
}
}
}
},
cutout: isMobile ? '60%' : '50%'
},
plugins: [ChartDataLabels]
});
// Graphique des dépenses par garantie
const dataConso = <?= $dataConsoParGaranties ?>;
const barCtx = document.getElementById('depensesChart').getContext('2d');
const barChart = new Chart(barCtx, {
type: 'bar',
data: {
labels: dataConso.garanties,
datasets: [{
label: 'Dépenses',
data: dataConso.depenses,
backgroundColor: 'rgba(54, 162, 235, 0.7)',
borderColor: 'rgba(54, 162, 235, 1)',
borderWidth: 1
}]
},
options: {
responsive: true,
maintainAspectRatio: false,
plugins: {
annotation: {
annotations: dataConso.plafonds.map((plafond, index) => {
if (plafond === null) return null;
return {
type: 'line',
yMin: plafond,
yMax: plafond,
borderColor: 'rgba(255, 99, 132, 0.7)',
borderWidth: 2,
borderDash: [6, 6],
label: {
content: `Plafond: ${formatMoney(plafond)}`,
enabled: true,
position: 'right'
}
};
}).filter(annotation => annotation !== null)
},
legend: {
display: false
},
tooltip: {
callbacks: {
label: function(context) {
const plafond = dataConso.plafonds[context.dataIndex];
let tooltip = `Dépenses: ${formatMoney(context.parsed.y)}`;
if (plafond !== null) {
const pourcentage = Math.min(100, Math.round((context.parsed.y / plafond) * 100));
tooltip += ` (${pourcentage}% du plafond)`;
} else {
tooltip += ' (plafond illimité)';
}
return tooltip;
}
}
}
},
scales: {
y: {
beginAtZero: true,
title: {
display: true,
text: `Montant des dépenses (${userCurrency})`,
font: {
weight: 'bold'
}
},
ticks: {
callback: function(value) {
return formatMoney(value);
}
},
suggestedMax: Math.max(...dataConso.depenses) * 1.5
},
x: {
title: {
display: true,
text: 'Garanties',
font: {
weight: 'bold'
}
},
grid: {
display: false
}
}
}
}
});
// Générer la légende au chargement et lors du redimensionnement
generateCustomLegend(distributionChart, 'pieChartLegend');
window.addEventListener('resize', function() {
generateCustomLegend(distributionChart, 'pieChartLegend');
});
// Boutons d'export PDF
document.getElementById('exportTrendBtn').addEventListener('click', () => {
exportChartToPDF('expenseTrendChart', 'evolution_depenses_mensuelles');
});
document.getElementById('exportPieBtn').addEventListener('click', () => {
exportChartToPDF('expenseDistributionChart', 'repartition_depenses_parente');
});
document.getElementById('exportBarBtn').addEventListener('click', () => {
exportChartToPDF('depensesChart', 'depenses_par_garantie');
});
})();
</script>
<style>
/* Styles communs pour tous les graphiques */
.chart-container {
position: relative;
width: 100%;
min-height: 300px;
}
#pieChartLegend {
font-size: 0.8rem;
line-height: 1.4;
}
.legend-text {
vertical-align: middle;
}
.btn-export {
padding: 0.25rem 0.5rem;
font-size: 0.75rem;
}
@media (max-width: 768px) {
#pieChartLegend {
font-size: 0.7rem;
}
.chart-container {
height: 60vh;
}
.card-header {
flex-direction: column;
align-items: flex-start !important;
}
.btn-export {
margin-top: 0.5rem;
align-self: flex-end;
}
}
</style>
<div id="div_legende_couleur" style="width:100%; margin: 5px; background-color: #f8f8ff;" class="tab-container">
<table class="table-responsive" style="width:100%; margin:auto; background-color: #f8f8ff; font-size:12pt;">
<tbody>
<tr>
<td style="font-weight:bold; text-align:right; background-color: #f8f8ff; text-decoration-line: underline;"> <?= _("Légende").":"; ?></td>
<td style="font-weight:bold; text-align:right; background-color: #f8f8ff;"> <?= _("Consommation")." >= 50%"; ?></td>
<td width="1%" style="background-color: #f8f8ff"></td>
<td width="4%" style="background-color:#726a57"></td >
<td width="2%" style="background-color: #f8f8ff"></td>
<td style="font-weight:bold; text-align:right; background-color: #f8f8ff;"><?= _("Consommation")." >= 80%"; ?></td>
<td width="1%" style="background-color: #f8f8ff"></td>
<td width="4%" style="background-color: orange"></td >
<td width="1%" style="background-color: #f8f8ff"></td>
<td style="font-weight:bold; text-align:right; background-color: #f8f8ff;" ><?= _("Consommation")." = 100% / ". _("Transaction")." = 100%"; ?></td>
<td style="background-color: #f8f8ff"></td>
<td width="4%" style="background-color: red;"></td >
</tr>
</tbody>
</table>
</div>
<fieldset>
<table class="table table-striped table-bordered table-hover table-condensed table-responsive" style="font-size:10pt;">
<thead>
<tr>
<th rowspan="2" width="5%" style="text-align:center"> <?= _("Exercice") ?> </th>
<th rowspan="2" width="20%" style="text-align:center"> <?= _("Garantie") ?> </th>
<th rowspan="2" style="text-align:center" width="5%"> <?= _("Taux") ?> </th>
<th colspan="4" style="text-align:center"> <?= _("Consommations") ?> </th>
<th colspan="4" style="text-align:center"> <?= _("Prestations") ?> </th>
</tr>
<tr>
<th style="text-align:center" width="10%"> <?= _("Plafond") ?> </th>
<th style="text-align:center" width="10%"> <?= _("Périodicité") ?> </th>
<th style="text-align:center" width="10%"> <?= _("Dépenses") ?> </th>
<th style="text-align:center" width="10%"> <?= _("Solde") ?> </th>
<th style="text-align:center" width="10%"> <?= _("Nb Transaction") ?> </th>
<th style="text-align:center" width="10%"> <?= _("Périodicité") ?> </th>
<th style="text-align:center" width="10%"> <?= _("Nbre Prestation") ?> </th>
<th style="text-align:center" width="10%"> <?= _("Solde") ?> </th>
</tr>
</thead>
<tbody>
<?php foreach ($garantieadherents as $v):
$champApplication = $this->nettoyer($v['champApplication']);
$pourcentConsoFamille = $this->nettoyer($v['pourcentConsoFamille']);
$transactionFamille = $this->nettoyer($v['transactionFamille']);
$soldeTransactionFamille = $this->nettoyer($v['soldeTransactionFamille']);
$idAdherent = $this->nettoyer($v['idAdherent']);
$codeGarantie = $this->nettoyer($v['codeGarantie']);
$exercieReference = $this->nettoyer($v['exercieReference']);
$plafondFamille = format_N($this->nettoyer($v['plafondFamille']));
$nbreTransactionFamille = $this->nettoyer($v['nbreTransactionFamille']);
?>
<?php if($pourcentConsoFamille>='50' && $pourcentConsoFamille<'80'): ?>
<tr style="background-color: yellow;" valign="top">
<?php elseif($pourcentConsoFamille>='80' && $pourcentConsoFamille <'100'): ?>
<tr style="background-color: orange;" valign="top">
<?php elseif($pourcentConsoFamille >='100' || $transactionFamille=="1"): ?>
<tr style="background-color: red; color:white" valign="top">
<?php else: ?>
<tr valign="top">
<?php endif; ?>
<td align='center'> <?= $this->nettoyer($v['exercieReference'])?> </td>
<td align='center'>
<?php if($pourcentConsoFamille >='95' || $transactionFamille=="1"): ?>
<a title="<?= _("Plafond ou nombre de transaction atteint pour cette garantie.") ?>" href="javascript:alert_ebene('Plafond ou nombre de transaction atteint pour cette garantie!', 'Limit or number of transactions reached for this guarantee!');">
<span style="color:blue; background-color:#eeeeee; border:1px solid #000; border-radius:3px;">
<?= $this->nettoyer($v['garantie'])?>
</span>
</a>
<?php else: ?>
<?= $this->nettoyer($v['garantie'])?>
<?php endif; ?>
</td>
<td align='center'><?= $this->nettoyer($v['tauxPlafond']).'%'; ?></td>
<td align='center' ><?= $plafondFamille ?></td>
<td align='center'><?= $v['codePeriodicitePlafondFamille'] ?></td>
<td align='center'><?= format_N($this->nettoyer($v['consommationFamille'])) ?></td>
<td align='center' ><?= format_N($this->nettoyer($v['soldeGarantieFamille'])) ?></td>
<td align='center'><?= $this->nettoyer($v['nbreTransactionFamille']) ?></td>
<td align='center'><?= $v['codePeriodiciteFamille'] ?></td>
<td align='center'><?= $this->nettoyer($v['comptePrestationFamille']) ?></td>
<td align='center'><?= $this->nettoyer($v['soldeTransactionFamille']) ?></td>
</tr>
<?php endforeach; ?>
</tbody>
</table>
</fieldset>
<div id="div_suppressionReussie">
</div>
<div id="div_historique_prestations" class="modal fade">
</div>