Miniscreen Multiline text

So now that I am working with the miniscreen and having some difficulty

What I am trying to do is something like this

Lat : {coords}
Lon: {coords}
Speed: {spd} {tabspace} Fix: {fix, type, sats}

Looking something like this

Lat : XX°N XXm XXs
Lon : XX°W XXm XXs
SPD : XX.X MPH     FIX: Yes, 3D, 8

However when i try to format it and display it, the text just wraps itself from 1 line to the other
ms.display_multiline_text(f'Lat : {gpsLat}\nLat : {gpsLat}\nSpd : {gpsSpd}\t Fix: {'Yes' if gpsFix else 'No'}, {gpsFxt}, {gpsSat}', font_size=10)

however it appears that the the \n for new line and \t for tab space just get ignored

i did also try this, as an example

ms.display_text(f'Lat:  {gpsLat}', font_size=10)
ms.display_text(f'Lon {gpsLon}', font_size=10, xy=(0,12))

but what i get is each line displays flashes on then off alternating between the lines. I tried to array the display text but that does not work either

My questions
how do you actually do multi line text?
how to you do text so you can position on the screen and not cause blinking between text?

The SDK is fine to point you in the right direction BUT has no explanation how to solve this issue

So i figured it out, not really the way i thought it would need to be done but it works

best way to do this is to think of the screen as a canvas, each line of text its own object to that canvas and each object has its own coordinates

the code i used to solve this was from one of the examples, luckily i spotted this approach in 5.3.1.7. Handling basic 2D graphics drawing and displaying

from pitop.miniscreen import Miniscreen
from time import sleep
from PIL import Image, ImageDraw, ImageFont

ms = Miniscreen()
image = Image.new(ms.mode, ms.size,)
canvas = ImageDraw.Draw(image)
ms.set_max_fps(1)

def msclear():
    canvas.rectangle(ms.bounding_box, fill=0)

msclear()
canvas.text((0, 0),f'Lat:  {gpsLat}',font=ImageFont.load_default(),fill=1)
canvas.text((0, 12),f'Lon: {gpsLon}',font=ImageFont.load_default(),fill=1)
canvas.text((0, 24),f'Spd: {gpsSpd}',font=ImageFont.load_default(),fill=1)
canvas.text((0, 36),f"Fix: {'Yes' if gpsFix else 'No'}, {gpsFxt}, {gpsSat} sats",font=ImageFont.load_default(),fill=1)
ms.display_image(image)

I have other code its running with obviously, but this is all Ihad added to get it Multi line text working

1 Like

Hey - glad you got something working for this!

So, the long and short of it is that the miniscreen’s display_text and display_multiline_text functions do not behave in the most intuitive way…

display_multiline_text will automatically determine when to produce newlines to wrap your text, and ignore whitespace between words in the string.

display_text will handle your string directly, including newlines. This is not acknowledged in the docs, which opts to describe the function as so:

Renders a single line of text to the screen at a given position and size.

This is actually due to the fact that this ‘feature’ of PIL’s ImageDraw function was not understood when these were first developed.

For now, if you wish to handle your own newlines, then use display_text.

In the near future, we will most likely deprecate display_multiline_text, in favour of adding an auto_word_wrap parameter to display_text - one text function for everything!

1 Like