IPP Software Navigation Tools IPP Links Communication Pan-STARRS Links

Ignore:
Timestamp:
Aug 7, 2009, 4:08:25 PM (17 years ago)
Author:
Paul Price
Message:

Merging trunk (r25026) to get up-to-date on old branch.

Location:
branches/pap
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • branches/pap

  • branches/pap/psModules

    • Property svn:mergeinfo deleted
  • branches/pap/psModules/src/imcombine/pmPSFEnvelope.c

    r23242 r25027  
    3333
    3434
    35 //#define TESTING                         // Enable test output
     35// #define TESTING                         // Enable test output
    3636#define PEAK_FLUX 1.0e4                 // Peak flux for each source
    3737#define SKY_VALUE 0.0e0                 // Sky value for fake image
     
    4040#define PSF_STATS PS_STAT_SAMPLE_MEDIAN | PS_STAT_SAMPLE_STDEV // Statistics options for measuring PSF
    4141#define SOURCE_FIT_ITERATIONS 100       // Number of iterations for source fitting
     42#define MODEL_MASK (PM_MODEL_STATUS_NONCONVERGE | PM_MODEL_STATUS_OFFIMAGE | \
     43                    PM_MODEL_STATUS_BADARGS | PM_MODEL_STATUS_LIMITS) // Mask to apply to models
    4244
    4345
     
    112114    psImageInit(envelope, SKY_VALUE);
    113115    pmReadout *fakeRO = pmReadoutAlloc(NULL); // Fake readout
    114     float maxRadius = 0.0;              // Maximum radius of sources
     116    float maxRadius = 0.0;              // Maximum radius for sources
     117    psVector *numbers = psVectorAlloc(numFakes, PS_TYPE_S32); // Number of detections for each source
     118    psVectorInit(numbers, 0);
    115119    for (int i = 0; i < inputs->n; i++) {
    116120        pmPSF *psf = inputs->data[i];   // PSF of interest
     
    127131            psFree(xOffset);
    128132            psFree(fakes);
     133            psFree(numbers);
    129134            psf->residuals = resid;
    130135            return NULL;
     
    140145
    141146            double flux = fakeRO->image->data.F32[(int)y][(int)x];
     147            if (!isfinite(flux) || flux < 0) {
     148                continue;
     149            }
    142150            float norm = PEAK_FLUX / flux; // Normalisation for source
    143151            psRegion region = psRegionSet(x - radius, x + radius, y - radius, y + radius); // PSF region
     
    151159            // Get the radius
    152160            pmModel *model = pmModelFromPSFforXY(psf, x, y, PEAK_FLUX); // Model for source
    153             psAssert (model, "failed to generate model: should this be an error or not?");
     161            if (!model || (model->flags & MODEL_MASK)) {
     162                continue;
     163            }
    154164            float srcRadius = model->modelRadius(model->params, PS_SQR(VARIANCE_VAL)); // Radius for source
     165            if (srcRadius == 0) {
     166                continue;
     167            }
    155168            if (srcRadius > maxRadius) {
    156169                maxRadius = srcRadius;
    157170            }
    158             psFree(model);
     171
     172            // If we got this far, the source is decent
     173            numbers->data.S32[j]++;
    159174        }
    160175
     
    175190    psFree(fakeRO);
    176191
    177     if (maxRadius > radius) {
    178         maxRadius = radius;
    179     }
    180 
    181192#ifdef TESTING
    182193    {
     
    190201
    191202    // Put the fake sources onto a full-size image
     203    psArray *goodFakes = psArrayAllocEmpty(numFakes); // Good fake sources
    192204    pmReadout *readout = pmReadoutAlloc(NULL); // Readout to contain envelope pixels
    193205    readout->image = psImageAlloc(numCols, numRows, PS_TYPE_F32);
     
    195207    for (int i = 0; i < numFakes; i++) {
    196208        pmSource *source = fakes->data[i]; // Fake source
     209        if (numbers->data.S32[i] > 0) {
     210            psArrayAdd(goodFakes, goodFakes->n, source);
     211        }
     212
    197213        // Position of source on fake image
    198214        int xFake = source->peak->x + xOffset->data.S32[i];
     
    213229            psFree(yOffset);
    214230            psFree(fakes);
     231            psFree(numbers);
    215232            return NULL;
    216233        }
     
    220237    psFree(yOffset);
    221238    psFree(envelope);
     239    psFree(numbers);
     240
     241    psFree(fakes);
     242    fakes = goodFakes;
     243    numFakes = fakes->n;
     244
     245    if (numFakes == 0.0) {
     246        psError(PS_ERR_UNKNOWN, false, "No fake sources are suitable for PSF fitting.");
     247        psFree(fakes);
     248        psFree(readout);
     249        return false;
     250    }
    222251
    223252    // XXX Setting the variance seems to be an art
     
    232261    psImageInit(readout->mask, 0);
    233262
     263    if (maxRadius > radius) {
     264        maxRadius = radius;
     265    }
     266
    234267#ifdef TESTING
    235268    {
     
    243276
    244277    // Reset the sources to point to the new pixels, and measure the moments in preparation for PSF fitting
     278    int numMoments = 0;                 // Number of moments measured
    245279    for (int i = 0; i < numFakes; i++) {
    246280        pmSource *source = fakes->data[i]; // Fake source
     
    257291        source->maskObj = NULL;
    258292
    259         if (!pmSourceDefinePixels(source, readout, x, y, maxRadius)) {
     293        if (!pmSourceDefinePixels(source, readout, x, y, radius)) {
    260294            psError(PS_ERR_UNKNOWN, false, "Unable to define pixels for source.");
    261295            psFree(readout);
     
    264298        }
    265299
    266         if (!pmSourceMoments(source, maxRadius)) {
    267             psError(PS_ERR_UNKNOWN, false, "Unable to measure moments for source.");
    268             psFree(readout);
    269             psFree(fakes);
    270             return NULL;
    271         }
     300        // measure the source moments: tophat windowing, no pixel S/N cutoff
     301        if (!pmSourceMoments(source, maxRadius, 0.0, 1.0)) {
     302            // Can't do anything about it; limp along as best we can
     303            psErrorClear();
     304            continue;
     305        }
     306        numMoments++;
     307    }
     308
     309    if (numMoments == 0) {
     310        psError(PS_ERR_UNKNOWN, true, "Unable to measure moments for sources.");
     311        psFree(fakes);
     312        psFree(readout);
     313        return NULL;
    272314    }
    273315
     
    286328    options->psfFieldXo = 0;
    287329    options->psfFieldYo = 0;
     330    options->chiFluxTrend = false;      // All sources have similar flux, so fitting a trend often fails
    288331
    289332    pmSourceFitModelInit(SOURCE_FIT_ITERATIONS, 0.01, VARIANCE_VAL, true);
Note: See TracChangeset for help on using the changeset viewer.