https://github.com/CIS-566-2018/homework-2-ray-marching-implicit-surfaces
- Name: Mauricio Mutai
- PennKey:
mmutai
- Click below for the live demo! (Autoplays audio!)
- You will note the program plays an audio file. This shader is inspired by the rhythm game Rhythm Heaven, released for the Nintendo DS. In particular, I tried to re-create the mini-game "Built to Scale", which you can see on this video.
- The animations are supposed to play in sync with the audio, similar to what happens in the video. It works okay (not perfectly) when running on my own machine, but there are issues with the version up on Github pages, for some reason.
- The bulk of this project was developed based on IQ's publications about ray-marching SDFs. In particular, I made use of many SDFs published by him.
- The green blocks are created with a combination of domain repetition, intersection, and subtraction of a cube primitive. The cube is repeated on a grid, and then intersected with a scaled cube to create a rectangular subset of this grid. Other sections of this subset are subtracted away in order to create the staircase effect.
- The blocks are slightly smaller than the grid dimensions. This gives the illusion of "edges" on the grid, without requiring textures or similar methods.
- The white squares with holes are made from a scaled cube, from which a cylinder is subtracted.
- The contraption that shoots the cylinders is made from the addition of two "capped cylinders", a sphere, and a scaled cube. Note I avoided the smooth blend on purpose to give this a more mechanical look.
- The animations are achieved by rotating, translating, and scaling the point used to sample each SDF accordingly. I developed an overly-complicated method of parametrizing these animations that led to the use of several uniform time variables in the shader.
- Small note: the pieces with holes on them fly off into the distance. This is due to a dilemma I had when deciding what to do with the pieces, since the game does not show what happens to them at the end of the "production line". I chose the simplest solution of just making them fly off into the distance, since this is technically something that could happen in-game (it's just that the player would never see it), and I thought it was entertaining.
- Animating the white squares with holes was a pretty challenging task.
- Ambient occlusion is computed using IQ's "5-tap" method explained in the external resource linked below.
- A sub-surface scattering approximation is computed using a combination of IQ's AO method and the ideas presented in this GDC presentation.
- A moving light was added in hopes of making this effect more clear.
- A couple of control options are available:
renderMode: You can choose between applying only ambient occlusion (AO), only sub-surface scattering (SSS), only Lambert, or applying all three shading techniques ("Full", enabled by default).baseShape: This lets you swap out the green cubes for green spheres. Wow!
- Jamie Wong's generally useful resource for SDF
- IQ's article about ray-marching SDFs
- Article about bias/gain functions
- IQ's article for help with SDF ambient occlusion
- matiasm97's playthrough of "Built to Scale", from which I took the audio
- Howler library for playing audio
- Gain more experience with GLSL Shader writing and raymarching
- Experiment with procedural modeling and animation of scenes
-
Install Node.js. Node.js is a JavaScript runtime. It basically allows you to run JavaScript when not in a browser. For our purposes, this is not necessary. The important part is that with it comes
npm, the Node Package Manager. This allows us to easily declare and install external dependencies such as dat.GUI, and glMatrix. -
Using a command terminal, run
npm installin the root directory of your project. This will download all of those dependencies. -
Do either of the following (but we highly recommend the first one for reasons we will explain later).
a. Run
npm startand then go tolocalhost:5660in your web browserb. Run
npm run buildand then go openindex.htmlin your web browser
One of the most important dependencies of our projects is Webpack. Webpack is a module bundler which allows us to write code in separate files and use imports and exports to load classes and functions for other files. It also allows us to preprocess code before compiling to a single file. We will be using Typescript for this course which is Javascript augmented with type annotations. Webpack will convert Typescript files to Javascript files on compilation and in doing so will also check for proper type-safety and usage. Read more about Javascript modules in the resources section below.
All of the JavaScript code is living inside the src directory. The main file that gets executed when you load the page as you may have guessed is main.ts. Here, you can make any changes you want, import functions from other files, etc. The reason that we highly suggest you build your project with npm start is that doing so will start a process that watches for any changes you make to your code. If it detects anything, it'll automagically rebuild your project and then refresh your browser window for you. Wow. That's cool. If you do it the other way, you'll need to run npm build and then refresh your page every time you want to test something.
We would suggest editing your project with Visual Studio Code https://code.visualstudio.com/. Microsoft develops it and Microsoft also develops Typescript so all of the features work nicely together. Sublime Text and installing the Typescript plugins should probably work as well.
- The framework is a simplified version of the homework 0 base. It has been pruned to emphasize that the only geometry being rasterized is a single quad on the entire screen. Your job is to rewrite the shaders in src/shaders to create a raymarched scene drawn on top of the quad, and modify any other .ts files to provide the necessary info and interactivity to your raymarcher.
- Create and animate a scene! Using SDFs creatively, you must model and animate a "cool" scene. You can make whatever you want of course, but if you just can't think of something, then our suggestion is to make something mechanical like this. Additionally, we (Dan and Joe) like using GraphToy for easy editing and creation of custom functions for modeling and animating. Specific requirements:
- Blending: at least three of union, intersection, subtraction, smooth blend operations
- Domain repetition
- Parts that animate in interesting ways
- A background that isn't a constant color
- Finally: You must give your scene at least one kind of interesting material/reflection model, and we're not talking Lame-bert or Blinn-Phong...there are a ton of things you could do! If you just can't think of something, try specular reflection/transmission...or a real-time subsurface scattering approximation.
- Optional features (for added credit):
- Ambient occlusion
- Soft shadows
- Extra optimizations (explain in your readme)
- Volumetric marching
- Marching height fields / non-SDF surfaces with reasonable speed
- Toggleable controllable camera
- Lecture slides (see the last two slides)
