00001 #include "mex.h"
00002 #include <stdio.h>
00003 #include <math.h>
00004 #include "mexhead.h"
00005 #include "Doc/hmi_segment_docstring.h"
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054 #define NARGIN_MIN 11
00055 #define NARGIN_MAX 13
00056 #define NARGOUT_MIN 1
00057 #define NARGOUT_MAX 4
00058
00059 #define ARG_xm 0
00060 #define ARG_xp 1
00061 #define ARG_edge 2
00062 #define ARG_iter 3
00063 #define ARG_T 4
00064 #define ARG_beta 5
00065 #define ARG_alpha 6
00066 #define ARG_geom 7
00067 #define ARG_rho 8
00068 #define ARG_m1 9
00069 #define ARG_m2 10
00070 #define ARG_m3 11
00071 #define ARG_m4 12
00072
00073 #define ARG_y 0
00074 #define ARG_s 1
00075 #define ARG_post 2
00076 #define ARG_nclean 3
00077
00078 static const char *progname = "hmi_segment";
00079 #define PROGNAME hmi_segment
00080 static const char *in_specs[NARGIN_MAX] = {
00081 "RM",
00082 "RM",
00083 "RV(2)",
00084 "RS|RV(2)",
00085 "RS|RV(2)|RV(3)|RV(4)",
00086 "RS(1)|RM",
00087 "RV",
00088 "RV(5)",
00089 "RS(1)",
00090 "RM",
00091 "RM",
00092 "RM",
00093 "RM"};
00094 static const char *in_names[NARGIN_MAX] = {
00095 "xm",
00096 "xp",
00097 "edge",
00098 "iter",
00099 "T",
00100 "beta",
00101 "alpha",
00102 "geom",
00103 "rho",
00104 "m1",
00105 "m2",
00106 "m3",
00107 "m4"};
00108 static const char *out_names[NARGOUT_MAX] = {"y", "s", "post", "nclean"};
00109
00110
00111 #define SHORTNAME Hseg
00112
00113
00114 #include "makemrfdiscwts.h"
00115 #include "mixNprob2d.h"
00116 #include "mrf_segment_wts.h"
00117 #include "clean_edge_label.h"
00118 #include "roi_stats_mag.h"
00119
00120
00121 #define MXT_mdw_NARGIN_USE MXT_mdw_NARGIN_MIN // omit last arg (ell)
00122 #define MXT_mdw_NARGOUT_USE MXT_mdw_NARGOUT_MAX
00123 #define MXT_m2d_NARGIN_USE MXT_m2d_NARGIN_MIN // omit last arg (mode)
00124 #define MXT_m2d_NARGOUT_USE MXT_m2d_NARGOUT_MAX
00125 #define MXT_msw_NARGIN_USE MXT_msw_NARGIN_MAX // actually variadic
00126 #define MXT_msw_NARGOUT_USE MXT_msw_NARGOUT_MAX
00127 #define MXT_cel_NARGIN_USE MXT_cel_NARGIN_MAX
00128 #define MXT_cel_NARGOUT_USE MXT_cel_NARGOUT_MAX
00129 #define MXT_rsm_NARGIN_USE MXT_rsm_NARGIN_MAX
00130 #define MXT_rsm_NARGOUT_USE 1 // names, combo unused
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143
00144
00145
00146
00147
00148 static
00149 void
00150 segment_offdisk_nan(double *p, int maxx, int maxy, double *ctr)
00151 {
00152 const double cenx = ctr[0] - 1.0;
00153 const double ceny = ctr[1] - 1.0;
00154 const double rsun2 = ctr[2]*ctr[2];
00155 const double nan = mxt_getnand();
00156 int x, y, inx;
00157 double dx, dy, r2;
00158
00159 for (y = 0; y < maxy; y++)
00160 for (x = 0; x < maxx; x++) {
00161
00162
00163
00164 inx = y*maxx + x;
00165 if (isnan(p[inx]))
00166 continue;
00167
00168 dx = x - cenx;
00169 dy = y - ceny;
00170
00171 r2 = dx*dx + dy*dy;
00172
00173 if (r2 > rsun2)
00174 p[inx] = nan;
00175 }
00176 }
00177
00178
00179
00180
00181 #ifdef StaticP
00182 StaticP
00183 #endif
00184 void
00185 mexFunction(int nlhs,
00186 mxArray *plhs[],
00187 int nrhs,
00188 const mxArray *prhsC[])
00189 {
00190 mxArray **prhs = (mxArray **) prhsC;
00191
00192 mxArray *prhs_m2d[MXT_m2d_NARGIN_USE];
00193 mxArray *plhs_m2d[MXT_m2d_NARGOUT_USE];
00194
00195 mxArray *prhs_mdw[MXT_mdw_NARGIN_USE];
00196 mxArray *plhs_mdw[MXT_mdw_NARGOUT_USE];
00197
00198 mxArray *prhs_msw[MXT_msw_NARGIN_USE];
00199 mxArray *plhs_msw[MXT_msw_NARGOUT_USE];
00200
00201 mxArray *prhs_cel[MXT_cel_NARGIN_USE];
00202 mxArray *plhs_cel[MXT_cel_NARGOUT_USE];
00203
00204 mxArray *prhs_rsm[MXT_rsm_NARGIN_USE];
00205 mxArray *plhs_rsm[MXT_rsm_NARGOUT_USE];
00206
00207 int M, N;
00208 int Nmod;
00209 int i;
00210 const int verbose = 0;
00211 char errstr[256];
00212 char *msg;
00213
00214
00215 if (nrhs < 0) {
00216 plhs[0] = mxt_PackSignature((mxt_Signature) (-nrhs),
00217 NARGIN_MIN, NARGIN_MAX,
00218 NARGOUT_MIN, NARGOUT_MAX,
00219 in_names, in_specs, out_names, docstring);
00220 return;
00221 }
00222
00223
00224
00225 if ((nrhs < NARGIN_MIN) || (nrhs > NARGIN_MAX))
00226 mexErrMsgTxt((snprintf(errstr, sizeof(errstr),
00227 "%s: Expect %d <= input args <= %d",
00228 progname, NARGIN_MIN, NARGIN_MAX), errstr));
00229 if ((nlhs < NARGOUT_MIN) || (nlhs > NARGOUT_MAX))
00230 mexErrMsgTxt((snprintf(errstr, sizeof(errstr),
00231 "%s: Expect %d <= output args <= %d",
00232 progname, NARGOUT_MIN, NARGOUT_MAX), errstr));
00233 if (verbose) printf("in %s\n", progname);
00234 mexargparse(nrhs, prhsC, in_names, in_specs, NULL, progname);
00235
00236 start_sizechecking();
00237 sizeinit(prhs[ARG_xp]);
00238 sizeagree(prhs[ARG_xm]);
00239 sizecheck_msg(progname, in_names, ARG_xp);
00240
00241
00242
00243
00244 M = mxGetM(prhs[ARG_xp]);
00245 N = mxGetN(prhs[ARG_xp]);
00246 Nmod = nrhs - ARG_m1;
00247
00248
00249
00250 prhs_mdw[MXT_mdw_ARG_n ] = mxCreateDoubleMatrix(1, 2, mxREAL);
00251 prhs_mdw[MXT_mdw_ARG_del ] = mxCreateDoubleScalar(3.0);
00252 prhs_mdw[MXT_mdw_ARG_ctr ] = prhs[ARG_geom];
00253 prhs_mdw[MXT_mdw_ARG_rho ] = prhs[ARG_rho];
00254 prhs_mdw[MXT_mdw_ARG_mode] = mxCreateString("sesw");
00255 if (!prhs_mdw[MXT_mdw_ARG_n ] ||
00256 !prhs_mdw[MXT_mdw_ARG_del ] ||
00257 !prhs_mdw[MXT_mdw_ARG_mode])
00258 mexErrMsgTxt((snprintf(errstr, sizeof(errstr),
00259 "%s: Failed to allocate makemrfdiscwts inputs",
00260 progname), errstr));
00261
00262 mxGetPr(prhs_mdw[MXT_mdw_ARG_n])[0] = (double) M;
00263 mxGetPr(prhs_mdw[MXT_mdw_ARG_n])[1] = (double) N;
00264 if (verbose) printf("segment: calling makemrfdiscwts\n");
00265 msg = main_makemrfdiscwts(MXT_mdw_NARGOUT_USE, plhs_mdw,
00266 MXT_mdw_NARGIN_USE, prhs_mdw);
00267 if (msg)
00268 mexErrMsgTxt((snprintf(errstr, sizeof(errstr),
00269 "%s: Trouble in makemrfdiscwts (%s)",
00270 progname, msg), errstr));
00271
00272 mxDestroyArray(prhs_mdw[MXT_mdw_ARG_n ]);
00273 mxDestroyArray(prhs_mdw[MXT_mdw_ARG_del ]);
00274 mxDestroyArray(prhs_mdw[MXT_mdw_ARG_mode]);
00275
00276
00277 prhs_m2d[MXT_m2d_ARG_i1] = prhs[ARG_xm];
00278 prhs_m2d[MXT_m2d_ARG_i2] = prhs[ARG_xp];
00279 for (i = 0; i < Nmod; i++) {
00280 prhs_m2d[MXT_m2d_ARG_model] = prhs[ARG_m1+i];
00281 if (verbose) printf("segment: calling mixNprob2d\n");
00282 msg = main_mixNprob2d(MXT_m2d_NARGOUT_USE, plhs_m2d,
00283 MXT_m2d_NARGIN_USE, prhs_m2d);
00284 if (msg)
00285 mexErrMsgTxt((snprintf(errstr, sizeof(errstr),
00286 "%s: Trouble in mixNprob2d[mod=%d] (%s)",
00287 progname, i, msg), errstr));
00288 if (verbose) printf("\tprob%d[M/2,N/2] = %g\n", i,
00289 mxGetPr(plhs_m2d[MXT_m2d_ARG_p])[(M/2)*N+N/2]);
00290
00291
00292
00293 if (i == 0)
00294 segment_offdisk_nan(mxGetPr(plhs_m2d[MXT_m2d_ARG_p]),
00295 M, N, mxGetPr(prhs[ARG_geom]));
00296
00297 prhs_msw[MXT_msw_ARG_lprob1+i] = plhs_m2d[MXT_m2d_ARG_p];
00298 }
00299
00300
00301
00302
00303 prhs_msw[MXT_msw_ARG_iters] = prhs[ARG_iter];
00304 prhs_msw[MXT_msw_ARG_T] = prhs[ARG_T];
00305 prhs_msw[MXT_msw_ARG_beta] = prhs[ARG_beta];
00306 prhs_msw[MXT_msw_ARG_alpha] = prhs[ARG_alpha];
00307 prhs_msw[MXT_msw_ARG_dist] = plhs_mdw[MXT_mdw_ARG_dist];
00308 prhs_msw[MXT_msw_ARG_y] = mxCreateDoubleMatrix(0, 0, mxREAL);
00309 if (!prhs_msw[MXT_msw_ARG_y])
00310 mexErrMsgTxt((snprintf(errstr, sizeof(errstr),
00311 "%s: Failed to allocate mrf_segment_wts input",
00312 progname), errstr));
00313 if (verbose) printf("segment: calling mrf_segment\n");
00314
00315 msg = main_mrf_segment_wts(MXT_msw_NARGOUT_USE, plhs_msw,
00316 MXT_msw_ARG_lprob1+Nmod, prhs_msw);
00317 if (msg)
00318 mexErrMsgTxt((snprintf(errstr, sizeof(errstr),
00319 "%s: Trouble in mrf_segment (%s)",
00320 progname, msg), errstr));
00321 if (verbose) printf("\tseg[M/2,N/2] = %g\n",
00322 mxGetPr(plhs_msw[MXT_msw_ARG_yp])[(M/2)*N+N/2]);
00323
00324 mxDestroyArray(prhs_msw[MXT_msw_ARG_dist]);
00325 mxDestroyArray(prhs_msw[MXT_msw_ARG_y]);
00326 for (i = 0; i < Nmod; i++)
00327 mxDestroyArray(prhs_msw[MXT_msw_ARG_lprob1+i]);
00328
00329
00330
00331 prhs_cel[MXT_cel_ARG_image ] = plhs_msw[MXT_msw_ARG_yp];
00332 prhs_cel[MXT_cel_ARG_center] = prhs[ARG_geom];
00333 prhs_cel[MXT_cel_ARG_delta ] = mxCreateDoubleScalar(mxGetPr(prhs[ARG_edge])[0]);
00334 prhs_cel[MXT_cel_ARG_fill ] = mxCreateDoubleScalar(mxGetPr(prhs[ARG_edge])[1]);
00335 prhs_cel[MXT_cel_ARG_mode ] = mxCreateString("sesw");
00336 if (!prhs_cel[MXT_cel_ARG_delta] ||
00337 !prhs_cel[MXT_cel_ARG_fill ] ||
00338 !prhs_cel[MXT_cel_ARG_mode ])
00339 mexErrMsgTxt((snprintf(errstr, sizeof(errstr),
00340 "%s: Failed to allocate clean_edge_label inputs",
00341 progname), errstr));
00342 if (verbose) printf("segment: calling clean_edge_label\n");
00343 msg = main_clean_edge_label(MXT_cel_NARGOUT_USE, plhs_cel,
00344 MXT_cel_NARGIN_USE, prhs_cel);
00345 if (msg)
00346 mexErrMsgTxt((snprintf(errstr, sizeof(errstr),
00347 "%s: Trouble in clean_edge_label (%s)",
00348 progname, msg), errstr));
00349 if (verbose) printf("\tsegp[M/2,N/2] = %g\n",
00350 mxGetPr(plhs_cel[MXT_cel_ARG_res])[(M/2)*N+N/2]);
00351
00352 mxDestroyArray(prhs_cel[MXT_cel_ARG_image]);
00353 mxDestroyArray(prhs_cel[MXT_cel_ARG_delta]);
00354 mxDestroyArray(prhs_cel[MXT_cel_ARG_fill ]);
00355 mxDestroyArray(prhs_cel[MXT_cel_ARG_mode ]);
00356
00357
00358 if (nlhs > ARG_s) {
00359
00360
00361
00362
00363 prhs_rsm[MXT_rsm_ARG_x ] = plhs_cel[MXT_cel_ARG_res];
00364 prhs_rsm[MXT_rsm_ARG_y ] = plhs_cel[MXT_cel_ARG_res];
00365 prhs_rsm[MXT_rsm_ARG_mag ] = prhs[ARG_xm];
00366 prhs_rsm[MXT_rsm_ARG_geom] = prhs[ARG_geom];
00367 prhs_rsm[MXT_rsm_ARG_nroi] = mxCreateDoubleScalar((double) Nmod);
00368 prhs_rsm[MXT_rsm_ARG_mode] = mxCreateString("sesw");
00369 if (!prhs_rsm[MXT_rsm_ARG_mode])
00370 mexErrMsgTxt((snprintf(errstr, sizeof(errstr),
00371 "%s: Failed to allocate roi_stats_mag inputs",
00372 progname), errstr));
00373
00374 if (verbose) printf("segment: calling roi_stats_mag\n");
00375 msg = main_roi_stats_mag(MXT_rsm_NARGOUT_USE, plhs_rsm,
00376 MXT_rsm_NARGIN_USE, prhs_rsm);
00377 if (msg)
00378 mexErrMsgTxt((snprintf(errstr, sizeof(errstr),
00379 "%s: Trouble in roi_stats_mag (%s)",
00380 progname, msg), errstr));
00381
00382 mxDestroyArray(prhs_rsm[MXT_rsm_ARG_mode]);
00383 mxDestroyArray(prhs_rsm[MXT_rsm_ARG_nroi]);
00384 }
00385
00386
00387
00388
00389 if (verbose) printf("segment: setting up outputs...\n");
00390
00391 plhs[ARG_y] = plhs_cel[MXT_cel_ARG_res];
00392
00393 if (nlhs > ARG_s) {
00394
00395 plhs[ARG_s] = plhs_rsm[MXT_rsm_ARG_s];
00396 } else {
00397
00398 }
00399
00400 if (nlhs > ARG_post) {
00401
00402 plhs[ARG_post] = plhs_msw[MXT_msw_ARG_post];
00403 } else {
00404
00405 mxDestroyArray(plhs_msw[MXT_msw_ARG_post]);
00406 }
00407
00408 if (nlhs > ARG_nclean) {
00409
00410 plhs[ARG_nclean] = plhs_cel[MXT_cel_ARG_nclean];
00411 } else {
00412
00413 mxDestroyArray(plhs_cel[MXT_cel_ARG_nclean]);
00414 }
00415 }
00416
00417
00418
00419 #ifdef MEX2C_TAIL_HOOK
00420 #include "mex2c_tail.h"
00421 #endif