** New Frontiers in VIC-Hires-Graphics, Part 5

Basic and Machine Language

Moderator: Moderators

Post Reply
User avatar
tokra
Vic 20 Scientist
Posts: 1120
Joined: Tue Apr 27, 2010 5:32 pm
Location: Scheessel, Germany

** New Frontiers in VIC-Hires-Graphics, Part 5

Post by tokra »

So, we had accomplished the 208x208 resolution, but it still nagged me that 208x240 didn't have BASIC-support, which lead to this:

Just a little in-between-update: Regarding the "slide-show" today i spent some time thinking about how to make the 208x240-bitmap useable from BASIC. I've done it now in way that doesn't use any IRQ - the assembler routine does the following:

- save lower 1K
- turn on graphics
- check for "Space"-keypress after each screen display cycle
- if pressed: turn off graphics, restore lower 1K

This way you can POKE the graphics-data from BASIC, then turn on the viewer and after pressing "Space" normal BASIC will continue. One can still use the top 16 lines of 22 chars in BASIC since the graphic-data start in memory at 4448.

The addressing-mode is hell-squared though. It isn't enough that you have to put the values into the unrolled loop at the LDA #xx-fields. A "bonus" is that due to timing the switch to the $0000-video- and char-RAM has to be in the middle of this loop. So at 2 places there is a jump of 10 instead of the normal 5 byte for the next graphics-data value. My solution for this would be to place the whole graphics-data (208x240) at $a000 and only when turning on the graphics-mode to copy it on need to the right places. This way only about 6K in the whole RAM would be free for your own programs, though.

My code isn't quite ready yet, I'll probably have something by tomorrow.
User avatar
Mike
Herr VC
Posts: 4816
Joined: Wed Dec 01, 2004 1:57 pm
Location: Munich, Germany
Occupation: electrical engineer

Re: ** New Frontiers in VIC-Hires-Graphics, Part 5

Post by Mike »

tokra wrote:A "bonus" is that due to timing the switch to the $0000-video- and char-RAM has to be in the middle of this loop. So at 2 places there is a jump of 10 instead of the normal 5 byte for the next graphics-data value.
You can amend these irregularities by realising the extra instructions as "knapsack".

That way, you'd replace one STA instruction by a JMP instruction - same length! - within the knapsack you put exactly the STA instruction again, together with the extra switch for video-, and character RAM; and a JMP back to the main routine. JSR, RTS wouldn't work if the stack area is used for graphics data.
User avatar
tokra
Vic 20 Scientist
Posts: 1120
Joined: Tue Apr 27, 2010 5:32 pm
Location: Scheessel, Germany

Re: ** New Frontiers in VIC-Hires-Graphics, Part 5

Post by tokra »

Mike wrote: You can amend these irregularities by realising the extra instructions as "knapsack".
Hmm, this might lead to timing-problems since the two JMP-instructions will need a little more time each. But I will try this, thanks for your suggestion.

(later that day):

It's online now:

Binary: http://www.tokra.de/vic/208240-24k.prg
Source: http://www.tokra.de/vic/208240-24k.asm

Self-explanatory code-example:

Code: Select all

10 sys9095:rem clear graphic
20 fori=0to1663:poke9782+5*i,rnd(1)*256:next
30 sys9092:rem clear color ram only
40 sys9089:rem show graphic, wait for keypress, turn off graphic
41 print "hello"
50 fori=0to2079:poke6112+i,rnd(1)*256:next
60 sys9092
70 sys9089
80 print "hello again"
90 fori=0to1663:poke18102+5*i,rnd(1)*256:next
100 sys9092
110 sys9089
120 print "hello three"
130 fori=0to831:poke8192+i,rnd(1)*256:next
140 sys9092
150 sys9089
200 print "bye"
User avatar
Mike
Herr VC
Posts: 4816
Joined: Wed Dec 01, 2004 1:57 pm
Location: Munich, Germany
Occupation: electrical engineer

Post by Mike »

Wow! :shock:

I might retract my earlier statement about my demo "hiatus". These routines really deserve to be shown in a demo.

