home *** CD-ROM | disk | FTP | other *** search
/ Otherware / Otherware_1_SB_Development.iso / mac / developm / source / macraysh.sit / Code / Source / fogdeck.c < prev    next >
Encoding:
C/C++ Source or Header  |  1991-10-24  |  2.7 KB  |  120 lines

  1. /*
  2.  * fogdeck.c
  3.  *
  4.  * Copyright (C) 1989, 1991, Craig E. Kolb
  5.  * All rights reserved.
  6.  *
  7.  * This software may be freely copied, modified, and redistributed
  8.  * provided that this copyright notice is preserved on all copies.
  9.  *
  10.  * You may not distribute this software, in whole or in part, as part of
  11.  * any commercial product without the express consent of the authors.
  12.  *
  13.  * There is no warranty or other guarantee of fitness of this software
  14.  * for any purpose.  It is provided solely "as is".
  15.  *
  16.  * $Id: fogdeck.c,v 4.0 91/07/17 14:40:28 kolb Exp Locker: kolb $
  17.  *
  18.  * $Log:    fogdeck.c,v $
  19.  * Revision 4.0  91/07/17  14:40:28  kolb
  20.  * Initial version.
  21.  * 
  22.  */
  23. #include "atmosphere.h"
  24. #include "fogdeck.h"
  25.  
  26. Fogdeck *
  27. FogdeckCreate(alt, offset, scale, chaoscale, octaves, color, trans)
  28. Float alt, offset, chaoscale;
  29. Vector *scale;
  30. int octaves;
  31. Color *color, *trans;
  32. {
  33.     Fogdeck *fogdeck;
  34.  
  35.     fogdeck = (Fogdeck *)Malloc(sizeof(Fogdeck));
  36.  
  37.     fogdeck->alt = alt;
  38.     fogdeck->octaves = octaves;
  39.     fogdeck->scale = *scale;
  40.     fogdeck->chaoscale = chaoscale;
  41.     fogdeck->offset = offset;
  42.  
  43.     if (color == (Color *)NULL)
  44.         fogdeck->color.r = fogdeck->color.g = fogdeck->color.b = 0.;
  45.     else
  46.         fogdeck->color = *color;
  47.     if (trans == (Color *)NULL)
  48.         fogdeck->trans.r = fogdeck->trans.g = fogdeck->trans.b =
  49.             FAR_AWAY;
  50.     else {
  51.         fogdeck->trans = *trans;
  52.     }
  53.     return fogdeck;
  54. }
  55.  
  56. /*
  57.  * Add fogdeck to the given color.
  58.  */
  59. void
  60. FogdeckApply(fogdeck, ray, pos, dist, color)
  61. Fogdeck *fogdeck;
  62. Ray *ray;
  63. Vector *pos;
  64. Float dist;
  65. Color *color;
  66. {
  67.     Float atten, hitdist, density;
  68.     Color trans;
  69.     Vector endp;
  70.     extern Float ExpAtten(), PAChaos();
  71.  
  72.     /*
  73.      * Find distance from origin at which ray strikes
  74.      * z = fogdeck->alt plane
  75.      */
  76.     if (abs(ray->dir.z) < EPSILON)
  77.         return;
  78.     hitdist = (fogdeck->alt - ray->pos.z) / ray->dir.z;
  79.     if (hitdist < EPSILON || hitdist > dist)
  80.         return;
  81.     /*
  82.      * Compute ray endpoint
  83.      */
  84.     VecAddScaled(ray->pos, hitdist, ray->dir, &endp);
  85.  
  86.     /*
  87.      * Modify transmissivity based on point of
  88.      * intersection.
  89.      */
  90.     endp.x *= fogdeck->scale.x;
  91.     endp.y *= fogdeck->scale.y;
  92.     endp.z *= fogdeck->scale.z;
  93.  
  94.     density = fogdeck->offset +
  95.             fogdeck->chaoscale * PAChaos(&endp, fogdeck->octaves);
  96.     if (density < EPSILON)
  97.         density = 1.;
  98.     else
  99.         density = 1. / density;
  100.  
  101.     trans = fogdeck->trans;
  102.     ColorScale(density, trans, &trans);
  103.  
  104.     dist -= hitdist;
  105.     
  106.     atten = ExpAtten(dist, trans.r);
  107.  
  108.     if (trans.r == trans.g &&
  109.         trans.r == trans.b) {
  110.         ColorBlend(color, &fogdeck->color, atten, 1. - atten);
  111.         return;
  112.     }
  113.     color->r = atten*color->r + (1. - atten) * fogdeck->color.r;
  114.  
  115.     atten = ExpAtten(dist, trans.g);
  116.     color->g = atten*color->g + (1. - atten) * fogdeck->color.g;
  117.     atten = ExpAtten(dist, trans.b);
  118.     color->b = atten*color->b + (1. - atten) * fogdeck->color.b;
  119. }
  120.