Phong illumination produces black - graphics

I guess I am somehow stuck with a basic question where I just don't get the correct answer.
The Phong illumination model contains an ambient, diffuse and specular part.
Each part contains a multiplication of the color of light (ambient or source) with a coefficient (ambient, diffuse, specular)): I * coe
The light and the coefficents consist of the r,g,b color channels:
I_r * coe_r
I_g * coe_g
I_b * coe_b
Assuming a light would be green (0,1,0) and the coefficient (doesn't matter which) is blue (0,0,1) the result would be black (0,0,0).
How does this make any sense?

A blue object only reflects blue light. If you light it using white light, which contains all colors, it reflects only the blue light, so that is why it appears blue to the viewer. If you shine a light that has no blue component on a blue object, no light will be reflected.
In real life, lights and pigments are never "pure", and a object will not appear completely black in these situations. However, in the world of computer graphics, this can happen easily.

Related

Flat shading coordinate system

can someone please direct me to a link where I would be able to then solve such a question, seeing as this is an exam question I would like to attempt it first before asking for a solution.
Consider a triangular face of three vertices A(0,2,-1), B(1,0,1) and the origin O, and
the normal vectors at the vertices are nA=(0,1,0), nB=(1,0,0) and nO=(0,0,1),
respectively. The incident light is white and directional in direction of L=(1,2,2) and the
intensity is 1, the background ambient light intensity is 0.1, and the diffuse reflection
coefficients for (red, green, blue) are (0.6,0.7,0.8). No specular light contribution
needs to be considered..
a) Find the (red, green, blue) intensity values in the face using flat shading at the centre of the face.
Thanks
BeyelerStudios comment tells everything you need to know. But I feel you are complete rookie in the field so here some more info:
definitions
Lets have triangle face defined by its 3 vertexes (v0,v1,v2) and normals (n0,n1,n2). Let the light source be directional with to light vector light. The light has ambient and directional parts with (r,g,b) colors: col_dir=(1.0,1.0,1.0) and col_amb=(0.1,0.1,0.1). The reflectance of the surface is col_face=(0.6,0.7,0.8). You want to get the pixel color for center point of triangle.
compute normal at the the point of interest
To map arbitrary point of interest you can use barycentric coordinates (as you are computing this on paper it is better in such case).
But in your case the point is center so the normal is just average of the 3 normals:
n=(n0+n1+n2)/3.0
If I remember correctly In case of arbitrary point given in barycentric coordinates (u,v,w=1-u-v) it would be like this:
n=u*n0 + v*n1 + w*n2
compute cos(angle) between normal and to light vector
That is easy use dot product for this (while both vectors are unit in size ... normalized):
cos(angle) = (n.x*light.x)+(n.y*light.y)+(n.z*light.z)
If your vectors are not normalized you need to divide the result by their size.
cos(angle) = ( (n.x*light.x)+(n.y*light.y)+(n.z*light.z) ) / (|n|*|light|)
compute the color
That is also easy:
color = col_face * ( col_dir*cos(ang) + col_amb )
Do not forget to handle negative cos(ang). The behavior depends on your implementation. sometimes is used max(0.0,cos(ang)) other times |cos(ang)|.
[Notes]
If you are interested how rendering engines handle the interpolations see
how to rasterize rotated rectangle (in 2d by setpixel)

Proper way of calculating lighting

I am implementing lighting in a 3D engine, and have discovered a flaw in the way I calculate lighting. In the combine shader, I get the diffuse color and the lighting calculations.
return diffuseColor * (diffuseLight + ambient);
As far as I can tell, this is the standard way of doing things.
But, for example, what if the color is 0,1,0, and the light is 1,0,0. (Ignore ambient in this example)
The result would be 0,0,0. But in real life, if I get a pure green bit of paper, and shine a tinted red light onto it, it should turn out yellow. Or at least not black.
How do other games solve this problem?
A green paper will absorb red light and appear black, not yellow.
Addition means you shine a white paper with red and green light. Then the paper appears yellow.
http://www.physics.wisc.edu/museum/Exhibits-2/Light_Optics/ColorObj/Color_index.html
It should be (for each RGB component)
return (diffuseColor * diffuseLight) + ambient;
The ambient component is constant and is added after all of the other lighting calculations have been done, and doesn't depend on the light direction or viewing direction.
As Julio says, a pure green paper will look black under pure red light.
When something looks green, it's because it absorbs all other colours from the spectrum and what's left (i.e. green) is reflected. If you shine a red light on it there's no green to get reflected.

