Cycles: Code cleanup, spaces around keywords
[blender-staging.git] / intern / cycles / render / blackbody.cpp
1 /*
2  * Adapted from Open Shading Language with this license:
3  *
4  * Copyright (c) 2009-2010 Sony Pictures Imageworks Inc., et al.
5  * All Rights Reserved.
6  *
7  * Modifications Copyright 2013, Blender Foundation.
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions are
11  * met:
12  * * Redistributions of source code must retain the above copyright
13  *   notice, this list of conditions and the following disclaimer.
14  * * Redistributions in binary form must reproduce the above copyright
15  *   notice, this list of conditions and the following disclaimer in the
16  *   documentation and/or other materials provided with the distribution.
17  * * Neither the name of Sony Pictures Imageworks nor the names of its
18  *   contributors may be used to endorse or promote products derived from
19  *   this software without specific prior written permission.
20  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
23  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
24  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
25  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
26  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
27  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
28  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
29  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
30  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31  */
32
33 #include "blackbody.h"
34 #include "util_color.h"
35 #include "util_math.h"
36
37 #include "kernel_types.h"
38
39 CCL_NAMESPACE_BEGIN
40
41 vector<float> blackbody_table_build()
42 {
43         /* quoted from OSLs opcolor.cpp
44         In order to speed up the blackbody computation, we have a table
45         storing the precomputed BB values for a range of temperatures.  Less
46         than BB_DRAPER always returns 0.  Greater than BB_MAX_TABLE_RANGE
47         does the full computation, we think it'll be rare to inquire higher
48         temperatures.
49
50         Since the bb function is so nonlinear, we actually space the table
51         entries nonlinearly, with the relationship between the table index i
52         and the temperature T as follows:
53         i = ((T-Draper)/spacing)^(1/xpower)
54         T = pow(i, xpower) * spacing + Draper
55         And furthermore, we store in the table the true value raised ^(1/5).
56         I tuned this a bit, and with the current values we can have all
57         blackbody results accurate to within 0.1% with a table size of 317
58         (about 5 KB of data).
59         */
60
61         const float cie_colour_match[81][3] = {
62                 {0.0014f,0.0000f,0.0065f}, {0.0022f,0.0001f,0.0105f}, {0.0042f,0.0001f,0.0201f},
63                 {0.0076f,0.0002f,0.0362f}, {0.0143f,0.0004f,0.0679f}, {0.0232f,0.0006f,0.1102f},
64                 {0.0435f,0.0012f,0.2074f}, {0.0776f,0.0022f,0.3713f}, {0.1344f,0.0040f,0.6456f},
65                 {0.2148f,0.0073f,1.0391f}, {0.2839f,0.0116f,1.3856f}, {0.3285f,0.0168f,1.6230f},
66                 {0.3483f,0.0230f,1.7471f}, {0.3481f,0.0298f,1.7826f}, {0.3362f,0.0380f,1.7721f},
67                 {0.3187f,0.0480f,1.7441f}, {0.2908f,0.0600f,1.6692f}, {0.2511f,0.0739f,1.5281f},
68                 {0.1954f,0.0910f,1.2876f}, {0.1421f,0.1126f,1.0419f}, {0.0956f,0.1390f,0.8130f},
69                 {0.0580f,0.1693f,0.6162f}, {0.0320f,0.2080f,0.4652f}, {0.0147f,0.2586f,0.3533f},
70                 {0.0049f,0.3230f,0.2720f}, {0.0024f,0.4073f,0.2123f}, {0.0093f,0.5030f,0.1582f},
71                 {0.0291f,0.6082f,0.1117f}, {0.0633f,0.7100f,0.0782f}, {0.1096f,0.7932f,0.0573f},
72                 {0.1655f,0.8620f,0.0422f}, {0.2257f,0.9149f,0.0298f}, {0.2904f,0.9540f,0.0203f},
73                 {0.3597f,0.9803f,0.0134f}, {0.4334f,0.9950f,0.0087f}, {0.5121f,1.0000f,0.0057f},
74                 {0.5945f,0.9950f,0.0039f}, {0.6784f,0.9786f,0.0027f}, {0.7621f,0.9520f,0.0021f},
75                 {0.8425f,0.9154f,0.0018f}, {0.9163f,0.8700f,0.0017f}, {0.9786f,0.8163f,0.0014f},
76                 {1.0263f,0.7570f,0.0011f}, {1.0567f,0.6949f,0.0010f}, {1.0622f,0.6310f,0.0008f},
77                 {1.0456f,0.5668f,0.0006f}, {1.0026f,0.5030f,0.0003f}, {0.9384f,0.4412f,0.0002f},
78                 {0.8544f,0.3810f,0.0002f}, {0.7514f,0.3210f,0.0001f}, {0.6424f,0.2650f,0.0000f},
79                 {0.5419f,0.2170f,0.0000f}, {0.4479f,0.1750f,0.0000f}, {0.3608f,0.1382f,0.0000f},
80                 {0.2835f,0.1070f,0.0000f}, {0.2187f,0.0816f,0.0000f}, {0.1649f,0.0610f,0.0000f},
81                 {0.1212f,0.0446f,0.0000f}, {0.0874f,0.0320f,0.0000f}, {0.0636f,0.0232f,0.0000f},
82                 {0.0468f,0.0170f,0.0000f}, {0.0329f,0.0119f,0.0000f}, {0.0227f,0.0082f,0.0000f},
83                 {0.0158f,0.0057f,0.0000f}, {0.0114f,0.0041f,0.0000f}, {0.0081f,0.0029f,0.0000f},
84                 {0.0058f,0.0021f,0.0000f}, {0.0041f,0.0015f,0.0000f}, {0.0029f,0.0010f,0.0000f},
85                 {0.0020f,0.0007f,0.0000f}, {0.0014f,0.0005f,0.0000f}, {0.0010f,0.0004f,0.0000f},
86                 {0.0007f,0.0002f,0.0000f}, {0.0005f,0.0002f,0.0000f}, {0.0003f,0.0001f,0.0000f},
87                 {0.0002f,0.0001f,0.0000f}, {0.0002f,0.0001f,0.0000f}, {0.0001f,0.0000f,0.0000f},
88                 {0.0001f,0.0000f,0.0000f}, {0.0001f,0.0000f,0.0000f}, {0.0000f,0.0000f,0.0000f}
89         };
90
91         const double c1 = 3.74183e-16; // 2*pi*h*c^2, W*m^2
92         const double c2 = 1.4388e-2;   // h*c/k, m*K
93                                                                    // h is Planck's const, k is Boltzmann's
94         const float dlambda = 5.0f * 1e-9f;  // in meters
95
96         /* Blackbody table from 800 to 12k Kelvin (319 entries (317+2 offset) * 3) */
97         vector<float> blackbody_table(956);
98
99         float X, Y, Z;
100
101         /* ToDo: bring this back to what OSL does with the lastTemperature limit ? */
102         for(int i = 0;  i <= 317;  ++i) {
103                 double Temperature = pow((double)i, (double)BB_TABLE_XPOWER) * (double)BB_TABLE_SPACING + (double)BB_DRAPER;
104                 X = 0;
105                 Y = 0;
106                 Z = 0;
107
108                 /* from OSL "spectrum_to_XYZ" */
109                 for(int n = 0; n < 81; ++n) {
110                         float lambda = 380.0f + 5.0f * n;
111                         double wlm = lambda * 1e-9f;   // Wavelength in meters
112                         // N.B. spec_intens returns result in W/m^2 but it's a differential,
113                         // needs to be scaled by dlambda!
114                         float spec_intens = float((c1 * pow(wlm, -5.0)) / (exp(c2 / (wlm * Temperature)) -1.0));
115                         float Me = spec_intens * dlambda;
116
117                         X += Me * cie_colour_match[n][0];
118                         Y += Me * cie_colour_match[n][1];
119                         Z += Me * cie_colour_match[n][2];
120                 }
121                 
122                 /* Convert from xyz color space */
123                 float3 col = xyz_to_rgb(X, Y, Z);
124
125                 /* Clamp to zero if values are smaller */
126                 col = max(col, make_float3(0.0f, 0.0f, 0.0f));
127
128                 col.x = powf(col.x, 1.0f / BB_TABLE_YPOWER);
129                 col.y = powf(col.y, 1.0f / BB_TABLE_YPOWER);
130                 col.z = powf(col.z, 1.0f / BB_TABLE_YPOWER);
131
132                 /* Store in table in RRRGGGBBB format */
133                 blackbody_table[i] = col.x;
134                 blackbody_table[i+319*1] = col.y;
135                 blackbody_table[i+319*2] = col.z;       
136         }
137
138         return blackbody_table;
139 }
140 CCL_NAMESPACE_END