1 /*
2 Copyright (c) 2005-2021 Intel Corporation
3
4 Licensed under the Apache License, Version 2.0 (the "License");
5 you may not use this file except in compliance with the License.
6 You may obtain a copy of the License at
7
8 http://www.apache.org/licenses/LICENSE-2.0
9
10 Unless required by applicable law or agreed to in writing, software
11 distributed under the License is distributed on an "AS IS" BASIS,
12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 See the License for the specific language governing permissions and
14 limitations under the License.
15 */
16
17 /*
18 The original source for this example is
19 Copyright (c) 1994-2008 John E. Stone
20 All rights reserved.
21
22 Redistribution and use in source and binary forms, with or without
23 modification, are permitted provided that the following conditions
24 are met:
25 1. Redistributions of source code must retain the above copyright
26 notice, this list of conditions and the following disclaimer.
27 2. Redistributions in binary form must reproduce the above copyright
28 notice, this list of conditions and the following disclaimer in the
29 documentation and/or other materials provided with the distribution.
30 3. The name of the author may not be used to endorse or promote products
31 derived from this software without specific prior written permission.
32
33 THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
34 OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
35 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
36 ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
37 DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
38 DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
39 OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
40 HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
41 LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
42 OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
43 SUCH DAMAGE.
44 */
45
46 /*
47 * texture.cpp - This file contains functions for implementing textures.
48 */
49
50 #include "machine.hpp"
51 #include "types.hpp"
52 #include "macros.hpp"
53 #include "texture.hpp"
54 #include "coordsys.hpp"
55 #include "imap.hpp"
56 #include "vector.hpp"
57 #include "box.hpp"
58
59 /* plain vanilla texture solely based on object color */
standard_texture(vector * hit,texture * tex,ray * ry)60 color standard_texture(vector *hit, texture *tex, ray *ry) {
61 return tex->col;
62 }
63
64 /* cylindrical image map */
image_cyl_texture(vector * hit,texture * tex,ray * ry)65 color image_cyl_texture(vector *hit, texture *tex, ray *ry) {
66 vector rh;
67 flt u, v;
68
69 rh.x = hit->x - tex->ctr.x;
70 rh.z = hit->y - tex->ctr.y;
71 rh.y = hit->z - tex->ctr.z;
72
73 xyztocyl(rh, 1.0, &u, &v);
74
75 u = u * tex->scale.x;
76 u = u + tex->rot.x;
77 u = fmod(u, 1.0);
78 if (u < 0.0)
79 u += 1.0;
80
81 v = v * tex->scale.y;
82 v = v + tex->rot.y;
83 v = fmod(v, 1.0);
84 if (v < 0.0)
85 v += 1.0;
86
87 return ImageMap((rawimage *)tex->img, u, v);
88 }
89
90 /* spherical image map */
image_sphere_texture(vector * hit,texture * tex,ray * ry)91 color image_sphere_texture(vector *hit, texture *tex, ray *ry) {
92 vector rh;
93 flt u, v;
94
95 rh.x = hit->x - tex->ctr.x;
96 rh.y = hit->y - tex->ctr.y;
97 rh.z = hit->z - tex->ctr.z;
98
99 xyztospr(rh, &u, &v);
100
101 u = u * tex->scale.x;
102 u = u + tex->rot.x;
103 u = fmod(u, 1.0);
104 if (u < 0.0)
105 u += 1.0;
106
107 v = v * tex->scale.y;
108 v = v + tex->rot.y;
109 v = fmod(v, 1.0);
110 if (v < 0.0)
111 v += 1.0;
112
113 return ImageMap((rawimage *)tex->img, u, v);
114 }
115
116 /* planar image map */
image_plane_texture(vector * hit,texture * tex,ray * ry)117 color image_plane_texture(vector *hit, texture *tex, ray *ry) {
118 vector pnt;
119 flt u, v;
120
121 pnt.x = hit->x - tex->ctr.x;
122 pnt.y = hit->y - tex->ctr.y;
123 pnt.z = hit->z - tex->ctr.z;
124
125 VDOT(u, tex->uaxs, pnt);
126 /* VDOT(len, tex->uaxs, tex->uaxs);
127 u = u / sqrt(len); */
128
129 VDOT(v, tex->vaxs, pnt);
130 /* VDOT(len, tex->vaxs, tex->vaxs);
131 v = v / sqrt(len); */
132
133 u = u * tex->scale.x;
134 u = u + tex->rot.x;
135 u = fmod(u, 1.0);
136 if (u < 0.0)
137 u += 1.0;
138
139 v = v * tex->scale.y;
140 v = v + tex->rot.y;
141 v = fmod(v, 1.0);
142 if (v < 0.0)
143 v += 1.0;
144
145 return ImageMap((rawimage *)tex->img, u, v);
146 }
147
grit_texture(vector * hit,texture * tex,ray * ry)148 color grit_texture(vector *hit, texture *tex, ray *ry) {
149 int rnum;
150 flt fnum;
151 color col;
152
153 rnum = rand() % 4096;
154 fnum = (rnum / 4096.0 * 0.2) + 0.8;
155
156 col.r = tex->col.r * fnum;
157 col.g = tex->col.g * fnum;
158 col.b = tex->col.b * fnum;
159
160 return col;
161 }
162
checker_texture(vector * hit,texture * tex,ray * ry)163 color checker_texture(vector *hit, texture *tex, ray *ry) {
164 long x, y, z;
165 flt xh, yh, zh;
166 color col;
167
168 xh = hit->x - tex->ctr.x;
169 x = (long)((fabs(xh) * 3) + 0.5);
170 x = x % 2;
171 yh = hit->y - tex->ctr.y;
172 y = (long)((fabs(yh) * 3) + 0.5);
173 y = y % 2;
174 zh = hit->z - tex->ctr.z;
175 z = (long)((fabs(zh) * 3) + 0.5);
176 z = z % 2;
177
178 if (((x + y + z) % 2) == 1) {
179 col.r = 1.0;
180 col.g = 0.2;
181 col.b = 0.0;
182 }
183 else {
184 col.r = 0.0;
185 col.g = 0.2;
186 col.b = 1.0;
187 }
188
189 return col;
190 }
191
cyl_checker_texture(vector * hit,texture * tex,ray * ry)192 color cyl_checker_texture(vector *hit, texture *tex, ray *ry) {
193 long x, y;
194 vector rh;
195 flt u, v;
196 color col;
197
198 rh.x = hit->x - tex->ctr.x;
199 rh.y = hit->y - tex->ctr.y;
200 rh.z = hit->z - tex->ctr.z;
201
202 xyztocyl(rh, 1.0, &u, &v);
203
204 x = (long)(fabs(u) * 18.0);
205 x = x % 2;
206 y = (long)(fabs(v) * 10.0);
207 y = y % 2;
208
209 if (((x + y) % 2) == 1) {
210 col.r = 1.0;
211 col.g = 0.2;
212 col.b = 0.0;
213 }
214 else {
215 col.r = 0.0;
216 col.g = 0.2;
217 col.b = 1.0;
218 }
219
220 return col;
221 }
222
wood_texture(vector * hit,texture * tex,ray * ry)223 color wood_texture(vector *hit, texture *tex, ray *ry) {
224 flt radius, angle;
225 int grain;
226 color col;
227 flt x, y, z;
228
229 x = (hit->x - tex->ctr.x) * 1000;
230 y = (hit->y - tex->ctr.y) * 1000;
231 z = (hit->z - tex->ctr.z) * 1000;
232
233 radius = sqrt(x * x + z * z);
234 if (z == 0.0)
235 angle = 3.1415926 / 2.0;
236 else
237 angle = atan(x / z);
238
239 radius = radius + 3.0 * sin(20 * angle + y / 150.0);
240 grain = ((int)(radius + 0.5)) % 60;
241 if (grain < 40) {
242 col.r = 0.8;
243 col.g = 1.0;
244 col.b = 0.2;
245 }
246 else {
247 col.r = 0.0;
248 col.g = 0.0;
249 col.b = 0.0;
250 }
251
252 return col;
253 }
254
255 #define NMAX 28
256 short int NoiseMatrix[NMAX][NMAX][NMAX];
257
InitNoise(void)258 void InitNoise(void) {
259 byte_t x, y, z, i, j, k;
260
261 for (x = 0; x < NMAX; x++) {
262 for (y = 0; y < NMAX; y++) {
263 for (z = 0; z < NMAX; z++) {
264 NoiseMatrix[x][y][z] = rand() % 12000;
265
266 if (x == NMAX - 1)
267 i = 0;
268 else
269 i = x;
270
271 if (y == NMAX - 1)
272 j = 0;
273 else
274 j = y;
275
276 if (z == NMAX - 1)
277 k = 0;
278 else
279 k = z;
280
281 NoiseMatrix[x][y][z] = NoiseMatrix[i][j][k];
282 }
283 }
284 }
285 }
286
Noise(flt x,flt y,flt z)287 int Noise(flt x, flt y, flt z) {
288 byte_t ix, iy, iz;
289 flt ox, oy, oz;
290 int p000, p001, p010, p011;
291 int p100, p101, p110, p111;
292 int p00, p01, p10, p11;
293 int p0, p1;
294 int d00, d01, d10, d11;
295 int d0, d1, d;
296
297 x = fabs(x);
298 y = fabs(y);
299 z = fabs(z);
300
301 ix = ((int)x) % (NMAX - 1);
302 iy = ((int)y) % (NMAX - 1);
303 iz = ((int)z) % (NMAX - 1);
304
305 ox = (x - ((int)x));
306 oy = (y - ((int)y));
307 oz = (z - ((int)z));
308
309 p000 = NoiseMatrix[ix][iy][iz];
310 p001 = NoiseMatrix[ix][iy][iz + 1];
311 p010 = NoiseMatrix[ix][iy + 1][iz];
312 p011 = NoiseMatrix[ix][iy + 1][iz + 1];
313 p100 = NoiseMatrix[ix + 1][iy][iz];
314 p101 = NoiseMatrix[ix + 1][iy][iz + 1];
315 p110 = NoiseMatrix[ix + 1][iy + 1][iz];
316 p111 = NoiseMatrix[ix + 1][iy + 1][iz + 1];
317
318 d00 = p100 - p000;
319 d01 = p101 - p001;
320 d10 = p110 - p010;
321 d11 = p111 - p011;
322
323 p00 = (int)((int)d00 * ox) + p000;
324 p01 = (int)((int)d01 * ox) + p001;
325 p10 = (int)((int)d10 * ox) + p010;
326 p11 = (int)((int)d11 * ox) + p011;
327 d0 = p10 - p00;
328 d1 = p11 - p01;
329 p0 = (int)((int)d0 * oy) + p00;
330 p1 = (int)((int)d1 * oy) + p01;
331 d = p1 - p0;
332
333 return (int)((int)d * oz) + p0;
334 }
335
marble_texture(vector * hit,texture * tex,ray * ry)336 color marble_texture(vector *hit, texture *tex, ray *ry) {
337 flt i, d;
338 flt x, y, z;
339 color col;
340
341 x = hit->x;
342 y = hit->y;
343 z = hit->z;
344
345 x = x * 1.0;
346
347 d = x + 0.0006 * Noise(x, (y * 1.0), (z * 1.0));
348 d = d * (((int)d) % 25);
349 i = 0.0 + 0.10 * fabs(d - 10.0 - 20.0 * ((int)d * 0.05));
350 if (i > 1.0)
351 i = 1.0;
352 if (i < 0.0)
353 i = 0.0;
354
355 /*
356 col.r=i * tex->col.r;
357 col.g=i * tex->col.g;
358 col.b=i * tex->col.b;
359 */
360
361 col.r = (1.0 + sin(i * 6.28)) / 2.0;
362 col.g = (1.0 + sin(i * 16.28)) / 2.0;
363 col.b = (1.0 + cos(i * 30.28)) / 2.0;
364
365 return col;
366 }
367
gnoise_texture(vector * hit,texture * tex,ray * ry)368 color gnoise_texture(vector *hit, texture *tex, ray *ry) {
369 color col;
370 flt f;
371
372 f = Noise((hit->x - tex->ctr.x), (hit->y - tex->ctr.y), (hit->z - tex->ctr.z));
373
374 if (f < 0.01)
375 f = 0.01;
376 if (f > 1.0)
377 f = 1.0;
378
379 col.r = tex->col.r * f;
380 col.g = tex->col.g * f;
381 col.b = tex->col.b * f;
382
383 return col;
384 }
385
InitTextures(void)386 void InitTextures(void) {
387 InitNoise();
388 ResetImages();
389 }
390