Most "stable" color representation : RGB? HSV? CIELAB?

There are several color representations in computer science : the standard RGB, but also HSV, HSL, CIE XYZ, YCC, CIELAB, CIELUV, ... It seems to me that most of the times, these representation try to approximate human vision (colors perceptually identical should have similar representations)
But what I want to know is which representation is the most "stable" when it comes to pictures. I have an object, let's say a bottle of Coke, and I have thousands of pictures of this bottle, taken under very different circumstances (the main difference would be the how light or dark the picture is, but there's orientation, etc...)
My question is : what color representation will empirically give me the most stable representation of the colors of the bottle? The "red" color of the label should not vary too much. Well, I'll know it will vary, but I would like to know the most "stable" representation.
I've been taught that HSV is better than RGB for these kind of things, but I have no clue for the rest.
Edit (technical details) : I take a particular point of the bottle. I pick the corresponding pixels in a thousand pictures of this point. I now have a cloud of points, that depend on the representation. I want the representation that minimizes the "size" of this cloud, for example the one that minimizes the mean distance of the points of the cloud to its barycenter.
You might want to check out http://www.cs.harvard.edu/~sjg/papers/cspace.pdf, which proposes a new colorspace apparently designed to address this precise question.
I'm not aware of a colourspace that does what you want, but I do have some remarks:
RGB closely matches the way colours are displayed to us on monitors. It is one of the worst colourspaces available in terms of approximating human perception.
As for the other colourspaces: Some try to make sure colours that are perceptually close together are also close together in the colourspace. Others also try to ensure that perceptually similar differences in colour also produce similar differences in the colourspace, regardless of where in the colourspace you are.
The first means that if you think the difference in colour between blue A, and blue B is similar to the difference in colour between the blue A and blue C, then in the colourspace the distance between blue A and blue B will be similar to the distance between blue A and blue C, and they will all three be close together in the colourspace. I think this is called a perceptually smooth colourspace. CIE XYZ is an example of this.
The second means that if you think the difference in colour between blue A and blue B is similar to the difference in colour between red A and red B then in the colourspace the distance between blue A and blue B will be similar to the difference between red A and red B. This is called a perceptually uniform colourspace. CIE Lab is an example of this.
[edit 2011-07-29] As for your problem: Any of HSV, HSL, CIE XYZ, YCC, CIELAB, CIELUV, YUV separate out the illumination from the colour info in some way, so those are the better options. They provide some immunity from illumination changes, but won't help you when the colour temperature changes drastically or coloured light is used. XYZ and YUV are computationally less expensive to get to from RGB (which is what most cameras give you) but also less "good" than HSV, HSL, or CIELAB (the latter is often considered one of the best, but it is also one of the most difficult).
Depending on what you are searching for you could calibrate the color balance of the images. For example: suppose you are matching coca cola logos: You know that the letters in the logo are always white. So if they are not in your image you can use the colour they have to correct that, which gives you information about the other colours.
Our perception of the color of something is mostly determined by its hue; a colorspace such as HSV which gives a single value representing hue will work best.
The eye is a remarkable instrument though, and knowing the color of a single point is not enough. If the entire scene has a yellow or blue tint to it, the eye will compensate and your perception will be of a purer color - the orange Coke bottle will appear to be redder than it is. Likewise with darkness and brightness. If possible, you should try to compensate the image before taking the color sample.

Why rgb and not cmy? [closed]

