IPP Software Navigation Tools IPP Links Communication Pan-STARRS Links

Ignore:
Timestamp:
Feb 8, 2019, 8:20:03 PM (7 years ago)
Author:
eugene
Message:

add deimos fitslit, mkobj, mkslit commands

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/Ohana/src/opihi/mana/deimos_commands.c

    r40617 r40622  
    22
    33int deimos_mkslit (int argc, char **argv) {
    4   OHANA_UNUSED_PARAM(argv);
    5   if (argc != 5) {
    6     gprint (GP_ERR, "USAGE: deimos mkslit (profile) (trace) (flux) (buffer)\n");
    7     return FALSE;
    8   }
    94
    105  // generate model observed flux given a uniformly illuminated slit
     
    1611
    1712  Vector *profile = NULL;
    18   Vector *flux = NULL;
    19   Spline *trace = NULL;
    20   Buffer *buff = NULL;
     13  Vector *flux    = NULL;
     14  Vector *sky     = NULL;
     15  Spline *trace   = NULL;
     16  Buffer *buff    = NULL;
     17
     18  // user-specified flux value (otherwise assumed to be 1)
     19  if ((N = get_argument (argc, argv, "-flux"))) {
     20    remove_argument (N, &argc, argv);
     21    if ((flux = SelectVector (argv[N], OLDVECTOR, TRUE)) == NULL) return (FALSE);
     22    remove_argument (N, &argc, argv);
     23  }
     24
     25  // user-specified sky value (otherwise assumed to be 0)
     26  if ((N = get_argument (argc, argv, "-sky"))) {
     27    remove_argument (N, &argc, argv);
     28    if ((sky = SelectVector (argv[N], OLDVECTOR, TRUE)) == NULL) return (FALSE);
     29    remove_argument (N, &argc, argv);
     30  }
     31
     32  // either flux or fluxbins must be specified to define output size
     33  int fluxbins = 0;
     34  if ((N = get_argument (argc, argv, "-fluxbins"))) {
     35    remove_argument (N, &argc, argv);
     36    Nrows = atoi (argv[N]);
     37    remove_argument (N, &argc, argv);
     38  }
     39
     40  if (argc != 4) {
     41    gprint (GP_ERR, "USAGE: deimos mkslit (profile) (trace) (buffer) [-flux vector] [-fluxbins N] [-sky vector]\n");
     42    return FALSE;
     43  }
     44
     45  if (!flux && !fluxbins) {
     46    gprint (GP_ERR, "either flux or fluxbins must be specified to define output size\n");
     47    return FALSE;
     48  }
    2149
    2250  // XXX I probably should rename FindSpline as SelectSpline and give it the same behavior
    2351  if ((profile = SelectVector (argv[1], OLDVECTOR, TRUE)) == NULL) return (FALSE);
    2452  if ((trace   = FindSpline (argv[2])) == NULL) return (FALSE);
    25   if ((flux    = SelectVector (argv[3], OLDVECTOR, TRUE)) == NULL) return (FALSE);
    26   if ((buff    = SelectBuffer (argv[4], ANYBUFFER, TRUE)) == NULL) return (FALSE);
    27  
     53  if ((buff    = SelectBuffer (argv[3], ANYBUFFER, TRUE)) == NULL) return (FALSE);
     54
    2855  // define the output window
    2956  int Nx = 2*profile[0].Nelements;
    30   int Ny = flux[0].Nelements;
     57  int Ny = flux ? flux[0].Nelements : fluxbins;
    3158 
    3259  ResetBuffer (buff, Nx, Ny, -32, 0.0, 1.0);
    33  
     60
     61  // the profile is registered to the midpoint of the vector : (int) N / 2
     62  // the output window is registered to the midpoint of the window : (int) Nx / 2
     63
     64  int NxMidProfile = profile->Nelements / 2;
     65  int NxMidWindow  = Nx / 2;
     66
     67  float *out = (float *) buff[0].matrix.buffer;
    3468
    3569  // loop over the y positions
    36   for (iy = 0; iy < flux->Nelements; iy++) {
     70  for (int iy = 0; iy < Ny; iy++) {
    3771
    38     // evaluate the trace spline at this y-coord to find the x-coord of the profile center
    39     opihi_flt dx = spline_apply_dbl (trace->xk, trace->yk, trace->y2, trace->Nknots, iy);
     72    // evaluate the trace spline at this y-coord to find the x-coord offset of the profile center
     73    float dx = spline_apply_dbl (trace->xk, trace->yk, trace->y2, trace->Nknots, iy);
    4074   
    41     // interpolate the profile with offset of dx
    42     for (ix = 0; ix < profile->Nelements; ix++) {
    43       // interpolate from profile->elements.Flt[ix], interpolate from profile->elements.Flt[ix+1] to ix+dx
     75    // extract the integer pixel offset and the fractional offset
     76    int dxi = floor(dx); // -1.7 -> -2, -0.5 -> -1, +0.5 -> 0, +1.7 -> 1
     77    float dxf = dx - dxi;  // -1.7 -> +0.3, -0.5 -> +0.5, +0.5 ->+0.5, +1.7 -> +0.7
     78
     79    // starting point in output window is :
     80    // XXX handle case if profile is wider than window
     81    int Sx = (int)(NxMidWindow - NxMidProfile) + dxi;
     82
     83    // if fractional offset is small, do not interpolate
     84    int doInterp = fabs(dxf) < 1e-5 ? FALSE : TRUE;
     85
     86    // loop over the relevant pixels in the window:
     87    for (int ix = 0; ix < Nx; ix++) {
     88
     89      // equivalent coord in the profile:
     90      int px = ix - Sx;
     91      if (px < 0) continue;
     92      if (px >= profile->Nelements) continue;
     93
     94      float vout = NAN;
     95
     96      if (doInterp) {
     97        if ((px > 0) && (px < profile->Nelements - 1)) {
     98          // if ((px == 5) && (iy % 50 == 0)) {
     99          //   fprintf (stderr, "%d : %d %d : %d, %f\n", iy, Sx, px, dxi, dxf);
     100          // }
     101          // XXX something is not quite right in my math: I think (1-dx), dx are reversed
     102          // but if I use what I expect the interpolation is backwards...
     103          vout = profile->elements.Flt[px]*(1 - dxf) + profile->elements.Flt[px-1]*dxf;
     104        }
     105        if (px == 0) {
     106          vout = profile->elements.Flt[px]*dxf;
     107        }
     108        if (px == profile->Nelements - 1) {
     109          vout = profile->elements.Flt[profile->Nelements - 1]*(1.0 - dxf);
     110        }
     111      } else {
     112        vout = profile->elements.Flt[px];
     113      }
     114
     115      if (flux) vout *= flux->elements.Flt[iy];
     116      if (sky) vout += sky->elements.Flt[iy];
     117
     118      out[ix + iy*Nx] = vout;
    44119    }
    45 
    46120  }
    47121
Note: See TracChangeset for help on using the changeset viewer.