In Part 1, I designed a very simple VGA controller, but without any content to display, it's not very useful. The next part that's required is the display controller, which is responsible for drawing the text, graphics and colours on the display.
The Display Controller shall take its input from the read side of a dual port RAM, which shall be written to by the Teletext Data Processor in this project, but the Teletext Data Processor could easily be replaced with something else for non-Teletext applications. A Display Controller based on the Teletext specification makes an excellent FPGA display generator, even for non-Teletext applications. This is because the specification was designed in the 1970s to be relatively easy to design an ASIC around, which means that the compiled logic size is very small compared to modern FPGAs, and makes it very "cheap" in terms of resources to add the display generator to any project.
Level 1 Teletext supports text and graphics via a character generator ROM, mosaics of 2x3 pixels, and selectable background colour.
Key display features
Text
The font used was taken from the datasheet for the Texas Instruments SN74S262N CGROM, originally used in the 1970s "Tifax" decoder design, and entered into a VHDL file.
The CGROM has a row output format, which is better than column output for horizontal-scanning display systems because the input address only has to change once for each character along the line currently being drawn rather than for every pixel.
Graphics
Basic graphics capability is provided by 2x3 mosaic tiles:
Careful examination of the mosaics set will reveal that each of the six tiles in the mosaic correspond to particular bits of the address. No additional CGROM is required, and the logic to draw the mosaics ends up being very simple. The addresses marked (1) are displayed from the CGROM; this allows CAPITAL LETTERS to be mixed in with mosaic graphics without having to switch between text and mosaic modes.
Mosaics can be contiguous or separated; this is set using spacing attributes.
Double height text
Double height display can be enabled at any point on a line, and applies to any characters or mosaics drawn after the Double Height command up until the end of the line or a Normal Height command. If a Double Height command is used anywhere on a line, the entire line below is ignored (even below characters that aren't double height), which seems strange, but this simplifies the logic design. The CGROM glyphs are easily "doubled in height" by bit-shifting the row selector right by one bit when in double height mode, with just a little bit of extra logic required to correctly draw the second line.
Colours
The available colours are: White, Yellow, Cyan, Green, Magenta, Red, Blue, Black. All of these can be output using only one bit per channel (R, G, B). Black cannot be used as the foreground colour in standards-compliant Level 1.0 and Level 1.5 Teletext decoders, but most modern decoders will interpret it anyway. Not interpreting it does not make the logic simpler, but my decoder will be designed to not interpret it in order to stick as closely to the specification as possible.
Spacing attributes
All attributes are set using these commands. They are called "spacing attributes" because each one takes up a space on the display. Level 2.5 and 3.5 Teletext also supports non-spacing attributes which do not take up space on the display, but that is outside of the current scope for this project.
All attributes are described in detail in Section 12.2 of the ETSI EN 300 706 V1.2.1 Enhanced Teletext Specification.
Attributes can be "set-at", meaning they apply immediately, or "set-after", meaning they apply from the next character position onwards. Correct implementation is required to ensure the correct display of "held" mosaics. Hold mosaics is a feature which displays spacing attributes as a repeat of the last mosaic to enable seamless colour changes; without hold mosaics, spacing attributes would always be displayed as spaces and graphics like the famous Ceefax weather map would not be possible.
Mix and Reveal
The Conceal attribute hides text and mosaics. Setting the Reveal input high will display the hidden content.
The Mix feature on a real TV displays the foreground content on top of the TV picture. All background colours effectively become transparent. Currently, the design has no capability of drawing the text on top of an existing video signal, so all this function does at the moment is show all background colours as black. The Start Box and End Box attributes are unimplemented for the same reasons.
Firmware
The main parts of the logic are:
- Combinational logic for mosaic generation
- CGROM
- Active area controller: Determines whether we're currently in the area of the screen where the content will be drawn using a set of constants which determine character height, display height and width, characters per line, and number of VGA pixels per Teletext pixel
- Line and character counters: each pixel and each row within each character needs to be counted
- Display generator: reads the dual port RAM data and interprets the spacing attributes
- Logic to control setting the output signals to the foreground/background colours, and flashing
Teletext uses 40 characters and 25 lines, but the display controller is in no way constrained to that, and this can easily be changed using constants in the code for other applications.
Development
As the Display Controller operates independently of the Teletext decoding, development can be done without the decoder by loading a Teletext page into the dual port RAM by specifing it as the default data in Quartus. It is not possible to use .tti files directly because the spacing attributes are converted into ASCII sequences, and unnecessary header stuff is added, but it's simple enough to convert it to raw data by hand.
Here's the display from an early version of the display decoder:
A largely-completed display generator combined with working teletext decoder:
The firmware is available on GitHub
Despite making little attempt to "optimise" the code, the whole system including teletext decoding takes up only 6% of the small (to modern standards) 22k logic element Cyclone 10 LP FPGA.
Still to come...
Next: Data recovery, processing and page extraction
See all posts with the label Teletext to see my future progress on this project.
An additional challenge would be to design firmware to synchronise to an external VGA signal and draw text on top of the incoming VGA signal.