Scan Converting Triangles

Similar documents
Triangle Rasterization

Clipping & Culling. Lecture 11 Spring Trivial Rejection Outcode Clipping Plane-at-a-time Clipping Backface Culling

What is Clipping? Why do we Clip? Lecture 9 Comp 236 Spring Clipping is an important optimization

2D rendering takes a photo of the 2D scene with a virtual camera that selects an axis aligned rectangle from the scene. The photograph is placed into

Triangle Fast Scan-Conversion Algorithm Report

Computing Visibility. Backface Culling for General Visibility. One More Trick with Planes. BSP Trees Ray Casting Depth Buffering Quiz

Chapter 8: Implementation- Clipping and Rasterization

Topic #1: Rasterization (Scan Conversion)

CS 130 Exam I. Fall 2015

Polygon Filling. Can write frame buffer one word at time rather than one bit. 2/3/2000 CS 4/57101 Lecture 6 1

Announcements. Midterms graded back at the end of class Help session on Assignment 3 for last ~20 minutes of class. Computer Graphics

COMP30019 Graphics and Interaction Scan Converting Polygons and Lines

OpenGL and Qt Creator: a Gentle Introduction

CSE 167: Lecture #5: Rasterization. Jürgen P. Schulze, Ph.D. University of California, San Diego Fall Quarter 2012

CS 130 Final. Fall 2015

Clipping and Scan Conversion

Imaging and 2D Transforms

CS602 MCQ,s for midterm paper with reference solved by Shahid

CSCI 4620/8626. Coordinate Reference Frames

CS 543: Computer Graphics. Rasterization

Computer Graphics Geometry and Transform

The Traditional Graphics Pipeline

Polygonal Meshes: Representing 3D Objects

Reading on the Accumulation Buffer: Motion Blur, Anti-Aliasing, and Depth of Field

Shadows in the graphics pipeline

The Traditional Graphics Pipeline

521493S Computer Graphics Exercise 1 (Chapters 1-3)

Computer Graphics 7 - Rasterisation

Class of Algorithms. Visible Surface Determination. Back Face Culling Test. Back Face Culling: Object Space v. Back Face Culling: Object Space.

Project 1, 467. (Note: This is not a graphics class. It is ok if your rendering has some flaws, like those gaps in the teapot image above ;-)

The Traditional Graphics Pipeline

CS452/552; EE465/505. Clipping & Scan Conversion

Last class. A vertex (w x, w y, w z, w) - clipping is in the - windowing and viewport normalized view volume if: - scan conversion/ rasterization

CSE 167: Introduction to Computer Graphics Lecture #10: View Frustum Culling

Ray tracing. Computer Graphics COMP 770 (236) Spring Instructor: Brandon Lloyd 3/19/07 1

Renderer Implementation: Basics and Clipping. Overview. Preliminaries. David Carr Virtual Environments, Fundamentals Spring 2005

Cs602-computer graphics MCQS MIDTERM EXAMINATION SOLVED BY ~ LIBRIANSMINE ~

CSE528 Computer Graphics: Theory, Algorithms, and Applications

Scan Conversion. Drawing Lines Drawing Circles

CS488 2D Graphics. Luc RENAMBOT

Computer Graphics (CS 543) Lecture 10: Rasterization and Antialiasing

Shadow Algorithms. CSE 781 Winter Han-Wei Shen

CS488. Visible-Surface Determination. Luc RENAMBOT

Rasterization and Graphics Hardware. Not just about fancy 3D! Rendering/Rasterization. The simplest case: Points. When do we care?

CS 130 Exam I. Fall 2015

2D Graphics Primitives II. Additional issues in scan converting lines. 1)Endpoint order. Want algorithms to draw the same pixels for each line

Surface shading: lights and rasterization. Computer Graphics CSE 167 Lecture 6

Rasterization. COMP 575/770 Spring 2013

RASTERIZING POLYGONS IN IMAGE SPACE

? Which intermediate. Recall: Line drawing algorithm. Programmer specifies (x,y) of end pixels Need algorithm to determine pixels on line path

The goal is the definition of points with numbers and primitives with equations or functions. The definition of points with numbers requires a

FROM VERTICES TO FRAGMENTS. Lecture 5 Comp3080 Computer Graphics HKBU

CSE 167: Introduction to Computer Graphics Lecture #4: Vertex Transformation

