00001 !!ARBfp1.0
00002 OPTION NV_fragment_program2;
00003
00004 # Copyright (c) 2005 Institute for Visualization and Interactive
00005 # Systems, University of Stuttgart, Germany
00006 #
00007 # This source code is distributed as part of the single-pass volume
00008 # rendering project. Details about this project can be found on the
00009 # project web page at http://www.vis.uni-stuttgart.de/eng/research/
00010 # fields/current/spvolren. This file may be distributed, modified,
00011 # and used free of charge as long as this copyright notice is
00012 # included in its original form. Commercial use is strictly
00013 # prohibited.
00014 #
00015 # Filename: isosurface_clipped_sm3.fp
00016
00017 #! VOLUME = 0
00018 #! BACKGROUND = 1
00019 #! CLIPVOLUME = 2
00020
00021 # r = step
00022 # g = gradient scale
00023 # b = gradient offset
00024 # a = z-value of background plane
00025 PARAM params = program.local[0];
00026
00027 # r = texture coordinate scale
00028 # g = number of iterations
00029 # b = isovalue of isosurface
00030 PARAM params2 = program.local[1];
00031
00032 # r = scattering scale
00033 # g = isovalue of clipping isosurface
00034 PARAM params3 = program.local[4];
00035
00036 PARAM center = program.local[2];
00037 PARAM texMax = program.local[3];
00038
00039 PARAM scaleFactors = program.local[5];
00040
00041 PARAM isColor1 = {0.0, .5, 0.0, 1.0};
00042 PARAM isColor2 = {0.0, 0.0, .5, 1.0};
00043
00044 TEMP geomDir;
00045 TEMP geomPos;
00046 TEMP lightVec;
00047 TEMP texCoord;
00048 TEMP prevPos;
00049 TEMP texblen;
00050 TEMP diffVec;
00051 TEMP halfway;
00052 TEMP eyeVec;
00053 TEMP intens;
00054 TEMP camera;
00055 TEMP normal;
00056 TEMP weight;
00057 TEMP temp1;
00058 TEMP temp2;
00059 TEMP temp;
00060 TEMP grad;
00061 TEMP pos;
00062 TEMP src;
00063 TEMP dst;
00064 TEMP dir;
00065 TEMP tex;
00066 TEMP scalActInner;
00067 TEMP scalPreInner;
00068 TEMP scalActOuter;
00069 TEMP scalPreOuter;
00070
00071 # Compute the ray's starting point
00072 MOV geomPos, fragment.texcoord[0];
00073 MUL pos, geomPos, scaleFactors;
00074 MOV pos.a, 0.0;
00075
00076 # Compute the camera position by translating the origin to the center of the
00077 # volume
00078 MOV camera, state.matrix.modelview.invtrans.row[3];
00079
00080 # Compute the ray direction
00081 SUB geomDir, geomPos, camera;
00082
00083 # Normalize the direction
00084 DP3 geomDir.w, geomDir, geomDir;
00085 RSQ geomDir.w, geomDir.w;
00086 MUL geomDir, geomDir, geomDir.w;
00087 MOV geomDir.w, 0.0;
00088
00089 MUL dir, geomDir, scaleFactors;
00090
00091 # Initialize the 'previous' intensity
00092 TXL intens, pos, texture[0], 3D;
00093 MOV scalPreOuter, intens.a;
00094
00095 MAD pos, dir, params.r, pos;
00096
00097 # Initialize texture corrdinates
00098 # texcood.a inherits level of detail
00099 MOV texCoord, 0.0;
00100
00101 # Initialize destination color
00102 MOV dst, 0.0;
00103
00104 #REP params2.g;
00105
00106 REP params2.g;
00107 # Lookup scalar and gradient
00108 MOV texCoord.rgb, pos;
00109 TXL tex, texCoord, texture[0], 3D;
00110
00111 MOV scalActOuter, tex.a;
00112
00113 # Move one step forward
00114 MAD pos, dir, params.r, pos;
00115
00116 # Isosurface if differences with past and present
00117 # scalar values and isovalue have different signs
00118 MOV intens.r, scalActOuter;
00119 MOV intens.g, scalPreOuter;
00120 SUB temp.rg, intens, params2.b;
00121 MULC temp, temp.r, temp.g;
00122 IF LE.x;
00123 # Isosurface found
00124 MOV src, isColor1;
00125
00126 # Get scalar value from actual position
00127 MAD pos, -dir, params.r, pos;
00128 TXL scalActInner, pos, texture[0], 3D;
00129
00130 # Get scalar value from previous position
00131 MAD prevPos, -dir, params.r, pos;
00132 TXL scalPreInner, prevPos, texture[0], 3D;
00133
00134 SUB temp.r, params2.b, scalPreInner.a;
00135 SUBC temp.g, scalActInner.a, scalPreInner.a;
00136
00137 # Determine isosurface color
00138 MOV src (LT.g), isColor2;
00139
00140 # Perform linear interpolation to increase accuracy
00141 DIV_SAT temp.b, temp.r, temp.g;
00142 LRP pos, temp.b, pos, prevPos;
00143
00144 TXL tex, pos, texture[2], 3D;
00145 SUBC tex.x, tex.x, params3.g;
00146 IF GE.x;
00147 # Determine gradient at corrected position (same as above)
00148 MOV texCoord.rgb, pos;
00149 TXL tex, pos, texture[0], 3D;
00150 MOV grad.rgb, tex;
00151
00152 # Determine scale factor for gradient
00153 SNE temp.rgb, grad, 0.0;
00154 DP3_SAT temp.r, temp, 1.0;
00155
00156 # Reconstruct the gradient
00157 MAD_SSAT grad.rgb, tex, 2.0, -1.0;
00158 NRM_SSAT grad.rgb, grad;
00159
00160 # Set gradient to zero if it was zero
00161 MUL grad.rgb, grad, temp.r;
00162
00163 # Re-orient the gradient to get a
00164 # correct surface normal
00165 MOV temp, 0.0;
00166 DP3 temp.r, -geomDir, grad;
00167 NRM temp, temp;
00168 MUL grad.rgb, grad, temp.r;
00169
00170 # Perform the lighting calculation (yes, we know LIT!)
00171
00172 # Ambient term
00173 MUL dst, state.light[0].ambient, src;
00174
00175 # Diffuse term
00176 SUB lightVec.rgb, state.light[0].position, geomPos;
00177 MOV lightVec.a, 0.0;
00178 NRM lightVec, lightVec;
00179 DP3_SAT temp.a, lightVec, grad;
00180 MUL temp, src, temp.a;
00181 MAD dst, state.light[0].diffuse, temp, dst;
00182
00183 # Specular term
00184 # First calculate halfway vector
00185 ADD halfway, lightVec, -geomDir;
00186 MOV halfway.a, 0.0;
00187 NRM halfway, halfway;
00188 # Specular Lighting
00189 SUB eyeVec.rgb, camera, geomPos;
00190 MOV eyeVec.a, 0.0;
00191 NRM eyeVec, eyeVec;
00192 DP3_SAT temp.a, halfway, grad;
00193 POW temp.a, temp.a, 10.0;
00194 MAD dst, state.light[0].specular, temp.a, dst;
00195 # Isofurfaces are opaque
00196 MOV dst.a, 1.0;
00197
00198 # Everything is done, jump out of loop
00199 MOVC temp.x, 0.0;
00200 BRK (EQ.x);
00201 ENDIF;
00202 ENDIF;
00203
00204 MOV scalPreOuter, scalActOuter;
00205
00206 # Set values to zero if outside volume
00207 SGE temp1, pos, 0.0;
00208 SLE temp2, pos, texMax;
00209 DP3 weight.r, temp1, temp2;
00210 SEQC weight.r, weight.r, 3.0;
00211
00212 # Already outside volume, skip the rest
00213 BRK (EQ.x);
00214
00215 ENDREP;
00216
00217 #BRK (EQ.x);
00218
00219 #ENDREP;
00220
00221 # Compute the normal of the background plane (this is just the negative view
00222 # direction which initially is (0, 0, -1))
00223 MOV normal, state.matrix.modelview.row[2];
00224
00225 # Compute the plane constant (we want the plane to be located in the volume
00226 # center)
00227 DP3 temp1.r, normal, center;
00228
00229 # Move the plane behind the volume: d' = <n,(x - l n)> = <n, x> - l <n, n>;
00230 # l = 0.71 is chosen since it is greater than half the cube diagonal
00231 DP3 temp1.g, normal, normal;
00232 MAD temp1.r, temp1.g, -.71, temp1.r;
00233
00234 # Compute ray parameter
00235 DP3 temp1.g, normal, geomPos;
00236 SUB temp1.g, temp1.r, temp1.g;
00237 DP3 temp1.b, normal, geomDir;
00238 DIV temp.r, temp1.g, temp1.b;
00239
00240 # Compute ray/plane intersection
00241 MAD temp.rgb, temp.r, geomDir, geomPos;
00242
00243 # Compute the difference vector
00244 SUB diffVec, temp, center;
00245
00246 # Compute the texture coordinates
00247 DP3 temp.r, diffVec, state.matrix.modelview.row[0];
00248 DP3 temp.g, diffVec, state.matrix.modelview.row[1];
00249 MUL temp.rg, temp, params2.r;
00250
00251 # Center background image
00252 ADD temp.rg, temp, .5;
00253
00254 # Look up the texel value
00255 TEX temp.rgb, temp, texture[1], 2D;
00256 MOV temp.a, 1.0;
00257
00258 # Blend the background pixel
00259 SUB texblen, 1.0, dst.a;
00260 MAD dst, temp, texblen.x, dst;
00261
00262 # Write the output color
00263 MOV result.color, dst;
00264
00265 END