Skip to content

Latest commit

 

History

History
794 lines (541 loc) · 21.2 KB

File metadata and controls

794 lines (541 loc) · 21.2 KB

News and changes

These changes are about the current source code. These are effected once new binary release is published

April 2026

18th April 2026

Fixed: Concanationing did not work with arrays

a$+= 5 ' worked
arr$(1) += 5 ' did not work
' but works now with ver. 1.3b

Added: several more example codes. Rosett-code solutions counter now a bit over 130.

Added: MOUSEHIDE and MOUSESHOW statemetens

MOUSEHIDE hides mouse cursor on graphics screen
MOUSESHOW brings it back.

Both works only when graphical screen is initialized (SCREEN 'mode')

Added: INBETWEEN. Returns true, if n is between min and max and not equal to them

INBETWEEN(1, 1, 10) ' false
INBETWEEN(2, 1, 10) ' true
BETWEEN(1, 1, 10) ' true
BETWEEN(2, 1, 10) ' true

Unlike BETWEEN which returns true if n is equal or between min and max, INBETWEEN returns true if n is not equal and between min and max

Added: ATAN2().

PRINT ATAN2(x$, y$) ' 0.4636476090008061

13th April 2026

Fixed: LOADSHEET — sprite indexing now starts at 0

Sprites loaded from a sheet are now indexed from 0, consistent with all other arrays in BazzBasic. Previously the first sprite was at index 1.

Fixed: VSYNC — keyboard input no longer breaks after toggling VSync at runtime

VSYNC(TRUE/FALSE) now uses SDL_RenderSetVSync to switch vertical sync without destroying the renderer. Previously the renderer was recreated on each call, causing the window to briefly lose focus and SDL to reset the keyboard state — making KEYDOWN and INKEY unresponsive until the next keypress.

10th April 2026

Version 1.3 released as binary

Added: DRAWSTRING and LOADFONT — text rendering in graphics mode

Renders text directly to the SDL2 graphics surface. Requires SDL2_ttf.dll in the same directory as the interpreter. Prefer over PRINT in graphics mode — PRINT bypasses the SDL2 rendering pipeline and causes flickering.

' Default font (Arial, size 20)
DRAWSTRING "Hello!", 100, 200, RGB(255, 255, 255)

' Load alternative font — becomes the new active font
LOADFONT "myfont.ttf", 24
DRAWSTRING "Hello!", 100, 200, RGB(255, 255, 255)

' Reset to default (Arial, size 20)
LOADFONT

DRAWSTRING positions text by its top-left corner. Copy .ttf files next to your .bas for portability — Windows system fonts can be referenced by full path but are not recommended for distribution.

Added: ROWCOUNT — count array rows

Returns the number of distinct first-dimension keys in an array.

PRINT ROWCOUNT(myArray$)

Added: ARGCOUNT and ARGS() — command-line arguments

Access command-line arguments passed to the program.

PRINT ARGCOUNT          ' Number of arguments
PRINT ARGS(0)           ' First argument

Added: compound assignment operators

