Changeset 9315
- Timestamp:
- Oct 5, 2006, 1:36:26 PM (20 years ago)
- Location:
- trunk/psModules/src/detrend
- Files:
-
- 2 edited
-
pmShutterCorrection.c (modified) (6 diffs)
-
pmShutterCorrection.h (modified) (2 diffs)
Legend:
- Unmodified
- Added
- Removed
-
trunk/psModules/src/detrend/pmShutterCorrection.c
r9298 r9315 121 121 psError(PS_ERR_BAD_PARAMETER_VALUE, true, 122 122 "Not enough good values to guess shutter correction.\n"); 123 goto ERROR;123 goto GUESS_ERROR; 124 124 } 125 125 tmpX->data.F32[0] = exptime->data.F32[index]; … … 133 133 psError(PS_ERR_BAD_PARAMETER_VALUE, true, 134 134 "Exposure times are all identical --- cannot guess shutter correction.\n"); 135 goto ERROR;135 goto GUESS_ERROR; 136 136 } 137 137 tmpY->data.F32[1] = counts->data.F32[index]; … … 141 141 if (!psVectorFitPolynomial1D(line, NULL, 0, tmpY, NULL, tmpX)) { 142 142 psError(PS_ERR_UNEXPECTED_NULL, false, "Unable to fit for the time offset.\n"); 143 goto ERROR;143 goto GUESS_ERROR; 144 144 } 145 145 float ratio = psPolynomial1DEval(line, 0.0) / corr->scale; … … 170 170 if (!psVectorFitPolynomial1D (line, NULL, 0, tmpY, NULL, tmpX)) { 171 171 psError(PS_ERR_UNEXPECTED_NULL, false, "Unable to fit for the reference offset.\n"); 172 goto ERROR;172 goto GUESS_ERROR; 173 173 } 174 174 corr->offref = psPolynomial1DEval(line, value); … … 181 181 return corr; 182 182 183 ERROR:183 GUESS_ERROR: 184 184 psFree(tmpX); 185 185 psFree(tmpY); … … 344 344 return corr; 345 345 } 346 347 ////////////////////////////////////////////////////////////////////////////////////////////////////////////// 348 349 #define MEASURE_SAMPLES 4 350 351 psImage *pmShutterCorrectionMeasure(const psVector *exptimes, // Exposure times 352 const psArray *images, // Input images 353 const psArray *masks, // Mask images 354 unsigned int size, // Size of samples 355 psStatsOptions meanStat, // Statistic to use for mean 356 psStatsOptions stdevStat, // Statistic to use for stdev 357 psMaskType maskVal // Mask value 358 ) 359 { 360 PS_ASSERT_VECTOR_NON_NULL(exptimes, NULL); 361 PS_ASSERT_VECTOR_TYPE(exptimes, PS_TYPE_F32, NULL); 362 PS_ASSERT_ARRAY_NON_NULL(images, NULL); 363 if (masks) { 364 PS_ASSERT_ARRAYS_SIZE_EQUAL(images, masks, NULL); 365 } 366 long num = images->n; // Number of images 367 PS_ASSERT_VECTOR_SIZE(exptimes, num, NULL); 368 369 // Check input sizes, generate first-pass statistics 370 psRegion refRegion; // Reference region 371 psVector *refs = psVectorAlloc(num, PS_TYPE_F32); // Reference measurements 372 refs->n = num; 373 psVectorInit(refs, 0); 374 psArray *regions = psArrayAlloc(MEASURE_SAMPLES); // Array of sample regions, made on each image 375 regions->n = MEASURE_SAMPLES; 376 psImage *samplesMean = psImageAlloc(num, MEASURE_SAMPLES, PS_TYPE_F32); // Measurements for each file 377 psImage *samplesStdev = psImageAlloc(num, MEASURE_SAMPLES, PS_TYPE_F32); // Errors for each file 378 psStats *stats = psStatsAlloc(meanStat | stdevStat); 379 int numRows = 0, numCols = 0; // Size of images 380 for (long i = 0; i < images->n; i++) { 381 psImage *image = images->data[i]; // Image of interest 382 if (!image) { 383 continue; 384 } 385 if (numRows == 0 || numCols == 0) { 386 numRows = image->numRows; 387 numCols = image->numCols; 388 // Set up the sample regions 389 refRegion = psRegionForSquare(0.5 * numCols, 0.5 * numRows, size); 390 for (int j = 0; j < MEASURE_SAMPLES; j++) { 391 int x = (j % 2) ? size : image->numCols - size; 392 int y = (j > 1) ? size : image->numRows - size; 393 psRegion region = psRegionForSquare(x, y, size); 394 region = psRegionForImage(image, region); 395 regions->data[j] = psRegionAlloc(region.x0, region.x1, region.y0, region.y1); 396 } 397 } else if (numRows != image->numRows || numCols != image->numCols) { 398 psError(PS_ERR_BAD_PARAMETER_SIZE, true, 399 "Image sizes don't match: %dx%d vs %dx%d\n", image->numCols, image->numRows, 400 numCols, numRows); 401 goto MEASURE_ERROR; 402 } 403 404 // Measure statistics 405 if (!psImageStats(stats, image, masks->data[i], maskVal)) { 406 psWarning("Unable to measure reference statistics.\n"); 407 } 408 refs->data.F32[i] = psStatsGetValue(stats, meanStat); 409 if (refs->data.F32[i] <= 0.0) { 410 psError(PS_ERR_UNKNOWN, true, "Measured non-positive reference value.\n"); 411 goto MEASURE_ERROR; 412 } 413 refs->data.F32[i] = 1.0 / refs->data.F32[i]; 414 for (int j = 0; j < MEASURE_SAMPLES; j++) { 415 psRegion *region = regions->data[j]; // Region of interest 416 psImage *subImage = psImageSubset(image, *region); // Sub-image 417 if (!psImageStats(stats, subImage, masks->data[i], maskVal)) { 418 psString regionString = psRegionToString(*region); 419 psWarning("Unable to measure sample statistics at %s in image %ld.\n", 420 regionString, i); 421 psFree(regionString); 422 } 423 psFree(subImage); 424 samplesMean->data.F32[j][i] = psStatsGetValue(stats, meanStat) * refs->data.F32[i]; 425 samplesStdev->data.F32[j][i] = psStatsGetValue(stats, stdevStat) * refs->data.F32[i]; 426 } 427 } 428 psFree(regions); 429 psFree(stats); 430 431 float meanRef = 0.0; // Mean reference offset 432 int numGood = 0; // Number of good measurements 433 psVector *counts = psVectorAlloc(num, PS_TYPE_F32); // Mean for each image 434 psVector *errors = psVectorAlloc(num, PS_TYPE_F32); // Stdev for each image 435 for (int i = 0; i < MEASURE_SAMPLES; i++) { 436 counts = psImageRow(counts, samplesMean, i); 437 errors = psImageRow(errors, samplesStdev, i); 438 pmShutterCorrection *guess = pmShutterCorrectionGuess(exptimes, counts); // Guess at correction 439 pmShutterCorrection *params = pmShutterCorrectionFullFit(exptimes, counts, errors, guess); // Correc'n 440 if (isfinite(params->offref)) { 441 meanRef += params->offref; 442 numGood++; 443 } 444 psFree(params); 445 psFree(guess); 446 } 447 psFree(samplesMean); 448 psFree(samplesStdev); 449 450 if (numGood == 0) { 451 psError(PS_ERR_UNKNOWN, true, "Unable to measure mean reference offset.\n"); 452 psFree(counts); 453 psFree(errors); 454 goto MEASURE_ERROR; 455 } 456 meanRef /= (float)numGood; 457 458 psImage *shutter = psImageAlloc(numCols, numRows, PS_TYPE_F32); // Shutter correction image 459 //psImage *pattern = psImageAlloc(numCols, numRows, PS_TYPE_F32); // Illumination pattern 460 for (int y = 0; y < numRows; y++) { 461 for (int x = 0; x < numCols; x++) { 462 for (int i = 0; i < num; i++) { 463 psImage *image = images->data[i]; // Image of interest 464 counts->data.F32[i] = image->data.F32[y][x] * refs->data.F32[i]; 465 errors->data.F32[i] = sqrtf(image->data.F32[y][x]) * refs->data.F32[i]; 466 } 467 468 pmShutterCorrection *corr = pmShutterCorrectionLinFit(exptimes, counts, errors, meanRef); 469 shutter->data.F32[y][x] = corr->offset; 470 //pattern->data.F32[y][x] = corr->scale; 471 psFree(corr); 472 } 473 } 474 psFree(counts); 475 psFree(errors); 476 psFree(refs); 477 478 return shutter; 479 480 481 MEASURE_ERROR: 482 // Clean up after error 483 psFree(refs); 484 psFree(regions); 485 psFree(stats); 486 psFree(samplesMean); 487 psFree(samplesStdev); 488 return NULL; 489 } -
trunk/psModules/src/detrend/pmShutterCorrection.h
r9298 r9315 48 48 * @author Eugene Magnier, IfA 49 49 * 50 * @version $Revision: 1. 5$ $Name: not supported by cvs2svn $51 * @date $Date: 2006-10-05 2 0:48:56 $50 * @version $Revision: 1.6 $ $Name: not supported by cvs2svn $ 51 * @date $Date: 2006-10-05 23:36:26 $ 52 52 * 53 53 * Copyright 2004 Maui High Performance Computing Center, University of Hawaii 54 54 */ 55 56 #ifndef PM_SHUTTER_CORRECTION_H 57 #define PM_SHUTTER_CORRECTION_H 55 58 56 59 #include "pslib.h" … … 88 91 const pmShutterCorrection *guess // Initial guess 89 92 ); 93 94 // Measure a shutter correction image from an array of images 95 psImage *pmShutterCorrectionMeasure(const psVector *exptimes, // Exposure times 96 const psArray *images, // Input images 97 const psArray *masks, // Mask images 98 unsigned int size, // Size of samples 99 psStatsOptions meanStat, // Statistic to use for mean 100 psStatsOptions stdevStat, // Statistic to use for stdev 101 psMaskType maskVal // Mask value 102 ); 103 104 #endif
Note:
See TracChangeset
for help on using the changeset viewer.