CSE328 Fundamentals of Computer Graphics

Lecture 2: Digital Drawing. Computer Graphics and Imaging UC Berkeley CS184/284

Pipeline and Rasterization. COMP770 Fall 2011

- Rasterization. Geometry. Scan Conversion. Rasterization

How shapes are represented in 3D Graphics. Aims and objectives By the end of the lecture you will be able to describe

Adaptive Point Cloud Rendering

Intermediate Mathematics League of Eastern Massachusetts

Culling. Computer Graphics CSE 167 Lecture 12

CSE 167: Introduction to Computer Graphics Lecture #9: Visibility. Jürgen P. Schulze, Ph.D. University of California, San Diego Fall Quarter 2018

Mathematics Curriculum

Visibility: Z Buffering

Rasterization. MIT EECS Frédo Durand and Barb Cutler. MIT EECS 6.837, Cutler and Durand 1

Rasterization, or What is glbegin(gl_lines) really doing?

CSE 167: Introduction to Computer Graphics Lecture #11: Visibility Culling

Visible-Surface Detection Methods. Chapter? Intro. to Computer Graphics Spring 2008, Y. G. Shin

Shading Techniques Denbigh Starkey

Midterm Exam Fundamentals of Computer Graphics (COMP 557) Thurs. Feb. 19, 2015 Professor Michael Langer

3D Rendering Pipeline (for direct illumination)

CS 4731: Computer Graphics Lecture 21: Raster Graphics: Drawing Lines. Emmanuel Agu

Rasterization. CS 4620 Lecture Kavita Bala w/ prior instructor Steve Marschner. Cornell CS4620 Fall 2015 Lecture 16

Computer Graphics Prof. Sukhendu Das Dept. of Computer Science and Engineering Indian Institute of Technology, Madras Lecture - 24 Solid Modelling

General Hidden Surface Removal Algorithms. Binghamton University. EngiNet. Thomas J. Watson. School of Engineering and Applied Science CS 460/560

Review for Mastery Using Graphs and Tables to Solve Linear Systems

9. Visible-Surface Detection Methods

CS184 : Foundations of Computer Graphics Professor David Forsyth Final Examination

CS559: Computer Graphics. Lecture 12: Antialiasing & Visibility Li Zhang Spring 2008

Curves and Surfaces. Computer Graphics COMP 770 (236) Spring Instructor: Brandon Lloyd

9. Three Dimensional Object Representations

Scan Conversion- Polygons

CS602- Computer Graphics Solved MCQS From Midterm Papers. MIDTERM EXAMINATION Spring 2013 CS602- Computer Graphics

CS 248 Assignment 2 Polygon Scan Converter. CS248 Presented by Abe Davis Stanford University October 17, 2008

COMP 161 Lecture Notes 16 Analyzing Search and Sort

4.5 VISIBLE SURFACE DETECTION METHODES

Graphics Pipeline 2D Geometric Transformations

the gamedesigninitiative at cornell university Lecture 17 Color and Textures

Box It Up (A Graphical Look)

Clipping. CSC 7443: Scientific Information Visualization

3D Programming. 3D Programming Concepts. Outline. 3D Concepts. 3D Concepts -- Coordinate Systems. 3D Concepts Displaying 3D Models

Computer Graphics Fundamentals. Jon Macey

Hidden-Surface Removal.

Soft shadows. Steve Marschner Cornell University CS 569 Spring 2008, 21 February

CS184 : Foundations of Computer Graphics Professor David Forsyth Final Examination (Total: 100 marks)

Graphics Hardware and Display Devices

To Do. Computer Graphics (Fall 2008) Course Outline. Course Outline. Methodology for Lecture. Demo: Surreal (HW 3)

Graphics Programming

8. Hidden Surface Elimination

6.001 Notes: Section 8.1

Transcription:

