Index: /trunk/psLib/test/astronomy/tst_psCoord01.c
===================================================================
--- /trunk/psLib/test/astronomy/tst_psCoord01.c	(revision 3471)
+++ /trunk/psLib/test/astronomy/tst_psCoord01.c	(revision 3472)
@@ -6,6 +6,6 @@
 *    @author Eric Van Alst, MHPCC
 *
-*    @version $Revision: 1.2 $ $Name: not supported by cvs2svn $
-*    @date  $Date: 2005-03-19 02:20:02 $
+*    @version $Revision: 1.3 $ $Name: not supported by cvs2svn $
+*    @date  $Date: 2005-03-22 01:37:31 $
 *
 *    Copyright 2005 Maui High Performance Computing Center, Univ. of Hawaii
@@ -26,4 +26,8 @@
 static psS32 testProjectFail(void);
 static psS32 testDeprojectFail(void);
+static psS32 testSetOffsetSphere(void);
+static psS32 testSetOffsetLinear(void);
+static psS32 testGetOffsetSphere(void);
+static psS32 testGetOffsetLinear(void);
 
 testDescription tests[] = {
@@ -39,9 +43,23 @@
                               {testProjectFail, 834, "psProject",0,false},
                               {testDeprojectFail, 835, "psProject",0,false},
+                              {testSetOffsetSphere, 0000, "psSphereSetOffset",0,false},
+                              {testSetOffsetLinear, 0000, "psSphereSetOffset",0,false},
+                              {testGetOffsetSphere, 0000, "psSphereGetOffset",0,false},
+                              {testGetOffsetLinear, 0000, "psSphereGetOffset",0,false},
                               {NULL}
                           };
 
+
 #define ERROR_TOL    0.0001
 #define TESTPOINTS   4
+#define DEG_INC   30.0
+
+#define MY_TINY 0.0001
+#define PS_COMPARE_TINY_THEN_PRINT_ERROR(ACTUAL, EXPECT, TESTSTATUS) \
+if (MY_TINY < fabs(EXPECT - ACTUAL)) { \
+    psError(PS_ERR_UNKNOWN,true,"%s is %lg, should be %lg", #ACTUAL, ACTUAL, EXPECT, TESTSTATUS); \
+    return TESTSTATUS; \
+}
+
 
 //  alpha, delta, alpha-center, delta-center, scale-x, scale-y
@@ -84,4 +102,49 @@
             {  1.432951,  0.971372 }
         };
+
+// Testpoints, offset and expected values for psSphereSetOffset test
+#define TESTPOINTS_OFFSET  4
+psF64 setOffsetTestpoint[TESTPOINTS_OFFSET][2] = {
+            { 0.50,  0.50 },
+            {-0.50,  0.50 },
+            { 0.00,  0.00 },
+            { 1.50, -0.10 }
+        };
+
+psF64 setOffsetOffset[TESTPOINTS_OFFSET][2] = {
+            { 0.190761, -0.272205 },
+            {-0.553049, -0.460926 },
+            { 0.100335,-14.172222 },
+            {14.172222, -0.100335 }
+        };
+
+psF64 setOffsetResult[TESTPOINTS_OFFSET][2] = {
+            { 0.25,  0.75 },
+            { 0.20,  0.80 },
+            {-0.10,  1.50 },
+            { 0.00,  0.00 }
+        };
+
+psF64 getOffsetTestpoint1[TESTPOINTS_OFFSET][2] = {
+            { 0.00,  0.00 },
+            {-0.25,  0.50 },
+            { 0.50, -0.25 },
+            { 0.25, -0.10 }
+        };
+
+psF64 getOffsetTestpoint2[TESTPOINTS_OFFSET][2] = {
+            { 0.75,  0.25 },
+            { 0.40, -0.60 },
+            { 1.50,  0.50 },
+            { 0.10,  0.75 }
+        };
+
+psF64 getOffsetResult[TESTPOINTS_OFFSET][2] = {
+            { -0.931596, -0.348976 },
+            { -1.632830,  2.649629 },
+            { -2.166795, -1.707211 },
+            {  0.167752, -1.151351 }
+        };
+
 
 psS32 main( psS32 argc, char* argv[] )
