Assignment 2: Blocky 3D Animal
- Due Feb 3, 2020 by 11:59pm
- Points 10
- Submitting a file upload
Objectives
To transform (translation, rotation, scaling, etc) simple 2D geometric shapes and 3D objects using matrices.
Description
See this video for a sample. You don't need to make one this complex.
https://www.youtube.com/watch?v=ka8prwshnuo
Links to an external site.
Create a simple 3D animal. You will create this out of simple geometric objects, like cubes, spheres, and cylinders. The animal must have at least 8 parts, e.g. body, upper legs (x4), lower legs(x4), head OR whatever. The sample above has 20+ parts. There needs to be at least one chain of parts that extends at least two elements away from the body. For example, there should be a bend at the knee so the leg has two parts. At least one part should animate. There should be a way (slider or mouse) to rotate the object and see the animal from all sides.
In order to help you structure your code, I'm going to walk you through what I would do to get this working. You aren't required to structure code this way, I'm just trying to help.
- First get a function working that can drawCube(). This function should build the buffer needed to draw a cube out of triangles. Don't have this spread out all over in your code, get a single function that does this. Its just like the circle, except that you have to place the vertices to form a cube instead. Actually you could even start with a drawCircle() function instead of drawCube(), you'll just have a very flat animal, but the principle is the same.
-
- Once you will be drawing 3D geometries in this assignment, you will have to enable depth test on your WebGL context. To do that, you can execute the following command just after retrieving the gl context:
-
gl.enable(gl.DEPTH_TEST);
-
- Once that is enabled, you also have to clear the DEPTH_BUFFER when you clear your screen:
-
gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT);
-
- Once you will be drawing 3D geometries in this assignment, you will have to enable depth test on your WebGL context. To do that, you can execute the following command just after retrieving the gl context:
-
- Modify this function to take a Matrix parameter drawCube(Matrix M), that will apply this matrix when drawing the cube. The Matrix should get passed the the vertex shader as a uniform variable before calling drawArrays(). The vertex shader should have a line similar to glPosition = u_ModelMatrix * a_position; Test this function with some simple translate and rotate matrices and see that your cube does move around on the screen.
- Have a slider that sets a global variable for the rotation angle gAnimalGlobalRotation; Also attach this to a uniform variable that gets passed to GLSL. Modify the vertex shader to be glPostion = u_GlobalRotation * uModelMatrix * a_position; Check that you can rotate your single cube with this slider.
- Create a function renderScene() which is going to draw your whole scene. All the drawing happens in this function. Initially its just going to have a few lines {glClear(); M=scale(2,1,2); drawCube(M);}
- Call the renderScene() function at the end of main(), and also after you update the slider. (And later when you are animating or updating the window. The key is having all the drawing isolated in one place so you can just call that function to draw).
- Now expand your renderScene() function to add one more cube to your animal, placed in the right location. e.g. {glClear(); M=scale(2,1,2); drawCube(M); M=identity(); M.translate(1,2,3);M.rotate(30);drawCube(M)}
- Add some more cubes until you have a whole animal.
- Add a tick() function (as discussed in the book). Create a global variable for the time, or frame of your animation. You are going to use this to update the animation. Whenever there is a tick() event, then you need to {g_time=theNewTime(); renderScene()} Just to test if your tick() is working, pick any cube in your animal and modify its matrix with M.rotate(g_time); in drawScene() before calling drawCube(M); Its going to move in some crazy way, but we just want to make sure tick() is doing something before moving on.
- Pick a cube that will animate. You probably have a rotation matrix in the list of things you did to position that part. make that rotation matrix not be a fixed Rot(30) but instead be a Rot(30+time*3) or something like that. This part will then move, but the others wont.
- Thats it, you're done with the basic assignment. -
- To get an 'A', add complete animation and color-- see the step below
- Keep adding animation to the other cubes. Try to make the creature move in a natural way. The real challenge comes from dealing with parts not directly attached to the body. The foot connects to the calf that connects to the thigh that connects to the body. These lower parts need to reflect the motion of the parts higher in the tree or they won't stay connected. Start with moving the thigh. Then figure out the stack of matrices that will get the calf to move connected. Then get the foot to stay connected to the calf. Hint: The foot rotation occurs in the calf coordinate frame, so first apply all the xforms you applied to the thigh, then those for the calf, then finally those for the foot. Dont try to just rotate the foot independently. (I havent asked students to use it previously, but Chap9 appears to talk about hierarchical objects, which is just what this is)
- Add color using a uniform variable, same as assignment 1. modify your drawCube(M, color) to take a color parameter so you can set this uniform before drawing the cube. Fix up your creature to be colored nicely.
Resources
- Readings:
- (WebGL) Matsuda/Lea Ch3 (91-113) and Ch 4 (Appendix C)
- Possibly Chap 9 in Matsuda will be helpful as well (not tested on previous classes)
- Introduction presented in the Lab:
What to Turn in
1. Canvas Submission
Zip your entire project and submit it to Canvas under the appropriate assignment. Name your zip file "[FirstName]_[LastName]_Assignment_2.zip" (e.g. "Lucas_Ferreira_Assignment_2.zip").
2. Live Hosted Submission
Host your assignment on your UCSC portal. This can be achieved by just putting your entire project directory into the 'public_html' folder which you can access via the UCSC Unix timeshare. Your site link is 'https://people.ucsc.edu/~ucsc_user_name/'.
WHEN SUBMITTING YOUR PROJECT ON CANVAS, PLACE YOUR SITE LINK AS A COMMENT OF THE SUBMISSION.
Read the SubmissionGuide.txt file for further explanation on how to submit your assignment.
Rubric
Criteria | Ratings | Pts |
---|---|---|
Draw a basic 3D shape (cube, sphere, cylinder). It is sufficient to have one of them, but you may want others. Have a function that draws this.
threshold:
pts
|
pts
--
|
|
Create an animal using the same basic object(s) (and reusing the same function(s)), but transformed using a matrix.
threshold:
pts
|
pts
--
|
|
Pass the ModelMatrix from javascript to GLSL correctly using a uniform variable.
The vertex shader should use this matrix to transform the object.
threshold:
pts
|
pts
--
|
|
The model can rotate when using the mouse or slider
threshold:
pts
|
pts
--
|
|
The model has at least one animated part (e.g. the head). The code has a variable to specify the current time or animation frame that updates with tick().
threshold:
pts
|
pts
--
|
|
The model is fully animated (all the parts which should move, do move)
That last 1.5 point to get to A is hard!
threshold:
pts
|
pts
--
|
|
Add color - the animal is colored nicely with more than one color part
threshold:
pts
|
pts
--
|