/** @file  pmPhotObj.c
 *
 *  @author EAM, IfA
 *
 *  @version $Revision: 1.13 $ $Name: not supported by cvs2svn $
 *  @date $Date: 2006-09-15 09:49:01 $
 * Copyright 2009 Institute for Astronomy, University of Hawaii
 */

#ifdef HAVE_CONFIG_H
#include <config.h>
#endif

#include <stdio.h>
#include <math.h>
#include <string.h>
#include <pslib.h>
#include "pmPhotObj.h"
#include "pmSource.h"

static void pmPhotObjFree (pmPhotObj *tmp)
{
    if (!tmp) return;
    psFree(tmp->sources);
}


pmPhotObj *pmPhotObjAlloc() 
{
    static int id = 1;
    pmPhotObj *obj = (pmPhotObj *) psAlloc(sizeof(pmPhotObj));
    psMemSetDeallocator(obj, (psFreeFunc) pmPhotObjFree);

    *(int *)&obj->id = id; // cast away the const to set the id.
    id++;

    obj->sources = NULL;
    return obj;
}

bool pmPhotObjAddSource(pmPhotObj *object, pmSource *source) {

    psAssert (source, "programming error: NULL source");
    if (!source->peak) {
	psError(PS_ERR_UNKNOWN, true, "source missing peak");
	return false; 
    }
    if (!finite(source->peak->xf)) {
	psError(PS_ERR_UNKNOWN, true, "NAN peak coordinate");
	return false; 
    }
    if (!finite(source->peak->yf)) {
	psError(PS_ERR_UNKNOWN, true, "NAN peak coordinate");
	return false; 
    }

    // XXX we should probably use the fitted position if it exists
    if (!object->sources) {
	object->sources = psArrayAllocEmpty(1);
	object->x  = source->peak->xf;
	object->y  = source->peak->yf;
	object->SN = source->peak->SN;
    } else {
	object->SN = PS_MAX(object->SN, source->peak->SN);
    }
    psArrayAdd (object->sources, 1, source);
    return true;
}

// sort by SN (descending)
int pmPhotObjSortBySN (const void **a, const void **b)
{
    pmPhotObj *objA = *(pmPhotObj **)a;
    pmPhotObj *objB = *(pmPhotObj **)b;

    psF32 fA = objA->SN;
    psF32 fB = objB->SN;

    psF32 diff = fA - fB;
    if (diff > FLT_EPSILON) return (-1);
    if (diff < FLT_EPSILON) return (+1);
    return (0);
}