@@ -577,2 +640,278 @@
 }
 
+psS32 testSetOffsetSphere( void )
+{
+    psSphere* position1 = psSphereAlloc();
+    psSphere* position2 = NULL;
+    psSphere* offset    = psSphereAlloc();
+    psSphere* tmpOffset = psSphereAlloc();
+
+    // Initialize first position
+    position1->r = DEG_TO_RAD(90.0);
+    position1->d = DEG_TO_RAD(45.0);
+    position1->rErr = 0.0;
+    position1->dErr = 0.0;
+
+    //  Using various offset verify spherical offset
+    //  Use all the valid unit types
+    for (psF64 r = 0.0; r < 180.0; r += DEG_INC) {
+        for (psF64 d = 0.0; d < 90.0; d += DEG_INC) {
+
+            offset->r = DEG_TO_RAD(r);
+            offset->d = DEG_TO_RAD(d);
+            offset->rErr = 0.0;
+            offset->dErr = 0.0;
+
+            position2 = psSphereSetOffset(position1, offset, PS_SPHERICAL, PS_RADIAN);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(position2->r, (position1->r + offset->r), 1);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(position2->d, (position1->d + offset->d), 2);
+            psFree(position2);
+
+            tmpOffset->r = RAD_TO_DEG(offset->r);
+            tmpOffset->d = RAD_TO_DEG(offset->d);
+            tmpOffset->rErr = 0.0;
+            tmpOffset->dErr = 0.0;
+            position2 = psSphereSetOffset(position1, tmpOffset, PS_SPHERICAL, PS_DEGREE);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(position2->r, (position1->r + offset->r), 3);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(position2->d, (position1->d + offset->d), 4);
+            psFree(position2);
+
+            tmpOffset->r = RAD_TO_MIN(offset->r);
+            tmpOffset->d = RAD_TO_MIN(offset->d);
+            tmpOffset->rErr = 0.0;
+            tmpOffset->dErr = 0.0;
+            position2 = psSphereSetOffset(position1, tmpOffset, PS_SPHERICAL, PS_ARCMIN);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(position2->r, (position1->r + offset->r), 5);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(position2->d, (position1->d + offset->d), 6);
+            psFree(position2);
+
+            tmpOffset->r = RAD_TO_SEC(offset->r);
+            tmpOffset->d = RAD_TO_SEC(offset->d);
+            tmpOffset->rErr = 0.0;
+            tmpOffset->dErr = 0.0;
+            position2 = psSphereSetOffset(position1, tmpOffset, PS_SPHERICAL, PS_ARCSEC);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(position2->r, (position1->r + offset->r), 7);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(position2->d, (position1->d + offset->d), 8);
+            psFree(position2);
+        }
+    }
+
+    // Attempt to call function with null input coordinate
+    psLogMsg(__func__,PS_LOG_INFO,"Following should generate error message null input coord");
+    position2 = psSphereSetOffset(NULL, offset, PS_LINEAR, PS_ARCSEC);
+    if (position2 != NULL) {
+        psError(PS_ERR_UNKNOWN,true,"Did not return NULL");
+        return 30;
+    }
+
+    // Attempt to call function with null offset
+    psLogMsg(__func__,PS_LOG_INFO,"Following should generate error message null offset");
+    position2 = psSphereSetOffset(position1, NULL, PS_LINEAR, PS_ARCSEC);
+    if (position2 != NULL) {
+        psError(PS_ERR_UNKNOWN,true,"Did not return NULL");
+        return 31;
+    }
+
+    // Attempt to call function with invalid mode
+    psLogMsg(__func__,PS_LOG_INFO,"Following should generate error message invalid mode");
+    position2 = psSphereSetOffset(position1, offset, 0x54321, 0);
+    if (position2 != NULL) {
+        psError(PS_ERR_UNKNOWN,true,"Did not return NULL");
+        return 32;
+    }
+
+    // Attempt to call function with invalid unit
+    psLogMsg(__func__,PS_LOG_INFO,"Following should generate an error message invalid unit");
+    position2 = psSphereSetOffset(position1, offset, PS_SPHERICAL, 0x54321);
+    if (position2 != NULL) {
+        psError(PS_ERR_UNKNOWN,true,"Did not return NULL");
+        return 33;
+    }
+
+    psFree(position1);
+    psFree(offset);
+    psFree(tmpOffset);
+
+    return 0;
+}
+
+psS32 testSetOffsetLinear(void)
+{
+    psSphere*   coord = psSphereAlloc();
+    psSphere*   offset = psSphereAlloc();
+    psSphere*   out = NULL;
+
+    for(psS32 i = 0; i < TESTPOINTS_OFFSET; i++) {
+
+        coord->r = setOffsetTestpoint[i][0];
+        coord->d = setOffsetTestpoint[i][1];
+
+        offset->r = setOffsetOffset[i][0];
+        offset->d = setOffsetOffset[i][1];
+
+        out = psSphereSetOffset(coord, offset, PS_LINEAR, PS_RADIAN);
+
+        if(fabs(out->r - setOffsetResult[i][0]) > ERROR_TOL) {
+            psError(PS_ERR_UNKNOWN,true,"Testpoint %d: Result out->r = %lg not equal to expected %lg",
+                    i, out->r, setOffsetResult[i][0]);
+            return i*10;
+        }
+        if(fabs(out->d - setOffsetResult[i][1]) > ERROR_TOL) {
+            psError(PS_ERR_UNKNOWN,true,"Testpoint %d: Result out->d = %lg not equal to expected %lg",
+                    i,out->d, setOffsetResult[i][1]);
+            return i*10+1;
+        }
+
+        psFree(out);
+    }
+
+    psFree(coord);
+    psFree(offset);
+
+    return 0;
+}
+
+psS32 testGetOffsetSphere( void )
+{
+    psSphere* position1 = psSphereAlloc();
+    psSphere* position2 = psSphereAlloc();
+    psSphere *offset = NULL;
+
+    position1->r = DEG_TO_RAD(90.0);
+    position1->d = DEG_TO_RAD(45.0);
+    position1->rErr = 0.0;
+    position1->dErr = 0.0;
+
+    for (psF64 r = 0.0; r < 180.0;r += DEG_INC) {
+        for (psF64 d = 0.0;d < 90.0; d += DEG_INC) {
+            position2->r = DEG_TO_RAD(r);
+            position2->d = DEG_TO_RAD(d);
+            position2->rErr = 0.0;
+            position2->dErr = 0.0;
+
+            offset = psSphereGetOffset( position1,  position2,
+                                        PS_SPHERICAL, PS_RADIAN);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(offset->r, (position2->r - position1->r), 1);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(offset->d, (position2->d - position1->d), 1);
+            psFree(offset);
+
+            offset = psSphereGetOffset( position1, position2,
+                                        PS_SPHERICAL, PS_DEGREE);
+            offset->r = DEG_TO_RAD(offset->r);
+            offset->d = DEG_TO_RAD(offset->d);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(offset->r, (position2->r - position1->r), 2);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(offset->d, (position2->d - position1->d), 3);
+            psFree(offset);
+
+            offset = psSphereGetOffset( position1,  position2,
+                                        PS_SPHERICAL, PS_ARCMIN);
+            offset->r = MIN_TO_RAD(offset->r);
+            offset->d = MIN_TO_RAD(offset->d);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(offset->r, (position2->r - position1->r), 2);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(offset->d, (position2->d - position1->d), 3);
+            psFree(offset);
+
+            offset = psSphereGetOffset( position1,  position2,
+                                        PS_SPHERICAL, PS_ARCSEC);
+            offset->r = SEC_TO_RAD(offset->r);
+            offset->d = SEC_TO_RAD(offset->d);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(offset->r, (position2->r - position1->r), 2);
+            PS_COMPARE_TINY_THEN_PRINT_ERROR(offset->d, (position2->d - position1->d), 3);
+            psFree(offset);
+        }
+    }
+
+    // Attempt to invoke function with null position 1 parameter
+    psLogMsg(__func__,PS_LOG_INFO,"Following should generate an error message for null position");
+    offset = psSphereGetOffset(NULL, position2, PS_LINEAR, 0);
+    if (offset != NULL) {
+        psError(PS_ERR_UNKNOWN,true,"Did not return NULL as expected");
+        return 10;
+    }
+
+    // Attempt to invoke function with null position 2 parameter
+    psLogMsg(__func__,PS_LOG_INFO,"Following should generate an error message for null position");
+    offset = psSphereGetOffset(position1, NULL, PS_LINEAR, 0);
+    if (offset != NULL) {
+        psError(PS_ERR_UNKNOWN,true,"Did not return NULL as expected");
+        return 11;
+    }
+
+    // Attempt to invoke function with invalid mode
+    psLogMsg(__func__,PS_LOG_INFO,"Following should generate an error message for invalid mode");
+    offset = psSphereGetOffset(position1, position2, 0x54321, 0);
+    if (offset != NULL) {
+        psError(PS_ERR_UNKNOWN,true,"Did not return NULL as expected");
+        return 12;
+    }
+
+    // Attempt to invoke function with invalid unit type
+    psLogMsg(__func__,PS_LOG_INFO,"Following should generate an error message for invalid unit type");
+    offset = psSphereGetOffset(position1, position2, PS_SPHERICAL, 0x54321);
+    if (offset != NULL) {
+        psError(PS_ERR_UNKNOWN,true,"Did not return NULL as expected");
+        return 13;
+    }
+
+    // Attempt to invoke function with coordinate 1 declination value 90.0 degree
+    position1->d = DEG_TO_RAD(90.0);
+    psLogMsg(__func__,PS_LOG_INFO,"Following should generate warning message");
+    offset = psSphereGetOffset(position1, position2, PS_SPHERICAL, PS_RADIAN);
+    if (offset != NULL) {
+        psError(PS_ERR_UNKNOWN,true,"Did not return NULL as expected");
+        return 14;
+    }
+
+    // Attempt to invoke function with coordinate 2 declination value 90.0 degree
+    position1->d = DEG_TO_RAD(45.0);
+    position2->d = DEG_TO_RAD(90.0);
+    psLogMsg(__func__,PS_LOG_INFO,"Following should generate warning message");
+    offset = psSphereGetOffset(position1, position2, PS_SPHERICAL, PS_RADIAN);
+    if (offset != NULL) {
+        psError(PS_ERR_UNKNOWN,true,"Did not return NULL as expected");
+        return 15;
+    }
+
+    psFree(position1);
+    psFree(position2);
+
+    return 0;
+}
+
+psS32 testGetOffsetLinear(void)
+{
+    psSphere*   coord1 = psSphereAlloc();
+    psSphere*   coord2 = psSphereAlloc();
+    psSphere*   out = NULL;
+
+    for(psS32 i = 0; i < TESTPOINTS_OFFSET; i++) {
+
+        coord1->r = getOffsetTestpoint1[i][0];
+        coord1->d = getOffsetTestpoint1[i][1];
+
+        coord2->r = getOffsetTestpoint2[i][0];
+        coord2->d = getOffsetTestpoint2[i][1];
+
+        out = psSphereGetOffset(coord1, coord2, PS_LINEAR, PS_RADIAN);
+
+        if(fabs(out->r - getOffsetResult[i][0]) > ERROR_TOL) {
+            psError(PS_ERR_UNKNOWN,true,"Testpoint %d: Result out->r = %lg not equal to expected %lg",
+                    i, out->r, getOffsetResult[i][0]);
+            return i*10;
+        }
+        if(fabs(out->d - getOffsetResult[i][1]) > ERROR_TOL) {
+            psError(PS_ERR_UNKNOWN,true,"Testpoint %d: Result out->d = %lg not equal to expected %lg",
+                    i,out->d, getOffsetResult[i][1]);
+            return i*10+1;
+        }
+
+        psFree(out);
+    }
+
+    psFree(coord1);
+    psFree(coord2);
+
+    return 0;
+}
+
+
Index: /trunk/psLib/test/astronomy/verified/tst_psCoord01.stderr
===================================================================
--- /trunk/psLib/test/astronomy/verified/tst_psCoord01.stderr	(revision 3471)
+++ /trunk/psLib/test/astronomy/verified/tst_psCoord01.stderr	(revision 3472)
@@ -122,2 +122,78 @@
 ---> TESTPOINT PASSED (psCoord{psProject} | tst_psCoord01.c)
 
