This file contains random thoughts that might be interesting for other
vectrex programmers.
And a <short> history of Vectrex Frogger making!
----------------------------------------------------------------------------

Programming Vectrex Frogger related notes...


Vectrex frogger does allways refresh with 50Hz.
All drawing is done in 30000 cycles or less. There are some notes below on
optimization techniques used to accomplish that.
Actually I'm quite proud of the speed I accomplished! It might be possible
that the sprite functions are the fastest that exist in any vectrex game.
(at least I would like to think so...)

The sprites look a bit peculiar on a real vectrex, a bit dotted, but one
can get used to that. They are 'dotted' because I used a fixed scale factor
of 6 for every sprite. If I wanted to draw a long line, I had to use several
small ones. And vectrex by nature doesn't allways turn the light off at
exactly the right time (actually at least 2 - 3 cycles later),
AND it allways turns the light on a few cycles befor starting to draw...
This allways results in a bright spot (one could naturally write some new
(non timer using) vector draw function, which would use some other form
of calculating the time, and be thus more exact, but who would want to do
a thing like that?).

Vectrex frogger was partly intended to serve as a well documented vectrex
programm to teach how to program the machine. I think I failed with that.
Because of the huge amount of vectors that had to be drawn in a tiny
timeframe, it was neccessary to optimize for every cycle I could lay my
hands on to (in timecritical parts anyway). Because of that optimizing I guess
the program is not well readable anymore. In the main program loop only
one BIOS function is still used (ask for digital joystick position).
Every other once used BIOS function was subsequently removed and replaced
by optimized (for the required situation) makros or routines specifically for
the thing I had to do.
All this is highly confusing to get into, if you didn't program it in the
first place.
NOTE:
One optimization technique used was:
 preface:
  Explaining how to place and draw a vector.
  ...
  Well anyway, to move the beam to a required position, you set the
  speed and direction of the beam and the time for how long the speed
  should be applied. Than you wait for the 'how long' to end.
  The 'how long' is the scale factor you set. If you set a scale factor
  of $90. This value gets written to the timer 1 and is waited for in an
  highly iddle loop!
  What I did was to un'iddle' that loop. Many calculations are done by
  vectrex frogger in that normally 'iddle' time.
  Note: I did that mainly with the 'move to' functionality. The nice thing is
  even if I had done to much in that iddle time, it doesn't matter!
  The only thing you have to watch out for is that you don't take less time
  than the timer value. But that is easily accomplished by a time request loop
  at the end of your own calculations.
  Note:
   You could use the same technique while drawing a vector. Drawing a vector
   and positioning the beam are the same thing. The only difference is
   the 'pattern' that is set in the SHIFT_REGISTER.
   On positioning that is '0', on drawing that is '$ff' (if you wanted to
   draw a solid line that is).
   But with drawing you should make sure that you switch the beam off
   in time (moving 0 to shift), otherwise you have a bright dot at the end
   of your vector!


Another optimization was (see below) to write a specific vector list draw
function (makro). Any cycle saved there was gold.
See, if I draw 30 sprites, and each sprite consists of, say 20 vectors.
That makes about 600 vectors. If I can write an optimized vector list draw
function, which saves about 10 cycles per vector, we have saved with one 'hit'
about 6000 cycles!!!

And another NEW one. Loop unrolling!
Actually I use that techinque all the time with my Watcom C programs, I just
didn't think about implementing it myself. Today I tried my luck unrolling
the vector list draw function. Strike! I saved more than 10 cycles for EACH
vector! That gives me another speed hit of nearly 3.000 cycles!
I just unrolled one loop, the main one for sprite drawing.
The other major sprite loop (for home sprites) remains as yet untouched,
but if I was to optimize all loops that way, I could probably get another
increase of 500 to 1.000 cycles. But a major drawback with this remains.
It makes the programm considerably longer! Well, can't have it all, can you?

Another one, not implemented, because there seems to be no need anymore.
But implementing a new kind of vector list, that includes scale information
might again save some cycles, since many long lines are drawn now doing
small lines. One could save a major overhead, if one could include a second
length variable in the vector list.


Note:
The assembler I used is VERY good. For optimization be sure to look at the
*.lst file it produces. There are all cycle information and length of
instructions listed, as well as the code... really very nice :-)