I'm really fed up by those claims found at other places, that the VIC-20 "really" doesn't have graphics - only UDG's, bla-bla. These new modes, 208x208, and 208x240 should convince people, that the method how the bitmap is realised doesn't matter, only the result.

But before we can incorporate the 208x240 mode in a slide-show, a file format needs to be defined as well. Then MINIPAINT could be put to use as editor, by providing a tool which transfers 160x192 segments from the four edges of the bigger format.

Regards the proposed demo: here are some ideas ...

(most of them left out here to leave at least some surprise, should the demo surface at some time. ;) )

... and at the end, some big screens in 208x240 with special greetings to TRSI for 'going lowres'. :mrgreen:
User avatar
tokra
Vic 20 Scientist
Posts: 1120
Joined: Tue Apr 27, 2010 5:32 pm
Location: Scheessel, Germany

Post by tokra »

At this point this series ends (a little abruptly) since Mike and I continued chatting about how these modes could be used in a demo or what else could be done with them. I added a plot and line-drawing routine courtesy of Mike, but right now these only work with POKE and SYS. At first I wanted to convert those to sys ,x,y -calls but since then I took a look at the original MINIGRAFIK and want to make it into a BASIC-extension just like Mike's. Also I suggested converting an old BASIC-Mandelbrot-program of mine from 1990 or so to the new resolution, which is a good way to demonstrate the new graphics mode without being able to draw, but this will have to wait until the BASIC-extension is done. I must confess I'm more enthusiastic about trying new stuff than to flesh out the ideas that proved to work.

Anyway, it's nice to see that the VIC still holds some secrets to be unburied after all those years. Much of this would have been nearly impossible in the eighties without the programming tools of today (just imagine typing in an unrolled-loop for a 2000 byte copy) or re-loading from tape and compiling each time to try a new position for a raster-split.

I hope you had as much fun reading this series as we had making it. It doesn't end here, of course. We encourage you to post your ideas and questions, even if they seem silly or stupid, to any of the posts of the series. Hopefully this is just the beginning in expanding the possibilities of the VIC even further.

Cheers,
Torsten
User avatar
Mike
Herr VC
Posts: 4816
Joined: Wed Dec 01, 2004 1:57 pm
Location: Munich, Germany
Occupation: electrical engineer

Post by Mike »

tokra wrote:Also I suggested converting an old BASIC-Mandelbrot-program of mine from 1990 or so to the new resolution, which is a good way to demonstrate the new graphics mode without being able to draw, but this will have to wait until the BASIC-extension is done.
I would give it a try. Most of the time is spent in computation, so there's really no big "loss" (speed-wise, or memory-wise) in that pixels are set (or cleared) with a SYS call. In that regard, the '@' commands of MINIGRAFIK are just a slightly more compact notation, but not something inherently more capable.

Would you care to provide a listing or *.prg of your fractal program?
User avatar
tokra
Vic 20 Scientist
Posts: 1120
Joined: Tue Apr 27, 2010 5:32 pm
Location: Scheessel, Germany

Post by tokra »

Ok, since you challenged me:

Code: Select all

10 poke36865,52:poke36867,32:print"{clr}{blu}":poke36879,27:printchr$(142)chr$(8);
20 print"*** apfelmaennchen ***                      ";
30 print" 1) neue werte        ";
40 print" 2) bild laden        ";
50 print" 3) bild speichern    ";
60 print" 4) bild ansehen      ";
70 print" 5) programm beenden  ";
80 geta$:ifa$<"1"ora$>"5"then80
90 onval(a$)gosub500,2000,3000,4000,5000
100 goto10
500 rem bild zeichnen
510 print"{clr}***** neue werte *****"
520 input"linker  rand ";li:ro=li*-1
530 input"rechter rand ";re:ru=re*-1
540 input"unterer rand ";iu
550 input"oberer  rand ";io
560 print"{down}iterationen (>4,<255)":inputnm:ifnm<5ornm>254thenprint"{3 up}";:goto560
570 sys9095
580 da=(ro-ru)/208:db=(io-iu)/240:b=iu-db
590 foru=0to239:b=b+db:a=ru-da:forv=0to207:a=a+da:n=0:r=0:i=0:d=0
600 ifd>=4then640
610 x=r:y=i:r=x*x-y*y+a:i=2*x*y+b:d=r*r+i*i:n=n+1
620 ifn=nmthen650
630 goto600
640 ifn-int(n/2)*2=1thengosub1200
650 nextv,u
660 return
1200 rem punkt setzen
1205 poke780,1:poke781,v:poke782,u:sys9098
1250 return
2000 rem laden
2010 input"{clr}name des bildes ";n$
2020 sys57809n$,8,1:poke780,0:sys62786:return
3000 rem speichern
3010 input"{clr}name des bildes ";n$
3020 sys57809n$,8,1
3030 poke251,96:poke252,17
3040 poke781,80:poke782,103
3050 poke780,251:sys65496
3060 return
4000 rem ansehen
4010 poke646,1:poke36879,8:sys9092:sys9089:return
5000 rem ende
5010 sys58648
or just download:

