' **********************************************************
' PROGRAM:      bmi.bac
' PURPOSE:      calculate and display body mass index [BMI]
' AUTHOR:               vovchik (Puppy Linux forum)     
' DEPENDS:      gcc, bacon
' PLATFORM:     Puppy Linux (actually, any *nix)
' DATE:         26-11-2011
' NOTES:                food for thought? :)
' LICENSE:      GPL3
' INFO:         http://en.wikipedia.org/wiki/Body_mass_index
' **********************************************************


' *********************
' DECLARATIONS
' *********************

DECLARE bmi, len_m, len_cm, mass_kg TYPE FLOATING
DEF FN in2cm(myval) = myval * 2.54
DEF FN cm2in(myval) = myval / 2.54
DEF FN lb2kg(myval) = myval * 0.45359
DEF FN kg2lb(myval) = myval / 0.45359
CONST myversion$ = "v.0.1a"

' *********************
' END DECLARATIONS
' *********************


' *********************
' SUBS & FUNCTIONS
' *********************

' --------------
FUNCTION DECROUND(FLOATING num, FLOATING places)
' --------------
        ' round decimal nums [floats] to given number of places
        LOCAL m, y, q, retval TYPE FLOATING
        m = 1 / POW(10, places)
        y = num / m
        q = ROUND(y)
        retval = q * m
        RETURN retval
END FUNCTION

' --------------
SUB SHOW_USAGE()
' --------------
        ' show help
        PRINT "bmi - Body Mass Index Calculator (vovchik - ", myversion$, ")"
        PRINT "Usage:     bmi unit_flag weight height"
        PRINT "where      unit_flag = -m (metric units) or -e (English units)"
        PRINT "           weight    = weight in kilograms (metric) or pounds (English)"
        PRINT "           height    = height in cm (metric) or inches (English)"
        PRINT "Example:   bmi -e 155 71"
        PRINT "Result:    Your current BMI [21.6] is in the 'Normal' category. The"
        PRINT "           recommended weight range for your height [180.34 cm/71 in]"
        PRINT "           is from 60.2 kg [132.6 lbs] to 81 kg [178.5 lbs]."
        END
END SUB

' --------------
SUB CHECK_ARGS()
' --------------
        ' check command line args
        SPLIT ARGUMENT$ BY " " TO argv$ SIZE argc
        IF argc EQ 4 THEN
                SELECT argv$[1]
                        CASE "-m"
                                mass_kg = VAL(argv$[2])
                                len_cm = VAL(argv$[3])
                        CASE "-e"
                                mass_kg = lb2kg(VAL(argv$[2]))
                                len_cm = in2cm(VAL(argv$[3]))
                END SELECT
                ' convert cm to m for simple bmi calc
                len_m = len_cm / 100
        ELSE
                SHOW_USAGE
        END IF
END SUB

' --------------
SUB CALC_BMI()
' --------------
        ' calculate bmi
        bmi = DECROUND(mass_kg / (len_m * len_m), 1)
END SUB

' --------------
SUB SHOW_RESULTS()
' --------------
        ' display/interpret the results of bmi calculation
        LOCAL bmi_cat$ TYPE STRING
        LOCAL lo_lb, lo_kg, up_lb, up_kg TYPE FLOATING
        ' determine category for given bmi
        IF bmi <= 16.5 THEN
                bmi_cat$ = "Emaciated"
        ELIF bmi > 16.5 AND bmi <= 18.4 THEN
                bmi_cat$ = "Underweight"
        ELIF bmi >= 18.5 AND bmi <= 24.9 THEN
                bmi_cat$ ="Normal"
        ELIF bmi >=25 AND  bmi <= 29.9 THEN
                bmi_cat$ = "Overweight"
        ELIF bmi >= 30 AND  bmi <= 34.9 THEN
                bmi_cat$ = "Obese"
        ELIF bmi >= 35 THEN
                bmi_cat$ = "Morbidly Obese"
        END IF
        ' calculate recommended weight ranges in kg and lbs for given height
        lo_kg = 18.5 * (len_m * len_m)
        up_kg = 24.9 * (len_m * len_m)
        lo_lb = kg2lb(lo_kg)
        up_lb = kg2lb(up_kg)
        ' output results
        PRINT "Your current BMI [", bmi, "] is in the '", bmi_cat$, "' category. The"
        PRINT "recommended weight range for your height [", len_cm, " cm/", DECROUND(cm2in(len_cm), 1), " in]"
        PRINT "is from ", DECROUND(lo_kg, 1), " kg [", DECROUND(lo_lb, 1), " lbs]", \
                 " to ", DECROUND(up_kg, 1), " kg [", DECROUND(up_lb, 1), " lbs]."
END SUB

' *********************
' END SUBS & FUNCTIONS
' *********************


' *********************
' MAIN
' *********************

CHECK_ARGS
CALC_BMI
SHOW_RESULTS
END

' *********************
' END MAIN
' *********************