use cgmath::Euler;
use glow::NativeProgram;
use nalgebra_glm::{look_at, Mat4x4, Vec3};
use std::num::NonZeroU32;

#[derive(Clone)]
pub(crate) struct Camera {
    pos: Vec3,
    upward: Vec3,
    front: Vec3,
}

pub type CameraPositon = Vec3;

impl Camera {
    pub(crate) fn new(world_loc: CameraPositon, upward: Vec3, front: Vec3) -> Self {
        Self {
            pos: world_loc,
            upward,
            front,
        }
    }

    pub fn get_position(&self) -> CameraPositon {
        self.pos
    }

    pub fn set_position(&mut self, pos: CameraPositon) {
        self.pos = pos;
    }

    pub fn get_front(&self) -> Vec3 {
        self.front
    }

    pub fn set_front(&mut self, front: Vec3) {
        self.front = front;
    }

    pub fn get_upward(&self) -> Vec3 {
        self.upward
    }

    pub fn set_upward(&mut self, upward: Vec3) {
        self.upward = upward;
    }

    pub fn get_view_matrix(&self) -> Mat4x4 {
        let l = self.pos + self.front;
        look_at(&l, &self.pos, &self.upward)
    }
}

impl Default for Camera {
    fn default() -> Self {
        Self {
            pos: Vec3::new(0.0, 0.0, 0.0),
            upward: Vec3::new(0.0, 1.0, 0.0),
            front: Vec3::new(0.0, 0.0, -1.0),
        }
    }
}
