Bio-Graph

Date: 198x
Type: Program
Platform(s): TS 2068

This program plots a biorhythm chart, graphing the Physical (23-day), Sensitivity (28-day), and Intellectual (33-day) sinusoidal cycles for a given person and calendar month. The user inputs their birth date and the target month, and the program computes the elapsed days between those dates using a Julian-day-style integer accumulation routine at line 3000. Each cycle is drawn pixel-by-pixel using PLOT, with the sine argument converted from degrees to radians by multiplying by the constant 0.0174533. When a curve exceeds the screen boundaries (above row 18 or below row 158), the cycle identifier letter (“P”, “S”, or “I”) is printed at the top or bottom of the screen to indicate overflow. The calendar logic at lines 2082–2088 correctly handles month lengths including a basic leap-year check for February.


Program Analysis

Program Structure

The program is organized into well-separated functional blocks:

  1. Lines 105–210: Draw the chart grid — vertical lines every 8 pixels for each day, and a horizontal baseline at y=88.
  2. Lines 400–430: Print day-number labels along the x-axis.
  3. Lines 500–740: Plot the three biorhythm curves (Physical, Sensitivity, Intellectual) by calling the shared curve-drawing subroutine at line 1000.
  4. Line 999: STOP to halt after display.
  5. Lines 1000–1040: Generic sine-curve plotter; shared by all three cycles.
  6. Lines 2000–2095: Main input and setup subroutine — collects birth date, graph month, computes elapsed days, determines month length, and prints the chart header.
  7. Lines 2200–2420: Cycle-specific phase-calculation subroutines for Physical (23), Sensitivity (28), and Intellectual (33) cycles.
  8. Lines 3000–3400: Date-to-integer-day conversion routine, producing an absolute day count in dt.
  9. Lines 4000–4010: SAVE block, separated from the main program flow.

Date Arithmetic (Lines 3000–3400)

The date-to-day-number routine at line 3000 converts a calendar date into an absolute integer day count stored in dt. It computes years elapsed since 1901 (yt), counts leap years (lt), and uses a hard-coded cumulative day-of-year table via a chain of IF … GO TO statements for each month. The formula yt*365+306+lt+mt+d is applied, with an additional +1 added at line 3310 if the year being processed is itself a leap year. There is a subtlety: the caller decrements y by 1 before the call (LET y=y-1 at lines 2000 and 2020), and the subroutine increments it back at line 3300 (LET y=y+1) before the leap-year check at 3310, meaning January and February of a leap year are handled via the lt adjustment at line 3020 rather than the post-increment check.

Curve-Drawing Subroutine (Lines 1000–1040)

The single generic plotter at line 1000 iterates x from 0 to 8*days pixels. For each pixel column, it computes y=88+72*SIN(s*0.0174533), converting the accumulated angle s in degrees to radians using the approximation π/180 ≈ 0.0174533. The center baseline is y=88 and the amplitude is 72 pixels. The PAPER color is set by each caller before invoking the subroutine, coloring the ink of subsequent PLOTs. If the computed y-coordinate falls outside the visible plot area (above 158 or below 18), the cycle’s letter identifier is printed at the screen edge to signal overflow.

Phase Calculation Subroutines

Lines 2200–2420 each calculate the starting phase for one biorhythm cycle from the total elapsed days r (the difference between graph-month start and birth date). The integer quotient q is discarded; the remainder d gives the number of days into the current cycle. The angular increment per pixel a and starting angle s are then set in the calling block before the curve subroutine is invoked. The current phase day is also printed on the screen as a status line.

CyclePeriod (days)SubroutineColor (PAPER)Label
Physical2322005 (Cyan)P
Sensitivity282300(unchanged)S
Intellectual3324004 (Green)I

Month-Length Calculation (Lines 2082–2088)

After the user inputs the graph month number, days is initially set equal to the month number (LET days=m). Lines 2082–2088 then replace days with the actual number of days in that month. February gets 28 days by default, bumped to 29 if the year is divisible by 4. April, June, September, and November get 30 days. All other months (except already-handled February) get 31. Note that the leap-year test (years/4=INT(years/4)) is a simple divisibility-by-4 check and does not account for century years.

Key BASIC Idioms and Notable Techniques

  • The shared curve subroutine at line 1000 is parameterized entirely through global variables (a, s, a$, days), avoiding code duplication across the three cycles.
  • The delay loop FOR t=1 TO 250: NEXT t at line 2040 provides a brief pause before clearing the screen on an input error, a common BASIC timing idiom.
  • The grid lines are drawn using PLOT/DRAW within a FOR loop stepping by 8 pixels, matching each screen column to one day.
  • PAPER is used to change the color context for each curve, with PAPER 7 restoring white at line 740 after all curves are drawn.
  • The month table at lines 3100–3210 uses explicit GO TO 3300 or GO TO 3400 branches to handle months needing the post-increment leap adjustment separately from those that do not.