Shorthand for common arithmetic assignments. Works on variables ($), not constants (#).

x$ += 5    ' x$ = x$ + 5
x$ -= 2    ' x$ = x$ - 2
x$ *= 3    ' x$ = x$ * 3
x$ /= 4    ' x$ = x$ / 4
str$ += " world"   ' String concatenation

Changed: INSTR() — case-sensitivity parameter

INSTR now accepts an optional case-sensitivity flag.

PRINT INSTR("Hello World", "world")       ' 0 (case-sensitive, not found)
PRINT INSTR("Hello World", "world", 0)    ' 7 (case-insensitive)

Changed: math constants now use # suffix

PI, HPI, QPI, and TAU are now PI#, HPI#, QPI#, TAU# for consistency with the rest of the language.
⚠️ Breaking change — update any code using the old names.

Changed: IDE and CLI improvements

Menu Shortcut Action CLI option
File Ctrl+N New file BazzBasic.exe
File Ctrl+O Open file none
File Ctrl+S Save file none
File Ctrl+Shift+S Save As none
File Ctrl+W Close tab none
File Alt+F4 Exit none
Edit Ctrl+F Find none
Edit Ctrl+H Replace none
Run F5 Run Program BazzBasic.exe file.bas
Run Compile as Exe BazzBasic.exe -exe file.bas
Run Compile as Library (.bb) BazzBasic.exe -lib file.bas
Help About BazzBasic.exe -v
Help Beginner's Guide BazzBasic.exe -guide
Help Check For Updates BazzBasic.exe -checkupdates

New files now open with a starter template:

' BazzBasic version 1.3
' https://ekbass.github.io/BazzBasic/

Bugfix: early RETURN inside FOR loop left function scope dirty

If a function returned early (e.g. via RETURN inside a FOR loop), local variables were not cleared. This caused stale values on subsequent calls to the same function. Now fixed.


3rd April 2026

Released as version 1.2 with some bug fixes and new features.

3rd April 2026

A Beginners Guide to BazzBasic is now available. It covers all the basics of programming in BazzBasic with what beginner can star at.

https://github.com/EkBass/BazzBasic-Beginners-Guide/blob/main/BazzBasic_Beginners_Guide.md

Mar 2026

31st Mar 2026

Added: BBVER# — version constant

Returns the running BazzBasic version as a string. Value is read directly from Version.cs at startup.

PRINT "Running BazzBasic "; BBVER#   ' Output: Running BazzBasic 1.1d

Added: JOIN — merge two arrays

Merges src1$ and src2$ into dest$. If both source arrays share a key, src2$ overwrites src1$.

JOIN dest$, src1$, src2$

Added: CURPOS("row"/"col") — read cursor position

Returns the current cursor row or column (1-based). Useful after PRINT or LOCATE.

LOCATE 5, 10
PRINT "Hello"
PRINT CURPOS("row")   ' Output: 5
PRINT CURPOS("col")   ' Output: 15

Renamed: ROOT#PRG_ROOT#

The built-in system constant holding the program's base directory path has been renamed to PRG_ROOT# for clarity.
⚠️ Breaking change — update any code using ROOT#.

Bugfix: SCREEN reinitialization

Calling SCREEN more than once no longer causes a crash or corrupted graphics state. Reinitializing the window mid-program now works correctly.


26th Mar 2026

I spent a couple of hours editing the already somewhat confusing documentation.

I think the new structure and division is clearer now and it's easier to find what you need.
Ek

26th Mar 2026

Due MOUSE issue below is pretty major, BazzBasic 1.1d released as source and binary

26th Mar 2026

Bugfix: Mouse button detection rewrite

MOUSEB AND MOUSE_LEFT# did not work correctly because AND in BazzBasic is logical, not bitwise — any non-zero value is TRUE, so all three buttons appeared pressed simultaneously.

Removed:

  • MOUSE_LEFT#, MOUSE_RIGHT#, MOUSE_MIDDLE# built-in constants
  • MOUSEB keyword (token kept internally for binary compatibility)

Added:

  • MOUSELEFT — returns 1 if left mouse button is pressed, 0 otherwise
  • MOUSERIGHT — returns 1 if right mouse button is pressed, 0 otherwise
  • MOUSEMIDDLE — returns 1 if middle mouse button is pressed, 0 otherwise
WHILE INKEY <> KEY_ESC#
    LOCATE 1, 1
    PRINT "X:"; MOUSEX; " Y:"; MOUSEY; "   "

    IF MOUSELEFT   THEN PRINT "Left clicked  "
    IF MOUSERIGHT  THEN PRINT "Right clicked "
    IF MOUSEMIDDLE THEN PRINT "Middle clicked"

    SLEEP 10
WEND

22nd Mar 2026

Quick "rerelease" as 1.1b

  • I forgot to update version from source
  • I forgot to update syntax files for Notepad++, VS Code, Geany and built-in IDE
  • Headers "support" not documented
HTTPGET(url$)                           ' works as before
HTTPGET(url$, headers$)         ' new, optional

HTTPPOST(url$, body$)                       ' works as before
HTTPPOST(url$, body$, headers$)     ' new, optional

See OpenAI API example for more.

22nd Mar 2026

Released as version 1.1

22nd Mar 2026

At Rosetta code I got inspired to create pendulum animation. pendulum_animation.bas

21st Mar 2026

BazzBasic-AI_guide.md is a tutorial for modern AI's. With it, AI can easily teach the user how to use BazzBasic.

Just download the file, attach it as project file or via prompt to AI and you are cool to go.

Technical guide ment for AI


Unfortunately, the GamePad support I planned didn't make it to version 1.1

The reason is that the SDL2 library has been having problems for some time, especially with Bluetooth gamepads.

I didn't want to do something half-hearted, so the gamepad support is now on hold until SDL2 gets its library back in condition.

Instead, I added three other functions that I've had in mind for some time: BASE64ENCODE, BASE64DECODE and SHA256

21st Mar 2026

Added JSON support: ASJSON, ASARRAY, LOADJSON, SAVEJSON

DIM data$
data$("name") = "Alice"
data$("score") = 9999
data$("address,city") = "New York"

LET json$ = ASJSON(data$)
' Output: {"name":"Alice","score":9999,"address":{"city":"New York"}}

DIM back$
LET count$ = ASARRAY(back$, json$)
PRINT back$("name")         ' Alice
PRINT back$("address,city") ' New York

SAVEJSON data$, "save.json"
DIM loaded$
LOADJSON loaded$, "save.json"

Added BASE64ENCODE, BASE64DECODE and SHA256

LET encoded$ = BASE64ENCODE("Hello, World!")
PRINT encoded$              ' SGVsbG8sIFdvcmxkIQ==

LET decoded$ = BASE64DECODE(encoded$)
PRINT decoded$              ' Hello, World!

LET hash$ = SHA256("password123")
PRINT hash$                 ' ef92b778... (64-char lowercase hex)

14th Mar 2026

Sound system fix — parallel audio playback

Problem: The old implementation loaded MP3/OGG/FLAC files with Mix_LoadMUS() which uses the SDL2_mixer's global Music channel — only one sound at a time.

Fixes:

  • All sounds are now loaded with Mix_LoadWAV() → play on their own Mix_Channels in parallel
  • SDL_INIT_AUDIO added to SDL_Init() call in Graphics.cs
  • SoundManager calls SDL_Init + SDL_InitSubSystem to ensure audio subsystem even without SCREEN command
  • SDL_AUDIODRIVER=directsound set in Program.cs to work around WASAPI issues (Nahimic middleware causes "Invalid Handle" error in WASAPI)
  • PlayOnceWait gets 50ms delay before polling loop due to DirectSound startup delay

7th Mar 2026

Added HTTP support for LOADIMAGE

LOADIMAGE with url

LET sprite$ = LOADIMAGE("https://example.com/sprite.png")
' → downloads "sprite.png" to root of your program
' → sprite$ works just as with normal file load

' to remove or move the downloaded file
SHELL("move sprite.png images\sprite.png")   ' move to subfolder
' or
FileDelete "sprite.png"                       ' just delete it

Added WAITKEY() function.

WAITKEY

Halts the execution until requested key is pressed.

' Wait just the ENTER key
PRINT "ENTER"
PRINT WAITKEY(KEY_ENTER#) ' output: 13

' Wait any of "a", "b" or "esc" keys
PRINT "A, B or ESC"
PRINT WAITKEY(KEY_A#, KEY_B#, KEY_ESC#) ' output: depends of your choice of key

PRINT "Press any key..." 
LET a$ = WAITKEY()
PRINT a$ ' output: val of key you pressed

2nd Mar 2026

Added SHELL feature

' SHELL arg$, timeout$
' Sends a command to the system command interpreter  
' Param *timeout$* is optional. If not given, standard 5000 milliseconds used for timeout.

' with default timeout option
LET a$ = SHELL("dir *.txt")
PRINT a$

' sets timeout to 2 seconds
' 1000ms = 1 second etc.
LET a$ = SHELL("dir *.txt", 2000)
PRINT a$

Feb 2026

22nd Feb. 2026

  • Released as version 1.0, source and binary

21st Feb. 2026

  • FILEREAD and FILEWRITE now supports arrays too.
  • Example with array:
LET FILENAME# = "array.txt"
DIM a$
a$("first") = 1
a$("second") = 2
a$("third") = 3
a$("fourth") = "Four"
a$("fourth", "temp") = "Temp"
FileWrite FILENAME#, a$
DIM b$ = FileRead(FILENAME#)
PRINT b$("fourth", "temp") ' Output: Temp

array.txt content:

first=1
second=2
third=3
fourth=Four
fourth,temp=Temp

21st Feb. 2026

  • Added statements HTTPPOST and HTTPGET. These statements allow you to send HTTP POST and GET requests to a specified URL and retrieve the response as a string.
DIM response$
LET response$ = HTTPGET("https://httpbin.org/get")
PRINT response$

DIM postResult$
LET postResult$ = HTTPPOST("https://httpbin.org/post", "{""key"":""value""}")
PRINT postResult$
  • Added statement LOADSHEET(, , )
REM ============================================
REM LOADSHEET demo: countdown 9 -> 0
REM sheet_numbers.png: 640x256, 128x128 sprites
REM Sprite 1=0, 2=1, 3=2 ... 10=9
REM ============================================

SCREEN 640, 480, "Countdown!"

DIM sprites$
LOADSHEET sprites$, 128, 128, "examples/sheet_numbers.png"

REM Center position for a 128x128 sprite on 640x480 screen
LET x# = 256
LET y# = 176

REM Count down from 9 to 0
REM Sprite index = number + 1  (sprite 10 = digit 9, sprite 1 = digit 0)
FOR i$ = 9 TO 0 STEP -1
    CLS
    LET spriteIndex$
    LET spriteIndex$ = i$ + 1
    MOVESHAPE sprites$(spriteIndex$), x#, y#
    DRAWSHAPE sprites$(spriteIndex$)
    SLEEP 500
NEXT

END
    • Added FULLSCREEN TRUE/FALSE. Enables or disables borderless fullscreen mode.
SCREEN 640, 480, "My title"
FULLSCREEN TRUE   ' borderless fullscreen on
FULLSCREEN FALSE  ' Windowed mode

14th Feb. 2026

  • Fixed INPUT and LINE INPUT when using GFX. Binary release also updated

14th Feb. 2026

  • Added KEYDOWN(<key constant#>) function with what it's possible to check state of all key constants
  • Added key constants to all keys I could imagine. Will add more if figured out some is missing

13th Feb. 2026

  • Released as version 0.9

12th Feb. 2026

  • Added LERP(start, end, t). Linear interpolation between two values. Returns a value between start and end based on parameter t (0.0 to 1.0).
  • Added EULER, which returns raw coded value of e (EULER) 2.718281828459045
  • Added VSYNC(TRUE/FALSE). VSync limits frame rate to display refresh rate (typically 60 FPS) but prevents screen tearing. Disabling VSync allows unlimited frame rate but may cause visual artifacts.
  • Added DISTANCE(x1, y1, x2, y2) or DISTANCE(x1, y1, z1, x2, y2, z2) which returns distance of 2D or 3D coordinates
  • Added CLAMP(n, min, max). If the given parameter n falls below or exceeds the given limit values ​​min or max, it is returned within the limits
LET brightness$ = CLAMP(value$, 20, 255)
' Replaces lines
' IF brightness$ < 20 THEN brightness$ = 20
' IF brightness$ > 255 THEN brightness$ = 255

11th Feb. 2026

  • Added TAU, which returns raw coded value of PI * 2
  • Added QPI, which returns raw coded value of PI / 4
  • Added BETWEEN(value, min, max) which returns TRUE if value is between min and max.

8th Feb 2026

Version 0.8 released as binary

8th Feb. 2026

  • Succesfully changed audio from NAudio to SDL2_mixer.

Fast Trigonometry (Lookup Tables)

For graphics-intensive applications (games, raycasting, animations), BazzBasic provides fast trigonometric functions using pre-calculated lookup tables. These are significantly faster than standard SIN/COS functions but have 1-degree precision.

Performance: ~20x faster than SIN(RAD(x)) for integer degree values.

Memory: Uses ~5.6 KB when enabled (360 values 2 tables 8 bytes).

FastTrig(enable)

Enables or disables fast trigonometry lookup tables.

Parameters:

  • TRUE (or any non-zero value) - Creates lookup tables
  • FALSE (or 0) - Destroys lookup tables and frees memory

Important: Must call FastTrig(TRUE) before using FastSin, FastCos, or FastRad.

' Enable at program start
FastTrig(TRUE)

' Use fast trig functions...
LET x$ = FastCos(45)
LET y$ = FastSin(45)

' Disable at program end to free memory
FastTrig(FALSE)
FastSin(angle)

Returns the sine of an angle (in degrees) using a lookup table.

Parameters:

  • angle - Angle in degrees (automatically normalized to 0-359)

Returns: Sine value (-1.0 to 1.0)

Precision: 1 degree (sufficient for most games and graphics)

FastTrig(TRUE)

PRINT FastSin(0)    ' Output: 0
PRINT FastSin(90)   ' Output: 1
PRINT FastSin(180)  ' Output: 0
PRINT FastSin(270)  ' Output: -1

' Angles are automatically wrapped
PRINT FastSin(450)  ' Same as FastSin(90) = 1
PRINT FastSin(-90)  ' Same as FastSin(270) = -1

FastTrig(FALSE)
FastCos(angle)

Returns the cosine of an angle (in degrees) using a lookup table.

Parameters:

  • angle - Angle in degrees (automatically normalized to 0-359)

Returns: Cosine value (-1.0 to 1.0)

Precision: 1 degree (sufficient for most games and graphics)

FastTrig(TRUE)

PRINT FastCos(0)    ' Output: 1
PRINT FastCos(90)   ' Output: 0
PRINT FastCos(180)  ' Output: -1
PRINT FastCos(270)  ' Output: 0

' Use in raycasting
FOR angle$ = 0 TO 359
    LET dx$ = FastCos(angle$)
    LET dy$ = FastSin(angle$)
    ' Cast ray in direction (dx, dy)
NEXT

FastTrig(FALSE)
FastRad(angle)

Converts degrees to radians using an optimized formula.

Parameters:

  • angle - Angle in degrees (automatically normalized to 0-359)

Returns: Angle in radians

Note: This function doesn't require FastTrig(TRUE) but is included for consistency.

PRINT FastRad(90)   ' Output: 1.5707963267948966 (HPI)
PRINT FastRad(180)  ' Output: 3.141592653589793 (PI)
PRINT FastRad(360)  ' Output: 6.283185307179586 (2*PI)
Fast Trig Example: Raycasting
REM Fast raycasting demo
SCREEN 12

' Enable fast trigonometry
FastTrig(TRUE)

LET player_angle$ = 0
LET num_rays# = 320

[mainloop]
    ' Update player rotation
    LET player_angle$ = player_angle$ + 1
    IF player_angle$ >= 360 THEN player_angle$ = 0
    
    ' Cast all rays
    FOR ray$ = 0 TO num_rays# - 1
        LET ray_angle$ = player_angle$ + ray$
        
        ' Fast lookup instead of SIN(RAD(angle))
        LET dx$ = FastCos(ray_angle$)
        LET dy$ = FastSin(ray_angle$)
        
        ' Raycast logic here...
        ' (20x faster than using SIN/COS!)
    NEXT
    
    IF INKEY = KEY_ESC# THEN GOTO [cleanup]
    GOTO [mainloop]

[cleanup]
' Free memory
FastTrig(FALSE)
END
When to Use Fast Trig

Use FastTrig when:

  • Rendering graphics at high frame rates (60+ FPS)
  • Raycasting or ray tracing
  • Rotating sprites or shapes
  • Particle systems with many particles
  • Any loop that calls SIN/COS hundreds of times per frame

Use regular SIN/COS when:

  • Math calculations requiring high precision
  • One-time calculations
  • Angles are not in integer degrees
  • Memory is extremely limited

7th Feb. 2026

  • Added keyword HPI which returns raw coded 1,5707963267929895
  • Added keyword PI which returns 3.14159265358979
  • Added keywords RAD & DEG

PI and HPI are raw coded values, so no math involved. Should make performance much better.

REM Test RAD and DEG functions
PRINT "Testing RAD() and DEG() functions"
PRINT

REM Test degrees to radians
PRINT "90 degrees = "; RAD(90); " radians"
PRINT "180 degrees = "; RAD(180); " radians"
PRINT "360 degrees = "; RAD(360); " radians"
PRINT

REM Test radians to degrees  
PRINT "PI radians = "; DEG(PI); " degrees"
PRINT "PI/2 radians = "; DEG(PI/2); " degrees"
PRINT

REM Test with trigonometry
PRINT "SIN(RAD(90)) = "; SIN(RAD(90))
PRINT "COS(RAD(180)) = "; COS(RAD(180))
PRINT

END
Testing RAD() and DEG() functions

90 degrees = 1.5707963267948966 radians
180 degrees = 3.141592653589793 radians
360 degrees = 6.283185307179586 radians

PI radians = 179.99999999999983 degrees
PI/2 radians = 89.99999999999991 degrees

SIN(RAD(90)) = 1
COS(RAD(180)) = -1

1st Feb 2026

The documentation has been worked on and is now a bit better than good.

BazzBasic supports creating libraries: bazzbasic.exe -lib file.bas

LINE INPUT is now in the list of supported commands

Version 0.7 released to this date

Jan 2026

18th Jan 2026

With all the previous add-ons, BazzBasic ver. 0.6 is now available as binary and source.

18th Jan 2026

Merging BazzBasic and basic code into a single executable file is now possible.

bazzbasic.exe -exe filename.bas produces the filename.exe file.

BazzBasic does not compile the BASIC code, but rather includes it as part of itself.

Read more https://ekbass.github.io/BazzBasic/manual/#/packaging

18th Jan 2026

Finished working with PNG and Alpha-color supports.
LOCATE in graphical screen now overdraws old text instead of just writing new top of it.

Supported Formats

Format: PNG
Transparency: Full alpha (0-255)
Recomended

Format: BMP
Transparency: None
Legacy support


18th Jan 2026

Generated a manual with Docify.
BazzBasic homepage now links to it.

Major idea is, that github wiki becomes a as development wiki and this docify as user wiki.


17th Jan 26

Fixed a bug that prevented to use custom resolution with SCREEN 0
Terminal now closes if no errors when running via IDE
Small gap between IDE line numbers and user code.


17th Jan 26

BazzBasic has now in-built simple IDE.
Start bazzbasic.exe with out params to open it.
If opened with params, the .bas file is interpreted normally.
After few new features, released as version 0.6


10th Jan 26

Generated vsix file to add BazzBasic syntaxes for VS Code.
See https://github.com/EkBass/BazzBasic/blob/main/extras/readme.md


9th Jan 26

Released first one, version 0.5