There's a bunch of 40 column programs created for VIC, but I believe this one is different. Instead of slowly drawing nybbles to a huge bitmap, 4ty switches rapidly between two text fields of standard text [using a nybble-thin font]: Even frames display even columns and odd frames display odd columns only. Screen x-coordinate is adjusted by 4 pixels accordingly to make the characters fall in place.

Yes, it flickers (the screenshots were created by blending 2 adjacent frames together) - but it works very well on an unexpanded VIC 20 and leaves almost 3K for user programs

4ty-writer.prg is a "letter writer" application demonstrating the routine. The program repeats all your keystrokes and edits. sys4109 = display mode, sys4113 = write mode. F1/F3 to change text/background color. F5 to clear screen. F7 to exit to basic, where you can save your letter. When you have 254 keystrokes of memory left a star sign appears in top left corner.

Great stuff! I had the same idea a while back, and remember discussing it with Mike, but disregarded it because of the flicker. Kudos for being crazy enough to implement this

I see that you do not use the "native" interlace-mode when using NTSC. I noticed during my experiments with NTSC-interlace-pictures when I connect my NTSC-VIC20 to my modern LCD-TV that it automatically weaves this "native" interlace so that you effectively have no flicker at all on the screen.

Your split-routine would have to be adapted slightly, since one frame in interlace NTSC has 262 lines and the other 263 lines (opposed to 261 in non-interlace mode).

You can try this emulator http://www.z64k.com that is the first one to emulate the NTSC-VIC-interlace feature.

you could reduce the flicker considerably on PAL too if you'd set up an irq routine that switches between the two frames every scanline.... and then in even frames make the first scanline show frame1, second frame2 etc and in odd frames the other way around. would take quite a bit of CPU of course.

What program did you make that with? I'm looking for a 40 column solution for NinjaTerm.

I've considered defining a charset with the upper and lower case character in each cell so that I only need one 4k (normal and inverse) set of data instead of 8k. Then, I would use a 40x23 "screen". The upper four bytes of the line would be the upper/lower bytes of the char set for the left character, and the lower four bytes of the line would be the upper/lower bytes of the char set for the right character.

The issue, of course, is that color could only be applied to 2 characters at a time. Also, I need all of the characters from both the upper and lower sets as PETSCII graphics tend to use all of them.

One of them produces a *.pgm file from a text file, using the glyphs of an own font to display 7-bit ASCII. This font has also been used in several other applications, also by other people. It's included in the source of MG BROWSE, for example.

The next tool takes that *.pgm file and produces a charset and screen binary from it, eliminating doubles. That's pretty much the same way Sentoria works, just the later directly works on incoming character pairs, while I compare 8 bytes in the bitmap.

I converted the two *.bin files for use within my assembler, added the colour information manually, and finally completed it with the necessary display code and BASIC stub. A one-off approach.

I'm looking for a 40 column solution for NinjaTerm. I've considered defining a charset with the upper and lower case character in each cell so that I only need one 4k (normal and inverse) set of data instead of 8k.

Within MG BROWSE, the font definition takes up 96 chars (code numbers 32..127, no inverse chars), 8 bytes per char, 768 bytes total. The 4x8 pixel glyphs are doubled into the left half, making the extraction easier, without the necessity to shift 4 times - masking with $F0 or $0F suffices. That's geared for speed.

Then, I would use a 40x23 "screen".

Any reason not to use 24 or 25 lines in the display?

The upper four bytes of the line would be the upper/lower bytes of the char set for the left character, and the lower four bytes of the line would be the upper/lower bytes of the char set for the right character.

Now I'm completely lost on this one. I'd understand, if you'd pack the standard PETSCII upper/graphics set (reduced to 4 pixels width) into one half, and the PETSCII lower/upper set into the other half of the character definitions. That'd require just 2K for all character definitions, was it that what you meant? You'd then shift and mask the character definitions into the target bitmap data, as you'd need.

The issue, of course, is that color could only be applied to 2 characters at a time.

Yes, I could only include the colouring in red and blue, because I did "reply.prg" with single height chars, and whole words always have the necessary padding to the left and right with spaces to make colour clash a non-issue.

Also, I need all of the characters from both the upper and lower sets as PETSCII graphics tend to use all of them.

You quickly run into hardware limits though. The interlaced display method set aside - when you use single height characters, you either can be lucky to use a single prepared character set with the Sentoria method laid out above. Or not be lucky, and you exceed 256 characters and are then forced to use a raster interrupt to change the character base register mid-screen. In the worst case, the screen contents might require 500 different characters (in case there are no dupes), so you'd need 4000 bytes character set (preferably in the range $1000..$1FFF), and you'd still have to put the 'text' screen somewhere else into internal RAM: either at $0000..$01FF or $0200..$03FF. Neither of those latter choices is going to be OS friendly, especially not in the presence of interrupts and I/O over RS232 or IEC bus.

