Blender V2.61 - r43446
|
00001 /* 00002 * Copyright 2011, Blender Foundation. 00003 * 00004 * This program is free software; you can redistribute it and/or 00005 * modify it under the terms of the GNU General Public License 00006 * as published by the Free Software Foundation; either version 2 00007 * of the License, or (at your option) any later version. 00008 * 00009 * This program is distributed in the hope that it will be useful, 00010 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00011 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00012 * GNU General Public License for more details. 00013 * 00014 * You should have received a copy of the GNU General Public License 00015 * along with this program; if not, write to the Free Software Foundation, 00016 * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 00017 */ 00018 00019 CCL_NAMESPACE_BEGIN 00020 00021 /* Perspective Camera */ 00022 00023 __device float2 camera_sample_aperture(KernelGlobals *kg, float u, float v) 00024 { 00025 float blades = kernel_data.cam.blades; 00026 00027 if(blades == 0.0f) { 00028 /* sample disk */ 00029 return concentric_sample_disk(u, v); 00030 } 00031 else { 00032 /* sample polygon */ 00033 float rotation = kernel_data.cam.bladesrotation; 00034 return regular_polygon_sample(blades, rotation, u, v); 00035 } 00036 } 00037 00038 __device void camera_sample_perspective(KernelGlobals *kg, float raster_x, float raster_y, float lens_u, float lens_v, Ray *ray) 00039 { 00040 /* create ray form raster position */ 00041 Transform rastertocamera = kernel_data.cam.rastertocamera; 00042 float3 Pcamera = transform(&rastertocamera, make_float3(raster_x, raster_y, 0.0f)); 00043 00044 ray->P = make_float3(0.0f, 0.0f, 0.0f); 00045 ray->D = Pcamera; 00046 00047 /* modify ray for depth of field */ 00048 float aperturesize = kernel_data.cam.aperturesize; 00049 00050 if(aperturesize > 0.0f) { 00051 /* sample point on aperture */ 00052 float2 lensuv = camera_sample_aperture(kg, lens_u, lens_v)*aperturesize; 00053 00054 /* compute point on plane of focus */ 00055 float ft = kernel_data.cam.focaldistance/ray->D.z; 00056 float3 Pfocus = ray->P + ray->D*ft; 00057 00058 /* update ray for effect of lens */ 00059 ray->P = make_float3(lensuv.x, lensuv.y, 0.0f); 00060 ray->D = normalize(Pfocus - ray->P); 00061 } 00062 00063 /* transform ray from camera to world */ 00064 Transform cameratoworld = kernel_data.cam.cameratoworld; 00065 00066 ray->P = transform(&cameratoworld, ray->P); 00067 ray->D = transform_direction(&cameratoworld, ray->D); 00068 ray->D = normalize(ray->D); 00069 00070 #ifdef __RAY_DIFFERENTIALS__ 00071 /* ray differential */ 00072 float3 Ddiff = transform_direction(&cameratoworld, Pcamera); 00073 00074 ray->dP.dx = make_float3(0.0f, 0.0f, 0.0f); 00075 ray->dP.dy = make_float3(0.0f, 0.0f, 0.0f); 00076 00077 ray->dD.dx = normalize(Ddiff + float4_to_float3(kernel_data.cam.dx)) - normalize(Ddiff); 00078 ray->dD.dy = normalize(Ddiff + float4_to_float3(kernel_data.cam.dy)) - normalize(Ddiff); 00079 #endif 00080 00081 #ifdef __CAMERA_CLIPPING__ 00082 /* clipping */ 00083 ray->P += kernel_data.cam.nearclip*ray->D; 00084 ray->t = kernel_data.cam.cliplength; 00085 #else 00086 ray->t = FLT_MAX; 00087 #endif 00088 } 00089 00090 /* Orthographic Camera */ 00091 00092 __device void camera_sample_orthographic(KernelGlobals *kg, float raster_x, float raster_y, Ray *ray) 00093 { 00094 /* create ray form raster position */ 00095 Transform rastertocamera = kernel_data.cam.rastertocamera; 00096 float3 Pcamera = transform(&rastertocamera, make_float3(raster_x, raster_y, 0.0f)); 00097 00098 ray->P = Pcamera; 00099 ray->D = make_float3(0.0f, 0.0f, 1.0f); 00100 00101 /* transform ray from camera to world */ 00102 Transform cameratoworld = kernel_data.cam.cameratoworld; 00103 00104 ray->P = transform(&cameratoworld, ray->P); 00105 ray->D = transform_direction(&cameratoworld, ray->D); 00106 ray->D = normalize(ray->D); 00107 00108 #ifdef __RAY_DIFFERENTIALS__ 00109 /* ray differential */ 00110 ray->dP.dx = float4_to_float3(kernel_data.cam.dx); 00111 ray->dP.dy = float4_to_float3(kernel_data.cam.dy); 00112 00113 ray->dD.dx = make_float3(0.0f, 0.0f, 0.0f); 00114 ray->dD.dy = make_float3(0.0f, 0.0f, 0.0f); 00115 #endif 00116 00117 #ifdef __CAMERA_CLIPPING__ 00118 /* clipping */ 00119 ray->t = kernel_data.cam.cliplength; 00120 #else 00121 ray->t = FLT_MAX; 00122 #endif 00123 } 00124 00125 /* Common */ 00126 00127 __device void camera_sample(KernelGlobals *kg, int x, int y, float filter_u, float filter_v, float lens_u, float lens_v, Ray *ray) 00128 { 00129 /* pixel filter */ 00130 float raster_x = x + kernel_tex_interp(__filter_table, filter_u, FILTER_TABLE_SIZE); 00131 float raster_y = y + kernel_tex_interp(__filter_table, filter_v, FILTER_TABLE_SIZE); 00132 00133 /* motion blur */ 00134 //ray->time = lerp(time_t, kernel_data.cam.shutter_open, kernel_data.cam.shutter_close); 00135 00136 /* sample */ 00137 if(kernel_data.cam.ortho) 00138 camera_sample_orthographic(kg, raster_x, raster_y, ray); 00139 else 00140 camera_sample_perspective(kg, raster_x, raster_y, lens_u, lens_v, ray); 00141 } 00142 00143 CCL_NAMESPACE_END 00144