Showing posts with label Graphics. Show all posts
Showing posts with label Graphics. Show all posts

Monday, September 19, 2022

HIRES for Vic-20 (BASIC 2.0 extension) is READY.

 


The BASIC commands are implemented, small font created, and demonstrations implemented.   Please enjoy this Space War and Omega Race inspired flying ship.

Source, disk image, and more details are on github for Commodore Vic-20 with memory expansion.

BASIC extension command syntax is:

COLOR [foreground[+8][,[background][,[border][,auxillary[,inverse]]]]]

COLOR [foreground[+8]] @ x1,y1 [TO x2,y2]

TEXT

HIRES xresolution, yresolution [,fillbyte]

DELAY jiffies

PLOT COLOR ON|OFF

PLOT [NOT|CLR] (@ x1,y1)|(TO x2,y2)...    **

PLOT 0|1|2|3 (@ x1,y1)|(TO x2,y2)...

PLOT "ABC" @ x,y [,addr [,width,height [,bytes]]]

RECT [NOT|CLR] [@] x1,y1 TO x2,y2

RECT 0|1|2|3 @ x1,y1 TO x2,y2

SHAPE GET|PUT|OR|XOR|AND|NOT|CLR addr @ x1, y1 TO x2, y2


** only first @ optional, when not multi-color

Monday, August 29, 2022

Vic-20 Hi-Res BASIC extension progress

 


Shape operations are functional, and work has begun on leveraging BASIC keyword extensions (borrowing from my own HIRES for C64).

4UPART program listing


While the SYS syntax is implemented, the BASIC keyword work has just begun.

Current vs. Proposed Syntaxes

Source and disk image are on github



Sunday, July 17, 2022

Vic-20 HI-RES in progress - Memory Layout

Vic-20 Graphics Memory Layout

The Vic-20 doesn't have a native graphics mode.  But it can use a character set from onboard RAM, and double the size of character cells from 8x8 to 8x16 pixels.


A solution puts video memory at address 4096 ($1000), and character RAM at ($1000).  Notice they are the same?  Yes, there's only 5K onboard RAM in addition to color RAM.   The first 1K starts at address 0 ($0000), and the other 4K starts at address 4096 ($1000).   Regardless of any other RAM present in the system (can add 35K), only that latter 4K is accessible as video/character RAM to the video chip.  (Even if the earlier 1K is available, there's too many conflicts with BASIC and KERNAL use).

So bitmapped characters (graphics) and video RAM (characters on the screen) have to share the same section of memory.  The way bytes work, at most 256 characters could be displayed on the screen, but that would require a full 4K of RAM for their bitmaps (16*256), so something has to give.   By using only 240 characters on the screen, that reserves 16*16 = 256 bytes for video memory, and the remaining memory can be used for graphics.  For the bitmap to skip over screen memory and avoiding any overlap, the characters used on the screen are indexed starting at 16 ($10).

$1000-$10EF screen (240 bytes), values $10-$FF (16 to 255)
$10F0-$10FF unused (16 bytes)
$1100-$1FFF bitmap (3840 bytes)

BASIC RAM can be moved to either 3K expansion RAM ($400-$FFF) or 8K or greater expansion RAM ($2000 and later).

One layout that is possible is 20 characters wide by 12 characters tall = 240 characters = 160x192 resolution.

The easiest layout of characters is to store them consecutively in memory as shown above.   Character layout for the screen is left to right, then wraps to the next row.   This scheme matches color memory layout as well.   An additional advantage is that time sensitive updates to graphics can be more aligned with the raster line.

Another layout of characters is to line them up vertically as shown below.  This has the advantage that memory is contiguous vertically until advancing to the next column of 8 pixels.   This allows for optimizations in managing graphics memory at the disadvantage of working vertically instead of horizontally, thus fighting the raster line.  But color memory is still horizontally oriented, so the address calculation is different, the same as the earlier layout.

 
As the Vic-20 allows for configuring the number of character columns, character rows, and adjusting top and left margins, a variety of resolutions are possible.

Some notable resolutions include