Object definition (this is specific for the routines used in vectrex frogger)
-----------------
All displayed 'items' in the game are called now objects. These objects
consist of two different entities, the vector list and the object definition
structure. The vector list is the day to day vectrex vector list. First
the number of vectors (minus 1), than relative vector coordinates (offsets).

For easier collision detection these vector lists should all start at the
leftmost point. In an earlier version of the sprite routine it was neccessary
for them to be closed, that is not needed anymore.
Following is an example of the object structure (taken from vectrex frogger,
first otter object).

otter1a_object:
                DB 0                    ; speed + direction
                DW otter1a_sprite       ; graphic definition
                DB 0                    ; length in SCALE_FACTOR_GAME
                DB 5                    ; anim delay value
                DW otter1b_object       ; pointer to next anim object
                DB -4                   ; offsets y in 'SCALE_IN_HOME', since this is a home object
                DB 0                    ; offsets x in 'SCALE_IN_HOME', since this is a home object
                DB $60                  ; brightness
                DB 0                    ; special flag

Note:
The sprites are drawn with a fixed scale factor of 6 (that might change
in future versions, I'm thinking about a new vector list, that includes
scaling information...).
Due to highly optimzed draw routines this cannot (and should not) be altered.
In fact these routines are so optimized, they don't draw exactly anymore.
There are two faults:
- the last vector in the list is cut off 2-4 cycles to early
- between objects in the object list (not yet explained...) we allways do
  a zeroing of the vector beam.
  This zeroing is not 100% correctly done (only 98% or so :-)).
  In fact the routine is slightly to fast. The vector beam has not time
  enough to reach zero (as a matter of fact I allready slowed the routine
  down for about 4 or 5 cycles, but it was not enough...).
  This results in an (bearly noticable) inaccuracy in the object positioning.

Emulator notes:
---------------
Vectrex frogger works OK on the emulator.
But note!!!:
The optimizing was done using a real vectrex, the emulator can as yet not
cope with many fiddlings that were neccessary to test the routines.
They work ok as they are now. But if you do your own optimization be sure to
have a vectrex handy, otherwise you will be very dissapointed if the real
thing is completely different.
Especially timing should be considered dangerous.
The emulator does many things at once, where the real vectrex takes it's time.
So for example beam zeroing, and accessing any VIA register...
There are many interesting e-functions to watch on your vectrex screen :-)!
(as the capcitors of the integrators load and unload...)


History
-------
My history programming vectrex, and vectrex frogger in special.

First, I was interested in vectrex since 1983, but I never had the money to
buy the thing. 1996 I thought I might try my programming skills and write a
vectrex emulator. But Keith Wilkins also thought that might be the way to go.
He released his sourcecode at a point where I had only done preliminary
stuff towards my emulator, so I dropped it, and looked at Keith's sources.
Over the next 2 years I improved his emulator in some relations, and I guess
I'm now sort of in charge of the thing.
A few months ago I thought it would be fun to turn DVE into a development
environmenmt for vectrex, 'cause I thought that emulation by now was good
enough for that (though it is not, I know now, and possibly never will, unless
Pentiums III 500Mhz are released soon, and at a reasonable price).
I scanned the internet again for all references concerning programming the
machine in order to find out what would be needed for a programmer.
Little enough was found. Some disassambled game images, well documented
though. Stuff from Clay and John, though both not all that well documented
(especially yours, John). There was no 'real' programming information avail-
able. So I thought I must figure stuff out by my own. I sat down one day and
tried to write my first vectrex game, VPONG. That was written in about
4-5 hours, and for a beginner it worked remarkable well, although it is by
no means a noticable game achievment (single player and pretty hard).
But all basic stuff was put into it - sound, vectors, text, joystick, buttons,
scaling, fading and so on.
The following week the idea of vectrex frogger made its way to my head, and
a first prototype of a sprite engine evolved from that. That was the time I
made the 'discovery' that scaling with high values is a really bad idea.