http://www.tokra.de/vic/apfel240.prg

be sure to re-download the graphics-binary as well since I applied a small change that means the graphics will be deleted with whatever value is in the color-value at 646 ($286).

http://www.tokra.de/vic/208240-24k.prg

I also changed the save-routine from my old program so that it saves the whole area from $1160-$6750 - this means it saves the whole program loop together with the graphic: 22 KB per picture. What the heck - I suppose most people will use SD-cards or VICE-emulators by now anyways. At least a simple way to load and save pictures.

Also please note the program is still in german. The values for the Mandelbrots are those from the "Apfelmaennchen"-program from 64er magazine 11/1985 which differ a little from the usual notation (see lines 520-550 for easy conversion which my program actually uses itself).

Here are some pictures to try out (from 64er magazine 12/1985):

Code: Select all

Linker Rand     Rechter Rand    Unterer Rand    Oberer Rand     Iterationen
-0.7            2.1             -1              1               30
1.67            1.86            -0.075          0.075           40
0.1429          0.1802          1.02            1.0477          100
0.5665          0.5737          0.5602          0.5665          85
0.7425          0.74825         0.09621         0.10067         150
-0.103          0.379           0.618           0.929           50
0.7654          0.76722         0.10021         0.10151         200
-0.0171         -0.00944        0.6534          0.658           150
0.22223         0.2545          0.7089          0.7421          150
0.76461         0.76498         0.10056         0.10082         254
User avatar
Mike
Herr VC
Posts: 4816
Joined: Wed Dec 01, 2004 1:57 pm
Location: Munich, Germany
Occupation: electrical engineer

Post by Mike »

For the sheer fun of it, I compared your program against my own implementation with MINIGRAFIK, and a later conversion to C.

I could run the VIC versions with ~120x speed within VICE, so the total computation times were bearable even with the last co-ordinate set you gave:

Code: Select all

x_min=0.76461
x_max=0.76498
y_min=0.10056
y_max=0.10082
max_iter=254
At first, my own program, result 160x192 pixels, time: ~2360 minutes:

Image

Then, your program, result 208x240 pixels, time: ~7550 minutes. It's obvious we're using different methods to display the set, even though the math behind that is the same:

Image

On average, my program displays (160x192)/2360 ~= 13.0 pixels/minute, yours does only (208x240)/7550 ~= 6.6 pixels/minute. There might be some room for improvement ;), but anyway here's the C version, 800x576 pixels, 1000 iterations (to get deeper into the "black holes" visible above), time on PC: <1 second: :mrgreen:

Image

Cheers,

Michael
User avatar
tokra
Vic 20 Scientist
Posts: 1120
Joined: Tue Apr 27, 2010 5:32 pm
Location: Scheessel, Germany

Post by tokra »

I remember copying the calculating routine from some 64er article or program back then since I just have a bare idea how it works. The difference must be in the pixel-set routine:

Code: Select all

640 ifn-int(n/2)*2=1thengosub1200
- apparantly this not only sets a pixel within the mandelbrot-set but also outside for some cases, leading to the "pipes" you will see in many of the pictures.