160x192, 192x160, 200x144, 144x208, 160x160

The last is mentioned as it is the resolution used by the Super Expander cartridge.  But note it only requires 200 bytes of screen memory, so using that resolution leaves 696 bytes of onboard memory unused for graphics/screen that could be available for another use, maybe 506 bytes is still text screen memory. 

Links




Sunday, April 25, 2021

Low Resolution Graphics for Commodore

Commodore systems come with a graphical character set that can be used for low resolution graphics.

PETSCII low resolution 80x50 example

All the Commodores include block patterned graphics that can be used to display 2x2 pattern blocks, to double both the horizontal and vertical text resolution, for example from 40x25 to 80x50.  Like 4K for the day!  

PETSCII block characters including inverted

In the back of our high school math classroom was an original PET 2001.   This system had a chicklet keyboard, built-in cassette drive, and 40 column white on black monochrome screen.  This system has no graphics modes beyond the PETSCII capabilities.

One of the exercises in my Algebra 2 class was to graph mathematically functions.  I successfully challenged myself back then to plot the graph on the PET using this block graphics method.

Using 8 PETSCII characters, and the inverse of those characters, all 16 combinations of the patterns can be achieved by setting (POKE) the correct value onto the screen (see the A array in the source).  Also achieved is reading (PEEK) the current PETSCII value, converting that into pixel data, and combining existing plotted pixels with a new pixel (see the B array in the source).

LORES PET 40COL listing

My handwritten PET listing from 1982

I found my handwritten program listing that dates back to 1982.  It's beautiful to see that graphics could be achieved with PETSCII with only a few lines of code.  From my positive experiences with the PET, I purchased a Commodore Vic-20, and the Super Expander later in 1983 and switched to high resolution graphics at that point.

A disk image (D64) of samples for PET/Vic-20/C64 is available.  Screen memory locations for PEEK/POKE are different for all the systems, and sizes are adjusted with variables for the 80 column PET, and 22 column Vic-20.  The Vic-20 and C64 also have color memory, so an additional POKE is included to match the current text foreground color (PEEK(646)).  

Update [5/13/2022] there are ports for both Commodore 128 40 column screen, Commodore 128 80 column screen (including SYS calls to read/write VDC 8563), and a port to the TED (C16, Plus/4) series systems showing a color gradient possible with those systems.

Disk Listing for different Commodore Models

Vic-20 low resolution 44x46 plot

Contrast with 320x200 high resolution from C64

PET 80 column screen 160x50 sample

[Change:] 80 P=COS(I)*SIN(I)*2

Commodore 16, Plus/4 screen 80x50 sample (TED)

Friday, March 13, 2020

New Hi-res Graphics for Commodore 64

