Android Question Convert C or C++ to b4a

BugNot

Member
Here is the code :

C:
/* standalone moon phase calculation */

#include <stdio.h>
#include <math.h>

#define        PI    3.1415926535897932384626433832795
#define        RAD    (PI/180.0)
#define         SMALL_FLOAT    (1e-12)

typedef struct {
    int year,month,day;
    double hour;
} TimePlace;

void JulianToDate(TimePlace* now, double jd)
{
    long jdi, b;
    long c,d,e,g,g1;

    jd += 0.5;
    jdi = jd;
    if (jdi > 2299160) {
        long a = (jdi - 1867216.25)/36524.25;
        b = jdi + 1 + a - a/4;
    }
    else b = jdi;

    c = b + 1524;
    d = (c - 122.1)/365.25;
    e = 365.25 * d;
    g = (c - e)/30.6001;
    g1 = 30.6001 * g;
    now->day = c - e - g1;
    now->hour = (jd - jdi) * 24.0;
    if (g <= 13) now->month = g - 1;
    else now->month = g - 13;
    if (now->month > 2) now->year = d - 4716;
    else now->year = d - 4715;
}

double
Julian(int year,int month,double day)
{
    /*
      Returns the number of julian days for the specified day.
      */
    
    int a,b,c,e;
    if (month < 3) {
    year--;
    month += 12;
    }
    if (year > 1582 || (year == 1582 && month>10) ||
    (year == 1582 && month==10 && day > 15)) {
    a=year/100;
    b=2-a+a/4;
    }
    c = 365.25*year;
    e = 30.6001*(month+1);
    return b+c+e+day+1720994.5;
}

double sun_position(double j)
{
    double n,x,e,l,dl,v;
    double m2;
    int i;

    n=360/365.2422*j;
    i=n/360;
    n=n-i*360.0;
    x=n-3.762863;
    if (x<0) x += 360;
    x *= RAD;
    e=x;
    do {
    dl=e-.016718*sin(e)-x;
    e=e-dl/(1-.016718*cos(e));
    } while (fabs(dl)>=SMALL_FLOAT);
    v=360/PI*atan(1.01686011182*tan(e/2));
    l=v+282.596403;
    i=l/360;
    l=l-i*360.0;
    return l;
}

double moon_position(double j, double ls)
{
    
    double ms,l,mm,n,ev,sms,z,x,lm,bm,ae,ec;
    double d;
    double ds, as, dm;
    int i;
    
    /* ls = sun_position(j) */
    ms = 0.985647332099*j - 3.762863;
    if (ms < 0) ms += 360.0;
    l = 13.176396*j + 64.975464;
    i = l/360;
    l = l - i*360.0;
    if (l < 0) l += 360.0;
    mm = l-0.1114041*j-349.383063;
    i = mm/360;
    mm -= i*360.0;
    n = 151.950429 - 0.0529539*j;
    i = n/360;
    n -= i*360.0;
    ev = 1.2739*sin((2*(l-ls)-mm)*RAD);
    sms = sin(ms*RAD);
    ae = 0.1858*sms;
    mm += ev-ae- 0.37*sms;
    ec = 6.2886*sin(mm*RAD);
    l += ev+ec-ae+ 0.214*sin(2*mm*RAD);
    l= 0.6583*sin(2*(l-ls)*RAD)+l;
    return l;
}

double moon_phase(int year,int month,int day, double hour, int* ip)
{
    /*
      Calculates more accurately than Moon_phase , the phase of the moon at
      the given epoch.
      returns the moon phase as a real number (0-1)
      */

    double j= Julian(year,month,(double)day+hour/24.0)-2444238.5;
    double ls = sun_position(j);
    double lm = moon_position(j, ls);

    double t = lm - ls;
    if (t < 0) t += 360;
    *ip = (int)((t + 22.5)/45) & 0x7;
    return (1.0 - cos((lm - ls)*RAD))/2;
}

static void nextDay(int* y, int* m, int* d, double dd)
{
    TimePlace tp;
    double jd = Julian(*y, *m, (double)*d);
    
    jd += dd;
    JulianToDate(&tp, jd);
    
    *y = tp.year;
    *m = tp.month;
    *d = tp.day;
}