Closed. This question is off-topic. It is not currently accepting answers.
Want to improve this question? Update the question so it's on-topic for Stack Overflow.
Closed 11 years ago.
Improve this question
Seeing as how the three primary colors are cyan, magenta and yellow (CMY), why do monitors and almost all the GUI components out there use red, green and blue (RGB)? (If I'm not mistaken, printers use the CMYK model.)
Is there a historical, hardware/software, or other reason for it?
There's a difference between additive colors (http://en.wikipedia.org/wiki/Additive_color) and subtractive colors (http://en.wikipedia.org/wiki/Subtractive_color).
With additive colors, the more you add, the brighter the colors become. This is because they are emitting light. This is why the day light is (more or less) white, since the Sun is emitting in almost all the visible wavelength spectrum.
On the other hand, with subtractive colors the more colors you mix, the darker the resulting color. This is because they are reflecting light. This is also why the black colors get hotter quickly, because it absorbs (almost) all light energy and reflects (almost) none.
Specifically to your question, it depends what medium you are working on. Traditionally, additive colors (RGB) are used because the canon for computer graphics was the computer monitor, and since it's emitting light, it makes sense to use the same structure for the graphic card (the colors are shown without conversions). However, if you are used to graphic arts and press, subtractive color model is used (CMYK). In programs such as Photoshop, you can choose to work in CMYK space although it doesn't matter what color model you use: the primary colors of one group are the secondary colors of the second one and viceversa.
P.D.: my father worked at graphic arts, this is why i know this... :-P
The difference lies in whether mixing colours results in LIGHTER or DARKER colours. When mixing light, the result is a lighter colour, so mixing red light and blue light becomes a lighter pink. When mixing paint (or ink), red and blue become a darker purple. Mixing paint results in DARKER colours, whereas mixing light results in LIGHTER colours.
Therefore for paint the primary colours are Red Yellow Blue (or Cyan Magenta Yellow) as you stated. Yet for light the primary colours are Red Green Blue. It is (virtually) impossible to mix Red Green Blue paint into Yellow paint, or mixing Red Yellow Blue light into Green light.
The basic colours are RGB not RYB. Yes most of the softwares use the traditional RGB which can be used to mix together to form any other color i.e. RGB are the fundamental colours (as defined in Physics & Chemistry texts).
The printer user CMYK (cyan, magenta, yellow, and black) coloring as said by #jcomeau_ictx.
You can view the following article to know about RGB vs CMYK: RGB Vs CMYK
A bit more information from the extract about them:
Red, Green, and Blue are "additive
colors". If we combine red, green and
blue light you will get white light.
This is the principal behind the T.V.
set in your living room and the
monitor you are staring at now.
Additive color, or RGB mode, is
optimized for display on computer
monitors and peripherals, most notably
scanning devices.
Cyan, Magenta and Yellow are
"subtractive colors". If we print
cyan, magenta and yellow inks on white
paper, they absorb the light shining
on the page. Since our eyes receive no
reflected light from the paper, we
perceive black... in a perfect world!
The printing world operates in
subtractive color, or CMYK mode.
the 3 additive colors are in fact red, green, and blue. printers use cmyk (cyan, magenta, yellow, and black).
and as http://en.wikipedia.org/wiki/Additive_color explains: if you use RYB as your primary colors, how do you make green? since yellow is made from equal amounts of red and green.
This is nothing to do with hardware nor software. Simply that RGB are the 3 primary colours which can be combined in various ways to produce every other colour. It is more about the human convention/perception of colours which carried over.
You may find this article interesting.

The right model for shading in Ray tracing

I am wondering about the most accurate way to calculate the shadow generated from several different light sources and ambient light.
Ambient light is light that exists in the entire 'world' with the same intensity and no particular direction, and diffused lighting is the lighting that occurs due a direct lighting from a point light source.
Given that Ka is the coefficient for the surface ambient reflectivity, Ia is the intensity of the ambient light, Kd is the surface diffuse reflectivity, Ip1 is intensity of the the first (accordingly) point light source, N is the surface normal, and L1 is the light (of the first source accordingly) direction.
According to my reference material the intensity of the color at the spot should be:
I=Ka.Ia+Kd(Ip1(N.L1)+Ip2(N.L2))
where '.' is the dot product.
But according to my understanding the real light intensity should do some sort of average between the light sources and not just add them up, so that if there are only two light sources the equation should look like:
I=Ka.Ia+Kd(Ip1(N.L1)+Ip2(N.L2))/2
and if there are 3 light sources, but the third is blocked and doesn't light the surface directly then:
I=Ka.Ia+Kd(Ip1(N.L1)+Ip2(N.L2))/3
(so that if there is a place where all 3 lights contribute it would be lighten brighter.
Am I right at my assumption?
Well, no, light shouldn't be averaged. Think about it. If you have just one powerful light source, and you add another, very faint light, would the color of the object be diminished? For example say the powerful light has intensity 10, the color (presuming the direction is perpendicular to the normal, and no ambient light, for simplicity sake) would be 10. Then after you add the second faint light, with say intensity 0.1 the color would be (10 + 0.1) / 2 which is 5.05. So adding more light would make the object seem darker. That doesn't make sense.
In the real world, light adds. It should in your ray tracer, too.
Luminance is not a linear function of light intensity. In other words, two identical light sources aimed at one spot are not perceived as twice as "bright" as one light. (Brightness is an ambiguous term -- luminance is a better term that means radiance weighted by human vision).
What you can do as an approximation to correcting the image to be viewed on your monitor, knowing intensities of various pixels, is called gamma correction.

Resources