0

I'm currently making a typing game in turtle graphics. As the user types, an arrow above the sentence they are typing moves. This is used to show the user where they are in the sentence. However, I'm having trouble making the arrow stay above the letter that the user is actually on. It seems that the width of each letter isn't a constant measurement. Therefore, this will not work:t.forward(any number here) Is there any way to know the width of every single letter in a sentence? Or is there a certain font type that has a constant width no matter the character? I apologize if this does not make sense. Thanks

SWEEPC
  • 3
  • 3

1 Answers1

0

There are a couple of ways you can look at this:

To know width of character you just wrote

You can do this by always lifting the pen prior to writing a character, and asking the turtle to move with the character. If you record the turtle position before and after writing, then you can work out and return the width:

    import turtle
    def write_character(t: turtle, char: str, font: str = "Arial") -> float:
        """Write character and return width"""
        pen_was_down = t.isdown()
        if pen_was_down:
            t.penup()
        x_start, _ = t.position()
        t.write(char, move=True, font=(font, 50, "normal"))
        x_end, _ = t.position()
        if pen_was_down:
            t.pendown()
        return x_end - x_start

This way you can then move your arrow forward by the width returned.

To use a fixed width character

As you've found out some fonts do not have a fixed with. Some do however - these are called monospaced. One commonly used example of this is Courier. The following snippet uses the previous method to examine the distribution of character widths for both Arial and Courier fonts:

print("Arial", Counter(
    [write_character(turtle.Turtle(), c, "Arial") for c in string.ascii_lowercase]
))
print("Courier", Counter(
    [write_character(turtle.Turtle(), c, "Courier") for c in string.ascii_lowercase]
))

which outputs:

Arial Counter({27.0: 11, 24.0: 7, 11.0: 3, 13.0: 2, 41.0: 1, 16.0: 1, 36.0: 1})
Courier Counter({30.0: 26})

Here we can see that Arial has 7 different character widths, whilst Courier has only a single character width.

Ben Horsburgh
  • 563
  • 4
  • 10