Files
sics/fourtable.c
2012-11-15 12:39:51 +11:00

201 lines
5.1 KiB
C

/*---------------------------------------------------------------------------
F O U R T A B L E
A SICS object which holds the variation of scan parameters for four circle
reflection list measurements.
copyright: see copyright.h
Mark Koennecke, February 2005
Massively reworked to make use of the new hdbtable object.
Mark Koennecke, March 2009
---------------------------------------------------------------------------*/
#include <stdlib.h>
#include <assert.h>
#include "sics.h"
#include "hdbtable.h"
#include <sicshipadaba.h>
#include "fourtable.h"
/*==================== functions =======================================*/
pSICSOBJ MakeFourCircleTable()
{
pSICSOBJ table = NULL;
pHdb node = NULL;
table = MakeHdbTable("fmesstable","FourMess");
node = GetHipadabaNode(table->objectNode,"template");
assert(node != NULL);
AddSICSHdbPar(node, "endTTH", usUser, MakeHdbFloat(.0));
AddSICSHdbPar(node, "scanvar", usUser, MakeHdbText(""));
AddSICSHdbPar(node, "step", usUser, MakeHdbFloat(.0));
AddSICSHdbPar(node, "np", usUser, MakeHdbInt(0));
AddSICSHdbPar(node, "preset", usUser, MakeHdbFloat(.0));
ReadTableTemplate(table, NULL);
return table;
}
/*-----------------------------------------------------------------------*/
void DeleteFourCircleTable(pSICSOBJ data)
{
KillSICSOBJ(data);
}
/*---------------------------------------------------------------------
Make sure that the entry is added in a sorted way according to two_theta
----------------------------------------------------------------------*/
static int rowCompare(const void *r1, const void *r2)
{
pHdb *row1, *row2;
pHdb tth1, tth2;
row1 = (pHdb *)r1;
row2 = (pHdb *)r2;
tth1 = GetHipadabaNode(*row1,"endTTH");
tth2 = GetHipadabaNode(*row2,"endTTH");
assert(tth1 != NULL && tth2 != NULL);
if(tth1->value.v.doubleValue < tth2->value.v.doubleValue){
return -1;
} else if(tth1->value.v.doubleValue > tth2->value.v.doubleValue){
return 1;
} else {
return 0;
}
}
/*--------------------------------------------------------------------*/
static void sortFourTable(pSICSOBJ self)
{
pHdb data, *dataArray, child;
int count, i;
char number[10];
data = GetHipadabaNode(self->objectNode,"data");
assert(data != NULL);
count = CountHdbChildren(data);
if(count <= 1){
return;
}
dataArray = malloc(count*sizeof(pHdb));
if(dataArray == NULL){
return;
}
child = data->child;
count = 0;
while(child != NULL){
dataArray[count] = child;
count++;
child = child->next;
}
qsort(dataArray, count, sizeof(pHdb), rowCompare);
data->child = NULL;
for(i = 0; i < count; i++){
snprintf(number,10,"%4.4d", i);
child = dataArray[i];
if(child->name != NULL){
free(child->name);
}
child->name = strdup(number);
AddHipadabaChild(data,child, NULL);
}
free(dataArray);
}
/*------------------------------------------------------------------------*/
int HandleFourCircleCommands(pSICSOBJ self, SConnection * pCon,
int argc, char *argv[], int *err)
{
int status;
/*
test if this is for us
*/
if (argc >= 3) {
strtolower(argv[1]);
if (strcmp(argv[1], "table") != 0) {
return 0;
}
} else {
return 0;
}
status = InvokeSICSOBJ(pCon,pServ->pSics,self,argc-1,&argv[1]);
if(strcmp(argv[2],"addrow") == 0){
sortFourTable(self);
}
return status;
}
/*-----------------------------------------------------------------------*/
static pHdb findEntry(pSICSOBJ self, double two_theta)
{
pHdb data, row, tth;
data = GetHipadabaNode(self->objectNode,"data");
assert(data != NULL);
row = data->child;
while(row != NULL){
tth = GetHipadabaNode(row,"endTTH");
if(tth != NULL){
if(tth->value.v.doubleValue > two_theta){
return row;
}
}
row = row->next;
}
return NULL;
}
/*------------------------------------------------------------------------*/
char *GetFourCircleScanVar(pSICSOBJ handle, double two_theta)
{
pHdb row, val;
row = findEntry(handle, two_theta);
if(row != NULL){
val = GetHipadabaNode(row,"scanvar");
if(val != NULL){
return strdup(val->value.v.text);
}
}
return strdup("Not found");
}
/*------------------------------------------------------------------------*/
double GetFourCircleStep(pSICSOBJ handle, double two_theta)
{
pHdb row, val;
row = findEntry(handle, two_theta);
if(row != NULL){
val = GetHipadabaNode(row,"step");
if(val != NULL){
return val->value.v.doubleValue;
}
}
return -999.99;
}
/*------------------------------------------------------------------------*/
float GetFourCirclePreset(pSICSOBJ handle, double two_theta)
{
pHdb row, val;
row = findEntry(handle, two_theta);
if(row != NULL){
val = GetHipadabaNode(row,"preset");
if(val != NULL){
return val->value.v.doubleValue;
}
}
return -999.99;
}
/*------------------------------------------------------------------------*/
int GetFourCircleScanNP(pSICSOBJ handle, double two_theta)
{
pHdb row, val;
row = findEntry(handle, two_theta);
if(row != NULL){
val = GetHipadabaNode(row,"np");
if(val != NULL){
return val->value.v.intValue;
}
}
return 1;
}