Автор: Shirley P.  

Теги: mathematics   physics  

ISBN: 1-56881-110-1

Год: 2000

Текст
                    MM
RAY 1MIN6
PETER SHIRLEY
1
V
r
^
r
' i


Realistic Ray Tracing PETER SHIRLEY H A K Peters Natick, Massachusetts
Editorial, Sales, and Customer Service Office A K Peters, Ltd. 63 South Avenue Natick, MA 01760 Copyright © 2000 by A K Peters. Ltd. All rigffts reserved. No part of the materia3 protected by this copyright notice may be reproduced or utilized in any form, electronic or mechanical, including photocopying, recording, or by any information storage and retrieval system, without written permission from the copyright owner. Library of Congress Cataloging-in-Publication Data Shirley. P. (Peter), 1963- Realistic ray tracing / Peter Shirley. p. cm. Includes bibliographical references and index. ISBN 1-56881-110-1 (alk. paper) 1. Computer graphics. I. Title. T385 .S438 2000 006.6'2—dc2I 00-039987 Printed in Canada 04 03 02 01 00 10 9 8 7 6 5 4 3 2 1 Contents Preface ix Introduction xi I The Basic Ray Tracing Program 1 1 Getting Started 3 1.1 RGB Colors 3 1.2 Images 4 1.3 Vectors 4 1.4 Rays 7 1.5 Intervals 7 1.6 Orthonormal Bases and Frames 7 1.7 Transformation Matrices 9 2 Ray-Object Intersections 17 2.1 Parametric Lines 17 2.2 General Ray-Object Intersections 18 2.3 Ray-Sphere Intersection 21 2.4 Ray-Box Intersection 22 2.5 Ray-Triangle Intersection 24 2.6 More Than One Object 28 2.7 A Simple Ray Tracer 29 3 Lighting and Shadows 31 3.1 Implementing Lighting 31 3.2 Adding Shadows 32 3.3 Outward Normal Vectors 34 V
vi Contents 4 Viewing 37 4.1 Axis-aligned viewing 37 4.2 Setting View Parameters 39 5 Basic Materials 43 5.1 Smooth Metal 43 5.2 Smooth Dielectrics 44 5.3 Polished Surfaces 47 II Bells and Whistles 51 6 Solid Texture Mapping 53 6.1 Stripe Textures 53 6.2 Solid Noise 54 6.3 Turbulence 56 6.4 Bump Textures 56 7 Image Texture Mapping 59 8 Triangle Meshes 63 9 Instancing 67 9.1 Intersecting Rays with Transformed Objects 68 9.2 Lattices 69 10 Grids for Acceleration of Intersection 71 10.1 Grid Traversal 71 10.2 Grid Creation 76 III Advanced Ray Tracing 79 11 Monte Carlo Integration 81 11.1 Monte Carlo Overview 81 11.2 A Little Probability 83 11.3 Estimating Definite Integrals 87 11.4 Quasi-Monte Carlo Integration 88 11.5 Multidimensional Monte Carlo Integration 89 11.6 Weighted Averages 91 11.7 Multidimensional Quasi-Monte Carlo Integration 92 12 Choosing Sample Points 95 12.1 Overview 95 12.2 Generating ID Random Numbers With Nonuniform Densities . . 96 12.3 Generating 2D Random Numbers With Nonuniform Densities . . 97 Contents 98 12.4 Sampling Triangles 12.5 Sampling Disks . iUU 13 Antialiasing ^ 13.1 Rasters 105 13.2 Display Devices 106 13.3 Filtering 107 13.4 Sampling U0 14 Cameras 113 14.1 Thin-lens cameras 113 14.2 Reai Cameras 113 14.3 Multidimensional sampling 116 15 Soft Shadows 119 15.1 Mathematical Framework 119 15.2 Sampling a Spherical Luminaire 122 15.3 Nondiffuse Luminaires 124 15.4 Direct Lighting from Many Luminaires 124 16 Path Tracing 129 16.1 Simple Path Tracing 129 16.2 Adding Shadow Rays 133 16.3 Adding Specularity 135 17 General Light Reflection 137 17.1 Scattering functions 137 17-2 An Advanced Model 139 17.3 Implementing the Model 142 17-4 Including Indirect Light 145 18 Spectral Color and Tone Reproduction 147 18.1 Spectral Operations 147 18.2 Luminance 148 18.3 CIE Tristimulous Values 148 18-4 Tone Mapping 151 19 Going Further 153 Bibliography 155 Index 163
Preface The main code I use to generate images is a ray tracer. The basie ray tracing concepts were developed and popularized primarily by Turner Whitted in the late 1970s and early 1980s. These were expanded into some probabilistic ray tracing by Rob Cook and Jim Kajiya in the mid 1980s. Most of the book's content is due to these pioneers. Of course, many other people dealt with tracking the movement of rays around an environment, such as Appel and Kay, and with luck a full history of computer graphics will get written up someday. I have taught people about ray tracers in several classes and seminars at Indiana University. Cornell University, and the University of Utah. The notes from these classes have grown into this book. This book is intended to fill in missing details that I am always wishing were in the books I read. Itwas never meant to be a survey, and I hope that it doesn't read like one. Its subtitle could be "how Pete Shirley implements a ray tracer," and it should be read in that light. There are many things I don't cover due to my priorities and sometimes ignorance, but if you find you are missing something important, or have a better way to do something, especially if it is simpler. I'd love to hearabout it. If you want to learn everything about ray tracing, there is a variety of books that you should read, but the most complete collection is the online Ray Tracing News, edited by Eric Haines. This is a remarkably complete discussion of ray tracing issues by hard-core ray tracing geeks. Eric also runs the annual ray tracing meeting at the SIGGRAPH annual conference. I hope you will make it there! Eric deserves special praise for his many selfless contnbutions to this field. ABOUT THE COVER The cover image was modeled by Bill Martin at the University of Utah. It uses the "Utah Teapot" developed by Martin Newell in the 1970s. In the reflections
x Preface are one of the first ray traced images by Turner Whitted, and one of the first bump-mapped images by Jim Blinn. The ray tracer that generated the image was written by Steve Parker at The University of Utah with a little help fromPeter- Pike Sloan, Bill Martin, and myself. It can run interactively on medium-sized images on a parallel computer. The serial portion of that code is essentially what is presented in the first two parts of this book. ACKNOWLEDGEMENTS This book would not have been possible without the many students who have helped me determine which presentation methods work best. In addition, much of the materia3 in the book has been taught to me by my teachers, students, and co-workers. In particular. Teresa Hughey taught me many fundamentals of ray tracing; Don Hearn taught me how to make transform matrices simple: Greg Rogers and Kelvin Sung helped me understand how to use object-oriented programming without becoming a zealot: Don Mitchell provided many e-mail answers to sampling questions I never would have worked out on my own: Jim Arvo helped me understand much of the mathematics behind rendering algorithms: Steve Marschner helped me with many subtle coding and algorithmic issues'. Brian Smits and Steve Parker have given me many details of implementation and optimization that have made my code simpler and faster. Michael Herf. Steve Marschner, Peter-Pike Sloan, and Mike Stark were extremely helpful in improving drafts of the book. Michael Ashikhmin develpedthe reflection model presented in Chapter 17 and graciously allowed me to include it before its publication. My parents. Bob Shirley and Molly Lind, provided some crucial baby-sitting that allowed the book to get done. My wife Jean did allthe work in our household for a year, or the book never would have happened. Alice and Klaus Peters deserve special credit for encouraging me to write this book, and I am very grateful to the publisher of this book. A K Peters, for their great dedication to quality publications. Peter Shirley Salt Lake City. USA April, 2000 Introduction This book will show you how to implement a rax tracer. A ray tracer uses simple local algorithms to make pictures that are realistic. Ray tracing is becoming more and more popular because of increases in computing power and because of lts ability to cleanly deal with effects such as shadows and transparency. It has even been used in feature animations, and it is just a matter of time before it is used in video oames. Most importantly. I think writing ray tracing code is fun. and it is a great way to learn many graphics concepts. An overview of a ray tracing program is shown in Figure 1- Here. fae eye js at point e and it is looking through a 3D "window" at two shaded spheres. For each point on the window we send a 3D "ray" to that point and extend it into the scene as shown by the arrow and dotted line. Whatever this ray hits first is what is seen in that pixel. Each pixel can be computed independently by simple computations to form the image shown in the lower-lettof the figure. The two majn tasks of the program are determining what point on what object js hit, and what coior that point is. The first task will require intersecting 3D 'ines with surfaces sucn as spheres, which will require some mathematics. Determining the color will require some simple physics and the generation of rays from the intersection point to see how the world "looks" to that point. All of this will turn out to be quite elegant, which is why people usually enjoy writing ray tracing programs. The book is divided into three parts: • part I The Basic Ray Tracing Program shows how to write a program to make simple images. • Part II Bells and Whistles gives several independent extensions which can be added to your program. These chapters can be read in any order. • Part m Advanced Ray Tracing shows you how to add special effects such as soft shadows, depth-of-field, motion-blur, and indirect lighting.
Introduction IMgure 1. An 'overview of the ray tracing .concept. My (general3[philosophy iisithat'dleani mathematics* maps' directly to> clean'code. The text 'wSlllibe-veryidetail-orientedi Nothing 'will Ibe Heft as ;an exercise to the ireader. )I also assume some comfort with high-school mathematics in genera8. If you are math-phobic, mow iis (the itiime ito iGure yourself; 'take lit: slowly, and keep itJhe (a%dbr<a ifirmly mapped to the geometry: Read every .-'cction carefeffly. and jgo on to itlhe imexit section only when you are iready. Just don't give up! A firm grasp of the fundamentals iis lhard if© (get. but wiffll Uas't ■& Hifetime. Throughout ittie Ibook, )I .assume (thatiilight obeys ithe i niles'of ,'geometrie op- itics andithatjpolarization'does mo't'exist. This iis'Of course not true—Konnen's took l[2S] Contains teamy 'examples 'where polarization is very important, and diffraction is visible 'on isany animals' 'exteriors—butffor at lleast the next couple 'of decades,.a lack of polarization .or physicalioptics effects willi not be the biggest llifiitationf 6ft rendering'cotes. iFfaorescence is another issue I do not deal with. This is am iimnpoiitamtt 'effect, especially in man-made environments where almost revery bright rcolor iis ipartially'duetto J fluorescence. fQlassner |[1:S] developed a Metkod (to iindltrde (fluorescence in ra Tenderer which interested readers should "Consult. il'do fflot 'talk.'about/radiosity, which'already ifias ! three/good books 'devoted ito ift l[5., % 36]. 'There .'are also riiahy topics related to. Monte' Carlo sampling, variants 'of jpath 'tracing, and hybrid algorithms which will be skipped entirely. iFor a teoaier (treatment of image synthesis algorithms, the reader should con-- rsrilt(theUWo^v6tonieslhyrfflassner([r6],randfthelbook by Watt and Watt |[7'0]. JFor an excellent treatment of interactive rendering, see the book by Moller arid iHainesf35]. Introduction I build up the ray tracer one step at a time, and your progg™™ wlU expand wira each chapter. There will ibe images in each chapter you j should duplicate. I emphasize a clean program and .leave -efficiency as a second^ pnonty. C ean programs .are usually :fast programs, so this won't cause as ms^any problems as you .might expect. At the end, you willhave a really powerful ] program wou a jot ,of code. This program can be improved in the many ways s discussed ^ gjg :last chapter, but it will be very useful as is. Let's begin!
Parti The Basic Ray Tracing Program
1 Getting Started Underlying any graphics program is utility code that allows us to think and program at a higher level. In ray tracing programs, there are certain pieces of utility code that pop up repeatedly and are worth coding up front. This chapter descnbes what code you can write before getting started. It uses the vocabulary of an object-oriented language such as C++ or Java, but the principles apply to any language. 1.1 RGB COLORS Your output image will be in a "red-green-blue" color space, referred to for the rest of the book as RGB. You should have three real numbers to represent the three components. You will want to make all the "normal" arithmetic operations work with RGBs. Given RGBs a, b. and scalar k, the following operators should be implemented: -l-a = (a,-. a3. Oj,). -a = (-a,..-ag.-a6). k * a = {kar,kag. kcib) . a*k = (kar.kag. kai,) , a/k = (ar/k,ag/k,abfk). a + b = {ar+br,ag + bg,at, +bb), a-b = (aT—br,ag—bg,ai,—bb), a*b = (aTbT,agbg,abbb), a/b = (aT/br,ag/by,ab/bt,) 3
4 1.2 IMAGES You will want to use simple 2D arrays of RGB colors both for storing your computed image and for texture-mapping. You will want to write a few utility functions to output images, either as they are computed or as they are finished. If you output to a file, use whatever format is easiest to implement. You can always convert the files you want to save to a compact or portable format offline. For now, assume the convention that colors whose components are all zero are black, and colors whose components are all one are white. That is, if RGB = (1, 1, 1) that represents the color white. You must usually convert each of these numbers / € [0.1) into a one byte quantity i € {0,1,..., 255}, where [0,1) indicates the interval of numbers between zero to one including zero but not one. This is accomplished with i = mi(256* /). If you are not sure that / is in that range, an "if" should be added to force i within the range. On most systSms, the intensity on the screen is nonlinear; ;' = 128 is significantly less than half as bright as i = 255. The standard way to handle this is to assume the screen or printer has a "power curve" described by a parameter gamma -.. / ' V briahtness x 1 -— ] . V255/ Thus the "gamma-corrected" image that you output should be i = mr(256*/% The values of gamma for most systems range from 1.7 to 2.3. Most PCs are 2.2 and most Macs are 1.8. The emerging standard "sRGB"' uses gamma 2.2. See www.srgb.com for details. A more complete discussion of this topie is given in Glassner's two volume text [16] and in Chapter 13. 1.3 VECTORS A vector describes an n-dimensional offset or location. For our purposes, we need 2D and 3D vectors. Rather than trying to write an n-dimensional class, you should write two classes vector2 and vector3. For the actual storage of the (x, y, z] cordinates you should use an array. For example, you should have dotal3J rather than x, y, z. This allows a member function element(i) which returns the ith data element without using any ;/ statements. For example, v.element(l) should return the y coordinate of v. This is most efficient if an array is used. 1,3, Vectors 5 You may want to make a separate point class to store locations, but my current belief is that although this improves type checking and aids implicit documentation, it makes coding more awkward in practice. So I advocatejust using vectors to store points; the value of the vector is the displacement from the point to the origin. The length of a vector a = (ax,ay, az) is given by llal'l = ya* -t-aj+a*. You should have member functions that return Mall and ||a||2. If the length of v is one, it is called a unit vector. You may want a special class for that, and you may not. It strengthens type checking, but can interfere with efficiencyanQ increases the number of possibly nonobvious type conversions. You will want to make all the "normal" arithmetic operations for vectors. Given vectors a b. and scalar k, the following operators should be implemented: -i-a -a k * a a,* k a/fr a4- b a-b = = = = = = = (ax.ay.az). (-ar.-ay.-a:), [kaT.kay. kaz). {ktij.kay. ka-). [ar/k.ay/k.a:/k), («.,.+ bj-- fiy + by. az + b:). (<!• _ fcj-.ay - bu.a: - b:) . There are two important operators for 3D vectors; the dot product (•) and the cross product (•<). To compute these use the following formulae: a-b = aTbx + ayby + a:bz. a x b = ( a:/b: - azby. a-ftr - axb:, axby - aybz ) ■ Note that the dot product returns a scalar and the cross product returns a 3D vector. The dot product has a property that is used in an amazing number of ways in various graphics programs: a b = ||a]| ||b|| cos0, where d is the angle between a and b. The most common use of the dot product is to compute the cosine of the angle between two vectors If a and b are unit vectors, this is accomplished with three multiplications and two additions. The cross product a x b has a different, but equally interesting, geometrie property. First, the length of the resulting vector is related to sin 8: ||axb|| = l|a||||b||sin0.
6 /. Getting Started ,, f) t£ aXb J -"""h a Figure 1.1. To establish whether a x b points "up" or "down." place your right hand in a way that your wrist is at the bases of a and b and your palm will push [he arrow of a toward the arrow of b. You thumb will point in the direction of the resulting cross product. Since x. y. and z obey this, they are referred to as a "right-handed" coordinate system. In addition, a x b is perpendicular to both a and b. Note that there are only two possible directions for such a vector. For example, if the vectors in the direction of the.r-. y- and c-axes are given by x = (1.0.0), y = '(0.1,0), z = (0.0.1). then x x y must be in the plus or minus z direction. You can compute this to determine that in fact, x x y = z. But how do we visualize what the geometrie configuration of these vectors is? To settle this, a convention is used: the right- hand rule. This rule in illustrated in Figure 1.1. Note that this implies the useful properties: x x y = +z, y x x = -z, y X z = +X, z '-x y = —x, z x x = -t-y, x x z = —y. 1.4. Rays 1 1.4 RAYS A 3D ray is really a 3D parametric line. It is usually called a ray by graphics programmers for reasons discussed in the next chapter. A ray is defined by an origin location o and a direction vector d. A ray class is very simple; it has these data members and one function: point-at-parameter(t) which returns the point o + td for scalar /. There should be no restriction that d be a unit vector, as will be discussed in Chapter 9. 1.5 INTERVALS An interval is a set of points bounded by an ordered pair [a, b\ where b > a. Intervals are useful in a variety of contexts. You will want to implement a boolean function that tells whether a scalar t is within the interval, a boolean function that tells whether two intervals overlap, and a function that computes the (possibly empty) interval of overlap between two intervals. For example, the overlap between [1.3jand [2. 7j is [2. 3j. 1.6 ORTHONORMAL BASES AND FRAMES Graphics programs usually manage many coordinate systems. For example, in a flight simulator the airplane is stored in the coordinate system aligned with the fuselage, wings, and tail. The orientation part of such a coordinate system is stored as three orrhonormal vectors u. v, and w. which are unit length, mutually perpendicular, and right-handed (u x v = w). These three vectors are called the basis vectors of the coordinate system. As a set they are an orthonormal basis (ONB). The x, y, and z vectors form a special ONB called the canonicalbasis. This •s the natural basis of our program, and all other bases are stored in terms of it. For example, any vector can be stored in xyz coordinates: a = («j-, ov, fij.) = axx + ayy + a.z. We are so : familiar with this that we sometimes forget what these coordinates mean. The coordinates (ar,ay.az)are computed by dot product as ax = a • x, ay = ay, a, = a • z.
g 1. Getting Started The same would apply for any ONB. For example, a = (a • u)u + (a • v)v + (a • w)w. In programs we would often store these coordinates as [0^,^,0^. You might have two different vectors declared a and a-uvw that have different numbers in them, but represent the same directions. Note that I do not say the first vector is a-xyz—the default coordinate system is the canonical one. These vectors are the same geometrically even though they have different components. You would multiply them by different basis vectors before you would compare their coordinates. As you will see, we will use a noncanonical coordinate system when it is convenient, and that will make a-xyz have elements like (7,0,0) or some other simple set of numbers because we are in a "natural" coordinate system. This may all sound like a pain, but stick with it because your program will be simpler and more efficient. You should add some constructors or utility functions for ONBs. For example, you should make one constrttct-from-uvthat takes two vectors a and b and produces an ONB where u is parallel to a. v is in the piane of a and b, and w is parallel to a x b. To accomplish this proceed with the following assignments: a Ni' a x b w = . ||axb|| V = W X U Note that neither a nor b need be unit length, but neither can be zero length, and they cannot be parallel. Also note that the order of these operations must be as above. You should make five other constructors. The first is constnct-fmm-vit which makes v parallel to the first vector. The other four are for vw. iiv. ««•, and wit. Sometimes you want a coordinate system where one of the vectors has a particular direction, and the other two basis vectors can be arbitrary as long as they make a valid ONB. So implement a function constritct-from-vw/hich makes w parallel to a. Unfortunately, this requires an if: w = -— , i|a|1 . if \wx\ < \wy\and \wx\ < wz\ then _ (o.^.-*'J \\(a,wz.-wy)\\ else if \wy\ < \wz\ then _ (mt.'D.-uij) IKii,,, 0.-^)11 else (u.,,-11^,0) V 11(1^.-^,0)11 u = v x w jj. TransformationMatrices 9 This is all so complicated because some components of a couldbe zero. You may want to clean this up using utility functions of vectors such as perpendicular- vector, unit-vector, and index-of-min-abs-component. Once you have an ONB defined by u, v, and w, it is very easy to1 convert from a = (ax,ay,az)back and forth to autIW = (a au = a ♦ u, av = a v, aw = a • w. a = auu + avv + o„w. Note that the asymmetry of these equations arises because a has components stored in the canonical coordinate system while aul,U! does not. To define a whole coordinate system, you will also need an origin point. This origin combined with an orthonormal basis can be called a frame of reference or frame. Define a class frame which is just an ONB and a point. It needs no member functions other than for access and construction. 1.7 TRANSFORMATION MATRICES You should implement a class tnmsform-matrixvihich stores a 4 x 4 matrix of scalars. So a matrix has values mm m0i ni{)2 rnm M_ "tin "Hi m 12 "'13 r"2n m-2\ hi 22 ni2:i _ 0 0 0 1 _ This matrix is used to transform vectors to other vectors. For convenience. I advocate storing the inverse matrix N = M" along with M. Also, you can of course not bother to store the bottom row of the matrix. Note that the matrix should transform points and displacements and normal vectors differently. I will not go over the details why these matrices work the way they do here; for more information see any introductory computer graphics book. Suppose we are given a transform matrix M and a point (location) p, then the transform rule is m-ooPz + maiPy + mo2Pz + mo3 mioPx + mnPy + muPz + TU3 m20px 4- mupy + rn^xpz + m-23 jn-ioPx + m3ipy + m32pz + m33 Mp = moo m-oi fn02 m0s m10 ma mi2 mi3 m20 m21 m22 m23 m30 m.31 m.32 m33 Px Py P; 1
10 /. Getting Started Figure 1.2. When the normal vector in local coordinates is transformed as a conventional vector, you get a nonnormal vector (dotted). A different transformation rule is needed for normalst0 ?et the solid (not dotted) vector. In practice, all the matrices we deal with will have a bottom row of (0.0.0.1) so the transformed point will have a one for its last coordinate. Because vectors indicate a direction they do not change when translated (e.g„ "North" is the same everywhere). But we do want to have scales and rotate count. Fortunately, we can use the row that points set to one to manage this for the transform of a vector v: Mv = "'00 »»01 "1t>2 77(03 ml0 mn m12 m13 rraao ni2i n?22 m23 m-M m:il m-si mX\ I's 0 mo<>t\r + moivy+ m02r, m-wfr + mm'y-L- ml2t': f7!2()('r + m-nl'n + ni22l': niMvT + rn3ii'j,+ m-s,v. So when we transform a ray p(t) = o + tv, we need to make sure we transform o and v according to location and displacement mies respectively. In your code this implies you should have separate functions such as "transformAsLocation." "transformAsOffset." and "transformAsNormal." Surface normal vectors transform a different way still (Figure 1.2) A nice discussion of this is available in the OpenGL Programming Guide [72] which nas a wonderful discussion of transformation matrices in genera3. Instead of Mn, as it would be for a conventional vector, it is (M~"l)r, where T indicates transpose. Ifyou follow my recommendation and store N = M_1.this gives (M_1)Tn = NTn "00 n 10 "20 "30 ram rin ri2i «3i 7102 TJl2 "22 7732 7103 7113 123 «33_ noofz + nmvu + niovs "Olfn + 7lllWj,+ n2lv* 7l02"x + rii2Vy + ri2lVz no3Vx ■+- nisVy + 1231;. I J. Transformation Matrices 11 The first operator the matrix should have is transform-location which takes the location o to anothor location o': ITloOOi + TTloiOj, + 771020s. + 77103 mioOi + mnOt, + 77ii20z + mu m20Ox + 771210„ + m22°z + 7123 1 This matrix is used to transfer vectors to other vectors. Since vectors do not get changed when translated, we "turn off the last column of the matrix for a vector v: O'z o\ 1 Oz 1 77100 77110 77120 0 77101 mu 77121 0 77102 77112 77122 0 77103 77113 77123 1 Ox Oy Oz 1 moo "lot m02 m03 mio mu m.12 mn 771-20 T»21 m22 m23 0 0 0 1 Vz 0 moot'i + ^rioivy+ mm'vz m\ovx +TnnVy + mi2Vz m,'>QVx+ 77121 Vy + Wl22 l>2 0 normal vector n' to a surface transformed by M is n'=(M-1)rn = "00 "11 n20 0 "01 "11 "21 O Tl02 "12 "22 0 "03 1 ••13 "23 1. n where n^ are the elements of N = M Your class should contain both M and N. and should have functions to transform points, vectors, and surface normal vectors. This is a total of six functions: three for each of two matrices. You will also need functions or constructors for common matrix types. First is an identity that leaves points unchanged: f'l 0 0 Ol Identity " " n 0 10 0 JO-" To translate (move) by a vector t = [tx.tu.t:): r 1 Q 0 ** 0 1 0 ty 0 0 1 t, 0 0 0 1 translate(t) To scale by coefficients {sx,sy, s: scaic(sx,sv,s~) = 0 Oj o o 1 0 0 Sz |_0 0 0 lj
12 /. Getting Started To rotate counterclockwise around the x, y, or z axis by angle 0: rotate-x(0) = rotate- y(9) = 1 0 0 cosO O sine 0 0 cosO 0 0 1 -sin6 0 0 0 0 — sin 9 cos 9 0 sinO 0 cos 9 0 0 0 Q 1_ 0' 0 0 1 rotate-z(S) cos d — sin 0 0 0 sin6» cosO 0 0 O 0 10 O 0 0 1 For more arbitrary rotations, we employ ONBs. This may be the most |m. portant measure to avoid ugly programs, so make sure you absorb this pan of the materia3 if you aren't familiar with it. Suppose we want to find the unique rotation matrix which takes the ONB defined by u. v. w to the canonical ONB definedby x. y. z (Figure 1.3). A nice way to work out what matrix is required to represent that transform. Whatever this matrix is, its inverse will take the canonical basis in the other direction, i.e., it will take x to u. y to v, and z to w. So if we assume Mx = u. we can see what the first column of the matrix is. The following matrix accomplishes exactly that: 0 0 0 0 1 11111 0 0 L° = uT Uy u. 0 You can verify that there are no other possibilities for these numbers in the first column, and that the numbers in the blank fields don't matter. We can observe similar behavior by transforming the y and z axes to determine rotate-xyz-to-uvw ux uy "z 0 vx vy vz 0 wx •V, w2 0 0 0 0 1 / 7. Transformation Matrices Figure 13. Some rotation matrix takes an ONB defined by u, v, w to the canonical ONB defined by x, y, z. Because the algebraic inverse of a transform matrix is always the matrix that performs the opposite geometrie transform, and the algebraic inverse of a rotation matrix-is its transpose, we know rotate-uvw-to-xyz = Note that this transpose property assumes the matrix is orthonormal, which all rotation matrices are. If we apply this matrix to u we get Ujr Vx Wx 0 Uy Vy U>i, 0 u- Vz V-': o 0 0 0 1 "T t\l U\r 0 uu l'y Wy 0 u. V; U'; 0 uT Uy _0_ = u • u V • U w • u L o, = HI It 0 0 0 1 The dot products v • u and w • u are zero because u, v, and w are mutually orthogonal. Similiar behavior is true for transforming v and w. 1.7.1 Using Transformation Matrices Transform matrices are usually applied in series. So, for example, to rotate a sphere centered at c about its own center by an angle O, where the "north pole" is an axis in d'rection a, we 1. move the sphere to the origin (Mi), 2. rotate a to align with z (M2), 3. rotate by 6 about z (M3),
14 1. Getting Started 4. rotate z back to a (M~2 *), 5. move the sphere back to c (M^1). Algebraically, this composite transform M is given by M = M^Mj-'MaMaM!. Because the vector is multiplied on the right of the matrix, the transforms tnat are applied first are 0n the right. The only nonobvious rnatrix is M2 which aligns a with z. This is surprisingly easy: Just construct an ONB where w is aligned to a as described earlier, and then create a rotate-u\w-to-x\z matrix as described earlier. 1.7.2 Coordinate Changes Coordinate transforms are a pain because it's easy to get things backwards. Suppose we nave a canonical coordinate system, which is the implicit one that forms tne defauit frame of reference in our program. This is defined bv an origin location o and basis vectors x. y, and z Note mat 0 x y and z' are not really written down anywhere; they are our universal reference and we thus not expressible numerically. They do, however, allow us to set up geometrie Information that relates locations to other locations. For example we know that point (3.4.2) is one Unit away from (3. 4. 3). We sometimes forsjet nlj the coordinate machinery that tells us this is true, -phe point (3 4 0) is "reallv shorthand for 0 + 3x + 4y + 2z. Some grinding tells us the difference vector between the two points is lx so they are one unit apart. Suppose I don't like the origin at o For convenience I wish it were ar o = (2.0.0). If 1 were to write down the coordinates of a point p = (x. u. :) in this new coordinate system it would be (x- 2. y , ;). Recall that this is really shorthand for (2. 0,j)) + (x - 2)x + yy + zz. If we want t0 generaliZe this, and the new origin is o' = (o'xo'.,o'z), the canonical representation of the point is (x, y, z), and the representation in the new coordinate system is [x' 1/ z') then we know \x <y • z) = (x - o'x,y - o'. z - ol). In matrix form this is expressed as "l 0 0 0 1 0 0 0 1 0 0 0 And of course to go from an (*', y', 2')n our newoordinate systerto canonical coordinates is achieved by "x'~ y' -r' x "~ < 4 -o\ 1 " X y z 1 //. TransformationMatrices 15 "1 0 0 0 0 1 0 0 0 0 1 0 o'x °'y o'z 1 1 y' z' 1 1 Note that in all of the above, nothing moved; we are only changing how the same location is described in two different coordinate systems. The same reasoning applies if we want to express the location (x, y. z) in a coordinate system with origin o and an ONB u, v, w. We know that if (u, v, w) represents the point in the new coordinate system then o + xx + yy + zz = o — uu + w + u'w. Since the canonical basis vectors are linearly independent, we can expand an equation in each dimension: UU r + W . U'U'j. In matrix form this becomes 0 1 L~J L 0 0 Wy If; 0 D V 0' ' tf 11 11 And to go from a point in eanonicaioordinates to tne new coordinates we can take advantage of the matrix above being orthonormal (invfflfis'piose): n ux Uy U; 0 v _ i'x vy <■': o W WT ICy ii'; 0 ■A' L» ° ° ^ '^ Note that these are just the same matnces we used to actually rotate the coordinate systems to each other! Now suppose we want a coordinate system with a new origin o and basis vectors u, v, and w- We can move from one coordinate system to another by setting up a third coordinate system with canonical basis vectors and origin o . This implies x y 1 0 0 0 0 1 0 0 0 0 1 0 < °y 0'. 1" , Ur Uy U; 0 vx Vy- Vz 0 irx Wy IV z 0 0, 0 1 0 1 1 , u V 1 w 1 1 L.
16 /. Getting Started And of course the reverse. ux vx Wx 0 H7jy Vy Wy 0 Uz vz wz 0 o O O 1 1 0 0 0 0 1 0 0 0 0 1 0 -o[ -°; -o'. 1 4' y X y z [l\ Now let's apply this to a problem: Change FROM a point written in terms of a coordinate system with origin at (a, b, c) and basis vectors u = (ux,uy,uz),v = (vx, vy, vz),w = (wx.wy,wz) (e.g., the point (u, v, w) is location ox+ by + cz + uu+ w + «rw) TO a point written in terms of coordinate system with origin at (d,e, f) and basis vectors r = (rx,ry, rz),s = (sx.sy,sz),t = (tx.ty,t:). This is just switching from one frame to the canonical frame and from the canonical frame to a third frame: "1 0 0 -J 0 1 0 -e t„ r- 0 O O 1 -/ 0 0 lj [o 0 0 1 All of that may seem confusing, but it will get easier as you use it more. And if you are serious about graphics, read it and reread it. playing around with 2D examples, until you are comfortable with it. Almost all graphics programs, ray tracers, and otherwise use these concepts. The matrix stacks and transform nodes of graphics APIs are built assuming the programmer is familiar with these concepts. 1 0 0 0 0 1 0 0 0 0 1 0 o" 6 c 1 0' 0 o 1 u u w J. Ray-Object Intersections This chapter describes how to compute intersections between rays and objects, and how to produce a simple ray traced image. The genera3 problem we are trying so solve is at what point, if any, a 3D line intersects a 3D surface. The line is always given in parametric form because that is the most convenient for ray tracing. The surface is sometimes given in implicit form and sometimes in parametric form. Solving for intersection is usually a mechanical algebraic exercise. 2.1 PARAMETRIC LINES A line in 2D can be given in implicit form, usually y — rnx-b = 0. or parametric form. Parametric form uses some real parameter to mark position on the line. For example, a parametric line in 2D might be written as x(t) = 2 + 7t, y(3) = 1 + 7t. This would be equivalent to the explicit form v = x - 1. In a parametric 3D line might be x{t) =2+7*, y(t) = 1 + 2t. Z(t) = 3 - 5t. This is a cumbersome thing to write, and does not translate well to code variables, so we will write it in vector formi: p(i) = o + td, where, for this example, o and d are given by o=(2,l,3), d = (7,2,-5).
18 2. Ray-Object Intersections Figure 2.1. A parametric line. Note that the point o can be expressed as p(0) = o + Od, and the point labeled t = 2.5 at the right can be expressed as p(2.5) = o + 2.5d. Every point along the line has a corresponding t value, and every value of t has a corresponding point. The way to visualize this is to imagine that the line passes though o and is parallel to d. Given any value of t, you get some point p(() on the line. For example. at t - 2, p(t) = (2.1,3) + 2(7.2. -5) = (16.5. -71. This genera3 concept is illustrated in Figure 2.1. A line segment can be described by a 3D parametric line and an interval t e [ta,tk]. The line segment between two points a and b is given by p(f) .= a + t(b-a) with* [0.1]. Here p(0) = a. p(l) = b. and p(0.5) = (a + b),,2. the midpoint between a and b. A ray, or half-line,is a 3D parametric line with a half-open interval, usually [0. -x.). From now on we will refer to all lines, line segments, and rays as -'rays." This is sloppy, but corresponds to common usage, and makes the discussion simpler. 2.2 GENERAL RAY-OBJECT INTERSECTIONS Surfaces are described in one of two ways; either as implicit equations, OTparametric equations. This section describes standard ways to intersect rays with each type of object. 2.2.1 Implicit Surfaces Implicit equations implicitly define a set of po'nts that are on the surface f(x,y,z)=0. 2.2. General Ray-Object Intersections 19 Any point (x, y, z) that is on the surface returns zero when given as an argument to /. Any point not on the surface returns some number other than zero. This is called implicit rather than explicit because you can check whether a point is on the surface by evaluating /, but you cannot always explicitly construct a set of points on the surface. As a convenient shorthand, I will write such functions of p = (x, y, z) as /(p) = 0. Given a ray p(£) = o + id and an implicit surface /(p) = 0. we'd like to know where they intersect. The intersection points occur when points on the ray satisfy the implicit equation /(p(0) = o. This is just /(o + fd) = 0. As an example, consider the infinite piane though point a with surface normal n. The implicit equation to describe this piane is given by (p-a)n = 0. Note that a and n are known quantities. The point p is any unknown point that satisfies the equation. In geometrie terms this equation says "the vector from a to p is perpendicular to the piane normal." If p were not in the plane, then (p -a) would not make a right angle with n. Plugging in the ray p(f) = o + td we get (o + rd - a) • n = 0. Note that the only unknown here is /. The rest of the variables are known properties of the ray or piane. If you expand this in terms of the components (x. y. z) of p you will get the familiar form of the piane equation Ax + By + Cz + D = 0. If we find a t that satisfies the equation, the corresponding point p(f) will be a point where the line intersects the piane. Solving for /, we get (a — o) • n f~ d n ' If we are interested only in intersections on some interval on the line, then this t must be tested to see if it is in that range. Note that there is at most one solution to the above equation, which is good because a line should hit the piane at most once. The case where the denominator on the right is zero corresponds
20 2. Ray-Object Intersections to when the ray is parallel to the piane, and thus perpendicular to n, and there is no defined intersection. When both numerator and denominator are zero, the ray is in the piane. Note that finding the intersection with implicit surfaces is often not this easy algebraically. A surface normal, which is needed for lighting computations, is a vector perpendular to the surface. Each point on the surface may have a different normal vector. The surface normal at the intersection point p is given by the gradient of the implicit function A/(P) 9/(p) df(P\ dx ' ay " dz )' The gradient vector may point "into" the surface or may point "out" from the surface. 2.2.2 Parametric Surfaces Another way to specify 3D surfaces is with 2D ' puranierenThesc surfaces have the form x = f(u. r). y - gU'-v)- 2 = h(u.i). For example, a point on the surface of the earth is given by the two parameters longitude and latitude. For example, if we put a polar coordinate system on a unit sphere with center at the origin (see Figure 2.2), we get the parametric equations x = cos <5 sin O, y = sin 0 sin 6*. 2 = cos 9. Ideally, we'd like to write this in vector form like the piane equation, but it isn't possible for this particular parametric form. We will return to this equation when we texture map a sphere. To intersect a ray with a parametric surface, we set up a system of equations where the Cartesian coordinates all match: ox + tdx = f(u, v), oy + tdy = g(u,v), oz + tdz = h(u,v). n = V/(p) = 2.5. Ray-Sphere Intersection 21 Figure 2.2. Polar coordinator on the sphere. These eoordinates will be u>ed in se\em! p!uces later in the book. Here we have three equations and three unknowns (/. u. and <■). so we can numerically solve for the unknowns. If we are lucky, we can solve for them analytically. The normal vector for a parametric surface is given by , , fdf dy 0h\ (Of 0() 0h\ \Ou On du \c)r dr dv I 2.3 RAY-SPHERE INTERSECTION A sphere with center c = (cT, c,,.c-) and radius R can be represented by the implicit equation (x - cTf + (y -r,,)- + (; - cz)2 - Ft2 = O. We can write this same equation in vector form: (p-c)-(P-c)-fl2 = 0. Again, any point p that satisfies this equation is on the sphere. If we plug points on the ray p(t) = o + td into this equation we can solve for the values of t on the ray that yield points on the sphere: (o + id - c) • (o + td - c) - B ? = O.
22 2. Ray-Object Intersections Moving terms around yields (d • d)t2 + 2d • (o - c)t+ (o-c)*(o-c)-R2 = 0. Here, everything is known but the parameter t, so this is a classic quadratic equation in t, meaning it nas the form At2 +Bt+C-0. The solution to this equation is t _. -B ± %/B2- 4AC 2A Here, the term under the square root sign, B2 — 4AC, is called the discriminant and te"s us how many real solutions there are. If the discriminant is negative. Its square root is imaginary and there are no intersections between the sphere and the line.Jf the discriminant is positive, there are two solutions;one solution where the ray enters the sphere, and one where it leaves. If the discriminant is zero, the ray grazes the sphere touching it at exactly one point. Plugging in the actual terms for the sphere and eliminating the common factors of two. we get: -d ■ (o - c) ± y'(d • (o - c))' - fd • di |(o - c) • (o - c) _ #J) (d~d) ' 'n an actual implementation, you should first check the value of the discriminant before computing other terms. If the sphere is used just as a bound ins objeaet for more complex objects, then we need only determine whether we hit it and checking the discriminant suffices. The normal vector at point p is given by the gradient n = 2(p — c). The unit normal is (p — c) 'Ft. 2.4 RAY-BOX INTERSECTION When y0U nave an axis-aligned box with corners pn = (.r0. ;/n. ;„) and p _ [xi.yi. zi), one could do an intersection with all six rectangular sides, but there is a standard trick that is faster. Instead, think of three infinite slabs °f space: x 6 t^Oj^iJ. y € illo, 2/i].and ~ € [20.21.]. We can compute the intersection of ray p( ) = o + td and slab x e [i0lI,]: ^o = ox + tx0 dx, xi = ox + t.xldx. 2.4. Ray-Box Intersection Figure 2.3. A 2D ray intersecting a 2D box. Left: The intersections with the x slab are elven between the solid circles, while the intersections with the y slab are given between the open circles. Right: the intersection of the two intervals in ray parameter (4) space is represented by the bold line. Points within this ray parameter interval are in the box. The unknowns here are fr() and txl. so the line segment on ray ray is given by t e !(.r0 - ox)/dr. (xi - or)/dx}. Note that it would be nice computationally if a line segment t [a. 6; were a valid increasing interval, that is b > a. but we don't know this for the slab because the ray is going "backwards" in x if d,r < 0. So. we can convert the interval t 6 [f.r(l.r.ri] to t € tx ,„,„,f rm„,r))y setting it to [fro-fritf (^> 0 and [^ri-frol otherwise. Similarly, we can get the intersections with the y and z slabs t e [t,im,„. tuiniir] and t e [tz ,„,„. t: „mr\. Each of these intervals can be merged into overlapping intervals. For example, if the .c slab interval is f e [2.4] and the y interval is / 6 3.5.5 . then the overlap of these two intervals is i 6 [3.4]. The intersection of all three •''• y, and z intervals is where the ray is inside the box. This principle is illustrated in Figure 2.3. If the intersection of the three intervals is empty, the ray misses thebox. There is a nice way to code described by Smits and discussed further in his article on efficient ray tracing [57]. It avoids tests for degenerate cases by taking advantage of the IEEE floating point properties: Comparing anything against NaN returns.false, everything is less than infinity.sad everything is greater than minus infinity. if dx > O then txmin <— (-£() - Ox)/dx txmax *~ ixl - Ox)l'dx else txmin •*- Ol - ox)/dx txmax <— {XQ ~ Ox)/dx
4 Z Ray-Object Intersections if dy > O then ty min <~ (j/0-— Ovi/dj, Xy m-iu: <—'(jl - Oy)/dy else futnin <— .(yr- oyydy tymax*- (yo - oy)/dy if dt > 0 then ^min <~ "2{)"- 0:)/az t z max +- (21 - O- )/ds else fe min 4-(21 — 0.j/dz tz max ■<— (-0 - Oz)/d2 {Findthe biggest of txmul. tymln,tznun} if f.r mm > tj, „„■„ thdl f(] <"j.r .-,-,„„ else t(> '"'Otllll! if /; ,„, „ > to then t<) *~~tz „i ,„ {Findthe smallest offx.,„„.r. tumnj.,tz ,„„.,.} '■* *.r Fiidi < fy/ri«(f then tl '<-'^m«.r else ' 1 ^ < u m; av r if t: ma < 3\ then ti '*- t.nuir .{Intersection with box at /(1 and ti if t0 < fj hit -<— .f -< 11; 2.5 RAY TRIANGLE INTERSECTION There ;>ire -a variety'of ray-polygon and ray-triangle intersection routines. These are discussed extensively by Eric Haines in various ray tracing news articles that you should read' once you get your basie ray;, tracer working. 1 will present only one simple routine for triangles. 'A 'triangle is defined by three points a, b and c. If not co-linear, these points define a piang. A common way to describe this piane is with barycentric coordinates: p(ay0,7} = aa+ ,3b + 7c (2.1) 2.5. Ray-Triangle Intersection 25 Figure 2A Barycentric coordinates can be found by computing the areas of subtriangks. with the constraint Q + J-- = 1. Barycentric coordinates seem like an abstract and unintuitive construct at first, but they turn out to be powerful and convenient. Barycentric coordinates are defined for all points on the piane. The point p is inside the triangle if and only if O < Q < 1. 0<j < 1. O < -. < 1. If one of the coordinates is zero, you are on an edge. If two are zero, you are at a vertex. One way to compute barycentric coordinates is to compute the areas A„. Ab. and Ac, of subtriangles as shown in Figure 2.4. Barycentric coordinates obey the rule ••: Q = a, i a. 0 = AbIA. 1 = AJA, where A is the area of the triangle. This rule still holds for points outside the triangle if the areas are allowed to be signed. We can eliminate one of the variables by plugging in a = 1 — /3 — 7 into Equation 2.1: p(a, /?,7) = a + 0{b - a) + 7(c - a).
26 2. Ray-Object Intersections 2.5. Ray-Triangle Intersection figure 2.5. An intersection of a ray and the plane aintainina the triangle. Figure 2.6. Bup-centrie coordinates on a piane intersected by a ray. Now points are in the triangle if and only if .?-rv< i. 0 <J. 0 < -v. Together 3 and 7 parameterize nonorthogonal coordinate system on the piane as shown in Figure 2.5. The ray t = o + rd hits the piane when o + td= a + ;i(b - a) + -{c - a). (2.2) This hitpoint is in the triangle if and only if J > 0. 7 > 0, and j + 7 < 1. A configuration where the ray hits at (3. 7) — (1.2. 0.8) is shown in Figure 2.6, which is not inside the triangle as predicted by the sum of 3 and 7 being two. To solve for t, 3, and 7 in Equation 2.2, we expand it from its vector form into the three equations for the three coordinates: This can be rewritten as a standard linear equation: "x a,j a. -bx ^y -b. a.r - cx °y ~ cy a. — c- dx rfv rf- "J" ■) J - = aT - Ox ay - oy az — o- The fastest classic method to solve this 3 x 3 linear system is Cramet This gives us the solutions: ax ay a- - Or ~ <>» — o- (>.t - Cr au - ?a a._— c, d. dy d; Or- av az - -bx - by -b- Qj- - a,j - d~- -ox °y - o~ dx d« d. ox + tdx = 0(bx -f y(cx - ax o„ _i_ td. + y + ""y o. j. td. o-y+P(by~ay)+1(cy-ay)> = a, + 0(bz-az)+j(cz ax ay- a~- - bx -by -b: ax — *Iy - az — Cx cy c, ax - ox *r - o, az — oz
2. Ray-Object Intersections where the matrix A is b, by b2 a,j a a A = and |A| denotes the determinant of A. The 3x3 determinants have common subterms that can be exploited. Looking at the linear systems with dummy variables a d b e F f ~3 7 t f k J Cramer's rule gives us 3 = j(ei - hf) where t = M k(gf - di) + l(dh- eg) M i((ih-jb)+ h(je al) 4- g(bl- kc) M /(((A- - jh) + f(jc- al) + d(bl - kc) M a(ei - hf) + b(gf- di) + c(dh - eg). These equations can be put into code mechanically by creating variables suchas a and ei-miiuis-hfanA assuming that the compiler will (at least eventually) do its job. There are faster ways to compute triangle intersection (e.g. [36]). but this way is straightforward and requires no global storage besides the triangle vertices. 2.6 MORE THAN ONE OBJECT Once you have multiple objects, you will need a routine to return the firstobject hit by a ray. Usually you will be only interested in hits for / € [fo.fi] for a ray p(f) = o + fd. For example, if you are interested only in hit points "in front" of o, that corresponds to t e [0. do]. If you are using an object-oriented language, you should make ah abstract class or interface or superclass whatever your language calls a class you inherit from. This class is for anything you can hit which I will call surface. This class needs a routine hit that returns true or false for whether a ray hits it, and fills in some data (like the / value) if it returns true. Since a list of objects can be hit, the list is also a surface and has a hit function: 27. A Simple Ray Tracer 29 function surfacelist.hit(ray o + td, t0, ti.prim) {primis a pointer to the object hit} [t and prim are filled in if hit returns true} bool hitone <- false for all surf in list do if surf->hit(o + id, to, t, prim) then hitone ■*— true return hitone Note a trick in this code: The interval passed to the object is [to-t] where t is the smallest t of an object hit so far. This uses the interval to sort for you. With this interface the code for a sphere intersection is as follows: function sphere.hit(ray o + td. to. ti, prim) {sphere has center c and radius R} float A <- dot(d.d) float B <r- 2*dot(d.o-c) float C <— dot(o-c.o-c) discriminant <- B*B-4*A*C if B > epsilon then prim <— this sqrtd 4— sqrt(discriminant) t <- (-B - sqrtd) / (2*A) if f > to and t < fi then return true t 4- (-B + sqrtd) / (2*A) if t > to and t < t\ then return true return hitone The epsilon in the code above is to avoid degenerate code when the ray is tangent to the sphere. You may want to also return the hitpoint p = o + td and the surface normal at the hitpoint. I usually have a class that contains all the "returned" variables I compute that I pass in as an argument, and I think you will find you will like it if you do the same. 2.7 A SIMPLE RAY TRACER We can now generate a simple image using spheres and triangles with an orthographies camera. Let's assume we have 101 by 101 pixels {i,j) numbered
2. Ray-Object Intersections Figure 2.7. Sample image with sphere and triarmlc (0. 0) through (100. 100). For each pixel generate a ray r = o + td. such that o = (i.j.O). d = (0.0,-1). where me negative c direction is chosen for d to avoid reinventina the left-handed coordinate system. Let's create a sphere with center (0. 0. —150) and radius 100.1, and trianale with vertices (0,0.-100). (100.1.0,-100). and (50.100.1.-100). Now put these [W0 objects into a list and for each ray find the closest hitpoint. if you hit the sphere, color pixel (i.j) light grey. If you hit the triangle, color it dark grey. If you hit neither, color it black. You should get an itnage that looks like Figure 2.7. Lighting and Shadows To make your images more realistic, the shading on objects should depend on both surface orientation and lighting direction. For marre (nonshiny) materials.a good approximation to how surfaces react to lighting is given by Lambert's Law: L = ER cos Q where E is the color of the light source (RGB). R is the reflectance of thesurface (RGB), and d is the angle between the surface normal at the illuminated point, and the direction from which the viewing ray comes. 3.1 IMPLEMENTING LIGHTING Recall that the viewing ray is coming into the illuminated point. Let's define a unit-length vector e pointing in the direction d comes from (it points away from the surface): _ d e"_iidi: Figure 3.1. Geometry for lighting computation. 31
32 3. Lighting and Shadows Figure 3.2. Two images illustrating lighting. These images have the same viewing rays used at the end ofthe last chapter, and two spheres with centers (50.0. -80.0. -1000) and (50.0. 50.0. -IIXX)). and radi* 100 and 30. The lighting vector 1 is (0.1.0). Left: Using absolute value when L is negative. Right: Clamping negative L to zero. You should define 1 to be a unit vector toward the direction from which the light comes (it also points away from the surface). In this context. Lambert's Law becomes L = EH(n-l). The thing to note is that there is no e in this equation! This means the surface does not change brightness as you move your eye. You should observe that many "matte" surfaces in the real world don't change brightness much as you move your viewpoint, so this is not a bad property. A problem with this formu3a is that L can be negative. There are two potential solutions to this: Take the absolute value, or clamp answers below zero. These alternatives are shown in Figure 3.2. 3.2 ADDING SHADOWS Shadows should occur whenever a point "sees" another object in direction 1. This can be accomplished as follows: 1. When the viewing ray hits an object at point q, create a shadow ray p(t) = 1 + tl. 2. If the shadow ray hits no objects, then apply the lighting equation. Otherwise, set L to zero. 3.2. Adding Shadows 33 1 1 incoming light 1 1 i 1 f T k viewing ray /shadow ray >i / J5 1 incoming * 1 i viewing ray u >1 2 j f jr: ^> y 7fq ] 1 light 3 ♦ T } Figure 3.3. Shadow ravs originate at q and propagate in the direction from which the light comes. Intersections at or behind q (f < 0) are not of interest. An important thing to realize is that "hits no objects" above does nnot include any hits with 3 < 0. This can be seen in Figure 3.3 where the shado'»w ray hits the lower object at both / = O (where p(0) = q + 01) and some tmegative /. Instead, we are only interested in positive values of t. A problem to keep in mind is that because of finite-precision arithmetic, the shadow ray may intersect the surface q at some t value other than zesro. Tf this number is positive, we will detect a false shadow as shown in Figure: 3.4 (left). <<$$^\> Figure 3.4. Left: Using an interval t £ (0. oo) causes some rays to hit the surface : at q causing black pixels. Right: Using t € (e, oo) avoids these artifacts.
34 3. Lighting and Shadows ^ unclosed model arbitrary normals outward normals Figure 3.5. The three classes of models. Sometimes these dark pixels are more irregular and resemble a Moire' pattern. Instead, we pick some smali e that t must be bigger than. This is an inelegant hack, but doe^ usually solve the problem. For a more principled discussion of such problems, see the paper by Amanatides and Mitchell [11. 3.3 OUTWARD NORMAL VECTORS When you implement the simple lighting in this chapter, an important issue will arise: The normal vector n for a polygon may point into the surface. This matters because it changes how your code computes cosines. It rays can come from either side, this has to happen for one side of the polygon or the other. You must now decide on a convention for your ray tracer: Does it assume outward- facing surface normals? This problem is shown in Figure 3.5 where three classes of models are shown. In the first, surfaces can be hanging in space, so normal vectors are arbitrary. In the second, surfaces must be closed, meaning they huve a well-defined inside and outside, but the normals can tace in or out. The third has outward-facing normals. Outward-facing normals certainly make the job of writing your program easier, so I would suggest you assume your models will have outward facing normals. This is in the long tradition of leaving any hard work to the modeling program. A convention that is usually followed is that polygonal models will obey the right-hand rule, meaning that a polygon that contains three vertices p0, Pj, and p2 will generate a normal :(Pi -Po) x (P2-P0) ■ If you do assume outward-facing normals, you can eliminate the epsilon-hack from shadow ray testing. When testing for shadow ray intersections, disregard 3.3. Outward Nurmul Vectors 35 any intersections where n • 1 > O at the intersection points. This counts only intersections where the ray is entering the object, rather than leaving it as is true at q. Alternatively, you can flip normals when they point "into" the surface, i.e., if (d • n) > 0.
Viewing The simplest image aquisition device we can makers ^pinhole camera: We ju'st take a box painted black cm the inside^ poke" a' hole in one side;, and tape film; to the inside of the opposite side-(Figure 4.1). In this chapter; we'sittiuliate ' such a device. As shown in the figure, we can compute light passing through some rectangle in front of the camera.- In effect, this is computing the: light coming through a "window" in front of the ""viewer." The only reason fo do'this is; that it may be more intuitive: it is for most people. r^^^m \ i f ■*—_ : Mr '" ",' - ':.? '■"' pCohofc *V---J Figure14.1. A real pinhole- camera. Light enters the pinhole froma' specific direction a'tfd' exposes; a particular part of the film. The film will capture a scene in sharp focus, but it fequifes significant exposure lime. The color of Tight at point s in the difectioh shown will stay the sanie as it passes- through the pinhole, and as it hits the film at f. 41 AXIS-ALIGNED VIEWING We can implement a synthetic version of a pinhole camera; A" nice'thing isul&t we can create a virtual film piane in front of the camera" and forget-that-the filhi1 is behind the pinhole. To do this, we need to set up a projection of .the film-out 37
4. Viewing Figure 4.2. An image passing through a rectangle at distance s wili he mapped unto the tilm. in space. This is shown in Figure 4.2. Note that the selection ofthe distance s is arbitrary: if we make it bigger the rectangle and the image grow, and the same image will be saved. To implement the camera, we pick a specific rectangle aligned to our viewing system as shown in Figure 4.3. The viewing system has center o which is defined to be the origin in uvw coordinates and is aligned to the uvw basis. Points a and b are the corner points of this rectangle. The rectangle need not be centered on the gaze direction. The rectangle is in the negative w direction because we want to both maintain a right-handed coordinate system, and have u go to the right on the rectangle. The points we sample on the image are mapped onto that rectangle as shown in Figure 4.4. The equations for mapping a pixel (i.j) on an nx by ny pixel image to the correct (u, v) are i u = a„+(6„-a„) . Tlj - 1 v = av + (6t - o„)—1—.-. ny - 1 This means the ray in uvw coordinates is ' i i p(t) = (0, 0, 0) + t ( an + (6U - au) - -,a„ + {bv - av)— s \ rij. - 1 ny - / • 4,2. Setting View Parameters 39 Figure 4.3. The viewing rectangle is a distance s from o along the negative w axis, and is parallel to the uv piane. (0.0,0) -. b = (blrb,.-s) a = (au.a,,-s) Figure 4.4. Pixel coordinates are mapped to the 3D window in uvw coordinates. 4.2 SETTING VffiW PARAMETERS If we choose to have an axis-aligned view from the origin then we can use just the ray above as xyz coordinates. However, we would usually like to be able to set view location and orientation. There are many ways to do this, but I will describe only my favorite, shown in Figure 4.5.
40 4. Viewing Figure 4.5. Viewing trom an arbiirury poiition. The variables that are specified are: • e. the xyz eyepoint (pinhole); g, the xyz direction of gaze (This is also the normal to the viewing rectangle. so it is sometimes called the v/Vvv '-plane nortnal '"• • v,,p. tne view-up vector. This is any vector in the piane of the £aze direction g and the vector pointing out of the top of the heatl; • s. the distance from e to the viewing rectangle: a„,a,,.6„.6„, the uv coordinates of the rectangle corners. From this information we can establish an aligned uvw frame where e is the origin and the basis vectors are w = -A. llvupX W|| V = W X U. Note that y°u could also just make a call to make-ONB-from-WV(g,vupfc have such a function implemented So we have the ray in Uvw coordinates, and we have the xyz coordinates of the uvw basis vectors and origin. We could construct a coordinate transform A 2 Setting View Parameters 41 matrix aS described111 Chapter 2, or we can just proceed from the definition^ coordinates: plf) = e + t((a» + (bu- o.u)^^) u + (a, + (fc, - a»)^Ti) v + ~sw) Note that this 1S a Prettv genera3 viewing system so some care mustbe taken in setting parameters. If you want the viewing 'rectangle centered around the gaze airectl011> make sure au = -bu and av- -&„. if you want t0 have square pixels, make sure that bu — Ou _ Ttj bv - av ny Fln!jly' note tnat although s is arbitrary as long as it is positive, the bigger it is the bigger (a a„.bu.bt,)have to be to get the same imaee. The ratio of bu~au t0 s 1S the tanSent of half of the -'vertical field-of-view." Tf vn]] are more comfortable with that concept, set s to one and input the vertical field-of-view. One nice thing about not requiring the viewing rectangle to be centered around the direction is that you can run different "tiles' of a si le ■ in concurrently running programs and then join them together for a lazy programmer's Parallel code- You can also generate stereo images with proper eye separation; neither eye is centered on the screen if the nose is. example is shown in Figure 4.6 with parameters e = (0-0.2). vup = ^■l-°)J = (0-0-2)- (*u,av) = (-2.-2). (bB.M = (2.2) s = 2 - 101, and a sphere with center (0.0.0). radius >/2. and the u8"f vector Figure 4.6. A sample use of viewing parameters.
42 4. Viewing (0,1,0). An ambient factor of 0.1 is added, and the sphere reflectance is 0-9, so colors range from 0.1 to 1.0. Nol:e that you could change g to anything with a positive y component and a zero x component and the image won't change. Change vup to point in the x direction and the image should rotate 90 degrees. Decrease ,s and the sphere should '°°k smaller. Change e to be any vector in the xz piane where x*+z2 = 2 and the image should not change. Basic Materials Materials such as glass and metal which show mirror-like reflection and refraction are collectively known as specular surfaces. The physics of these surfaces is well-understood and is straightforward to approximate in an implementation. Surfaces that show some diffuse and some specular behavior, such as smooth plastic, are more complex, but the approximation I like to use works reasonably well and is not too difficult to implement. 5.1 SMOOTH METAL Smooth metals are the simplest materials to describe, and they are easy to implement in a ray tracer. Smooth metals obey two principles: • The law of reflection, which States that the angle of incident light relative to the surface normal is the same as the angle of reflected light, and that the incident direction, surface normal, and reflected direction are coplanar; • The Fresnel eauations. which describe how much of the light is reflected, and by complement how much is absorbed. Let's assume we have functions to compute the lighting on a diffuse surface, the reflected vector, and the reflectance. The function for computing a ray color that "sees" a diffuse or metal surface is function color(ray o + t d) if r hits object at point p with normal n then if p is diffuse then return R{p) * direct-light(p.n) else r <— reflect(d. n) return R(pj * color(p + tr) else return background 43
44 5. Basic Materials - - ^ i Figure 5.1. The reflection from a smooth surface. To implement the law of reflection, observe Figure 5.1. where the incident direction is d. the surface normal vector is n, and the reflected vector is r. As can be seen in the Figure, r = d + 2a. The vector a is parallel to n but has length of d scaled by the cosine of the angle between d and n. This yields r = d 4- 2a d» n d — £ n Note that if n is a unit vector, dividing by the square of its length is not needed. To compute the reflectance, the simplest approximation is to set it to some constant RGB value. This works well enough for most images. However, the reflectance of real metals increases as the angle between d and n increases. Schlick developed ah accurate approximation to the rather uglv Fresnel equations [48] to simulate the change in reflectance: R(8) a R0 + (1 - Ro)(l -cos£)5 (5.1) where Rq is the reflectance when d is parallel to n. Try setting Rn to 0.8 for all three channels RGB. This will make an object that behaves similarly to any modem "stainless" alloy. Although there is a smali error implicit in Schlick's approximation, it is no bigger than the error we imposed when we decided not to use polarization, so you shouldn't worry about that. 5.2 SMOOTH DIELECTRICS A dielectric is a transparent materia3 that refracts light. Diamonds, glass, water, and air are dielectrics. Dielectrics also filter light; some glass filters out more 5.2. Smooth Dielectrics 45 red and blue than green light, so the glass takes on a green tint. When a ray travels from a medium with refractive index n into one with a refractive index ntt some of the light is transmitted, and it bends. This is shown for nt > n in Figure 5.2. Snell's Law tells us that n sin 8 = nt sin O . From this and the equation shr d+ cos20 = 1, we can derive a relationship for cosines: "2 (l-COS^) cos-6' = 1 nt From the figure, we can see that n and b form a basis for the piane of refraction. Important: The following discussion assumes d and n are unit vectors, so when you implement this be sure to make unit length variables in this routine. By definition, we can describe t in this basis: t = sini9'b - cos#'n. Since we can describe d in the same basis, and d is known, we can solvefor b: d b sin #b - cos On. d — n cos 0 sin 0 Figure 5.2. The refraction of light at a smooth surface.
46 5. Basic Materials This means We can solve for t with known variables: n (d + ncos#)) t = — --ncos^' nt n (d - n(d • n)) f n2 (1 - (d - n)20) — — ni /1 = . nt \j nf Note that this equation works regardless of which of n and nt is bigger. For homogeneous impurities as is found in typical glass, a light-carrying ray's intensity will be attenuated according to Beer's Lena. As the ray travels through the medium, it loses intensity according to dl = —CIdxwhere dx is distance. This means dl/dx = —CI. This is solved by the exponential / = fcexp(-Cx) + k'. The strength of attenuation is described by the RGB attenuation constant a, which is the attenuation after one unit of distance. Putting in boundary conditions, we know that 7(0) = /()• and ^(1) = al(0). The first implies I(x) = Iq exp(-Cr). The second implies /,,« = 70exp(-C) so -C = ln(a). .So the fina3 formu3a is I{*) - l(0)e-inil"s where Us) is the intensity of the beam at distance * from the interface, hi practice, we reverse-engineer a by eye because such data is rarelv easy to find. To add transparent materials in our code, we need a way to determine when a ray is going "into" an object. The simplest way to do this is to assume that all objects are embedded in air with refractive index verv close to 1.0, and that surface normals point "out" (toward the air). This concept is illustrated in Figure 5.3. The code segment for rays and dielectrics with these assumptions is: if p is dielectric then r = reflect! d. n) if d • n < O then t <- refractfd, n,n) c < d n Kj- ^- K„ i— fjflj i— / else t <-- refract(d. -n. 1/n) c <- t n kT «■- exp(-ori) kg*-exp{-ast) kb f- exp(-a(,r.) i?o<-(n-l)2/(n+l)2 R <- R0 + (1-Ro)* (1 -c)5 return k(R * color(p + tr) + (1 - R) * color(p + tt)) 5.3. Polished Surfaces Figure 5.3. If a direction and the surface normal have a negative dot product, the direction points into the object. This is useful for deciding whether the ray bends in or out. The code above assumes that the natural log has been folded into the constants (ar. as. ai,). An image that uses both Fresnel equations and Beer's law is shown in Figure 5.4. 5.3 POLISHED SURFACES Many surfaces are dielectrics, but have smali reflecting particles embedded which diffusely scatter light (e.g., plastic), or coat an underlying diffuse surface (e-g- finished wood). Such surfaces act as combinations of specular and diffuse surfaces. An interesting aspect of this behavior is that when the incoming light is "grazing" (9 is near 90 degrees), the specular component dominates, and when the incoming light is near-normal (0 is small), the diffuse interaction dominates. This is actually not surprising; the specular reflectance approximated by Equation 5.1 approaches one for the grazing case, so little light goes into the dielectric to interact with the subsurface materia3 that creates the diffuse behavior. In the normal case, the typical normal reflectance is around five percent, so most of the light is transmitted to interact diffusely with the subsurface materia3. A simple model for these polished surfaces tries just to maintain physical constraints of reflection and the diffuse/specular behavior [53]. The specular component acts just like the reflected part of a dielectric. The diffuse component
5. Basic Materials 48 j 3 Polished Surfaces 49 is given by L = R(p)E (1 - (1 - n ■ e)5) (1 - (1 - n "J)5) • "turns off the diffuse component if either the light or the eye is near D. ° and does so in a way that prevents a violation of energy conserva l Figure 5.4. Dielectrics rendered with Fresnel equations and ^eer s law.
Part II Bells and Whistles
Solid Texture Mapping In previous chapters, we used the reflectance at a point x as a function R{x). For a solid-colored object this might return just the reflectance of the object that contains x. But for objects with texture, we should expect R(x) to vary as x moves across a surface. One way to do this is to create a solid texture that defines an RGB at every point in 3D space. When a ray hits a surface at x. this function can be evaluated and the return value can be used for R{x). Such a strategy is clearly suitable for surfaces that are "carved" from a solid medium, such as a marble sculpture. In this chapter, we describe how to add interesting solid textures to your system. More traditional surface textures are covered in the next chapter. A more extensive treatment of procedural te,\tures can be found in the book by Ebert et ai. [12]. 6.1 STRIPE TEXTURES There are surprisingly many ways to make a striped texture. Let's assume we have two colors en and c\ that we want to make the stripe color. We need some oscillating function to switch between the two colors. An easy one is a cosine: RGB stripe( point x ) if sin<x.z()) > 0 then return sO else return si We can also make the stripe's width w controllable: RGB stripe( point x, double w ) 3f sin(7r * x.z() / w) > 0 then return sO else return si 53
6. Solid Texture Mapping Figure 6.1. Various stripe textures. It we want to interpolate smoothly between the stripe colors we can use a parameter t: RGB stripeCpoint x. double w ) double t <- (1 + sin(- * x.z()iw))/2 return f * sO + (1 - t) * si These three possibilities are shown in Figure 6.1. 6.2 SOLID NOISE We would like to be able to make "mottled" textures such as we see on birds' eggs. Perlin introduced a way to do this which can be seen in a huge number of graphics images [40. 41 ]. Just calling a random number for everv point wouldn't be appropriate because it wouldjust be like "white noise" in TV static. We would like to make it smoother without losing the random quality. One possibility would be to blur white noise, but there is no practical implementation of this. Another possibility would be to make a big lattice with a random number at every lattice point and interpolate these random points for points between lattice nodes. This would make the lattice too obvious. Perlin used a variety of tricks to improve this basie lattice technique so the lattice was not so obvious [41). Here is his basie method: kl + i LsJ+i L-J + i n(x. y. z) = Y, E E fiO'*(* " *'« ~ 3- = ~ k) where (x, y. z) are the Cartesian coordinates of x, and fijjfc("iv, w) = ^{u)u}(v)ui(w){rijk* (u, v, u;)), :,-: 6.2. Solid Noise Figure 6.2. Absolute value of solid noise and noise for scaled* and y values. and uj{t) is the cubic weighting function: „.m = /21tl3-3|t|2 + 1 ififl<L 10 otherwise. V The fina3 piece is that r,^- is a random unit vector for the lattice point (x. y, z) = (j j, k). Since we want any potential ijk. we use a pseudorandom table: T,j, = G(Q(i+0(j+o(k)))) where G is a precomputed array of n random unit vectors, and o(i) = P[i mod n] where P is an array of length n containing a permutation of the integers O throush n — 1. In practice. Perlin reports n = 256 works well. To choose a random unit vector (rx. r,;, v.) uniformly first set vx = 2 * random(O.l) - 1. vy = 2 * random(O.l) — 1. c. = 2 * random(0.1) - 1. Then, if (v- + t>2 + L>2) < 1 make the vector a unit vector. Otherwise, keep setting it randomly until its length is below one and then make it a unit vector. This is an example of a rejectionmethod. which will be discussed in more depth later. Essentially, the less than test gets a random point in the unit sphere. ancj the vector for the origin to that point is uniformly random. That would not be true of random points in the cube so we "get rid" of the corners with the test. Because solid noise can be positive or negative, it must be transformed before being converted to a color. The absolute value of noise over a 10 x 10 square is shown in Figure 6.2 along with stretched versions. These versions are stretched by scaling the points input to the noise function. The dark curves are where the original noise function went from positive to negative. Since noise varies from — 1 to 1, a smoother image can be gotten by
56 6. Solid Texture Mapping Figure 63. Using 0.5 * noise + 0.5 (left) and 0.8 * noise + 0.5 (right) tor color. using (noise + l)/2 for color. However, since noise values close to 1 or —1 are rare, this will be a fairly smooth image. Larger scaling can increase the contrast (Figure 6.3). 6.3 TURBULENCE Many natural textures contain a variety of feature sizes in the same texture. Perlin uses a pseudofractal "turbulence" function: i The turbulence function is shown for various values of n in Figure 6.4. This can be used to distort the stripe function: RGB turbstripe( point x, double w ) double t — (1 + sin(/l-i.r.r0 + turbuience(k.2x)))/w)/2 return t * sO + (1 - t) * si Various values for fcL and fc2 were used to generate Figure 6.5. 6.4 BUMP TEXTURES Although so far I have only discussed changing materia3 properties using solid texture, you can also change the surface normal to give an illusion of fine-scale 6.4- Bump Textures Figure 6.4. Turbulence function with one through eight terms in the summation. Figure 65- Various turbulent stripe textures with different ki. k2. Top row has only the first term of the turbulence series geometry on tne surface- We could do this by applying a bump map which perturbs the surface normal. One way to do this is as follows: vector3 n = surfaceNormal(x) n+ = ki * vectcrrTu.rbulence(k2* x)))/w)/2 return t * sO + (1 - t) * si This is shown in Figure 6.6.
58 6. Solid Texture Mapping Figure 6.6. Using vector turbulence on sphere of radius 1.6. Lighting directly from above Left, fei = 0. Middle: fci = 0.08, fc2 = 8. Right: la. = 0.24, fc2 = 8. To implement vectorTurbulence, we first need vectorNoise which produces a simple spatially-varying 3D vector: L-rJ + l iyj + l [:j+l nL.(x.y.z)= /__, j_^ ^ rijkOmega{x)* ointyn(y)* omega(z) ! = l-'-J j='.y}i'=[-s With th's- vectorTurbulence is a direct analog of turbulence: Sum a series of scaled versions of vectorNoise. 7 Image Texture Mapping We often want to take a pixel-based image and "map" it onto a surface. This is not difficult to implement once you understand the coordinate systems involved. In the last chapter, we used the point on a surface to look up a texture. Here we use a 2D coordinate, often called MV, which is used to create a reflectance R(u,v). The key is to take an image and associate a (u.v) coordinate system on it so that it can be associated with points on a 3D surface. For example, if the latitudes and longitudes on the world map are associated with polar coordinate systems on the sphere, we get a globe (Figure 7.1). As should be clear from Figure 7.1. it is crucial that the coordinates on the image and the object match in "just the right way." As a convention, the coordinate system on the image is set to be the unit square (u. v) e [0.1] x [0. I1. For (u. r) outside of this square, only the fractional parts of the coordinates are used resulting in a tiling of the piane (Figure 7.2). Note that the image has a different number of pixels horizontally and vertically so the image pixels have a nonuniform aspect ratio in (u. r) space. Figure 7.1. A Mercator projection world map and its placement on the sphere. The distortions in the texture map (i.e.. Greenland being so large) exactly correspond to the shrinking that occurs when the map is applied to the sphere. 59
60 7. Image Texture Mapping ) 'A i, A y. '^■■reeJKr: Figure 7.2. The tiling of an image onto the (u. u) piane. Note that the input image is rectangular and that this rectangle is mapped to a unit square on the (u, v) piane. To map this (u.r) € [0.1] x [0.1] image onto a sphere, we first compute the polar coordinates. (Recall the coordinate system shown in Figure 2.2). For a sphere of radius R and with center {cx. cs. r-),fhe parametric equation of the sphere is X y z = — = xc + R cos <t> sin 9 yc + Rs"m0 sinfi. zc + R cos 6. The {8, <b) can be found using z arccos - 0 = arctan2(j/ - yc, x - xc where arctan2(a, 6) is the atari! of most math libraries which returns the arctangent of a/b. Because (6,0) £ [0,t] x [—tt, ?r], we convert to (u, v) as follows, 61 v=0.7S v=0.5 u=0.25 u=0.5 u=0.75 lv=0.25 Figure 7.3. Left: a calibration texture map. Right: the sphere viewed along the y-i after first adding 2- to o if it is negative: o U = 2V 7T-0 V = . 7T (7.1) This mapping is shown in Figure 7.3. There is a similar, although likely more complicated way. to generate coordinates for most 3D shapes. Once the (n. v) coordinate of an object is known, all that remains is to find the corresponding color in the image. First, we remove the integer portion of (M, v) so that it is in the unit square. We then use one of three interpolation strategies to compute the image color for that coordinate. The simplest strategy is to treat each image pixel as a constant-colored rectangular tile. This is shown on the left of Figure 7.4. To compute this, apply c(u.v) = c,j. where c(u.v) is the texture color at (u. r) and aj is the pixel color for pixel indices: [vny (7.2) where (nI,n!/)is the size of the image being textured, and the indices start at (U) = (0,0).
7. Image Texture Mapping 1 0 1 0 1 0 1 0 1 Figure 7.4. Right to left: values in texture file, point texture, bilinear texture, and bicubic texture. For a smoother texture, a bilinear interpolation can be used as shown in the middle of Figure 1.4. Here we use the formu3a: c(u.i-) = (l - u')(l - v')CiJ + u'(l- l/ku-M); + (7.3) where K v') = (nu~ [nu\.m-— [nv\). The discontinuities in the derivative in intensity can cause visible mach bands, so hermite smoothing can be used: c(u.r) = (1 -u")(l- r")cu + (i - " )'' <\<j~n + u"(.'"c(j4.nUJ.i) (7.4) where (u".y") = (3(u')2-2(u')3.3(c')2-2(r'f) which results in the rightmost image of Figure 7.4. I have described how textures can be used to modulate diffuse reflectance. They can also be used to modulate any parameter that controls lighting and even for transparency (a "alpha-map"). Readers interested in more information on such techniques should consult either of the excellent Renderman books [3. 64]. 8 Triangle Meshes Most real-world models are composed of complexes of triangles with shared vertices. In many fields these are known as triangular meshes or triangular irregular networks (TINs). In this chapter. I describe how to manage these types of models without too much storage, and with texture maps. A simple triangular mesh is shown in Figure 8.1. You could store these three triangles as independent entities and thus store point px three times, and the other vertices twice each for a total of nine stored points (three vertices for each of two triangles), or you could try to somehow share the common vertices and store only tour. So instead of class triangle materia3 m point3 p„. Pep. meshtrum\>lt parent — vertices 0 meshtritiniiie parent vertices run] meshtrianylt- vertices 1 ^ 1 "> 1 | I 4 mesh material vertice-i | Po| P P: H Figure 8.1. A three triangle mesh with tour vertices. 63
54 8. Triangle Meshes you would have two classes: class mesh materia3 m array of point3 vertices and class meshtriangle pointer to mesh meshptr int iq, i\, i2 where «o, i\, and 12 are indices into the vertices array. Either the triangle class or the mesh class will work. Is there a space advantage for the mesh class? Typically, a large mesh has each vertex being stored by about six triangles, although there can be any number for extreme cases. This means about two triangles for each shared vertex. If you have n triangles, then there are about n/2 vertices-in the shared case and 3rc in the unshared case. But when you share you get an extra 3ri integers and n pointers. Since you don't have to store the materia3 in each mesh triangle, that saves n pointers which cancels out the storage for meshptr. If we assume that the data for floats, pointers, and integers all take the same storage (a dubious assumption), the triangles will take 10/i storage Figure 82. Various mesh textures obtained by changing (u, v) coordinates stored at vertices. 9. Triangle Meshes 65 rmixs and the mesh will take 5.5n storage units. So this amounts to around a factor of two, which has generally been true for the real implementations I have seen. Is this factor of two worth the complication? I think the answer is yes as soon as you start adding "properties" to the vertices. Each vertex can have materia3 parameters, texture coordinates, irradiances, and essentially any parameter that a Tenderer might use. In practice, these parameters are bilinearly interpolated across the triangle. So. if a triangle is in_ tersected at barycentric coordinates (,3,7), you interpolate the (u. v) coordinates the same way you interplate points. Recall that the point at the barycentric coordinate {'3,1) is p{3, -)') = Po + t?(Pi - Po) + 7(P2 - Po)' A similar equation applies for (u. v): u{3.-<) = uu +3[ui - un) -+--, (u2 - u0). c[3. = !•() + 3(l'l - I',)) +~,{V-2 - CO). (8.1) Several ways in which a texture could be applied by changing the (u. r) at triangle vertices are shown in Figure 8.2.
Instancing This chapter discusses instancing, where an object is stored in its own local coordinates along with a separate transform matrix. In a conventional z-buffer graphics system, each vertex of the object is transformed by the matrix before being drawn. So if a scale in z by 0.5 is applied, the object will become squat in that dimension. In ray tracing, instancing is easy to manage, but the way the transforms are done is a little trickier to understand than with a z-buffer. as you will see. The basie idea of instancing for ray tracing is shown in Figure 9.1. A neat thing about instancing is that you can have the same object be associated with two different "instances" which have different values for the transform. A wonderful thing about instances is that although they require only a few lines of code, you can create more primitives. For example, if you implement a sphere, you can get ellipsoids by having scaled instances. global coordinates local coordinates Figure 9.1. If rays and objects are all transformed together, the image remains the same. This can change the problem of ray tracing ellipsoids into the easier problem of intersecting with a sphere. 67
68 9. Instancing o+rd M-'o + r M-'d alobal coordinates local coordinates Figure 9.2. A ray traced against an ellipsoid can be trumfonned mi that the ellipsoid becomes sphere centered at the origin. 9.1 INTERSECTING RAYS WITH TRANSFORMED OBJECTS The basie idea of how to do intersections with transformed objects is shown in Figure 9.2. Rather than transforming the points on the object, which might global coordinates local coordinates Figure 9.3. When the normal vector in local coordinates is transformed as a conventional vector, you get a non-normal vector (dotted). A different transformation rule is needed for normals to get the solid vector. 9,2. Lattices 69 be complicated, we transform the ray. I use the convention that the "local" points on the object are transformed by M. This means the opposite transform should bring the ray into local coordinates. This transformed ray, M~1o + iM_ld, is 3ntersected with the object in its native local coordinate system and the intersection point is x. The intersection point in world coordinates is Mx. If the local normal vector is n, then the transformed normal that we use for lighting computations is(M_1)Tx. An interesting issue is whether we implement solid textures with local or glocal coordinates. Usually, using local coordinates is the right answer, so that the texture will move with the object as the object is changed. One implication of instancing is that the length of the vector in rays cannot be restricted to one. We need arbitrary vector lengths so that they can be scaled into the local coordinate system; if d had length one. a scaled version of d in local coordinates could have any length. The pseudocode for the intersection with a surface 5Mrftransformed by a matrix M is given below: function hit-instance( ray o + fd) o' ^-Mo d' <— Md {if hit-surf returns true, assume hit point p' and normal n' are somehow returned) if hit-surt'(o'+ fd') then p <- A/~ V nf- (M~lfn' return true else return false 9.2 LATTICES Instances can be used to create procedural complexity without code specific to a specific type of geometrie object. This is accomplished by making many copies of the same object with different transform matrices. This essentially makes copies of objects. A procedural way to make this is with a "lattice" that creates a 3D array of object copies. If we have a way to create a transformed instance create-instance(surf,M)the pseudocode for a lattice is as follows: for all i 6 {0,.. .nx}, j € {0,.. .ny}, k {0—nv} do M «- translate(ax + i*dx, ay + j*dy. az+ fc*dz) {(ax.ay.az)is the startpoint and (dx,dy.dz) is the base offset} create-instance(obj ect,M)
10 Grids for Acceleration of Intersection This chapter describes how to use a regular grid subdivision structure to avoid computing intersections with every object in the scene. This is similar to how hashing is used to speed searches in ordered data. However, it is somewhat more complicated because ordering objects in 3D is somewhat ill-detlned. There are many alternative acceleration strategies to the one presented here. Interested readers can find more information in the aniele by Arvo and Kirk [4]. 10.1 GRID TRAVERSAL The grid is a 3D axis-aligned box that is subdivided into a lattice of smaller boxes. Each box contains a list ot" which primitives have any points within the box. A simple grid and the corresponding array data structure are shown in a empty grid data structure grid geometry Figure 10.L A 2D grid (left) with the corresponding array data structure (right). 71
72 10. Gridsfor Acceleration of Intersection Figure 10.2. A ray first enters cell a and is tested against surface 2. Since it misses, it is advanced to celt b and then to cell c where it is tested against surface I. Since it hits surface 1. the seurchis terminated. Note that object 0 is never tested. 2D example in Figure 10.1. The array should contain pointers which are either null or point to a list (or another grid) depending on whether the cell is empty. Since a ray can hit a grid, the grid, like the list, should be of the same type or class as the basie spheres and triangles. The key advantage of a grid is that it can be used to skip testing hits with some of the objects. This is illustrated in Figure 10.2 where only two of the three objects are tested. In larger data sets, a higher fraction of objects is skipped. A special case that should be accounted for is shown in Figure 10.3. Because ot this type of situation, we must test whether an intersection occurs in the cell in question. Note also that in the next cell we test the triangle again. In practice, we can test the same primitive many times. Although we could put in a special case check to avoid multiple tests, that would add if tests that slowdown the case where we test an object once. I believe that if there is any speed advantage to this type of test, it is not worth making your code more complex, so just test every object in each cell that the ray visits and don't worry about the multiple tests. The basie code for a grid traversal is given below: if ray misses whole grid then return false find first cell (i.j, k) ray visits findtjn, tout for that cell while true do if ray hits an object in cell (i,j, k) with t € [fnn,£0„t]then return true change i, j, or k by +1 or —1. 10.1. Grid Traversal 73 if (i,j, k) out of range (hen return false Lin — ^out compute new tout To convert this into more explicit operations, we need to do some clever steps developed by Amanatides and Woo [2]. The key concept to making the traversal efficient is shown in Figure 10.4. The inner loop of the 2D traversal for rays traveling in the positive x and y directions will thus look something like this: loop II txnext^ Cy7iexfU'cII ^ t in — lout 'out — r.i- nert if hit in cell (i.j, k) with t e [f,n.f„„(]then return true i <- I + 1 t.r nt.rt ^~ tx in .rt + «?•'" else t,„ <- t„»t taut * Mi i}' .rt if hit in cell (i.j. kj with f 6 [f,„. f,Jllf|then return true j +-J+1 IU ,i, .rt +~ i,i ii' rt + litII Figure 10.3. A special case that must be accounted for: Although the triangle is tested for and hit in cell a, the hitpoint is not inside that cell so it should not be accepted.
10. Gridsfor Acceleration of Intersection To turn this into more complete code, we need to get the loop started and we need to terminate it when the ray leaves the grid. First, some definitions: The grid has extreme corners pa = (x0,yo,z0) and p, = (zi,j/i,Zi). The grid has nx by ny by nz cells, each of the same size. The basie code is as follows: if vx > 0 then *xmin * ^0 tx max ^ \X\ else *x triin ^ («£l - ^1 max ^ (^-0 - if i'tf > O then ty min v 1,3/0 f y max ^ \U\ ~ else *-y min ^ [Ml If/max *~ {TjO - if r. > O then t; nun <~ (-0 ~ ' : max i V - 1 else tzmin ^~ (~1 - - ox)/vx - ox)/vx - ox)/vx - ox)/vx -Oy)IVy o:)/r: ":)/('; '->.-)/'*; t;n,ax <~ ( ~0 ~0-)/v: {Find the biggest of tr ,„,„. t^ if tr mm > ty ,„, <() *" *x nun else 'o <- fv„,„, „ then m in - ' ; / •all hils • y hits ' \ hits Figure 10.4. The intersection points with cell walls are irregular, but closer inspection shows that the intersection points with the vertical sides are evenly spaced, as are the intersection points with the horizontal sides. ' 10.1. Grid Traversal if tz min > tobig then tr) ^ — tz min {Find the smallest of tx max Jy max, tzmax} if txmax < tymax then tl 4 I'Xmax else l-l ■* £y max if tzmax ^tIsmail then A i *~ max. {Intersection with box at to and t\ if to <'*i} if (t0 > ti) then return false (Add intersection of tmin, tmax} dtx <- (rrl - txQ)/nx dty <- (iyl - ty0)/ny dtz <- (r:l -tz0)/n: p <— o + fd i-x <- (fix - ■Vo)nxi[x\ - J"u) iy *r- U>y - i/o)».y/(.i/i - i/n! 'i'2 <~ (Pr. - =<j)"-/Ul - -o) clamper. O, nx - 1) clamp(7M. 0. ny - 1) clamp(/;. 0. nz - 1) if vr > O then fr ,.,-.rf <- '•'•" + ('i- + '>*** ixStep <— +1 ixStop <— n.r else txnrst <- f-'-0 + (»•*•- 'j)rf^' ixStep <- —1 ixStop <— -1 if v„ > O then iyStep <— +1 iyStop •(— ny else tsnexf <~ %0+ (ny - iy)dty iyStep <- -1 iyStop <— -1 if vz > O then izStep <- +1
76 10. Grids /(^Acceleration of Intersection izStop <— nz else tznext <— tzO + (nz - lz)dtz izStep <— -1 izStop <— —1 while true do if (txnext < tynextandtxnext< tznext) then if (grid(ix,iy,iz) and grid(ix,iy,iz)-^hit(r,time,t,txnext.VHR,rnp)) then return true t «— txnext: txnext += dtx: ix += ixStep: if (ix = ixStop) then return false; else if tynext < tznext then if (grid(ix.iy.iz) and grid(ix.iy.iz)-t;hit(r.time.t.tynext.VHR.mp)) then return true t <— tynext: tynext += dty; iy += iyStep: if (iy = iyStop) then return false: else if (grid(ix.iy.iz) and grid(ix,iy.iz)-t-,hit(r.timt\t.tznext.VHR.mp)) then return true t <— tznext; tznext += dtz: iz += izStep; if (iz == izStop) then return false: 102 GRID CREATION There are two tasks to be done when creating a grid. The first is, given the axis-aligned bounding box of the objects to be placed in the grid, to choose the number of subdivisions nx, ny,nz. The second is to actually add object lists to the grid cells. Various authors have argued that it is best that the grid cells be roughly cubes and that the number of gridcells be on the same order of magnitude as the number of objects. This can be accomplished in the following manner: 102. Grid Creation T? 'WXWyWZ\3 n I round1! 4\ = round (^), round (T) where u:x. wy. and tu- are the lengths of the bounding box sides and nr- ny. and n, are the number of subdivisions used to create a nx x ny x n- grid. To add objects to the grid, you should employ a sort of 3D scan conversion. The easiest way is to add a surface to a cell if that surface's bounding box overlaps the cell. This can be accomplished easily by finding the grid cell indices occupied by the two extreme corners of the surface bounding box and adding the object to every cell in the range of indices between these two extremes. This may add the surface to cells it doesn't actually overlap, but such false negatives will only impact performance and not correctness. More efficiency can be gained by more sophisticated overlap tests, but I rarely employ them.
Partm Advanced Ray Tracing
11 Monte Carlo Integration To go further in making our pictures look realistic, we need to use Monte Carlo methods, which use random numbers to solve numerical problems. "Monte Carlo" refers to any method that uses averages of random computations to get an approximate answer to a problem. We cover only Monte Carlo integration here. Readers interested in a broader treatment of Monte Carlo techniques should consult one of the classic texts [20, 55. 19. 74]. 11.1 MONTE CARLO OVERVIEW To get an idea of how a Monte Carlo simulation progresses, observe the dart impact positions shown in Figure 11.1. As more and more darts are thrown, we can see that there is a definte pattern, or density to how the darts are hitting. Two important questions: 1) How do we describe this pattern mathematically? 2) How do we simulate the generation of dart positions to fit that pattern? The answer to the first question is a probability density function which we will discuss now. The second question is dealt with in the next chapter. If we take a smali area ,4 on the dartboard and count hits within that area, the number will increase as the number of darts thrown increases. We can normalize this by measuring the fraction of darts within the area. This fraction will vary as the number of darts increases, eventually settling on the true probability of hitting the area. Note the simplicity of that concept: The probability of hitting the square is j ust the fraction of an infinite number of darts that hit the area. We can generalize this concept further by making the area very smali. However, then the probability will also get very smali. To normalize again, we can divide the fraction that hits the smali region by the area of the smali region. As we make the region smaller and smaller, eventually it is infinitesimal,and every point will have a probability divided by a smali area. The probability and the area both go to zero, but their fraction does not. For every point x, this fraction 81
82 11. Monte Carlo Integration Figure 11.1. A dun board with dart impaot positions shown. As more darts are thrown, the underlying distribution ot" dart positions becomes more obwous. has a potentially different value p(.v). This is a probability detnitx function. Note that the probability of selection, given points .n or x-i. is zero, but the rado /•>(•'■ t), p(.('j)is the relative likelihood of choosing a point near xi as opposed to a point near ,r>. How does all this relate to ray tracing? As we will see, we need to solve integrals to generate realistic images. Rays will be generated probabilistically to help us estimate solutions to these integrals. Random numbers and points can be great ways to solve integrals. For example, in our dart board problem, each dart location x has a score s(x). The average score for a player is f average score = / p(x).s(x)dA.r. Jxedartboard We could compute this by hand or we could write a program that just averages N dart scores: average score =s — > s xt). it ^—' This assumes we can generate random xt with the right density. Obviously, this indicates we can approximate integrals for some problems via simulation. In fact, we can approximate any integral with any density function. Consider the one dimensional integral: r" 1 = I f(x) dx. Ja 11.2. A Linie Probability 83 This can be viewed as taking an area under / in the interval [a, 6]. Another way to consider this integral is / = (b - a)average(/(i)) where the average is taken over the interval [a. b]. This 3s really just saying that the area is the base times the average height. We can estimate averages by picking random x, € [a. b\: This is analogous to what a telephone survey does to estimate otheraverages. Less obvious is that we do not need the x, to be uniform. For example, suppose H has an underlying density p(x) which has a preference for numbers near b. This means b is more likely to be chosen than a. If we use just the simple averaging formula, then we would get the wrong answer; our results would be biased. Butp(</) tells us exactly how skewed our sample is. If p(a) is large, we are likely to get samples near a and we need to weight them less. To do this, our scaling factor should be proportional to the inverse of pix): What is not obvious is that the scaling constant on this formu3a is right. However, consider the case where p(.r) is a constant. This constant is l/( b - a). So this case can be used to normalize the above expression and see that it is right. Now that we have established some intuition for why integrals and randomness go together, we will go through a more formal treatment. Take it slow and keep your intuition by trying examples. 112 A LITTLE PROBABILITY Before getting to the specifics of Monte Carlo techniques, we need several definitions, the most important of which are continuous random variable.probability density function, expectedvalue. and variance. This section is meant as a review and those unfamiliar with these terms should consult an elementary probability theory book (particularly the sections on continuous, rather than discrete, random variables). Loosely speaking, a continuous random variable z is a scalar or vector quantity that "randomly' takes on some value from a continuous space S, and
84 //. Monte Carlo Integration the behavior of x is entirely described by the distribution of values it takes. This distribution of values can be quantitatively described by the probability density function, p, associated with x (the relationship is denoted x - p). If x ranges over a space S, then the probability that x will take on a value in some region Si C S is given by the integral Prob(x € 5.) = / p{x)dp. (p:S-> R1). (11.1) J Hi Here Prob{event) is the probability that event is true, so the integral is the probability that x takes on a value in the region St. The notation p :S —» R1 should be read "p is a function that takes a point in set 5 and returns a value in set R1." This is similar to the familiar function prototypes such as int func(realx) which could as easily be written "f unc: real—>int." The measure p is the measure on our probability space. In graphics. S is often an area (dp = dA = d.rdy) OT a set of directions (points on a unit sphere: rf/j = <L; = *m6dftdo). Loosely speaking, the probability density function describes the relative likelihood of a random variable taking a certain value: if p(.z'i) = 6.0 and p(.r->) = 3.0. then a random variable with density p is twice as likely to have a value "near" .i) than it is to have a value near rj. The density p has two characteristics: p(.r) > O (Probability is nonnegutive). (I 1.2) p[x)dp = 1 (Probi.r e S) = 1). ( 11.31 As an example, the canonical random variable $ takes on values between zero (inclusive) and one (non-inclusive) with uniform probability (here, uniform simply means each value for is equally likely). This implies that ){ [ 1 ifO < < 1 [ O otherwise. The space over which is defined is simply the interval [0.1). The probability that takes on a value in a certain interval [a. 6] 6 [0. 1) is Prob(a < £ < b) = f 1 dx = b — a. J a As an example, a two-dimensional random variable a is a uniformly distributed random variable on a disk of radius R. Here, uniformly means uniform with respect to area, e.g., the way a bad dart player's hits would be distributed on I 11.2. A Linie Probability 85 a dart board. Since it is uniform, we know that p(a) is some constant. From Equation 11.3, and the fact that area is the appropriate measure, we can deduce thatp(a) = l/(7ri?2). This means that the probability that a is in a certain subset Si of the disk is j ust Prob(a S,) = / ^dA. J Si *"•« This is all very abstract. To actually use this information, we need the integral in a form we can evaluate. Suppose Sz is the portion of the disk closer to the center than the perimeter. If we convert to polar coordinates, then Q is represented as a (r, 6} pair, and Si is where r < R/l. Note that just because a is uniform does not imply that 9 or r are necessarily uniform (in fact, 0 is uniform and r is not uniform). The differential area dA becomes r dr dt). This leads to o r'lir r— i Prob(r <--)=/ / • -—^rdrdO = 0.25. Ju J» "K- The average value that a real function / of a one-dimensional random variable will take on is called its expected value. E(fl.r)): I £(/U'))= / fU-)p(x)dn. The expected value of a one-dimensional random variable can be calculated by letting /(.;•) = x. The expected value has a surprising and useful property: The expected value of the sum of two random variables is the sum of the expected values of those variables: £(.!•+ ,,) = F(.r)+ E(u) for random variables x and y. Since functions of random variables are themselves random variables, this linearity of expectation applies to them as well: £■(/(-'•) + <)(!))) = £(/(•<•)) + E(!)(n)l An obvious question is whether this property holds if the random \ariables being summed are correlated. (Variables that are not correlated are called independent.) This linearity property in fact does hold whether or not the variables are independent! Since the sum of two random variables is itself a random variable, this principle generalizes. As an example of expectation, consider random points on the disk of radius R. What is the expected distance r from the center of the disk of radius R'l ^nu* op rdrd6 = —. 3
86 //. Monte Carlo Integration The variance, var(x), of a one-dimensional random variable is the expected value of the square of the difference between x and E(x): var(x) = E([x - E(x)]2). Some algebraic manipulation can give the nonobvious expression: var(x) = E(x2) - [E(x)]2. The expression E([x- E(x)\") is more useful for thinking intuitively about variance, while the algebraically equivalent expression E[x2) — [E(x)$ usually convenient for calculations. The variance of a sum of random variables is the sum ot the variances if the variables are independent. This summation property of variance is one of the reasons it is frequently used in analysis of probabilistic models. The square root of the variance is called the standard deviation, a, which gives some indication of expected absolute deviation from the expected value. The variance tells us what the expected square of the deviation from the mean is. Sometimes we would like to know the absolute deviation from the mean, such as "the darts average ten centimeters from the bulls-eye." Computing such an absolute deviation is difficult. Often, it is sufficient to know the standard deviation a(.r) = y tw(j'). The standard deviation, at an intuitive level, will usually serve as an approximation to expected absolute deviation. Many problems involve sums of independent random variables .r,. where the variables share a common density /. Such variables are said to be independent identicalh-distrihutedmndom variables. When the sum is divided by the number of variables, we get an estimate of £"(>): ^^xri:*'- N f=i As N increases, the variance of this estimate decreases. We want n to be large enough that we have confidence that the estimate is "close enough." However, there are no sure things in Monte Carlo: we just gain statistical confidence that our estimate is good. To be sure, we would have to have n = x. This confidence is expressed by Law of Large Numbers: Prob 1 ' E{x) = lim — y^ xt JV-+CC N J-J JV-+CC N t=l So, with a probability of 1, our estimate will eventually converge to the right answer. 11.3. Estimating Definite Integrals 87 113 ESTIMATING DEFINITE INTEGRALS For a function / and a random variable x ~ p, we can approximate the expected value of f(x) by a sum: (f(x)) = I f(x)p(x)dp* -^2f{xi). (11.4) Jxes '■ i=1 Because the expected value can be expressed as an integral, the integral is also approximated by the sum. The form of Equation 11.4 is a bit awkward: we would usually like to approximate an integral of a single function g rather than a product f p. We can get around this by substituting g = f p as the integrand: / *<•>«« =4 ££t ^ r€5 -' ,= 1 P(J< For this formu3a to be valid, p must be positive where g is nonzero. So to get a good estimate, we want as many samples as possible, and we want the g.'p to have a low variance (y and p should have a similar shape). Choosing p intelligently is called importance sampling, because if p is large where g is large, there will be more samples in important regions. Equation 11.4 also shows the fundamental problem with Monte Carlo integration: diminishing return. Because the variance of the estimate is proportional to l/N, the standard deviation is proportional to 1 v^V. Since the error in the estimate behaves similarly to the standard deviation, we will need to quadruple A" to halve the error. Another wav to reduce variance is to partition 5, the domain of the integral, into several smaller domains 5,. and evaluate the integral as a sum of integrals over the 5,. This is called stratified sampling. Normally, only one sample is taken in each S, (with density p,), and in this case the variance of the estimate is p,(-i;) frT \Pt(x It can be shown that the variance of stratified sampling is never higher than unstratified if all strata have equal measure: I p(xW= "TV , p{x)d(i- Js, N Js The most common example of stratified sampling in graphics is jittering for pixel sampling [ll].
92 11. Monte Carlo Integration The sin 9 term arises because the measure is solid angle (area on the unit sphere: dui = dA = sm9d9d<j>). To solve this, we just need to choose a random direction u> to sample with a distribution according to the density function cos 9/n. This gives the estimator L(x) = pd(x.)L(x,u>). This makes it easy to figure out the color of the ground in the mid western United States: It's the weighted average of the color of the sky times the reflectance of the ground! 11.7 MULTIDIMENSIONAL QUASI-MONTE CARLO INTEGRATION Suppose we want to numerically estimate the value of an integral / on [0. lj-: /= / / /{■'■■ )/)d.rdf,. For pure Monte Carlo, we might use a set of uniform random points (.r, ,.i/,) € [0. I]2 and estimate / to be the average of f(x, .,</,). For stratified sampling, we might partition [0. lj- into several equal-area rectangles and take one sample (.r,. ,y,) in each rectangle and again average /(.(',.//,). Interestingly, we might also use "Poisson-disk" sampling to generate the points, or evenjust use points Figure 11-3. Random. Jittered, Poisson disk. Regular. 11-7. Multidimensional Quasi-Monte Carlo Integration 93 on a regular grid. No matter which of these point distributions (shown in Figure 11.3) we use, the estimate of/ is the average of f(xi, t/;). Interestingly, only when we use one of the first two patterns are we doing Monte Carlo integration. With Poission-disk (dart-throwing), the samples are correlated, and in regular sampling they are deterministic. As in the one-dimensional case, we can replace the random sample points with any set of samples that are in some sense uniform, and this is just quasi- Monte carlo integration. There is rich literature on this topie, but Mitchell has indicated that the graphics community will not be able to findmany useful answers there, because the patterns that are used in that literature are deterministic, which causes aliasing in images [33]. He suggests that perceptual issues should determine which type of sampling is best.
12 Choosing Sample Points The last chapter discussed how to estimate integrals using a set of random points with underlying density p. This chapter discusses how to get such points for various p with various domains. The section on disks is largely derived froma paper intended to sample camera lenses [52], 12.1 OVERVIEW We often want to generate sets of random or pseudorandom points on the unit square for applications such as distribution ray tracing. There are several methods for doing this such as jittering and Poisson disk sampling. These methods give us a set of N reasonably equidistributed points on the unit square: (ui.i'i) through (;/.v. r.v). Sometimes, our sampling space may not be square (e.g.. a circular lens), or may not be uniform (e.g.. a filter function centered on a pixel). It would be nice if we could write a mathematical transformation that would take our equidistributed points (u,. r,) as input, and output a set of points in our desired sampling space with our desired density. For example, to sample a camera lens, the transformation would take (iij, v,) and output (r-t. 0,} such that the new points were approximately equidistributed on the disk of the lens. In one dimension, we assume we can generate a set of canonical random numbers ( i. 3 &v) and transform them to the desired nonuniform numbers. For example. (£j. J %) are not uniform, but they are still random. The question is what transform T(E) gives us exactly the right behavior for probability density function p? The answer turns out to be a not immediately intuitive inverse of an integral of p. To get some insight into the behavior of the transform, see Figure 12.1. Here we take some canonical £: (in fact they are jittered), and attempt to create samples distributed to a triangle-shaped density. The dashed lines are bins of probability 1/10. Not surprisingly, the samples stay 95
96 12. Choosing Sample Points utx) , 1 x Figure 12.1. We can take a set of canonical random samples and transform them to nonunitbrm samples. within their bins. Taking this idea to infinitely many bins gives a mechanism to compute T as discussed in the next section. 12.2 GENERATING ID RANDOM NUMBERS WITH NONUNIFORM DENSITIES If the density we wish to sample is a one-dimensional pi.r) defined over the interval ,r £ [/„,„,;„„,, . then we can generate random numbers n, that have density/? from a set of uniform random numbers ,. where , t [0. ll. To do this, we need the cumulative probability distribution function P(.r): Prob{a < x) = P(x) = j p(x ')dfi (12.1) To get a, we simply transform t: a,=P'l(^) (12.2) where P"] is the inverse of P. If P is not analytically invertiblethen numerical methods will sufficebecause an inverse exists for all valid probability distribution functions. For example, choose random points Xi ~ p, where , /2|i if i 6 [-1,1], O otherwise. 12.3. Generating 2D Random Numbers With NonuniformDensities 97 We can see that the associated probability distribution function is [0 if x < -1, PW= U-i¥^ if i e [-1,1], y if x > i. To find an inverse of this function, we compute xi in terms of x: * J-i 2 2 ' 2" Now we solve for x in terms of . completing the inversion of P: x= \/2?-l. So we can "warp" a set of canonical random numbers (£i.•• • ■ vv) to the properly distributed numbers (.ri.---.sx) = (v'2si — l.--- . ty'I'.x - 1). This same warping function can be used to transform "uniform" Poisson disk samples into nicely distributed samples with the desired density. So. a set of jittered samples with this density would be as given below: for / — O to n - 1 do .r, = {!2(,+i,)!n - 1 123 GENERATING 2D RANDOM NUMBERS WITH NONUNIFORM DENSITIES If we have a random variable o = (a,, n,,) with two-dimensional density i.'-.y) defined on [.!■„,,-„..r,„„.,- x [;/„,,„.</„,„.,■' then we need the two-dimensional distribution function Pvob\ar < x and au < ;;) = F(x.ij) = / / /(.)•'. i/')(//((.r'. ()'). We first choose an .;•, using the marginal distribution F(.r. (/,„„.,■). and then choose y, according to F(x,. y)/F(x,. t/„m.i)-If f(x->j) is separable (expressible as q(x)h[y)),then the one-dimensional techniques can be used on each dimension. For example, suppose we are sampling uniformly from the disk of radius R. so p(r,0) = l/(7ri?2). The two-dimensional distribution function is f6a [T° rdrd.9 6{)rl Prob(r <r0and8 <00) = F(r0,9o)= Jq ~^f = ^W'
98 12. Choosing Sample Points This means that a canonical pair ( i, 2) can be transformedto a uniform random point on the disk: (r, 0) = {R\/ti, 2n 2). To choose reflected ray directions for zonal calculations or distributed ray tracing, we can think of the problem as choosing points on the unit sphere or hemisphere (since each ray direction ^ can be expressed as a point on the sphere). For example, suppose that we want to choose rays according to the density: p(e, <j>) = ^-ti cosn 9 (12.3) In where n is a Phong-like exponent. 6 is the angle from the surface normal and B [0, k/"2] (is on the upper hemisphere), and 0 is the azimuthal angle (0 6 [0. 2t]). The distribution function is fa pf> P(0.o) = \ I pW'.o'^mO'dO'do'. (12.4) Ja Jo The cos ff term arises because on the sphere (/_• = cos QiWdo. When the marginal densities are found.p (as expected) is separable and we find that a (si-sV) pair of canonical random numbers can be transformed to a direction by (0.O)= (arccosfd - n J^O). 2-r_>) One nice thing about this method is that a set of jittered points on the unit square can be easily transformed to a set of jittered points on the hemisphere with a distribution of Equation 12.3. If n is set to 1 then we have a diffuse distribution needed for a Monte Carlo zonal method. 12.4 SAMPLING TRIANGLES To generate uniform random points on a triangle, we use the natural barycentric coordinates of the triangle and note that the determinant of the Jacobian matrix that takes a triangle defined with barycentric coordinates to a triangle with an unnormalized coordinate system is a constant. This means that if we pick random barycentric coordinates for one triangle, we can use them for any other triangle and the random point will still be uniform. We now go into some detail on the mechanics of choosing a uniform p, because when the uniform density function is written in terms of the two coordinates on the triangle, it is not separable. Using barycentric coordinates, everypoint on the plane containing a triangle with vertices p0, pj, and p2 can be described by p = p0 + B{p^ - p0) + 7(p2 - Po) and the p is in the triangle if and only if (0 > 0) and (7 > 0) and {3 + 1 < 1). 12.4. Sampling Triangles 99 Integrating the constant 1 across the triangle gives / r 1-7 ! dj3 dr) = This means that the value of our density function is 2 in barycentric coordinates (and 1/Ain Cartesian space, where A is the area of the triangle, implying the determinant of the Jacobian that transforms from barycentric to Cartesian space has the value 2.4). To perform an inversion, we must first find densities which correspond to 0 and 7 separately. If 3 and 7 were independent, we could simply use the marginal density for each. In this case, 0 is dependent on 7. Therefore, we will use the marginal density for 7, fed), and the conditional density of ,3 given 7, /B|G(J]-y). By definition /«:.■(-)= f ' f(l3.-i)d3 = 2{\ Jo and /(Jo) fod-i';-)) foil) !--> Now we can pertbrm the inversion by letting i= F&'d'land >= ■FBiG'Wb') and soKing for 3' and V. Here Fa and Fo c are the cumulative densities corresponding to the random variables -.' and J'\~-' respectively. Again by definition Zl=FC(-)')= f A;h)^=20-,'2. Jo Solving for V we get ~' = 1 - \A -Ti- For 3': ii = FB,G(3'W) = / /BIG(d'h') d3 = -^—,, Jo t — ~i thus ' = >(1 - 7') = £2v/T^Ti. Therefore. = Po + fe v/l-& (Pt " Po) + (1 - \/l-£ij (P2 - Po) • (l2-5) P This is the same method presented by Pattanaik [38] in his dissertation. Turk [62] presents a faster method for uniformly sampling triangles that makes stratification deteriorate slightly.
too 12. Choosing Sample Points 125 SAMPLING DISKS While the simple transforms just described will yield a correct program, sometimes we can make transforms with better numerical properties. In this section, we describe choosing random points on a disk in a "better" way. This section can be safely skipped as it is an improvement rather than a necessity. Many graphics applications map points on the unit square S = [0. I]2 to points oh the unit disk V — {(x.y) x2 + y2 < 1}. Sampling disk-shaped camera lenses is one such application. Though each application can have its own unique requirements, experience has shown that a good, general-purpose map should have the following properties. Preserve fractional area. Let R € S be a region in domain 5. The fractional area of if is defined as a{R)/a(S).where the function a denotes area. Then a map in :.S —> V preserves fractional area if the fractional area of R is the same as the fractional area a{m(R))(u{V) for all R e 5 (Figure 12.2). This property ensures that a "fair" set of points on the square will map to a fair set on the disk. For distribution ray tracers this means a jittered set of points on the square will transform to ajittered set of points on the disk. Bicontimious. A map is bicontimious if the map and its inverse are both continuous. Such a map will preserve adjacency: that is. points that are close on the disk came from points that are close on the square, and vice versa. This is especially usefulwhen working on the hemisphere, because it means that the angular distance between two directions can be estimated by their linear distance on the square. Low distortion. By low distortion, we mean that shapes are reasonably well preserved. Detining distortion more formally is possible, but probably of limited benefit because no single definition is clearly suitable for a wide range of applications. 2) s Figure 12.2. A map that preserves fractional area will map regions with the area constraint that 12.5. Sampling Disks 101 Figure 12.3. The polar map takes horizontal strips to concentric rings. These properties as well as several others are also important to map-makers who map the spherical Earth to a rectangular map [7]. Figure 12.3 shows the polar map. probably the most obvious way to map the square to the disk: x is mapped to r and y is mapped to o. Because the area between r and r + Ar is proportional to r to the first-order, the map is not a linear function of z: r = v'J o = 2-y This map preserves fractional area, but does not satisfy our other properties. As can be seen in the image, shapes are grossly distorted. Another problem is that althousih (r.o) = (s//x.2~i/)is continuous, the inverse map is not. For some applications we would prefer a bicontinuous map. 12.5.1 The Concentric Map We now present the concentric map. which maps concentric squares to concentric circles, as shown in Figure 12.4. This map has the properties listed above. and is easy to compute. It has been advocated for ray tracing applications [51] and has been shown empirically to provide lower error for stochastic camera Figure 12.4. The concentric map takes concentric square strips to concentric rings.
102 12. Choosing Sample Points Figure 12.5. Quantities for mapping region 1. lens sampling [24], but the details of its computation have not been previously published. The algebra behind the map is illustrated in Figure 12.5. The square is mapped to (o. h) -1. I]2. and is divided into four regions by the lines a = b and a = -b. For the first region, the map is X — U Ttb o — —- 4 a This produces an angle o e [—n/i. tt/4]. The other four regions have analogous transforms. How the polar map and concentric map transform the connected points in a uniform grid is shown in Figure 12.6. We show in the Appendix that this map preserves fractional area. This concentric square to concentric circle map can be implemented in a smali piece of robust code which has been written to minimize branching: ■Afy. ■■ Figure 126. Left: unit square with gridlines and letter "F". Middle: polar mapping of gridlines and "F\ Right: concentric mapping of gridlines and "F\ 12.5- Sampling Disks 103 Vector2 ToUnitDisk( Vector2 o) real <t>, r, u, v ' real a = 2ox - 1 {(a,b) is now on [-1, l]2-} real 6 = 2oM - 1 if (a > -b) {region 1 or 2} then if (a > b) {region 1, also \a > \b\} then 0 = (7r/4)(6/a) else r = 6 © = (7r/4)(2-a/6) else if (a < b) {region 3. also lol > 161, a i= 0} then r = -a 0 = (tt/4)(4 + b/a) else r = -b if (MO then o = (-/4)(6 - a/b) else phi - O u — r cos o v = r sin O return Vector2( u. c ) The inverse map is straightforward provided the function atan2 () is available. The code below assumes atan2 () returns a number in the range [-"■ ""j- as it does in ANSI C. ANSI C++, ANSI FORTRAN.and Java. Vector2 FromUnitDisk(Vector2 p ) real r = ^Jpj. + p2 real o — atan2(prpJ.) real a. b. x. y if 0 < -n/4 { (p e {-pi/4.7pi/i}} then 0 = o + It; if phi < ?r/4 {region 1} then a = r 6 = 0a/[ir/4) else if 0 < 3tt/4 {region 2} then b = r a = _(0_,r/2)*6/(ir/4) else if 4> < 57r/4 {region 3} then a = — r
1<M 12. Choosing Sample Points b = (0 - 7r)a/(7r/4) else b= -r a = -{<t>- 37r/2)6/(7r/4) x = (a + l)/2 y = (6+l)/2 return Vector2(x, y) A random point on the disk of radius R can be generated by passing a random point on [O, 1] through the map and multiplying both coordinates by R. A set of n jittered points can be generated similarly using uniform random numbers between O and 1 such as generated by a call to a canonical random number generator that produces number and ' on two adjacent calls: int s = O for i = O to n - 1 do for j = O "to n - 1 do Vector! o = {{> + £)/n. (j | .')/n) onDisk[s++] = Tol!nitDisk{ o ) Note that the random numbers are generated by new calls on each iteration of the loop. 12.5.2 Jacobians When the concentric map is expanded out so that we map from (a. 6) € [-1. l:'- to (u. r) on the unit disk, the map is fitb\ u = a cos ' — ' . v = a sin r —J1. The ratio of differential areas in the range and domain for the map is given by the determinant of the Jacobian matrix. If this determinant is the constant ratio of the area of the entire domain to the entire range, then the map preserves fractional area as is desired. This is in factthe case for the concentric map: du Jfe da du & 96 IT This is the constant 7r/4 because that is the ratio of the area of the unit disk to the area 'of [-1J l]2. By symmetry, the determinant of the Jacobian matrix is the same for the other three regions. 13 Antialiasing This is the first of several chapters which use random sampling to compute better images. Until now, your images suffer from "jaggies," a result of aliasing. It's been shown empirically that you can usually get better images if you think of a pixel as the average color of the sampled continuous image near the pixel center. Quite a bit is understood about why this is true, but there are still open questions about-how this averaging should really be done. This chapter describes the simplest way to do it. which will give you much better images withjust a little extra code (and a lot of extra execution time). 13.1 RASTERS In the real world, we can think of the light seen through a window as a rectangular 2D image. This is bogus for a moving viewer, but it is reasonable for a smali instant of time. We can also think of the 2D rectangular image cast onto the backplane of a camera. For a black and white camera, all we care about is the total amount of light falling on each point on the film. Let's say we put an sy coordinate system on the film. The light falling on the film could be denoted f(x. y) where / is some, as yet unspecified, intensity. Of course, the amount of light at any point is zero, but the light per unit area is finite. When we look at the window or film piane we see an image as a picture. Where / is big, we see white. Where it is small, we see black. In between, we see greys. Now suppose we want to duplicate that picture on a digital medium such as an LCD screen. Such media typically have some layout of light emitting (or reflecting) atomie regions known as pixels, short for "picture elements." Each pixel might be a square region that gets a constant intensity (e.g., for an LCD screen) or it might be a set of smaller colored "blobs" (e.g., for a traditional CRT). In any case, for the rest of this discussion, we assume that there are nxby ny pixels, and that they are in a rectangular array. Further, we assume coordinate 105
106 13. Antialiasing 9.5.7.5) j-ai (-0.5.-0.5 V ,. .51 i 'i + -j + ■) + - 4- - + -1 + * + + ! + + + + + + + -r + -L- + + + -f + + + + 4- + + 4- 9 + - + 4- £" (\ 5.7.5) + T + | Figure 13.1. Sampling an image of the letter "a" on a 10 x 8 pixel screen. The c<x>rdinate systems assumed tor the function / being sampled and the screen image /^. Note that the integer coordinates occur at pi\el centers, that / is definedoutside the screen boundaries, and that the coordinate systems have a direct correspondence. The image on the right uses the average colorWithin each square pixel. systems for/ and what is displayed on the screen is shown in Figure 13.1. This makes a very simple mapping between the coordinate system of/ and /... Note that pixel centers have coordinates (0.0) through {n,. — 1. n,, - 1). 13.2 DISPLAY DEVICES Digital display devices typically have a finite set of p intensity values they can achieve: [0. I\ ^-i- For convenience, we pretend it is really a continuous set of values parameterized by a multiplier a in the range [0. 1). Further, we also pretend that /<) is zero, although this is never true. So a = O is the same as saying intensity / — /(). and a = 0.999 is the same as saying a = Ip-\. Why 0.999 and not 1? This allows each discrete intensity level to own the same size interval on a and to get the following conversion: r _ L«pJ r p-i If we allowed a to be 1, we could get intensities greater than Imax, the maximum intensity of the device. If we had p = 10, then we would have a lot of banding in images. This could be alleviated if we used this formu3a for conversion: p-i 13.3. Filtering 107 where is a canonical random number, which is a uniform random number 0n me interval [0,1) such as approximated by drand4 8 (). That is a crude form °f dithering, which we will not discuss further — for a survey see the book by Ulichney [63]. What does p need to be to display smooth images? If we let the spacing between It and Ii+l be the same for all i. then we will notice that we stop seeing banding near white for a smali p. say around 40. But we need to drive p far above 256 before the banding disappears for smali values of I (i.e.,dark colors). This is because we are sensitive to the relative difference between intensities, so the absolute difference between two dark intensities looks bigger than the same absolute difference between two light intensities. The obvious solution is to push more of the color levels toward dark values. This is what is done on almost all display devices, and the parameter that controls how much nonuniform bunching is done is usually called qamnui (the greek letter 7). Suppose we have an intensity that is a fraction a of the maximum intensity we wish to display. The level i e {0. 1 p - 1} we pick is , i / = a ' p . Here. / is the number (between O and 255 for an 8-bit file format) that you write out to disk when outputting the image. Note that this means the screen intensity for a given a is p- i Note that this is all a game to allow us to use only eight bits of storage for the intensities in tranie buffers and image f iles. If we used sixteen bits, we wouldn't need to worry about gamma in this context. What is the best gamma? It depends on display conditions. So there is no right answer, although there will hopefully one day be a standard. For Macs, it is 1.8. for SGIs. it is 1.4. and for other devices gamma is usually 2.2. For a more complete discussion of gamma, see the book by Poynton [44). 133 FILTERING Suppose we have a continuous greyscale image we want to display on a monitor with a rectangular array of pixels (e.g.. Figure 13.1). We cannot do it because the continuous image has a potentially infinite amount of information in it and the monitor is controlled by a smali number of probably 8-bit integers. Let's pretend we can display any continuous intensity using the linear a parameter above. We
™> 13. Antialiasing -still have ihe pfobfem 'of finite pixels. What shall we do? An obvious thing to 36 is to divide ih& screen" up into squares around each' pixel. If we want to fee fancy, \ve can'call this a voronoi partition because each square is the set of points closer to each pixel Oeiitef than any other pixel 'center. Let's just set the ipix'el intensity equal to the-average of the'-continuous image'intensities within 'the ;sqtfare. iFor ;f he i pixel'eehfered 'at (i,j) this is [t+i rJ+i M*-J)= / / f(x,y)dydx, (ill) We Iheh rconvert<"6achof the//a(/, j)fo 'a variable 'a{ij)= ;kf„{i.j).where t is'chosen :su©h that'irfdstrdf 'all'a(/. j)afe in [0.1), and the a's are written to an linage 'file 'of computer screen. This tyipe 'of aveTagiifg shown in liquation 13.1 "is called "box filterina." There are "rnaay other types of averaging of weighted averaging that can be used instead: arid some of them yield better empirical results than simple box filterina. The g;ehefaliz£fi<$fi of Equation 13.1 is /.,{>-■]) = / u-,j(.i:i/)fl.r.y)dijdx < 13.2) Where it'o is the "filter" dr "weighting" function for pixel (i.j,). To turn Equation ] 13.2Tritb 'TJtjUati(Jh 113.1. we:tis'e the filter function: TO otherwise. To make our lite simpler, we oaii assume that the filter is the same shape everywhere, but is translated: fA'J) = j J w(i + i\j + y)f(s.y)<ixdy. (13.3) Here, ((he empty integration Hmits 'are shorthand for integrating over all ;t and all !j: For the> box" fitter of width" W" (a generalization of the simple width one box filter),- the Weighting function is [ 'O ©thenvis'e. The literature implies 'that rsoffie nonuniform w that is maximum 'at the pixel tenter is" best- Oiie su6h filter i's 'the 'Separable triangle filter with support width twa. "The term "support" refers to the region where w in nonzero. The term 13.3. Filtering 109 FigilfS 132. A unit width support box filter (left) "and "a width two support separable triangle filter (right). The ellipses on the xy plane are pixel centers. "separable" means the filter is in the form of a product of two ID functions: w(x. j/) — a(x)(b). The separable triangle filter is given by: I 0 otherwise. and is shown in Figure 13.2. The separable triangle filter has a property that is Usually desirable: in a filter function [34]: The total contribution of any given (x. y) to the fina3 image is one. This ensures that the average of /, is the same as the average "of./. The difference" between" box and tent filters is not obvious for most still frames. For an infinite checkerboard, the differences are barelv obvious as seen Figure 133. An infinite checkerboard sampled with box (left) and tent (right) filters. Images ibuftesy of Mike Stark.
110 13. Antialiasing Figure 13.4. An extreme function to emphasize aliasing sampled with box (left! and lent (right) filters. Note that, ideally, the far right of the image should be very smooth. All features there are alaising. Images eourtes* of Mike Stark. in Figure 13.3. The differences are more obvious if we use an extreme 2D function usually used to illustrute human contrast sensitvily: L{.r.y) = ~(l^f*m(2-u/"'))- where a = x/nT. / = (1 — (i/ «,,))'. and .;' and y are coordinates in the system where the lower left corner of the image is (0. 0) and the upper right is (tir. nu). This image is shown in Figure 13.4. For moving images, all of the artifact.s are much more obvious. For this reason, higher-order filters than the tent are sometimes used. For more details see the books by Glassner [17]. 13.4 SAMPLING Given /. a screen resolution (nA.. ny), and a filter w, we could try to analytically evaluate Equation 13.3 for every pixel (i.j) € {0.* • • . nx — l}x {0.* • • . nu — l}. Unfortunately, these integrals may not be analytic, and we may have only an implicit representation for /. By "implicit." I mean that we can evaluate / for a given (x,y), but we have no explicit equation for it; we have only a procedure for evaluating it. In such cases where we need to integrate some way other than algebraically, we invariably use numencal integration (sometimes called "quadrature"). A large class of numencal integration methods take a very simple 13.4. Sampling ill strategy of trying to estimate the average value of the integrand overthe domain of integration, and multiplying it by the measure of the domain: Jn Jn where < /(x) >n means the average of/ on domain Q. This is a straightforward manipulation of the definition of "average," and in 2D it just says the volume is equal to the base times the average height. We can estimate the average numerically by taking a set of N sample points X; fi and averaging the value of/(x,): 1 'V_1 </(x)>^</(x,)>=-£/(xt). (13.5) i=0 For Equation 13.5 to be valid, the sample points x, must in some sense be uniformly distributed. There are several possible definitions of uniformly distributed, and a reasonable one is that any given vex CI is just as likely to be a sample point as any other rex € U. This is. in fact, overkill, but is a good defmition in the limit. Let's apply Monte Carlo integration to a unit width W box filter. For pixel (i.j). we first generate a set of uniformly random points in [^— ir/2,i-t-U /2] x fj-ir/2.j + H72]: where and ' are canonical random numbers. We then displace these to pixel center (i.j) and evaluate Equation 13.2 using Equation 13.5: .j_j.ii; .,■-,. is: l »-i fsdJ) = 77^ / ', / „. /U. y)drdU * - £ /(A- yk). Images with various numbers of samples are shown in Figure 13.5. For a nonuniform filter, we can instead use sample points whose distribution is nonuniform in exactly the right way to give the result of the filter. For the separable triangle filter, such points that are random (but nonuniform) can be generated by the transform ' -1 + v^lit if *<0.5, Xk — < 1 - y/2 - 2& otherwise.
112 13. Antialiasing Figure 13.5. A checkerboard sampled with 1. 16. and 256 samples. Images courtesy of Mike Stark. An analogous formu3a transforms 'k into to yk. The formu3a for the pixel intensity is then ii-i JAiJ) - ^ J^ f(i + -Vk-j -r Uk). i--o Note that this formu3a only applies to nonunifoniipoints that have been "warped" according to the appropriate function. Also, note that the input points need not be random for this to work: they need only be uniform. The process for sampling a pixel with warped regular sampiing is shown in Figure 13.6 T l+ #•'''•' -1 1.4-1) *■ ,. • ■ •• <i .+ 1) .V (1.1 ) (0.5.0.5) 5) -- 14. \.v5) .V Figure 13.6. The stages in applying a separable triangle to pixel (2. 1). Lett: A set of regular samples are generated on [O, 1]". Middle: These samples are warped to have the density of the filter. Right: The warped samples are moved over the center of the pixel. Note that the same procedure is used if the initial samples are random, jittered, etc. 14 Cameras In most graphics programs, a "pinhole" camera model is used where everything is in perfect focus. For images with "depth-of-field." where some objects are not in focus, we use a "thin-lens" camera model. Such a model is easy to implement in a path tracer. 14.1 THIN-LENS CAMERAS A thin-lens camera replaces the pinhole with a disk-shaped "thin-lens" which nas certain idealized behavior (Figure 14.1). If the camera is focused on a point at distance s f rom the lens, all light from that point will be focused at a point distance i behind the lens. These two points will both lie along a line through the lens center. The distances / and .s obey the thin-lens hiw. 1 _ I _ J. 14.2 REAL CAMERAS Specify film size (W.H) and focal length /. The film size is the actual physical size of the film that gets exposed—so H is approximately the distance between the sprockets on 35 mm film. Then we can specify where we are focusing on s > f. To specify the aperture of the lens we could just specify R. but the tradition is to use the perhaps less cbwousf-number, N = f/(2R). Given these variables, we have ui _ v\ _ s W/2= ~H]2~~i' 113
114 14. Cameras Figure 14.1. For four samples, stratified samples on the lens are randomly paired with stratihed samples on the pixel. rxr m T _: 25 ml.25 m Figure 14.2. Cameras with f-numbers 22, 11,5.6, and 3.3 focused at 0.5 meters. Images courtesy of Mike Stark. 14.2. Real Cameras 115 .5 m 25 m Figure 143. Camera with f-number 5.6 varying the focus. Images courtesy of Mike Stark. We know that and s-r /T,I/ /„ A IT (* — t\\ (ui,n) = (-uo,-i>o)= ^y—j—. y J y For a typical 35 mm camera and lens, / = 50 mm, W = 36 mm, and H = 24 mm. Images for a camera with f-number 5.6 are shown in Figure 14.2. Changing the focus is shown in Figure 14.3.
14. Cameras Figure 14.4. For four samples, stratified samples on the lens are randomly paired with stratitied samples on the pixel. 14.3 MULTIDIMENSIONAL SAMPLING One way to implement the camera is to take a random point ( . '. ". '") in [0. I)4 and use the first two coordinates to seed the lens sampling, and the last two for the pixel sampling. But this wouldn't stratify, which is very bad. An alternative is to stratify in 4D, but that is difficult and will produce poor stratification on the pixel and the lens relative to 2D stratification. One could Figure 14.5. Motion blur by generating rays with different times. Balls have center positions that vary with time. Image courtesy of Greg Coombe. 14.3. Multidimensional sampling 117 lens («»v0) <";.V/) (llj.V,) (u3,v3) y\ pixel (ao,b0) (a,,b,) (.a2,b2) U'j.bj) V time 'o 'I fi h Figure 14.6. The dark-shaded path represents a set of sample seeds that that each column is a set of 2D or 1 D stratified samples. generates one ray. Note also create two sets of stratified 2D samples and match the first lens sample with the first pixel samples, but this would lead to correlation and artifacts: in every pixel, the same part of the lens would be matched with the same parts of the pixel. But this matching will work if the pairing is random (Figure 14.4). If we add time to the mix. each ray is at a specific random time within the shutter-open time. For a moving object, a ray at time 3 is intersected at the point where the object is at time t. This automatically gives motum-hlureffects (Figure 14.5). The samples for a four sample pixel with time effects are shown in Figure 14.6.
15 Soft Shadows In this chapter, we will create soft shadows that arise from area light sources. One way to do this is tojust sprinkle point light sources across an area and use techniques from Chapter 3. Instead, we will use Monte Carlo methods to choose random points on the area of a light source. As the number of samples in the pixel becomes large, the number of samples on the light will become large as well. Thus, the shadows will become smooth. 15.1 MATHEMATICAL FRAMEWORK To calculate the direct light from one luminaire (light emitting object) onto a diffuse surface, we solve the following equations: L(x) = L,.(x)+ ~1 f , (x.^)cos6\L: (15.1) " Vail j where L(x) is radiance (color) of x. I,(x) is the light emitted at x. i?(x) is the reflectance of the point. *; is the direction from which the light is incident, and 6 is the angle between the incident light and the surface normal. Suppose we wanted to restrict this integral to a domain of one luminaire. Instead of "all uj." we would need to integrate overjust the directions toward the luminaire. In practice, this can be difficult (the projection of a polygon onto the hemisphere is a spherical polygon, and the projection of a cylinder is stranger still). So, we can change variables to integrate overjust area (Figure 15.1). Note that the differential relationship exists: dA cos B' &» = T-, M9- (15-2) 119
120 15. Soft Shadows Figure 15.1. Integrating over the luminaire. Note that there is a direct correspondence between dx. the differential area on the luminaire. and d^. the area of the projection o\ dx onto the unit sphere eentered at x. Just plugging those relationships into Equation 15.1 gives , i?(x) f T , ^<IA cos f?' L(X) = Z,„(X + -1 / LA-O COS 0-— rp;. * Jmk ||x'-x!|- There is an important flaw in the equation above. It is possible that the points x and x' cannot "see'" each other (there is a shadowing object between them). This can be encoded in a "shadow function." ,s(x. x'). wnich is either 1 or O depending on whether or not there is a clear line of sight between x and x'. This gives us the equation L(x) = L,.(x) + R[x) £1 f £,.(x )cosfl- „ / — . (1:>.3) X' I|X' - X„- If we are to sample Equation 15.3. we need to pick a random point x' On the surface of the luminaire with density function p (so x' ~ p). Just plugging into the Monte Carlo equation with one sample gives L(x)» LJ-x.) + R(x) Up \A. ) V.UO L n s(x,x')cos#' = '"p(x')||x'-x||2'' (15.4) If we pick a uniform random point on the luminaire, then p — 1/A where A is the area of the luminaire. This gives L(x) w Le{x) H Le(x ) cos9—^—■' . (15.5) 15.1. Mathematical Framework 121 We can use Equation 15.5 to sample planar (e.g., rectangular) luminaires in a straightforward fashion. We simply pick a random point on each luminaire. The code for one luminaire would be as follows: spectrum directLightfa n J pick random point x' with normal vector n' on light d = (x' - x) ;/ ray x + td hits at x' then return ALe(x')(n« d)(-n' - d)/||d||4 else return O The above code needs some extra tests such as clamping the cosines to zero if they are negative. Note that the term ||dj|4 comes from th-c distance squared term and the two cosines, e.g.. n • d = lldjl cos 9 because d is not necessarily a unit vector. Several examples of soft shadows are shown in Figure 15.2. Figure 15.2 Various soft shadows on a backlit sphere with a square and a spherical light source. Top: one sample. Bottom: 100 samples. Note that the shape of the light source is less important than its size in determining shadow appearance.
122 15. Soft Shadows Figure 15.3. Geometry for spherical lunuruiire. 15.2 SAMPLING A SPHERICAL LUMINAIRE Although a sphere with center c and radius r can be sampled using Equation 15.5. this will yield a very noisy image because many samples will be on the back of the sphere, and the cos 0' term varies so much. Instead, we can use a more complex p(x') to reduce noise. The first nonuniform density we might try is p(x') y. cos#'. This turns out to be just as complicated as samplingwith p(x') x cos 0' :\\x' — x]!2. so we instead discuss that here. We observe that sampling on the luminaire this way is the same as using a density constant function q{^) = const defined in the space of directions subtended by the luminaire as seen from x. We now use a coordinate system defmed with x at the origin, and a right- handed orthonormal basis with w = (c-x)/||c-x||. and v = (wxn)/ll(wxn)ll (see Figure 15.3). We also define [a.o) to be the azimuthai and polar angles with respect to the uvw coordinate system. The maximum Q that includes the spherical luminaire is given by • / r \ ( r V Qmax = arcsm I r. rr = arCCOS U 1 — J, 17 Vl|x-c||/ V Vl|x-c||y Thus, a uniform density (with respect to solid angle) within the cone of directions subtended by the sphere is just the reciprocal of the solid angle 2rr(l — cos ana,) 15.2. Sampling a Spherical Luminaire 123 subtended by the sphere: And we get, COSQ 0 fcrll-vMlP^)' This gives us the direction to x'. To find the actual point, we need to find the first point on the sphere in that direction. The ray in that direction is just (x + ia), where a is given by cos o sm a sin o sin a cos a We must also calculate p(x'). the probability density function with respect to the area measure (recall that the density function q is defined in solid angle space). Since we know that q is a valid probability density function using the a measure, and we know that do(^)- dA{x!) cosO1 /\\x-x'\\2. we can relate any probability density function <7(a.')with its associated probability density function p(x'): <?("<•) = p(x') costf' ■ x. (15.6) Figure 15.4 A sphere with Lc = 1 touching a sphere of reflectance 1. Where they touch the reflective sphere should have L(x) = 1. Left: one sample. Middle: 100 samples. Right: 100 samples, close-up.
124 15. Soft Shadows So we can solve for p(x'): , ,, cos 9' P(x ) = / , v • 2T||x-xT^l-V/l-(p^)j A good debugging case for this is shown in Figure 15.4. For further details on sampling the sphere with p see the article by Wang [66]. 153 NONDIFFUSE LUMINAIRES There is no reason the brightness of the luminaire cannot vary with both direction and position. It can vary with position x' if the luminaire is a television. Itcan vary with direction for car headlights and other directional sources. Nothing need change from the previous sections, except that Lr(x') must change to £p(x'.u-'). The simplest way to vary the intensity with direction is to use a phong-like pattern with respect to the normal vector n'. To keep the total light output independent of the exponent, you can use the form: L,:(x .a.') — — cos' n—l)0 where E(x')is the radiant exitance (power per unit area) at point x'. and n is the phong-exponent. You get a diffuse light for n = 1. 15.4 DIRECT LIGHTING FROM MANY LUMINAIRES Traditionally, when Nl luminaires are in a scene, the direct lighting integral is broken into A*l separate integrals [11]. This implies at least NL samples must be taken to approximate the direct lighting, or some bias must be introduced (as done by Ward where smali value samples are not calculated [67]). This is what you should probably do when you first implement your program. However, you can later leave the direct lighting integral intact and design a probability density function over all NL luminaires. As an example, suppose we have two luminaires, li and l2, and we devise two probability functions pi(x') and P2(x')- where pj(x')= O for x' not on lt and Pi(x') is found by a method such as one of those described previously for generating x on k. These functions can be combined into a single density over both lights by applying a weighted average: p(x') = api(x') + (1 - a)p2(x') 15.4. Direct Lighting from Many Luminaires 123 where a e (0,1). We can see that p is a probability density function because its integral over the two luminaires is one, and it is strictlypositive at all points on the luminaires. Densities that are "mixed" from other densities are often called mixture densities' and the coefficients a and (1 — Q) are called the mixing weights [59]. To estimate L = [L\ + £2). where L is the direct lighting and Li is the lighting from luminaire li, we first choose a random canonical pair (fi. C2). and use it to decide which luminaire will be sampled. If O < £1 < a, we estimate L\ with ei using the methods described previously to choose x' and to evaluate pi(x'), and we estimate L with ei/a. If £1 > a, then we estimate L with e2/(l — q). In either case, once we decide which source to sample, we cannot use (^1^2) directly because we have used some knowledge of £i- So, if we choose l\ (so d < Q), then we choose a point on l\ using the random pair (£i/a- &>)• If we sample U (so £j > a), then we use the pair ((£1 — q)/(1 -a),£i)- This way. a collection of stratified samples will remain stratified in some sense. Note that it is to our advantage to have ^j stratified in one dimension, as well as having the pair (£i.sa) stratified in two dimensions, so that the /, we choose will be stratified over many (fi.£>) pairs, so some multijittered sampling method may be helpful (e.g., [8]). This basie idea used to estimate L = (Li -t- L2) can be extended to Nl luminaires by mixing Nr. densities: p(x') = QiPi(x') + a2p_>(x') H 4- q'.Vlp.vl(x') 05.7) where the a,'s sum to 1. and where each Q, is positive if /, contributes to the direct lighting. The value of a, is the probability of selecting a point on the I,. and p, is then used to determine which point on /, is chosen. If I, is chosen, then we estimate L with ejai. Given a pair (si-s.')- we choose I, by enforcing the conditions i-i ( Y,qj <^< Y,aJ- And to sample the light we can use the pair (£,[. Ca) where «, This basie process is shown in Figure 15.5. It cannot be overstressed that it is important to "reuse" the random samples in this way to keep the variance low. in the same way we used stratified sampling (jittering) instead of random sampling in the space of the pixel. To choose the point on the luminaire U given (£i-52)> we can use the same types of pi for luminaires as used in the last section. The question remaining is what to use for on.
126 IS. Soft Shadows •\2±u a3. tt4 I I J L $1=0 $,=0.45 Actual § | chosen means we E -055 pick luminaire 3. Si=0 Si=0-33 I I ^1=0.75 I 41=1 5i=i.o Figure 15.5. Diagram of mapping i to choose /, and me reMiUing remapping to new canonical sample [. 15.4.1 Constant Weights The simplest way to choose values for n, was proposed by Lange [29] (and this method is also implied in the figure on page 148 ot" [23]). where all weights are made equal: a, = l/.Y^for all /'. This would definitely make a valid estimator because the n, sum to 1 and none ot" them is zero. Unfortunately, in many scenes this estimate would produce a high variance (when the Li are very different as occurs in most niaht "walkthroughs"). 15.4.2 Linear Weights Suppose we had perfect p; defined for all the luminaires. A zero variance solution would then result if we could set t*,; rx Lt. where Lt is the contribution from the ith luminaire. If we can make at approximately proportional to L,, then we should have a fairly good estimator. We call this the linear method of setting Qi because the time used to choose one sample is linearly proportional to JV L, the number of luminaires. To obtain such on we get an estimated contribution &£at x by approximating the rendering equation for li with the geometry term set to one. These eis (from 15.4. Direct Lightingfrom Many Luminaires 127 all luminaires) can be directly converted to a, by scaling them so their sum is 1: Qi _ ± . (15.8) i +e2H + eN,. This method of choosing on will be valid because all potentially visible luminaires will end up with positive Qi. We should expect the highest variance in areas where shadowing occurs, because this is where setting the geometry term to 1 causes qj to be a poor estimate of Qi. Implementing the linear a, method has several subtleties. If the entire luminaire is below the tangent piane at x. then the estimate for e* should be zero. An easy mistake to make is to set ex to zero if the center of the luminaire is below the horizon. This will make a; take the one value that is not allowed: an incorrect zero- Such a bug will become obvious in pictures of spheres illuminated by luminaires that subtend large solid angles, but for many scenes such errors are not noticeable (the figures in [51] had this bug. but it was not noticeable). To overcome this problem, we make sure that for a polygonal luminaire. all of its vertices are below the horizon before it is given a zero probability of being sampled. For spherical luminaires. we checkthatthe center of the luminaire is a distance greater than the sphere radius under the horizon piane before it is given a zero probability of being sampled.
16 Path Tracing This chapter describes path tracing where indirect lighting is computed using Monte Carlo methods. The roots of path tracing are in Whitted's odgina3 paper [71] and were expanded on by Cook [11] and were finally fully generalized by Kajiya [23[. Path tracing is elegant and general, but is not for the faint-of- heart when it comes to CPU intensity! 16.1 SIMPLE PATH TRACING To make our lite simple, let's assume for now that all surfaces are Lambertian, which is an idealization of a matte/dull surface. Let's also assume that all luniinaires (light-emitting objects) are diffuse emitters—they look the same color from all directions (as opposed to a car headlight which is much brighter head- on). The radiance of a reflective surface in this situation is given by the equation pin r L(p) = £,(p) + ^^ L[p. x) cos ft dx (16.1) where £f(p)is the emitted radiance (zero unless the surface is a luminaire). Rip) is the reflectance at point p. When we start ray tracing, our rays will either hit background or a surface. If a surface, we evaluate Equation 16.1 for p as the intersection point. When evaluating this equation, L,..(p. A) and R(p. A) are materia3 properties which are known inputs to our program. This leaves us with the integral. Provided we can pick random directions x ~ p for some density p. we get the equation L(p) asLe(p)+— -— . IT P(.w) This assumes only one sample. For good results we should average over many cdi. Note that 9 is entirely determined by u. So, if we took uniform directions <j. 129
130 16. Path Tracing Figure 16.1. A single ray in a path tracer just bounces around the environment. It does not branch. It terminates when it misses all objects, or exceeds some maximum depth. that would make/? = l/(2~-). But we can get better results if we use importance sampling to cancel out the cosine term/? x cos ft When we normalize the density function p so that its volume is 1. we see that p = (costf) 'it, and the integral becomes I(p) = L, (p) -t-/?lp)L(p.^)- (16.2) Note that Equation 16.2 applies if and only //the density of the ^ is proportional to the cosine of 0. This suggests the following function radiance to compute L: color radiance! ray r ) if r hits at p then generate random ray r„ return Le(p}— /?(p)radiance(r„) else return background This is a very easy function to write, but it may not terminate without some maximum allowed depth. Note that a ray just keeps bouncing without branching (Figure 16.1). This is why it is called part tracing: a whole path is generated for each sample point on the screen. The only missing detail is how one generates the random ray r„ with the right density. Given an orthonormal basis uvw for the surface where w points in the direction of the outward surface normal, we can think of the problem as choosing points on the unit sphere or hemisphere (since each ray direction u> can be expressed as a point on the sphere). If we assume the coordinate system where 9 is the angle to the w axis, and 4> is the angle around the w axis (the u axis is at <i> = 0), then, the canonical random numbers ( , ') can be mapped to 16.1. Simple Path Tracing 131 an appropriate point: (0, cj>) = (arccosVl-C,2<'). ux Uy u* Vx VV Vz Wj Wy Wz The scattered ray is with respect to some unit normal vector N (as opposed to the z axis). We can first convert the angles to a unit vector a: a = (cos 0 sin O, sin cj> sin 6, cos 0} We can then transform a to be an a' with respect to ur by multiplying a by a rotation matrix R (a' = Ra.). This rotation matrix is simple to write down: R = where u = {uT.uy,uz).v = (tv i'y, v~)>w = {wx,wy,wx)ionn a basis (an orthonormal set of unit vectors where u=vxw, v=wxu, and w = u x v) with the constraint that w is aligned with N: N |N| To get u and v. we need to find a vector t that is not co!linear with w. To do this, simply set t equal to w and change the smallest magnitude component 0f t to one. The u and v follow easily: t x w t x w] v = w x u. As an efficiency improvement, you can avoid taking trigonometric functions 0t inverse trigonometric functions (e.g., cos (arc cos (.r)) rather than the equivalent but cheaper x). For example, the vector a for our rays is a=(cos(27rOv/l7. sin(27r^)V?, \/l-^) A good way to initially debug this program is to use an enclosure of any shape with constant emitted radiance E and constant reflectance R. Your program should compute L — E + RE + R2E + ■ ■ ■. The converged solution is Try this with R = E = 0.5. Your program should have all pixels with value 1.0. ^ more complicated example is the touching spheres as in shown in Figure 16.2. A "Cornell box" is shown in Figure 16.3.
132 16. Path Tracing Figure 162. A simple path traced image with |(i) rays. per p]\ei. Figure 163. A simple path traced image with 100 rays per pixel (left) and 1600 ravs per (right). 16.2. Adding Shadow Rays 133 162 ADDING SHADOW RAYS One problem with simple path tracing is that a ray has to get "lucky" and hit a luminaire before it can add any light to an image. For scenes with smali lumi- naires, this implies many rays. Instead, we can compute "direct lighting" using shadow rays and use path tracing only for the indirect lighting (Figure 16.4). The algorithm for this is as follows: color retlectedRadiance( ray r ) if r hits at p then Ld = direct light at p generate random ray r„ return Z,di?(p)reflectedRadiance(r„) else return background Here "direct light" uses the techniques of the last chapter. Note that this just computes the reflected radiance, so it would not suy a luminaire is bright. For the first viewing rays you would have to add in L, (x). The difference between using shadow rays and not using them for a 100 sample image is shown in Figure 16.5. A more complex scene is shown in Figure 16.6. Figure 16A A single ray in a path tracer with shadow rays.
134 16. Path Tracing Figure 16.5. A 100 sample rendering with simple path tracing (left) and shadow rays (right). Figure 16A An image computed using a path tracer with shadow rays. The gloss on the tables uses nondiffuse reflectance which is discussed in the next chapter. 16.3. Adding Specularity 135 16.3 ADDING SPECULARITY It is not practical to compute direct lighting for specular surfaces, so instead we call radiance (simple path tracing) for initial viewing and specularly reflected rays, and reflectedRadiancefor diffusely scattered rays. For other forms of reflectance, as discussed in the next chaptEr, you need to evaluate more complex integrals.
17 General Light Reflection If you want more realistic looking images, idea3 diffuse and specular materials are usually not enough. This chapter discusses basics of genera3 light reflection and presents one advanced model. 17.1 SCATTERING FUNCTIONS Reflection from a surface can be described by how light incident on the surface is scattered into a continuum of directions. This scattering function can be described mathematically, and there are several strategies for deriving a mathematical model for reflection. To do any simulation using spread reflection, we need to develop a mathematical convention to describe its properties. We could look at a concept similar to diffuse reflectance. The simplest way to do this is to describe the ratio of incident light power at a given angle to outgoing light power integrated over all outgoing angles: power incident from (O.o) R\B.6) = - : . total outgoing power This quantity is often called directional hemispherical reflectance. But to describe the directional behavior of spread reflectance, we need some function over the outgoing directions {9'.0'). One way to do this is to imagine a hypothetical photon-like light particle that is incident to the surface from direction {6,<t>). This particle will be absorbed by the surface with probability 1 — R(9,<p). If it is not absorbed, it will be scattered in some outgoing direction {9', (b')with probability density function p(6. 4>.9'. <f>'). We callp(#, (p. 9'. 0') the scattering probability density function, or SPDF for short. Note that there is no standard term for the SPDF. Also note that the SPDF refers to a potentially different 137
138 17. General Light Reflection probability density function for each (9,4>). Readers who prefer to think deter- ministically can think of the product of R and p as an energy density function without losing any information. Given the directional hemispherical reflectance and the SPDF for a particular type of material, we have completely specified its reflectance behavior. We could change the definition in several ways without changing the completeness. The most common way to do this is to multiply the directional hemispherical reflectance, the SPDF, and reciprocal of cos 9' into a single product: P{0,<t>,e'.o') = ^)p{6>0e'^ cos 01 There is no gain or loss of information in this transformation, but the form ofp is convenient for many image synthesis and measurement applications as it relates incoming irradiance to outgoing radiance, quantities that are often computed and measured. The standard name for p is the bidirectional reflectance distribution function, or BRDF for short. One fundamental property of a BRDF is that lAO.o.B'.o') = plti'.o'.e.o). This property is known as reciprocity: incident and outgoing directions can be interchanged. Although almost all of the reflection literature is written in terms of BRDF. it is often convenient to think in terms of the SPDF (or the outgoing energy density function) when intuition can play a role. The directional hemispherical reflectance can be written in terms of the BRDF: R(0.o) = I ['p(8. 0.8'.0')cos 6'sin O'dO'do'. Jo Jo This equation is equivalent to saying the SPDF must have unit volume, which is required for any probability density function. For a physically valid materia3 model, it is necessary that R(d.cti) < 1; it must be energyconsenins>. Many rendering algorithms rely on these properties, so it is important when using these Tenderers that BRDF models both conserve energy and be reciprocal. Lewis calls BRDF models that are faithful to these constraints physically plausible [31], As an example we see that the Lambertian BRDF, Pl(M,0 ??•) = —, 7T is both reciprocal and energy conserving provided the reflectance Rd is less than 1- The division by n is necessary because the BRDF is integrated over the cosine-weighted hemisphere. 17.2. An Advanced Model 139 Figure 17.1. Geometry of reflection. Note that ki, k2. and h share a plane, which usually does not include n. 17.2 AN ADVANCED MODEL A BRDF model that will produce scratched metals and polished surfaces is presented here. For a derivation, see the paper by Ashikmin and Shirley [6]. We decompose the BRDF into a specular component and a diffuse component. Accordingly, we write our BRDF as the classical sum of two parts: plki.ki) =/9,(k1.k2)+pd(k1.k2) (17.1) where the first term accounts for the specular reflection and is presented first. 17.2.1 Anisotropic Specular BRDF Several shapes for the specular lobe have been proposed with Phong power-of- cosine lobe being the most popular. This is primarily due to its simplicity. The original form of the Phong shader [43] has several problems which triggered the development of more physically plausible Phong-style BRDFs [27, 31. 37]. We can also use an anisotropic Phong-style specular lobe and incorporate Fresnel behavior while attempting to preserve the simplicity of the initial model and physical plausibility achieved earlier for the Phong BRDF by other researchers. This BRDF is -^(cosa) (17.2) /j(kl.k,) = v' " '" ' '— —— 8~ cos Q ma.x(cos ii\, cos d-2) where nu and nv are control parameters. Again, we use Schlick's approximation to Fresnel fraction [49]: F(cosq) = Ra + (1 -Rs)(l- cos a)5 (17.3) where R3 is the material's reflectance for the normal incidence.
140 17. General Light Reflection Figure 17.2. Metallic spheres for various exponents The specular BRDF described in this section is useful for representing metallic surfaces where the diffuse component of reflection is verysmali. Figure 17.2 shows a set of spheres on a texture-mapped Lambertian piane. As the values of parameters nu and n,, change, the appearance of the spheres shifts from rough metal to almost perfect mirror, and from highly anisotropic to the more familiar phong-like behavior. 17.2.2 Diffuse Term It is possible to use a Lambertian BRDF together with the specular term. However, a simple angle-dependent form of the diffuse component can account for the fact that the amount of energy available for diffuse scattering varies due to the dependence of the specular term's total reflectance on the incident angle. In 17.2. An Advanced Model 141 particular, diffuse color of a surface disappears near the grazing angle because the total specular reflectance is close to 1 in this case. This well-known effect cannot be reproduced with a Lambertian diffuse term and is therefore missed by most reflection models. Another, perhaps more important, limitation of the Lambertian diffuse term is that it must be set to zero to ensure energy conservation in the presence of a Fresnel-weighted term. The diffuse term that behaves this way is Note that this diffuse BRDF does not depend on n,L and nv. A set of polished spheres with different phong exponents nu, n„ is shown = 10 11.= 100 n„= 1000 n„= 10000 Figure 17J. Diffuse spheres for various exponents.
142 17. General Light Reflection Figure 17.4. Three views for n, = nv = 400 and a diffuse substrate. in Figure 17.3. For all spheres. R, is set to 0.05 across the visible spectrum which is a typical value for plastics. In addition to anisotropic highlights and blurred reflections, we can observe strengthening of the specular reflection near the silhouette of the sphere along with simultaneous decrease in the intensity of the diffuse intensity. This effect is mere prominent in Figure 17.4 where three different views of the same scene are shown. 17.3 IMPLEMENTING THE MODEL Recall the BRDF is a combination of diffuse and specular components: /9(ki.k2) =ps(k1.k,) + p,,(k,.k,). (17.4) It is not necessary to call trigonometric functions to compute the exponent, so the specular BRDF is p(kL.k2)= V'K + D(^1) (n-h) »-^~ air (h« k)max((n- kL), (n k2)) (17.5) In a Monte Carlo setting we are interested in the following problem: Given kj, generate samples of ki with a distribution with a shape similar to the cosine-weighted BRDF. The key observation is inspired by discussion by Zimmerman [76] and by Lafortune and Willems [27] who point out that greatly 17.3. Implementing the Model 143 Figure 17.5. A close-up of the model implemented in a path tracer with 9. 26. and 100 samples. undersampling a large value of the integrand is a serious error while greatly oversampling a smali value is acceptable in practice. The reader can verify that the densities suggested below have this property. We can just use the probability density function. Pi, (h) = - 1) 1) , co?" o-^-n, sm" o i (17.6) to generate a random h. However, to evaluate the rendering equation, we need both a reflected vector k^ and a probability density function p^i). It is important to note that if you generate h according to />/, (h) and then transform to the resulting ki. k. = -ki +2(kih)h. (17.7) the density of the resulting k-j is not pi,(k_>). This is because of the difference in measures in h and k_> space: = 4(k1h)</u,'/l. So the actual density p(k2) is P(k2) P/,(h) 4(k!h)- Note that it is possible to generate an h vector whose corresponding vector k2 will point inside the surface, i.e.. (kin) < 0. The weight of such a sample should be set to zero. This situation corresponds to the specular lobe going below the horizon and is the main source of energy loss in the model. Clearly, this problem becomes progressively less severe as nu, nv become larger. The only thing left now is to describe how to generate h vectors with probability density function of pj,.(h). We will start by generating h with its spherical
144 17. General Light Reflection angles in the range (9, 0) e [0, f ]x [0, §]. Note that thisis onlythe firstquadrant of the hemisphere. Given two random numbers ( 1, 2) uniformly distributed in [0,1], we can choose and then use this value of (j> to obtain 9 according to COS 9 = (1 - 2) »««»:<♦+..„.i»<*-(-l. (17.9) To sample the entire hemisphere, the standard manipulation where 1 is mapped to one of four possible functions depending on whether it is in [0.0.25), [0.25,0.5), [0.5,0.75), or [0.75,1.0). For example, for & 6 [0.25,0.5), find 0(1 _ 4(0.5 - 1)) Vla Equation 17.8, and then "flip" it about the 4>= 7r/2axis. This ensures full coverage and stratification. Three images sampled using this method are shown in Figure 17.5. For the diffuse term, it would be possible to do an importance sample with a density close to cosine-weighted BRDF in a way similar to that described by Shirley et al. [53], but it works well to use a simpler approach Figure 17.6. An image with a Lambertian sphere (left) and a sphere with "» - 17A- Including Indirect Light 145 an<^ venerate samples according to cosine distribution. This is sufficientlycjQse to the complete diffuse BRDF to substantially reduce variance 0f ^ jyjon(e An example of the model in a full scene inspired by Lafortune pg] js shown in Figure 17.6. Note tne specular effects on the horizon 0f the ri8ht sphere which implements the model of this paper, and the absence of these effects on the left sphere which is Lambertian. 17.4 INCLUDING INDIRECT LIGHT To generalize path tracins t0 include genera3 BRDF we need to solve the rendering equation: L(k1) = Le(ki)-/ p(k1.k2)L(k2)cos.32<Mk-2)- (17-10) H» we have l^ out tne Polnt x we are fading for simpler notation. we choose a random k, with density p(k>). we get p(ki.k.»)L(k>)cos,J2 KkO^Uki)- ^j T, , . , |ast chapter can be simply extended to account for equation.
18 Spectral Color and Tone Reproduction To create more "physically accurate" images, you will need to implement "spectral" color. Although it has all the same base operations as RGB colors, a spectral color has values for every wavelength in the visible spectrum. An additional complication is that a spectral color needs to eventually be displayed or written to file, usually as an RGB color. This chapter deals with issues of converting radiometric quantities to control vectors for real display devices such as CRTs or printers. 18.1 SPECTRAL OPERATIONS The key issue in designing a spectral class is deciding what representation to use. A real spectrum, for visible light computation, is a mapping from the visible spectrum j380nm. 800am] to nonnegative real values. This is an infinite amount of data so we need to approximate such a mapping. Typically, we would approximate a spectrum s(\) with a weighted sum of N basis functions b,(\): N S(x) = y>i&,-(A). This allows us to store a spectrum using a vector of N weights n^. Being a believer in the KISS principle, I suggest using nonoverlapping piecewise constant basis functions that evenly partition the vis3ble spectrum into N "boxes." Glassner has an excellent discussion of the mathematics behind such a system in his two volume set [17], 147
148 18. Spectral Color and Tone Reproduction 18.2 LUMINANCE The signal that reaches the eye varies with wavelength and can be described by spectral radiance L(A) which represents the intensity of light coming froma particular direction at a particular wavelength. The SI units of spectral radiance are Wm~2sr_1 run-1. All light is not created equal; humans are more sensitive to some wavelengths than others, and are not sensitive at all to light outside the range [380nm, SOOnm]. Based on many experiments, psychologists came up with an empirical formu3a to determine how much "useful" light for protraying light/dark was available in a given spectral radiance signal. The formu3a for luminance is /■800 Y = k / y(X)L{\)d\. J380 where k = 683cd/W. an odd constant whose value ensures backward compatibility with historical units that were based on the number of candles requiredto produce equivalent light. The data for y(A)are given in Table 18,1. 18.3 CIE TRISTIMULOUS VALUES Luminance only provides light/dark information. For color, we need two other signals. The standard one is XZ which together with Y give us the CIE tris- tiinulous values: ^ 800 X = k / x(\)L{\)d\. J380 ,800 Z = k / z{\)L(\)dX J :iso where k is the same constant as in the equation for Y. For low levels of illumination, such as moonlight, your eyes go into a different perceptual mode, and the spectral sensitvity changes. The values of XYZ become irrelevant, and the scotopic luminance determines lights and darks: /•800 V = k' I v'{\)L(\)d\, J3S0 where k' = 1700#. 18.3. CIETristimulous Values A (rm) 380 390 400 410 420 430 440 450 460 470 480 490 500 510 520 530 540 550 560 570 580 590 600 610 620 630 640 650 660 670 680 690 700 710 720 730 740 750 760 770 X 0.0014 0.0042 0.0143 0.0435 0.1344 0.2839 0.3483 0.3362 0.2908 0.1954 0.0956 0.0320 0.0049 0.0093 0.0633 0.1655 0.2904 0.4334 0.5945 0.7621 0.9163 1.0263 1.0622 1 .0026 0.8544 0.6424 0.4479 0.2835 0.1649 0.0874 0.0468 0.0227 0.0114 0.0058 0.0029 0.0014 0.0007 0.0003 0.0002 0.0001 y 0.0000 0.0001 0.0004 0.0012 0.0040 0.0116 0.0230 0.0380 0.0600 0.0910 0.1390 0.2080 0.3230 0.5030 0.7100 0.8620 0.9540 0.9950 0.9950 0.9520 0.8700 0.7570 0.6310 0.5030 0.3810 0.2650 0.1750 0.1070 0.0610 0.0320 0.0170 0.0082 0.0041 0.0021 0.0010 0.0005 0.0002 0.0001 0.0001 0.0000 z 0.0065 0.0201 0.0679 0.2074 0.6456 1.3856 1.7471 1.7721 1.6692 1.2876 0.8310 0.4652 0.2720 0.1582 0.0782 0.0422 0.0203 0.0087 0.0039 0.0021 0.0017 0.0011 0.0008 0.0003 0.0002 0.0000 0.0000 0.0000 0.0000 0.0000 0.0000 0.0000 0.0000 0.0000 0.0000 0.0000 0.0000 0.0000 0.0000 0.0000 v' 0.0006 0.0022 0.0093 0.0348 0.0966 0.1998 0.3281 0.4550 0.5670 0.6760 0.7930 0.9040 0.9820 0.9970 0.8350 0.8110 0.6500 0.4810 0.3288 0.2076 0.1212 0.0655 0.0332 0.0159 0.0074 0.0033 0.0015 0.0007 0.0003 0.0001 0.0001 0.0000 0.0000 0.0000 0.0000 0.0000 0.0000 0.0000 0.0000 0.0000 Table [g.j. Values for the trisimulous and scotopic sensitivity curves.
150 18. Spectral Color and Tone Reproduction Often, we want to factor out luminance and concentrate on color. The standard for this is to use chromaticity values: y ,yi \X + Y + Z' X + Y + Zj' There is a similar formu3a for z but it is rarely used because x + y + z = 1. Instead of XYZ, people often pass around only xyY. This way we can talk about "color" and "intensity" seperately. We can also compute XYZ from xyY: (x.r.z) = fg,y,(i-'-»)n. (18,) V y y J We sometimes know the tristimulous values for the RGB channels of our CRT. Let's say these are (Ar.Y'r, Zr) for the red channel, (A"9.Y'<,. Zg)for the red channel, and {Xb.Yt. Zb) for the blue channel. If we assume a perfect black point for the monitor (unlikely), then given a gamma-corrected RGB signal of (?•,<?. 6). we can compute the screen tristimulous values (X.,. V'3.ZS): rX,.+ gXg + bX,~ X A',; .\V| [r~ rY,.+gYg + bYh ' = ' Yr Y,, Yb g rZy + gZg + bZ>, ' Z, Za Zh\ [b You can invert the equation above to figure out how to set (r,g. b) givena desired (A*. Y.Z). Note that you may get values much larger than 1.0. or smaller than 0.0, so you will need to do some manipulation to deal with that. However, there is a bigger problem. Monitor manufacturers almost never tell you (A*,.. V,.. Zr) etc. Instead they give the chromiticities of the phosphors (x,.,y,.). {x,r yt/). (.;-(,. (/;,). and the chromiticity of the white point (.r„..;/„.). In addition, you can usually measure the luminance Y„. of the brightest white screen with a consumer photometer. If you can't measure that, assume it is approximately Y"„. = lOOcd/nr. The reason manufacturers don't tell you Y^.is that your brightness now changes it. The reason the white point varies is that "white" is usually the averagecolor in the room. Thus, what looks white in a fluorescenl-litroom will have dominant short wavelengths, and what looks white in an incandescent-lit room will have dominant long wavelengths. So, if you move a monitor with a white-looking image from a fluorescent-lighted room to a incandescent-lit room that same display will look blue. This same issue causes photographers to buy "daylight" or "tungsten" film. To convert the information the manufacturers give us (tristimulous values), we need to do some algebra. First, let's write a straightforward equality: '*r *a Xi.~ Yr Ys Y„ 111 Z^ £ Z^ [. r, y, Yb _, A, y. z. = "Yr 1 = Xw Yw 18.4. Tone Mapping 151 Now we do some subsitutions so we have only (Yr,Yg,Yb)as unknowns: 1 V9 1 l-J»-»g Vb 2l Vb 1 1—ib—Vh Vb x,.,Y„, yw Y We can use numerical methods, or algebraically Cramer's rule, to solve for (Yr, Yg, Yi,): Once we have that, we can get (XrXg.Xi,), {Yr. Yg. Yb), [Zr,Zg. Z\,) using Equation 18.1. For a typical trinitron monitor we have: (xr,yr) = (0.625,0.340) {xg,yg) = (0.280.0.595) (xb.yb) = (0.155.0.070) (xu..yw) = (0.283.0.298) lOOcd/nr Using the earlier equations, this yields 1 1000 ' 348.3 -107.2 6.35 152.1 196.6 20.00 55.9" 3.67 8.11 X" y; z. where (A".,. Y',. Z.s) are the tristimulous values for the computed spectrum. An emersina standard for RGB monitors and gammas is "sRGB". This standard is worth investigating for long-term use. For details see www.srgb.com. 18.4 TONE MAPPING A physically-based Tenderer can produce arbitrarily large RGB values to be displayed on a monitor or printed page. People use tone mapping to scale these quantities to a "reasonable" level that can be seen on the display. This is analogous to what photographers do to make sure their pictures are viewable. For example, a photo of a night scene is really much brighter than the night scene is. Tone mapping is a complex issue with hundreds of papers related to it, and research continues today. The psychophysical approach of making displayed synthetic images have certain correct objective characteristics was introduced by Upstill [65]. The mapping of intensity has been dealt with by brightness matching [60], contrast detection threshold mapping [13, 30, 65, 68], and a combination of the two [39].
152 18. Spectral Color and Tone Reproduction This section will provide just one simple way to tone map rendered images. It implements the work of Ward [68]. s W X y X y Y = = = = = = = < 0 3/iogl0y+2\2' o/iogl0y+2^ \ 2.6 / I 2.6 J l X + Y+Z X/W Y/W (1 - s)xw+ s(x +xw — 0.33) (l-s)yw+s(y +yu, - 0.33) 0 .4468(1 - s)V + sY if log10 Y < -2, if -2 < log10 Y < 0.6 otherwise. Here. V" is the scotopic luminance. After this process, the scotopic pixels will be desaturated. the mesopic pixels will be partially desaturated. Also, the )' channel will store scaled scotopic luminance for scotopic pixels, photopic luminance for photopic channels, and a combination for mesopic pixels. The scaling factor 0.4468 is the ratio of Y to V for a uniform white field. To scale the resulting luminance Y we now apply Y = Y_ i 1.219 + (V.,/2)0"1 v„. ^ i.2i9 + r0-1 where Y, is the log-average of luminances in the computed image. Finally, the A"Z for the fina3 display is X = *. When the fina3 XYZ are converted to RGB, the RGB may be negative or above one. They should be clamped to [0.1] if that is true. 19 Going Further This book has described how to implement a basie ray tracer and the classic probabilistic extensions. There are many places you can take it from^gj-g j give the basie references below: • More shapes. In addition to triangles and spheres, you can implement any primitive with which you can intersect a 3D line. Examples include: genera3 polygons |18|. superquadrics [261. constructive-solid geometry Inland quadric surfaces [14|. • Other rendering algorithms. These include radiosity [9. 56]. density estimation [54]. photon maps [21. 22). and irradiance caching [69|. • Displacement maps. These displace positions based on a procedural func- ti0n. There is a variety of ways to treat displacement mapping, the most practical being caching [42]. and all are somewhat awkward. However, displacement maps make amazing images! • Participating media. For tog and smoke to "partcipate" in light scattering, there is a varietv of algorithms. 1 think the best one is also the easiest to implement: photon maps |22]. • Natural illumination. Your images will look more realistic if you use reasonable values for sunlight and skylight. These can be found jn a variety of sources referenced in Preetham et al. [45]. • Better tone mapping. For images that have a high dymanie range, the simple tone mapping presented earlier is insufficient. For such scenes, a spatially-varying operator should be used [39. 61]. For scenes with a dominant hue. chromatic adaptation should be accounted for [391. For scenes with very bright objects, glare should be simulated [58]. Have fun, and if you render any neat images, please send me a pointer as I always love seeing new rendered images! 153
Bibliography [ 1 ] John Amanatides and Don P. Mitchell. Some regularization problems in ray tracing. In Proceedings of Graphics Interface '90, pages 221-228. June 1990. [2] John Amanatides and Andrew Woo. A fast voxel traversal algorithm for ray tracing. In Eurographics '87, 1987. [31 Anthony A. Apodaca and Larry Gritz. AdvancedRenderman Creating CCI for Motion Pictures. Morgan Kaufmann. 2000. [4] James Arvo and David Kirk. A survey of ray tracing acceleration techniques. In Andrew S. Glassner. editor. An Introduction to Ray Tracing. Academic Press. San Diego. CA. 1989. [5] Ian Ashdown. Radiosm: A Programmer's Perspective. John Wiley & Sons. New York. 1994. includes C++ source code for fully functional radiosity Tenderer. [6] Michael A.shikmin and Peter Shirley. An anisotropic phong reflection model. To appear. [7] Frank Canters and Hugo Decleir. The World in Perspective. Bath Press, Avon. Great Britain. 1989. [8] Kenneth Chiu. Peter Shirley, and Changyaw Wang. Multi-jittered sampling. In Paul Heckbert. editor, Graphics Gems TV, pages 370-374. Academic Press, Boston, 1994. [9] Michael F. Cohen and John R. Wallace. Radiosity and Realistic [mage Synthesis. Academic Press, Boston, MA, 1993. [10] Robert L. Cook. Stochastic sampling in computer graphics. ACM Transactions on Graphics, 5(l):51-72, January 1986. 155
156 Bibliography [11] Robert L. Cook, Thomas Porter, and Loren Carpenter. Distributed ray tracing. Computer Graphics, 18(4): 165-174, July 1984. ACM Siggraph '84 Conference Proceedings. [12] David Ebert, Kent Musgrave, Darwin Peachy, Ken Perlin, and Steve Wor- ley. Texturing and Modeling: A Procedural Approach. Academic Press, Burlington, MA, 1994. [13] James A. Ferwerda, Sumant N. Pattanaik, Peter Shirley, and Donald P. Greenberg. An adaptation model for realistic image sysnthesis. In Computer Graphics, Computer Graphics Proceedings, Annual Conference Series, August 1996. ACM Siggraph '96 Conference Proceedings. [14] Andrew S. Glassner, editor. An Introduction to Ray Tracing. Academic Press. San Diego. CA, 1989. [15] Andrew S. Glas'sner. A model for fluorescence and phospherescence. in Proceedings of the Fifth Eurographics Workshop on Rendering, pages 57- 68. June 1994. [16] Andrew S. Glassner. Principles of Digital Image Synthesis. Morgan- Kaufman. San Francisco. 1995. [17] Andrew S. Glassner. Principles of Digital Image Synthesis. Morgan- Kaufman, San Francisco. 1995. [18] Eric Haines. Point in polygon strategies. Graphics Gems IV, pages 24-46. 1994. [ 19] John H. Halton. A retrospective and prospective of the Monte Carlo method. SIAMReview. 12(1): 1-63. January 1970. [20] J. M. Hammersley and D. C. Handscomb. Monte Carlo Methods. Wiley. New York, N.Y..'l964. [21] Henrik Wann Jensen and Niels Jorgen Christensen. Bidirectional Monte Carlo ray tracing of complex objects using photon maps. Computers & Graphics, 19(2), 1995. [22] Henrik Wann Jensen and Per H. Christensen. Efficient simulation of 'ignt transport in scenes with participating media using photon maps. Proceedings of SIGGRAPH 98, pages 311-320, July 1998. [23] James T. Kajiya. The rendering equation. Computer Graphics, 20(4): 143- 150, August 1986. ACM Siggraph '86 Conference Proceedings. Bibliography 157 [24] Craig Ko^> Pat Hanrahan, and Don Mitchell. A realistic camera model for computer graphics. In Rob Cook, editor, Proceedings of SIGGRAPH (Anaheim California, August 6-11, 1995), Computer Graphics Proceedings, Annual Conference Series, pages 317-324, August 1995. [25] G. P. jQjnnen. Polarized light in nature. Cambridge University Press, Cambridge, 1985. [26] Roman Kuchkuda. An introduction to ray tracing. In R. A. Earnsnaw- editor, Theoretical Foundations of Computer Graphics and CAD, pages 1039-1060. Springer-Verlag, 1988. [27] Eric P. LafbrtUne and Yves D- willems- UsinS the modified Phong BRDF for pr,ysicaiiy based rendering. Technical Report CW197, Computer Science Department, K.U.Leuven, November 1994 [28] Eric P. F. Lafortune, Sing-Choong Foo. Kenneth R Torrance. and Don_ aid P. Greenberg. Non-linear approximation of reflectance functions. In SIGGRAPH 97 Conference Proceedings, pages 117-126. August 1997. [29] Brigitta Lange. The simulation of radiant light transfer with stochastic r-iv-tracin" ^n Proceedings of the Second Eurographics Workshop on Rendering (Barcelona. May 1991). 1991. [30] Gregory Ward Larson. Holly Rushmeier. and Christine Pi'tko. A visibility matching tone reproduction operator for high dynamie range scenes. IEEE Transactions on Visualization and Computer Graphics, 3(4):291-306. tober - December 1997. ISSN 1077-2626. ■ •,■] Robert Lewis. Making shaders more physically plausible. In Micnae R Cohen. Claude pUech. and Francois Sillion. editors. Fourth Eurographics Workshop on Rendering, pages 47-62. Eurographics. June 1993. in Paris. France, 14-16 June 1993. [32] Don P. Mitchell. Spectrally optimal sampling for distributed ray tracing. In Thomas W. Sederberg, editor. Computer Graphics (SIGGRAPH Proceedings), volume 25, pages 157-164, July '991. [33] Don P. Mitchell. Ray tracing and irregularities of distribution. In Pr"~ reedines °ft^le Third Eurographics Workshop on Rendering, pages ~ ' 1992. [34] Don P. Mitchell and Arun N. Netravali. Reconstruction Filters in com_ puter graphics. Computer Graphics, 22(4):221-228, August 1988. ACM Siggraph '88 Conference Proceedings.
158 Bibliography [35] Tomas Moller and Eric Haines. Real-Time Rendering A K Peters, Natick, MA, 1999. [36] Tomas Moller and Ben Tmmbore. Fast, minimum storage ray-triangle intersection. Journal of Graphics Tools, 2(l):21-28, 1997. [37] Laszlo Neumann, Attila Neumann, and Laszld Szirmay-Kalos. Compact metallic reflectance models. Computer Graphics Forum, 18(13X 1999. [38] S. N. Pattanaik. Computational Methodsfor Global Illumination an(^ Visualisation 0f Complex 3D Environments. PhD thesis, Birla Institute of Technology & Science, Computer Science Department, Pilani, India, February 1993. [39] Sumanra N. Pattanaik, James A. Ferwerda, Mark D. Fairchild. and Don" ^ P. Greenberg. A multiscale model of adaptation and spatial vision for realistic inla?e display. Proceedings of S1GGRAPH 98. pages 287-298. [40] Ken Perlin. An image synthesizer. Computer Graphics, 19(3)-">87-">96 July 1985. ACM Siggraph "85 Conference Proceedings. [41] Ken Per''n and Eric M. Hoffert. Hypertexture. Computer Graphics, 23(3):253-262. July 1989. ACM Siggraph "89 Conference Proceedings. [42] Matt Pllarr and Pat Hanrahan. Geometry caching for ray-tracing displacement maps. Eurographics Rendering Workshop 1996, pages -^ i_j.o June 1996. ' " • [43] Bui-Tuong Phong. Illumination for computer generated ima„es Commit nications of' the ACM, 18(6):311-317, June 1975. c" [44] Charles A. Poynton. A Technical Introduction to Digital Video. wj,„v New York. 1996. ey' [45] A. J. Preetham, peter Shirley, and Brian E. Smits. A practjcai analytic model for daylight. Proceedings of SIGGRAPH 99, pages 91-100, August 1999. [46] Werner Purgathofer. a statistical method for adaptive stochastic sampling. Computers and Graphics, 11(2): 157-162, feb 1987. [47] S. D. Roth. Ray casting for modeling solids. Computer Graphics and Image Processing, 18(2): 109-144, February 1982. Bibliography 159 [48] Christophe Schlick. A customizable reflectance model for everyday rendering. In Proceedings of the Fourth Eurographics Workshop on Rendering, pages 73-84, June 1993. [49] Christophe Schlick. An inexpensive BRDF model for physically-based rendering. Computer Graphics Forum, 13(3):233—246, 1994. [50] P. Shirley. Discrepancy as a quality measure for sample distributions. In Werner Purgathofer, editor, Eurographics '91, pages 183-194. North- Holland, September 1991. [51 ] Peter Shirley. A ray tracing method for illumination calculation in diffuse- specular scenes. In Proceedings of Graphics Interface '90. pages 205-212, May 1990. [52] Peter Shirley and Kenneth Chiu. . a low distortion map between disk and square. Journal of Graphics Tools. 2(3):45-52. 1997. [53] Peter Shirley. Helen Hu. Brian Smits. and Eric Lafortune. A practitioners' assessment of light reflection models. In Pacific Graphics, pages 40-49. October 1997. [54] Peter Shirley. Bretton Wade. David Zareski. Philip Hubbard. Bruce Walter, and Donald P. Greenberg. Global illumination via density estimation. In Proceedings of iheSixth Eurographics Workshop on Rendering, pages 187— 199. June 1995. [55] Y. A. Shreider. The Monte Carlo Method. Pergamon Press. New York. N.Y. 1966. [56] Francois X. Sillion and Claude Puech. Radiosity & Global Illumination. Morgan-Kaufmann. San Francisco. 1994. [57] Brian Smits. Efficiency issues for ray tracing. Journal of Graphics Tools. 3(2):1-14. 1998. [58] Greg Spencer, Peter Shirley, Kurt Zimmerman, and Donald P. Greenberg. Stratified sampling of spherical triangles. In Computer Graphics. Computer Graphics Proceedings, Annual Conference Series, pages 325-334, August 1995. ACM Siggraph "95 Conference Proceedings. [59] D. M. Titterington, A. F. M. Smith, and U. E. Makov. The Statistical Analysis of Finite Mixture Distributions. John Wiley & Sons, New York, NY, 1985.
160 Bibliography [60] Jack Tumblin and Holly E. Rushmeier. Tone reproduction for realistic images. IEEE Computer Graphics and Applications, 13(6):42-48, November 1993. also appeared as Tech. Report GIT-GVU-91-13, Graphics, Visualization & Usability Center, Coll. of Computing, Georgia Institute of Tech. [61] Jack Tumblin and Greg Turk. Lcis: A boundary hierarchy for detail- preserving contrast reduction. Proceedings ofSIGCRAPW9, pages 83-90, August 1999. [62] Greg Turk. Generating random points in triangles. In Andrew Glassner, editor, Graphics Gems. Academic Press, New York, NY, 1990. [63] Robert Ulichney. Digital Halftoning. MIT Press, Boston. 1988. [64] Steve Upstill. The Renderman Companion. Addison-Wesley, Reading. MA, 1990. [65] Steven Upstill. The Realistic Presentation of Synthetic Images: Image Processing in Computer Graphics. PhD thesis. Berkeley. 1985. [66] Changyaw Wang. Physically correct direct lighting for distribution ray tracing. In David Kirk, editor, Graphics Gems 3. Academic Press. New York, NY, 1992. [67] Greg Ward. Adaptive shadow testing for ray tracing. In Proceedings of the Second Eurographics Workshop on Rendering (Barcelona. May 1991). 1991. [68] Greg Ward. A contrast-based scalcfactor for luminance display. In Paul Heckbert, editor, Graphics Gems IV, pages 415—421. Academic Press, Boston. 1994. [69] Gregory J. Ward. Francis M. Rubinstein, and Robert D. Clear. A ray tracing solution for diffuse interreflection. In John Dill, editor, Computer Graphics (SIGGRAPH '88 Proceedings), volume 22, pages 85-92, August 1988. [70] Alan Watt and Mark Watt. Advanced Animation and Rendering Techniques: Theory and Practice. Addison-Wesley Publishing Company, 1992. [71] T. Whitted. An improved illumination model for shaded display. CACM, 23(6):343-349, June 1980. [72] Mason Woo, editor. OpenGL Programming Guide. Addison-Wesley, Reading, MA, 3rd edition, 1999. Bibliography [73] H. Wozniakowski. Average case complexity of multivariate integration. Bulletin (New Series) of the American Mathematical Society, 24(1): 185- 193, January 1991. [74] Sidney J. Yakowitz. Computational Probability and Simulation. Addison- Wesley, New York, N.Y., 1977. [75] S. K. Zaremba. The mathematical basis of Monte Carlo and quasi-Monte Carlo methods. SIAMReview, 10(3):303-314, July 1968. [76] Kurt Zimmerman. Density Prediction forlmportance Sampling in Realistic Image Synthesis. PhD thesis, Indiana University, June 1998.
Index aliasing, 105 anisotropic reflection, 139 aperture. 113, 115 attenuation constant. 46 barycentric coordinates. 24-26.65, 98 Beer's Law. 46. 47 bidirectional reflectance distribution function (BRDF). 138 box filter. 108 bump map. 57 camera. 35mm. 115 orthographic. 29 pinhole. 37, 113 thin-lens. 113 canonical basis, 7 canonical random number, 84, 95, 107 chromaticity, 150 CIEphotopic sensitivity function, 148 color operations, 3 color, RGB, 3, 147, 150-152 spectral, 147 coordinate systems, 14—16 coordinates. local. 69 world, 69 Cramer's rule. 27 cross product. 5 cumulative probability distribution function. 96 depth-of-field. 113 dielectrics. 44. 46, 47 diminishing return, 87 direct lighting. 133 directional hemispherical reflectance, 137 discrepancy, 88 displacement mapping. 153 dot product. 5 energy conservation. 138 expected value. 83, 85 f-number. 113. 115 filtering, 91, 108 focal length, 113 form factor, 90 frame of reference, 9 Fresnel reflectance, 44, 47, 139, 141 163
164 Index gamma, 107, 150 gamma correction, 4 gaze direction, 40 grid spatial subdivision structure, 71 grid traversal, 72, 74, 76 grid, initialization, 76 importance sampling, 87, 88, 112, 143 indirect light, 133, 145 instancing. 67 interpolation, bilinear, 62 hermite, 62 ray-box, 23. 24 ray-ellipsoid. 67 ray-grid. 71 ray-implicit, 19 ray-list, 28 ray-object. 18 ray-parametric, 20 ray-plane. 19 ray-sphere, 21 ray-triangle. 24. 26 interval. 7 Jucobiun matrix. 104 jaggies. 105 jittering. 87. 95 Law of Large Numbers, 86 line. implicit, 17 parametric, 7. 17 vector form, 17 luminaires. 119, 129 luminance. 148, 152 scotopic, 148, 152 matrix, composite, 13 inverse, 13 rotation, 12 scale, 11 transformation, 9 translation, 11 mesh, 63 monitor, gamma, 4, 107 phosphors, 150 trinitron, 151 tristimulous values, 150 white point, 150 Monte Carlo integration, 81-83.87, 88 motion-blur, 117 normal vector, transformation. 10 orthonormal bases. 7-9. 12 construction. 8 participating media. 153 path tracing. 129. 130. 145 piane. implicit, 19 parametric. 24 points. 5 transformation. 9. 11 Poisson disk sampling. 93. 95 probability, 83 probability density function. 83 quadratic equation. 22 quasi-Monte Carlo integration. 88. 92 radiosity. 153 random points, cosine density, 131 disk, 90, 97, 100 Phong density, 98 tnangle, 98 random sampling, 93 random variable, 83 Index 165 ray, vii, 7, 18 shadow, 32, 133 viewing, 31, 40 ray tracing, vii reciprocity for BRDFs, 138 reflection, shadow, 32, 133 genera3, 137 Lambertian, 31. 32, 91, 119, 129, 138, 141 metal, 43 Phong, 139 physically plausible, 138 poiished. 47, 141 specular, 43. 44. 135. 140 refraction. 44 refractive index. 45 regular sampling. 93 rendering equation. 145 right-hand rule. 6 sampling. 110 scattering probability density function (SPDF). 137 Schlick's approximation. 44. 139 shadows. 32 soft. 119 Snell's Law. 45 solid noise. 54 spatial subdivision. 71 grid. 71 sphere. implicit form. 21 normal vector. 22 parametric. 60 vector form, 21 standard deviation, 86 stratified sampling, 87, 88 surface, implicit, 18 parametric, 20 texture coordinates, 59, 61, 65 texture mapping, 4, 59-62 texture, marble, 56 procedural, 53 solid, 53 tiled, 59 thin-lens law, 113 tone mapping, 151. 153 transparency. 44, 46, 62 triangular irregular networks (TINs), 63 triangular meshes. 63 tristimulous values. 148 turbulence function. 56 variance. 83. 86-88 vector noise. 58 vector operations. 5 vector turbulence, 58 vectors. 4. 7 length. 5 normal. 20. 21. 34, 69 reflection. 44 refraction. 45 transformation. 10. II unit. 5 view-plane normal, 40 view-up vector, 40 viewing. 37, 39, 41, 42 weighted average, 91