Scan Converting Triangles Why triangles? Rasterizing triangles Interpolating parameters Post-triangle rendering Comp 236 Spring 2005 Primitive Rasterization 2-D SAMPLING problem Which pixels (samples) of an ideal analytical primitive should be turned on? Based on closeness of the primitive to the sample to the sample point (lines as you saw in 235) Percentage coverage of an aperture (a notion that used to be popular) Whether the sample is inside or outside of a closed primitive 2 Why Triangles? Triangles are minimal! Triangles are determined by 3 points or 3 edges We can define a triangle in terms of three points, for example: (x 1, y 1 ), (x 2, y 2 ), (x 3, y 3 ) Or we can define a triangle in terms of its three edges, for example: A 1 x + B 1 y + C 1 = 0, A 2 x + B 2 y + C 2 = 0, A 3 x + B 3 y + C 3 = 0 Why does it appear to take more parameters to represent the edges than the points? (Hint: Edge equations are Homogeneous) As a result, triangles are mathematically very simple. Scan converting triangles involves simple linear equations. Triangles are always Convex polygons What does it mean to be a convex? An object is convex if and only if any line segment connecting two points on its boundary is contained entirely within the object or one of its boundaries. Why is being convex important? Because no matter how a triangle is oriented on the screen a given scan line will contain only a single segment or span of that triangle. 3 4

