import * as THREE from 'three';
import * as Types from '../../../../types/world/worldTypes';
import * as CONSTANTS from '../../../../types/world/worldConstants';

export default async function addAisleToScene(
    aisle: Types.Line,
    floorGroupAisle: Types.RefGroup,
): Promise<void> {
    if (aisle.length >= 2 && aisle[0] && aisle[1]) {
        const start: Types.Vector3 = aisle[0][0];
        const end: Types.Vector3 = aisle[1][0];

        const direction = new THREE.Vector3(
            end.x - start.x,
            end.y - start.y,
            end.z - start.z
        ).normalize();

        const perp = new THREE.Vector3(-direction.z, 0, direction.x).normalize();
        const offsetDistance = CONSTANTS.aisleConfig.width;

        const leftStart = new THREE.Vector3().copy(start).addScaledVector(perp, offsetDistance);
        const rightStart = new THREE.Vector3().copy(start).addScaledVector(perp, -offsetDistance);
        const leftEnd = new THREE.Vector3().copy(end).addScaledVector(perp, offsetDistance);
        const rightEnd = new THREE.Vector3().copy(end).addScaledVector(perp, -offsetDistance);

        const stripShape = new THREE.Shape();
        stripShape.moveTo(leftStart.x, leftStart.z);
        stripShape.lineTo(leftEnd.x, leftEnd.z);
        stripShape.lineTo(rightEnd.x, rightEnd.z);
        stripShape.lineTo(rightStart.x, rightStart.z);
        stripShape.lineTo(leftStart.x, leftStart.z);

        const extrudeSettings = {
            depth: CONSTANTS.aisleConfig.height,
            bevelEnabled: false,
        };

        const stripGeometry = new THREE.ExtrudeGeometry(stripShape, extrudeSettings);
        const stripMaterial = new THREE.MeshStandardMaterial({
            color: CONSTANTS.aisleConfig.defaultColor, 
            polygonOffset: true,
            polygonOffsetFactor: -1,
            polygonOffsetUnits: -1,
        });

        const stripMesh = new THREE.Mesh(stripGeometry, stripMaterial);
        stripMesh.receiveShadow = true;
        stripMesh.castShadow = true;

        stripMesh.position.y = (aisle[0][2] - 1) * CONSTANTS.wallConfig.height + 0.01;
        stripMesh.rotateX(Math.PI / 2);

        floorGroupAisle.current.add(stripMesh);
    }
}
