import { Color } from "../filler/common";
import { fillRectangle } from "./2d"
import { LayerAB, Scene } from "./Scene"
import { createProgram, createShader } from "./utils"




export class BoxLayer extends LayerAB {


  private vertexShaderCode = /*glsl*/ `
    attribute vec2 a_position;
    uniform mat4 u_matrix;

    void main() {
      gl_Position = u_matrix * vec4(a_position, 0, 1);
    }

  `;

  private fragmentShaderCode = /*glsl*/ `
    precision mediump float;
    uniform vec4 u_color;

    void main() {
      gl_FragColor = u_color;
    }
  
  `

  program: WebGLProgram


  aPositionLoc: number
  uMatrixLoc: WebGLUniformLocation
  uColorLoc: WebGLUniformLocation

  vertexBuffer: WebGLBuffer

  vertexArray = new Float32Array(12)

  colorArray: Float32Array

  constructor(
    public readonly scene: Scene,
    public readonly x: number,
    public readonly y: number,
    public readonly width: number,
    public readonly height: number,
    public readonly color: number = 0xffffffff,  //abgr
    private fragmentShader: string | null = null
  ) {
    super()

    const gl = scene.gl;


    this.program = createProgram(gl,
      createShader(gl, gl.VERTEX_SHADER, this.vertexShaderCode)!,
      createShader(gl, gl.FRAGMENT_SHADER, fragmentShader || this.fragmentShaderCode)!)!

    this.aPositionLoc = gl.getAttribLocation(this.program, "a_position")
    this.uMatrixLoc = gl.getUniformLocation(this.program, "u_matrix")!
    this.uColorLoc = gl.getUniformLocation(this.program, "u_color")!


    fillRectangle(this.vertexArray, 0, x, y, width, height)


    this.vertexBuffer = gl.createBuffer()!;
    gl.bindBuffer(gl.ARRAY_BUFFER, this.vertexBuffer);
    gl.bufferData(gl.ARRAY_BUFFER, this.vertexArray, gl.STATIC_DRAW);

    this.colorArray = new Color(color).toFloatArray()

  }


  override draw() {
    const gl = this.scene.gl;
    gl.useProgram(this.program);

    gl.enableVertexAttribArray(this.aPositionLoc);
    gl.bindBuffer(gl.ARRAY_BUFFER, this.vertexBuffer);
    gl.vertexAttribPointer(this.aPositionLoc, 2, gl.FLOAT, false, 0, 0)


    gl.uniformMatrix4fv(this.uMatrixLoc, false, this.scene.drawMatrix)
    gl.uniform4fv(this.uColorLoc, this.colorArray)

    gl.drawArrays(gl.TRIANGLES, 0, 6);

  }



  toString(): string {
    return `BoxLayer()`
  }

}