Bugs and Anomalies

  • Line 2000 contains a typo in the prompt string: "Your BIIRTHDAY (MM/DD/YY)?" — “BIRTHDAY” is misspelled with a double “I”.
  • Line 2100 contains a REM *S/cycle* comment that appears to be a leftover stub; it is never reached by normal program flow (line 2095 returns before reaching it).
  • The leap-year test at line 2084 uses only divisibility by 4, not the full Gregorian rule (divisible by 100 and 400 exceptions), so years like 1900 would be incorrectly treated as leap years if entered.
  • The SENSITIVITY curve subroutine at line 2300 does not set a PAPER color before plotting, so it inherits whatever color was last set (Cyan from the Physical curve). This may be intentional to distinguish it visually, but it is not explicit.

Content

Appears On

One of a series of library tapes. Programs on these tapes were renamed to a number series. This tape contained

Related Products

Related Articles

Related Content

Image Gallery

Bio-Graph

Source Code

  105 GO SUB 2000
  110 FOR l=0 TO 8*days STEP 8
  120 PLOT l,16: DRAW 0,144: NEXT l
  200 PLOT 0,88
  210 DRAW days*8,0
  400 PRINT AT 11,0;"0": PRINT AT 11,5;"5"
  410 FOR n=10 TO days STEP 5
  420 PRINT AT 11,n-1;n
  430 NEXT n
  500 REM *p/curve*
  510 PAPER 5: GO SUB 2200
  520 LET a=360/(8*23): LET s=a*d*8: LET a$="P"
  530 GO SUB 1000
  600 REM *s/curve*
  610 GO SUB 2300
  620 LET a=360/(8*28): LET s=a*d*8: LET a$="S"
  630 GO SUB 1000
  700 REM *I/curve*
  710 PAPER 4: GO SUB 2400
  720 LET a=360/(8*33): LET s=a*d*8: LET a$="I"
  730 GO SUB 1000
  740 PAPER 7
  999 STOP 
 1000 FOR x=0 TO 8*days
 1005 LET y=88+72*SIN (s*.0174533)
 1006 IF y>158 AND x/8=INT (x/8) THEN PRINT AT 2,x/8;a$
 1007 IF y<18 AND x/8=INT (x/8) THEN PRINT AT 19,x/8;a$
 1010 PLOT x,y
 1020 LET s=s+a
 1030 NEXT x
 1040 RETURN 
 2000 INPUT "Your BIIRTHDAY (MM/DD/YY)?";m,d,y: LET y=y-1
 2005 GO SUB 3000
 2010 LET ds=dt
 2020 INPUT "BIO-GRAPH month (MM/YY)?";m,y: LET d=1: LET days=m: LET month=m: LET years=y: LET y=y-1
 2025 GO SUB 3000
 2030 LET de=dt
 2040 LET r=de-ds: IF r<0 THEN PRINT "OOPS!! Dates entered wrong!": FOR t=1 TO 250: NEXT t: CLS : GO TO 2000
 2082 IF days=2 THEN LET days=28
 2084 IF days=28 AND years/4=INT (years/4) THEN LET days=29
 2087 IF days=4 OR days=6 OR days=9 OR days=11 THEN LET days=30: GO TO 2090
 2088 IF days<>28 AND days<>29 THEN LET days=31
 2090 INPUT "What is your FIRST NAME?";n$
 2092 PRINT "      B I O - G R A P H"
 2093 PRINT "For: ";n$;"    Month: ";month;"/";years
 2095 RETURN 
 2100 REM *S/cycle*
 2200 REM *P/cycle*
 2210 LET q=INT (r/23): LET d=r-(q*23): PRINT AT 20,0;"Physical=";d
 2220 RETURN 
 2300 REM 
 2310 LET q=INT (r/28): LET d=r-q*28: PRINT AT 20,16;"Sensitivity=";d
 2320 RETURN 
 2400 REM 
 2410 LET q=INT (r/33): LET d=r-q*33: PRINT AT 21,8;"Intellectual=";d
 2420 RETURN 
 3000 LET yt=y-1901
 3010 LET lt=INT (yt/4)
 3020 IF y/4=INT (y/4) AND m<3 THEN LET lt=lt+1
 3100 IF m=1 THEN LET mt=0: GO TO 3400
 3110 IF m=2 THEN LET mt=31: GO TO 3400
 3120 IF m=3 THEN LET mt=59: GO TO 3300
 3130 IF m=4 THEN LET mt=90: GO TO 3300
 3140 IF m=5 THEN LET mt=120: GO TO 3300
 3150 IF m=6 THEN LET mt=151: GO TO 3300
 3160 IF m=7 THEN LET mt=181: GO TO 3300
 3170 IF m=8 THEN LET mt=212: GO TO 3300
 3180 IF m=9 THEN LET mt=243: GO TO 3300
 3190 IF m=10 THEN LET mt=273: GO TO 3300
 3200 IF m=11 THEN LET mt=304: GO TO 3300
 3210 IF m=12 THEN LET mt=334
 3300 LET dt=(yt*365+306)+lt+mt+d: LET y=y+1
 3310 IF y/4=INT (y/4) THEN LET dt=dt+1
 3330 RETURN 
 3400 LET dt=(yt*365+306)+lt+mt+d: RETURN 
 4000 SAVE "BIO-GRAPH"
 4010 STOP 

Note: Type-in program listings on this website use ZMAKEBAS notation for graphics characters.

People

No people associated with this content.

Scroll to Top