Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

WebGLAnimation #105

Open
wants to merge 12 commits into
base: main
Choose a base branch
from
17 changes: 17 additions & 0 deletions src/as/renderers/WebGL2RenderingContext.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
/**
* @author Kara Rawson / [email protected]
*/

import { WebGL2RenderingContext } from "./WebGL2RenderingContext";

/**
* Test class used to verify that we have the WebGL2RenderingContext placeholder
* within GLAS. This will be replaced with the real WebGLRenderingContext class.
*/
describe('Renderers', () => {
test('WebGL2RenderingContext_', (): void => {
var context: WebGL2RenderingContext = new WebGL2RenderingContext()
expect(context.context).toBe(2,
"Make sure we are using version 2.x of WebGL in the 'WebGL2RenderingContext' class")
})
})
27 changes: 27 additions & 0 deletions src/as/renderers/WebGL2RenderingContext.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
/**
* @author Kara Rawson / [email protected]
*/

import { WebGLAnimationFrame } from "./webgl/WebGLAnimation";

/**
* simple placeholder class until we get support with AS web glue which is meant
* to provide access to the underlying context canvas element that exposes the
* GL layer of the browser.
*/
export class WebGL2RenderingContext {
context: i8 = 2 // version placeholder

//// TODO needs ASGLue module to access native context canvas of GL in the browser

// functions or properties required for testing

requestAnimationFrame(animationLoop: WebGLAnimationFrame): void {
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ASWebGLue in fact now provides WebGLRenderingContext (we could add WebGLRenderingContext at some point, but for now I just want to get things running).

For requestAnimationFrame, see https://github.com/trusktr/ecmassembly.

// ...
}
}

/* lib.dom.d.ts -- interface reference from the domlib
interface WebGL2RenderingContext extends WebGL2RenderingContextBase, WebGL2RenderingContextOverloads, WebGLRenderingContextBase {
}
*/
17 changes: 17 additions & 0 deletions src/as/renderers/WebGLRenderingContext.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
/**
* @author Kara Rawson / [email protected]
*/

import { WebGLRenderingContext } from "./WebGLRenderingContext";

/**
* Test class used to verify that we have the WebGLRenderingContext placeholder
* within GLAS. This will be replaced with the real WebGLRenderingContext class.
*/
describe('Renderers', () => {
test('WebGLRenderingContext_', (): void => {
var context: WebGLRenderingContext = new WebGLRenderingContext()
expect(context.context).toBe(1,
"Make sure we are using version 1.x of WebGL in the 'WebGLRenderingContext' class")
})
})
27 changes: 27 additions & 0 deletions src/as/renderers/WebGLRenderingContext.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
/**
* @author Kara Rawson / [email protected]
*/

import { WebGLAnimationFrame } from './webgl/WebGLAnimation'

/**
* simple placeholder class until we get support with AS web glue which is meant
* to provide access to the underlying context canvas element that exposes the
* GL layer of the browser.
*/
export class WebGLRenderingContext {
context: i8 = 1 // version placeholder

//// TODO needs ASGLue module to access native context canvas of GL in the browser

// functions or properties required for testing

requestAnimationFrame(animationLoop: WebGLAnimationFrame): void {
// animationLoop.onAnimationFrame(0,0,animationLoop)
}
}

/* lib.dom.d.ts -- interface reference from the domlib
interface WebGL2RenderingContext extends WebGL2RenderingContextBase, WebGL2RenderingContextOverloads, WebGLRenderingContextBase {
}
*/
2 changes: 2 additions & 0 deletions src/as/renderers/index.spec.ts
Original file line number Diff line number Diff line change
@@ -1 +1,3 @@
import './webgl/index.spec'
import './WebGLRenderingContext.spec'
import './WebGL2RenderingContext.spec'
11 changes: 0 additions & 11 deletions src/as/renderers/webgl/WebGLAnimation.d.ts

This file was deleted.

39 changes: 39 additions & 0 deletions src/as/renderers/webgl/WebGLAnimation.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
/**
* @author Kara Rawson / [email protected]
*/

import { WebGLAnimation } from './WebGLAnimation'
import { WebGLRenderingContext } from "../WebGLRenderingContext";
import { WebGL2RenderingContext } from "../WebGL2RenderingContext";

/**
* @todo make sure we test the WebGLAnimationFrame
*/

describe('Renderers', () => {
describe('WebGL', () => {
describe('WebGLAnimation', () => {
todo('start')
todo('stop')
todo('setAnimationLoop')
todo('WebGlAnimationFrame_callback')
test('setContext', (): void => {
var animation = new WebGLAnimation()
var gl: WebGLRenderingContext = new WebGLRenderingContext()
var gl2: WebGL2RenderingContext = new WebGL2RenderingContext()

animation.setContext(gl, null)

expect(animation.context).not.toBeNull("WebGLRenderingContext should not be null")
expect(animation.context2).toBeNull("WebGL2RenderingContext should be null")
expect(animation.context).toStrictEqual(gl, "WebGLRenderingContext should be type gl")

animation.setContext(null, gl2)

expect(animation.context).toBeNull("WebGLRenderingContext should be null")
expect(animation.context2).not.toBeNull("WebGL2RenderingContext should not be null")
expect(animation.context2).toStrictEqual(gl2, "WebGLRenderingContext should be type gl2")
})
})
})
})
114 changes: 114 additions & 0 deletions src/as/renderers/webgl/WebGLAnimation.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,114 @@
/**
* @author mrdoob / http://mrdoob.com/
* @author Kara Rawson / [email protected]
*/

