I have decided to stop developing against the STM32F407 and switch to the STM32F413, the main reason being that this part has much more on-chip SRAM- 320KB to be exact. This will be enough for a 360 * 288 double frame buffer, which will give the same resolution as the MAX7456 chip used in the MinimOSD board.
Although this is only half the resolution of an analog TV picture, it is adequate for graphics and text overlays.
I have purchased a Nucleo-F413zh board and ported the code over to it, it is working but I have not taken advantage of the extra ram to create a larger frame buffer yet. That will be the next objective.
Colour looks great when there are 4 or more horizontally-adjacent pixels. But when there is an isolated single overlay pixel in a scanline (e.g. as part of a vertical line or the upright stems of text characters) then the colour is faint, as you can see in this image below.
Notice how much darker the vertical and diagonal lines are compared to the solid green horizontal lines. Also, although it’s not visible here, the green appears to “bleed” into the adjacent left and right pixels from the video feed.
This may be the result of signal processing in either the decoder, encoder, or my video monitor. Or it could be the result of the analog video encoding, which attempts to squeeze 3 signals (1 luminance and 2 chrominance) down one wire, with limited bandwidth. The ADV7184 datasheet states:
Due to the higher bandwidth, the signal transition of the luma component is usually much sharper than that of the chroma component. The color edge is not sharp and can be blurred, in the worst case, over several pixels.
The decoder has a Chroma Transient Improvement block, and the encoder has various Digital Noise Reduction filters. I will need to experiment with all of them. Next step will be to add a pushbutton handler which will progressively enable and disable the CTI and DNR settings so I can observe what difference if any they make.
The STM32F407 has 128K of SRAM (as well as an additional 64K of core coupled memory). 128K is just enough to implement a double frame buffer with 300 * 200 resolution. This does not quite cover the full screen (the grey strips at the right and left indicate the available area for graphics).
I could increase resolution by changing to a 4 bits per pixel colour space, giving a palette of 16 colours. Currently using 8bpp I have access to 64 simultaneous colours.
The other option would be to “race the beam” – generate raster scans in realtime without using a frame buffer. This is how the early game consoles did it. I did some experiments earlier and while it is possible, I found I was running out of clock cycles when doing anything other than very simple graphics. A single raster scan is equivalent to around 12,000 clock cycles on the STM32F407.