1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136
|
/* Copyright (C) 2000-2002 Damir Zucic */
/*=============================================================================
spacefill_color.c
Purpose:
Prepare the color for a single pixel which is on the atomic sphere
surface.
Input:
(1) Pointer to AtomS structure.
(2) Pointer to GUIS structure.
(3) Cosine of the angle between the vector from sphere center and
the current pixel and the light source unit vector.
Output:
(1) Return value.
Return value:
The pixel (color) value.
Notes:
(1) This function uses left, right and black color. Note that the
middle color is not used here!
(2) This function may be quite slow (a lot of math).
=============================================================================*/
#include <stdio.h>
#include <math.h>
#include <X11/Xlib.h>
#include <X11/Xutil.h>
#include <X11/Xos.h>
#include <X11/Xatom.h>
#include "defines.h"
#include "typedefs.h"
/*======spacefill color:=====================================================*/
unsigned long SpacefillColor_ (AtomS *curr_atomSP,
GUIS *guiSP,
double cos_angle)
{
static long double w1, w2;
static unsigned long colorID;
static unsigned long red_mask, green_mask, blue_mask;
static unsigned long red1, red2, red;
static unsigned long green1, green2, green;
static unsigned long blue1, blue2, blue;
static long double r1, r2, g1, g2, b1, b2;
static long double r, g, b;
/* Factors which are used to weight colors: */
w1 = cos_angle * cos_angle;
w2 = 1 - w1;
/* Copy masks: */
red_mask = guiSP->visual_infoS.red_mask;
green_mask = guiSP->visual_infoS.green_mask;
blue_mask = guiSP->visual_infoS.blue_mask;
/* Bright side (cos_angle between zero and one): */
if (cos_angle >= 0.0)
{
/* Extract input color components: */
red1 = curr_atomSP->left_colorID & red_mask;
red2 = curr_atomSP->right_colorID & red_mask;
green1 = curr_atomSP->left_colorID & green_mask;
green2 = curr_atomSP->right_colorID & green_mask;
blue1 = curr_atomSP->left_colorID & blue_mask;
blue2 = curr_atomSP->right_colorID & blue_mask;
/* Convert to doubles: */
r1 = (double) red1;
r2 = (double) red2;
g1 = (double) green1;
g2 = (double) green2;
b1 = (double) blue1;
b2 = (double) blue2;
/* Calculate new color components: */
r = w1 * r1 + w2 * r2;
g = w1 * g1 + w2 * g2;
b = w1 * b1 + w2 * b2;
}
/* Dark side (cos_angle between minus one and zero): */
else
{
/* Extract input color components: */
red1 = curr_atomSP->right_colorID & red_mask;
red2 = guiSP->black_colorID & red_mask;
green1 = curr_atomSP->right_colorID & green_mask;
green2 = guiSP->black_colorID & green_mask;
blue1 = curr_atomSP->right_colorID & blue_mask;
blue2 = guiSP->black_colorID & blue_mask;
/* Convert to doubles: */
r1 = (double) red1;
r2 = (double) red2;
g1 = (double) green1;
g2 = (double) green2;
b1 = (double) blue1;
b2 = (double) blue2;
/* Calculate new color components: */
r = w2 * r1 + w1 * r2;
g = w2 * g1 + w1 * g2;
b = w2 * b1 + w1 * b2;
}
/* Check new color components: */
if (r < 0.0) r = 0.0;
if (g < 0.0) g = 0.0;
if (b < 0.0) b = 0.0;
/* Convert new color components: */
red = ((unsigned long) r) & red_mask;
green = ((unsigned long) g) & green_mask;
blue = ((unsigned long) b) & blue_mask;
/* Combine new color components: */
colorID = red | green | blue;
/* Return the pixel value: */
return colorID;
}
/*===========================================================================*/
|