+/***************************** TESTPOINT ******************************************\
+*             TestFile: tst_psCoord01.c                                            *
+*            TestPoint: psCoord{psSphereSetOffset}                                 *
+*             TestType: Positive                                                   *
+\**********************************************************************************/
+
+<DATE><TIME>|<HOST>|I|testSetOffsetSphere
+    Following should generate error message null input coord
+<DATE><TIME>|<HOST>|E|psSphereSetOffset (FILE:LINENO)
+    Unallowable operation: position is NULL.
+<DATE><TIME>|<HOST>|I|testSetOffsetSphere
+    Following should generate error message null offset
+<DATE><TIME>|<HOST>|E|psSphereSetOffset (FILE:LINENO)
+    Unallowable operation: offset is NULL.
+<DATE><TIME>|<HOST>|I|testSetOffsetSphere
+    Following should generate error message invalid mode
+<DATE><TIME>|<HOST>|E|psSphereSetOffset (FILE:LINENO)
+    Specified offset mode, 0x54321, is not supported.
+<DATE><TIME>|<HOST>|I|testSetOffsetSphere
+    Following should generate an error message invalid unit
+<DATE><TIME>|<HOST>|E|psSphereSetOffset (FILE:LINENO)
+    Specified units, 0x54321, is not supported.
+
+---> TESTPOINT PASSED (psCoord{psSphereSetOffset} | tst_psCoord01.c)
+
+/***************************** TESTPOINT ******************************************\
+*             TestFile: tst_psCoord01.c                                            *
+*            TestPoint: psCoord{psSphereSetOffset}                                 *
+*             TestType: Positive                                                   *
+\**********************************************************************************/
+
+
+---> TESTPOINT PASSED (psCoord{psSphereSetOffset} | tst_psCoord01.c)
+
+/***************************** TESTPOINT ******************************************\
+*             TestFile: tst_psCoord01.c                                            *
+*            TestPoint: psCoord{psSphereGetOffset}                                 *
+*             TestType: Positive                                                   *
+\**********************************************************************************/
+
+<DATE><TIME>|<HOST>|I|testGetOffsetSphere
+    Following should generate an error message for null position
+<DATE><TIME>|<HOST>|E|psSphereGetOffset (FILE:LINENO)
+    Unallowable operation: position1 is NULL.
+<DATE><TIME>|<HOST>|I|testGetOffsetSphere
+    Following should generate an error message for null position
+<DATE><TIME>|<HOST>|E|psSphereGetOffset (FILE:LINENO)
+    Unallowable operation: position2 is NULL.
+<DATE><TIME>|<HOST>|I|testGetOffsetSphere
+    Following should generate an error message for invalid mode
+<DATE><TIME>|<HOST>|E|psSphereGetOffset (FILE:LINENO)
+    Specified offset mode, 0x54321, is not supported.
+<DATE><TIME>|<HOST>|I|testGetOffsetSphere
+    Following should generate an error message for invalid unit type
+<DATE><TIME>|<HOST>|E|psSphereGetOffset (FILE:LINENO)
+    Specified units, 0x54321, is not supported.
+<DATE><TIME>|<HOST>|I|testGetOffsetSphere
+    Following should generate warning message
+<DATE><TIME>|<HOST>|W|psSphereGetOffset
+    WARNING: psDeproject(): position1->d is larger than 90 degrees.  Returning NULL.
+<DATE><TIME>|<HOST>|I|testGetOffsetSphere
+    Following should generate warning message
+<DATE><TIME>|<HOST>|W|psSphereGetOffset
+    WARNING: psDeproject(): position2->d is larger than 90 degrees.  Returning NULL.
+
+---> TESTPOINT PASSED (psCoord{psSphereGetOffset} | tst_psCoord01.c)
+
+/***************************** TESTPOINT ******************************************\
+*             TestFile: tst_psCoord01.c                                            *
+*            TestPoint: psCoord{psSphereGetOffset}                                 *
+*             TestType: Positive                                                   *
+\**********************************************************************************/
+
+
+---> TESTPOINT PASSED (psCoord{psSphereGetOffset} | tst_psCoord01.c)
+
