66 #define IMAGE_VAL(x,y,c,w,n,mem) (mem[x*n + y*w*n + c]) 70 void ScaleBilnear(
double* src,
double* dst,
int w,
int h,
int neww,
int newh,
double multiplyval = 1.0);
71 void reArrangeChannel(std::vector<double*>& src,
double* dst,
int pnx,
int pny,
int chnum);
72 void rotateCCW180(
double* src,
double* dst,
int pnx,
int pny,
double mulival = 1.0);
84 LOG(
"<FAILED> Wrong file ext.\n");
91 LOG(
"<FAILED> Loading file (%d)\n", ret);
98 char szNodeName[32] = { 0, };
99 sprintf(szNodeName,
"SLM_WaveNum");
101 if (!next ||
XML_SUCCESS != next->QueryIntText(&nWave))
103 LOG(
"<FAILED> Not found node : \'%s\' (Integer) \n", szNodeName);
111 for (
int i = 1; i <= nWave; i++) {
112 sprintf(szNodeName,
"SLM_WaveLength_%d", i);
116 LOG(
"<FAILED> Not found node : \'%s\' (Double) \n", szNodeName);
121 sprintf(szNodeName,
"SLM_PixelNumX");
125 LOG(
"<FAILED> Not found node : \'%s\' (Integer) \n", szNodeName);
129 sprintf(szNodeName,
"SLM_PixelNumY");
133 LOG(
"<FAILED> Not found node : \'%s\' (Integer) \n", szNodeName);
137 sprintf(szNodeName,
"SLM_PixelPitchX");
141 LOG(
"<FAILED> Not found node : \'%s\' (Double) \n", szNodeName);
145 sprintf(szNodeName,
"SLM_PixelPitchY");
149 LOG(
"<FAILED> Not found node : \'%s\' (Double) \n", szNodeName);
164 if (!next ||
XML_SUCCESS != next->QueryDoubleText(&rec_config.EyeLength))
167 if (!next ||
XML_SUCCESS != next->QueryDoubleText(&rec_config.EyePupilDiaMeter))
170 if (!next ||
XML_SUCCESS != next->QueryDoubleText(&rec_config.EyeBoxSizeScale))
173 if (!next ||
XML_SUCCESS != next->QueryDoubleText(&rec_config.EyeBoxSize[
_X]))
176 if (!next ||
XML_SUCCESS != next->QueryDoubleText(&rec_config.EyeBoxSize[
_Y]))
179 if (!next ||
XML_SUCCESS != next->QueryIntText(&rec_config.EyeBoxUnit))
182 if (!next ||
XML_SUCCESS != next->QueryDoubleText(&rec_config.EyeCenter[
_X]))
185 if (!next ||
XML_SUCCESS != next->QueryDoubleText(&rec_config.EyeCenter[
_Y]))
188 if (!next ||
XML_SUCCESS != next->QueryDoubleText(&rec_config.EyeCenter[
_Z]))
191 if (!next ||
XML_SUCCESS != next->QueryDoubleText(&rec_config.EyeFocusDistance))
194 if (!next ||
XML_SUCCESS != next->QueryDoubleText(&rec_config.ResultSizeScale))
197 if (!next ||
XML_SUCCESS != next->QueryDoubleText(&rec_config.SimulationTo))
200 if (!next ||
XML_SUCCESS != next->QueryDoubleText(&rec_config.SimulationFrom))
203 if (!next ||
XML_SUCCESS != next->QueryIntText(&rec_config.SimulationStep))
206 if (!next ||
XML_SUCCESS != next->QueryIntText(&rec_config.SimulationMode))
209 if (!next ||
XML_SUCCESS != next->QueryDoubleText(&rec_config.RatioAtRetina))
212 if (!next ||
XML_SUCCESS != next->QueryDoubleText(&rec_config.RatioAtPupil))
215 if (!next ||
XML_SUCCESS != next->QueryBoolText(&rec_config.CreatePupilFieldImg))
218 if (!next ||
XML_SUCCESS != next->QueryBoolText(&rec_config.CenteringRetinaImg))
224 rec_config.EyeBoxSize = rec_config.EyeBoxSizeScale * rec_config.EyePupilDiaMeter * rec_config.EyeBoxSize;
232 LOG(
"**************************************************\n");
233 LOG(
" Read Config (Common) \n");
239 LOG(
"4) Image Rotate : %s\n",
imgCfg.
rotate ?
"Y" :
"N");
243 LOG(
"6) Image Merge : %s\n",
imgCfg.
merge ?
"Y" :
"N");
244 LOG(
"**************************************************\n");
253 const int N = pnX * pnY;
260 int nSize = nLine *
h;
264 LOG(
"Failed::Image Load: %s\n", path);
267 LOG(
"Succeed::Image Load: %s\n", path);
270 memset(tmp, 0,
sizeof(
char) * nSize);
272 if (
w != pnX ||
h != pnY)
278 memcpy(tmp, imgload,
sizeof(
char) * nSize);
285 for (
int i = 0; i < N; i++)
300 const int N = pnX * pnY;
307 int nSize = nLine *
h;
311 LOG(
"Failed::Image Load: %s\n", phase);
314 LOG(
"Succeed::Image Load: %s\n", phase);
317 memset(phaseTmp, 0,
sizeof(
char) * nSize);
319 if (
w != pnX ||
h != pnY)
325 memcpy(phaseTmp, imgload,
sizeof(
char) * nSize);
338 LOG(
"Failed::Image Load: %s\n", amplitude);
341 LOG(
"Succeed::Image Load: %s\n", amplitude);
344 memset(ampTmp, 0,
sizeof(
char) * nSize);
346 if (
w != pnX ||
h != pnY)
352 memcpy(ampTmp, imgload,
sizeof(
char) * nSize);
361 for (
int i = 0; i < N; i++)
366 p = p / 255.0 * PI2 -
M_PI;
384 const int N = pnX * pnY;
391 int nSize = nLine *
h;
395 LOG(
"Failed::Image Load: %s\n", real);
398 LOG(
"Succeed::Image Load: %s\n", real);
401 memset(realTmp, 0,
sizeof(
char) * nSize);
403 if (
w != pnX ||
h != pnY)
409 memcpy(realTmp, imgload,
sizeof(
char) * nSize);
421 LOG(
"Failed::Image Load: %s\n", imag);
424 LOG(
"Succeed::Image Load: %s\n", imag);
427 memset(imagTmp, 0,
sizeof(
char) * nSize);
429 if (
w != pnX ||
h != pnY)
435 memcpy(imagTmp, imgload,
sizeof(
char) * nSize);
442 for (
int i = 0; i < N; i++)
456 LOG(
"Propagation to observer plane\n");
461 field_set_.resize(channel);
462 pp_set_.resize(channel);
463 fftw_complex *in =
nullptr;
464 fftw_complex *out =
nullptr;
467 for (
int ch = 0; ch < channel; ch++)
472 fftw_destroy_plan(fftw_plan_fwd);
477 LOG(
"Propagation to observer plane\n");
482 const int N = pnX * pnY;
486 field_set_.resize(nChannel);
487 pn_set_.resize(nChannel);
488 pp_set_.resize(nChannel);
490 fftw_complex *in =
nullptr, *out =
nullptr;
497 Real ssX = pnX * ppX;
498 Real ssY = pnY * ppY;
501 for (
int ctr = 0; ctr < nChannel; ctr++)
503 LOG(
"Color Number: %d\n", ctr + 1);
512 Real kk = k / (prop_z * 2);
513 Real kpropz = k * prop_z;
514 Real lambdapropz = lambda * prop_z;
515 Real ss_res_x = fabs(lambdapropz / ppX);
516 Real ss_res_y = fabs(lambdapropz / ppY);
517 Real hss_res_x = ss_res_x / 2.0;
518 Real hss_res_y = ss_res_y / 2.0;
519 Real pp_res_x = ss_res_x /
Real(pnX);
520 Real pp_res_y = ss_res_y /
Real(pnY);
521 Real absppX = fabs(lambdapropz / (4 * ppX));
522 Real absppY = fabs(lambdapropz / (4 * ppY));
525 #pragma omp parallel for private(loopi) 526 for (loopi = 0; loopi < N; loopi++)
531 double xx_src = (-ssX / 2.0) + (ppX * double(x));
532 double yy_src = (ssY / 2.0) - ppY - (ppY * double(y));
534 if (f_field != prop_z)
536 double effective_f = f_field * prop_z / (f_field - prop_z);
537 double sval = (xx_src*xx_src) + (yy_src*yy_src);
538 sval *=
M_PI / lambda / effective_f;
543 double anti_aliasing_mask = fabs(xx_src) < fabs(lambda*effective_f / (4 * ppX)) ? 1 : 0;
544 anti_aliasing_mask *= fabs(yy_src) < fabs(lambda*effective_f / (4 * ppY)) ? 1 : 0;
546 field_set_[ctr][x + y * pnX] = u[x + y * pnX] * kernel * anti_aliasing_mask;
552 field_set_[ctr][x + y * pnX] = u[x + y * pnX];
563 #pragma omp parallel for private(loopi) 564 for (loopi = 0; loopi < N; loopi++)
569 double xx_res = (-ss_res_x / 2.0) + (pp_res_x * double(x));
570 double yy_res = (ss_res_y / 2.0) - pp_res_y - (pp_res_y * double(y));
578 double ssval = (xx_res*xx_res) + (yy_res*yy_res);
579 ssval *= k / (2 * prop_z);
586 field_set_[ctr][x + y * pnX] *= coeff;
589 pp_set_[ctr][0] = pp_res_x;
590 pp_set_[ctr][1] = pp_res_y;
594 fftw_destroy_plan(fft_plan_fwd);
601 const int N = pnX * pnY;
610 const Real simGap = (simStep > 1) ? (simTo - simFrom) / (simStep - 1) : 0;
612 const Real tx = 1 / ppX;
613 const Real ty = 1 / ppY;
614 const Real dx = tx / pnX;
615 const Real dy = ty / pnY;
617 const Real htx = tx / 2;
618 const Real hty = ty / 2;
619 const Real hdx = dx / 2;
620 const Real hdy = dy / 2;
621 const Real baseX = -htx + hdx;
622 const Real baseY = -hty + hdy;
628 for (
int i = 0; i < nWave; i++)
633 LOG(
"%s : Get Spatial Kernel\n", __FUNCTION__);
635 for (
int ch = 0; ch < nWave; ch++)
644 #pragma omp parallel for private(i) firstprivate(pnX, lambda, dx, dy, baseX, baseY) 646 for (i = 0; i < N; i++)
651 Real curX = baseX + (x * dx);
652 Real curY = baseY + (y * dy);
653 Real xx = curX * lambda;
654 Real yy = curY * lambda;
655 Real powxx = xx * xx;
656 Real powyy = yy * yy;
658 kernels[ch][i][
_RE] = 0;
659 kernels[ch][i][
_IM] = sqrt(1 - powxx - powyy);
663 LOG(
"%s : Simultation\n", __FUNCTION__);
666 for (
int step = 0; step < simStep; step++)
669 for (
int ch = 0; ch < nWave; ch++)
675 Real z = simFrom + (step * simGap);
684 for (
int i = 0; i < N; i++)
694 for (
int i = 0; i < N; i++)
696 encode[i] = dst[i].
mag();
704 m_vecEncoded.push_back(encode);
705 m_vecNormalized.push_back(normal);
708 LOG(
"step: %d => max: %e / min: %e\n", step, max, min);
711 for (
int ch = 0; ch < nWave; ch++)
713 int idx = step * nWave + ch;
714 normalize(m_vecEncoded[idx], m_vecNormalized[idx], pnX, pnY, max, min);
718 normalize(m_vecEncoded[step], m_vecNormalized[step], pnX, pnY);
721 m_oldSimStep = simStep;
725 for (
int i = 0; i < nWave; i++)
736 LOG(
"Color Number: %d\n", chnum + 1);
740 const int N = pnX * pnY;
746 Real ssX = pnX * ppX;
747 Real ssY = pnY * ppY;
748 Real hssX = ssX / 2.0;
749 Real hssY = ssY / 2.0;
754 Real kk = k / (prop_z * 2);
755 Real kpropz = k * prop_z;
756 Real lambdapropz = lambda * prop_z;
757 Real ss_res_x = fabs(lambdapropz / ppX);
758 Real ss_res_y = fabs(lambdapropz / ppY);
759 Real hss_res_x = ss_res_x / 2.0;
760 Real hss_res_y = ss_res_y / 2.0;
761 Real pp_res_x = ss_res_x /
Real(pnX);
762 Real pp_res_y = ss_res_y /
Real(pnY);
771 Real absppX = fabs(lambdapropz / (ppX4));
772 Real absppY = fabs(lambdapropz / (ppY4));
775 #pragma omp parallel for private(i) 776 for (i = 0; i < N; i++)
781 Real xx_src = -hssX + (ppX *
Real(x));
782 Real yy_src = hssY - ppY - (ppY *
Real(y));
783 Real xxx = xx_src - cxy[
_X];
784 Real yyy = yy_src - cxy[
_Y];
786 Real sval = xxx * xxx + yyy * yyy;
792 Real anti_aliasing_mask = fabs(xxx) < absppX ? 1 : 0;
793 anti_aliasing_mask *= fabs(yyy) < absppY ? 1 : 0;
795 field_set_[chnum][x + y * pnX] = tmp[x + y * pnX] * kernel * anti_aliasing_mask;
803 #pragma omp parallel for private(i) 804 for (i = 0; i < N; i++)
809 Real xx_res = -hss_res_x + (pp_res_x *
Real(x));
810 Real yy_res = hss_res_y - pp_res_y - (pp_res_y *
Real(y));
811 Real xxx = xx_res - cxy[
_X];
812 Real yyy = yy_res - cxy[
_Y];
820 Real ssval = xxx * xxx + yyy * yyy;
828 field_set_[chnum][x + y * pnX] *= coeff;
833 pp_set_[chnum][
_X] = pp_res_x;
834 pp_set_[chnum][
_Y] = pp_res_y;
839 LOG(
"Simulation start\n");
861 memcpy(&bSimPos[0], rec_config.
SimulationPos,
sizeof(bSimPos));
864 std::vector<vec3> var_vals;
865 var_vals.resize(simStep);
869 var_step = (simTo - simFrom) / (simStep - 1);
870 for (
int i = 0; i < simStep; i++)
871 var_vals[i] = simFrom + var_step * i;
875 var_vals[0] = (simTo + simFrom) / 2.0;
879 Real pp_e_x, pp_e_y, ss_e_x, ss_e_y;
881 Real pp_p_x, pp_p_y, ss_p_x, ss_p_y;
882 vec2 eye_box_range_x, eye_box_range_y;
883 ivec2 eye_box_range_idx, eye_box_range_idy;
884 ivec2 eye_shift_by_pn;
886 field_ret_set_.resize(nChannel);
887 pn_ret_set_.resize(nChannel);
888 pp_ret_set_.resize(nChannel);
889 ss_ret_set_.resize(nChannel);
890 recon_set.resize(simStep * nChannel);
891 img_set.resize(simStep * nChannel);
892 img_size.resize(simStep * nChannel);
893 focus_recon_set.resize(simStep);
894 focus_img_set.resize(simStep);
895 focus_img_size.resize(simStep);
897 std::string varname2;
899 for (
int vtr = 0; vtr < simStep; vtr++)
902 eyeFocusDistance = var_vals[vtr][
_X];
905 if (bSimPos[
_X]) eyeCenter[
_X] = var_vals[vtr][
_X];
906 if (bSimPos[
_Y]) eyeCenter[
_Y] = var_vals[vtr][
_X];
907 if (bSimPos[
_Z]) eyeCenter[
_Z] = var_vals[vtr][
_X];
910 for (
int ctr = 0; ctr < nChannel; ctr++)
913 k = 2 *
M_PI / lambda;
917 pp_e_x = pp_set_[ctr][
_X];
918 pp_e_y = pp_set_[ctr][
_Y];
919 ss_e_x =
Real(pn_e_x) * pp_e_x;
920 ss_e_y =
Real(pn_e_y) * pp_e_y;
922 eye_shift_by_pn[0] = round(eyeCenter[
_X] / pp_e_x);
923 eye_shift_by_pn[1] = round(eyeCenter[
_Y] / pp_e_y);
926 memset(hh_e_shift, 0.0,
sizeof(
Complex<Real>) * pn_e_x * pn_e_y);
927 circshift(field_set_[ctr], hh_e_shift, -eye_shift_by_pn[0], eye_shift_by_pn[1], pn_e_x, pn_e_y);
932 eye_box_range_x[0] = -boxSize[
_X] / 2.0;
933 eye_box_range_x[1] = boxSize[
_X] / 2.0;
934 eye_box_range_y[0] = -boxSize[
_Y] / 2.0;
935 eye_box_range_y[1] = boxSize[
_Y] / 2.0;
936 eye_box_range_idx[0] = floor((eye_box_range_x[0] + ss_e_x / 2.0) / pp_e_x);
937 eye_box_range_idx[1] = floor((eye_box_range_x[1] + ss_e_x / 2.0) / pp_e_x);
938 eye_box_range_idy[0] = pn_e_y - floor((eye_box_range_y[1] + ss_e_y / 2.0) / pp_e_y);
939 eye_box_range_idy[1] = pn_e_y - floor((eye_box_range_y[0] + ss_e_y / 2.0) / pp_e_y);
944 int temp = floor((pn_e_x - boxSize[
_X]) / 2.0);
945 eye_box_range_idx[0] = temp;
946 eye_box_range_idx[1] = temp + boxSize[
_X] - 1;
947 temp = floor((pn_e_y - boxSize[
_Y]) / 2.0);
948 eye_box_range_idy[0] = temp;
949 eye_box_range_idy[1] = temp + boxSize[
_Y] - 1;
952 pn_p_x = eye_box_range_idx[1] - eye_box_range_idx[0] + 1;
953 pn_p_y = eye_box_range_idy[1] - eye_box_range_idy[0] + 1;
956 ss_p_x = pn_p_x * pp_p_x;
957 ss_p_y = pn_p_y * pp_p_y;
959 int N = pn_p_x * pn_p_y;
960 int N2 = pn_e_x * pn_e_y;
966 for (
int p = 0; p < N2; p++)
971 if (x >= eye_box_range_idx[0] - 1 && x <= eye_box_range_idx[1] - 1 && y >= eye_box_range_idy[0] - 1 && y <= eye_box_range_idy[1] - 1)
973 int xx = cropidx % pn_p_x;
974 int yy = cropidx / pn_p_x;
975 hh_p[yy*pn_p_x + xx] = hh_e_shift[p];
981 Real f_eye = eyeLen * (eyeCenter[
_Z] - eyeFocusDistance) / (eyeLen + (eyeCenter[
_Z] - eyeFocusDistance));
982 Real effective_f = f_eye * eyeLen / (f_eye - eyeLen);
989 for (loopp = 0; loopp < N; loopp++)
991 int x = loopp % pn_p_x;
992 int y = loopp / pn_p_x;
994 Real XE = -ss_p_x / 2.0 + (pp_p_x *x);
995 Real YE = ss_p_y / 2.0 - pp_p_y - (pp_p_y * y);
997 Real sval = (XE*XE) + (YE*YE);
998 sval *=
M_PI / lambda / effective_f;
1000 eye_propagation_kernel.
exp();
1002 Real eye_lens_anti_aliasing_mask = fabs(XE) < fabs(lambda*effective_f / (4 * pp_e_x)) ? 1.0 : 0.0;
1003 eye_lens_anti_aliasing_mask *= fabs(YE) < fabs(lambda*effective_f / (4 * pp_e_y)) ? 1.0 : 0.0;
1005 Real eye_pupil_mask = sqrt(XE*XE + YE * YE) < (eyePupil / 2.0) ? 1.0 : 0.0;
1007 hh_e_[x + y * pn_p_x] = hh_p[x + y * pn_p_x] * eye_propagation_kernel * eye_lens_anti_aliasing_mask * eye_pupil_mask;
1014 Real pp_ret_x, pp_ret_y;
1015 int pn_ret_x, pn_ret_y;
1018 pp_ret_x = lambda * eyeLen / ss_p_x;
1019 pp_ret_y = lambda * eyeLen / ss_p_y;
1022 ret_size_xy[0] = pp_ret_x * pn_ret_x;
1023 ret_size_xy[1] = pp_ret_y * pn_ret_y;
1025 field_ret_set_[ctr] =
new Real[pn_p_x * pn_p_y];
1026 memset(field_ret_set_[ctr], 0.0,
sizeof(
Real)*pn_p_x*pn_p_y);
1029 for (loopp = 0; loopp < pn_p_x*pn_p_y; loopp++)
1031 int x = loopp % pn_p_x;
1032 int y = loopp / pn_p_x;
1034 Real XR = ret_size_xy[0] / 2.0 + (pp_ret_x * x);
1035 Real YR = ret_size_xy[1] / 2.0 - pp_ret_y - (pp_ret_y * y);
1037 Real sval = (XR*XR) + (YR*YR);
1038 sval *= k / (2 * eyeLen);
1046 field_ret_set_[ctr][x + pn_p_x * y] = (hh_e_[x + pn_p_x * y] * (val1 * val2 / val3)).mag();
1051 pp_ret_set_[ctr] =
vec2(pp_ret_x, pp_ret_y);
1052 pn_ret_set_[ctr] =
ivec2(pn_ret_x, pn_ret_y);
1053 ss_ret_set_[ctr] = pp_ret_set_[ctr] * pn_ret_set_[ctr];
1055 if (bCreatePupilImg)
1057 Real pp_min = (pp_e_x > pp_e_y) ? pp_e_y : pp_e_x;
1058 Real ss_max = (ss_e_x > ss_e_y) ? ss_e_x : ss_e_y;
1059 Real pn_tar = ceil(ss_max / pp_min);
1060 pp_min = ss_max / pn_tar;
1061 Real pn_e_tar_x = round(ss_e_x / pp_min);
1062 Real pn_e_tar_y = round(ss_e_y / pp_min);
1064 Real resize_scale_x = pn_e_tar_x * resultSizeScale;
1065 Real resize_scale_y = pn_e_tar_y * resultSizeScale;
1067 int N = resize_scale_x * resize_scale_y;
1069 recon_set[vtr * nChannel + ctr] =
new Real[N];
1070 img_set[vtr * nChannel + ctr] =
new uchar[N];
1072 memset(recon_set[vtr * nChannel + ctr], 0.0,
sizeof(
Real) * N);
1073 memset(img_set[vtr * nChannel + ctr], 0,
sizeof(
uchar) * N);
1076 , pn_e_x, pn_e_y, pp_e_x, pp_e_y, resize_scale_x, resize_scale_y);
1078 std::string fname = std::string(
"./").append(
"").append(
"/FIELD/");
1079 fname = fname.append(
"FIELD_COLOR_").append(std::to_string(ctr + 1)).append(
"_").append(
"").append(
"_SAT_").append(
"").append(
"_").append(std::to_string(vtr + 1)).append(
".bmp");
1080 normalize(recon_set[vtr * nChannel + ctr], img_set[vtr * nChannel + ctr], (
int)resize_scale_x, (
int)resize_scale_y);
1081 img_size[vtr * nChannel + ctr][
_X] = (int)resize_scale_x;
1082 img_size[vtr * nChannel + ctr][
_Y] = (int)resize_scale_y;
1087 Real pnx_max = 0.0, pny_max = 0.0;
1088 for (
int i = 0; i < nChannel; i++)
1090 pnx_max = (pn_ret_set_[i][0] > pnx_max ? pn_ret_set_[i][0] : pnx_max);
1091 pny_max = (pn_ret_set_[i][1] > pny_max ? pn_ret_set_[i][1] : pny_max);
1094 Real retinal_image_shift_x = eyeCenter[
_X] * eyeLen / eyeCenter[
_Z];
1095 Real retinal_image_shift_y = eyeCenter[
_Y] * eyeLen / eyeCenter[
_Z];
1097 res_set_.resize(nChannel);
1098 res_set_norm_255_.resize(nChannel);
1102 for (loopi = 0; loopi < nChannel; loopi++)
1105 Real* hh_ret_ =
new Real[pn_ret_set_[loopi][0] * pn_ret_set_[loopi][1]];
1106 memset(hh_ret_, 0.0,
sizeof(
Real)*pn_ret_set_[loopi][0] * pn_ret_set_[loopi][1]);
1108 if (bCenteringRetinaImg)
1110 Real retinal_image_shift_by_pn_x = round(retinal_image_shift_x / pp_ret_set_[loopi][0]);
1111 Real retinal_image_shift_by_pn_y = round(retinal_image_shift_y / pp_ret_set_[loopi][1]);
1113 circshift(field_ret_set_[loopi], hh_ret_, -retinal_image_shift_by_pn_x, retinal_image_shift_by_pn_y, pn_ret_set_[loopi][0], pn_ret_set_[loopi][1]);
1117 hh_ret_ = field_ret_set_[loopi];
1119 delete[] field_ret_set_[loopi];
1121 int size = (int)(pnx_max * pny_max);
1122 res_set_[loopi] =
new Real[size];
1123 memset(res_set_[loopi], 0.0,
sizeof(
Real) * size);
1124 ScaleBilnear(hh_ret_, res_set_[loopi], pn_ret_set_[loopi][0], pn_ret_set_[loopi][1], pnx_max, pny_max, lambda * lambda);
1128 Real maxvalue = res_set_[0][0];
1129 Real minvalue = res_set_[0][0];
1130 for (
int i = 0; i < nChannel; i++)
1132 for (
int j = 0; j < pnx_max*pny_max; j++)
1134 maxvalue = res_set_[i][j] > maxvalue ? res_set_[i][j] : maxvalue;
1135 minvalue = res_set_[i][j] < minvalue ? res_set_[i][j] : minvalue;
1139 for (
int j = 0; j < pnx_max*pny_max; j++)
1141 res_set_[0][j] = (res_set_[0][j] - minvalue) / (maxvalue - minvalue) * 255;
1145 for (loopi = 0; loopi < nChannel; loopi++)
1147 for (
int j = 0; j < pnx_max*pny_max; j++)
1149 if (res_set_[loopi][j] > ratioAtRetina * maxvalue)
1150 res_set_[loopi][j] = ratioAtRetina * maxvalue;
1152 res_set_[loopi][j] = (res_set_[loopi][j] - minvalue) / (ratioAtRetina*maxvalue - minvalue);
1157 Real ret_size_x = pnx_max * resultSizeScale;
1158 Real ret_size_y = pny_max * resultSizeScale;
1160 int size = (int)(ret_size_x * ret_size_y);
1163 for (loopi = 0; loopi < nChannel; loopi++)
1165 Real* res_set_norm =
new Real[size];
1166 memset(res_set_norm, 0.0,
sizeof(
Real) * size);
1168 ScaleBilnear(res_set_[loopi], res_set_norm, pnx_max, pny_max, ret_size_x, ret_size_y);
1170 res_set_norm_255_[loopi] =
new Real[size];
1171 memset(res_set_norm_255_[loopi], 0.0,
sizeof(
Real) * size);
1173 rotateCCW180(res_set_norm, res_set_norm_255_[loopi], ret_size_x, ret_size_y, 255.0);
1175 delete[] res_set_norm;
1178 for (
int i = 0; i < nChannel; i++)
1179 delete[] res_set_[i];
1181 int N = ret_size_x * ret_size_y;
1183 focus_recon_set[vtr] =
new Real[N * nChannel];
1184 focus_img_set[vtr] =
new uchar[N * nChannel];
1185 memset(focus_recon_set[vtr], 0.0,
sizeof(
Real) * N * nChannel);
1186 memset(focus_img_set[vtr], 0,
sizeof(
uchar) * N * nChannel);
1189 memcpy(focus_recon_set[vtr], res_set_norm_255_[0],
sizeof(
Real)*ret_size_x*ret_size_y);
1191 reArrangeChannel(res_set_norm_255_, focus_recon_set[vtr], ret_size_x, ret_size_y, nChannel);
1193 std::string fname = std::string(
"./").append(
"").append(
"/").append(
"").append(
"_SAT_").append(
"").append(
"_").append(varname2).append(
"_").append(std::to_string(vtr + 1)).append(
".bmp");
1195 normalize(focus_recon_set[vtr], focus_img_set[vtr], ret_size_x, ret_size_y);
1197 focus_img_size[vtr][
_X] = (int)ret_size_x;
1198 focus_img_size[vtr][
_Y] = (int)ret_size_y;
1200 m_vecEncoded.push_back(focus_recon_set[vtr]);
1201 m_vecNormalized.push_back(focus_img_set[vtr]);
1204 for (
int i = 0; i < nChannel; i++)
1205 delete[] res_set_norm_255_[i];
1213 if (fname ==
nullptr)
return bOK;
1215 uchar* source = src;
1216 bool bAlloc =
false;
1220 if (px == 0 && py == 0)
1224 std::string file = fname;
1225 std::replace(file.begin(), file.end(),
'\\',
'/');
1228 std::vector<std::string> components;
1229 std::stringstream ss(file);
1233 while (std::getline(ss, item, token)) {
1234 components.push_back(item);
1239 for (
size_t i = 0; i < components.size() - 1; i++)
1241 dir += components[i];
1245 std::string filename = components[components.size() - 1];
1249 size_t ext_pos = file.rfind(
".");
1250 hasExt = (ext_pos == string::npos) ?
false :
true;
1253 filename.append(
".bmp");
1255 std::string fullpath = dir + filename;
1257 if (nChannel == 1) {
1258 saveAsImg(fullpath.c_str(), bitsperpixel, src, p[
_X], p[
_Y]);
1260 else if (nChannel == 3) {
1262 uint nSize = (((p[
_X] * bitsperpixel >> 3) + 3) & ~3) * p[
_Y];
1265 for (
uint i = 0; i < nChannel; i++) {
1268 saveAsImg(fullpath.c_str(), bitsperpixel, source, p[
_X], p[
_Y]);
1269 if (bAlloc)
delete[] source;
1272 char path[FILENAME_MAX] = { 0, };
1273 sprintf(path,
"%s%s", dir.c_str(), filename.c_str());
1274 saveAsImg(path, bitsperpixel / nChannel, src, p[
_X], p[
_Y]);
1301 pnX = focus_img_size[0][
_X];
1302 pnY = focus_img_size[0][
_Y];
1306 step = (simTo - simFrom) / (nSimStep - 1);
1309 char tmpPath[FILENAME_MAX] = { 0, };
1310 bool bMultiStep = nSimStep > 1 ?
true :
false;
1311 uint nSize = (((pnX * nChannel) + 3) & ~3) * pnY;
1314 for (
int i = 0; i < nSimStep; i++)
1316 sprintf(tmpPath,
"%s\\FOCUS_%.4f.%s", path, bMultiStep ?
1317 simFrom + (step * i) : (simFrom + simTo) / 2, ext);
1323 for (
int ch = 0; ch < nChannel; ch++)
1325 mergeColor(ch, pnX, pnY, m_vecNormalized[i * nChannel + ch], tmp);
1327 saveAsImg(tmpPath, 8 * nChannel, tmp, pnX, pnY);
1331 for (
int ch = 0; ch < nChannel; ch++)
1333 memset(tmp, 0,
sizeof(
uchar) * nSize);
1334 sprintf(tmpPath,
"%s\\FOCUS_%.4f (%d).%s", path, bMultiStep ? simFrom + step * i : (simFrom + simTo) / 2, ch, ext);
1335 mergeColor(ch, pnX, pnY, m_vecNormalized[i * nChannel + ch], tmp);
1336 saveAsImg(tmpPath, 8 * nChannel, tmp, pnX, pnY);
1342 memcpy(tmp, m_vecNormalized[i],
sizeof(
uchar) * nSize);
1343 saveAsImg(tmpPath, 8 * nChannel, tmp, pnX, pnY);
1351 const int N = pnx * pny;
1358 memset(dimg, 0.0,
sizeof(
Real) * N);
1361 for (
int k = 0; k < N; k++)
1364 maxvalue = val > maxvalue ? val : maxvalue;
1368 Real SAT_VAL = maxvalue * ratioAtPupil;
1369 Real hss_x = (pnx * ppx) / 2.0;
1370 Real hss_y = (pny * ppy) / 2.0;
1371 Real halfPupil = eyePupil / 2.0;
1373 Real maxv = dimg[0], minv = dimg[0];
1374 for (
int k = 0; k < N; k++)
1376 if (dimg[k] > SAT_VAL)
1379 maxv = (dimg[k] > maxv) ? dimg[k] : maxv;
1380 minv = (dimg[k] < minv) ? dimg[k] : minv;
1383 for (
int k = 0; k < N; k++)
1388 Real xx = -hss_x + (ppx * x);
1389 Real yy = -hss_y + (pny - 1) * ppy - (ppy * y);
1390 Real xxx = xx - eyeCenter[
_X];
1391 Real yyy = yy - eyeCenter[
_Y];
1392 bool eye_pupil_mask = sqrt(xxx * xxx + yyy * yyy) < halfPupil ? 1.0 : 0.0;
1395 Real field_out = (val - minv) / (maxv - minv) * 255.0;
1396 Real field_in = (val - minv) / (maxv - minv) * 127.0 + 128.0;
1397 dimg[k] = field_in * eye_pupil_mask + field_out * (1 - eye_pupil_mask);
1409 memcpy(&bSimPos[0], rec_config.
SimulationPos,
sizeof(bSimPos));
1411 std::string varname;
1416 varname.append(
"FOCUS");
1418 LOG(
"Step # %d %s = %.8f \n", vtr + 1, varname.c_str(), var_vals[0]);
1420 sprintf(temp,
"%.5f", var_vals[0]);
1422 varname2.append(varname).append(
"_").append(temp);
1423 varname2.replace(varname2.find(
'.'), 1,
"_");
1428 varname.append(
"POSITION");
1430 if (bSimPos[
_X]) varname.append(
"_X");
1431 if (bSimPos[
_Y]) varname.append(
"_Y");
1432 if (bSimPos[
_Z]) varname.append(
"_Z");
1434 LOG(
"Step # %d %s = ", vtr + 1, varname.c_str());
1436 varname2.append(varname);
1439 LOG(
"%.8f ", var_vals[0]);
1441 sprintf(temp,
"%.5f", var_vals[0]);
1442 varname2.append(
"_").append(temp);
1443 varname2.replace(varname2.find(
'.'), 1,
"_");
1446 LOG(
"%.8f ", var_vals[1]);
1448 sprintf(temp,
"%.5f", var_vals[1]);
1449 varname2.append(
"_").append(temp);
1450 varname2.replace(varname2.find(
'.'), 1,
"_");
1453 LOG(
"%.8f ", var_vals[2]);
1455 sprintf(temp,
"%.5f", var_vals[2]);
1456 varname2.append(
"_").append(temp);
1457 varname2.replace(varname2.find(
'.'), 1,
"_");
1465 for (vector<Real*>::iterator it = m_vecEncoded.begin(); it != m_vecEncoded.end(); it++)
1470 for (vector<uchar*>::iterator it = m_vecNormalized.begin(); it != m_vecNormalized.end(); it++)
1474 m_vecEncoded.clear();
1475 m_vecNormalized.clear();
1484 LOG(
"1) Algorithm Method : Angular Spectrum\n");
1485 LOG(
"2) Reconstruct Image with %s\n", m_mode &
MODE_GPU ?
1507 for (
int i = 0; i < m_nOldChannel; i++) {
1517 for (
int i = 0; i < nChannel; i++) {
1521 m_nOldChannel = nChannel;
1528 for (vector<Real*>::iterator it = m_vecEncoded.begin(); it != m_vecEncoded.end(); it++)
1532 m_vecEncoded.clear();
1534 for (vector<uchar*>::iterator it = m_vecNormalized.begin(); it != m_vecNormalized.end(); it++)
1538 m_vecNormalized.clear();
1544 for (
int i = 0; i < nx; i++)
1546 for (
int j = 0; j < ny; j++)
1548 ti = (i + shift_x) % nx;
1551 tj = (j + shift_y) % ny;
1555 out[ti + tj * nx] = in[i + j * nx];
1563 for (
int i = 0; i < nx; i++)
1565 for (
int j = 0; j < ny; j++)
1567 ti = (i + shift_x) % nx;
1570 tj = (j + shift_y) % ny;
1574 out[ti + tj * nx] = in[i + j * nx];
1581 int x1 = (int)floor(xx);
1582 int x2 = (int)ceil(xx);
1583 int y1 = (int)floor(yy);
1584 int y2 = (int)ceil(yy);
1586 if (x1 < 0 || x1 >= (
int)
w || x2 < 0 || x2 >= (int)
w)
return vec3(0);
1587 if (y1 < 0 || y1 >= (
int)
h || y2 < 0 || y2 >= (
int)
h)
return vec3(0);
1590 double v1, v2, v3, v4, tvx, tvy;
1592 tvx = xx - floor(xx);
1593 tvy = yy - floor(yy);
1595 for (
int i = 0; i < tc; i++) {
1600 v1 = (1.0 - tvx)*v1 + tvx * v2;
1601 v3 = (1.0 - tvx)*v3 + tvx * v4;
1602 v1 = (1.0 - tvy)*v1 + tvy * v3;
1610 void ScaleBilnear(
double* src,
double* dst,
int w,
int h,
int neww,
int newh,
double multiplyval)
1612 for (
int y = 0; y < newh; y++)
1614 for (
int x = 0; x < neww; x++)
1616 float gx = (x / (float)neww) * (
w - 1);
1617 float gy = (y / (float)newh) * (
h - 1);
1620 dst[x + y * neww] = ret[0];
1643 void rotateCCW180(
double* src,
double* dst,
int pnx,
int pny,
double mulival)
1645 for (
int i = 0; i < pnx*pny; i++)
1650 int newx = pnx - x - 1;
1651 int newy = pny - y - 1;
1653 dst[newx + newy * pnx] = mulival * src[x + y * pnx];
1661 for (
int k = 0; k < pnx*pny; k++)
1663 for (
int c = 0; c < chnum; c++)
1666 dst[k*chnum + 2] = src[c][k];
1668 dst[k*chnum + 0] = src[c][k];
1670 dst[k*chnum + c] = src[c][k];
void GetPupilFieldImage(Complex< Real > *src, Real *dst, int pnx, int pny, Real ppx, Real ppy, Real scaleX, Real scaleY)
virtual bool saveAsImg(const char *fname, uint8_t bitsperpixel, uchar *src, int width, int height)
Function for creating image files.
void fftFree(void)
Resource release method.
#define IMAGE_VAL(x, y, c, w, n, mem)
void GetPupilFieldFromVWHologram()
vec3 image_sample(float xx, float yy, int c, size_t w, size_t h, double *in)
void SaveImage(const char *path, const char *ext="bmp")
void reArrangeChannel(std::vector< double *> &src, double *dst, int pnx, int pny, int chnum)
bool checkExtension(const char *fname, const char *ext)
Functions for extension checking.
structure for 2-dimensional integer vector and its arithmetic.
void rotateCCW180(double *src, double *dst, int pnx, int pny, double mulival=1.0)
void getVarname(int vtr, vec3 &var_vals, std::string &varname2)
virtual void ophFree(void)
Pure virtual function for override in child classes.
void circshift(Real *in, Real *out, int shift_x, int shift_y, int nx, int ny)
const XMLNode * FirstChild() const
Get the first child node, or null if none exists.
bool readImage(const char *path)
virtual ~ophRec(void)
Destructor.
void GetPupilFieldFromHologram()
void imgScaleBilinear(uchar *src, uchar *dst, int w, int h, int neww, int newh, int channels=1)
Function for change image size.
bool getImgSize(int &w, int &h, int &bytesperpixel, const char *fname)
Function for getting the image size.
bool readImagePNA(const char *phase, const char *amplitude)
bool readImageRNI(const char *real, const char *imaginary)
void fft2(ivec2 n, Complex< Real > *in, int sign=OPH_FORWARD, uint flag=OPH_ESTIMATE)
Functions for performing fftw 2-dimension operations inside Openholo.
structure for 2-dimensional Real type vector and its arithmetic.
void ScaleBilnear(double *src, double *dst, int w, int h, int neww, int newh, double multiplyval=1.0)
#define ELAPSED_TIME(x, y)
structure for 3-dimensional Real type vector and its arithmetic.
bool save(const char *fname, uint8_t bitsperpixel, uchar *src, uint px, uint py)
XMLError LoadFile(const char *filename)
void ASM_Propagation_GPU()
bool readConfig(const char *fname)
void Perform_Simulation()
void Propagation_Fresnel_FFT(int chnum)
Complex< Real > ** complex_H
bool loadAsImgUpSideDown(const char *fname, uchar *dst)
Function for loading image files | Output image data upside down.
const XMLElement * FirstChildElement(const char *name=0) const
bool mergeColor(int idx, int width, int height, uchar *src, uchar *dst)
Function for generate RGB image from each grayscale image.
virtual void ophFree(void)
Pure virtual function for override in child classes.
void normalize(T *src, uchar *dst, int x, int y)