The technical compromise I found uses the standard display method with double-height chars to bring a 160x192 bitmap to screen, within $1000..$1FFF ($1000..$10EF for the 'text screen' and $1100..$1FFF for the bitmap) and leaving the lower 1K untouched for maximum OS interoperability. That gives you a 40x24 display, just the colour resolution is reduced to 2x2 characters (of 4x8 pixel size each).

As I wrote earlier, I finally dispensed with PETSCII, as for text applications in English language, 7-bit ASCII is entirely sufficient. And if I still want graphical decoration besides the text, the text itself is hosted in a bitmap and I can add any graphics besides it that I want.

For NinjaTerm I would use a full screen bitmap with 8x16 chars, but arranged and wrapped around in a way so that you can scroll the screen very fast.

Odd lines can be scrolled up by just changing the value of screen y-position and wiping the top line (8-high). Even lines can be then scrolled up by restoring the screen y-position and rotating the screen memory and clearing the bottom bitmap for new text. Scrolling implemented this way takes only a couple of rasterlines, where a typical 4K bitmap scroll would take more than a frame or two.

I did something similar in Green Delicious Apple-1 Emulator on c64 (but with 4 raster splits due to larger bitmap and no 16-high char mode in hw), in order to use the original Signetics chip font that was 7x8 pixels instead of 8x8 and still scroll smoothly.

aeb wrote:For NinjaTerm I would use a full screen bitmap with 8x16 chars, but arranged and wrapped around in a way so that you can scroll the screen very fast.

Odd lines can be scrolled up by just changing the value of screen y-position and wiping the top line (8-high). Even lines can be then scrolled up by restoring the screen y-position and rotating the screen memory and clearing the bottom bitmap for new text. Scrolling implemented this way takes only a couple of rasterlines, where a typical 4K bitmap scroll would take more than a frame or two.

That would indeed justify the use of 'just' 23 rows instead of 24 - you need that extra row either at top or bottom, cleared.

Only slight caveat is you can (easily) apply this method only to a full screen scroll. The routines in MG BROWSE also allow for partial scrolls (keeping, for example top or bottom text rows at their place), and are not too shabby speed-wise, either. A full screen scroll, regardless of direction, takes roughly 35000 cycles. And then it's mainly a matter, whether scrolling forms a speed bottleneck in your application, or not.

The text body in MG BROWSE is scrolled at a speed in excess of 10 lines/second. *) The speed is limited only in part by the scroll and text line display routines. Some speed is 'lost' in the BASIC environment and, mostly, by the key repeat rate, which is normally 15 repetitions per second.

All in all, it depends on the application. I used MG BROWSE for quite some of my works **) to include several pages of instructions/manuals within the disk image, and it's quite well up to the job.

Greetings,

Michael

*) That could sustain 400 bytes/second text input, and would require a reliable RS232 connection ***) of at least 4 Kbaud.

***) I'm wondering, that plbyrd thus far didn't encounter any problems with missed characters, which made Bobbi and Srowe scratching their heads lately up to developing a RS232 wedge to replace the original KERNAL routines!

plbyrd wrote:The upper four bytes of the line would be the upper/lower bytes of the char set for the left character, and the lower four bytes of the line would be the upper/lower bytes of the char set for the right character.

Now I'm completely lost on this one. I'd understand, if you'd pack the standard PETSCII upper/graphics set (reduced to 4 pixels width) into one half, and the PETSCII lower/upper set into the other half of the character definitions. That'd require just 2K for all character definitions, was it that what you meant? You'd then shift and mask the character definitions into the target bitmap data, as you'd need.

Ooops, I wrote bytes when I meant bits. Here is a diagram of what I meant.

character mapping.png (10.62 KiB) Viewed 352 times

As you can see, I would double up each char with the upper and lower case 4x8 of each character/symbol. This would give me a font of 4k for regular and reverse characters. This set would reside at $7800. The screen itself would be a 160x192 [strike]bitmap[/strike] character map which would reside twice in RAM.

I would have two screens in memory. One at $1000 and the other at $1800. This would allow for double-buffering. The drawing of characters would be done on the non-visible screen, then the pointer moved to the opposite screen. This would totally eliminate flicker. As for scrolling, again, it would be done on the non-visible screen, then the screens swapped. At 2400 baud, the user should never notice any of this. The only thing the user WOULD notice is the color changes which would be at a 2x1 character basis instead of 1x1. All of this completely eliminates flicker and honestly, I can live with the slight color problem in order to get 40 columns.