Triangles can Approximate arbitrary shapes Polygons can be Decomposed into Triangles Any 2-dimensional shape (or 3D surface) can be approximated by a polygon using a locally linear (planar) approximation. To improve the quality of fit we need only increase the number edges. A convex n-sided polygon, with ordered vertices {v 0, v 1,... v n along the perimeter, can be trivially decomposed into triangles {(v 0,v 1,v 2 ), {v 0,v 2,v 3 ), (v 0,v i,v i+1 ),... (v 0,v n-1,v n ). You can usually decompose a non-convex polygon into triangles, but it is non-trivial, and in some overlapping cases you have to introduce a new vertex. 5 6 How to draw a Triangle? Scan-converting Triangles The two most common strategies for scan-converting triangles are edge walking and edge equations There are, however, other techniques including: Recursive subdivision of primitive (micro-polygons) Recursive subdivision of screen (Warnock s algorithm) Better question Why? A last side trip before we blast into 3D 7 8

Edge-Walking Triangle Rasterizer Fractional Offsets Notes on edge walking: Sort the vertices in both x and y Determine if the middle vertex, or breakpoint lies on the left or right side of the polygon. If the triangle has an edge parallel to the scan line direction then there is no breakpoint. Determines the left and right extents for each scan line (called spans). Walk down the left and right edges filling the pixels in-between until either a breakpoint or the bottom vertex is reached. Advantages and Disadvantages: We can use ceiling to find the leftmost pixel in span and floor to find the rightmost pixel. The trick comes when interpolating color values. It is straightforward to interpolate along the edges, but you must be careful when offsetting from the edge to the pixel s center. Generally very fast Loaded with special cases (left and right breakpoints, no breakpoints) Difficult to get right Requires computing fractional offsets when interpolating parameters across the triangle 9 An edge equation is simply a discriminating function. You can think of it as answering a question about any given point (x, y) An edge equation segments a planar region into three parts, a boundary, and two half-spaces. The boundary is identified by points where the edge equation is equal to zero. The halfspaces are distinguished by differences in the edge equation s sign. We can choose which half-space is positive by multiplication by -1. We can scale all three edges so that their negative half-spaces are on the triangle s exterior. 10 Notes on using Edge Equations Rasterizing Triangles with Edge Equations 11 Compute edge equations from vertices Orient edge equations (make the interior region positive) Compute a bounding box Scan through pixels in bounding box evaluating the edge equations When all three are positive then draw the pixel. 12

First we define a few useful objects An abstract Drawable class A 2D vertex, with and without a color Example Implementation public abstract class Drawable { public abstract void Draw(Raster r); public class Vertex2D : Drawable { public double x, y; public Color color; public Vertex2D(double xval, double yval) { x = xval; y = yval; public Vertex2D(double xval, double yval, Color cval) { x = xval; y = yval; color = cval; public override void Draw(Raster r) { r.setpixel((int) Math.Round(x), (int) Math.Round(y), color); public string tostring() { return " ["+x+", "+y+"]"; 13 Edge Equation Coefficients The edge equation coefficients are computed using the coordinates of the two vertices. Each point determines an equation in terms of our three unknowns, A, B, and C. We can solve for A and B in terms of C by setting up the following linear system. Multiplying both sides by the matrix inverse. If we choose, then we get and. Why could we just choose C? What are the advantages of our choice? Easy. However, there is still a problem. 14 Numerical Precision of the C coefficient Computers represent floating-point number internally in a format similar to scientific notation. The very worse thing that you can do with numbers represented in scientific notation is subtract numbers of similar magnitude. Here is what happens: We loose most of the significant digits in our result. In the case of triangles, these sort of precision problems to occur frequently, because, in general, the vertices of a triangle are close to each other and thus Maintaining Precision in C Thankfully, we can avoid this subtraction of large numbers when computing an expression for C. Given that we know A and B we can solve for C as follows: or To eliminate any bias toward either vertex we will average of these C values 15 16

An Edge Equation Object We compute A, B, and C as described earlier Notice that we also compute a few flags to remember the signs of the A and B coefficients We also have added a flip( ) method, which will be used shortly We also have a method to evaluate the edge equation Mostly obvious stuff here. A triangle has public class EdgeEqn { public double A, B, C; public int flag; public EdgeEqn(Vertex2D v0, Vertex2D v1) { A = v0.y - v1.y; B = v1.x - v0.x; C = -0.5*(A*(v0.x + v1.x) + B*(v0.y + v1.y)); flag = 0; if (A >= 0) flag += 8; if (B >= 0) flag += 1; 17 The Draw( ) Method // allows future extension public FlatTri(Vertex2D v0, Vertex2D v1, Vertex2D v2) { v = new Vertex2D[3]; v[0] = v0; v[1] = v1; v[2] = v2; /*... Our policy is to assign a triangle the average of it s vertex colors... */ byte r = (byte) ((2*(v0.color.r + v1.color.r + v2.color.r) + 3) / 6); byte g = (byte) ((2*(v0.color.g + v1.color.g + v2.color.g) + 3) / 6); byte b = (byte) ((2*(v0.color.b + v1.color.b + v2.color.b) + 3) / 6); color = new Color(r,g,b); 18 Explain trick public override void Draw(Raster r) { if (!trianglesetup(r)) return; int x, y; double A0 = edge[0].a; double A1 = edge[1].a; double A2 = edge[2].a; double B0 = edge[0].b; double B1 = edge[1].b; double B2 = edge[2].b; double t0 = edge[0].evaluateat(xmin, ymin); double t1 = edge[1].evaluateat(xmin, ymin); double t2 = edge[2].evaluateat(xmin, ymin); ymin *= r.width; ymax *= r.width; /*... scan convert triangle... */ for (y = ymin; y <= ymax; y += r.width) { double e0 = t0; double e1 = t1; double e2 = t2; bool beeninside = false; for (x = xmin; x <= xmax; x++) { if ((e0 >= 0) && (e1 >= 0) && (e2 >= 0)) { // all 3 edges must be >= 0 int i = 4*(y+x); r.data[i ] = color.r; r.data[i+1] = color.g; r.data[i+2] = color.b; r.data[i+3] = color.a; beeninside = true; else if (beeninside) break; e0 += A0; e1 += A1; e2 += A2; t0 += B0; t1 += B1; t2 += B2; public FlatTri() { We use vertex colors to set the triangle color, for now public double evaluateat(int x, int y) { return (A*x + B*y + C); public class FlatTri : Drawable { public Vertex2D [] v; public Color color; protected EdgeEqn [] edge; 3 vertices 3 edge equations A color public void flip() { A = -A; B = -B; C = -C; A Triangle Object Everything in our Draw( ) method is straightforward, with one exception. bool beeninside = false; for (x = xmin; x <= xmax; x++) { if ((e0 >= 0) && (e1 >= 0) && (e2 >= 0)) { int i = 4*(y+x); r.data[i ] = color.r; r.data[i+1] = color.g; r.data[i+2] = color.b; r.data[i+3] = color.a; beeninside = true; else if (beeninside) break; // all 3 edges must be >= 0 Since triangles are convex, we can only be inside for a single interval on any given scanline. The xflag variable is used to keep track of when we exit the triangle s interior. If ever we find ourselves outside of the triangle having already set some pixels on the span then we can skip over the remainder of the scanline. 19 20

Triangle Set-up protected bool trianglesetup(raster r) { if (edge == null) edge = new EdgeEqn[3]; edge[0] = new EdgeEqn(v[0], v[1]); edge[1] = new EdgeEqn(v[1], v[2]); edge[2] = new EdgeEqn(v[2], v[0]); area = edge[0].c + edge[1].c + edge[2].c; if (area == 0) { return false; // degenerate triangle else if (area < 0) { edge[0].flip(); edge[1].flip(); edge[2].flip(); area = -area; Some more tricks In trianglesetup() we did two critical things. We orient the edge equations, and we compute the bounding box. From analytic geometry we know the area of triangle {(x 1,y 1 ), (x 2,y 2 ), (x 3,y 3 ) is: int xflag = edge[0].flag + 2*edge[1].flag + 4*edge[2].flag; int yflag = (xflag >> 3) - 1; xflag = (xflag & 7) - 1; xmin = (int) (v[sort[xflag, 0]].x); xmax = (int) (v[sort[xflag, 1]].x + 1); ymin = (int) (v[sort[yflag, 1]].y); ymax = (int) (v[sort[yflag, 0]].y + 1); xmin = (xmin < 0)? 0 : xmin; xmax = (xmax >= r.width)? r.width - 1 : xmax; ymin = (ymin < 0)? 0 : ymin; ymax = (ymax >= r.height)? r.height - 1 : ymax; return true; 21 The area is positive if the vertices are counterclockwise and negative if clockwise An aside: In terms of our discriminator, what does a positive C imply? 22 Why a positive area implies a positive interior 1. The area of each sub-triangle gives the edge equation s sign at the origin 2. Assume a positive area thus, the sum of the sub-triangles areas are positive 3. Each point within the triangle falls within exactly one subtriangle thus, subtriangles with negative areas will lie outside of the triangle 4. Since the negative-subtriangle areas are outside of the triangle the edge equations are positive inside 23 5 min Immunity challenge #2 Examine the code for computing the bounding box of the triangle in EdgeEqn( ) and FlatTri.triangleSetup( ). Explain what is being saved in the EdgeEqn.flag Explain the contents FlatTri.sort[ ] Explain how the bounding box is computed Advantages and disadvantages of this approach public class EdgeEqn { : public EdgeEqn(Vertex2D v0, Vertex2D v1) { A = v0.y - v1.y; B = v1.x - v0.x; C = -0.5*(A*(v0.x + v1.x) + B*(v0.y + v1.y)); flag = 0; if (A >= 0) flag += 8; if (B >= 0) flag += 1; : protected bool trianglesetup(raster r) { : int xflag = edge[0].flag + 2*edge[1].flag + 4*edge[2].flag; int yflag = (xflag >> 3) - 1; xflag = (xflag & 7) - 1; xmin = (int) (v[sort[xflag, 0]].x); xmax = (int) (v[sort[xflag, 1]].x + 1); ymin = (int) (v[sort[yflag, 1]].y); ymax = (int) (v[sort[yflag, 0]].y + 1); xmin = (xmin < 0)? 0 : xmin; xmax = (xmax >= r.width)? r.width - 1 : xmax; ymin = (ymin < 0)? 0 : ymin; ymax = (ymax >= r.height)? r.height - 1 : ymax; return true; 24

27 28 The OpenGL code is simple public override void Init( ) { if ((panelsize.width!= width) (panelsize.height!= height)) { width = panelsize.width; height = panelsize.height; data = new PUInt8(4*width*height); glviewport(0, 0, width, height); glclearcolor(0.0f, 0.0f, 0.0f, 1.0f); glmatrixmode(gl_projection); glloadidentity(); gluortho2d(0, width, 0, height); glmatrixmode(gl_modelview); glloadidentity(); Demonstration public override void Draw() { clearraster(0,0,0,255); foreach (Drawable t in trilist) { t.draw(this); glrasterpos2i(0,0); gldrawpixels(width,height,gl_rgba,gl_unsigned_byte,data); glflush(); 25 Interpolating Parameters within a Triangle Currently, our triangle scan-converter draws only solid-colored triangles. Next we ll discuss how to smoothly vary parameters as we fill the triangle. In this case the parameters that are interpolated are the red, green, and blue components of the color. We might also want to interpolate other parameters such as the depth at each point on the triangle. First, let s frame the problem. At each vertex of a triangle we have a parameter, say its redness. When we actually draw the vertex, the specified shade of red is exactly what we want, but at other points we d like some sort of smooth transition between the values given. This situation is shown to the right: Notice that the shape of our desired redness function is planar. Actually, it is a special class of plane where there exists a corresponding point for every x-y coordinate. Planes of this type can always be expressed in the following form: z = Ax + By + C 26 A Familiar Equation It has the same form as our edge equations. Given the redness of the three vertices, we can set up the following linear system. By the way We ve already computed these matrix entries, they re exactly the coefficients of our edge equations with the solution: The desired plane equation is just a linear combination of our three edge equations! Obvious? So the additional work to interpolate is: 1) transform a parameter vector (by multiplying it by a matrix) 2) compute an extra edge equation for each parameter.

A Smooth Triangle More of the same A triangle has 3 vertices 3 edge equations We interpolate vertex colors public class SmoothTri : FlatTri { bool isflat; double scale; public SmoothTri(Vertex2D v0, Vertex2D v1, Vertex2D v2) { v = new Vertex2D[3]; v[0] = v0; v[1] = v1; v[2] = v2; /* Scale is always non zero and positive. This zero value indicates that it has not been computed yet */ scale = -1; 29 Modified Draw( ) Method public double [] PlaneEqn(int p0, int p1, int p2) { double Ap, Bp, Cp; double [] eqn = new double[3]; if (scale <= 0) { scale = 1 / ((double) area); double sp0 = scale * p0; double sp1 = scale * p1; double sp2 = scale * p2; Ap = edge[0].a*sp2 + edge[1].a*sp0 + edge[2].a*sp1; Bp = edge[0].b*sp2 + edge[1].b*sp0 + edge[2].b*sp1; Cp = edge[0].c*sp2 + edge[1].c*sp0 + edge[2].c*sp1; eqn[0] = Ap; eqn[1] = Bp; eqn[2] = Ap*xMin + Bp*yMin + Cp; return eqn; 30 Example Smooth shading with per-vertex colors Can interpolate arbitrary parameters over the triangle At the heart of modern rendering H/W public override void Draw(Raster r) { if (!trianglesetup(r)) return; int x, y; double A0 = edge[0].a; double A1 = edge[1].a; double A2 = edge[2].a; double B0 = edge[0].b; double B1 = edge[1].b; double B2 = edge[2].b; double t0 = edge[0].evaluateat(xmin, ymin); double t1 = edge[1].evaluateat(xmin, ymin); double t2 = edge[2].evaluateat(xmin, ymin); ymin *= r.width; ymax *= r.width; /*... scan convert triangle... */ for (y = ymin; y <= ymax; y += r.width) { double e0 = t0; double e1 = t1; double e2 = t2; bool beeninside = false; for (x = xmin; x <= xmax; x++) { if ((e0 >= 0) && (e1 >= 0) && (e2 >= 0)) { // all 3 edges must be >= 0 int i = 4*(y+x); r.data[i ] = color.r; r.data[i+1] = color.g; r.data[i+2] = color.b; r.data[i+3] = color.a; beeninside = true; else if (beeninside) break; e0 += A0; e1 += A1; e2 += A2; t0 += B0; t1 += B1; t2 += B2; Weve added two new instance variables. The first is simply an optimization that detects the case when all three vertices are the same color. In this case we ll call the slightly faster FlatTri methods that we inherited. The second is a scale factor that we ll discuss next. Next we add a new method to compute the plane equations of our parameters. The PlaneEqn() method performs the required matrix multiply and avoids computing the inverse of the triangle area more than once. /* check if all vertices are the same color */ isflat = (v0.color == v1.color) && (v0.color == v2.color); if (isflat) color = v0.color; Unless they are all the same Computing Plane Equations 31 32

A Post-Triangle World? Are triangles really the best rendering primitive? 100,000,000 primitive models displayed on 2,000,000 pixel displays. Even even if we assume that only 10% of the primitives are visible, and they are uniformly distributed over the whole screen, that s still 5 primitives/pixel. Remember, that in order to draw a single triangle we must specify 3 vertices, determine three colors, and interpolate within 3 edges. On average, these triangle will impact only a fraction of a pixel. Models of this magnitude are being built today. The leading and most ambitious work in this area is Stanfords "Digital Michelangelo Project". 33 Point-Cloud Rendering A new class of rendering primitives have recently been introduced to address this problem. Key Attibutes: Hierarchy Incremental Refinement Compact Representation (differental encoding) 130,712 Splats, 132 ms 259,975 Splats, 215 ms 1,017,149 Splats, 722 ms 14,835,967 Splats, 8308 ms 34 Next Time We return to manipulating images as textures Then we dive, head first, into 3-D Read in and display a 3-D model 35