main()
{
    int y, m, d;
    int m0;
    int h;
    int i;
    double step = 1;
    int begun = 0;

    double pmax = 0;
    double pmin = 1;
    int ymax, mmax, dmax, hmax;
    int ymin, mmin, dmin, hmin;
    double plast = 0;

    printf("tabulation of the phase of the moon for one month\n\n");

    printf("year: "); fflush(stdout);
    scanf("%d", &y);
    
    printf("month: "); fflush(stdout);
    scanf("%d", &m);   

    d = 1;
    m0 = m;

    printf("\nDate       Time   Phase Segment\n");
    for (;;) {
        double p;
        int ip;
        
        for (h = 0; h < 24; h += step) {
            
            p = moon_phase(y, m, d, h, &ip);

            if (begun) {
                if (p > plast && p > pmax) {
                    pmax = p;
                    ymax = y;
                    mmax = m;
                    dmax = d;
                    hmax = h;
                }
                else if (pmax) {
                    printf("%04d/%02d/%02d %02d:00          (fullest)\n",
                           ymax, mmax, dmax, hmax);
                    pmax = 0;
                }

                if (p < plast && p < pmin) {
                    pmin = p;
                    ymin = y;
                    mmin = m;
                    dmin = d;
                    hmin = h;
                }
                else if (pmin < 1) {
                    printf("%04d/%02d/%02d %02d:00          (newest)\n",
                           ymin, mmin, dmin, hmin);
                    pmin = 1.0;
                }
            
                if (h == 16) {
                    printf("%04d/%02d/%02d %02d:00 %5.1f%%   (%d)\n",
                           y, m, d, h, floor(p*1000+0.5)/10, ip);
                }
            }
            else begun = 1;

            plast = p;

        }       
        nextDay(&y, &m, &d, 1.0);
        if (m != m0) break;
    }
    return 0;
}
 
Upvote 0

Serge Bertet

Active Member
Licensed User
Do not look difficult, little time consumming.
I started cause I'm interrested in these functions ... no time to finish for now
B4X:
'Code module
'Subs in this code module will be accessible from all modules.
Sub Process_Globals
    'These global variables will be declared once when the application starts.
    'These variables can be accessed from all modules.
    Type TimePlace (year As Int, month As Int, day As Int, hour As Long) ' typedef struct { int year,month,day; double hour; } TimePlace;
    Private SMALL_FLOAT As Float = Power(10, -12)     ' #define SMALL_FLOAT (1e-12)
    'Use cPI // #define PI 3.1415926535897932384626433832795
    Private const RAD As Float = (cPI/180.0)
End Sub

' Moon phase calculation

Private Sub JulianToDate(jd As Double) As TimePlace
    Dim result As TimePlace
    Dim jdi, b As Long
    Dim c, d, e, g, g1 As Long

    jd = jd + 0.5
    jdi = jd
    If (jdi > 2299160) Then
        Dim a As Long = (jdi - 1867216.25) / 36524.25
        b = jdi + 1 + a - a/4
    Else
        b = jdi
    End If
    c = b + 1524
    d = (c - 122.1) / 365.25
    e = 365.25 * d
    g = (c - e) / 30.6001
    g1 = 30.6001 * g
    result.day = c - e - g1
    result.hour = (jd - jdi) * 24.0
    result.month = g - IIf(g <= 13, -1, -13)
    result.year = d - IIf(result.month > 2, 4716, 4715)
    Return result
End Sub

'  Returns the number of julian days For the specified day.
Private Sub Julian(year As Int,month As Int,day As Int) As Double
    Dim a,b,c,e As Int
    If (month < 3) Then
        year = year - 1
        month = month - 12
    End If
    If (year > 1582 Or (year == 1582 And month>10) Or (year == 1582 And month == 10 And day > 15)) Then
        a = year / 100
        b = 2 - a + a/4
    End If
    c = 365.25 * year
    e = 30.6001 * (month + 1)
    Return b + c + e + day + 1720994.5
End Sub

Private Sub sun_position(j As Double) As Double
    Dim n, x, e, l, dl, v As Double
    Dim i As Int

    n = 360 / 365.2422 * j
    i = n / 360
    n = n - i * 360.0
    x = n - 3.762863
    If ( x < 0 ) Then x = x + 360
    x = x * RAD
    e = x
    Do While True
        dl = e - .016718 * Sin(e) - x
        e = e - dl / (1 - .016718 * Cos(e))
        If (Abs(dl) < SMALL_FLOAT) Then Exit
    Loop
    v = 360 / cPI * ATan(1.01686011182 * Tan(e / 2))
    l = v + 282.596403
    i = l / 360
    l = l - i * 360.0
    Return l
End Sub

Private Sub moon_position(j As Double, ls As Double) As Double  
    Dim ms, l, mm, n, ev, sms, ae, ec As Double
    Dim i As Int
 
    ' ls = sun_position(j)
    ms = 0.985647332099 * j - 3.762863
    If (ms < 0) Then ms = ms + 360.0
    l = 13.176396 * j + 64.975464
    i = l / 360
    l = l - i * 360.0
    If (l < 0) Then l = l + 360.0
    mm = l - 0.1114041 * j - 349.383063
    i = mm / 360
    mm = mm - i * 360.0
    n = 151.950429 - 0.0529539 * j
    i = n / 360
    n = n - i * 360.0
    ev = 1.2739 * Sin(( 2 * (l - ls) - mm) * RAD)
    sms = Sin(ms * RAD)
    ae = 0.1858 * sms
    mm = mm + ev - ae - 0.37 * sms
    ec = 6.2886 * Sin(mm * RAD)
    l = l + ev + ec - ae + 0.214 * Sin(2 * mm * RAD)
    l = 0.6583 * Sin(2 * (l - ls) * RAD) + l
    Return l
End Sub
And so on ....
 
Last edited:
Upvote 0
Top