1#ifdef AUX_PREVIS_NAA
2//bayes step cell functor
3void step_cell_aux_previs_naa(AuxArgs aux_args, int data_ptr, uchar llid, float d)
4{
5    float  alpha = aux_args.alpha[data_ptr];
6    int cum_int = aux_args.seg_len[data_ptr];
7    int mean_int = aux_args.mean_obs[data_ptr];
8    float mean_obs = convert_float(mean_int) / convert_float(cum_int);
9    float cum_len = convert_float(cum_int) / SEGLEN_FACTOR;
10
11    //calculate pre_infinity denominator (shape of image)
12    float seg_len_real = d*aux_args.linfo->block_len;
13    float cum_len_real = cum_len*aux_args.linfo->block_len;
14
15    // if total length of rays is too small, do nothing
16    float PI = 0.0f;
17    if (cum_len_real > 1.0e-10f)
18    {
19        // retrieve albedo and normal probabilities
20        __global float16 *albedos = (__global float16*)&(aux_args.naa_apm[data_ptr*32]);
21        __global float16 *normal_weights = (__global float16*)&(aux_args.naa_apm[data_ptr*32 + 16]);
22
23        // compute mean and sigma of radiance value as linear function of albedo and albedo^2, respectively
24        float16 radiance_predictions = *aux_args.radiance_reflectance_factors * (*albedos) + *aux_args.radiance_offsets;
25        float16 radiance_variances = *aux_args.radiance_var_reflectance_sqrd_factors * (*albedos)*(*albedos) + *aux_args.radiance_var_offsets;
26        int16 invalid = islessequal(radiance_variances,(float16)0);
27        float16 radiance_sigmas = sqrt(radiance_variances);
28        float16 prediction_densities = gauss_prob_density_f16(&radiance_predictions, mean_obs, &radiance_sigmas);
29        // set prob. density to 0 for invalid normal directions
30        prediction_densities = select(prediction_densities,(float16)0,invalid);
31        // take weighted average based on surface normal probabilities
32        PI = dot(prediction_densities, *normal_weights);
33    }
34    // store and update pre and vis
35    float pass_prob = exp(-alpha * seg_len_real);
36    float vis_prob_end = (*aux_args.ray_vis) * pass_prob;
37
38    // compute this ray's contribution to beta
39    float cell_vis = (*aux_args.ray_vis) * d;
40    float cell_pre = (*aux_args.ray_pre) * d;
41
42    // updated pre                      Omega         *  PI
43    (* aux_args.ray_pre) += (* aux_args.ray_vis)*(1.0f-pass_prob)*PI;
44    // updated visibility probability
45    (* aux_args.ray_vis) *= pass_prob;
46
47    //discretize and store beta and vis contribution
48    int pre_int = convert_int_rte(cell_pre * SEGLEN_FACTOR);
49    atom_add(&aux_args.pre_array[data_ptr], pre_int);
50
51    int vis_int  = convert_int_rte(cell_vis * SEGLEN_FACTOR);
52    atom_add(&aux_args.vis_array[data_ptr], vis_int);
53}
54#endif // AUX_PREVIS_NAA
55
56
57#ifdef PREINF_NAA
58
59//preinf step cell functor for normal_albedo_array appearance model
60void step_cell_preinf_naa(AuxArgs aux_args, int data_ptr, uchar llid, float d)
61{
62    //keep track of cells being hit
63    //cell data, i.e., alpha and app model is needed for some passes
64    float  alpha = aux_args.alpha[data_ptr];
65
66    int cum_int = aux_args.seg_len[data_ptr];
67    int mean_int = aux_args.mean_obs[data_ptr];
68    float mean_obs = convert_float(mean_int) / convert_float(cum_int);
69    float cum_len = convert_float(cum_int) / SEGLEN_FACTOR;
70
71    //calculate pre_infinity denominator (shape of image)
72    float seg_len_real = d*aux_args.linfo->block_len;
73    float cum_len_real = cum_len*aux_args.linfo->block_len;
74
75    // if total length of rays is too small, do nothing
76    float PI = 0.0f;
77    if (cum_len_real > 1.0e-10f)
78    {
79        // retrieve albedo and normal probabilities
80        __global float16 *albedos = (__global float16*)&(aux_args.naa_apm[data_ptr*32]);
81        __global float16 *normal_weights = (__global float16*)&(aux_args.naa_apm[data_ptr*32 + 16]);
82
83        // compute mean and sigma of radiance value as linear function of albedo and albedo^2, respectively
84        float16 radiance_predictions = *aux_args.radiance_reflectance_factors * (*albedos) + *aux_args.radiance_offsets;
85        float16 radiance_variances = *aux_args.radiance_var_reflectance_sqrd_factors * (*albedos)*(*albedos) + *aux_args.radiance_var_offsets;
86        int16 invalid = islessequal(radiance_variances,(float16)0);
87        float16 radiance_sigmas = sqrt(radiance_variances);
88        float16 prediction_densities = gauss_prob_density_f16(&radiance_predictions, mean_obs, &radiance_sigmas);
89        // set prob. density to 0 for invalid normal directions
90        prediction_densities = select(prediction_densities,(float16)0,invalid);
91        // take weighted average based on surface normal probabilities
92        PI = dot(prediction_densities, *normal_weights);
93    }
94    // Calculate pre and vis infinity
95    float diff_omega = exp(-alpha * seg_len_real);
96    float vis_prob_end = (*aux_args.vis_inf) * diff_omega;
97
98    // updated pre                      Omega         *   PI
99    (*aux_args.pre_inf) += ((*aux_args.vis_inf) - vis_prob_end) *  PI;
100
101    // updated visibility probability
102    (*aux_args.vis_inf) = vis_prob_end;
103}
104
105#endif // PREINF_NAA
106
107
108#ifdef BAYES_NAA
109
110//bayes step cell functor for normal-albedo-array model, only update alpha
111void step_cell_bayes_naa(AuxArgs aux_args, int data_ptr, uchar llid, float d)
112{
113    //slow beta calculation ----------------------------------------------------
114    float  alpha = aux_args.alpha[data_ptr];
115
116    //load aux data
117    int cum_int = aux_args.seg_len[data_ptr];
118    int mean_int = aux_args.mean_obs[data_ptr];
119    float mean_obs = convert_float(mean_int) / convert_float(cum_int);
120    float cum_len = convert_float(cum_int) / SEGLEN_FACTOR;
121
122    float seg_len_real = d*aux_args.linfo->block_len;
123    float cum_len_real = cum_len*aux_args.linfo->block_len;
124
125    float PI = 0.0f;
126    if (cum_len_real > 1.0e-10f)
127    {
128        // retrieve albedo and normal probabilities
129        __global float16 *albedos = (__global float16*)&(aux_args.naa_apm[data_ptr*32]);
130        __global float16 *normal_weights = (__global float16*)&(aux_args.naa_apm[data_ptr*32 + 16]);
131
132        // compute mean and sigma of radiance value as linear function of albedo and albedo^2, respectively
133        float16 radiance_predictions = *aux_args.radiance_reflectance_factors * (*albedos) + *aux_args.radiance_offsets;
134        float16 radiance_variances = *aux_args.radiance_var_reflectance_sqrd_factors * (*albedos)*(*albedos) + *aux_args.radiance_var_offsets;
135        int16 invalid = islessequal(radiance_variances,(float16)0);
136        float16 radiance_sigmas = sqrt(radiance_variances);
137        float16 prediction_densities = gauss_prob_density_f16(&radiance_predictions, mean_obs, &radiance_sigmas);
138        // set prob. density to 0 for invalid normal directions
139        prediction_densities = select(prediction_densities,(float16)0,invalid);
140        // take weighted average based on surface normal probabilities
141        PI = dot(prediction_densities, *normal_weights);
142    }
143
144    //calculate this ray's contribution to beta
145    float ray_beta = ((*aux_args.ray_pre) + PI*(*aux_args.ray_vis))*seg_len_real/aux_args.norm;
146    float vis_cont = (*aux_args.ray_vis) * seg_len_real;
147
148    //update ray_pre and ray_vis
149    float temp  = exp(-alpha * seg_len_real);
150
151    // updated pre                      Omega         *  PI
152    (*aux_args.ray_pre) += (*aux_args.ray_vis)*(1.0f-temp)*PI;
153    // updated visibility probability
154    (*aux_args.ray_vis) *= temp;
155
156    //discretize and store beta and vis contribution
157    int beta_int = convert_int_rte(ray_beta * SEGLEN_FACTOR);
158    atom_add(&aux_args.beta_array[data_ptr], beta_int);
159    int vis_int  = convert_int_rte(vis_cont * SEGLEN_FACTOR);
160    atom_add(&aux_args.vis_array[data_ptr], vis_int);
161    //-------------------------------------------------------------------------- */
162
163    //reset cell_ptrs to -1 every time
164    aux_args.cell_ptrs[llid] = -1;
165}
166#endif // BAYES_NAA
167
168