Java代写:CMPT361RenderComponents


解析指定的语句,对图像进行渲染。

Requirement

For this assignment, you are to interpret a 3D graphics specification
language, along with doing some preparatory work. The preparatory work is (1)
to incorporate lerping and blerping into your line and polygon renderers, and
(2) to implement zbuffering. The graphics interpretation will involve
manipulating and transforming polygons and lines, and rendering using depth
cueing.
These rendering components should be shown in a program that displays eight
pages. Each of the required pages displays 1 panel, as shown in the following
diagram:
The drawing area should be 650 x 650 pixels, the the white margins are all 50
pixels wide or tall. Thus, the total display area is 750 x 750 pixels. Use
white and black for the backgrounds, as shown above.
You will be using and modifying your line drawing and polygon filling from
assignment 1. You only need one line drawer for this assignment; I recommend
using the DDA.

Color Interpolation

Modify your line drawer to linearly interpolate (lerp) RGB colors between its
endpoints. Assume that each endpoint of a line is given to you with an RGB
color attached. (You can decide between keeping colors in the range 0-1 or the
range 0-255.) For each component (R, G, and B), you must interpolate that
component.
Interpolating a color component is exactly like interpolating the y-value of
the line when working in the first octant. You get the (say) red component r1
for p1, and the red component r2 for p2, and compute dr/dx = (r2-r1) /
(x2-x1). Start the line with r = r1 and x = x1, and each time you advance one
unit in x, you add dr/dx to r (and round). Do the same for g and b, and when
writing the pixel with the current x and y, use the current r, g, and b. You
should get a smooth gradation of color along a line.
Similarly, modify your polygon renderer to do bi-linear interpolation
(blerping) of RGB colors between its vertices.
For pages 1 and 2 of your assignment, use the same setup as the perturbed mesh
test from assignment 1 (page 4, third panel). Almost fill the (650 x 650)
drawing area, not the smaller panel from assignment 1. On page 1, draw the
mesh in wireframe: draw the edges (lines) of the mesh, not the filled
polygons. On page 2, draw the mesh as solid: don’t use any lines, just fill in
the polygons. On each page, assign a random color to each vertex of the mesh.
These pages are for showing me that your color interpolation works.
To implement wireframe rendering, I recommend that you make a class that
satisfies the same interface as your polygon renderer, but that class simply
calls a line renderer (which one could be a constructor argument) to render
the (usually 3) edges of a polygon.

Z-buffering

