44static float nextfr(
RNG *rng,
float min,
float max)
49static float gaussRand(
RNG *rng)
59 x =
float(nextfr(rng, -1, 1));
60 y =
float(nextfr(rng, -1, 1));
70MINLINE float catrom(
float p0,
float p1,
float p2,
float p3,
float f)
72 return 0.5f * ((2.0f * p1) + (-p0 + p2) * f + (2.0f * p0 - 5.0f * p1 + 4.0f * p2 - p3) * f * f +
73 (-p0 + 3.0f * p1 - 3.0f * p2 + p3) * f * f * f);
76MINLINE float omega(
float k,
float depth)
82static float Ph(
Ocean *o,
float kx,
float kz)
85 float k2 = kx * kx + kz * kz;
92 tmp = (o->_wx * kx + o->_wz * kz) /
sqrtf(k2);
94 tmp *= o->_damp_reflections;
97 return o->_A *
expf(-1.0f / (k2 * (o->_L * o->_L))) *
expf(-k2 * (o->_l * o->_l)) *
98 powf(
fabsf(tmp), o->_wind_alignment) / (k2 * k2);
101static void compute_eigenstuff(
OceanResult *ocr,
float jxx,
float jzz,
float jxz)
103 float a,
b, qplus, qminus;
105 b =
sqrt((jxx - jzz) * (jxx - jzz) + 4 * jxz * jxz);
108 ocr->
Jplus = 0.5f * (a +
b);
110 qplus = (ocr->
Jplus - jxx) / jxz;
111 qminus = (ocr->
Jminus - jxx) / jxz;
113 a =
sqrt(1 + qplus * qplus);
114 b =
sqrt(1 + qminus * qminus);
116 ocr->
Eplus[0] = 1.0f / a;
117 ocr->
Eplus[1] = 0.0f;
118 ocr->
Eplus[2] = qplus / a;
130static void init_complex(fftw_complex cmpl,
float real,
float image)
136static void add_comlex_c(fftw_complex res,
const fftw_complex cmpl1,
const fftw_complex cmpl2)
138 res[0] = cmpl1[0] + cmpl2[0];
139 res[1] = cmpl1[1] + cmpl2[1];
142static void mul_complex_f(fftw_complex res,
const fftw_complex cmpl,
float f)
144 res[0] = cmpl[0] *
double(f);
145 res[1] = cmpl[1] *
double(f);
148static void mul_complex_c(fftw_complex res,
const fftw_complex cmpl1,
const fftw_complex cmpl2)
151 temp[0] = cmpl1[0] * cmpl2[0] - cmpl1[1] * cmpl2[1];
152 temp[1] = cmpl1[0] * cmpl2[1] + cmpl1[1] * cmpl2[0];
157static float real_c(fftw_complex cmpl)
162static float image_c(fftw_complex cmpl)
167static void conj_complex(fftw_complex res,
const fftw_complex cmpl1)
173static void exp_complex(fftw_complex res, fftw_complex cmpl)
175 float r =
expf(cmpl[0]);
177 res[0] =
cosf(cmpl[1]) * r;
178 res[1] =
sinf(cmpl[1]) * r;
183 float foam = jminus * -0.005f + coverage;
184 CLAMP(foam, 0.0f, 1.0f);
191 float frac_x, frac_z;
226 interpf(interpf(m[i1 * oc->_N + j1], m[i0 * oc->_N + j1], frac_x), \
227 interpf(m[i1 * oc->_N + j0], m[i0 * oc->_N + j0], frac_x), \
231 if (oc->_do_disp_y) {
232 ocr->
disp[1] = BILERP(oc->_disp_y);
235 if (oc->_do_normals) {
236 ocr->
normal[0] = BILERP(oc->_N_x);
237 ocr->
normal[1] = oc->_N_y ;
238 ocr->
normal[2] = BILERP(oc->_N_z);
242 ocr->
disp[0] = BILERP(oc->_disp_x);
243 ocr->
disp[2] = BILERP(oc->_disp_z);
250 if (oc->_do_jacobian) {
251 compute_eigenstuff(ocr, BILERP(oc->_Jxx), BILERP(oc->_Jzz), BILERP(oc->_Jxz));
261 int i0, i1, i2, i3, j0, j1, j2, j3;
262 float frac_x, frac_z;
298 i0 = i0 < 0 ? i0 + oc->_M : i0;
299 i3 = i3 >= oc->_M ? i3 - oc->_M : i3;
303 j0 = j0 < 0 ? j0 + oc->_N : j0;
304 j3 = j3 >= oc->_N ? j3 - oc->_N : j3;
307 catrom(catrom(m[i0 * oc->_N + j0], \
308 m[i1 * oc->_N + j0], \
309 m[i2 * oc->_N + j0], \
310 m[i3 * oc->_N + j0], \
312 catrom(m[i0 * oc->_N + j1], \
313 m[i1 * oc->_N + j1], \
314 m[i2 * oc->_N + j1], \
315 m[i3 * oc->_N + j1], \
317 catrom(m[i0 * oc->_N + j2], \
318 m[i1 * oc->_N + j2], \
319 m[i2 * oc->_N + j2], \
320 m[i3 * oc->_N + j2], \
322 catrom(m[i0 * oc->_N + j3], \
323 m[i1 * oc->_N + j3], \
324 m[i2 * oc->_N + j3], \
325 m[i3 * oc->_N + j3], \
330 if (oc->_do_disp_y) {
331 ocr->
disp[1] = INTERP(oc->_disp_y);
333 if (oc->_do_normals) {
334 ocr->
normal[0] = INTERP(oc->_N_x);
335 ocr->
normal[1] = oc->_N_y ;
336 ocr->
normal[2] = INTERP(oc->_N_z);
339 ocr->
disp[0] = INTERP(oc->_disp_x);
340 ocr->
disp[2] = INTERP(oc->_disp_z);
347 if (oc->_do_jacobian) {
348 compute_eigenstuff(ocr, INTERP(oc->_Jxx), INTERP(oc->_Jzz), INTERP(oc->_Jxz));
373 ocr->
disp[1] = oc->_do_disp_y ?
float(oc->_disp_y[i * oc->_N + j]) : 0.0f;
376 ocr->
disp[0] = oc->_disp_x[i * oc->_N + j];
377 ocr->
disp[2] = oc->_disp_z[i * oc->_N + j];
384 if (oc->_do_normals) {
385 ocr->
normal[0] = oc->_N_x[i * oc->_N + j];
386 ocr->
normal[1] = oc->_N_y ;
387 ocr->
normal[2] = oc->_N_z[i * oc->_N + j];
392 if (oc->_do_jacobian) {
394 ocr, oc->_Jxx[i * oc->_N + j], oc->_Jzz[i * oc->_N + j], oc->_Jxz[i * oc->_N + j]);
400struct OceanSimulateData {
407static void ocean_compute_htilda(
void *__restrict userdata,
411 OceanSimulateData *osd =
static_cast<OceanSimulateData *
>(userdata);
412 const Ocean *o = osd->o;
413 const float scale = osd->scale;
414 const float t = osd->t;
420 for (j = 0; j <= o->_N / 2; j++) {
421 fftw_complex exp_param1;
422 fftw_complex exp_param2;
423 fftw_complex conj_param;
425 init_complex(exp_param1, 0.0, omega(o->_k[i * (1 + o->_N / 2) + j], o->_depth) * t);
426 init_complex(exp_param2, 0.0, -omega(o->_k[i * (1 + o->_N / 2) + j], o->_depth) * t);
427 exp_complex(exp_param1, exp_param1);
428 exp_complex(exp_param2, exp_param2);
429 conj_complex(conj_param, o->_h0_minus[i * o->_N + j]);
431 mul_complex_c(exp_param1, o->_h0[i * o->_N + j], exp_param1);
432 mul_complex_c(exp_param2, conj_param, exp_param2);
434 add_comlex_c(o->_htilda[i * (1 + o->_N / 2) + j], exp_param1, exp_param2);
435 mul_complex_f(o->_fft_in[i * (1 + o->_N / 2) + j], o->_htilda[i * (1 + o->_N / 2) + j], scale);
439static void ocean_compute_displacement_y(
TaskPool *__restrict pool,
void * )
442 const Ocean *o = osd->o;
444 fftw_execute(o->_disp_y_plan);
447static void ocean_compute_displacement_x(
TaskPool *__restrict pool,
void * )
450 const Ocean *o = osd->o;
451 const float scale = osd->scale;
452 const float chop_amount = osd->chop_amount;
455 for (i = 0; i < o->_M; i++) {
456 for (j = 0; j <= o->_N / 2; j++) {
457 fftw_complex mul_param;
458 fftw_complex minus_i;
460 init_complex(minus_i, 0.0, -1.0);
461 init_complex(mul_param, -scale, 0);
462 mul_complex_f(mul_param, mul_param, chop_amount);
463 mul_complex_c(mul_param, mul_param, minus_i);
464 mul_complex_c(mul_param, mul_param, o->_htilda[i * (1 + o->_N / 2) + j]);
465 mul_complex_f(mul_param,
467 ((o->_k[i * (1 + o->_N / 2) + j] == 0.0f) ?
469 o->_kx[i] / o->_k[i * (1 + o->_N / 2) + j]));
470 init_complex(o->_fft_in_x[i * (1 + o->_N / 2) + j], real_c(mul_param), image_c(mul_param));
473 fftw_execute(o->_disp_x_plan);
476static void ocean_compute_displacement_z(
TaskPool *__restrict pool,
void * )
479 const Ocean *o = osd->o;
480 const float scale = osd->scale;
481 const float chop_amount = osd->chop_amount;
484 for (i = 0; i < o->_M; i++) {
485 for (j = 0; j <= o->_N / 2; j++) {
486 fftw_complex mul_param;
487 fftw_complex minus_i;
489 init_complex(minus_i, 0.0, -1.0);
490 init_complex(mul_param, -scale, 0);
491 mul_complex_f(mul_param, mul_param, chop_amount);
492 mul_complex_c(mul_param, mul_param, minus_i);
493 mul_complex_c(mul_param, mul_param, o->_htilda[i * (1 + o->_N / 2) + j]);
494 mul_complex_f(mul_param,
496 ((o->_k[i * (1 + o->_N / 2) + j] == 0.0f) ?
498 o->_kz[j] / o->_k[i * (1 + o->_N / 2) + j]));
499 init_complex(o->_fft_in_z[i * (1 + o->_N / 2) + j], real_c(mul_param), image_c(mul_param));
502 fftw_execute(o->_disp_z_plan);
505static void ocean_compute_jacobian_jxx(
TaskPool *__restrict pool,
void * )
508 const Ocean *o = osd->o;
509 const float chop_amount = osd->chop_amount;
512 for (i = 0; i < o->_M; i++) {
513 for (j = 0; j <= o->_N / 2; j++) {
514 fftw_complex mul_param;
517 init_complex(mul_param, -1, 0);
519 mul_complex_f(mul_param, mul_param, chop_amount);
520 mul_complex_c(mul_param, mul_param, o->_htilda[i * (1 + o->_N / 2) + j]);
521 mul_complex_f(mul_param,
523 ((o->_k[i * (1 + o->_N / 2) + j] == 0.0f) ?
525 o->_kx[i] * o->_kx[i] / o->_k[i * (1 + o->_N / 2) + j]));
526 init_complex(o->_fft_in_jxx[i * (1 + o->_N / 2) + j], real_c(mul_param), image_c(mul_param));
529 fftw_execute(o->_Jxx_plan);
531 for (i = 0; i < o->_M; i++) {
532 for (j = 0; j < o->_N; j++) {
533 o->_Jxx[i * o->_N + j] += 1.0;
538static void ocean_compute_jacobian_jzz(
TaskPool *__restrict pool,
void * )
541 const Ocean *o = osd->o;
542 const float chop_amount = osd->chop_amount;
545 for (i = 0; i < o->_M; i++) {
546 for (j = 0; j <= o->_N / 2; j++) {
547 fftw_complex mul_param;
550 init_complex(mul_param, -1, 0);
552 mul_complex_f(mul_param, mul_param, chop_amount);
553 mul_complex_c(mul_param, mul_param, o->_htilda[i * (1 + o->_N / 2) + j]);
554 mul_complex_f(mul_param,
556 ((o->_k[i * (1 + o->_N / 2) + j] == 0.0f) ?
558 o->_kz[j] * o->_kz[j] / o->_k[i * (1 + o->_N / 2) + j]));
559 init_complex(o->_fft_in_jzz[i * (1 + o->_N / 2) + j], real_c(mul_param), image_c(mul_param));
562 fftw_execute(o->_Jzz_plan);
564 for (i = 0; i < o->_M; i++) {
565 for (j = 0; j < o->_N; j++) {
566 o->_Jzz[i * o->_N + j] += 1.0;
571static void ocean_compute_jacobian_jxz(
TaskPool *__restrict pool,
void * )
574 const Ocean *o = osd->o;
575 const float chop_amount = osd->chop_amount;
578 for (i = 0; i < o->_M; i++) {
579 for (j = 0; j <= o->_N / 2; j++) {
580 fftw_complex mul_param;
583 init_complex(mul_param, -1, 0);
585 mul_complex_f(mul_param, mul_param, chop_amount);
586 mul_complex_c(mul_param, mul_param, o->_htilda[i * (1 + o->_N / 2) + j]);
587 mul_complex_f(mul_param,
589 ((o->_k[i * (1 + o->_N / 2) + j] == 0.0f) ?
591 o->_kx[i] * o->_kz[j] / o->_k[i * (1 + o->_N / 2) + j]));
592 init_complex(o->_fft_in_jxz[i * (1 + o->_N / 2) + j], real_c(mul_param), image_c(mul_param));
595 fftw_execute(o->_Jxz_plan);
598static void ocean_compute_normal_x(
TaskPool *__restrict pool,
void * )
601 const Ocean *o = osd->o;
604 for (i = 0; i < o->_M; i++) {
605 for (j = 0; j <= o->_N / 2; j++) {
606 fftw_complex mul_param;
608 init_complex(mul_param, 0.0, -1.0);
609 mul_complex_c(mul_param, mul_param, o->_htilda[i * (1 + o->_N / 2) + j]);
610 mul_complex_f(mul_param, mul_param, o->_kx[i]);
611 init_complex(o->_fft_in_nx[i * (1 + o->_N / 2) + j], real_c(mul_param), image_c(mul_param));
614 fftw_execute(o->_N_x_plan);
617static void ocean_compute_normal_z(
TaskPool *__restrict pool,
void * )
620 const Ocean *o = osd->o;
623 for (i = 0; i < o->_M; i++) {
624 for (j = 0; j <= o->_N / 2; j++) {
625 fftw_complex mul_param;
627 init_complex(mul_param, 0.0, -1.0);
628 mul_complex_c(mul_param, mul_param, o->_htilda[i * (1 + o->_N / 2) + j]);
629 mul_complex_f(mul_param, mul_param, o->_kz[i]);
630 init_complex(o->_fft_in_nz[i * (1 + o->_N / 2) + j], real_c(mul_param), image_c(mul_param));
633 fftw_execute(o->_N_z_plan);
638 return o->_k !=
nullptr;
645 OceanSimulateData osd;
647 scale *= o->normalize_factor;
652 osd.chop_amount = chop_amount;
668 settings.use_threading = (o->_M > 16);
680 if (o->_do_jacobian) {
686 if (o->_do_normals) {
689 o->_N_y = 1.0f / scale;
699static void set_height_normalize_factor(
Ocean *oc)
706 if (!oc->_do_disp_y) {
710 oc->normalize_factor = 1.0;
716 for (i = 0; i < oc->_M; i++) {
717 for (j = 0; j < oc->_N; j++) {
718 if (max_h <
fabs(oc->_disp_y[i * oc->_N + j])) {
719 max_h =
fabs(oc->_disp_y[i * oc->_N + j]);
730 res = 1.0f / (max_h);
732 oc->normalize_factor = res;
748 if (omd->
ocean->_M == resolution * resolution) {
762 short do_heightfield, do_chop, do_normals, do_jacobian, do_spray;
764 do_heightfield =
true;
773 resolution * resolution,
774 resolution * resolution,
811 float sharpen_peak_jonswap,
812 short do_height_field,
829 o->_damp_reflections = 1.0f - damp;
830 o->_wind_alignment = alignment * 10.0f;
836 o->_L =
V *
V / GRAVITY;
840 o->_spectrum = spectrum;
843 o->_fetch_jonswap = fetch_jonswap;
844 o->_sharpen_peak_jonswap = sharpen_peak_jonswap * 10.0f;
849 if ((o->_k = (
float *)
MEM_mallocN(
sizeof(
float) *
size_t(
M) * (1 +
N / 2),
"ocean_k")) &&
850 (o->_h0 = (fftw_complex *)
MEM_mallocN(
sizeof(fftw_complex) *
size_t(
M) *
N,
"ocean_h0")) &&
851 (o->_h0_minus = (fftw_complex *)
MEM_mallocN(
sizeof(fftw_complex) *
size_t(
M) *
N,
852 "ocean_h0_minus")) &&
853 (o->_kx = (
float *)
MEM_mallocN(
sizeof(
float) * o->_M,
"ocean_kx")) &&
854 (o->_kz = (
float *)
MEM_mallocN(
sizeof(
float) * o->_N,
"ocean_kz")))
869 o->_do_disp_y = do_height_field;
870 o->_do_normals = do_normals;
871 o->_do_spray = do_spray;
872 o->_do_chop = do_chop;
873 o->_do_jacobian = do_jacobian;
876 if (o->_Lx == 0.0f) {
880 if (o->_Lz == 0.0f) {
885 for (i = 0; i <= o->_M / 2; i++) {
886 o->_kx[i] = 2.0f *
float(
M_PI) * i / o->_Lx;
890 for (i = o->_M - 1, ii = 0; i > o->_M / 2; i--, ii++) {
891 o->_kx[i] = -2.0f *
float(
M_PI) * ii / o->_Lx;
895 for (i = 0; i <= o->_N / 2; i++) {
896 o->_kz[i] = 2.0f *
float(
M_PI) * i / o->_Lz;
900 for (i = o->_N - 1, ii = 0; i > o->_N / 2; i--, ii++) {
901 o->_kz[i] = -2.0f *
float(
M_PI) * ii / o->_Lz;
905 for (i = 0; i < o->_M; i++) {
906 for (j = 0; j <= o->_N / 2; j++) {
907 o->_k[size_t(i) * (1 + o->_N / 2) + j] =
sqrt(o->_kx[i] * o->_kx[i] + o->_kz[j] * o->_kz[j]);
913 for (i = 0; i < o->_M; i++) {
914 for (j = 0; j < o->_N; j++) {
919 const int hash_x = o->_kx[i] * 360.0f;
920 const int hash_z = o->_kz[j] * 360.0f;
924 float r1 = gaussRand(rng);
925 float r2 = gaussRand(rng);
928 init_complex(r1r2, r1, r2);
929 switch (o->_spectrum) {
931 mul_complex_f(o->_h0[i * o->_N + j],
934 mul_complex_f(o->_h0_minus[i * o->_N + j],
940 o->_h0[i * o->_N + j],
944 o->_h0_minus[i * o->_N + j],
950 o->_h0[i * o->_N + j],
954 o->_h0_minus[i * o->_N + j],
960 o->_h0[i * o->_N + j], r1r2,
float(sqrt(Ph(o, o->_kx[i], o->_kz[j]) / 2.0f)));
961 mul_complex_f(o->_h0_minus[i * o->_N + j],
963 float(sqrt(Ph(o, -o->_kx[i], -o->_kz[j]) / 2.0f)));
969 o->_fft_in = (fftw_complex *)
MEM_mallocN(o->_M * (1 + o->_N / 2) *
sizeof(fftw_complex),
971 o->_htilda = (fftw_complex *)
MEM_mallocN(o->_M * (1 + o->_N / 2) *
sizeof(fftw_complex),
977 o->_disp_y = (
double *)
MEM_mallocN(o->_M * o->_N *
sizeof(
double),
"ocean_disp_y");
978 o->_disp_y_plan = fftw_plan_dft_c2r_2d(o->_M, o->_N, o->_fft_in, o->_disp_y, FFTW_ESTIMATE);
981 if (o->_do_normals) {
982 o->_fft_in_nx = (fftw_complex *)
MEM_mallocN(o->_M * (1 + o->_N / 2) *
sizeof(fftw_complex),
984 o->_fft_in_nz = (fftw_complex *)
MEM_mallocN(o->_M * (1 + o->_N / 2) *
sizeof(fftw_complex),
987 o->_N_x = (
double *)
MEM_mallocN(o->_M * o->_N *
sizeof(
double),
"ocean_N_x");
989 o->_N_z = (
double *)
MEM_mallocN(o->_M * o->_N *
sizeof(
double),
"ocean_N_z");
991 o->_N_x_plan = fftw_plan_dft_c2r_2d(o->_M, o->_N, o->_fft_in_nx, o->_N_x, FFTW_ESTIMATE);
992 o->_N_z_plan = fftw_plan_dft_c2r_2d(o->_M, o->_N, o->_fft_in_nz, o->_N_z, FFTW_ESTIMATE);
996 o->_fft_in_x = (fftw_complex *)
MEM_mallocN(o->_M * (1 + o->_N / 2) *
sizeof(fftw_complex),
998 o->_fft_in_z = (fftw_complex *)
MEM_mallocN(o->_M * (1 + o->_N / 2) *
sizeof(fftw_complex),
1001 o->_disp_x = (
double *)
MEM_mallocN(o->_M * o->_N *
sizeof(
double),
"ocean_disp_x");
1002 o->_disp_z = (
double *)
MEM_mallocN(o->_M * o->_N *
sizeof(
double),
"ocean_disp_z");
1004 o->_disp_x_plan = fftw_plan_dft_c2r_2d(o->_M, o->_N, o->_fft_in_x, o->_disp_x, FFTW_ESTIMATE);
1005 o->_disp_z_plan = fftw_plan_dft_c2r_2d(o->_M, o->_N, o->_fft_in_z, o->_disp_z, FFTW_ESTIMATE);
1007 if (o->_do_jacobian) {
1008 o->_fft_in_jxx = (fftw_complex *)
MEM_mallocN(o->_M * (1 + o->_N / 2) *
sizeof(fftw_complex),
1009 "ocean_fft_in_jxx");
1010 o->_fft_in_jzz = (fftw_complex *)
MEM_mallocN(o->_M * (1 + o->_N / 2) *
sizeof(fftw_complex),
1011 "ocean_fft_in_jzz");
1012 o->_fft_in_jxz = (fftw_complex *)
MEM_mallocN(o->_M * (1 + o->_N / 2) *
sizeof(fftw_complex),
1013 "ocean_fft_in_jxz");
1015 o->_Jxx = (
double *)
MEM_mallocN(o->_M * o->_N *
sizeof(
double),
"ocean_Jxx");
1016 o->_Jzz = (
double *)
MEM_mallocN(o->_M * o->_N *
sizeof(
double),
"ocean_Jzz");
1017 o->_Jxz = (
double *)
MEM_mallocN(o->_M * o->_N *
sizeof(
double),
"ocean_Jxz");
1019 o->_Jxx_plan = fftw_plan_dft_c2r_2d(o->_M, o->_N, o->_fft_in_jxx, o->_Jxx, FFTW_ESTIMATE);
1020 o->_Jzz_plan = fftw_plan_dft_c2r_2d(o->_M, o->_N, o->_fft_in_jzz, o->_Jzz, FFTW_ESTIMATE);
1021 o->_Jxz_plan = fftw_plan_dft_c2r_2d(o->_M, o->_N, o->_fft_in_jxz, o->_Jxz, FFTW_ESTIMATE);
1028 set_height_normalize_factor(o);
1045 if (oc->_do_disp_y) {
1046 fftw_destroy_plan(oc->_disp_y_plan);
1050 if (oc->_do_normals) {
1053 fftw_destroy_plan(oc->_N_x_plan);
1054 fftw_destroy_plan(oc->_N_z_plan);
1063 fftw_destroy_plan(oc->_disp_x_plan);
1064 fftw_destroy_plan(oc->_disp_z_plan);
1069 if (oc->_do_jacobian) {
1073 fftw_destroy_plan(oc->_Jxx_plan);
1074 fftw_destroy_plan(oc->_Jzz_plan);
1075 fftw_destroy_plan(oc->_Jxz_plan);
1116# define CACHE_TYPE_DISPLACE 1
1117# define CACHE_TYPE_FOAM 2
1118# define CACHE_TYPE_NORMAL 3
1119# define CACHE_TYPE_SPRAY 4
1120# define CACHE_TYPE_SPRAY_INVERSE 5
1122static void cache_filepath(
1123 char *filepath,
const char *
dirname,
const char *relbase,
int frame,
int type)
1126 const char *filename;
1129 case CACHE_TYPE_FOAM:
1132 case CACHE_TYPE_NORMAL:
1133 filename =
"normal_";
1135 case CACHE_TYPE_SPRAY:
1136 filename =
"spray_";
1138 case CACHE_TYPE_SPRAY_INVERSE:
1139 filename =
"spray_inverse_";
1141 case CACHE_TYPE_DISPLACE:
1154MINLINE void rgb_to_rgba_unit_alpha(
float r_rgba[4],
const float rgb[3])
1161MINLINE void value_to_rgba_unit_alpha(
float r_rgba[4],
const float value)
1178 for (i = och->
start, f = 0; i <= och->
end; i++, f++) {
1187 for (i = och->
start, f = 0; i <= och->
end; i++, f++) {
1196 for (i = och->
start, f = 0; i <= och->
end; i++, f++) {
1205 for (i = och->
start, f = 0; i <= och->
end; i++, f++) {
1214 for (i = och->
start, f = 0; i <= och->
end; i++, f++) {
1251 ocr->
foam = result[0];
1308 const char *relbase,
1313 float foam_coverage,
1343 och->
time =
nullptr;
1355 const int f = frame - och->
start;
1365 cache_filepath(filepath, och->
bakepath, och->
relbase, frame, CACHE_TYPE_DISPLACE);
1368 cache_filepath(filepath, och->
bakepath, och->
relbase, frame, CACHE_TYPE_FOAM);
1371 cache_filepath(filepath, och->
bakepath, och->
relbase, frame, CACHE_TYPE_SPRAY);
1374 cache_filepath(filepath, och->
bakepath, och->
relbase, frame, CACHE_TYPE_SPRAY_INVERSE);
1377 cache_filepath(filepath, och->
bakepath, och->
relbase, frame, CACHE_TYPE_NORMAL);
1383 void (*update_cb)(
void *,
float progress,
int *cancel),
1384 void *update_cb_data)
1392 int f, i = 0,
x,
y, cancel = 0;
1395 ImBuf *ibuf_foam, *ibuf_disp, *ibuf_normal, *ibuf_spray, *ibuf_spray_inverse;
1406 if (o->_do_jacobian) {
1407 prev_foam =
static_cast<float *
>(
1408 MEM_callocN(res_x * res_y *
sizeof(
float),
"previous frame foam bake data"));
1411 prev_foam =
nullptr;
1421 for (f = och->
start, i = 0; f <= och->
end; f++, i++) {
1433 for (y = 0; y < res_y; y++) {
1434 for (x = 0; x < res_x; x++) {
1441 if (o->_do_jacobian) {
1444 float pr = 0.0f, foam_result;
1445 float neg_disp, neg_eplus;
1451 pr = prev_foam[res_x * y +
x];
1462 neg_disp = ocr.
disp[1] < 0.0f ? 1.0f + ocr.
disp[1] : 1.0f;
1463 neg_disp = neg_disp < 0.0f ? 0.0f : neg_disp;
1466 neg_eplus = ocr.
Eplus[2] < 0.0f ? 1.0f + ocr.
Eplus[2] : 1.0f;
1467 neg_eplus = neg_eplus < 0.0f ? 0.0f : neg_eplus;
1473 pr *= och->
foam_fade * (0.75f + neg_eplus * 0.25f);
1478 prev_foam[res_x * y +
x] = foam_result;
1482 value_to_rgba_unit_alpha(&ibuf_foam->
float_buffer.
data[4 * (res_x * y + x)],
1488 rgb_to_rgba_unit_alpha(&ibuf_spray_inverse->
float_buffer.
data[4 * (res_x * y + x)],
1493 if (o->_do_normals) {
1500 cache_filepath(filepath, och->
bakepath, och->
relbase, f, CACHE_TYPE_DISPLACE);
1502 printf(
"Cannot save Displacement File Output to %s\n", filepath);
1505 if (o->_do_jacobian) {
1506 cache_filepath(filepath, och->
bakepath, och->
relbase, f, CACHE_TYPE_FOAM);
1508 printf(
"Cannot save Foam File Output to %s\n", filepath);
1512 cache_filepath(filepath, och->
bakepath, och->
relbase, f, CACHE_TYPE_SPRAY);
1514 printf(
"Cannot save Spray File Output to %s\n", filepath);
1517 cache_filepath(filepath, och->
bakepath, och->
relbase, f, CACHE_TYPE_SPRAY_INVERSE);
1519 printf(
"Cannot save Spray Inverse File Output to %s\n", filepath);
1524 if (o->_do_normals) {
1525 cache_filepath(filepath, och->
bakepath, och->
relbase, f, CACHE_TYPE_NORMAL);
1527 printf(
"Cannot save Normal File Output to %s\n", filepath);
1539 update_cb(update_cb_data, progress, &cancel);
1660 void (*update_cb)(
void *,
float progress,
int *cancel),
bool BKE_imbuf_write(ImBuf *ibuf, const char *filepath, const ImageFormatData *imf)
bool BKE_ocean_ensure(struct OceanModifierData *omd, int resolution)
float BLI_ocean_spectrum_piersonmoskowitz(const struct Ocean *oc, float kx, float kz)
float BLI_ocean_spectrum_jonswap(const struct Ocean *oc, float kx, float kz)
bool BKE_ocean_is_valid(const struct Ocean *o)
float BLI_ocean_spectrum_texelmarsenarsloe(const struct Ocean *oc, float kx, float kz)
BLI_INLINE unsigned int BLI_hash_int_2d(unsigned int kx, unsigned int ky)
MINLINE float min_ff(float a, float b)
MINLINE void copy_v3_v3(float r[3], const float a[3])
MINLINE float normalize_v3(float n[3])
#define BLI_path_join(...)
struct RNG * BLI_rng_new(unsigned int seed)
void BLI_rng_free(struct RNG *rng) ATTR_NONNULL(1)
void BLI_rng_seed(struct RNG *rng, unsigned int seed) ATTR_NONNULL(1)
float BLI_rng_get_float(struct RNG *rng) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL(1)
void * BLI_task_pool_user_data(TaskPool *pool)
void BLI_task_pool_work_and_wait(TaskPool *pool)
void BLI_task_parallel_range(int start, int stop, void *userdata, TaskParallelRangeFunc func, const TaskParallelSettings *settings)
TaskPool * BLI_task_pool_create(void *userdata, eTaskPriority priority)
BLI_INLINE void BLI_parallel_range_settings_defaults(TaskParallelSettings *settings)
void BLI_task_pool_free(TaskPool *pool)
void BLI_task_pool_push(TaskPool *pool, TaskRunFunction run, void *taskdata, bool free_taskdata, TaskFreeFunction freedata)
void BLI_rw_mutex_end(ThreadRWMutex *mutex)
void BLI_thread_unlock(int type)
void BLI_thread_lock(int type)
#define THREAD_LOCK_WRITE
void BLI_rw_mutex_lock(ThreadRWMutex *mutex, int mode)
void BLI_rw_mutex_init(ThreadRWMutex *mutex)
void BLI_rw_mutex_unlock(ThreadRWMutex *mutex)
const char * dirname(char *path)
typedef double(DMatrix)[4][4]
@ MOD_OCEAN_GENERATE_NORMALS
@ MOD_OCEAN_GENERATE_FOAM
@ MOD_OCEAN_GENERATE_SPRAY
@ MOD_OCEAN_SPECTRUM_TEXEL_MARSEN_ARSLOE
@ MOD_OCEAN_SPECTRUM_JONSWAP
@ MOD_OCEAN_SPECTRUM_PIERSON_MOSKOWITZ
ImBuf * IMB_loadiffname(const char *filepath, int flags, char colorspace[IM_MAX_SPACE])
Contains defines and structs used throughout the imbuf module.
Read Guarded memory(de)allocation.
ATTR_WARN_UNUSED_RESULT const BMLoop * l
ATTR_WARN_UNUSED_RESULT const BMVert * v
SIMD_FORCE_INLINE const btScalar & z() const
Return the z value.
SIMD_FORCE_INLINE const btScalar & w() const
Return the w value.
static unsigned long seed
SIMD_FORCE_INLINE btScalar length2() const
Return the length of the vector squared.
input_tx image(0, GPU_RGBA16F, Qualifier::WRITE, ImageType::FLOAT_2D, "preview_img") .compute_source("compositor_compute_preview.glsl") .do_static_compilation(true)
local_group_size(16, 16) .push_constant(Type b
draw_view in_light_buf[] float
draw_view push_constant(Type::INT, "radiance_src") .push_constant(Type capture_info_buf storage_buf(1, Qualifier::READ, "ObjectBounds", "bounds_buf[]") .push_constant(Type draw_view int
struct ImBuf * IMB_allocImBuf(unsigned int, unsigned int, unsigned char, unsigned int)
void IMB_freeImBuf(ImBuf *)
void *(* MEM_mallocN)(size_t len, const char *str)
void MEM_freeN(void *vmemh)
void *(* MEM_callocN)(size_t len, const char *str)
ccl_device_inline float2 fmod(const float2 a, const float b)
ccl_device_inline float2 floor(const float2 a)
ccl_device_inline float2 fabs(const float2 a)
ccl_device_inline float3 cos(float3 v)
T sin(const AngleRadianBase< T > &a)
bool BKE_ocean_init_from_modifier(Ocean *, OceanModifierData const *, int)
bool BKE_ocean_init(Ocean *, int, int, float, float, float, float, float, float, float, float, float, float, int, float, float, short, short, short, short, short, int)
void BKE_ocean_eval_ij(Ocean *, OceanResult *, int, int)
OceanCache * BKE_ocean_init_cache(const char *, const char *, int, int, float, float, float, float, int)
void BKE_ocean_free_cache(OceanCache *och)
float BKE_ocean_jminus_to_foam(float, float)
void BKE_ocean_free_modifier_cache(OceanModifierData *omd)
void BKE_ocean_bake(Ocean *, OceanCache *, void(*update_cb)(void *, float progress, int *cancel), void *)
void BKE_ocean_free_data(Ocean *)
void BKE_ocean_cache_eval_ij(OceanCache *, OceanResult *, int, int, int)
void BKE_ocean_free(Ocean *oc)
void BKE_ocean_eval_xz(Ocean *, OceanResult *, float, float)
void BKE_ocean_eval_uv_catrom(Ocean *, OceanResult *, float, float)
void BKE_ocean_eval_uv(Ocean *, OceanResult *, float, float)
void BKE_ocean_simulate_cache(OceanCache *, int)
void BKE_ocean_eval_xz_catrom(Ocean *, OceanResult *, float, float)
void BKE_ocean_cache_eval_uv(OceanCache *, OceanResult *, int, float, float)
void BKE_ocean_simulate(Ocean *, float, float, float)
ImBufFloatBuffer float_buffer
struct ImBuf ** ibufs_disp
struct ImBuf ** ibufs_spray
struct ImBuf ** ibufs_norm
struct ImBuf ** ibufs_foam
struct ImBuf ** ibufs_spray_inverse
struct OceanCache * oceancache
float sharpen_peak_jonswap
void ibuf_sample(ImBuf *ibuf, float fx, float fy, float dx, float dy, float result[4])
ccl_device_inline int abs(int x)
CCL_NAMESPACE_BEGIN struct Window V