diff --git a/public/userarea/parts.js b/public/userarea/parts.js index 2fa8ce8..68512f1 100644 --- a/public/userarea/parts.js +++ b/public/userarea/parts.js @@ -1,7 +1,28 @@ $(document).ready(function () { console.log("parts.js caricato correttamente"); - // Gestione del popup per le parti + // =================== + // GLOBAL STATE (NEW) + // =================== + let photoData = { + naturalWidth: 0, + naturalHeight: 0, + displayWidth: 0, + displayHeight: 0, + scale: 1, + }; + + // markers keyed by photo src => [{ partNumber, x, y } using NATURAL coords] + let photoMarkers = {}; + + // selection & descriptions + let selectedPartNumber = null; + let descriptionPosition = { x: 10, y: 10 }; // NATURAL coords + let hasDescriptions = false; + + // =================== + // POPUP HANDLING + // =================== const partsButtons = document.querySelectorAll(".parts-btn"); const partsModal = document.getElementById("partsModal"); const closeBtn = document.querySelector("#partsModal .close-btn"); @@ -12,14 +33,8 @@ $(document).ready(function () { console.log("Pulsante Parts cliccato"); const iddatadb = $(this).data("iddatadb"); const rowIndex = $(this).data("row"); - const importRef = $("table tbody tr") - .eq(rowIndex) - .find("td") - .eq(1) - .text(); - const description = - $("table tbody tr").eq(rowIndex).find("td").eq(2).text() || - "Sconosciuto"; + const importRef = $("table tbody tr").eq(rowIndex).find("td").eq(1).text(); + const description = $("table tbody tr").eq(rowIndex).find("td").eq(2).text() || "Sconosciuto"; $("#trfHeader").text(`${iddatadb} - ${importRef} - ${description}`); $("#partsModal").data("iddatadb", iddatadb); @@ -36,7 +51,6 @@ $(document).ready(function () { }); }); - // Gestione della chiusura del modal Parts if (closeBtn) { closeBtn.addEventListener("click", function () { partsModal.style.display = "none"; @@ -55,6 +69,9 @@ $(document).ready(function () { }); } + // =================== + // PHOTO LOADERS + // =================== function loadPhoto(iddatadb) { $.ajax({ url: "load_photo.php", @@ -63,10 +80,8 @@ $(document).ready(function () { success: function (response) { if (response.success) { if (response.photos && response.photos.length > 1) { - // Multiple photos available, create a selector showPhotoSelector(response.photos); } else if (response.photos && response.photos.length === 1) { - // Only one photo, load it directly loadSinglePhoto(response.photos[0]); } else { $("#samplePhoto").attr("src", ""); @@ -83,10 +98,9 @@ $(document).ready(function () { } function showPhotoSelector(photos) { - const selectorContainer = $("#photoSelectorContainer"); // A div to hold the photo selector - selectorContainer.empty(); // Clear any previous options + const selectorContainer = $("#photoSelectorContainer"); + selectorContainer.empty(); - // Create a dropdown const selector = $(''); photos.forEach((photo, index) => { const option = $('').val(photo).text(`Photo ${index + 1}`); @@ -101,40 +115,62 @@ $(document).ready(function () { selectorContainer.append(selector); selectorContainer.show(); - // ๐Ÿ‘‰ Load first photo by default if (photos.length > 0) { - selector.val(photos[0]); // set the first option selected - loadSinglePhoto(photos[0]); // actually load it + selector.val(photos[0]); + loadSinglePhoto(photos[0]); } } - function loadSinglePhoto(photoPath) { const img = $("#samplePhoto"); + img.off("load"); // avoid stacking multiple handlers img.attr("src", photoPath); img.on("load", function () { - const container = img.parent(); const canvas = document.getElementById("photoCanvas"); - const containerWidth = container.width(); - const containerHeight = container.height(); - const scaleX = containerWidth / img[0].naturalWidth; - const scaleY = containerHeight / img[0].naturalHeight; - const scale = Math.min(scaleX, scaleY); - - canvas.width = img[0].naturalWidth * scale; - canvas.height = img[0].naturalHeight * scale; - canvas.style.width = `${containerWidth}px`; - canvas.style.height = `${containerHeight}px`; - const ctx = canvas.getContext("2d"); - ctx.clearRect(0, 0, canvas.width, canvas.height); - ctx.drawImage(img.get(0), 0, 0, canvas.width, canvas.height); + + // Real image size + const naturalWidth = img[0].naturalWidth; + const naturalHeight = img[0].naturalHeight; + + // Compute scale to FIT inside its parent without distorting aspect ratio + const parent = $(canvas).parent(); + const maxW = parent.width(); + const maxH = parent.height(); + const scale = Math.min(maxW / naturalWidth, maxH / naturalHeight); + + // Display size on screen + const displayWidth = Math.max(1, Math.round(naturalWidth * scale)); + const displayHeight = Math.max(1, Math.round(naturalHeight * scale)); + + // Save globally + photoData = { naturalWidth, naturalHeight, displayWidth, displayHeight, scale }; + + // Canvas in REAL size (so saving uses natural coords 1:1) + canvas.width = naturalWidth; + canvas.height = naturalHeight; + + // Visual size on screen + canvas.style.width = `${displayWidth}px`; + canvas.style.height = `${displayHeight}px`; + + // Also size/align the overlay containers to match the canvas + $("#markerContainer").css({ width: `${displayWidth}px`, height: `${displayHeight}px` }); + $("#descriptionList").css({ maxWidth: `${Math.max(200, Math.round(displayWidth * 0.35))}px` }); + + // Draw fresh image at full resolution + ctx.clearRect(0, 0, naturalWidth, naturalHeight); + ctx.drawImage(img.get(0), 0, 0, naturalWidth, naturalHeight); updateMarkers(); + if (hasDescriptions) drawDescriptions(descriptionPosition.x, descriptionPosition.y); }); } + // =================== + // PARTS TABLE + // =================== function addNewRow(nextPartNumber, isMix = false) { const description = isMix ? "Mix" : ""; const newRow = ` @@ -148,33 +184,25 @@ $(document).ready(function () { - - `; + `; $("#partsTableBody").append(newRow); updateRowButtons(); } function updateRowButtons() { const rowCount = $("#partsTableBody tr").length; - $("#partsTableBody tr").each(function (index) { + $("#partsTableBody tr").each(function () { const $removeBtn = $(this).find(".remove-row"); - if (rowCount > 1) { - $removeBtn.show(); - } else { - $removeBtn.hide(); - } + if (rowCount > 1) $removeBtn.show(); else $removeBtn.hide(); }); } $(document).on("click", ".add-row", function (e) { e.preventDefault(); - console.log("Pulsante Aggiungi riga cliccato"); const maxPartNumber = Math.max( - ...$("#partsTableBody tr") - .map(function () { - return parseInt($(this).find(".part-number").val()) || 0; - }) - .get(), + ...$("#partsTableBody tr").map(function () { + return parseInt($(this).find(".part-number").val()) || 0; + }).get(), ); addNewRow(maxPartNumber + 1); updatePartsList(); @@ -182,13 +210,10 @@ $(document).ready(function () { $(document).on("click", ".add-mix-row", function (e) { e.preventDefault(); - console.log("Pulsante Aggiungi Mix cliccato"); const maxPartNumber = Math.max( - ...$("#partsTableBody tr") - .map(function () { - return parseInt($(this).find(".part-number").val()) || 0; - }) - .get(), + ...$("#partsTableBody tr").map(function () { + return parseInt($(this).find(".part-number").val()) || 0; + }).get(), ); addNewRow(maxPartNumber + 1, true); updatePartsList(); @@ -196,26 +221,16 @@ $(document).ready(function () { $(document).on("click", ".remove-row", function (e) { e.preventDefault(); - console.log("Pulsante Rimuovi riga cliccato"); const $row = $(this).closest("tr"); const partId = $row.data("part-id"); - console.log("ID parte da eliminare:", partId); if (partId !== "new" && partId !== undefined && partId !== null) { - console.log("Procedo con la cancellazione dal database"); $.ajax({ url: "delete_part.php", method: "POST", data: JSON.stringify({ part_id: partId }), contentType: "application/json", - beforeSend: function () { - console.log( - "Invio richiesta AJAX a delete_part.php con part_id:", - partId, - ); - }, success: function (response) { - console.log("Risposta da delete_part.php:", response); if (response.success) { $row.remove(); updateRowButtons(); @@ -226,21 +241,10 @@ $(document).ready(function () { } }, error: function (xhr, status, error) { - console.log("Errore AJAX:", status, error); - alert( - "Errore nell'eliminazione: " + - error + - ". Stato: " + - xhr.status + - " - " + - xhr.responseText, - ); + alert("Errore nell'eliminazione: " + error + ". Stato: " + xhr.status + " - " + xhr.responseText); }, }); } else { - console.log( - 'Riga non salvata nel database (partId = "new" o non definito), rimuovo solo visivamente', - ); $row.remove(); updateRowButtons(); updatePartsList(); @@ -257,12 +261,6 @@ $(document).ready(function () { const iddatadb = $("#partsModal").data("iddatadb"); const isMix = partDescription.startsWith("Mix") ? "Y" : "N"; - console.log("Evento blur su input:", { - partNumber, - partDescription, - isMix, - }); - if (partDescription && iddatadb) { $saveLoading.show(); $saveStatus.hide(); @@ -285,10 +283,6 @@ $(document).ready(function () { if (response.success) { if (response.part_id) { $row.data("part-id", response.part_id); - console.log( - "Aggiornato partId della riga:", - response.part_id, - ); } $saveLoading.hide(); $saveStatus.show(); @@ -328,8 +322,7 @@ $(document).ready(function () { - - `; + `; $("#partsTableBody").append(newRow); }); } else { @@ -338,10 +331,7 @@ $(document).ready(function () { updateRowButtons(); updatePartsList(); } else { - alert( - "Errore nel caricamento delle parti: " + - response.message, - ); + alert("Errore nel caricamento delle parti: " + response.message); addNewRow(1); } }, @@ -357,11 +347,7 @@ $(document).ready(function () { $("#partsTableBody tr").each(function () { const partNumber = $(this).find(".part-number").val(); const partDescription = $(this).find(".part-description").val(); - if ( - partNumber && - partDescription && - !partDescription.startsWith("Mix") - ) { + if (partNumber && partDescription && !partDescription.startsWith("Mix")) { const listItem = `
  • ${partNumber} - ${partDescription} @@ -374,15 +360,10 @@ $(document).ready(function () { $(document).on("click", ".add-to-mix-btn", function () { const $listItem = $(this).closest("li"); - const partDescription = $listItem.text().split(" - ")[1].trim(); // Prende tutta la descrizione dopo il trattino - const $mixRow = $("#partsTableBody tr") - .filter(function () { - return $(this) - .find(".part-description") - .val() - .startsWith("Mix"); - }) - .last(); + const partDescription = $listItem.text().split(" - ")[1].trim(); + const $mixRow = $("#partsTableBody tr").filter(function () { + return $(this).find(".part-description").val().startsWith("Mix"); + }).last(); if ($mixRow.length === 0) { alert("Crea prima una riga Mix usando il pulsante 'M'."); @@ -397,167 +378,131 @@ $(document).ready(function () { } else if (!currentDescription.includes(partDescription)) { currentDescription += ` + ${partDescription}`; } else { - return; // Parte giร  presente, non aggiungerla + return; } $descriptionInput.val(currentDescription); - $descriptionInput.trigger("blur"); // Attiva il salvataggio + $descriptionInput.trigger("blur"); updatePartsList(); }); - let selectedPartNumber = null; - let markers = []; - let descriptionPosition = { x: 10, y: 10 }; - let hasDescriptions = false; - $("#partsList").on("click", "li", function (e) { if ($(e.target).hasClass("add-to-mix-btn")) return; selectedPartNumber = $(this).data("part-number"); - console.log("Part number selezionato:", selectedPartNumber); $(this).addClass("active").siblings().removeClass("active"); }); + // =================== + // MARKERS & DESCRIPTIONS + // =================== const canvas = document.getElementById("photoCanvas"); const ctx = canvas.getContext("2d"); $("#markerContainer").on("click", function (e) { - console.log("Click sul markerContainer rilevato"); - if (selectedPartNumber !== null) { - const img = $("#samplePhoto"); - const canvas = document.getElementById("photoCanvas"); - const rect = canvas.getBoundingClientRect(); - const container = img.parent(); - const containerWidth = container.width(); - const containerHeight = container.height(); - const scaleX = containerWidth / img.get(0).naturalWidth; - const scaleY = containerHeight / img.get(0).naturalHeight; - const scale = Math.min(scaleX, scaleY); - const x = (e.clientX - rect.left) / scale; - const y = (e.clientY - rect.top) / scale; + if (selectedPartNumber === null) return; - console.log("Coordinate cliccate (x, y):", x, y); + const rect = canvas.getBoundingClientRect(); + const clickX = e.clientX - rect.left; + const clickY = e.clientY - rect.top; - const existingMarker = markers.find( - (m) => m.partNumber == selectedPartNumber, - ); - if (existingMarker) { - existingMarker.x = x; - existingMarker.y = y; - } else { - markers.push({ partNumber: selectedPartNumber, x, y }); - } - console.log("Markers aggiornati:", markers); - updateMarkers(); - if (hasDescriptions) { - drawDescriptions(descriptionPosition.x, descriptionPosition.y); - } - selectedPartNumber = null; - $("#partsList li").removeClass("active"); + const x = clickX / photoData.scale; // convert to NATURAL coords + const y = clickY / photoData.scale; + + const currentPhoto = $("#samplePhoto").attr("src"); + if (!photoMarkers[currentPhoto]) photoMarkers[currentPhoto] = []; + + const existingMarker = photoMarkers[currentPhoto].find(m => m.partNumber == selectedPartNumber); + if (existingMarker) { + existingMarker.x = x; + existingMarker.y = y; } else { - console.log("Nessun part number selezionato"); + photoMarkers[currentPhoto].push({ partNumber: selectedPartNumber, x, y }); } + + updateMarkers(); + if (hasDescriptions) drawDescriptions(descriptionPosition.x, descriptionPosition.y); + + selectedPartNumber = null; + $("#partsList li").removeClass("active"); }); function updateMarkers() { - const img = $("#samplePhoto"); - const container = img.parent(); - const containerWidth = container.width(); - const containerHeight = container.height(); - const scaleX = containerWidth / img.get(0).naturalWidth; - const scaleY = containerHeight / img.get(0).naturalHeight; - const scale = Math.min(scaleX, scaleY); - const markerContainer = $("#markerContainer"); markerContainer.empty(); + // keep overlay sized to canvas display + markerContainer.css({ width: `${photoData.displayWidth}px`, height: `${photoData.displayHeight}px` }); + + const currentPhoto = $("#samplePhoto").attr("src"); + const markers = photoMarkers[currentPhoto] || []; + markers.forEach((marker) => { - const scaledX = marker.x * scale; - const scaledY = marker.y * scale; - console.log( - "Aggiungo marker:", - marker.partNumber, - "a posizione (scaledX, scaledY):", - scaledX, - scaledY, - ); - const $marker = $( - `
    ${marker.partNumber}
    `, - ).css({ + const scaledX = marker.x * photoData.scale; + const scaledY = marker.y * photoData.scale; + + const $marker = $(`
    ${marker.partNumber}
    `).css({ left: scaledX - 8 + "px", top: scaledY - 8 + "px", }); markerContainer.append($marker); - makeDraggable($marker, marker, scale); + makeDraggable($marker, marker); }); } - function makeDraggable($element, item, scale) { + function makeDraggable($element, item) { let isDragging = false; - let currentX = parseFloat($element.css("left")) || 0; - let currentY = parseFloat($element.css("top")) || 0; - let initialX, initialY; + let startLeft = 0; + let startTop = 0; + let initialX = 0; + let initialY = 0; $element.on("mousedown", function (e) { e.preventDefault(); isDragging = true; - initialX = e.clientX - currentX; - initialY = e.clientY - currentY; + startLeft = parseFloat($element.css("left")) || 0; + startTop = parseFloat($element.css("top")) || 0; + initialX = e.clientX - startLeft; + initialY = e.clientY - startTop; $element.css("z-index", 1001); }); - $(document).on("mousemove", function (e) { - if (isDragging) { - e.preventDefault(); - currentX = e.clientX - initialX; - currentY = e.clientY - initialY; - const container = $("#photoCanvas").parent(); - const containerWidth = container.width(); - const containerHeight = container.height(); - const maxX = containerWidth - $element.width(); - const maxY = containerHeight - $element.height(); + $(document).on("mousemove.dragMarker", function (e) { + if (!isDragging) return; + let currentX = e.clientX - initialX; + let currentY = e.clientY - initialY; - currentX = Math.max(0, Math.min(currentX, maxX)); - currentY = Math.max(0, Math.min(currentY, maxY)); + const maxX = photoData.displayWidth - $element.width(); + const maxY = photoData.displayHeight - $element.height(); - $element.css({ - left: currentX + "px", - top: currentY + "px", - }); + currentX = Math.max(0, Math.min(currentX, maxX)); + currentY = Math.max(0, Math.min(currentY, maxY)); - if (item.partNumber) { - item.x = (currentX + 8) / scale; - item.y = (currentY + 8) / scale; - } else { - descriptionPosition.x = (currentX + 5) / scale; - descriptionPosition.y = (currentY + 5) / scale; - } + $element.css({ left: currentX + "px", top: currentY + "px" }); + + if (item && item.partNumber) { + item.x = (currentX + 8) / photoData.scale; + item.y = (currentY + 8) / photoData.scale; + } else { + // draggable description panel + descriptionPosition.x = (currentX + 5) / photoData.scale; + descriptionPosition.y = (currentY + 5) / photoData.scale; } }); - $(document).on("mouseup", function () { + $(document).on("mouseup.dragMarker", function () { + if (!isDragging) return; isDragging = false; $element.css("z-index", 1000); + $(document).off("mousemove.dragMarker mouseup.dragMarker"); }); } function drawDescriptions(x, y) { - const img = $("#samplePhoto"); - const container = img.parent(); - const containerWidth = container.width(); - const containerHeight = container.height(); - const scaleX = containerWidth / img.get(0).naturalWidth; - const scaleY = containerHeight / img.get(0).naturalHeight; - const scale = Math.min(scaleX, scaleY); - const partsList = []; $("#partsTableBody tr").each(function () { const partNumber = $(this).find(".part-number").val(); const partDescription = $(this).find(".part-description").val(); - if ( - partNumber && - partDescription && - !partDescription.startsWith("Mix") - ) { + if (partNumber && partDescription && !partDescription.startsWith("Mix")) { partsList.push(`${partNumber} ${partDescription}`); } }); @@ -566,52 +511,42 @@ $(document).ready(function () { descriptionList.empty(); descriptionList.css({ display: "block", - top: y * scale + "px", - left: x * scale + "px", - width: "200px", - }); - partsList.forEach((part) => { - descriptionList.append(`
    ${part}
    `); + top: y * photoData.scale + "px", + left: x * photoData.scale + "px", }); + partsList.forEach((part) => descriptionList.append(`
    ${part}
    `)); updateMarkers(); } function clearCanvasMarkers() { - markers = []; + const currentPhoto = $("#samplePhoto").attr("src"); + photoMarkers[currentPhoto] = []; hasDescriptions = false; $("#descriptionList").css("display", "none"); $("#markerContainer").empty(); - const canvas = document.getElementById("photoCanvas"); - const img = $("#samplePhoto"); - const ctx = canvas.getContext("2d"); - const container = img.parent(); - const containerWidth = container.width(); - const containerHeight = container.height(); - const scaleX = containerWidth / img.get(0).naturalWidth; - const scaleY = containerHeight / img.get(0).naturalHeight; - const scale = Math.min(scaleX, scaleY); - canvas.width = img.get(0).naturalWidth * scale; - canvas.height = img.get(0).naturalHeight * scale; + const canvas = document.getElementById("photoCanvas"); + const ctx = canvas.getContext("2d"); + + // reset canvas to current image (keeps proportions) + canvas.width = photoData.naturalWidth; + canvas.height = photoData.naturalHeight; + canvas.style.width = `${photoData.displayWidth}px`; + canvas.style.height = `${photoData.displayHeight}px`; + + const img = $("#samplePhoto"); ctx.clearRect(0, 0, canvas.width, canvas.height); - ctx.drawImage(img.get(0), 0, 0, canvas.width, canvas.height); + if (img[0].naturalWidth) { + ctx.drawImage(img.get(0), 0, 0, canvas.width, canvas.height); + } } $("#addDescriptionsBtn").on("click", function () { hasDescriptions = true; descriptionPosition = { x: 10, y: 10 }; drawDescriptions(descriptionPosition.x, descriptionPosition.y); - makeDraggable( - $("#descriptionList"), - descriptionPosition, - Math.min( - $("#photoCanvas").parent().width() / - $("#samplePhoto").get(0).naturalWidth, - $("#photoCanvas").parent().height() / - $("#samplePhoto").get(0).naturalHeight, - ), - ); + makeDraggable($("#descriptionList")); }); $("#removeAnnotationsBtn").on("click", function () { @@ -620,67 +555,90 @@ $(document).ready(function () { $("#savePhotoBtn").on("click", function () { const canvas = document.getElementById("photoCanvas"); - const img = $("#samplePhoto"); const ctx = canvas.getContext("2d"); + const img = $("#samplePhoto"); - canvas.width = img.get(0).naturalWidth; - canvas.height = img.get(0).naturalHeight; - ctx.drawImage(img.get(0), 0, 0); + // Ensure canvas is real size + const naturalWidth = img.get(0).naturalWidth; + const naturalHeight = img.get(0).naturalHeight; + canvas.width = naturalWidth; + canvas.height = naturalHeight; + // Redraw base image + ctx.drawImage(img.get(0), 0, 0, naturalWidth, naturalHeight); + + // Descriptions box const partsList = []; $("#partsTableBody tr").each(function () { const partNumber = $(this).find(".part-number").val(); const partDescription = $(this).find(".part-description").val(); - if ( - partNumber && - partDescription && - !partDescription.startsWith("Mix") - ) { + if (partNumber && partDescription && !partDescription.startsWith("Mix")) { partsList.push(`${partNumber} ${partDescription}`); } }); - if (hasDescriptions) { - ctx.fillStyle = "rgba(255, 255, 255, 0.8)"; - ctx.fillRect( - descriptionPosition.x, - descriptionPosition.y, - 200, - partsList.length * 12 + 10, - ); - ctx.fillStyle = "#000000"; - ctx.font = "10px Arial"; + if (hasDescriptions && partsList.length > 0) { + const fontSize = Math.round(naturalWidth * 0.02); + ctx.font = fontSize + "px Arial"; + const textHeight = fontSize + 8; + const boxWidth = Math.round(naturalWidth * 0.28); + const boxHeight = partsList.length * textHeight + 25; + + const x = descriptionPosition.x; + const y = descriptionPosition.y; + + // แƒฉแƒ แƒ“แƒ˜แƒšแƒ˜ + ctx.save(); + ctx.shadowColor = "rgba(0,0,0,0.3)"; + ctx.shadowBlur = 8; + ctx.shadowOffsetX = 3; + ctx.shadowOffsetY = 3; + + // แƒšแƒแƒ›แƒแƒ–แƒ˜ แƒ‘แƒ”แƒฅแƒ’แƒ แƒแƒฃแƒœแƒ“แƒ˜ + ctx.fillStyle = "rgba(255, 255, 255, 0.9)"; + ctx.beginPath(); + ctx.roundRect(x, y, boxWidth, boxHeight, 12); // ๐ŸŸข Rounded corners + ctx.fill(); + + ctx.restore(); + + // แƒขแƒ”แƒฅแƒกแƒขแƒ˜ + ctx.fillStyle = "#111111"; partsList.forEach((part, index) => { - ctx.fillText( - part, - descriptionPosition.x + 5, - descriptionPosition.y + 12 + index * 12, - ); + ctx.fillText(part, x + 15, y + 35 + index * textHeight); }); } + + // Markers + const currentPhoto = $("#samplePhoto").attr("src"); + const markers = photoMarkers[currentPhoto] || []; markers.forEach((marker) => { + const x = marker.x; // already NATURAL coords + const y = marker.y; + const radius = Math.max(5, Math.round(naturalWidth * 0.025)); + const fontSize = Math.max(8, Math.round(radius * 0.9)); + ctx.beginPath(); - ctx.arc(marker.x, marker.y, 8, 0, 2 * Math.PI); - ctx.fillStyle = "rgba(255, 0, 0, 0.5)"; + ctx.arc(x, y, radius, 0, 2 * Math.PI); + ctx.fillStyle = "rgba(255,0,0,0.85)"; ctx.fill(); - ctx.strokeStyle = "#ff0000"; - ctx.lineWidth = 1; + + ctx.lineWidth = 3; + ctx.strokeStyle = "#ffffff"; ctx.stroke(); + ctx.fillStyle = "#ffffff"; - ctx.font = "bold 8px Arial"; + ctx.font = `bold ${fontSize}px Arial`; ctx.textAlign = "center"; ctx.textBaseline = "middle"; - ctx.fillText(marker.partNumber, marker.x, marker.y); + ctx.fillText(marker.partNumber || "", x, y); }); const dataURL = canvas.toDataURL("image/png"); const timestamp = new Date().toISOString().replace(/[:.]/g, "-"); const defaultName = `photo_${$("#partsModal").data("iddatadb")}_${timestamp}.png`; - const newName = prompt( - "Inserisci il nome del file (senza estensione):", - defaultName.split(".png")[0], - ); + const newName = prompt("Inserisci il nome del file (senza estensione):", defaultName.split(".png")[0]); if (newName) { const finalName = newName + "_" + timestamp + ".png"; $.ajax({ @@ -689,9 +647,7 @@ $(document).ready(function () { data: { dataURL: dataURL, filename: finalName }, success: function (response) { if (response.success) { - alert( - "Foto salvata con successo: " + response.file_path, - ); + alert("Foto salvata con successo: " + response.file_path); } else { alert("Errore nel salvataggio: " + response.message); } @@ -703,11 +659,14 @@ $(document).ready(function () { } }); + // =================== + // DEBUG HOVER LOGS + // =================== $(document).on("mouseenter", "tr", function () { - console.log("Mouse entrato su riga"); + // console.log("Mouse entrato su riga"); }); $(document).on("mouseleave", "tr", function () { - console.log("Mouse uscito da riga"); + // console.log("Mouse uscito da riga"); }); });