Allocate an array of doubles (calling it, say, zBuffer) that is the size of
the image window (650 x 650). Set the entire array to 200 (which will be our
back clipping plane) at the start of each page. Whenever you are about to
write a pixel (x, y) with world-space coordinate z, first compare z to the
zBuffer value at (x, y). If z [ zBuffer(x, y) then go ahead a write the pixel.
Otherwise, do not write the pixel.
For page 3 of your assignment, I want you to draw 6 triangles (filled). Each
triangle should be given a color of (v, v, v) for v=1, .85, .7, .55, .4, .25,
respectively, for triangles 1 through 6. Each triangle should be regular (all
three sides the same length), with vertices on the circle centered at the
center of you drawing area, with radius 275. Give each triangle a random
rotation about that center, say, in the interval from 0 to 120 degrees. Also
give each triangle a random z-coordinate chosen between 1 and 199 inclusive.
(Either floating random numbers or integer random numbers is okay.) Render the
triangles, in order, using z-buffering.

Graphics file reading

You are required to be able to read in a file in “simp” format, which is as
follows. Simp format files always have a “.simp” extension.
Whitespace means spaces, tabs, carriage returns, and newlines.
A line containing whitespace only is ignored.
A line starting with “#” (before any whitespace or other characters) is a
comment and is also ignored.
The only other valid lines are ones containing one command from the commands
shown in the following table. Any of these lines may start with an arbitrary
number of whitespace characters.
All numbers are double precision.
Anything in angle brackets or double-quotes in the table is called a
parameter. All parameters that are points (denoted with [pN] below, where N is
a number) are of the format “(x, y, z)” where each of x, y, and z is a number.
To simplify interpretation, each comma must immediately follow the number
before it (no spaces or tabs inbetween), and a space after each comma is
mandatory. Adjacent parameters must be separated by tabs and/or spaces (and no
commas).
The language is case-sensitive. Use “rotate Z 45” and not “ROTATE Z 45” or
“rotate z 45”. Also, there is only one “command” per line. Only whitespace is
allowed on a line after the command and arguments (if any). (There are no
trailing comments.
Please indent lines between { and }, as you would in C++ or java.
The first section of lines/commands are things that affect the current
coordinate system or current transformation matrix (CTM). The second section
are our primitives: the shapes that our renderer should know about. The third
section are renderer directives, telling the renderer how to render the
primitives that we have specified. The default rendering type is “filled.”
If you encounter any malformed file, you may abort your program or allow it to
misbehave however it likes. We will not be testing behaviour on malformed
files.
When you get a primitive, you should transform it from the current coordinate
system to the world coordinate system by multiplying the vertices by the CTM.
The CTM starts as the identity matrix; this represents world space. The
rendering style starts as “filled.”
We will be viewing only a small part of the world (world space). The panel we
are using should map to the interval -100 to 100 in both X and Y in world
space. We are looking down the z-axis, and we will use parallel projection to
view objects. (This means that to convert from world space to window space, we
simply forget about the Z coordinate.) To find screen space from the window
space, scale by the appropriate amount (to convert 200 to 650) and translate
it so that the origin is in the middle of the screen.
The range of Z coordinates that we are interested in are from 0 to 200.
Anything with negative Z or Z greater than 200 should not be seen.
If a polygon or a line is completely outside any of the six planes defining
the viewing volume, then cull it (do not draw it). Otherwise (it is partially
or fully inside, or it is outside the viewing volume but not outside any one
plane), you may use pixel clipping (scissor testing) to keep the image in the
specified volume. Do not use pixel clipping on primitives that are entirely
outside the volume.
We will be using depth cueing or depth shading to render our primitives from
pages 3 on. In this technique, we give an object a color that indicates how
deep it is into the scene. Typically, the back (or far) clipping plane (in our
setup, Z=200) is given the color black and the front (or near) clipping plane
(Z=0) is given white or some other bright color. Color is linearly varied
through the Z range. For your renderer, when you find the world-space Z
coordinate of a vertex, then that point/vertex gets the corresponding color.
(For instance, assume your near clipping plane color is white (1, 1, 1). if a
point is at (32, 49, 150) it would get a color of (.25, .25, .25). [150 is a
quarter of the way from 200 (black) to 0 (white)]. Send this color along with
your vertex to your renderer, and have your renderer interpolate the colors
between its vertices or endpoints.
To create simp files, you may hand-edit them and/or you may use programs (that
you have written) to create them. I will provide you with a file box.simp that
contains a simple unit cube (one having every coordinate on every vertex
either 0 or 1).
Page 4. In simp format, make a scene that contains several scaled boxes with
some boxes (or parts of boxes) as far back as Z=200, and some as close as Z=0.
Render with depth cueing, from full green (0, 1, 0) for the near color to full
black (0, 0, 0) for the far color. Show rotations, translations, and scales of
boxes. Render filled polygons.
Page 5. In simp format, and using at least one file command, make a scene that
shows off the technical quality of your work. Use your own colors (or black
and white) for the depth cueing. Use interesting shapes: spheres, cylinders,
mountains, etc.
Pages 6 to 8. Read and display the following files from the current directory,
with the black-to-white depth cueing and setup as above: test1.simp (page 6),
test2.simp (page 7), and test3.simp (page 8). These are unknown files that we
will supply when testing your program. We will release these files (and any
files that they reference) with the assignment marks.

Implementation notes

Note 1

To read a file, start simple. First open the file (probably using an ifstream
in C++, or a BufferedReader in java). Then just loop through the file, reading
a line at a time, until there is no more in the file. Read the line as a
String if possible, and call a function on that string right after reading it.
Here’s the pseudocode:
fileStream = open(filename)
while (fileStream has input left) {
s = readALine(fileStream)
interpret(s)
}
close fileStream
—|—
Now all that remains is to write interpret. Start with an interpret that just
prints the line, to be sure that you’re doing the above loop correctly. If
that checks out, then all you have to do is interpret each line.
First, check for comments (s[0] is ‘#’) and blank lines (every character of s
is space or tab). Simply return if you find one of these cases.
For distinguishing between the commands, I recommend using java’s
String.split(), an STL equivalent if there is one, or simply writing one
yourself. Split takes a string and a regular expression, and splits the string
whereever it finds the regular expression. For our purposes, the regular
expression is simply any (positive) number of spaces and/or tabs ([ \t]+).
Split returns an array of Strings, which is the original String broken up into
pieces. For example
String inputLine = “whodo do \tyou do?”;
String[] tokens = inputLine.split(“[ \t]+”);
for (String token: tokens) {
System.out.println(token);
}
—|—
results in:
whodo
do
you
do?
Those are the four strings that tokens[] contains. If you do this split on an
input line, then the first token you get would be the command. Use an if-then-
elseif-elseif-elseif- or a switch statement to see which command you have.
Once you have the command, you know how to interpret the rest of the
tokenseach one is a parameter. Some numeric parameters may be preceded by a
‘(‘ or followed by a ‘)’ or a ‘,’, so you should trim these if they are
present. For example, if inputLine in the above code is “line (1, 2.3, 4.5)
(7.8, 9.01, 2.34)”, one gets:
line
(1,
2.3,
4.5)
(7.8,
9.01,
2.34)
To get rid of those extra characters, use something like this pseudocode,
probably in its own subroutine (you figure out the params and the return
value). You can call the subroutine whenever you have a numeric parameter.
Other parameters (axes and filenames) don’t need this. (Although filenames
will need you to remove the double-quotes.)
if (currentToken[0] == ‘(‘) {
currentToken = currentToken.substring(1, currentToken.length)
}
if(currentToken[currentToken.length-1] == ‘)’ or ‘,’) {
currentToken = currentToken.substring(0, currentToken.length-1)
}
—|—

Note 2

To perform the interpretation of a file, you will need the following objects1:

  1. A boolean or enum indicating whether you are rendering wireframe or filled polygons. Initially, this should be set to “filled”.
  2. A 4 x 4 matrix CTM, the Current Transformation Matrix. Initially, this should be set to the identity matrix, which means world space.
  3. A stack of 4 x 4 matrices. Initially, the stack is empty.
  4. A current file-reading object (ifstream, or whatever) to read commands from. Initially, set this to the file you are supposed to read.
  5. A stack of file-reading objects Initially, this is empty.
  6. A z-buffer attached to your (650 x 650) drawing area. Initially, set all values to 200.
  7. A line and a polygon renderer, and a wireframe polygon renderer, all with lerping or blerping.
    Each command has a simple interpretation in terms of these objects.

文章作者: SafePoker
版权声明: 本博客所有文章除特別声明外,均采用 CC BY 4.0 许可协议。转载请注明来源 SafePoker !
  目录