Subversion Repositories planix.SVN

Rev

Rev 2 | Blame | Compare with Previous | Last modification | View Log | RSS feed

#include <u.h>
#include <libc.h>
#include <bio.h>
#include "sky.h"

double  PI_180  = 0.0174532925199432957692369;
double  TWOPI   = 6.2831853071795864769252867665590057683943387987502;
double  LN2     = 0.69314718055994530941723212145817656807550013436025;
static double angledangle=(180./PI)*MILLIARCSEC;

int
rint(char *p, int n)
{
        int i=0;

        while(*p==' ' && n)
                p++, --n;
        while(n--)
                i=i*10+*p++-'0';
        return i;
}

DAngle
dangle(Angle angle)
{
        return angle*angledangle;
}

Angle
angle(DAngle dangle)
{
        return dangle/angledangle;
}

double
rfloat(char *p, int n)
{
        double i, d=0;

        while(*p==' ' && n)
                p++, --n;
        if(*p == '+')
                return rfloat(p+1, n-1);
        if(*p == '-')
                return -rfloat(p+1, n-1);
        while(*p == ' ' && n)
                p++, --n;
        if(n == 0)
                return 0.0;
        while(n-- && *p!='.')
                d = d*10+*p++-'0';
        if(n <= 0)
                return d;
        p++;
        i = 1;
        while(n--)
                d+=(*p++-'0')/(i*=10.);
        return d;
}

int
sign(int c)
{
        if(c=='-')
                return -1;
        return 1;
}

char*
hms(Angle a)
{
        static char buf[20];
        double x;
        int h, m, s, ts;

        x=DEG(a)/15;
        x += 0.5/36000.;        /* round up half of 0.1 sec */
        h = floor(x);
        x -= h;
        x *= 60;
        m = floor(x);
        x -= m;
        x *= 60;
        s = floor(x);
        x -= s;
        ts = 10*x;
        sprint(buf, "%dh%.2dm%.2d.%ds", h, m, s, ts);
        return buf;
}

char*
dms(Angle a)
{
        static char buf[20];
        double x;
        int sign, d, m, s, ts;

        x = DEG(a);
        sign='+';
        if(a<0){
                sign='-';
                x=-x;
        }
        x += 0.5/36000.;        /* round up half of 0.1 arcsecond */
        d = floor(x);
        x -= d;
        x *= 60;
        m = floor(x);
        x -= m;
        x *= 60;
        s = floor(x);
        x -= s;
        ts = floor(10*x);
        sprint(buf, "%c%d°%.2d'%.2d.%d\"", sign, d, m, s, ts);
        return buf;
}

char*
ms(Angle a)
{
        static char buf[20];
        double x;
        int d, m, s, ts;

        x = DEG(a);
        x += 0.5/36000.;        /* round up half of 0.1 arcsecond */
        d = floor(x);
        x -= d;
        x *= 60;
        m = floor(x);
        x -= m;
        x *= 60;
        s = floor(x);
        x -= s;
        ts = floor(10*x);
        if(d != 0)
                sprint(buf, "%d°%.2d'%.2d.%d\"", d, m, s, ts);
        else
                sprint(buf, "%.2d'%.2d.%d\"", m, s, ts);
        return buf;
}

char*
hm(Angle a)
{
        static char buf[20];
        double x;
        int h, m, n;

        x = DEG(a)/15;
        x += 0.5/600.;  /* round up half of tenth of minute */
        h = floor(x);
        x -= h;
        x *= 60;
        m = floor(x);
        x -= m;
        x *= 10;
        n = floor(x);
        sprint(buf, "%dh%.2d.%1dm", h, m, n);
        return buf;
}

char*
hm5(Angle a)
{
        static char buf[20];
        double x;
        int h, m;

        x = DEG(a)/15;
        x += 2.5/60.;   /* round up 2.5m */
        h = floor(x);
        x -= h;
        x *= 60;
        m = floor(x);
        m -= m % 5;
        sprint(buf, "%dh%.2dm", h, m);
        return buf;
}

char*
dm(Angle a)
{
        static char buf[20];
        double x;
        int sign, d, m, n;

        x = DEG(a);
        sign='+';
        if(a<0){
                sign='-';
                x=-x;
        }
        x += 0.5/600.;  /* round up half of tenth of arcminute */
        d = floor(x);
        x -= d;
        x *= 60;
        m = floor(x);
        x -= m;
        x *= 10;
        n = floor(x);
        sprint(buf, "%c%d°%.2d.%.1d'", sign, d, m, n);
        return buf;
}

char*
deg(Angle a)
{
        static char buf[20];
        double x;
        int sign, d;

        x = DEG(a);
        sign='+';
        if(a<0){
                sign='-';
                x=-x;
        }
        x += 0.5;       /* round up half degree */
        d = floor(x);
        sprint(buf, "%c%d°", sign, d);
        return buf;
}

char*
getword(char *ou, char *in)
{
        int c;

        for(;;) {
                c = *in++;
                if(c == ' ' || c == '\t')
                        continue;
                if(c == 0)
                        return 0;
                break;
        }

        if(c == '\'')
                for(;;) {
                        if(c >= 'A' && c <= 'Z')
                                c += 'a' - 'A';
                        *ou++ = c;
                        c = *in++;
                        if(c == 0)
                                return 0;
                        if(c == '\'') {
                                *ou = 0;
                                return in-1;
                        }
                }
        for(;;) {
                if(c >= 'A' && c <= 'Z')
                        c += 'a' - 'A';
                *ou++ = c;
                c = *in++;
                if(c == ' ' || c == '\t' || c == 0) {
                        *ou = 0;
                        return in-1;
                }
        }
}

/*
 * Read formatted angle.  Must contain no embedded blanks
 */
Angle
getra(char *p)
{
        Rune r;
        char *q;
        Angle f, d;
        int neg;

        neg = 0;
        d = 0;
        while(*p == ' ')
                p++;
        for(;;) {
                if(*p == ' ' || *p=='\0')
                        goto Return;
                if(*p == '-') {
                        neg = 1;
                        p++;
                }
                if(*p == '+') {
                        neg = 0;
                        p++;
                }
                q = p;
                f = strtod(p, &q);
                if(q > p) {
                        p = q;
                }
                p += chartorune(&r, p);
                switch(r) {
                default:
                Return:
                        if(neg)
                                d = -d;
                        return RAD(d);
                case 'h':
                        d += f*15;
                        break;
                case 'm':
                        d += f/4;
                        break;
                case 's':
                        d += f/240;
                        break;
                case L'°':
                        d += f;
                        break;
                case '\'':
                        d += f/60;
                        break;
                case '\"':
                        d += f/3600;
                        break;
                }
        }
}

double
xsqrt(double a)
{

        if(a < 0)
                return 0;
        return sqrt(a);
}

Angle
dist(Angle ra1, Angle dec1, Angle ra2, Angle dec2)
{
        double a;

        a = sin(dec1) * sin(dec2) +
                cos(dec1) * cos(dec2) *
                cos(ra1 - ra2);
        a = atan2(xsqrt(1 - a*a), a);
        if(a < 0)
                a = -a;
        return a;
}

int
dogamma(Pix c)
{
        float f;

        f = c - gam.min;
        if(f < 1)
                f = 1;

        if(gam.absgamma == 1)
                c = f * gam.mult2;
        else
                c = exp(log(f*gam.mult1) * gam.absgamma) * 255;
        if(c > 255)
                c = 255;
        if(gam.neg)
                c = 255-c;
        return c;
}