[Author's Note: There is text to this blog post.  Be sure to also scroll down]
 
[Author's Note: There is text to this blog post.  Be sure to also scroll down]
Dust off that Commodore 64.  It's time to play with graphics old school. In the highest resolution available to your Commodore 64 -- 320x200 in beautiful monochrome and up to 16 colors (limited to two per 8x8 cell -- foreground and background).   That's more than twice the resolution of your first generation Palm Pilot, and more colors, so cool!


So what shall we draw first on our Commodore 64?  I vote for a circle.  Since I'm running the show here, I get to pick my favorite one sided two dimensional object.  Just a little trigonometry in play here.  Ah, takes me back to high school in 1982.  Good times!

10 REM HI-RES CIRCLE, DAVEVW.COM
20 COLOR 1, 15, 0, 14: REM GRAPHICS COLORS: LT GRAY ON BLACK, LT BLUE BORDER
30 HIRES 1 CLR: REM SWITCH TO GRAPHICS AND CLEAR
40 PI=3.1416: REM OR USE PI CHARACTER
50 R=90: REM RADIUS
55 C=1: REM COLOR
60 FOR A=0 TO 2*PI+PI/30 STEP PI/15: REM LOOP THROUGH ALL THE ANGLES AND MORE
70 X=R*COS(A)+160
80 Y=-R*SIN(A)+100
85 PLOT COLOR C
86 C=C+1:IF C=16 THEN C=1
90 IF A=0 THEN:PLOT 1,X,Y: REM PLOT POINT FIRST
100 IF A<>0 THEN:PLOT 1 TO X,Y: REM ALL OTHERS ARE LINES

110 NEXT


Pretty cool.  The code fakes a circle with 30 lines (see the different colors!) using SIN/COS to get the coordinates. (Hint: to get out blind type HIRES 0 and RETURN, or just make a syntax error and that will return to text as well.  Or use STOP+RESTORE, or power cycle as a last resort).

But what?  You don't have the COLOR, HIRES, PLOT keywords in your Commodore 64 BASIC?  Shucks, time to install HI-RES FOR C64.  Better yet, let's just dive in to learning the new keywords by launching LOADHIRES.

Insert your HI-RES FOR C64 disk.   I wish I had a time machine.  We could dial back to 1982 and look for it in your favorite computer retailer shop, or mail order house.  If it only existed then.  I probably could have sold this for something.

Except we are in the 21st century now.  We have Internet and everything.  You're not reading this on a BBS are you?   Just download the HI-RES FOR C64 disk image (open source!) and run in your favorite C64 emulator (VICE 3.3 r35872 or later recommended as that's what I'm running).  Or just copy to a floppy or such (SD for use with SD2IEC, pi1541, etc.) and run in your real C64 or C128.  (I personally use ZoomFloppy to transfer to my 1581 on 3 1/2" floppy to run on my C128[DCR].)


Hi-res is a software extension to Commodore I wrote over the course of about a year (June 2019 - March 2020) to continue my retro vibe, and close the loop on a project I had embarked on in the early 1980s.  I realized my dream!  Achievement completed.  Okay that is pretty priceless.

The keyword commands that you can learn about in the interactive documentation shown above, include:
HIRES
COLOR
PLOT
RECT
PATTERN
SHAPE


I'm not going to explain how to use them here.  Run the interactive documentation and learn there.  Move the cursor up and down, and press return for a demo or more information.  The demos show the capabilities of this hi-res system and utilize its keywords.

Now I'm going to use this remaining blog space to continue to rant about my Commodore programming memories...

Now I started on a PET at high school school.  And soon afterwards bought a VIC-20 for home with my own money.  I didn't get a Commodore 64 until about 1986, and a Commodore 128(DCR) in 1987.  With limited funds available prior to the C128, my only graphics capabilities was from purchasing a Super Expander with 3K RAM for my VIC-20.  While I was underwhelmed by some specifics of the Super Expander product (after shelling out about $60), having access to graphics was way cool and I did use it along with my math studies.  But then I outgrew BASIC programming in 1982 and branched into 6502 assembly.  I used HESMON to code 6502 machine language to develop a graphics package I could call into from BASIC using SYS commands.  I remember adding ability to parse commas and numbers to get arguments to my hi-res routines.

And since this was a VIC-20 and not a C64, there were no sprites to speak of.  So I wrote my own shape routines to copy portions of screen to and from memory.   And wrote my own character editor, and wrote my own routines for 40 columns text.  Unfortunately I haven't recovered any of those programs for tape and disk yet.  Here's hoping!  Finishing this project has been in the back of my mind for more than 35 years.

But I did one better.  I rewrote the high resolution package from scratch.  Well, actually I had some help starting out, so can't take all the credit (more on that later).  And this time targeted the C64 instead of the VIC-20.  Modern equipment and upgrades, you know!  Well, the C64 is a better more popular target for now, and has pretty good resources available (64K vs. 5K), except my VIC-20 Golden RAM 24K expansion board is laying around here somewhere.  But the VIC-20 isn't running.  So yeah, back to the C128 in 64 mode or more technically, the VICE emulator.

Okay, so Paul Soper posted on Reddit a link to his blog post of plotting a math function.  And I was in the retro mood so I ported the BASIC code he posted directly to machine code.  So I could pretty much replace the BASIC GOSUB routines with SYS commands.   The result was a little messy for passing values in A,X,Y registers, but it worked, and the graphics init and clear were much faster.  I posted the response to a comment in Reddit and on his blog.  Thanks again Paul!   And Paul credits the book The Graphics Book for the Commodore 64 as a source for his program, so thanks also to Abacus Software!

So to make a long story longer, I patched BASIC vectors to add the keywords.  This is not something I had accomplished in the 80s.  But with PDFs of Commodore manuals accessible at my fingertips to search and reference at whim, and more determination, and more senior engineering experience and confidence, I was able to accomplish the complete task in a professional and ideal manner.

Here are the successes of hi-res summarized:
  • supports graphics screens across the memory map (except zero page, and not where character rom gets in the way)
  • can switch between multiple graphics screens.  Supporting both hardware screens, and software swapped color tables, depending on addresses used.
  • default graphics screen is under KERNAL ROM
  • alternate graphics screen and color table is under BASIC ROM and I/O
  • So two screens without taking away any BASIC RAM!!!
  • machine code is from $C000-D423 (or thereabouts).  Utilizes more than 5K of RAM under I/O using banking, so not taking away any BASIC RAM.
  • Shape routines can copy any size portion of hi-res screen to/from RAM, and combine using GET/PUT/AND/OR/NOT/XOR.  This is leveraged to also support filling rectangular area with 8x8 pixel pattern, and plotting character strings to hi-res screen.
  • Hi-res patches SCRLEDIT in RAM so it will list the new tokens correctly.  Scroll up and down through your BASIC programs with F1/F7 using software I published in Compute!'s Gazzette.
  • assembly compiled using ACME.  Developing 6502 Assembly using Microsoft Visual Code editor, and builds into a running VICE instance.   And vice has built in machine language monitor with symbol table loaded built by ACME.   Very nice edit+build+test+debug cycle for development!!!  So glad not developing in the 80s anymore.
  • Machine language interface is also there.   Load up A/X/Y with correct values and JSR to $C000 as entry point for all the routines.  See source for details.
  • There are actual comments in the source code!  Gasp!  Don't worry, the BASIC interactive demo source is almost indecipherable in comparison.
  • Writing the assembly code was fun!
  • Writing the BASIC code to drive the demo was so much of a chore it wore on and dragged on for months.  Finally it is done.  I'm done with it too.  I'm sure it's done with me too.
Finally there is a joke screen (easter egg?) at the end of the interactive demo.   Cursor down to my website name, and press RETURN.  You will get a fun prompt.


It's up to you to find out what happens if you brave disagreeing with this statement.  Press y or n, it's up to you!

So what do you think of this?   What would you do different or add?  Having any troubles with it?  Do you want to know more of a particular aspect of this software?   Do you have a Commodore computer to dust off and get running again?  What was your favorite vintage computer?

Enjoy!

Links:

Tuesday, June 4, 2019

Computer Graphics Final Project 1989 Detailed

My graphics final project included a demonstration to the professor.  The demo went well as I remember, involving hefting my C128D including monitor up to the second floor of the UCSC Applied Sciences Room 215 computer lab.  The date is March 16, 1989.


Then I either didn't have documentation or otherwise couldn't show the work how I got to that point, and I was stunned, all I can remember is the professor walking off and leaving me without a way to recover, and even dropping off the description of the project to the proctor during my final exam didn't satisfy that section of my grade, and my evaluation (no grades at UCSC then) was very clear I had failed or underachieved in the project yet passed the class.


Evidently I missed something in the requirements and focused too much on the demonstration.  Documentation was the farthest thing from my mind while the demo was everything.  Lesson learned the hard way -- always cross all your i's and dot all your t's or something like that.


Well here's the project fully documented now.  Only it's 30 years late.  This is the best, or one of my best, failures to date!  Hope you enjoy.

Okay, so what is all this?  The course I took was an undergraduate computer graphics class.  We quickly got into 3D projection graphics.  The mathematics was covered in our course textbook and also in class.  Our assignments were to take templates of code provided by the teaching assistant, fill in missing portions, and turn in the final code.  Our target system (from memory) was either a SCO UNIX or Microsoft Xenix 386 system (I think it was Xenix) with separately attached graphics display (graphics library was ig, can't remember what that stands for).  It did color of course, and had a resolution in the neighborhood of 512x512.   The system did not have a concept of quick animation to my recollection.

My project took our 3D graphics primitives built in my assignments, and built around them a scripting language to describe the scene and move through it, or move the objects, rotate the objects, or scale the objects, or a combination of all of these.  Most of my demonstrations set up the object and rotate it around in 360 degrees.   So I built on my compiler experience (lex/yacc) to build a reusable mini-language to do simple computer animation.

Now this is 30 years ago.  Now we take 3D graphics for granted.  We have software libraries and graphics hardware acceleration that can do polygons in the thousands, millions, billions.  And all this code is doing is wire frame animation, not solid objects.  Whoop de doo!   Yeah, but it's doing it from scratch.   And I built up my own graphics workstation software to replicate the lab experience, albeit in black and white and lower res (320x200).   Hello Commodore 128!   And Commodore 512KB RAM Expansion Unit (REU) for animation!


Most of these animations are 60 frames total (1 to 4 seconds), where the code was run on a UNIX system, converted to line graphics, downloaded to the Commodore 128 and rendered.  I wrote the Commdore 128 software to render the graphics, and swap in/out of the REU for animation.  Because the REU does DMA, the transfer is fast.  Yeah, it's only 8Kbytes, but we're still talking a 1MHz or 2MHz 6502 based system, and with 60 frames, thats 480Kbytes total, more than the 128Kbytes on board.


We start by defining an object.  A simple one is 3dbox.obj

-100 -100 -100 100 -100 -100
100 -100 -100 100 100 -100
100 100 -100 -100 100 -100
-100 100 -100 -100 -100 -100
-100 -100 100 100 -100 100
100 -100 100 100 100 100
100 100 100 -100 100 100
-100 100 100 -100 -100 100
-100 -100 -100 -100 -100 100
100 -100 -100 100 -100 100
100 100 -100 100 100 100
-100 100 -100 -100 100 100

This is a 200 unit cube defined in 3D space with x,y,z coordinates space separated, one line of the box defined on each line of the file

scripts/06_box that animates this box looks like this

output bin
object "objects/box.obj"
translate z 0 y 0
eye 0 0 -500 0 0 0 0
window -200 200 -200 200 -200 200
viewport 0 511 0 511
repeat 60
   draw
   frame
   rotate y 6
loop
quit

Now looking at this, I see I could have "cheated" and only rotated it 90 degrees, because the cube is the same on all sides.  I proceeded to use this cheat in creating the gif with online tools.  I leave it as an exercise to the user, hint: rotate at a finer pitch to get a finer animation.  Note that the numbers are floats, so decimals are allowed.



And here is more description for the animation scripting mini-language

CIS 160 Project
David R. VanWagner

My project includes an enhancement of assignment 5.  I changed it to use
a language with which most commands require a single statement, and
a repeat statement is used to generate animation.  The instructions are
as follows:

help                            list commands
device, output                  change device type (ig,c128,bin)
eye                             set eye from,to,tilt
window                          set window extents xmin,xmax ... zmax
viewport                        set viewport xmin,xmax,ymin,ymax (0-511)
display                         turn c128 graphics display off,on
clear, cls, frame               clear screen, next frame
draw                            draw on screen using current settings
quit, exit, done                quit
set                             set current settings as default
reset                           reset to default settings
rotate                          rotate in x, y, and/or z
                                        as in  rotate x 30 y -20
scale                           scale in x, y, and/or z
translate, move                 translate in x, y, and/or z
bezier                          load bezier curve data, filename in quotes
repeat                          specify a number of times to repeat
loop                              until loop statement
                                (repeat/loop-s may be nested!)
object                          load object line data
input                           input commands from file
perspective                     turn perspective off,on
                                        ( perspective on is default )

The code is done in C with a lot of help from lex and yacc because of
the repeat/loop statements -> parses the code before it is executed, and
in the case of repeat/loop, lists of psuedo-code are made that are executed.

To allow me to do the majority of my work at home, most of my preliminary
work was done specific to my home computer.  I wrote my own ADM-31 (not
3A!) terminal emulator some time ago, and added to it to turn it into a
graphics work station.  Since the Commodore 128 has seperate RGB and composite
outputs, the setup is very similar to AS215 with text terminals and attached
graphics displays.  I also added code to allow for saving video display
coordinate lines ( what is normally sent to the graphics display ) to a
file in a compressed format ( 34 bits per point: 9 bits each x, 8 bits each
y ) and then using a combination of BASIC and 8502 Assembly on the
Commodore, each frame is drawn and stashed in external DMA memory, then
fetched in sequence for the fast animation.

There's another piece missing.  The c128 output device is actually when running in my own custom terminal emulator, to render in real-time to the secondary graphics screen (320x200 monochrome) while commanding UNIX over my 2400 baud modem in 80x50 text from the RGBI screen.

What I found out was that once you write your own terminal emulator, adding additional emulation sequences to do other stuff is a breeze.  And there weren't that many new ones to add for graphics.  My graphics terminal was running in no time!  But in retrospect, I should have added flow control to slow down the UNIX system.  It probably would have been as easy as a ^S when receiving a graphics command, and ^Q when finished rendering it.

Having the real-time graphics allowed me to render a single frame on the screen to make sure I was doing the right thing.  Then I would switch to bin format to output to a file on the UNIX system, and then file transfer to my floppy drive (can you remember those!!!) and then run other programs to render to the DMA memory and replay quickly for animation.


Disclaimers to folks.  Except for the first 5 input files (mostly the MIG-25 planes), the other renders I did now in the present in reconnecting with this project.  And I ran all my recent tests and development with Vice 3.3 on Windows 10 using both cygwin and Ubuntu as my "UNIX" systems.  Also there's a bug somewhere in my code!  It craps out on the 64th frame.  Probably something stupid.  Anyways 60 is a more round number for 360 degrees anyways.  Also I haven't matched loadbin.src to the machine language version in animate.bas.  I suspect they are the same, just trusting 30 year old bits.

Another tip is that I created an AWK script for combining named points and named lines into a 2D object.  Add another AWK line, and you can place it in 3D.   Here's an example:

File abc.v defines the points

a1 -40 -30 -100
a2 -35 0 -100
a3 -30 30 -100
a4 -25 0 -100
a5 -20 -30 -100
b1 -10 0 -100
b2 -10 30 -100
b3 5 30 -100
b4 10 25 -100
b5 10 5 -100
b6 5 0 -100
b7 10 -5 -100
b8 10 -25 -100
b9 5 -30 -100
b10 -10 -30 -100
c1 40 30 -100
c2 25 30 -100
c3 20 25 -100
c4 20 -25 -100
c5 25 -30 -100
c6 40 -30 -100

File abc.l defines the lines (between the points)

a1 a2
a2 a3
a2 a4
a3 a4
a4 a5
b1 b2
b2 b3
b3 b4
b4 b5
b5 b6
b6 b1
b6 b7
b7 b8
b8 b9
b9 b10
b10 b1
c1 c2
c2 c3
c3 c4
c4 c5
c5 c6

Then use objects/draw.awk to combine all these

cat abc.v abc.l | awk -f draw.awk > abc.obj

Then abc3d.v and abc3d.l were created from the previous files, resulting in abc3d.obj


There is also a commodore.awk and circle.awk to generate 2D objects, be sure to append a Z value and you can place them in 3D space.  Also check out commodore.obj, and yes it is designed to the 1965 specifications, except for some aspect ratio stuff (if you're running in emulation, just resize the window until the slants are at right angles).  Then again, the scale command could be used to help adjust the aspect ratio.  Again, left to the student.

All the C128, UNIX, source, and animation files used in this project are provided at this link here, and be sure to check out the node-m terminal emulator with its graphics capabilities as well.  There are also 7 more sample animations on the disk not displayed here.