Canvas 3d JS Library

WebGL made easy!
  • rss
  • What is C3DL?
  • Download
  • Tutorials
    • Tutorial #1: WebGL Browsers
    • Tutorial #2: A simple scene
    • Tutorial #3: Callback
    • Tutorial #4: Models
    • Tutorial #5: Light effects
    • Tutorial #6: Picking
    • Tutorial #7: Materials
    • Tutorial #8: Particle Systems
    • Tutorial #9: Camera Basics
    • Tutorial #10: Advanced FreeCamera
    • Tutorial #11: OrbitCamera
    • Tutorial #12: Advanced Camera Functions
  • Development News
  • Documentation
  • Community
  • Resources
  • Contact
  • About

User Defined Shaders

Andor Salga | 14 July, 2009 | 13:06
We are adding a feature to the library which will allow users to create their own vertex and fragment shaders, compile them and then assign them to geometry. While trying to solve how this can be done, I realized the problem is actually much more complex than I initially anticipated. While working on the requirements, I kept stumbling into different issues. Instead of trying to analyze each of these issues in a lengthy blog, I decided to tackle each one separately.

Let’s begin with a use case. A user has a model of a person, which is actually composed of separate parts or “primitive sets”. We know this because we know the internal structure of the .DAE file. If the user does not know the structure of the file, they would be limited to assigning their shader to the entire object rather than portions of it. Let’s say the user knows the structure and needs to render the following primitive sets:
  • Shoes rendered with a cel shader
  • Shirt rendered with a sepia shader
  • Everything else with a scanline shader
The example is not realistic, but demonstrates the flexibility which must be available. I will use the term “effect” to describe both vertex and fragment shaders together. In OpenGL it is called a “program object”.

From the use case, it can be seen the main requirements are:
  • Must allow the user to specify shader code to create an effect.
  • Must allow user to assign effect to entire object, node, geometry or primitive set of a collada object.
To achieve this result, the user would first have to write the vertex and fragment shaders for each effect desired. The simplest and most flexible method to accept shaders would be as strings. Both vertex and fragment shaders would be required and no ‘default’ shaders would exist. The user would then have to somehow compile and link the shaders. Allowing the user to store the shaders somewhere and compile them is trivial and will be addressed a bit later.

Assume an effect object was created from the shaders. The user assigned the effect to part of the Collada object, but how will the uniform and attribute variables be set in the shaders? The library must somehow provide a mechanism for the user to pass data from their script to the library which in turn is sent to the shaders. Furthermore, to achieve some effects like the outline for cel shading, the logic isn’t part of the shader code at all, it’s part of the application. I first came up with the idea of creating an object which can have parameters added to it and when instantiated, must have those parameters filled and would be sent to the renderer. The solution didn’t address the cel shading outline problem and seemed a bit awkward. I had some other ideas, but none of them seemed clean enough to actually implement. I then came up with a simple solution: allow the user to provide a callback function. Since the user wrote the shader, they also know all the uniform and attribute variables which must be set. They would be able to set the variables and perform any other logic needed to create the desired effect in the callback. This technique does expose the user to the graphics context, but if the user is writing a shader, it can be assumed they have experience with OpenGL commands. To curb any confusion which may arise, tutorials, references and helper functions will be provided to aid users in writing their callbacks.

Creating an effect now involves the user specifying the shaders as strings as well as an appropriate callback. These objects can be encapsulated in an effect instance and then passed to a collada object, node, primitive set, etc. When the geometry is rendered, the renderer will detect it has a user defined effect and call the user’s callback. The user’s code will be responsible for switching to use their program object, setting the shader variables and perform any other logic needed to accomplish the rendering effect.

As mentioned earlier, this only solves one problem and many other small problems must still be addressed.
Categories
c3dl development
Comments rss
Comments rss
Trackback
Trackback

« Orbit Camera User Defined Shaders: Textures »

Leave a comment

You can use these tags : <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>

Videos

Demos

  • Asteroids-3D
  • RTS Prototype
  • Particle Systems Demo
  • Cross-Browser Orbiter
  • Mocap Demo With Spheres
  • Google Maps-3D

C3DL Development News

A spec change that keeps coming back to haunt me

At some point, the way firefox handles keyboard events changed. I’m not sure exactly when it happened, all I know is that it broke how I was dealing with keyboard interaction on almost every demo I’ve written (for example,the mocap demo and MotionView). When I wrote the demos, the keydown event would be fired once, [...]

Release 2.2

The 2.2 Release of the Canvas 3D Library includes a number of new features, updates to old features and fixes for several bugs along with the requisite changes to meet the evolving WebGL spec. Some of the things included (in no particular order) are: Better picking code. The ability to swap textures as a scene [...]

Tutorials

  • Tutorial #1: WebGL Browsers
  • Tutorial #2: A simple scene
  • Tutorial #3: Callback
  • Tutorial #4: Models
  • Tutorial #5: Light effects
  • Tutorial #6: Picking
  • Tutorial #7: Materials
  • Tutorial #8: Particle Systems
  • Tutorial #9: Camera Basics
    • Tutorial9-YawPitchRoll
  • Tutorial #10: Advanced FreeCamera
  • Tutorial #11: OrbitCamera
  • Tutorial #12: Advanced Camera Functions

Documentation

Archives

Archives

C3DL Development News

Recent Comments

  • June 2011
  • March 2011
  • October 2010
  • July 2010
  • April 2010
  • March 2010
  • February 2010
  • January 2010
  • December 2009
  • November 2009
  • October 2009
  • September 2009
  • July 2009
  • June 2009
  • May 2009
  • April 2009
  • March 2009
  • February 2009
  • January 2009
  • December 2008
  • November 2008
  • October 2008
  • September 2008
  • August 2008
  • July 2008
  • June 2008
  • May 2008
  • April 2008
  • March 2008
  • February 2008
  • January 2008
  • December 2007
  • A spec change that keeps coming back to haunt me
  • Release 2.2
  • 2.1 Release and things to come
  • Level Up! An Open Web Game Jam
  • Site moved!
  • SceneCreator0.3
  • WWW2010 in Raleigh
  • Motionview
  • On the train to Mountainview
  • C3DL 2.0-WebGL and beyond
  • That depends on what... - peter
  • This application is ... - Haisens
  • I think that example... - peter
  • The above links are ... - Atash
  • Hi there, just wante... - Patrick H. Lauke
  • Firefox 4 was releas... - Cathy Leung
  • In order to access l... - peter
  • I am not able to dis... - preksha
  • "JavaScript can’t di... - Joe Hocking
  • I should point out t... - peter



Canvas 3d JS Library

©2007- 2010 Canvas 3d JS Library

Disclaimer: This website is licensed under a Creative Commons Attribution-Noncommercial-Share Alike 2.5 Canada License.
The Canvas 3d JS Library and Demos found on this website are licenced under the MIT License

Creative Commons License