sean_s

Untitled

Aug 24th, 2023
110
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. import Matrix from './matrix';
  2. import Vector from './vector';
  3.  
  4. // Refer to https://developer.mozilla.org/de/docs/Web/API/WebGL_API/Tutorial/Hinzuf%C3%BCgen_von_2D_Inhalten_in_einen_WebGL-Kontext
  5. /**
  6.  * Class to assemble a Shader to use with WebGL
  7.  */
  8. export default class Shader {
  9.   /**
  10.    * The WebGL program consisting of the
  11.    * vertex shader and the fragment shader
  12.    */
  13.   shaderProgram: WebGLProgram;
  14.  
  15.   /**
  16.    * Creates a shader
  17.    * @param gl The 3D context
  18.    * @param vertexShaderSource The vertex shader source code
  19.    * @param fragmentShaderSource The fragment shader source code
  20.    */
  21.   constructor(
  22.     private gl: WebGL2RenderingContext,
  23.     private vertexShaderSource: string,
  24.     private fragmentShaderSource: string) {
  25.    
  26.       const vertexShader = this.getShader(gl, vertexShaderSource, gl.VERTEX_SHADER);
  27.       const fragmentShader = this.getShader(gl, fragmentShaderSource, gl.FRAGMENT_SHADER);
  28.  
  29.       // Create the shader program
  30.       const shaderProgram = gl.createProgram();
  31.       gl.attachShader(shaderProgram, vertexShader);
  32.       gl.attachShader(shaderProgram, fragmentShader);
  33.       gl.linkProgram(shaderProgram);
  34.  
  35.       // If creating the shader program failed, alert
  36.       if (!gl.getProgramParameter(shaderProgram, gl.LINK_STATUS)) {
  37.         alert("Unable to initialize the shader program: " + gl.getProgramInfoLog(shaderProgram));
  38.       }
  39.  
  40.       // Store the shader program for future use
  41.       this.shaderProgram = shaderProgram;
  42.  
  43.   }
  44.  
  45.   /**
  46.    * Use this shader program for the next
  47.    * WebGL calls
  48.    */
  49.   use() {
  50.     this.gl.useProgram(this.shaderProgram);
  51.   }
  52.  
  53.   /**
  54.    * Returns the attribute location of a variable in the shader program
  55.    * @param  {string} name - The name of the variable
  56.    * @return {number}        The variable's location
  57.    */
  58.   getAttributeLocation(name: string): number {
  59.     const attr = this.gl.getAttribLocation(this.shaderProgram, name);
  60.  
  61.     if (attr != -1) {
  62.       this.gl.enableVertexAttribArray(attr);
  63.     }
  64.     return attr;
  65.   }
  66.  
  67.   /**
  68.    * Loads a shader part from its script DOM node and compiles it
  69.    * @param gl The 3D context
  70.    * @param source The source code
  71.    * @return The resulting shader part
  72.    */
  73.   getShader(gl: WebGL2RenderingContext, source: string, type: number): WebGLShader {
  74.     const shader = gl.createShader(type);
  75.     // Send the source to the shader object
  76.     gl.shaderSource(shader, source);
  77.     // Compile the shader program
  78.     gl.compileShader(shader);
  79.  
  80.     // See if it compiled successfully
  81.     if (!gl.getShaderParameter(shader, gl.COMPILE_STATUS)) {
  82.       alert("An error occurred compiling the shaders: " + gl.getShaderInfoLog(shader));
  83.       return null;
  84.     }
  85.     return shader;
  86.   }
  87.  
  88.   /**
  89.    * Returns an object that can be used to set a matrix on the GPU
  90.    * @param name The name of the uniform to set
  91.    * @return The resulting object
  92.    */
  93.   getUniformMatrix(name: string): UniformMatrix {
  94.     return new UniformMatrix(this.gl,
  95.       this.gl.getUniformLocation(this.shaderProgram, name)
  96.     );
  97.   }
  98.  
  99.   /**
  100.    * Returns an object that can be used to set a vector on the GPU
  101.    * @param name The name of the uniform to set
  102.    * @return The resulting object
  103.    */
  104.   getUniformVec3(name: string): UniformVec3 {
  105.     return new UniformVec3(this.gl,
  106.       this.gl.getUniformLocation(this.shaderProgram, name)
  107.     );
  108.   }
  109.  
  110.   getUniformVec3Array(name: string): UniformVec3Array{
  111.     return new UniformVec3Array(this.gl, this.gl.getUniformLocation(this.shaderProgram, name)
  112.     );
  113.   }
  114.  
  115.  
  116.   /**
  117.    * Returns an object that can be used to set a vector on the GPU
  118.    * @param name The name of the uniform to set
  119.    * @return The resulting object
  120.    */
  121.   getUniformVec4(name: string): UniformVec4 {
  122.     return new UniformVec4(this.gl,
  123.       this.gl.getUniformLocation(this.shaderProgram, name)
  124.     );
  125.   }
  126.  
  127.   getUniformVec4Array(name: string): UniformVec4Array{
  128.     return new UniformVec4Array(this.gl, this.gl.getUniformLocation(this.shaderProgram, name)
  129.     );
  130.   }
  131.  
  132.   /**
  133.    * Returns an object that can be used to set an int on the GPU
  134.    * @param name The name of the uniform to set
  135.    * @return The resulting object
  136.    */
  137.   getUniformFloat(name: string): UniformFloat {
  138.     return new UniformFloat(this.gl,
  139.       this.gl.getUniformLocation(this.shaderProgram, name)
  140.     );
  141.   }
  142.  
  143.   /**
  144.    * Returns an object that can be used to set an int on the GPU
  145.    * @param name The name of the uniform to set
  146.    * @return The resulting object
  147.    */
  148.   getUniformInt(name: string): UniformInt {
  149.     return new UniformInt(this.gl,
  150.       this.gl.getUniformLocation(this.shaderProgram, name)
  151.     );
  152.   }
  153. }
  154.  
  155. /**
  156.  * Handler class to set uniform matrices
  157.  * in the shader program
  158.  */
  159. class UniformMatrix {
  160.   constructor(
  161.     private gl: WebGL2RenderingContext,
  162.     private position: WebGLUniformLocation
  163.   ) { }
  164.  
  165.   /**
  166.    * Sends the given matrix to the GPU
  167.    * @param matrix The matrix to send
  168.    */
  169.   set(matrix: Matrix) {
  170.     this.gl.uniformMatrix4fv(
  171.       this.position,
  172.       false,
  173.       matrix.data);
  174.   }
  175. }
  176.  
  177. /**
  178.  * Handler class to set uniform vectors
  179.  * in the shader program
  180.  */
  181. class UniformVec3 {
  182.   constructor(
  183.     private gl: WebGL2RenderingContext,
  184.     private position: WebGLUniformLocation
  185.   ) { }
  186.  
  187.   /**
  188.    * Sends the given vector to the GPU as 3dimensional vector
  189.    * @param vec The vector to send
  190.    */
  191.   set(vec: Vector) {
  192.     this.gl.uniform3f(
  193.       this.position, vec.x, vec.y, vec.z
  194.     );
  195.   }
  196. }
  197.  
  198. /**
  199.  * Handler class to set array of uniform vectors
  200.  * in the shader program
  201.  */
  202. class UniformVec3Array {
  203.   private content: UniformVec3[];
  204.   constructor(
  205.     private gl: WebGL2RenderingContext,
  206.     private position: WebGLUniformLocation
  207.    
  208.   ) { }
  209.  
  210.   /**
  211.    * Sends the given vector to the GPU as 3dimensional vector
  212.    * @param vecs The vectors to send in an array
  213.    */
  214.   set(vecs: Array<Vector>) {
  215.     var data = new Float32Array(24);
  216.  
  217.     for (var i = 0; i < vecs.length; i++){
  218.       let vec = vecs[i];
  219.       data[i*3+0] = vec.x;
  220.       data[i*3+1] = vec.y;
  221.       data[i*3+2] = vec.z;
  222.     }
  223.     this.gl.uniform3fv(this.position, data);
  224.   }
  225. }
  226. ////////////////
  227.  
  228.  
  229. /**
  230.  * Handler class to set uniform vectors
  231.  * in the shader program
  232.  */
  233. class UniformVec4 {
  234.   constructor(
  235.     private gl: WebGL2RenderingContext,
  236.     private position: WebGLUniformLocation
  237.   ) { }
  238.  
  239.   /**
  240.    * Sends the given vector to the GPU as 3dimensional vector
  241.    * @param vec The vector to send
  242.    */
  243.   set(vec: Vector) {
  244.     this.gl.uniform4f(
  245.       this.position, vec.x, vec.y, vec.z, vec.w
  246.     );
  247.   }
  248. }
  249.  
  250. /**
  251.  * Handler class to set array of uniform vectors
  252.  * in the shader program
  253.  */
  254. class UniformVec4Array {
  255.   private content: UniformVec4[];
  256.   constructor(
  257.     private gl: WebGL2RenderingContext,
  258.     private position: WebGLUniformLocation
  259.    
  260.   ) { }
  261.  
  262.   /**
  263.    * Sends the given vector to the GPU as 3dimensional vector
  264.    * @param vecs The vectors to send in an array
  265.    */
  266.   set(vecs: Array<Vector>) {
  267.     var data = new Float32Array(32);
  268.  
  269.     for (var i = 0; i < vecs.length; i++){
  270.       let vec = vecs[i];
  271.       data[i*3+0] = vec.x;
  272.       data[i*3+1] = vec.y;
  273.       data[i*3+2] = vec.z;
  274.       data[i*3+3] = vec.w;
  275.     }
  276.     this.gl.uniform3fv(this.position, data);
  277.   }
  278. }
  279.  
  280. /////////////////
  281.  
  282. /**
  283.  * Handler class to set uniform floats
  284.  * in the shader program
  285.  */
  286. class UniformFloat {
  287.   constructor(
  288.     private gl: WebGL2RenderingContext,
  289.     private position: WebGLUniformLocation
  290.   ) { }
  291.  
  292.   /**
  293.    * Sends the given float value to the GPU
  294.    * @param value The float value to send
  295.    */
  296.   set(value: number) {
  297.     this.gl.uniform1f(this.position, value);
  298.   }
  299. }
  300.  
  301. /**
  302.  * Handler class to set uniform ints
  303.  * in the shader program
  304.  */
  305. class UniformInt {
  306.   constructor(
  307.     private gl: WebGL2RenderingContext,
  308.     private position: WebGLUniformLocation
  309.   ) { }
  310.  
  311.   /**
  312.    * Sends the given int value to the GPU
  313.    * @param value The int value to send
  314.    */
  315.   set(value: number) {
  316.     this.gl.uniform1i(this.position, value);
  317.   }
  318. }
  319.  
Advertisement
Add Comment
Please, Sign In to add comment