update
This commit is contained in:
parent
1e1e078489
commit
6752d3515f
@ -1,8 +1,8 @@
|
|||||||
<!-- ========== Left Sidebar Start ========== -->
|
<!-- ========== Left Sidebar Start ========== -->
|
||||||
<div class="left side-menu">
|
<div class="left side-menu">
|
||||||
<button type="button" class="button-menu-mobile button-menu-mobile-topbar open-left waves-effect">
|
<!-- <button type="button" class="button-menu-mobile button-menu-mobile-topbar open-left waves-effect">
|
||||||
<i class="ion-close"></i>
|
<i class="ion-close"></i>
|
||||||
</button>
|
</button> -->
|
||||||
|
|
||||||
<!-- LOGO -->
|
<!-- LOGO -->
|
||||||
<div class="topbar-left">
|
<div class="topbar-left">
|
||||||
|
|||||||
@ -125,6 +125,47 @@
|
|||||||
transform: translateY(30px);
|
transform: translateY(30px);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
body.sidebar-collapsed .left.side-menu {
|
||||||
|
width: 80px;
|
||||||
|
/* Riduci la larghezza della sidebar */
|
||||||
|
overflow: hidden;
|
||||||
|
transition: all 0.3s ease;
|
||||||
|
}
|
||||||
|
|
||||||
|
body.sidebar-collapsed .content-page {
|
||||||
|
margin-left: 80px;
|
||||||
|
/* Adatta il contenuto */
|
||||||
|
transition: all 0.3s ease;
|
||||||
|
}
|
||||||
|
|
||||||
|
body.sidebar-collapsed .left.side-menu ul li a span {
|
||||||
|
display: none;
|
||||||
|
/* Nascondi il testo dei link */
|
||||||
|
}
|
||||||
|
|
||||||
|
body.sidebar-collapsed .left.side-menu ul li a {
|
||||||
|
text-align: center;
|
||||||
|
/* Centra le icone */
|
||||||
|
}
|
||||||
|
|
||||||
|
body.sidebar-collapsed .left.side-menu .sidebar-user h6,
|
||||||
|
body.sidebar-collapsed .left.side-menu .sidebar-user p {
|
||||||
|
display: none;
|
||||||
|
/* Nascondi dettagli utente */
|
||||||
|
}
|
||||||
|
|
||||||
|
.button-menu-mobile {
|
||||||
|
display: inline-block;
|
||||||
|
background-color: transparent;
|
||||||
|
border: none;
|
||||||
|
font-size: 20px;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
.mdi-menu {
|
||||||
|
font-size: 24px;
|
||||||
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|
||||||
<nav class="navbar-custom">
|
<nav class="navbar-custom">
|
||||||
@ -192,9 +233,9 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- item-->
|
<!-- item-->
|
||||||
<div id="notificationItemDiv">
|
<div id="notificationItemDiv">
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
<!-- <a href="javascript:void(0);" class="dropdown-item notify-item">
|
<!-- <a href="javascript:void(0);" class="dropdown-item notify-item">
|
||||||
<div class="notify-icon bg-primary"><i class="mdi mdi-cart-outline"></i></div>
|
<div class="notify-icon bg-primary"><i class="mdi mdi-cart-outline"></i></div>
|
||||||
<p class="notify-details"><b>Your order is placed</b><small class="text-muted">Dummy text of the printing and typesetting industry.</small></p>
|
<p class="notify-details"><b>Your order is placed</b><small class="text-muted">Dummy text of the printing and typesetting industry.</small></p>
|
||||||
@ -228,9 +269,10 @@
|
|||||||
|
|
||||||
<ul class="list-inline menu-left mb-0">
|
<ul class="list-inline menu-left mb-0">
|
||||||
<li class="float-left">
|
<li class="float-left">
|
||||||
<button class="button-menu-mobile open-left waves-light waves-effect">
|
<button id="toggle-sidebar" class="button-menu-mobile open-left waves-light waves-effect">
|
||||||
<i class="mdi mdi-menu"></i>
|
<i class="mdi mdi-menu"></i>
|
||||||
</button>
|
</button>
|
||||||
|
|
||||||
</li>
|
</li>
|
||||||
|
|
||||||
</ul>
|
</ul>
|
||||||
@ -308,13 +350,13 @@
|
|||||||
$.post("<?php echo USERAREA_PATH; ?>include/getNotifications.php", {
|
$.post("<?php echo USERAREA_PATH; ?>include/getNotifications.php", {
|
||||||
method: 'getNotifications'
|
method: 'getNotifications'
|
||||||
}, function(data) {
|
}, function(data) {
|
||||||
unseen_notifications =data.unseen_notifications;
|
unseen_notifications = data.unseen_notifications;
|
||||||
$("#notificationQuantity").text(unseen_notifications.length);
|
$("#notificationQuantity").text(unseen_notifications.length);
|
||||||
$("#notificationQuantityDropDown").text(unseen_notifications.length);
|
$("#notificationQuantityDropDown").text(unseen_notifications.length);
|
||||||
|
|
||||||
$("#notificationItemDiv").empty();
|
$("#notificationItemDiv").empty();
|
||||||
|
|
||||||
for(var i=0; i<data.unseen_notifications.length; i++){
|
for (var i = 0; i < data.unseen_notifications.length; i++) {
|
||||||
$("#notificationItemDiv").append(`
|
$("#notificationItemDiv").append(`
|
||||||
<a href="javascript:void(0);" class="dropdown-item notify-item">
|
<a href="javascript:void(0);" class="dropdown-item notify-item">
|
||||||
<div class="notify-icon bg-primary">
|
<div class="notify-icon bg-primary">
|
||||||
@ -324,20 +366,20 @@
|
|||||||
</a>
|
</a>
|
||||||
`);
|
`);
|
||||||
}
|
}
|
||||||
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div class="notification-space" id="mainNotificationDiv">
|
<div class="notification-space" id="mainNotificationDiv">
|
||||||
<!-- Notifications will be displayed here -->
|
<!-- Notifications will be displayed here -->
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="<?php echo USERAREA_PATH;?>assets/js/popper.min.js"></script>
|
<script src="<?php echo USERAREA_PATH; ?>assets/js/popper.min.js"></script>
|
||||||
<script src="<?php echo USERAREA_PATH;?>assets/js/bootstrap.min.js"></script>
|
<script src="<?php echo USERAREA_PATH; ?>assets/js/bootstrap.min.js"></script>
|
||||||
|
|
||||||
<script src="../assets/js/jquery.slimscroll.js"></script>
|
<script src="../assets/js/jquery.slimscroll.js"></script>
|
||||||
<!-- App js -->
|
<!-- App js -->
|
||||||
<script src="<?php echo USERAREA_PATH;?>assets/js/app.js"></script>
|
<script src="<?php echo USERAREA_PATH; ?>assets/js/app.js"></script>
|
||||||
<script src="<?php echo USERAREA_PATH;?>assets/plugins/alertify/js/alertify.js"></script>
|
<script src="<?php echo USERAREA_PATH; ?>assets/plugins/alertify/js/alertify.js"></script>
|
||||||
<!-- Top Bar End -->
|
<!-- Top Bar End -->
|
||||||
@ -35,17 +35,26 @@ SELECT
|
|||||||
WHEN LOWER(ap.test_Rating) NOT IN ('pass', 'p', 'comply', 'complies', 'fail', 'f', 'doesn\'t comply') THEN 1
|
WHEN LOWER(ap.test_Rating) NOT IN ('pass', 'p', 'comply', 'complies', 'fail', 'f', 'doesn\'t comply') THEN 1
|
||||||
ELSE 0
|
ELSE 0
|
||||||
END) AS data_analyses,
|
END) AS data_analyses,
|
||||||
GREATEST(0, 10 - (
|
CASE
|
||||||
SUM(
|
WHEN SUM(CASE WHEN LOWER(ap.test_Rating) IN ('fail', 'f', 'doesn\'t comply') THEN 1 ELSE 0 END) = 0
|
||||||
CASE
|
AND SUM(CASE WHEN LOWER(ap.test_Rating) NOT IN ('pass', 'p', 'comply', 'complies', 'fail', 'f', 'doesn\'t comply') THEN 1 ELSE 0 END) = 0
|
||||||
WHEN LOWER(ap.test_Rating) IN ('fail', 'f', 'doesn\'t comply') THEN
|
THEN 100
|
||||||
COALESCE(asv.severity, 1) *
|
ELSE GREATEST(0, 100 - (
|
||||||
CASE WHEN COALESCE(asv.is_legal, 'N') = 'Y' THEN 1.5 ELSE 1.0 END
|
SUM(
|
||||||
ELSE 0
|
CASE
|
||||||
END
|
WHEN LOWER(ap.test_Rating) IN ('fail', 'f', 'doesn\'t comply') THEN
|
||||||
) * (1 + SUM(CASE WHEN LOWER(ap.test_Rating) IN ('fail', 'f', 'doesn\'t comply') THEN 1 ELSE 0 END) / NULLIF(COUNT(ap.idAnalysis_Project), 0))
|
POWER(COALESCE(asv.severity, 1), 2) *
|
||||||
/ NULLIF(COUNT(ap.idAnalysis_Project), 0) * 100
|
CASE WHEN COALESCE(asv.is_legal, 'N') = 'Y' THEN 2.0 ELSE 1.0 END
|
||||||
)) AS rating,
|
ELSE 0
|
||||||
|
END
|
||||||
|
) / NULLIF(COUNT(ap.idAnalysis_Project), 0) * 100 *
|
||||||
|
(1 + 2 * (SUM(CASE WHEN LOWER(ap.test_Rating) IN ('fail', 'f', 'doesn\'t comply') THEN 1 ELSE 0 END) / NULLIF(COUNT(ap.idAnalysis_Project), 0)))
|
||||||
|
+ SUM(CASE
|
||||||
|
WHEN LOWER(ap.test_Rating) NOT IN ('pass', 'p', 'comply', 'complies', 'fail', 'f', 'doesn\'t comply') THEN 0.3
|
||||||
|
ELSE 0
|
||||||
|
END)
|
||||||
|
))
|
||||||
|
END AS rating,
|
||||||
NOW() AS calculation_date
|
NOW() AS calculation_date
|
||||||
FROM products p
|
FROM products p
|
||||||
JOIN reports r ON p.idproducts = r.idproducts
|
JOIN reports r ON p.idproducts = r.idproducts
|
||||||
@ -61,7 +70,6 @@ ON DUPLICATE KEY UPDATE
|
|||||||
data_analyses = VALUES(data_analyses),
|
data_analyses = VALUES(data_analyses),
|
||||||
rating = VALUES(rating),
|
rating = VALUES(rating),
|
||||||
calculation_date = VALUES(calculation_date);
|
calculation_date = VALUES(calculation_date);
|
||||||
|
|
||||||
";
|
";
|
||||||
|
|
||||||
if ($conn->query($query) === TRUE) {
|
if ($conn->query($query) === TRUE) {
|
||||||
|
|||||||
@ -32,6 +32,7 @@
|
|||||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/pdfmake/0.1.53/vfs_fonts.js"></script>
|
<script src="https://cdnjs.cloudflare.com/ajax/libs/pdfmake/0.1.53/vfs_fonts.js"></script>
|
||||||
<script src="https://cdn.datatables.net/buttons/2.3.7/js/buttons.html5.min.js"></script>
|
<script src="https://cdn.datatables.net/buttons/2.3.7/js/buttons.html5.min.js"></script>
|
||||||
<script src="https://cdn.datatables.net/buttons/2.3.7/js/buttons.print.min.js"></script>
|
<script src="https://cdn.datatables.net/buttons/2.3.7/js/buttons.print.min.js"></script>
|
||||||
|
<link href="https://cdn.materialdesignicons.com/5.4.55/css/materialdesignicons.min.css" rel="stylesheet">
|
||||||
|
|
||||||
|
|
||||||
</head>
|
</head>
|
||||||
@ -46,14 +47,22 @@
|
|||||||
|
|
||||||
<div class="page-content-wrapper">
|
<div class="page-content-wrapper">
|
||||||
<div class="container-fluid">
|
<div class="container-fluid">
|
||||||
<div class="row">
|
<br>
|
||||||
<div class="col-sm-12">
|
<div class="row mb-4">
|
||||||
<div class="page-title-box">
|
<div class="col-md-12">
|
||||||
<h4 class="page-title">Supplier Ratings</h4>
|
<div class="card p-4">
|
||||||
|
<div class="rating-box">
|
||||||
|
<h3 class="m-0">
|
||||||
|
RATE&GO
|
||||||
|
</h3>
|
||||||
|
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
<!-- Button for Rating Calculation -->
|
<!-- Button for Rating Calculation -->
|
||||||
<div class="row">
|
<div class="row">
|
||||||
<div class="col-md-12 text-right">
|
<div class="col-md-12 text-right">
|
||||||
@ -64,6 +73,24 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Chart Section -->
|
<!-- Chart Section -->
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-md-12 text-right">
|
||||||
|
<label for="rating-filter">Filter by Rating:</label>
|
||||||
|
<select id="rating-filter" class="form-control w-auto d-inline-block">
|
||||||
|
<option value="green">Green (80-100)</option>
|
||||||
|
<option value="orange">Orange (50-79)</option>
|
||||||
|
<option value="red">Red (0-49)</option>
|
||||||
|
<option value="all">All</option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-md-12">
|
||||||
|
<div id="supplier-rating-chart"></div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
|
||||||
<div class="row">
|
<div class="row">
|
||||||
<div class="col-md-12">
|
<div class="col-md-12">
|
||||||
<div id="supplier-rating-chart"></div>
|
<div id="supplier-rating-chart"></div>
|
||||||
@ -105,11 +132,17 @@
|
|||||||
|
|
||||||
<script>
|
<script>
|
||||||
$(document).ready(function() {
|
$(document).ready(function() {
|
||||||
// Funzione per aggiornare il grafico
|
let chart; // Variabile per memorizzare l'istanza del grafico
|
||||||
function updateChart(response) {
|
|
||||||
const suppliers = response.map(s => s.name);
|
// Funzione per generare il grafico
|
||||||
const ratings = response.map(s => s.rating);
|
function renderChart(filteredData) {
|
||||||
const colors = response.map(s => s.color);
|
const suppliers = filteredData.map(s => s.name);
|
||||||
|
const ratings = filteredData.map(s => s.rating);
|
||||||
|
const colors = filteredData.map(s => {
|
||||||
|
if (s.rating >= 80) return '#28a745'; // Green
|
||||||
|
if (s.rating >= 50) return '#ffc107'; // Orange
|
||||||
|
return '#dc3545'; // Red
|
||||||
|
});
|
||||||
|
|
||||||
const options = {
|
const options = {
|
||||||
series: [{
|
series: [{
|
||||||
@ -117,26 +150,92 @@
|
|||||||
}],
|
}],
|
||||||
chart: {
|
chart: {
|
||||||
type: 'bar',
|
type: 'bar',
|
||||||
height: 400
|
height: Math.max(filteredData.length * 18, 300), // Altezza dinamica
|
||||||
|
toolbar: {
|
||||||
|
show: true
|
||||||
|
},
|
||||||
|
animations: {
|
||||||
|
enabled: true, // Abilita animazioni fluide
|
||||||
|
easing: 'easeinout',
|
||||||
|
speed: 800
|
||||||
|
}
|
||||||
|
},
|
||||||
|
plotOptions: {
|
||||||
|
bar: {
|
||||||
|
distributed: true,
|
||||||
|
horizontal: true,
|
||||||
|
barHeight: '80%', // Altezza barra
|
||||||
|
dataLabels: {
|
||||||
|
position: 'inside' // Valori all'interno delle barre
|
||||||
|
}
|
||||||
|
}
|
||||||
},
|
},
|
||||||
colors: colors,
|
colors: colors,
|
||||||
|
dataLabels: {
|
||||||
|
enabled: true,
|
||||||
|
style: {
|
||||||
|
colors: ['#000'], // Colore nero per i valori
|
||||||
|
fontWeight: 'bold'
|
||||||
|
},
|
||||||
|
formatter: function(val) {
|
||||||
|
return val; // Mostra il valore direttamente
|
||||||
|
}
|
||||||
|
},
|
||||||
xaxis: {
|
xaxis: {
|
||||||
categories: suppliers
|
categories: suppliers,
|
||||||
|
labels: {
|
||||||
|
style: {
|
||||||
|
fontSize: '12px'
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
legend: {
|
||||||
|
show: false
|
||||||
},
|
},
|
||||||
title: {
|
title: {
|
||||||
text: 'Supplier Ratings',
|
text: 'Supplier Ratings (Filtered)',
|
||||||
align: 'center'
|
align: 'center'
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
// Renderizza il grafico
|
// Distruggi il grafico precedente, se esiste
|
||||||
const chart = new ApexCharts(
|
if (chart) {
|
||||||
document.querySelector("#supplier-rating-chart"),
|
chart.destroy();
|
||||||
options
|
}
|
||||||
);
|
|
||||||
|
// Crea un nuovo grafico
|
||||||
|
chart = new ApexCharts(document.querySelector("#supplier-rating-chart"), options);
|
||||||
chart.render();
|
chart.render();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Funzione per filtrare i dati
|
||||||
|
function filterData(data, filter) {
|
||||||
|
if (filter === "green") return data.filter(s => s.rating >= 80);
|
||||||
|
if (filter === "orange") return data.filter(s => s.rating >= 50 && s.rating < 80);
|
||||||
|
if (filter === "red") return data.filter(s => s.rating < 50);
|
||||||
|
return data; // All
|
||||||
|
}
|
||||||
|
|
||||||
|
// Caricamento iniziale
|
||||||
|
$.get('get_supplier_ratings.php', function(response) {
|
||||||
|
const allData = response;
|
||||||
|
|
||||||
|
// Filtro predefinito: Green
|
||||||
|
const defaultFilter = "green";
|
||||||
|
const filteredData = filterData(allData, defaultFilter);
|
||||||
|
$("#rating-filter").val(defaultFilter); // Imposta il filtro predefinito nel dropdown
|
||||||
|
|
||||||
|
// Renderizza il grafico iniziale
|
||||||
|
renderChart(filteredData);
|
||||||
|
|
||||||
|
// Cambia filtro
|
||||||
|
$("#rating-filter").on('change', function() {
|
||||||
|
const selectedFilter = $(this).val();
|
||||||
|
const filteredData = filterData(allData, selectedFilter);
|
||||||
|
renderChart(filteredData); // Re-renderizza il grafico con i dati filtrati
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
// Inizializza DataTables
|
// Inizializza DataTables
|
||||||
const supplierTable = $('#supplierTable').DataTable({
|
const supplierTable = $('#supplierTable').DataTable({
|
||||||
ajax: {
|
ajax: {
|
||||||
@ -167,7 +266,7 @@
|
|||||||
{
|
{
|
||||||
data: 'rating',
|
data: 'rating',
|
||||||
render: function(data, type, row) {
|
render: function(data, type, row) {
|
||||||
const color = data >= 8 ? '#28a745' : data >= 5 ? '#ffc107' : '#dc3545';
|
const color = data >= 80 ? '#28a745' : data >= 50 ? '#ffc107' : '#dc3545';
|
||||||
return `<span style="color: ${color}; font-weight: bold;">${data}</span>`;
|
return `<span style="color: ${color}; font-weight: bold;">${data}</span>`;
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@ -184,12 +283,15 @@
|
|||||||
buttons: [
|
buttons: [
|
||||||
'copy', 'csv', 'excel', 'pdf', 'print' // Tipi di esportazione
|
'copy', 'csv', 'excel', 'pdf', 'print' // Tipi di esportazione
|
||||||
],
|
],
|
||||||
|
lengthMenu: [
|
||||||
|
[10, 25, 50, 100, -1], // Valori
|
||||||
|
[10, 25, 50, 100, "All"] // Etichette corrispondenti
|
||||||
|
],
|
||||||
initComplete: function(settings, json) {
|
initComplete: function(settings, json) {
|
||||||
updateChart(json); // Aggiorna il grafico dopo aver caricato la tabella
|
renderChart(json); // Aggiorna il grafico dopo aver caricato la tabella
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
// Funzione per calcolare i rating e aggiornare grafico e tabella
|
// Funzione per calcolare i rating e aggiornare grafico e tabella
|
||||||
$('#calculate-rating').on('click', function() {
|
$('#calculate-rating').on('click', function() {
|
||||||
$.ajax({
|
$.ajax({
|
||||||
@ -199,7 +301,7 @@
|
|||||||
alert('Ratings calculated successfully!');
|
alert('Ratings calculated successfully!');
|
||||||
supplierTable.ajax.reload(); // Ricarica la tabella
|
supplierTable.ajax.reload(); // Ricarica la tabella
|
||||||
$.get('get_supplier_ratings.php', function(response) {
|
$.get('get_supplier_ratings.php', function(response) {
|
||||||
updateChart(response); // Aggiorna il grafico
|
renderChart(response); // Aggiorna il grafico
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
error: function() {
|
error: function() {
|
||||||
@ -211,6 +313,7 @@
|
|||||||
</script>
|
</script>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
</body>
|
</body>
|
||||||
|
|
||||||
</html>
|
</html>
|
||||||
@ -171,7 +171,7 @@ if (!$supplier) {
|
|||||||
<?php echo htmlspecialchars($supplier['name']); ?>
|
<?php echo htmlspecialchars($supplier['name']); ?>
|
||||||
</h3>
|
</h3>
|
||||||
<div class="rating-score
|
<div class="rating-score
|
||||||
<?php echo $supplier['rating'] >= 8 ? 'rating-high' : ($supplier['rating'] >= 5 ? 'rating-medium' : 'rating-low'); ?>">
|
<?php echo $supplier['rating'] >= 80 ? 'rating-high' : ($supplier['rating'] >= 50 ? 'rating-medium' : 'rating-low'); ?>">
|
||||||
<?php echo number_format($supplier['rating'], 2); ?>
|
<?php echo number_format($supplier['rating'], 2); ?>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -224,6 +224,18 @@ if (!$supplier) {
|
|||||||
<div class="card-body">
|
<div class="card-body">
|
||||||
<h5 class="card-title">Analysis Distribution</h5>
|
<h5 class="card-title">Analysis Distribution</h5>
|
||||||
<div id="pie-chart"></div>
|
<div id="pie-chart"></div>
|
||||||
|
<button id="toggle-pie-table" class="btn btn-secondary mt-3">Toggle Table</button>
|
||||||
|
<div id="pie-table-container" style="display: none;">
|
||||||
|
<table class="table table-bordered mt-3">
|
||||||
|
<thead>
|
||||||
|
<tr>
|
||||||
|
<th>Category</th>
|
||||||
|
<th>Count</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody id="pie-table-body"></tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -233,6 +245,18 @@ if (!$supplier) {
|
|||||||
<div class="card-body">
|
<div class="card-body">
|
||||||
<h5 class="card-title">Analysis Summary</h5>
|
<h5 class="card-title">Analysis Summary</h5>
|
||||||
<div id="stacked-bar-chart"></div>
|
<div id="stacked-bar-chart"></div>
|
||||||
|
<button id="toggle-stacked-table" class="btn btn-secondary mt-3">Toggle Table</button>
|
||||||
|
<div id="stacked-table-container" style="display: none;">
|
||||||
|
<table class="table table-bordered mt-3">
|
||||||
|
<thead>
|
||||||
|
<tr>
|
||||||
|
<th>Category</th>
|
||||||
|
<th>Count</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody id="stacked-table-body"></tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -245,18 +269,16 @@ if (!$supplier) {
|
|||||||
<div class="card-body">
|
<div class="card-body">
|
||||||
<h5 class="card-title">Total Analysis Distribution</h5>
|
<h5 class="card-title">Total Analysis Distribution</h5>
|
||||||
<div id="distribution-bar-chart"></div>
|
<div id="distribution-bar-chart"></div>
|
||||||
<button class="collapsible">Toggle Table</button>
|
<button id="toggle-distribution-table" class="btn btn-secondary mt-3">Toggle Table</button>
|
||||||
<div class="collapsible-content">
|
<div id="distribution-table-container" style="display: none;">
|
||||||
<table class="table table-bordered">
|
<table class="table table-bordered mt-3">
|
||||||
<thead>
|
<thead>
|
||||||
<tr>
|
<tr>
|
||||||
<th>Analysis Name</th>
|
<th>Analysis Name</th>
|
||||||
<th>Total</th>
|
<th>Total</th>
|
||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
<tbody id="distribution-table-body">
|
<tbody id="distribution-table-body"></tbody>
|
||||||
<!-- Data loaded dynamically -->
|
|
||||||
</tbody>
|
|
||||||
</table>
|
</table>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -272,40 +294,36 @@ if (!$supplier) {
|
|||||||
<h5 class="card-title">Top FAIL Analyses</h5>
|
<h5 class="card-title">Top FAIL Analyses</h5>
|
||||||
<div id="fail-bar-chart"></div>
|
<div id="fail-bar-chart"></div>
|
||||||
<!-- Pulsante Toggle Table -->
|
<!-- Pulsante Toggle Table -->
|
||||||
<button id="toggle-fail-table" class="btn btn-secondary">Toggle Table</button>
|
<button id="toggle-fail-table" class="btn btn-secondary mt-3">Toggle Table</button>
|
||||||
<div id="fail-table-container" style="display: none;">
|
<div id="fail-table-container" style="display: none;">
|
||||||
<table class="table table-bordered">
|
<table class="table table-bordered mt-3">
|
||||||
<thead>
|
<thead>
|
||||||
<tr>
|
<tr>
|
||||||
<th>Analysis Name</th>
|
<th>Analysis Name</th>
|
||||||
<th>Fail Count</th>
|
<th>Fail Count</th>
|
||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
<tbody id="fail-table-body">
|
<tbody id="fail-table-body"></tbody>
|
||||||
<!-- Popolato dinamicamente -->
|
|
||||||
</tbody>
|
|
||||||
</table>
|
</table>
|
||||||
</div>
|
</div>
|
||||||
<!-- Pulsante View Fail Details -->
|
<button id="view-fail-details" class="btn btn-primary mt-3">View Fail Details</button>
|
||||||
<button id="view-fail-details" class="btn btn-primary">View Fail Details</button>
|
|
||||||
<div id="fail-details-container" style="display: none;">
|
<div id="fail-details-container" style="display: none;">
|
||||||
<table class="table table-bordered">
|
<table class="table table-bordered mt-3">
|
||||||
<thead>
|
<thead>
|
||||||
<tr>
|
<tr>
|
||||||
<th>Analysis Name</th>
|
<th>Analysis Name</th>
|
||||||
<th>Report Number</th>
|
<th>Report Number</th>
|
||||||
<th>Ref Numb.</th>
|
<th>Ref Number</th>
|
||||||
<th>Product Description</th>
|
<th>Product Description</th>
|
||||||
<th>Action</th>
|
<th>Action</th>
|
||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
<tbody id="fail-details-table-body">
|
<tbody id="fail-details-table-body"></tbody>
|
||||||
<!-- Popolato dinamicamente -->
|
|
||||||
</tbody>
|
|
||||||
</table>
|
</table>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -315,12 +333,133 @@ if (!$supplier) {
|
|||||||
|
|
||||||
<script>
|
<script>
|
||||||
document.addEventListener("DOMContentLoaded", function() {
|
document.addEventListener("DOMContentLoaded", function() {
|
||||||
// Dati per i grafici principali
|
const supplierName = "<?php echo htmlspecialchars($supplier['name']); ?>";
|
||||||
|
|
||||||
|
// Pie Chart Configuration (Analysis Distribution)
|
||||||
const passCount = <?php echo isset($supplier['pass_analyses']) ? $supplier['pass_analyses'] : 0; ?>;
|
const passCount = <?php echo isset($supplier['pass_analyses']) ? $supplier['pass_analyses'] : 0; ?>;
|
||||||
const failCount = <?php echo isset($supplier['fail_analyses']) ? $supplier['fail_analyses'] : 0; ?>;
|
const failCount = <?php echo isset($supplier['fail_analyses']) ? $supplier['fail_analyses'] : 0; ?>;
|
||||||
const dataCount = <?php echo isset($supplier['data_analyses']) ? $supplier['data_analyses'] : 0; ?>;
|
const dataCount = <?php echo isset($supplier['data_analyses']) ? $supplier['data_analyses'] : 0; ?>;
|
||||||
|
|
||||||
// Pie Chart Configuration
|
|
||||||
|
$.getJSON(`get_fail_details.php?supplier=${supplierName}`, function(data) {
|
||||||
|
if (data.error) {
|
||||||
|
alert(data.error);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Configurazione del grafico
|
||||||
|
const failChartOptions = {
|
||||||
|
series: [{
|
||||||
|
data: data.failDistribution.map(item => item.fail)
|
||||||
|
}],
|
||||||
|
chart: {
|
||||||
|
type: 'bar',
|
||||||
|
height: 350,
|
||||||
|
horizontal: true
|
||||||
|
},
|
||||||
|
xaxis: {
|
||||||
|
categories: data.failDistribution.map(item => item.analysis_name),
|
||||||
|
title: {
|
||||||
|
text: 'Fail Count'
|
||||||
|
}
|
||||||
|
},
|
||||||
|
colors: ['#dc3545'],
|
||||||
|
title: {
|
||||||
|
text: 'Top FAIL Analyses',
|
||||||
|
align: 'center'
|
||||||
|
},
|
||||||
|
plotOptions: {
|
||||||
|
bar: {
|
||||||
|
horizontal: true,
|
||||||
|
barHeight: '50%'
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
const failChart = new ApexCharts(document.querySelector("#fail-bar-chart"), failChartOptions);
|
||||||
|
failChart.render();
|
||||||
|
|
||||||
|
// Popola la tabella di riepilogo delle analisi fallite
|
||||||
|
const failTableBody = document.querySelector("#fail-table-body");
|
||||||
|
data.failDistribution.forEach(row => {
|
||||||
|
failTableBody.innerHTML += `
|
||||||
|
<tr>
|
||||||
|
<td>${row.analysis_name}</td>
|
||||||
|
<td>${row.fail}</td>
|
||||||
|
</tr>`;
|
||||||
|
});
|
||||||
|
|
||||||
|
// Gestione del pulsante "View Fail Details"
|
||||||
|
|
||||||
|
|
||||||
|
const failDetailsButton = document.querySelector("#view-fail-details");
|
||||||
|
if (!failDetailsButton) {
|
||||||
|
console.error("Pulsante #view-fail-details non trovato nel DOM.");
|
||||||
|
} else {
|
||||||
|
console.log("Pulsante trovato:", failDetailsButton);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// Gestione del pulsante "View Fail Details"
|
||||||
|
document.querySelector("#view-fail-details").addEventListener("click", function() {
|
||||||
|
console.log("View Fail Details clicked");
|
||||||
|
const detailsContainer = document.querySelector("#fail-details-container");
|
||||||
|
|
||||||
|
if (!detailsContainer) {
|
||||||
|
console.error("The #fail-details-container was not found.");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const detailsTableBody = document.querySelector("#fail-details-table-body");
|
||||||
|
|
||||||
|
if (!detailsTableBody) {
|
||||||
|
console.error("The #fail-details-table-body was not found.");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Remove the nested AJAX call and use the existing data from the first AJAX call
|
||||||
|
if (!detailsContainer.hasAttribute("data-loaded")) {
|
||||||
|
// Use the data from the first AJAX call
|
||||||
|
const details = data; // This assumes 'data' is in scope from the previous $.getJSON call
|
||||||
|
|
||||||
|
// Clear any existing content
|
||||||
|
detailsTableBody.innerHTML = '';
|
||||||
|
|
||||||
|
// Populate the table with fail details
|
||||||
|
details.failDetails.forEach(detail => {
|
||||||
|
detailsTableBody.innerHTML += `
|
||||||
|
<tr>
|
||||||
|
<td>${detail.analysis_name}</td>
|
||||||
|
<td>${detail.report_number}</td>
|
||||||
|
<td>${detail.product_refnumber}</td>
|
||||||
|
<td>${detail.product_description}</td>
|
||||||
|
<td>
|
||||||
|
<a href="../products/reportdetails.php?idreports=${detail.report_id}" target="_blank" class="btn btn-sm btn-primary">
|
||||||
|
View Details
|
||||||
|
</a>
|
||||||
|
</td>
|
||||||
|
</tr>`;
|
||||||
|
});
|
||||||
|
|
||||||
|
detailsContainer.setAttribute("data-loaded", "true");
|
||||||
|
detailsContainer.style.display = "block";
|
||||||
|
} else {
|
||||||
|
// Toggle visibility if already loaded
|
||||||
|
detailsContainer.style.display = detailsContainer.style.display === "block" ? "none" : "block";
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
// Toggle per la tabella Fail Summary
|
||||||
|
document.querySelector("#toggle-fail-table").addEventListener("click", function() {
|
||||||
|
const table = document.querySelector("#fail-table-container");
|
||||||
|
table.style.display = table.style.display === "block" ? "none" : "block";
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
const pieChartOptions = {
|
const pieChartOptions = {
|
||||||
series: [passCount, failCount, dataCount],
|
series: [passCount, failCount, dataCount],
|
||||||
chart: {
|
chart: {
|
||||||
@ -347,7 +486,7 @@ if (!$supplier) {
|
|||||||
const pieChart = new ApexCharts(document.querySelector("#pie-chart"), pieChartOptions);
|
const pieChart = new ApexCharts(document.querySelector("#pie-chart"), pieChartOptions);
|
||||||
pieChart.render();
|
pieChart.render();
|
||||||
|
|
||||||
// Stacked Bar Chart Configuration
|
// Stacked Bar Chart Configuration (Analysis Summary)
|
||||||
const stackedBarChartOptions = {
|
const stackedBarChartOptions = {
|
||||||
series: [{
|
series: [{
|
||||||
name: 'PASS',
|
name: 'PASS',
|
||||||
@ -393,16 +532,14 @@ if (!$supplier) {
|
|||||||
const stackedBarChart = new ApexCharts(document.querySelector("#stacked-bar-chart"), stackedBarChartOptions);
|
const stackedBarChart = new ApexCharts(document.querySelector("#stacked-bar-chart"), stackedBarChartOptions);
|
||||||
stackedBarChart.render();
|
stackedBarChart.render();
|
||||||
|
|
||||||
// Fetch and populate data for additional charts and tables
|
// Fetch Data for Additional Charts and Tables
|
||||||
const supplierName = "<?php echo htmlspecialchars($supplier['name']); ?>";
|
|
||||||
|
|
||||||
$.getJSON(`get_analysis_data.php?supplier=${supplierName}`, function(data) {
|
$.getJSON(`get_analysis_data.php?supplier=${supplierName}`, function(data) {
|
||||||
if (data.error) {
|
if (data.error) {
|
||||||
alert(data.error);
|
alert(data.error);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Distribuzione delle analisi totali
|
// Distribution Bar Chart (Total Analysis Distribution)
|
||||||
const distributionChartOptions = {
|
const distributionChartOptions = {
|
||||||
series: [{
|
series: [{
|
||||||
data: data.analysisDistribution.map(item => item.total)
|
data: data.analysisDistribution.map(item => item.total)
|
||||||
@ -412,12 +549,6 @@ if (!$supplier) {
|
|||||||
height: 350,
|
height: 350,
|
||||||
horizontal: true
|
horizontal: true
|
||||||
},
|
},
|
||||||
plotOptions: {
|
|
||||||
bar: {
|
|
||||||
horizontal: true,
|
|
||||||
barHeight: '50%'
|
|
||||||
}
|
|
||||||
},
|
|
||||||
xaxis: {
|
xaxis: {
|
||||||
categories: data.analysisDistribution.map(item => item.analysis_name),
|
categories: data.analysisDistribution.map(item => item.analysis_name),
|
||||||
title: {
|
title: {
|
||||||
@ -428,22 +559,29 @@ if (!$supplier) {
|
|||||||
title: {
|
title: {
|
||||||
text: 'Total Analysis Distribution',
|
text: 'Total Analysis Distribution',
|
||||||
align: 'center'
|
align: 'center'
|
||||||
|
},
|
||||||
|
plotOptions: {
|
||||||
|
bar: {
|
||||||
|
horizontal: true,
|
||||||
|
barHeight: '50%'
|
||||||
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
const distributionChart = new ApexCharts(document.querySelector("#distribution-bar-chart"), distributionChartOptions);
|
const distributionChart = new ApexCharts(document.querySelector("#distribution-bar-chart"), distributionChartOptions);
|
||||||
distributionChart.render();
|
distributionChart.render();
|
||||||
|
|
||||||
// Aggiorna tabella per Distribuzione Totale
|
// Populate Distribution Table
|
||||||
const distTableBody = document.querySelector("#distribution-table-body");
|
const distTableBody = document.querySelector("#distribution-table-body");
|
||||||
data.analysisDistribution.forEach(row => {
|
data.analysisDistribution.forEach(row => {
|
||||||
distTableBody.innerHTML += `<tr>
|
distTableBody.innerHTML += `
|
||||||
<td>${row.analysis_name}</td>
|
<tr>
|
||||||
<td>${row.total}</td>
|
<td>${row.analysis_name}</td>
|
||||||
</tr>`;
|
<td>${row.total}</td>
|
||||||
|
</tr>`;
|
||||||
});
|
});
|
||||||
|
|
||||||
// Distribuzione delle analisi FAIL
|
// Fail Analysis Chart (Top FAIL Analyses)
|
||||||
const failChartOptions = {
|
const failChartOptions = {
|
||||||
series: [{
|
series: [{
|
||||||
data: data.failDistribution.map(item => item.fail)
|
data: data.failDistribution.map(item => item.fail)
|
||||||
@ -453,12 +591,6 @@ if (!$supplier) {
|
|||||||
height: 350,
|
height: 350,
|
||||||
horizontal: true
|
horizontal: true
|
||||||
},
|
},
|
||||||
plotOptions: {
|
|
||||||
bar: {
|
|
||||||
horizontal: true,
|
|
||||||
barHeight: '50%'
|
|
||||||
}
|
|
||||||
},
|
|
||||||
xaxis: {
|
xaxis: {
|
||||||
categories: data.failDistribution.map(item => item.analysis_name),
|
categories: data.failDistribution.map(item => item.analysis_name),
|
||||||
title: {
|
title: {
|
||||||
@ -469,58 +601,40 @@ if (!$supplier) {
|
|||||||
title: {
|
title: {
|
||||||
text: 'Top FAIL Analyses',
|
text: 'Top FAIL Analyses',
|
||||||
align: 'center'
|
align: 'center'
|
||||||
|
},
|
||||||
|
plotOptions: {
|
||||||
|
bar: {
|
||||||
|
horizontal: true,
|
||||||
|
barHeight: '50%'
|
||||||
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
const failChart = new ApexCharts(document.querySelector("#fail-bar-chart"), failChartOptions);
|
const failChart = new ApexCharts(document.querySelector("#fail-bar-chart"), failChartOptions);
|
||||||
failChart.render();
|
failChart.render();
|
||||||
|
|
||||||
// Aggiorna tabella per Distribuzione FAIL
|
// Populate Fail Table
|
||||||
const failTableBody = document.querySelector("#fail-table-body");
|
const failTableBody = document.querySelector("#fail-table-body");
|
||||||
data.failDistribution.forEach(row => {
|
data.failDistribution.forEach(row => {
|
||||||
failTableBody.innerHTML += `<tr>
|
failTableBody.innerHTML += `
|
||||||
<td>${row.analysis_name}</td>
|
<tr>
|
||||||
<td>${row.fail}</td>
|
<td>${row.analysis_name}</td>
|
||||||
</tr>`;
|
<td>${row.fail}</td>
|
||||||
|
</tr>`;
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
// Gestione Toggle Table
|
// Toggle Tables
|
||||||
|
document.querySelector("#toggle-distribution-table").addEventListener("click", function() {
|
||||||
|
const table = document.querySelector("#distribution-table-container");
|
||||||
|
table.style.display = table.style.display === "block" ? "none" : "block";
|
||||||
|
});
|
||||||
|
|
||||||
document.querySelector("#toggle-fail-table").addEventListener("click", function() {
|
document.querySelector("#toggle-fail-table").addEventListener("click", function() {
|
||||||
const table = document.querySelector("#fail-table-container");
|
const table = document.querySelector("#fail-table-container");
|
||||||
table.style.display = table.style.display === "block" ? "none" : "block";
|
table.style.display = table.style.display === "block" ? "none" : "block";
|
||||||
});
|
});
|
||||||
|
|
||||||
// Gestione View Fail Details
|
|
||||||
document.querySelector("#view-fail-details").addEventListener("click", function() {
|
|
||||||
const table = document.querySelector("#fail-details-container");
|
|
||||||
|
|
||||||
// Evita di richiamare più volte lo stesso contenuto
|
|
||||||
if (!table.hasAttribute("data-loaded")) {
|
|
||||||
$.getJSON(`get_fail_details.php?supplier=${supplierName}`, function(data) {
|
|
||||||
const failDetailsTableBody = document.querySelector("#fail-details-table-body");
|
|
||||||
|
|
||||||
data.failDetails.forEach(row => {
|
|
||||||
failDetailsTableBody.innerHTML += `
|
|
||||||
<tr>
|
|
||||||
<td>${row.analysis_name}</td>
|
|
||||||
<td>${row.report_number}</td>
|
|
||||||
<td>${row.product_refnumber}</td>
|
|
||||||
<td>${row.product_description}</td>
|
|
||||||
<td>
|
|
||||||
<a href="../products/reportdetails.php?idreports=${row.report_id}" target="_blank" class="btn btn-sm btn-primary">
|
|
||||||
View Details
|
|
||||||
</a>
|
|
||||||
</td>
|
|
||||||
</tr>`;
|
|
||||||
});
|
|
||||||
|
|
||||||
table.setAttribute("data-loaded", "true");
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
table.style.display = table.style.display === "block" ? "none" : "block";
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
|
|||||||
@ -24,6 +24,7 @@ if ($_POST['method'] == 'save') {
|
|||||||
}
|
}
|
||||||
$conn->query($sql);
|
$conn->query($sql);
|
||||||
echo 'Data saved';
|
echo 'Data saved';
|
||||||
|
|
||||||
} else if($_POST['method'] == 'load') {
|
} else if($_POST['method'] == 'load') {
|
||||||
$sql = "SELECT `order` FROM chart_order WHERE user_id = $iduserlogin ORDER BY insert_date DESC LIMIT 1";
|
$sql = "SELECT `order` FROM chart_order WHERE user_id = $iduserlogin ORDER BY insert_date DESC LIMIT 1";
|
||||||
$result = $conn->query($sql);
|
$result = $conn->query($sql);
|
||||||
|
|||||||
@ -248,16 +248,22 @@ $otherConditions = implode("', '", array_map('addslashes', RATING_OTHER));
|
|||||||
|
|
||||||
// Query per il grafico a barre orizzontali con sezioni multicolore
|
// Query per il grafico a barre orizzontali con sezioni multicolore
|
||||||
$horizontalBarQuery = "
|
$horizontalBarQuery = "
|
||||||
SELECT
|
SELECT
|
||||||
COALESCE(p.$groupingField, 'empty') AS groupingValue,
|
COALESCE(p.$groupingField, 'empty') AS groupingValue,
|
||||||
SUM(CASE WHEN UPPER(r.reportsRating) IN ('$passConditions') THEN 1 ELSE 0 END) AS passCount,
|
SUM(CASE WHEN UPPER(r.reportsRating) IN ('$passConditions') THEN 1 ELSE 0 END) AS passCount,
|
||||||
SUM(CASE WHEN UPPER(r.reportsRating) IN ('$failConditions') THEN 1 ELSE 0 END) AS failCount,
|
SUM(CASE WHEN UPPER(r.reportsRating) IN ('$failConditions') THEN 1 ELSE 0 END) AS failCount,
|
||||||
SUM(CASE WHEN UPPER(r.reportsRating) NOT IN ('$passConditions', '$failConditions') THEN 1 ELSE 0 END) AS otherCount
|
SUM(CASE WHEN UPPER(r.reportsRating) NOT IN ('$passConditions', '$failConditions') THEN 1 ELSE 0 END) AS otherCount
|
||||||
FROM reports r
|
FROM
|
||||||
LEFT JOIN products p ON r.idproducts = p.idproducts
|
reports r
|
||||||
$filters
|
LEFT JOIN
|
||||||
GROUP BY COALESCE(p.$groupingField, 'empty')
|
products p ON r.idproducts = p.idproducts
|
||||||
LIMIT 20
|
$filters
|
||||||
|
GROUP BY
|
||||||
|
COALESCE(p.$groupingField, 'empty')
|
||||||
|
ORDER BY
|
||||||
|
failCount DESC
|
||||||
|
LIMIT 20;
|
||||||
|
|
||||||
";
|
";
|
||||||
|
|
||||||
|
|
||||||
@ -285,6 +291,8 @@ $horizontalBarAnalysisQuery = "
|
|||||||
LEFT JOIN products p ON r.idproducts = p.idproducts
|
LEFT JOIN products p ON r.idproducts = p.idproducts
|
||||||
$filters
|
$filters
|
||||||
GROUP BY COALESCE(p.$groupingField, 'empty')
|
GROUP BY COALESCE(p.$groupingField, 'empty')
|
||||||
|
ORDER BY
|
||||||
|
failCount DESC
|
||||||
LIMIT 20
|
LIMIT 20
|
||||||
";
|
";
|
||||||
|
|
||||||
@ -302,15 +310,22 @@ while ($row = $horizontalBarAnalysisResult->fetch_assoc()) {
|
|||||||
|
|
||||||
// Statistic for worst suppliers based on % of failed reports
|
// Statistic for worst suppliers based on % of failed reports
|
||||||
$worstSuppliersQuery = "
|
$worstSuppliersQuery = "
|
||||||
SELECT p.namesupplier AS supplier, COUNT(r.idreports) AS totalReports,
|
SELECT
|
||||||
|
p.namesupplier AS supplier,
|
||||||
|
COUNT(r.idreports) AS totalReports,
|
||||||
SUM(CASE WHEN UPPER(r.reportsRating) IN ('FAIL', 'F', 'DOESN\'T COMPLY') THEN 1 ELSE 0 END) AS failedReports,
|
SUM(CASE WHEN UPPER(r.reportsRating) IN ('FAIL', 'F', 'DOESN\'T COMPLY') THEN 1 ELSE 0 END) AS failedReports,
|
||||||
(SUM(CASE WHEN UPPER(r.reportsRating) IN ('FAIL', 'F', 'DOESN\'T COMPLY') THEN 1 ELSE 0 END) / COUNT(r.idreports)) * 100 AS failPercentage
|
(SUM(CASE WHEN UPPER(r.reportsRating) IN ('FAIL', 'F', 'DOESN\'T COMPLY') THEN 1 ELSE 0 END) / COUNT(r.idreports)) * 100 AS failPercentage
|
||||||
FROM reports r
|
FROM
|
||||||
LEFT JOIN products p ON r.idproducts = p.idproducts
|
reports r
|
||||||
$filters
|
LEFT JOIN
|
||||||
GROUP BY p.namesupplier
|
products p ON r.idproducts = p.idproducts
|
||||||
ORDER BY failPercentage DESC
|
$filters
|
||||||
LIMIT 10
|
GROUP BY
|
||||||
|
p.namesupplier
|
||||||
|
ORDER BY
|
||||||
|
failPercentage DESC,
|
||||||
|
failedReports DESC
|
||||||
|
LIMIT 30;
|
||||||
";
|
";
|
||||||
$worstSuppliersResult = $conn->query($worstSuppliersQuery);
|
$worstSuppliersResult = $conn->query($worstSuppliersQuery);
|
||||||
$worstSuppliers = [];
|
$worstSuppliers = [];
|
||||||
|
|||||||
@ -280,7 +280,7 @@ include('parsedatachart.php');
|
|||||||
<!-- Begin page -->
|
<!-- Begin page -->
|
||||||
<div id="wrapper">
|
<div id="wrapper">
|
||||||
|
|
||||||
<?php // include('../include/navigationbar.php');
|
<?php include('../include/navigationbar.php');
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<!-- Start right Content here -->
|
<!-- Start right Content here -->
|
||||||
@ -484,10 +484,14 @@ include('parsedatachart.php');
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<!-- end row -->
|
<!-- end row -->
|
||||||
|
<div class="container my-4" data-id="1">
|
||||||
|
<h2 class="text-center text-primary fw-bold">Product Statistic</h2>
|
||||||
|
<hr class="my-3">
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="chart-container" id="charts">
|
<div class="chart-container" id="charts">
|
||||||
|
|
||||||
<div class="row chart-box" id="chart1" data-id="1">
|
<div class="row chart-box" id="chart1" data-id="2">
|
||||||
<div class="col-xl-12">
|
<div class="col-xl-12">
|
||||||
<div class="card">
|
<div class="card">
|
||||||
<div class="card-body">
|
<div class="card-body">
|
||||||
@ -548,7 +552,7 @@ include('parsedatachart.php');
|
|||||||
</div>
|
</div>
|
||||||
<!-- end row -->
|
<!-- end row -->
|
||||||
|
|
||||||
<div class="row chart-box" id="chart2" data-id="2">
|
<div class="row chart-box" id="chart2" data-id="3">
|
||||||
<div class="col-md-4"> <!-- Colonna per il primo grafico (Pie Chart) -->
|
<div class="col-md-4"> <!-- Colonna per il primo grafico (Pie Chart) -->
|
||||||
<div class="card">
|
<div class="card">
|
||||||
<div class="card-body">
|
<div class="card-body">
|
||||||
@ -565,19 +569,19 @@ include('parsedatachart.php');
|
|||||||
<div class="col-md-8"> <!-- Colonna per il secondo grafico -->
|
<div class="col-md-8"> <!-- Colonna per il secondo grafico -->
|
||||||
<div class="card">
|
<div class="card">
|
||||||
<div class="card-body">
|
<div class="card-body">
|
||||||
<h5 class="card-title">Worst Analysis</h5>
|
<h5 class="card-title">Reports Breakdown</h5>
|
||||||
<div id="worsttenanalysis"></div>
|
<div id="reportBarChart"></div>
|
||||||
<!-- Pulsante per mostrare/nascondere la tabella -->
|
|
||||||
<button class="btn btn-sm btn-primary toggle-table" data-target="#tableChartWorst">Toggle Data Table</button>
|
|
||||||
<!-- Contenitore per la tabella -->
|
|
||||||
<div id="tableChartWorst" class="hidden table-container"></div>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="row chart-box" id="chart3" data-id="3">
|
<div class="container my-4" data-id="4">
|
||||||
|
<h2 class="text-center text-primary fw-bold">Supplier Statistic</h2>
|
||||||
|
<hr class="my-3">
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row chart-box" id="chart3" data-id="5">
|
||||||
<div class="col-md-12">
|
<div class="col-md-12">
|
||||||
<div class="card">
|
<div class="card">
|
||||||
<div class="card-body">
|
<div class="card-body">
|
||||||
@ -593,7 +597,7 @@ include('parsedatachart.php');
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
|
||||||
<div class="row chart-box" id="chart4" data-id="4">
|
<div class="row chart-box" id="chart4" data-id="6">
|
||||||
<div class="col-md-12">
|
<div class="col-md-12">
|
||||||
<div class="card">
|
<div class="card">
|
||||||
<div class="card-body">
|
<div class="card-body">
|
||||||
@ -608,8 +612,12 @@ include('parsedatachart.php');
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="container my-4" data-id="7">
|
||||||
|
<h2 class="text-center text-primary fw-bold">Analysis Statistic</h2>
|
||||||
|
<hr class="my-3">
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="row chart-box" id="chart5" data-id="5">
|
<div class="row chart-box" id="chart5" data-id="8">
|
||||||
<div class="col-md-12">
|
<div class="col-md-12">
|
||||||
<div class="card">
|
<div class="card">
|
||||||
<div class="card-body">
|
<div class="card-body">
|
||||||
@ -624,8 +632,29 @@ include('parsedatachart.php');
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="row chart-box" id="chart5" data-id="9">
|
||||||
|
<div class="col-md-12">
|
||||||
|
<div class="card">
|
||||||
|
<div class="card-body">
|
||||||
|
<h5 class="card-title">Worst Analysis</h5>
|
||||||
|
<div id="worsttenanalysis"></div>
|
||||||
|
<!-- Pulsante per mostrare/nascondere la tabella -->
|
||||||
|
<button class="btn btn-sm btn-primary toggle-table" data-target="#tableChartWorst">Toggle Data Table</button>
|
||||||
|
<!-- Contenitore per la tabella -->
|
||||||
|
<div id="tableChartWorst" class="hidden table-container"></div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="row chart-box" id="chart6" data-id="6">
|
|
||||||
|
|
||||||
|
<div class="container my-4" data-id="10">
|
||||||
|
<h2 class="text-center text-primary fw-bold">Components/Substances Statistic</h2>
|
||||||
|
<hr class="my-3">
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row chart-box" id="chart6" data-id="11">
|
||||||
<div class="col-md-12">
|
<div class="col-md-12">
|
||||||
<div class="card">
|
<div class="card">
|
||||||
<div class="card-body">
|
<div class="card-body">
|
||||||
@ -640,8 +669,12 @@ include('parsedatachart.php');
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="container my-4" data-id="12">
|
||||||
|
<h2 class="text-center text-primary fw-bold">Other Parameter Statistic</h2>
|
||||||
|
<hr class="my-3">
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="row chart-box" id="chart7" data-id="7">
|
<div class="row chart-box" id="chart7" data-id="13">
|
||||||
<div class="col-md-12">
|
<div class="col-md-12">
|
||||||
<div class="card">
|
<div class="card">
|
||||||
<div class="card-body">
|
<div class="card-body">
|
||||||
@ -672,7 +705,7 @@ include('parsedatachart.php');
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="row mt-4">
|
<div class="row mt-4" data-id="14">
|
||||||
<!-- Colonna Sinistra per il Grafico a Torta -->
|
<!-- Colonna Sinistra per il Grafico a Torta -->
|
||||||
<div class="col-md-6">
|
<div class="col-md-6">
|
||||||
<div class="card">
|
<div class="card">
|
||||||
@ -905,7 +938,19 @@ include('parsedatachart.php');
|
|||||||
series: pieSeries,
|
series: pieSeries,
|
||||||
chart: {
|
chart: {
|
||||||
width: '100%',
|
width: '100%',
|
||||||
type: 'pie'
|
type: 'pie',
|
||||||
|
toolbar: {
|
||||||
|
show: true, // Mostra l'hamburger menu
|
||||||
|
tools: {
|
||||||
|
download: true, // Opzioni di download
|
||||||
|
selection: false,
|
||||||
|
zoom: false,
|
||||||
|
zoomin: false,
|
||||||
|
zoomout: false,
|
||||||
|
pan: false,
|
||||||
|
reset: false
|
||||||
|
}
|
||||||
|
}
|
||||||
},
|
},
|
||||||
labels: pieLabels,
|
labels: pieLabels,
|
||||||
colors: ['#FF4D4D', '#28A745', '#FFA500'],
|
colors: ['#FF4D4D', '#28A745', '#FFA500'],
|
||||||
@ -933,35 +978,83 @@ include('parsedatachart.php');
|
|||||||
// Genera la tabella
|
// Genera la tabella
|
||||||
$('#tableChart2').html(generatePieTable(pieLabels, pieSeries));
|
$('#tableChart2').html(generatePieTable(pieLabels, pieSeries));
|
||||||
|
|
||||||
|
var pieLabels = ['Pass', 'Fail', 'Others']; // Ordine richiesto
|
||||||
|
var pieSeries = [intPassReports, intFailReports, intOtherReports]; // Ordine dei dati: Pass, Fail, Others
|
||||||
|
|
||||||
|
// Configurazione del grafico a barre
|
||||||
|
var barOptions = {
|
||||||
|
series: [{
|
||||||
|
data: pieSeries // Utilizza i dati aggiornati
|
||||||
|
}],
|
||||||
|
chart: {
|
||||||
|
type: 'bar',
|
||||||
|
height: 400, // Altezza del grafico
|
||||||
|
toolbar: {
|
||||||
|
show: true, // Mostra l'hamburger menu
|
||||||
|
tools: {
|
||||||
|
download: true, // Opzioni di download
|
||||||
|
selection: false,
|
||||||
|
zoom: false,
|
||||||
|
zoomin: false,
|
||||||
|
zoomout: false,
|
||||||
|
pan: false,
|
||||||
|
reset: false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
plotOptions: {
|
||||||
|
bar: {
|
||||||
|
horizontal: false,
|
||||||
|
columnWidth: '50%',
|
||||||
|
distributed: true // Colori diversi per ogni colonna
|
||||||
|
}
|
||||||
|
},
|
||||||
|
dataLabels: {
|
||||||
|
enabled: true
|
||||||
|
},
|
||||||
|
xaxis: {
|
||||||
|
categories: pieLabels // Stesse etichette della pie chart
|
||||||
|
},
|
||||||
|
colors: ['#28A745', '#FF4D4D', '#FFA500'], // Verde, Rosso, Arancione
|
||||||
|
legend: {
|
||||||
|
show: false
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
// Inizializza e renderizza il grafico a barre
|
||||||
|
var barChart = new ApexCharts(document.querySelector("#reportBarChart"), barOptions);
|
||||||
|
barChart.render();
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
// remove bar chart and create a new one
|
// remove bar chart and create a new one
|
||||||
// Funzione per generare la tabella
|
// Funzione per generare la tabella
|
||||||
function generateTable(names, counts) {
|
function generateTable(names, counts) {
|
||||||
let tableHTML = `
|
let tableHTML = `
|
||||||
<table class="table table-striped table-bordered">
|
<table class="table table-striped table-bordered">
|
||||||
<thead>
|
<thead>
|
||||||
<tr>
|
<tr>
|
||||||
<th>Analysis</th>
|
<th>Analysis</th>
|
||||||
<th>Number of Failures</th>
|
<th>Number of Failures</th>
|
||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
<tbody>
|
<tbody>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
for (let i = 0; i < names.length; i++) {
|
for (let i = 0; i < names.length; i++) {
|
||||||
tableHTML += `
|
tableHTML += `
|
||||||
<tr>
|
<tr>
|
||||||
<td>${names[i]}</td>
|
<td>${names[i]}</td>
|
||||||
<td>${counts[i]}</td>
|
<td>${counts[i]}</td>
|
||||||
</tr>
|
</tr>
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
tableHTML += `
|
tableHTML += `
|
||||||
</tbody>
|
</tbody>
|
||||||
</table>
|
</table>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
return tableHTML;
|
return tableHTML;
|
||||||
}
|
}
|
||||||
@ -969,6 +1062,7 @@ include('parsedatachart.php');
|
|||||||
// Inizializza il grafico come prima
|
// Inizializza il grafico come prima
|
||||||
$('#worsttenanalysis').html('');
|
$('#worsttenanalysis').html('');
|
||||||
|
|
||||||
|
|
||||||
var analysisNames = data.topFailingAnalysis.map(function(item) {
|
var analysisNames = data.topFailingAnalysis.map(function(item) {
|
||||||
return item.name;
|
return item.name;
|
||||||
});
|
});
|
||||||
@ -987,6 +1081,7 @@ include('parsedatachart.php');
|
|||||||
plotOptions: {
|
plotOptions: {
|
||||||
bar: {
|
bar: {
|
||||||
horizontal: true,
|
horizontal: true,
|
||||||
|
borderRadius: 10,
|
||||||
dataLabels: {
|
dataLabels: {
|
||||||
position: 'center'
|
position: 'center'
|
||||||
}
|
}
|
||||||
@ -995,7 +1090,7 @@ include('parsedatachart.php');
|
|||||||
dataLabels: {
|
dataLabels: {
|
||||||
enabled: true,
|
enabled: true,
|
||||||
style: {
|
style: {
|
||||||
colors: ['#fff'],
|
colors: ['black'],
|
||||||
fontSize: '12px'
|
fontSize: '12px'
|
||||||
},
|
},
|
||||||
formatter: function(val, opt) {
|
formatter: function(val, opt) {
|
||||||
@ -1016,7 +1111,7 @@ include('parsedatachart.php');
|
|||||||
text: 'Analysis'
|
text: 'Analysis'
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
colors: ['#FF4D4D'],
|
colors: ['orange'],
|
||||||
responsive: [{
|
responsive: [{
|
||||||
breakpoint: 480,
|
breakpoint: 480,
|
||||||
options: {
|
options: {
|
||||||
@ -1069,7 +1164,7 @@ include('parsedatachart.php');
|
|||||||
],
|
],
|
||||||
chart: {
|
chart: {
|
||||||
type: 'bar',
|
type: 'bar',
|
||||||
height: 400,
|
height: 500,
|
||||||
stacked: true,
|
stacked: true,
|
||||||
horizontal: true
|
horizontal: true
|
||||||
},
|
},
|
||||||
@ -1080,6 +1175,7 @@ include('parsedatachart.php');
|
|||||||
plotOptions: {
|
plotOptions: {
|
||||||
bar: {
|
bar: {
|
||||||
horizontal: true,
|
horizontal: true,
|
||||||
|
borderRadius: 5,
|
||||||
dataLabels: {
|
dataLabels: {
|
||||||
enabled: false
|
enabled: false
|
||||||
}
|
}
|
||||||
@ -1118,7 +1214,7 @@ include('parsedatachart.php');
|
|||||||
],
|
],
|
||||||
chart: {
|
chart: {
|
||||||
type: 'bar',
|
type: 'bar',
|
||||||
height: 400,
|
height: 500,
|
||||||
stacked: true,
|
stacked: true,
|
||||||
horizontal: true
|
horizontal: true
|
||||||
},
|
},
|
||||||
@ -1129,6 +1225,7 @@ include('parsedatachart.php');
|
|||||||
plotOptions: {
|
plotOptions: {
|
||||||
bar: {
|
bar: {
|
||||||
horizontal: true,
|
horizontal: true,
|
||||||
|
borderRadius: 5,
|
||||||
dataLabels: {
|
dataLabels: {
|
||||||
enabled: false
|
enabled: false
|
||||||
}
|
}
|
||||||
@ -1144,33 +1241,33 @@ include('parsedatachart.php');
|
|||||||
// Funzione per generare la tabella
|
// Funzione per generare la tabella
|
||||||
function generateSupplierTable(names, failPercentages, totalReports, failedReports) {
|
function generateSupplierTable(names, failPercentages, totalReports, failedReports) {
|
||||||
let tableHTML = `
|
let tableHTML = `
|
||||||
<table class="table table-striped table-bordered">
|
<table class="table table-striped table-bordered">
|
||||||
<thead>
|
<thead>
|
||||||
<tr>
|
<tr>
|
||||||
<th>Supplier</th>
|
<th>Supplier</th>
|
||||||
<th>Failure Percentage (%)</th>
|
<th>Failure Percentage (%)</th>
|
||||||
<th>Failed Reports</th>
|
<th>Failed Reports</th>
|
||||||
<th>Total Reports</th>
|
<th>Total Reports</th>
|
||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
<tbody>
|
<tbody>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
for (let i = 0; i < names.length; i++) {
|
for (let i = 0; i < names.length; i++) {
|
||||||
tableHTML += `
|
tableHTML += `
|
||||||
<tr>
|
<tr>
|
||||||
<td>${names[i]}</td>
|
<td>${names[i]}</td>
|
||||||
<td>${failPercentages[i].toFixed(2)}%</td>
|
<td>${failPercentages[i].toFixed(2)}%</td>
|
||||||
<td>${failedReports[i]}</td>
|
<td>${failedReports[i]}</td>
|
||||||
<td>${totalReports[i]}</td>
|
<td>${totalReports[i]}</td>
|
||||||
</tr>
|
</tr>
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
tableHTML += `
|
tableHTML += `
|
||||||
</tbody>
|
</tbody>
|
||||||
</table>
|
</table>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
return tableHTML;
|
return tableHTML;
|
||||||
}
|
}
|
||||||
@ -1197,11 +1294,30 @@ include('parsedatachart.php');
|
|||||||
}],
|
}],
|
||||||
chart: {
|
chart: {
|
||||||
type: 'bar',
|
type: 'bar',
|
||||||
height: 400
|
height: 900
|
||||||
},
|
},
|
||||||
plotOptions: {
|
plotOptions: {
|
||||||
bar: {
|
bar: {
|
||||||
horizontal: true,
|
horizontal: true,
|
||||||
|
borderRadius: 5,
|
||||||
|
colors: {
|
||||||
|
ranges: [{
|
||||||
|
from: 0,
|
||||||
|
to: 30.00,
|
||||||
|
color: '#008000'
|
||||||
|
}, // Verde
|
||||||
|
{
|
||||||
|
from: 30,
|
||||||
|
to: 70,
|
||||||
|
color: '#FF8C00'
|
||||||
|
}, // Arancione
|
||||||
|
{
|
||||||
|
from: 70,
|
||||||
|
to: 100,
|
||||||
|
color: '#FF0000'
|
||||||
|
} // Rosso
|
||||||
|
]
|
||||||
|
},
|
||||||
dataLabels: {
|
dataLabels: {
|
||||||
position: 'center'
|
position: 'center'
|
||||||
}
|
}
|
||||||
@ -1233,13 +1349,24 @@ include('parsedatachart.php');
|
|||||||
text: 'Suppliers'
|
text: 'Suppliers'
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
colors: ['#3368FF'],
|
tooltip: {
|
||||||
|
enabled: true,
|
||||||
|
y: {
|
||||||
|
formatter: function(val, opt) {
|
||||||
|
return supplierNames[opt.dataPointIndex] +
|
||||||
|
' - ' + val.toFixed(2) + '%' +
|
||||||
|
' (Fail: ' + failedReportsForSupplier[opt.dataPointIndex] +
|
||||||
|
' - Total: ' + totalReportsForSupplier[opt.dataPointIndex] + ')';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
title: {
|
title: {
|
||||||
text: 'Top 10 Suppliers with the Highest Failed Reports Percentage',
|
text: 'Top Suppliers with the Highest Failed Reports Percentage',
|
||||||
align: 'center'
|
align: 'center'
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
var chart = new ApexCharts(document.querySelector("#worstSuppliersChart"), options);
|
var chart = new ApexCharts(document.querySelector("#worstSuppliersChart"), options);
|
||||||
chart.render();
|
chart.render();
|
||||||
|
|
||||||
@ -1318,6 +1445,7 @@ include('parsedatachart.php');
|
|||||||
plotOptions: {
|
plotOptions: {
|
||||||
bar: {
|
bar: {
|
||||||
horizontal: false,
|
horizontal: false,
|
||||||
|
borderRadius: 5,
|
||||||
columnWidth: '50%',
|
columnWidth: '50%',
|
||||||
dataLabels: {
|
dataLabels: {
|
||||||
position: 'top'
|
position: 'top'
|
||||||
@ -1415,11 +1543,12 @@ include('parsedatachart.php');
|
|||||||
}],
|
}],
|
||||||
chart: {
|
chart: {
|
||||||
type: 'bar',
|
type: 'bar',
|
||||||
height: 500
|
height: 550
|
||||||
},
|
},
|
||||||
plotOptions: {
|
plotOptions: {
|
||||||
bar: {
|
bar: {
|
||||||
horizontal: true,
|
horizontal: true,
|
||||||
|
borderRadius: 5,
|
||||||
columnWidth: '100%',
|
columnWidth: '100%',
|
||||||
endingShape: 'rounded'
|
endingShape: 'rounded'
|
||||||
}
|
}
|
||||||
@ -1453,7 +1582,7 @@ include('parsedatachart.php');
|
|||||||
},
|
},
|
||||||
fill: {
|
fill: {
|
||||||
opacity: 1,
|
opacity: 1,
|
||||||
colors: ['#004d00']
|
colors: ['green']
|
||||||
},
|
},
|
||||||
tooltip: {
|
tooltip: {
|
||||||
y: {
|
y: {
|
||||||
@ -1488,29 +1617,29 @@ include('parsedatachart.php');
|
|||||||
// Funzione per generare la tabella
|
// Funzione per generare la tabella
|
||||||
function generateAnalytesTable(analyteNames, failCounts) {
|
function generateAnalytesTable(analyteNames, failCounts) {
|
||||||
let tableHTML = `
|
let tableHTML = `
|
||||||
<table class="table table-striped table-bordered">
|
<table class="table table-striped table-bordered">
|
||||||
<thead>
|
<thead>
|
||||||
<tr>
|
<tr>
|
||||||
<th>Analyte Name</th>
|
<th>Analyte Name</th>
|
||||||
<th>Number of Failures</th>
|
<th>Number of Failures</th>
|
||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
<tbody>
|
<tbody>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
for (let i = 0; i < analyteNames.length; i++) {
|
for (let i = 0; i < analyteNames.length; i++) {
|
||||||
tableHTML += `
|
tableHTML += `
|
||||||
<tr>
|
<tr>
|
||||||
<td>${analyteNames[i]}</td>
|
<td>${analyteNames[i]}</td>
|
||||||
<td>${failCounts[i]}</td>
|
<td>${failCounts[i]}</td>
|
||||||
</tr>
|
</tr>
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
tableHTML += `
|
tableHTML += `
|
||||||
</tbody>
|
</tbody>
|
||||||
</table>
|
</table>
|
||||||
`;
|
`;
|
||||||
|
|
||||||
return tableHTML;
|
return tableHTML;
|
||||||
}
|
}
|
||||||
@ -1536,6 +1665,7 @@ include('parsedatachart.php');
|
|||||||
plotOptions: {
|
plotOptions: {
|
||||||
bar: {
|
bar: {
|
||||||
horizontal: true,
|
horizontal: true,
|
||||||
|
borderRadius: 5,
|
||||||
dataLabels: {
|
dataLabels: {
|
||||||
position: 'center' // Etichette al centro delle barre
|
position: 'center' // Etichette al centro delle barre
|
||||||
}
|
}
|
||||||
@ -1544,12 +1674,14 @@ include('parsedatachart.php');
|
|||||||
dataLabels: {
|
dataLabels: {
|
||||||
enabled: true,
|
enabled: true,
|
||||||
style: {
|
style: {
|
||||||
colors: ['#fff'], // Colore del testo all'interno delle barre
|
colors: ['black'], // Colore del testo all'interno delle barre
|
||||||
fontSize: '12px'
|
fontSize: '12px'
|
||||||
},
|
},
|
||||||
|
textAnchor: 'start', // Allinea il testo a sinistra
|
||||||
|
offsetX: -5, // Regola la distanza orizzontale
|
||||||
formatter: function(val, opt) {
|
formatter: function(val, opt) {
|
||||||
return analyteNames[opt.dataPointIndex]; // Mostra il nome dell'analita dentro la barra
|
return analyteNames[opt.dataPointIndex]; // Mostra il nome dell'analita dentro la barra
|
||||||
}
|
},
|
||||||
},
|
},
|
||||||
xaxis: {
|
xaxis: {
|
||||||
categories: failCounts, // Visualizza solo i numeri sull'asse X
|
categories: failCounts, // Visualizza solo i numeri sull'asse X
|
||||||
@ -1656,7 +1788,19 @@ include('parsedatachart.php');
|
|||||||
series: values,
|
series: values,
|
||||||
chart: {
|
chart: {
|
||||||
type: 'pie',
|
type: 'pie',
|
||||||
height: 350
|
height: 350,
|
||||||
|
toolbar: {
|
||||||
|
show: true, // Mostra l'hamburger menu
|
||||||
|
tools: {
|
||||||
|
download: true, // Opzioni di download
|
||||||
|
selection: false,
|
||||||
|
zoom: false,
|
||||||
|
zoomin: false,
|
||||||
|
zoomout: false,
|
||||||
|
pan: false,
|
||||||
|
reset: false
|
||||||
|
}
|
||||||
|
}
|
||||||
},
|
},
|
||||||
labels: labels,
|
labels: labels,
|
||||||
responsive: [{
|
responsive: [{
|
||||||
@ -1683,6 +1827,7 @@ include('parsedatachart.php');
|
|||||||
$('#tablePhasePie').html(generatePhasePieTable(labels, values));
|
$('#tablePhasePie').html(generatePhasePieTable(labels, values));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
function renderPhaseBarChart(phaseRatingsData) {
|
function renderPhaseBarChart(phaseRatingsData) {
|
||||||
const labels = phaseRatingsData.map(item => item.phase);
|
const labels = phaseRatingsData.map(item => item.phase);
|
||||||
const passCounts = phaseRatingsData.map(item => parseInt(item.passCount, 10));
|
const passCounts = phaseRatingsData.map(item => parseInt(item.passCount, 10));
|
||||||
@ -1718,7 +1863,8 @@ include('parsedatachart.php');
|
|||||||
colors: ['#28A745', '#FF4D4D', '#FFA500'],
|
colors: ['#28A745', '#FF4D4D', '#FFA500'],
|
||||||
plotOptions: {
|
plotOptions: {
|
||||||
bar: {
|
bar: {
|
||||||
horizontal: true,
|
horizontal: false,
|
||||||
|
borderRadius: 5,
|
||||||
dataLabels: {
|
dataLabels: {
|
||||||
enabled: false
|
enabled: false
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user