Details | Last modification | View Log | RSS feed
| Rev | Author | Line No. | Line |
|---|---|---|---|
| 1 | pmbaty | 1 | /* |
| 2 | * Portions of this file are copyright Rebirth contributors and licensed as |
||
| 3 | * described in COPYING.txt. |
||
| 4 | * Portions of this file are copyright Parallax Software and licensed |
||
| 5 | * according to the Parallax license below. |
||
| 6 | * See COPYING.txt for license details. |
||
| 7 | |||
| 8 | THE COMPUTER CODE CONTAINED HEREIN IS THE SOLE PROPERTY OF PARALLAX |
||
| 9 | SOFTWARE CORPORATION ("PARALLAX"). PARALLAX, IN DISTRIBUTING THE CODE TO |
||
| 10 | END-USERS, AND SUBJECT TO ALL OF THE TERMS AND CONDITIONS HEREIN, GRANTS A |
||
| 11 | ROYALTY-FREE, PERPETUAL LICENSE TO SUCH END-USERS FOR USE BY SUCH END-USERS |
||
| 12 | IN USING, DISPLAYING, AND CREATING DERIVATIVE WORKS THEREOF, SO LONG AS |
||
| 13 | SUCH USE, DISPLAY OR CREATION IS FOR NON-COMMERCIAL, ROYALTY OR REVENUE |
||
| 14 | FREE PURPOSES. IN NO EVENT SHALL THE END-USER USE THE COMPUTER CODE |
||
| 15 | CONTAINED HEREIN FOR REVENUE-BEARING PURPOSES. THE END-USER UNDERSTANDS |
||
| 16 | AND AGREES TO THE TERMS HEREIN AND ACCEPTS THE SAME BY USE OF THIS FILE. |
||
| 17 | COPYRIGHT 1993-1998 PARALLAX SOFTWARE CORPORATION. ALL RIGHTS RESERVED. |
||
| 18 | */ |
||
| 19 | |||
| 20 | /* |
||
| 21 | * |
||
| 22 | * Routines to draw the texture mapped scanlines. |
||
| 23 | * |
||
| 24 | */ |
||
| 25 | |||
| 26 | #include <math.h> |
||
| 27 | #include <limits.h> |
||
| 28 | #include <stdio.h> |
||
| 29 | #include <stdlib.h> |
||
| 30 | #include <stdint.h> |
||
| 31 | #include <string.h> |
||
| 32 | #include "maths.h" |
||
| 33 | #include "gr.h" |
||
| 34 | #include "grdef.h" |
||
| 35 | #include "texmap.h" |
||
| 36 | #include "texmapl.h" |
||
| 37 | #include "scanline.h" |
||
| 38 | #include "strutil.h" |
||
| 39 | #include "dxxerror.h" |
||
| 40 | |||
| 41 | namespace dcx { |
||
| 42 | |||
| 43 | tmap_scanline_function_table tmap_scanline_functions; |
||
| 44 | |||
| 45 | void c_tmap_scanline_flat() |
||
| 46 | { |
||
| 47 | uint8_t *dest; |
||
| 48 | int x, index = fx_xleft + (bytes_per_row * fx_y ); |
||
| 49 | |||
| 50 | dest = (write_buffer + fx_xleft + (bytes_per_row * fx_y )); |
||
| 51 | |||
| 52 | for (x= fx_xright-fx_xleft+1 ; x > 0; --x ) { |
||
| 53 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 54 | *dest++ = tmap_flat_color; |
||
| 55 | } |
||
| 56 | // memset(dest,tmap_flat_color,fx_xright-fx_xleft+1); |
||
| 57 | } |
||
| 58 | |||
| 59 | void c_tmap_scanline_shaded(const uint_fast32_t fade) |
||
| 60 | { |
||
| 61 | uint8_t tmp; |
||
| 62 | int x, index = fx_xleft + (bytes_per_row * fx_y ); |
||
| 63 | |||
| 64 | auto dest = &write_buffer[fx_xleft + (bytes_per_row * fx_y)]; |
||
| 65 | for (x= fx_xright-fx_xleft+1 ; x > 0; --x ) { |
||
| 66 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 67 | tmp = *dest; |
||
| 68 | *dest++ = gr_fade_table[fade][tmp]; |
||
| 69 | } |
||
| 70 | } |
||
| 71 | |||
| 72 | void c_tmap_scanline_lin_nolight() |
||
| 73 | { |
||
| 74 | uint c; |
||
| 75 | int x, index = fx_xleft + (bytes_per_row * fx_y ); |
||
| 76 | fix u,v,dudx, dvdx; |
||
| 77 | |||
| 78 | u = fx_u; |
||
| 79 | v = fx_v*64; |
||
| 80 | dudx = fx_du_dx; |
||
| 81 | dvdx = fx_dv_dx*64; |
||
| 82 | |||
| 83 | auto dest = &write_buffer[fx_xleft + (bytes_per_row * fx_y)]; |
||
| 84 | |||
| 85 | if (!Transparency_on) { |
||
| 86 | for (x= fx_xright-fx_xleft+1 ; x > 0; --x ) { |
||
| 87 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 88 | *dest++ = static_cast<uint32_t>(pixptr[ (f2i(v)&(64*63)) + (f2i(u)&63) ]); |
||
| 89 | u += dudx; |
||
| 90 | v += dvdx; |
||
| 91 | } |
||
| 92 | } else { |
||
| 93 | for (x= fx_xright-fx_xleft+1 ; x > 0; --x ) { |
||
| 94 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 95 | c = static_cast<uint32_t>(pixptr[ (f2i(v)&(64*63)) + (f2i(u)&63) ]); |
||
| 96 | if ( c!=255) |
||
| 97 | *dest = c; |
||
| 98 | dest++; |
||
| 99 | u += dudx; |
||
| 100 | v += dvdx; |
||
| 101 | } |
||
| 102 | } |
||
| 103 | } |
||
| 104 | |||
| 105 | void c_tmap_scanline_lin() |
||
| 106 | { |
||
| 107 | uint c; |
||
| 108 | int x, j, index = fx_xleft + (bytes_per_row * fx_y); |
||
| 109 | fix u,v,l,dudx, dvdx, dldx; |
||
| 110 | |||
| 111 | u = fx_u; |
||
| 112 | v = fx_v*64; |
||
| 113 | dudx = fx_du_dx; |
||
| 114 | dvdx = fx_dv_dx*64; |
||
| 115 | |||
| 116 | l = fx_l>>8; |
||
| 117 | dldx = fx_dl_dx/256; |
||
| 118 | auto dest = &write_buffer[fx_xleft + (bytes_per_row * fx_y)]; |
||
| 119 | |||
| 120 | if (!Transparency_on) { |
||
| 121 | const auto pixPtrLocalCopy = pixptr; |
||
| 122 | auto &fadeTableLocalCopy = gr_fade_table; |
||
| 123 | |||
| 124 | x = fx_xright-fx_xleft+1; |
||
| 125 | |||
| 126 | if ((j = reinterpret_cast<uintptr_t>(dest) & 3) != 0) |
||
| 127 | { |
||
| 128 | j = 4 - j; |
||
| 129 | |||
| 130 | if (j > x) |
||
| 131 | j = x; |
||
| 132 | |||
| 133 | while (j > 0) |
||
| 134 | { |
||
| 135 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 136 | //edited 05/18/99 Matt Mueller - changed from 0xff00 to 0x7f00 to fix glitches |
||
| 137 | *dest++ = fadeTableLocalCopy[(l>>8)&0x7f][pixPtrLocalCopy[ (f2i(v)&(64*63)) + (f2i(u)&63) ] ]; |
||
| 138 | //end edit -MM |
||
| 139 | l += dldx; |
||
| 140 | u += dudx; |
||
| 141 | v += dvdx; |
||
| 142 | x--; |
||
| 143 | j--; |
||
| 144 | } |
||
| 145 | } |
||
| 146 | |||
| 147 | j &= ~3; |
||
| 148 | while (j > 0) |
||
| 149 | { |
||
| 150 | uint32_t destlong; |
||
| 151 | //edited 05/18/99 Matt Mueller - changed from 0xff00 to 0x7f00 to fix glitches |
||
| 152 | destlong = fadeTableLocalCopy[(l>>8)&0x7f][pixPtrLocalCopy[ (f2i(v)&(64*63)) + (f2i(u)&63) ] ] << 24; |
||
| 153 | //end edit -MM |
||
| 154 | l += dldx; |
||
| 155 | u += dudx; |
||
| 156 | v += dvdx; |
||
| 157 | //edited 05/18/99 Matt Mueller - changed from 0xff00 to 0x7f00 to fix glitches |
||
| 158 | destlong |= fadeTableLocalCopy[(l>>8)&0x7f][pixPtrLocalCopy[ (f2i(v)&(64*63)) + (f2i(u)&63) ] ] << 16; |
||
| 159 | //end edit -MM |
||
| 160 | l += dldx; |
||
| 161 | u += dudx; |
||
| 162 | v += dvdx; |
||
| 163 | //edited 05/18/99 Matt Mueller - changed from 0xff00 to 0x7f00 to fix glitches |
||
| 164 | destlong |= fadeTableLocalCopy[(l>>8)&0x7f][pixPtrLocalCopy[ (f2i(v)&(64*63)) + (f2i(u)&63) ] ] << 8; |
||
| 165 | //end edit -MM |
||
| 166 | l += dldx; |
||
| 167 | u += dudx; |
||
| 168 | v += dvdx; |
||
| 169 | //edited 05/18/99 Matt Mueller - changed from 0xff00 to 0x7f00 to fix glitches |
||
| 170 | destlong |= fadeTableLocalCopy[(l>>8)&0x7f][pixPtrLocalCopy[ (f2i(v)&(64*63)) + (f2i(u)&63) ] ]; |
||
| 171 | //end edit -MM |
||
| 172 | l += dldx; |
||
| 173 | u += dudx; |
||
| 174 | v += dvdx; |
||
| 175 | *reinterpret_cast<uint32_t *>(dest) = destlong; |
||
| 176 | dest += 4; |
||
| 177 | x -= 4; |
||
| 178 | j -= 4; |
||
| 179 | index += 4; |
||
| 180 | if (index+4 >= SWIDTH*SHEIGHT) return; |
||
| 181 | } |
||
| 182 | |||
| 183 | while (x-- > 0) |
||
| 184 | { |
||
| 185 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 186 | //edited 05/18/99 Matt Mueller - changed from 0xff00 to 0x7f00 to fix glitches |
||
| 187 | *dest++ = fadeTableLocalCopy[(l>>8)&0x7f][pixPtrLocalCopy[ (f2i(v)&(64*63)) + (f2i(u)&63) ] ]; |
||
| 188 | //end edit -MM |
||
| 189 | l += dldx; |
||
| 190 | u += dudx; |
||
| 191 | v += dvdx; |
||
| 192 | } |
||
| 193 | |||
| 194 | } else { |
||
| 195 | for (x= fx_xright-fx_xleft+1 ; x > 0; --x ) { |
||
| 196 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 197 | c = static_cast<uint32_t>(pixptr[ (f2i(v)&(64*63)) + (f2i(u)&63) ]); |
||
| 198 | if ( c!=TRANSPARENCY_COLOR) |
||
| 199 | //edited 05/18/99 Matt Mueller - changed from 0xff00 to 0x7f00 to fix glitches |
||
| 200 | *dest = gr_fade_table[(l >> 8)&0x7f][c]; |
||
| 201 | //end edit -MM |
||
| 202 | dest++; |
||
| 203 | l += dldx; |
||
| 204 | u += dudx; |
||
| 205 | v += dvdx; |
||
| 206 | } |
||
| 207 | } |
||
| 208 | } |
||
| 209 | |||
| 210 | // This texture mapper uses floating point extensively and writes 8 pixels at once, so it likely works |
||
| 211 | // best on 64 bit RISC processors. |
||
| 212 | // WARNING: it is not endian clean. For big endian, reverse the shift counts in the unrolled loops. I |
||
| 213 | // have no means to test that, so I didn't try it. Please tell me if you get this to work on a big |
||
| 214 | // endian machine. |
||
| 215 | // If you're using an Alpha, use the Compaq compiler for this file for quite some fps more. |
||
| 216 | // Unfortunately, it won't compile the whole source, so simply compile everything, change the |
||
| 217 | // compiler to ccc, remove scanline.o and compile again. |
||
| 218 | // Please send comments/suggestions to falk.hueffner@student.uni-tuebingen.de. |
||
| 219 | static void c_fp_tmap_scanline_per() |
||
| 220 | { |
||
| 221 | uint c; |
||
| 222 | int x, j, index = fx_xleft + (bytes_per_row * fx_y); |
||
| 223 | double u, v, z, l, dudx, dvdx, dzdx, dldx, rec_z; |
||
| 224 | |||
| 225 | u = f2db(fx_u); |
||
| 226 | v = f2db(fx_v) * 64.0; |
||
| 227 | z = f2db(fx_z); |
||
| 228 | l = f2db(fx_l); |
||
| 229 | dudx = f2db(fx_du_dx); |
||
| 230 | dvdx = f2db(fx_dv_dx) * 64.0; |
||
| 231 | dzdx = f2db(fx_dz_dx); |
||
| 232 | dldx = f2db(fx_dl_dx); |
||
| 233 | |||
| 234 | rec_z = 1.0 / z; // gcc 2.95.2 is won't do this optimization itself |
||
| 235 | |||
| 236 | auto dest = &write_buffer[fx_xleft + (bytes_per_row * fx_y)]; |
||
| 237 | x = fx_xright - fx_xleft + 1; |
||
| 238 | |||
| 239 | if (!Transparency_on) { |
||
| 240 | if (x >= 8) { |
||
| 241 | if ((j = reinterpret_cast<uintptr_t>(dest) & 7) != 0) { |
||
| 242 | j = 8 - j; |
||
| 243 | |||
| 244 | while (j > 0) { |
||
| 245 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 246 | *dest++ = |
||
| 247 | gr_fade_table[static_cast<int>(fabs(l))][ |
||
| 248 | pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + |
||
| 249 | ((static_cast<int>(u * rec_z)) & 63)]]; |
||
| 250 | l += dldx; |
||
| 251 | u += dudx; |
||
| 252 | v += dvdx; |
||
| 253 | z += dzdx; |
||
| 254 | rec_z = 1.0 / z; |
||
| 255 | x--; |
||
| 256 | j--; |
||
| 257 | } |
||
| 258 | } |
||
| 259 | |||
| 260 | j = x; |
||
| 261 | while (j >= 8) { |
||
| 262 | uint64_t destlong = |
||
| 263 | gr_fade_table[static_cast<int>(fabs(l))][ |
||
| 264 | pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + |
||
| 265 | ((static_cast<int>(u * rec_z)) & 63)]]; |
||
| 266 | l += dldx; |
||
| 267 | u += dudx; |
||
| 268 | v += dvdx; |
||
| 269 | z += dzdx; |
||
| 270 | rec_z = 1.0 / z; |
||
| 271 | destlong |= |
||
| 272 | static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][ |
||
| 273 | pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + |
||
| 274 | ((static_cast<int>(u * rec_z)) & 63)]]) << 8; |
||
| 275 | l += dldx; |
||
| 276 | u += dudx; |
||
| 277 | v += dvdx; |
||
| 278 | z += dzdx; |
||
| 279 | rec_z = 1.0 / z; |
||
| 280 | destlong |= |
||
| 281 | static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][ |
||
| 282 | pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + |
||
| 283 | ((static_cast<int>(u * rec_z)) & 63)]]) << 16; |
||
| 284 | l += dldx; |
||
| 285 | u += dudx; |
||
| 286 | v += dvdx; |
||
| 287 | z += dzdx; |
||
| 288 | rec_z = 1.0 / z; |
||
| 289 | destlong |= |
||
| 290 | static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][ |
||
| 291 | pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + |
||
| 292 | ((static_cast<int>(u * rec_z)) & 63)]]) << 24; |
||
| 293 | l += dldx; |
||
| 294 | u += dudx; |
||
| 295 | v += dvdx; |
||
| 296 | z += dzdx; |
||
| 297 | rec_z = 1.0 / z; |
||
| 298 | destlong |= |
||
| 299 | static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][ |
||
| 300 | pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + |
||
| 301 | ((static_cast<int>(u * rec_z)) & 63)]]) << 32; |
||
| 302 | l += dldx; |
||
| 303 | u += dudx; |
||
| 304 | v += dvdx; |
||
| 305 | z += dzdx; |
||
| 306 | rec_z = 1.0 / z; |
||
| 307 | destlong |= |
||
| 308 | static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][ |
||
| 309 | pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + |
||
| 310 | ((static_cast<int>(u * rec_z)) & 63)]]) << 40; |
||
| 311 | l += dldx; |
||
| 312 | u += dudx; |
||
| 313 | v += dvdx; |
||
| 314 | z += dzdx; |
||
| 315 | rec_z = 1.0 / z; |
||
| 316 | destlong |= |
||
| 317 | static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][ |
||
| 318 | pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + |
||
| 319 | ((static_cast<int>(u * rec_z)) & 63)]]) << 48; |
||
| 320 | l += dldx; |
||
| 321 | u += dudx; |
||
| 322 | v += dvdx; |
||
| 323 | z += dzdx; |
||
| 324 | rec_z = 1.0 / z; |
||
| 325 | destlong |= |
||
| 326 | static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][ |
||
| 327 | pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + |
||
| 328 | ((static_cast<int>(u * rec_z)) & 63)]]) << 56; |
||
| 329 | l += dldx; |
||
| 330 | u += dudx; |
||
| 331 | v += dvdx; |
||
| 332 | z += dzdx; |
||
| 333 | rec_z = 1.0 / z; |
||
| 334 | |||
| 335 | *(reinterpret_cast<uint64_t *>(dest)) = destlong; |
||
| 336 | dest += 8; |
||
| 337 | x -= 8; |
||
| 338 | j -= 8; |
||
| 339 | index += 8; |
||
| 340 | if (index+8 >= SWIDTH*SHEIGHT) return; |
||
| 341 | } |
||
| 342 | } |
||
| 343 | while (x-- > 0) { |
||
| 344 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 345 | *dest++ = |
||
| 346 | gr_fade_table[static_cast<int>(fabs(l))][ |
||
| 347 | static_cast<uint32_t>(pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + ((static_cast<int>(u * rec_z)) & 63)])]; |
||
| 348 | l += dldx; |
||
| 349 | u += dudx; |
||
| 350 | v += dvdx; |
||
| 351 | z += dzdx; |
||
| 352 | rec_z = 1.0 / z; |
||
| 353 | } |
||
| 354 | } else { |
||
| 355 | if (x >= 8) { |
||
| 356 | if ((j = reinterpret_cast<uintptr_t>(dest) & 7) != 0) { |
||
| 357 | j = 8 - j; |
||
| 358 | |||
| 359 | while (j > 0) { |
||
| 360 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 361 | c = static_cast<uint32_t>(pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + ((static_cast<int>(u * rec_z)) & 63)]); |
||
| 362 | if (c != 255) |
||
| 363 | *dest = gr_fade_table[static_cast<int>(fabs(l))][c]; |
||
| 364 | dest++; |
||
| 365 | l += dldx; |
||
| 366 | u += dudx; |
||
| 367 | v += dvdx; |
||
| 368 | z += dzdx; |
||
| 369 | rec_z = 1.0 / z; |
||
| 370 | x--; |
||
| 371 | j--; |
||
| 372 | } |
||
| 373 | } |
||
| 374 | |||
| 375 | j = x; |
||
| 376 | while (j >= 8) { |
||
| 377 | uint64_t destlong; |
||
| 378 | destlong = *(reinterpret_cast<uint64_t *>(dest)); |
||
| 379 | c = static_cast<uint32_t>(pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + ((static_cast<int>(u * rec_z)) & 63)]); |
||
| 380 | if (c != 255) { |
||
| 381 | destlong &= ~static_cast<uint64_t>(0xFF); |
||
| 382 | destlong |= static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][c]); |
||
| 383 | } |
||
| 384 | l += dldx; |
||
| 385 | u += dudx; |
||
| 386 | v += dvdx; |
||
| 387 | z += dzdx; |
||
| 388 | rec_z = 1.0 / z; |
||
| 389 | c = static_cast<uint32_t>(pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + ((static_cast<int>(u * rec_z)) & 63)]); |
||
| 390 | if (c != 255) { |
||
| 391 | destlong &= ~(static_cast<uint64_t>(0xFF) << 8); |
||
| 392 | destlong |= static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][c]) << 8; |
||
| 393 | } |
||
| 394 | l += dldx; |
||
| 395 | u += dudx; |
||
| 396 | v += dvdx; |
||
| 397 | z += dzdx; |
||
| 398 | rec_z = 1.0 / z; |
||
| 399 | c = static_cast<uint32_t>(pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + ((static_cast<int>(u * rec_z)) & 63)]); |
||
| 400 | if (c != 255) { |
||
| 401 | destlong &= ~(static_cast<uint64_t>(0xFF) << 16); |
||
| 402 | destlong |= static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][c]) << 16; |
||
| 403 | } |
||
| 404 | l += dldx; |
||
| 405 | u += dudx; |
||
| 406 | v += dvdx; |
||
| 407 | z += dzdx; |
||
| 408 | rec_z = 1.0 / z; |
||
| 409 | c = static_cast<uint32_t>(pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + ((static_cast<int>(u * rec_z)) & 63)]); |
||
| 410 | if (c != 255) { |
||
| 411 | destlong &= ~(static_cast<uint64_t>(0xFF) << 24); |
||
| 412 | destlong |= static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][c]) << 24; |
||
| 413 | } |
||
| 414 | l += dldx; |
||
| 415 | u += dudx; |
||
| 416 | v += dvdx; |
||
| 417 | z += dzdx; |
||
| 418 | rec_z = 1.0 / z; |
||
| 419 | c = static_cast<uint32_t>(pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + ((static_cast<int>(u * rec_z)) & 63)]); |
||
| 420 | if (c != 255) { |
||
| 421 | destlong &= ~(static_cast<uint64_t>(0xFF) << 32); |
||
| 422 | destlong |= static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][c]) << 32; |
||
| 423 | } |
||
| 424 | l += dldx; |
||
| 425 | u += dudx; |
||
| 426 | v += dvdx; |
||
| 427 | z += dzdx; |
||
| 428 | rec_z = 1.0 / z; |
||
| 429 | c = static_cast<uint32_t>(pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + ((static_cast<int>(u * rec_z)) & 63)]); |
||
| 430 | if (c != 255) { |
||
| 431 | destlong &= ~(static_cast<uint64_t>(0xFF) << 40); |
||
| 432 | destlong |= static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][c]) << 40; |
||
| 433 | } |
||
| 434 | l += dldx; |
||
| 435 | u += dudx; |
||
| 436 | v += dvdx; |
||
| 437 | z += dzdx; |
||
| 438 | rec_z = 1.0 / z; |
||
| 439 | c = static_cast<uint32_t>(pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + ((static_cast<int>(u * rec_z)) & 63)]); |
||
| 440 | if (c != 255) { |
||
| 441 | destlong &= ~(static_cast<uint64_t>(0xFF) << 48); |
||
| 442 | destlong |= static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][c]) << 48; |
||
| 443 | } |
||
| 444 | l += dldx; |
||
| 445 | u += dudx; |
||
| 446 | v += dvdx; |
||
| 447 | z += dzdx; |
||
| 448 | rec_z = 1.0 / z; |
||
| 449 | c = static_cast<uint32_t>(pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + ((static_cast<int>(u * rec_z)) & 63)]); |
||
| 450 | if (c != 255) { |
||
| 451 | destlong &= ~(static_cast<uint64_t>(0xFF) << 56); |
||
| 452 | destlong |= static_cast<uint64_t>(gr_fade_table[static_cast<int>(fabs(l))][c]) << 56; |
||
| 453 | } |
||
| 454 | l += dldx; |
||
| 455 | u += dudx; |
||
| 456 | v += dvdx; |
||
| 457 | z += dzdx; |
||
| 458 | rec_z = 1.0 / z; |
||
| 459 | |||
| 460 | *(reinterpret_cast<uint64_t *>(dest)) = destlong; |
||
| 461 | dest += 8; |
||
| 462 | x -= 8; |
||
| 463 | j -= 8; |
||
| 464 | index += 8; |
||
| 465 | if (index+8 >= SWIDTH*SHEIGHT) return; |
||
| 466 | } |
||
| 467 | } |
||
| 468 | while (x-- > 0) { |
||
| 469 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 470 | c = static_cast<uint32_t>(pixptr[((static_cast<int>(v * rec_z)) & (64 * 63)) + ((static_cast<int>(u * rec_z)) & 63)]); |
||
| 471 | if (c != 255) |
||
| 472 | *dest = gr_fade_table[static_cast<int>(fabs(l))][c]; |
||
| 473 | dest++; |
||
| 474 | l += dldx; |
||
| 475 | u += dudx; |
||
| 476 | v += dvdx; |
||
| 477 | z += dzdx; |
||
| 478 | rec_z = 1.0 / z; |
||
| 479 | } |
||
| 480 | } |
||
| 481 | } |
||
| 482 | |||
| 483 | // note the unrolling loop is broken. It is never called, and uses big endian. -- FH |
||
| 484 | static void c_tmap_scanline_per() |
||
| 485 | { |
||
| 486 | uint c; |
||
| 487 | int x, j, index = fx_xleft + (bytes_per_row * fx_y); |
||
| 488 | fix l,u,v,z; |
||
| 489 | fix dudx, dvdx, dzdx, dldx; |
||
| 490 | |||
| 491 | u = fx_u; |
||
| 492 | v = fx_v*64; |
||
| 493 | z = fx_z; |
||
| 494 | dudx = fx_du_dx; |
||
| 495 | dvdx = fx_dv_dx*64; |
||
| 496 | dzdx = fx_dz_dx; |
||
| 497 | |||
| 498 | l = fx_l>>8; |
||
| 499 | dldx = fx_dl_dx/256; |
||
| 500 | auto dest = &write_buffer[fx_xleft + (bytes_per_row * fx_y)]; |
||
| 501 | |||
| 502 | if (!Transparency_on) { |
||
| 503 | const auto pixPtrLocalCopy = pixptr; |
||
| 504 | auto &fadeTableLocalCopy = gr_fade_table; |
||
| 505 | |||
| 506 | x = fx_xright-fx_xleft+1; // x = number of pixels in scanline |
||
| 507 | |||
| 508 | if ((j = reinterpret_cast<uintptr_t>(dest) & 3) != 0) |
||
| 509 | { |
||
| 510 | j = 4 - j; |
||
| 511 | |||
| 512 | if (j > x) |
||
| 513 | j = x; |
||
| 514 | |||
| 515 | while (j > 0) |
||
| 516 | { |
||
| 517 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 518 | //edited 05/18/99 Matt Mueller - changed from 0xff00 to 0x7f00 to fix glitches |
||
| 519 | *dest++ = fadeTableLocalCopy[(l>>8)&0x7f][static_cast<uint32_t>(pixPtrLocalCopy[ ( (v/z)&(64*63) ) + ((u/z)&63) ]) ]; |
||
| 520 | //end edit -MM |
||
| 521 | l += dldx; |
||
| 522 | u += dudx; |
||
| 523 | v += dvdx; |
||
| 524 | z += dzdx; |
||
| 525 | x--; |
||
| 526 | j--; |
||
| 527 | } |
||
| 528 | } |
||
| 529 | |||
| 530 | j &= ~3; |
||
| 531 | while (j > 0) |
||
| 532 | { |
||
| 533 | uint32_t destlong; |
||
| 534 | //edited 05/18/99 Matt Mueller - changed from 0xff00 to 0x7f00 to fix glitches |
||
| 535 | destlong = fadeTableLocalCopy[(l>>8)&0x7f][pixPtrLocalCopy[ ( (v/z)&(64*63) ) + ((u/z)&63) ] ] << 24; |
||
| 536 | //end edit -MM |
||
| 537 | l += dldx; |
||
| 538 | u += dudx; |
||
| 539 | v += dvdx; |
||
| 540 | z += dzdx; |
||
| 541 | //edited 05/18/99 Matt Mueller - changed from 0xff00 to 0x7f00 to fix glitches |
||
| 542 | destlong |= fadeTableLocalCopy[(l>>8)&0x7f][pixPtrLocalCopy[ ( (v/z)&(64*63) ) + ((u/z)&63) ] ] << 16; |
||
| 543 | //end edit -MM |
||
| 544 | l += dldx; |
||
| 545 | u += dudx; |
||
| 546 | v += dvdx; |
||
| 547 | z += dzdx; |
||
| 548 | //edited 05/18/99 Matt Mueller - changed from 0xff00 to 0x7f00 to fix glitches |
||
| 549 | destlong |= fadeTableLocalCopy[(l>>8)&0x7f][pixPtrLocalCopy[ ( (v/z)&(64*63) ) + ((u/z)&63) ] ] << 8; |
||
| 550 | //end edit -MM |
||
| 551 | l += dldx; |
||
| 552 | u += dudx; |
||
| 553 | v += dvdx; |
||
| 554 | z += dzdx; |
||
| 555 | //edited 05/18/99 Matt Mueller - changed from 0xff00 to 0x7f00 to fix glitches |
||
| 556 | destlong |= fadeTableLocalCopy[(l>>8)&0x7f][pixPtrLocalCopy[ ( (v/z)&(64*63) ) + ((u/z)&63) ] ]; |
||
| 557 | //end edit -MM |
||
| 558 | l += dldx; |
||
| 559 | u += dudx; |
||
| 560 | v += dvdx; |
||
| 561 | z += dzdx; |
||
| 562 | *reinterpret_cast<uint32_t *>(dest) = destlong; |
||
| 563 | dest += 4; |
||
| 564 | x -= 4; |
||
| 565 | j -= 4; |
||
| 566 | index += 4; |
||
| 567 | if (index+4 >= SWIDTH*SHEIGHT) return; |
||
| 568 | } |
||
| 569 | |||
| 570 | while (x-- > 0) |
||
| 571 | { |
||
| 572 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 573 | //edited 05/18/99 Matt Mueller - changed from 0xff00 to 0x7f00 to fix glitches |
||
| 574 | *dest++ = fadeTableLocalCopy[(l>>8)&0x7f][pixPtrLocalCopy[ ( (v/z)&(64*63) ) + ((u/z)&63) ] ]; |
||
| 575 | //end edit -MM |
||
| 576 | l += dldx; |
||
| 577 | u += dudx; |
||
| 578 | v += dvdx; |
||
| 579 | z += dzdx; |
||
| 580 | } |
||
| 581 | |||
| 582 | } else { |
||
| 583 | for (x= fx_xright-fx_xleft+1 ; x > 0; --x ) { |
||
| 584 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 585 | c = static_cast<uint32_t>(pixptr[ ( (v/z)&(64*63) ) + ((u/z)&63) ]); |
||
| 586 | if ( c!=TRANSPARENCY_COLOR) |
||
| 587 | *dest = gr_fade_table[(l >> 8) &0x7f][c ]; |
||
| 588 | dest++; |
||
| 589 | l += dldx; |
||
| 590 | u += dudx; |
||
| 591 | v += dvdx; |
||
| 592 | z += dzdx; |
||
| 593 | } |
||
| 594 | } |
||
| 595 | } |
||
| 596 | |||
| 597 | static void c_tmap_scanline_quad() |
||
| 598 | { |
||
| 599 | uint c; |
||
| 600 | int x, index = fx_xleft + (bytes_per_row * fx_y); |
||
| 601 | fix u,v,l,dudx, dvdx, dldx; |
||
| 602 | |||
| 603 | // Quadratic setup stuff: |
||
| 604 | fix a1, a2, b1, b2, dudx1, dvdx1; |
||
| 605 | fix u0 = fx_u; |
||
| 606 | fix u2 = fx_u + fx_du_dx*(fx_xright-fx_xleft+1); // This just needs to be uright from outer loop |
||
| 607 | fix v0 = fx_v; |
||
| 608 | fix v2 = fx_v + fx_dv_dx*(fx_xright-fx_xleft+1); // This just needs to be vright from outer loop |
||
| 609 | fix w0 = fx_z; |
||
| 610 | fix w2 = fx_z + fx_dz_dx*(fx_xright-fx_xleft+1); // This just needs to be zright from outer loop |
||
| 611 | fix u1 = fixdiv((u0+u2),(w0+w2)); |
||
| 612 | fix v1 = fixdiv((v0+v2),(w0+w2)); |
||
| 613 | int dx = fx_xright-fx_xleft+1; |
||
| 614 | u0 = fixdiv( u0, w0 ); // Divide Z out. This should be in outer loop |
||
| 615 | v0 = fixdiv( v0, w0 ); // Divide Z out. This should be in outer loop |
||
| 616 | u2 = fixdiv( u2, w2 ); // Divide Z out. This should be in outer loop |
||
| 617 | v2 = fixdiv( v2, w2 ); // Divide Z out. This should be in outer loop |
||
| 618 | a1 = (-3*u0+4*u1-u2)/dx; |
||
| 619 | b1 = (-3*v0+4*v1-v2)/dx; |
||
| 620 | a2 = (2*(u0-2*u1+u2))/(dx*dx); |
||
| 621 | b2 = (2*(v0-2*v1+v2))/(dx*dx); |
||
| 622 | dudx = a1 + a2; |
||
| 623 | dvdx = b1 + b2; |
||
| 624 | dudx1 = 2*a2; |
||
| 625 | dvdx1 = 2*b2; |
||
| 626 | u = u0; |
||
| 627 | v = v0; |
||
| 628 | |||
| 629 | // Normal lighting setup |
||
| 630 | l = fx_l>>8; |
||
| 631 | dldx = fx_dl_dx>>8; |
||
| 632 | |||
| 633 | // Normal destination pointer setup |
||
| 634 | auto dest = &write_buffer[fx_xleft + (bytes_per_row * fx_y)]; |
||
| 635 | |||
| 636 | if (!Transparency_on) { |
||
| 637 | for (x= fx_xright-fx_xleft+1 ; x > 0; --x ) { |
||
| 638 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 639 | *dest++ = gr_fade_table[(l>>8)&0xff][pixptr[ (f2i(v)&63)*64 + (f2i(u)&63) ] ]; |
||
| 640 | l += dldx; |
||
| 641 | u += dudx; |
||
| 642 | v += dvdx; |
||
| 643 | dudx += dudx1; // Extra add for quadratic! |
||
| 644 | dvdx += dvdx1; // Extra add for quadratic! |
||
| 645 | } |
||
| 646 | } else { |
||
| 647 | for (x= fx_xright-fx_xleft+1 ; x > 0; --x ) { |
||
| 648 | if (++index >= SWIDTH*SHEIGHT) return; |
||
| 649 | c = static_cast<uint32_t>(pixptr[ (f2i(v)&63)*64 + (f2i(u)&63) ]); |
||
| 650 | if ( c!=255) |
||
| 651 | *dest = gr_fade_table[(l>>8)&0xff][c]; |
||
| 652 | dest++; |
||
| 653 | l += dldx; |
||
| 654 | u += dudx; |
||
| 655 | v += dvdx; |
||
| 656 | dudx += dudx1; // Extra add for quadratic! |
||
| 657 | dvdx += dvdx1; // Extra add for quadratic! |
||
| 658 | } |
||
| 659 | } |
||
| 660 | } |
||
| 661 | |||
| 662 | //runtime selection of optimized tmappers. 12/07/99 Matthew Mueller |
||
| 663 | //the reason I did it this way rather than having a *tmap_funcs that then points to a c_tmap or fp_tmap struct thats already filled in, is to avoid a second pointer dereference. |
||
| 664 | void select_tmap(const std::string &type) |
||
| 665 | { |
||
| 666 | if (type == "fp") |
||
| 667 | { |
||
| 668 | cur_tmap_scanline_per=c_fp_tmap_scanline_per; |
||
| 669 | } |
||
| 670 | else if (type == "quad") |
||
| 671 | { |
||
| 672 | cur_tmap_scanline_per=c_tmap_scanline_quad; |
||
| 673 | } |
||
| 674 | else { |
||
| 675 | cur_tmap_scanline_per=c_tmap_scanline_per; |
||
| 676 | } |
||
| 677 | } |
||
| 678 | |||
| 679 | } |