Once again, how you organize the character definitions as such, and how you provide character generator data to VIC-I are two entirely different matters. From the diagram I'd conclude you plan to put the upper/graphics PETSCII set into the upper nibbles of the character definitions, and the lower/upper PETSCII set into the lower nibbles. Fine. But that will only require 2K in total, not 4K.

Whatever concerns you to use double buffering to avoid flicker during scrolls, it *will* flicker during scroll unless you do 50 (or, in NTSC, 60) lines per second (due to persistence of vision). A pretty unreadable speed.

Finally, you'll have to place the character generator data into the internal RAM. If you plan for two screens (a.k.a. 'address generator in bitmap') at $1000 and $1800 (regardless whether ~240..250 bytes for double-height characters or ~480..500 bytes to single height characters), you'll have no place in $1000..$1FFF where to put the character generator data in one single piece - and $7800..$7FFF is inaccessible for VIC-I.

Mike wrote:Once again, how you organize the character definitions as such, and how you provide character generator data to VIC-I are two entirely different matters. From the diagram I'd conclude you plan to put the upper/graphics PETSCII set into the upper nibbles of the character definitions, and the lower/upper PETSCII set into the lower nibbles. Fine. But that will only require 2K in total, not 4K.

You're right, I only need 2k for the charmap as the source map will reside bin bank 3 as it does today with the C64 font..

Whatever concerns you to use double buffering to avoid flicker during scrolls, it *will* flicker during scroll unless you do 50 (or, in NTSC, 60) lines per second (due to persistence of vision). A pretty unreadable speed.

Double-buffering may indeed be unnecessary. I'm accustomed to using it for screen updates from CONIO in C, so I just wanted to design it to be robust enough to handle it if necessary. If not, then that's obviously some RAM and cycles I can free up.

Finally, you'll have to place the character generator data into the internal RAM. If you plan for two screens (a.k.a. 'address generator in bitmap') at $1000 and $1800 (regardless whether ~240..250 bytes for double-height characters or ~480..500 bytes to single height characters), you'll have no place in $1000..$1FFF where to put the character generator data in one single piece - and $7800..$7FFF is inaccessible for VIC-I.

The calculated charset will reside at $1800. Double buffering should only need RAM from $1000-$11FF and $1400-$15FF.

Hmm, entry point is going to be $1201 per normal for expanded VIC20, but that code jumps straight to my application which resides at $2000. I will still have plenty of RAM for variables between ~$1201 to $13FF, two screens, and the charset.

You're right, I only need 2k for the charmap as the source map will reside bin bank 3 as it does today with the C64 font..

A full (i.e. 256 characters) single-height character set for the VIC chip requires 2K. If you ever plan to use a full double-height character set, that requires 4K and you have no other choice than to put it to $1000, and the text screens to either $0000, or $0200.

The 160x192 display just works out in the upper 4K area, because only 240 characters are necessary, screen and character base are set to $1000, the screen itself only needs 240 bytes (from $1000..$10EF), and the first (double-height) character used is "P" which addresses $1100.

plbyrd wrote:The calculated charset will reside at $1800. Double buffering should only need RAM from $1000-$11FF and $1400-$15FF.

Hmm, entry point is going to be $1201 per normal for expanded VIC20, but that code jumps straight to my application which resides at $2000. I will still have plenty of RAM for variables between ~$1201 to $13FF, two screens, and the charset.

Please let me know if I've missed anything.

O.K. - just two things you should be wary of:

- a 2K calculated charset (with single height chars) will only allow for 256 character pairs (1 of them almost invariably committed to a "double-space"). Whether or that suffices you'll need to verify for every new screen.

- scrolling might become interesting - just copying the text screen one line upwards won't re-use the character definitions automatically. You'll run out of available character pairs pretty soon unless you somehow check their activity and do sort of garbage collection. Rebuilding the entire screen from scratch will slow down the scrolling to no faster than 2 lines per second (Sentoria does its whole 50x28 screen in roughly 1 second, and it's only that *fast* thanks to a binary tree search I suggested!). In principle, that would justify the use of a double buffered screen (so one doesn't see the screen build-up on each scroll), but as you don't have a second character set, the screen contents will still become garbled, as the old (calculated) charset is overwritten.

I already pondered about all this when I thought about another text display tool in the style of Sentoria (and had also some slightly heated discussion with another Denial fellow who just wouldn't understand the issues with his approach), and as the 50x28 display had its own share of problems getting it to work within NTSC screen estate, I ditched the whole idea and settled on the working 160x192 bitmap. No need to maintain an underlying character pool (which couldn't anyhow be guaranteed to work for all inputs), just pure drawing into the bitmap. And it's still fast enough for its intended use.

*Did* you actually try out MG BROWSE, or one of the applications that use it, to see how it fares?