import { WebGLRenderingContext } from "../WebGLRenderingContext";
import { WebGL2RenderingContext } from "../WebGL2RenderingContext";

/**
* our requestion animation frames root callback function. Recusrively calls itself
* unless isAnimating flag is set to false
*
* @todo this could be optimized to not have an if check.. make two types of animators for gl and gl2
*/
export class WebGLAnimationFrame {

/**
* recursive callback function which is called by the WebGLRenderingContext for gl or gl2
* @param time the current time as an unsigned integer. This could overflow.. really big number
* @param frame the amount of times the gl_scene has rendered within our context
* @param animator the webgl animation class that handles the recursive callback
*/
onAnimationFrame(time: u64, frame: u64, animator: WebGLAnimation): void {
if (!animator.isAnimating) return;

this.onAnimationFrame(time, frame, animator);

if (animator.context) {
animator.context.requestAnimationFrame(animator.animationLoop);
return
}
if (animator.context2) {
animator.context2.requestAnimationFrame(animator.animationLoop);
}
}
}

/**
* a general purpose classes without a constructor for animating geometry within
* GLAS. This class requires explicitly setting either the 'WebGLRenderingContext' or
* 'WebGL2RenderingContext' depending on the version of GL and GLSL you with to use.
*
* NOTE: This is a terribly overloaded term. Animation in this case actually refers to
* the callback function which is passed by reference into the requestAnimationFrame.
* This is a bit confusing with a mesh's animation sequence which is completely different
* uses the same wording.
*/
export class WebGLAnimation {

context: WebGLRenderingContext | null = null
context2: WebGL2RenderingContext | null = null

isAnimating: bool = false
animationLoop: WebGLAnimationFrame = new WebGLAnimationFrame()

/**
* starts our animation loop in gl land
*/
start(): void {

if (this.isAnimating) return
if (this.setAnimationLoop === null) return

if (this.context) {
this.context.requestAnimationFrame(this.animationLoop)
}
else if (!this.context && this.context2) {
this.context2.requestAnimationFrame(this.animationLoop)
}

this.isAnimating = true
}

/**
* stops our animation loop in gl land
*/
stop(): void {
this.isAnimating = false
}

/**
* a recursive call back function that is used to call itself to loop the update of the
* GLAS webgl scene and gl_objects
* @param callback sets our animation frame that is looped. aka animation loop
*/
setAnimationLoop(callback: WebGLAnimationFrame): void {
this.animationLoop = callback
}

/**
* sets our local redering context which is used by our animator that calls rendering animation
* frame recursively
* @param gl version 1 of webgl used by most browsers
* @param gl2 version 2 of webgl which supports additional texture features and custom XR and VR devices
*/
setContext(gl: WebGLRenderingContext | null, gl2: WebGL2RenderingContext | null): void {
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Discriminated union. :)

if (gl) {
this.context = gl
this.context2 = null
return

}
else if (gl2) {
this.context = null
this.context2 = gl2
return
}

/// TODO exception handling not yet supported
//else {
// throw new Exception("webgl or webgl2 must be provided to 'setContext()'")
//}
}
}
2 changes: 1 addition & 1 deletion src/as/renderers/webgl/WebGLShader.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { WebGLShader } from './WebGLShader'

/**
* @see https://tenner-joshua.gitbook.io/as-pect/as-api
* @author Kara Rawson / https://github.com/ZoeDreams
* @author Kara Rawson / rawsonkara@gmail.com
*/

describe('Renderers', (): void => {
Expand Down
11 changes: 9 additions & 2 deletions src/as/renderers/webgl/WebGLShader.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,11 @@
/// THREE.js.r105 ///
/**
* @version 0.0.1
* @author Kara Rawson / https://github.com/ZoeDreams
* @author mrdoob / http://mrdoob.com/
* @author Kara Rawson / rawsonkara@gmail.com
*/

import { WebGLRenderingContext } from "../WebGLRenderingContext";

/**
* A lower level function to compile either a vertex or fragment shader.
*
Expand All @@ -14,9 +16,14 @@
* @see https://threejs.org/docs/#api/en/renderers/webgl/WebGLShader
*
* @todo Update WebGLShader.spec.ts test when we figure out how to load the ctx by as-pect
* @todo need to add gl2 argument. must be strong typed -- no unions
* @todo need to create wrapper class for webglshader
*/

export function WebGLShader(gl: WebGLRenderingContext, type: number, source: string): WebGLShader {

/// TODO implement WebGLShader_ placeholder library in the renderer root.

var shader: WebGLShader = gl.createShader(type)
gl.shaderSource(shader, source)
gl.compileShader(shader)
Expand Down
1 change: 1 addition & 0 deletions src/as/renderers/webgl/index.spec.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import './WebGLAnimation.spec'
import './WebGLLights.spec'
import './WebGLProperties.spec'
import './WebGLRenderLists.spec'
Expand Down