At that time I thought about the speed of my program, and my goal was to
do one update round in at least 70.000 cycles, otherwise I'd give the whole
thing up. I figured doing the thing in 70.000 cycles would result in an
update sequency of about greater 20 Hz per second, flickery, but still doable.
At that time I allready had a vectrex, but it was not hooked up to my
computers parallel port (thank god, had I made the connection at that point,
I'd given up the whole idea pretty soon). I experimented with those
scaling values and discovered, that a high scaling value resulted in
update rounds above 100.000 cycles. Doing a bit of more testing revealed,
that low scaling values would do the job nicely, and I was down to about
50.000 cycles. (by the way, being the one in charge off the emulator really
helps at some time, I wrote an emulator monitor function for cycle measurement
at that point, and I only had to type 'rc' and it would throw out the cycles
needed per update round :-)) (now it is pretty clear what the scaling really
does, since it is a timer... but back than I knew that too, but I didn't
really realize what it ment)
Anyway, I had a working sprite engine on my hands and all kinds of strange
vector plottings moved arround the screen in frogger manner. My sprite rou-
tines allready supported animation at that point, but after doing two or three
sprites I really grew bored with it. I drew out the sprites on a paper with
a pencil and translated the coordinates to vectrex coordinates. Doing that
for a large number of sprites is really !$"$"&!"$&=(!!!
Luckily I found a friend in search for a new project to do and I persuaded
him to make a small vector draw program, which would save the coordinates in
a way I could handle them easily with my routines. James (my friend), made
the vector drawing program, and I continued with the main program.
Quickly a joystick and collision detection routine was put together.
The first game of frogger (early stages) could be played after three
days of programming, though you could not enter an home nor were any special
features implemented.
Again I grew a bit tired doing the frogger thing. I moved on to some
routines I though about on a bus trip home from work. Routines which I
generously call 'morphing' routines. I had the idea, that two sets of
vector lists could be slowly changed from one set to the other, and that it
would result in a neat effect. I pondered that idea a bit and discovered,
that the 6809 had no DIV functions, and that the MUL is unsigned.
I made these two functions and wrote the two still available morphing
routines (setup and do_one_step). Ooops, they were really slow,
doing divide and mul via selfcoded subroutines many many times per frame
really takes its toll, let me tell you. I soon replaced the div function
with an optimized versions, that would be assigned as needed.
I still had a morphing function which could morph with any number (8 bit)
of steps. That still was to slow for any use. After many optimizations
I made the now implemented 16 step morph routine, for a fixed number of steps
(16). This is the function which is used upon startup and in some intermission
sequences.
That finnished I looked at the sound, I allways wondered what notes were
which, until I figured it out eventually. (vectrex BIOS related I mean)
Note: I cannot read any notes, and
I'm everything, but no musician. I searched the internet one day for notes
for 'the yankee doodle', but naturally I couldn't find any. I ended up with
a midi file. I searched again for a midi play/editor. I finally found one,
that would output the songs notes in some readable way. After these notes
and some heavy testing I 'wrote' the yankee doodle music for frogger.
For me that was a great feat indead!!!
First of, I wanted a drum giving the measure of the theme, but that somehow
sounded pretty bad. The way the song is played now, it uses three voices,
with an octave offset in each voice. Sounds ok with me, but I wouldn't
recocgnize any errors anyway :-(.
Now it was about time to make a couple of features. That was stuff I was
pretty afraid of, since it ment fiddling with code allready done, and
tweaking new features (bug filled, for sure) into it. These features were
flies, crocodiles, snakes, girls, timer, otter, diving turtles...
I closed my eyes and did program them all, but I didn't like a minute of it.
Actually I hated it. But these were things I had to do in order for frogger
to be frogger. These damn fiddlings with stupid timer variables, whether a
fly appears, checking coordinates over and over again, if frog is near a
snakes head, or if that turtle we just a sec befor were safely standing on
turned into a poodle of water... I hated it.
But I did it (as you can see). But it all took it's toll. Frogger was
slow going, it was pretty close to those 70.000 cycles again.
This was about the time I got the eprom card for my vectrex, and I checked
some other games, and I discovered, that slow games flicker a lot :-(,
and I really didn't like that. I still could not input my frogger to vectrex,
since I was still missing the ordered EPROM EMULATOR, but I had some EPROMs
and I watched them...
I was pretty ancious to see frogger on a real vectrex at that point, but I
couldn't, and I didn't find anyone with an EPROM burner either.
But I figured frogger was way to slow as it was, so I went looking for
optimizations and compromizations. First thing I did was remove the scoring,
live and level indicators from the main screen. Would you believe that one
call of that stupid 'print string' function took more than 10.000 cycles!
Further I edited all sprites, cut them down from using over twenty vectors
to using about 10-15 vectors, that resulted in another speed hit of about
10.000 cycles. (I hated editing all sprites again!)
(the turtle you see in the scroll text is a ancestor of the turtles you see
in the game btw.)
After that I was kind of confident that I could still reach my timing goal.
My goal now was to be able to draw every frame within 50.000 cycles, since
all measurement done with avaiable (once) commercial games suggested, that
this value would prove to be still ok, as many games go even beyond that
range.

Still waiting for that EPROM EMULATOR thing.
Having some time to spare, I thought that a scroll text would be a nice thing
to implement. Having done a nearly complete frogger, with 10 lanes of moving
sprites, I figured, that doing one lane of moving letters wouldn't be that
difficult. And actually after drawing all the letters 3 or 4 times
(the vector drawing program had a serious bug at that stage), and spending
some nerves at that, I completed that pretty soon. But another problem arose
at that stage. Vectrex has only so much RAM! And having the level and
sprite information and much other needed variables in RAM, and wanting to
do some morphing and still be able to provide a scroll text proved to be
another challenge. I re-arranged my ram division, and occupied several ram
locations double or triple times. That also was done, but I had second
thoughts about the easyness of programming vectrex by then.

Still waiting for that EPROM EMULATOR thing.
So I just waited and time went by without doing any changes to the program.
For a couple of weeks I didn't do anything, since final testing would have
to be done on a real vectrex.
...

Finally it arrived, hooked it up and... it didn't work :-(
Did some testing... Yep it worked all right, but the eprom cartridge I had
only had address lines supporting eproms up to 8 KB, frogger by than was
allready beyond that range, so I couldn't play my game :-(
(though nearly all other vectrex games, for the first time).
I cried loudly for help, 'cause I'm not a technical person, I wouldn't know
how to alter the cartridge for it to work with 16KB (or 32KB) EPROMS.
John heard my cries and sent me a couple of EPROM cartridges, which work
just great (but another 2 weeks went by).
Just beeing able to access 8KB was not so bad for a start, since I could split
frogger up into a couple of sections and test them one after another, though
I couldn't see the game with all features, it was enough for some testing.

At that point I encountered a heavy WOBBLE effect, that the emulator can as
yet not produce. I did some exploration and discovered that this was a time
related thing. The wobbling for now, mainly was seen at the startup. And
only when 'fixed' vectors were drawn, animated or moving vectors somehow were
sort of imune to it. (strange?)
Anyway, after some hairs turned gray, I realized, that if an update round
took more than 30.000 cycles, fixed vectors tend to wobble (at least with
my vectrex). It was not only my game that was effected by this, but nearly
all games that have fixed vectors at some point and take more than 30.000
cycles to complete an update round. Even minestorm, the inbuilt game,
is effected. When the game starts up, than for a few seconds, when the first
mines appear on the screen, the dots wobble (with my vectrex, which is the
only one I can test everything on).
Once you know how to look out for that effect, you discover it pretty often.
Needless to say, that I as a perfectionist didn't like that at all.
Other games can wobble like they want, but not my game, and certainly not at
the startup screen, the first thing you will see when starting the game.
(I still don't know what causes the effect, any technical information on
that topic is appreciated. I thought the only thing that would happen if
I took to long to complete my update round was a flickery effect. But even
if I set the 'wait recalibration' timer to a higher value than the BIOS
30000 cycles, fixed vectors DO WOBBLE! I think there is a second
FIX point, somewhere in the 50.000 but the flicker at that stage is not very
well tolerable)

I changed my code, so that 'VECTREX FROGGER' text and the other stuff do not
appear at the same time on the screen (that stupid text also takes about
5.000-6.000 cycles to draw). The wobble (at startup) was history.
Than I noticed another effect :-( (which still is seen on a real vectrex,
since I couldn't fix it in any clever manor).
My vectrex coordinates allways drift slowly to +,+ (upper, right).
If you leave the vector beam alone for long enough it will go to the upper
right. When drawing the large frog at the startup it takes quite a while
to complete the large vector list, at the large scale factor used.
It takes about 2000-3000 cycles to completly draw the huge frog. In that time
the vector beam drifts for about half a centimeter. What should be done, is
to recalibrate the beam between the drawings, that would fix the problem.
But there is not enough time to spare :-( (the frog consists of 63 vectors,
positioning 63 vectors with the given scale, in any non time critical way IS
impossible!
(63 * $90 = 9000 pure moving time, without overhead
 63 * $70 = 7000 pure drawing the vectors, without overhead
 overhead = 1000 cycles that is about 17.000 just for the frog,
 and I still want a scroll text, and the frog's morphing must be
 calculated!)).
Furthermore a fixed offset cannot be given, since this drift
is not a constant. It depends on the mood of my vectrex (it is after all an
old analog machine). So the frog looks ok on the emulator (if no drift is
set), but on a real vectrex the frog has a lose end. It bothers me a bit,
but cannot easily be fixed!

Apart from that everything seemed to work out just fine. I did a couple of
weeks not program any vectrex frogger (and didn't really miss it, after doing
work for some time, I tend to be glad to have it off my back eventually).
One fine day Johns cartridges finally arrived.
Tried frogger... and it worked!!! (badly :-()
Somehow it escaped me before, that in the game there are also fixed 'wobble'
vectors. And they DID wobble :-(. At that point I was ready to drop the whole
thing. I had been glad I achieved the 50.000 cycle goal after only wanting
70.000. But that seemed by far not enough. In order to lose the wobble, there
was no other way than to have go for 30.000 cycles.
I experimented some time to get rid of the fixed vectors, invented 'moving'
homes, and patterned lines for the middle stuff and the like. But it didn't
really help. I WAS quite dissapointed. My girlfriend tried to cheer me up
and said 'it isn't that bad' but in my view it was. I wanted to do a well
done full vectrex frogger game, WITHOUT compromising wobble effects.

I thought about changing all the sprites to again less vector usage, but that
would have resulted in Atari 2600 like sprites, more guess work than any
discernable objects. So I droped that notion. Than I had a first tentive go
at using the DP register (which befor was allways set to D0). Introducing
that more or less cleverly and some other optimization, saved me about
1000 to 2000 bytes of code. That enabled me again to 'inline' some BIOS
functions, and after optimizing the now inlined functions. I allready
achieved another save of 10.000 cycles. I was at 40.000, but at a loss as how
further optimization could be done. Going step by step through the code and
looking at the *.lst file the assembler produced and looking for neck breaking
cycle busters in critical positions... doing that for a day and a half...
allways saving in little steps 10-20 sometimes even 100 cycles...
I was down to about 37.000 cycles. Still a long way to go, and every further
step would be more difficult. Having a break... playing a nice round of
Diddy Kong on my N64 (yep, I have some other video consoles beside the
vectrex), an idea formed in my head... why not use the wait loops of the
positioning or drawing functions for something more usefull than just waiting
for timer to expire? Said and done (after 2 days fiddling, nerve breaking
draw backs and dissapointments implementing too fast functions, encountering
e-functions on the vectrex screen, weird effects and and and...), I saved
another 5.000 cycles! (this is pretty fast said here, but this was really
a nerve breaking experience, for more information look at the top of this
text file and/or at the source itself!)
Anyway I was at about 32.000 (allways worse case, with all 4 houses occupied,
girl, crocodile, otter and snakes displayed...).
After that I couldn't think of any more optimizing stuff. I edited all
levels, changed them and removed sprites, exchanged sprites, disabled
features, ... and so on, the levels still have their character I gave them
from start, but most are slightly changed (some were even OK).
But after that, I finally made it!!!

EVERY LEVEL REFRESHES IN BELOW 30.000 CYCLES!!!

Actually I'm very proud of my achievment. And I consider Vectrex Frogger
by now to be an outstanding vectrex program.

Perhaps that is just vanity on my side, but I put much effort into Vectrex
Frogger, and I hope people enjoy the game, and perhaps some people might
even find the source code helpfull and/or informative.




STOP STOP STOP STOP STOP STOP STOP STOP STOP STOP STOP STOP STOP STOP STOP

Another optimization hits the scene! Today I unrolled a couple of loops, speed
hit about 3.000 cycles! Hip Hip Hooray. I'll unchange all levels and they will
still be under 30.000 cycles...
By now I have even about 1.500 cycles to spare:-)

END OF FILE (Finally)