I am trying to convert one long text to multiline text. I wrote some code, and it mostly works. But I have some problems in line width calculation. Because the lines getting shorter and shorter. Probably caused by lastCalculatedWidth
or resultTextLength
or both of them. I tried a lot of things but I'm very confused and I want to solve this as soon as possible, I would appreciate it if you could help me.
text = "Lorem ipsum dolor sit amet, consectetur adipiscing elit. Donec augue leo, pulvinar maaaıs sagittis sit amet, tristique viverra mauris. Sed mauris quam, faucibus id pretium non, varius eget leo."
result_text = ""
messageBreakLineIndexes = []
calculatedWords = 0
messageLineWidth = draw.textlength(text, font=font)
resultTextLength = 0
lastCalculatedWidth = 0
calculationSwitch = True
while calculatedWords < len(text.split()):
result_text += text.split()[calculatedWords] + " "
resultTextLength += draw.textlength(text.split()[calculatedWords], font=font)
if resultTextLength > img.width - 60:
result_text = result_text.rstrip()
result_text = result_text.rsplit(" ", 1)[0]
messageBreakLineIndexes.append(len(result_text))
calculatedWords -= 1
resultTextLength -= draw.textlength(result_text.rstrip(), font=font) - lastCalculatedWidth
lastCalculatedWidth = draw.textlength(result_text.rstrip(), font=font)
calculatedWords += 1
print(messageBreakLineIndexes)
for i in range(len(messageBreakLineIndexes)):
index = messageBreakLineIndexes[i]
result_text = result_text[:index+i] + "\n" + result_text[index+i:]
draw.text(text_position, result_text, font=font, fill=text_color)
i merged codes with mine and @Attersson's answer because draw.textlength
cannot work with \n
. It's look like fine now.
text = "Lorem ipsum dolor sit amet, consectetur adipiscing elit. Donec augue leo, pulvinar maaaıs sagittis sit amet, tristique viverra mauris. Sed mauris quam, faucibus id pretium non, varius eget leo."
result_text = ""
messageBreakLineIndexes = []
resultTextLength = 0
words = text.split()
# Iterate over the words directly as an iterable, not by len
for word in words:
# Check the width of the current line plus the next word
word_width = draw.textlength(word, font=font)
if resultTextLength + word_width <= img.width - 60:
# If the line isn't too wide, add the word to the line
result_text += word + " "
resultTextLength += word_width + draw.textlength(" ", font=font) # Add space width
else:
# If the line is too wide, break the line
result_text = result_text.rstrip()
messageBreakLineIndexes.append(len(result_text))
result_text += word + " "
resultTextLength = word_width + draw.textlength(" ", font=font) # Reset line width
for i in range(len(messageBreakLineIndexes)):
index = messageBreakLineIndexes[i]
result_text = result_text[:index+i] + "\n" + result_text[index+i:]
draw.text(text_position, result_text, font=font, fill=text_color)