const video = document.getElementById("video");
const info  = document.getElementById("info");

let processing=false;
let alreadyCaptured = false;
let lastDetection = null;

//let lastColor="red";
let lastName = "Menunggu wajah...";
let lastColor = "#ffffff";
let name = "UNKNOWN";
let color = "#ff0000"; // default MERAH
const btnAbsen   = document.getElementById("btnAbsen");

/* ===== CUSTOM ROUNDED BOX ===== */

function drawRoundedRect(ctx, x, y, width, height, radius, color) {
    ctx.strokeStyle = color;
    ctx.lineWidth = 3;

    ctx.beginPath();
    ctx.moveTo(x + radius, y);
    ctx.lineTo(x + width - radius, y);
    ctx.quadraticCurveTo(x + width, y, x + width, y + radius);
    ctx.lineTo(x + width, y + height - radius);
    ctx.quadraticCurveTo(x + width, y + height, x + width - radius, y + height);
    ctx.lineTo(x + radius, y + height);
    ctx.quadraticCurveTo(x, y + height, x, y + height - radius);
    ctx.lineTo(x, y + radius);
    ctx.quadraticCurveTo(x, y, x + radius, y);
    ctx.closePath();
    ctx.stroke();
}

function absen_recognition(latitude, radius, radius_aktif, tipe, hak_akses) {

if (tipe == 'masuk') {
    var action = '../'+hak_akses+'/module/absen-in/sw-proses.php?action=absen-recognition';
} else {
    var action = '../'+hak_akses+'/module/absen-out/sw-proses.php?action=absen-recognition';
}

/* ================= LOAD MODEL ================= */
const MODEL_URL = "../template/vendor/webcame/models";
async function loadModels(){
 await faceapi.nets.tinyFaceDetector.loadFromUri(MODEL_URL); // LEBIH CEPAT
 await faceapi.nets.faceLandmark68Net.loadFromUri(MODEL_URL);
 await faceapi.nets.faceRecognitionNet.loadFromUri(MODEL_URL);
 startCamera();
}

function startCamera(){

    const isMobile = /Android|iPhone|iPad/i.test(navigator.userAgent);
    let constraints;
    if (isMobile) {
    // Mode portrait HP
    constraints = {
        video: {
            width: { ideal: 360 },
            height: { ideal: 480 },
            facingMode: "user"
        }
    };
    } else {
        // Mode PC normal
        constraints = {
            video: {
            width: { ideal: 640 },
            height: { ideal: 480 }
            }
        };
    }

    navigator.mediaDevices.getUserMedia(constraints)
    .then(stream => {
        video.srcObject = stream;
    });
}

/* ================= TRACKING ================= */
video.addEventListener("loadedmetadata",()=>{

  video.width  = video.videoWidth;
  video.height = video.videoHeight;

  const canvas = faceapi.createCanvasFromMedia(video);
  document.querySelector(".canvas-box").append(canvas);

  const displaySize = {
    width: video.videoWidth,
    height: video.videoHeight
  };

  faceapi.matchDimensions(canvas, displaySize);

  setInterval(async()=>{

    const detections =
    await faceapi.detectAllFaces(
        video,
        new faceapi.TinyFaceDetectorOptions({
            inputSize:320,
            scoreThreshold:0.5
        })
    )
    .withFaceLandmarks()
    .withFaceDescriptors();

    const resized =
    faceapi.resizeResults(detections,displaySize);

    const ctx = canvas.getContext("2d");
    ctx.clearRect(0,0,canvas.width,canvas.height);

    resized.forEach(async(det)=>{

        const box = det.detection.box;
        /* ===== DRAW ROUNDED BOX ===== */
        drawRoundedRect(
            ctx,
            box.x,
            box.y,
            box.width,
            box.height,
            20,
            color
        );

        /* ===== NAMA DENGAN BACKGROUND ===== */
        ctx.font = "15px Arial";
        ctx.textAlign = "center";
        ctx.textBaseline = "middle";
        const text = lastName;
        // ukur lebar teks
        const textWidth = ctx.measureText(text).width;
        const paddingX = 15;
        const paddingY = 6;
        const textX = box.x + box.width / 2;
        const textY = box.y - 18;

        // background rectangle
        ctx.fillStyle = color; // hijau jika match, merah jika unknown
        ctx.beginPath();
        ctx.roundRect(
            textX - textWidth/2 - paddingX,
            textY - paddingY,
            textWidth + paddingX*2,
            28,
            8
        );
        ctx.fill();

        // teks putih di atas background
        ctx.fillStyle = "#ffffff";
        ctx.fillText(text, textX, textY + 8);

      /* ===== RECOGNITION ===== */

      if(!processing){

        processing=true;
        const res = await fetch("../"+hak_akses+"/module/absen-in/sw-proses.php?action=cek-wajah",{
          method:"POST",
          body:JSON.stringify({
            descriptor:Array.from(det.descriptor)
          })
        });

        const data = await res.json();
            if(data.status==="match" && !alreadyCaptured){
                alreadyCaptured = true;
                lastName = data.nama + " ✓";
                lastColor = "#00ff00";
                color = "#00e676";
                btnAbsen.disabled = false;
                lastDetection = det;

                btnAbsen.addEventListener("click", async () => {
                    await captureAndSend(lastDetection);
                });

            } else if(!alreadyCaptured){
                lastName = "Wajah tidak dikenal";
                lastColor = "#ff0000";
                color = "#ff1744";
                btnAbsen.disabled = true;
            }

            setTimeout(()=>{
                processing=false;
                //lastName="Menunggu wajah...";
                lastColor="#ffffff";
            },2000);
        }

        

        function videoToImage(){
            const captureCanvas = document.createElement("canvas");
            captureCanvas.width = video.videoWidth;
            captureCanvas.height = video.videoHeight;

            const ctx = captureCanvas.getContext("2d");
            ctx.drawImage(video, 0, 0);

            return captureCanvas.toDataURL("image/jpeg", 0.7);
        }

        if(alreadyCaptured) return;
        async function captureAndSend(res){
            try {
                const response = await fetch("" + action + "", {
                    method: "POST",
                    headers: {
                        "Content-Type": "application/json"
                    },
                    body: JSON.stringify({
                        descriptor: Array.from(res.descriptor),
                        photo: videoToImage(),
                        latitude: latitude,
                        radius: radius,
                        radius_aktif: radius_aktif,
                    })
                });

                const text = await response.text();
                let r;
                try {
                    r = JSON.parse(text);
                } catch (e) {
                    throw new Error(text);
                }

                if (r.status === true) {

                    swal({
                        title: "Berhasil",
                        text: r.msg,
                        icon: "success",
                        button: "OK"
                    });

                } else {

                    swal({
                        title: "Gagal",
                        text: r.msg + (r.error ? "\n" + JSON.stringify(r.error) : ""),
                        icon: "error",
                        button: "OK"
                    });
                }

                //setTimeout(() => location.href = './', 3000);

            } catch (err) {

                swal({
                    title: "Server Error",
                    text: err.message.substring(0, 300),
                    icon: "error",
                    button: "OK"
                });

                console.error("SERVER ERROR:", err.message);
            }
        }

    });

  },300);

});

loadModels();
}