Maybe the calculating routine can be translated to assembler. It's just a few lines of BASIC-code and it would be an interesting to see how this can be done in assembler.

It's amazing to see that a PC today can do the same in under a second at much higher resolution. Back in 1993 my old Commodore 128 would need WEEKS for some sets calculated at the then insane resolution of 720x700 - that's why I added a save-and-continue option to that program...

Torsten
matsondawson
The Most Noble Order of Denial
Posts: 343
Joined: Fri May 01, 2009 4:44 pm

Post by matsondawson »

Heh, even java (1.5) does it in less than a second...

http://www.mdawson.net/mandelbrotApplet.php
User avatar
Mike
Herr VC
Posts: 4816
Joined: Wed Dec 01, 2004 1:57 pm
Location: Munich, Germany
Occupation: electrical engineer

Post by Mike »

matsondawson wrote:Heh, even java (1.5) does it in less than a second ...
"It" of course requires you specifying co-ordinate set, maximum iteration depth, and resolution used for the picture. I made a try with your Java version, and indeed it fared quite well, though I wouldn't say it took less than 1 second in that case:

Image

And, the pictures even get more interesting if you're zooming into regions which require more than 1000 iterations so you don't get an all-black picture.

BTW, my C version has an optimisation built-in which avoids calculating "into" the regions with iterations greater than the specified maximum: it's a simple floodfill algorithm at work, which fills in from all points of the picture border, and then regards all points with 'iter=max_iter' as boundary. This works because the Mandelbrot set is 'simply connected': it doesn't have holes inside which aren't part of the set, so nothing is missed out.
tokra wrote:apparantly this not only sets a pixel within the mandelbrot-set but also outside for some cases, leading to the "pipes" you will see in many of the pictures.
That region really isn't part of the main set, it rather is its 'decoration' outside - if you'd adopt the convention of painting all 'escaping' pixels in white, and really only points within the Mandelbrot set black, you'd get a near all-white picture at an iteration depth of 1000, as could be guessed from the Java-drawn picture above - except maybe for some lucky hits on satellites of the main set.

My display routine zeroes in on these decorations by re-painting the pixel black when a point of a comparatively high iteration depth is surrounded by two pixels of lower iteration depths in at least one of the horizontal, vertical, or the two diagonal directions.

Looking at your main loop:

Code: Select all

600 ifd>=4then640 
610 x=r:y=i:r=x*x-y*y+a:i=2*x*y+b:d=r*r+i*i:n=n+1 
620 ifn=nmthen650 
630 goto600 
compared to mine:

Code: Select all

17 FORI=1TON:X2=X*X:Y2=Y*Y:IFX2+Y2<4THENXY=X*Y:X=X2-Y2+R:Y=XY+XY+J:NEXT
gives some hints (one thing beforehand - a NEXTS further down in my program pops the pending 'NEXTI' off the stack if the FOR loop in line 17 is left prematurely ...):

Using 3 multiplications instead of 6 probably accounts for most of the speed difference, but then I also did an early assignment to most of the variables used within the main loop (not necessary for I, and N as BASIC holds a pointer to I, and reads N only once); finally '630 goto600' requires a scan from the beginning of the program to where 600 is, this would be slightly faster were the loop located more at the top - again, a FOR stores a pointer to the instruction immediately after the FOR, so in my case it wouldn't make a difference.
Maybe the calculating routine can be translated to assembler.
The arithmetic within CBM BASIC is really not something to be embarrased about regarding speed, the routines are quite efficient indeed for providing a 32-bit mantissa (hence 9 significant digits).

One could reduce the precision to 24 or even 16 bits, but then you can't zoom in beyond the point where the details of the set just become interesting enough ...

Translating the main loop to assembler (calling the arithmetic routines within BASIC directly) would indeed at least relieve the loop to scan the expressions, and doing the variable look-up again, and again. Which might speed it up by another 20-30%. I'll take a look at it over the next days - maybe I have a prototype running the next weekend. [*]

Greetings,

Michael

P.S.: Edit: [*] well it didn't take that long. ;) See here.
Post Reply