# include "relastro.h"
void dump_measures (Average *average, Measure *measure); // in ImageOps.c

// this function is called by UpdateObjectOffsets or relastro_images.c for reset
int UpdateMeasures (Catalog *catalog, int Ncatalog) {

  off_t i, j, Nimage;
  Image *image;
  double DPOS_MAX_ASEC;

  image = getimages (&Nimage, NULL);

  // track measurements which are far from their original position (poor at pole)
  int NoffRAori = 0; 
  int NoffDECori = 0;

  for (i = 0; i < Ncatalog; i++) {
    myAssert (!catalog[i].Nmeasure || catalog[i].measureT, "programming error");
    for (j = 0; j < catalog[i].Naverage; j++) {
      // normalize R,D to 0,360 & -90,90
      Average *average = &catalog[i].average[j];
      average[0].R = ohana_normalize_angle_to_midpoint(average[0].R, 180.0);
      average[0].D = ohana_normalize_angle_to_midpoint(average[0].D,   0.0);
    }

    for (j = 0; j < catalog[i].Nmeasure; j++) {
      MeasureTiny *measureT = &catalog[i].measureT[j];
      Measure     *measureB = catalog[i].measure ? &catalog[i].measure[j] : NULL;

      off_t im = getImageByID (measureT->imageID);
      if (im < 0) continue; // detections without imageIDs are not associated with a known image (eg, refs)

      // check that we have the right image:
      myAssert (measureT->photcode == image[im].photcode, "image photcode mismatch");
      myAssert (measureT->t >= image[im].tzero, "image time mismatch (1)");
      myAssert (measureT->t <= image[im].tzero + image[im].NX*image[im].trate/5000.0, "image time mismatch (2)");
      // I'm allowing the trate*NX to be a factor of 2x too small

      Coords *moscoords = image[im].coords.mosaic;
      Coords *imcoords = &image[im].coords;

      if (moscoords) {
	DPOS_MAX_ASEC = 3600.0*DPOS_MAX*hypot(moscoords->cdelt1, moscoords->cdelt2);
      } else {
	DPOS_MAX_ASEC = 3600.0*DPOS_MAX*hypot(imcoords->cdelt1, imcoords->cdelt2);
      }

      double X = measureT->Xccd;
      double Y = measureT->Yccd;
      if (USE_FIXED_PIXCOORDS) {
	if (isfinite(measureT->Xfix) && isfinite(measureT->Yfix)) {
	  float dX = measureT->Xfix - measureT->Xccd;
	  float dY = measureT->Yfix - measureT->Yccd;
	  if (hypot(dX,dY) < 2.0) {
	    X = measureT->Xfix;
	    Y = measureT->Yfix;
	  } 
	}
      }

      double R, D;
      XY_to_RD (&R, &D, X, Y, imcoords);

      R = ohana_normalize_angle_to_midpoint(R, 180.0);
      D = ohana_normalize_angle_to_midpoint(D,   0.0);

      double oldR = ohana_normalize_angle_to_midpoint(measureT[0].R, 180.0);
      double oldD = ohana_normalize_angle_to_midpoint(measureT[0].D,   0.0);

      float csdec = cos(oldD * RAD_DEG);

      double dR = 3600.0*fabs(csdec*(oldR - R));
      double dD = 3600.0*fabs(oldD - D);

      // complain if the new location is far from the old location
      if (dR > DPOS_MAX_ASEC) {
	NoffRAori ++;
	if (VERBOSE2 && catalog[i].measure) {
	  fprintf (stderr, "measurement moves far from original location (R): %f %f : %f %f (%f)\n", oldR, oldD, R, D, dR);
	}
      }
      if (dD > DPOS_MAX_ASEC) {
	NoffDECori ++;
	if (VERBOSE2 && catalog[i].measure) {
	  fprintf (stderr, "measurement moves far from original location (D): %f %f : %f %f (%f)\n", oldR, oldD, R, D, dD);
	}
      }
      measureT->R = R;
      measureT->D = D;
      if (measureB) {
	measureB->R = R;
	measureB->D = D;
      }
    }
  }
  // printNcatTotal ();

  int Noff = NoffRAori + NoffDECori;
  if (VERBOSE && (Noff > 0)) fprintf (stderr, "Noff ori RA %d, Noff ori DEC %d\n", NoffRAori, NoffDECori);

  return (TRUE);
}

// this function operates on Measure, not MeasureTiny
int UpdateMeasuresOld (Catalog *catalog, int Ncatalog) {

  off_t i, Nimage;
  Image *image;

  int badImage = 
    ID_IMAGE_ASTROM_NOCAL | 
    ID_IMAGE_ASTROM_POOR | 
    ID_IMAGE_ASTROM_FAIL | 
    ID_IMAGE_ASTROM_SKIP | 
    ID_IMAGE_ASTROM_FEW;

  if (RESET_BAD_IMAGES) badImage = 0;

  image = getimages (&Nimage, NULL);

  for (i = 0; i < Nimage; i++) {

    /* skip DIS images (since they have no associated detections) */
    if (!strcmp(&image[i].coords.ctype[4], "-DIS")) continue;

    // skip images that have failed solutions (divergent or otherwise)
    if (image[i].flags & badImage) continue;

    /* convert measure coordinates to raw entries */
    fixImageRaw (catalog, Ncatalog, i);
  }

  // printNcatTotal ();

  return (TRUE);
}

