Вот кладжа, который хорошо работает для меня. Это вариант ответа гнуда. (Достаточно отличается, чтобы заслуживать отдельного ответа и комментария, я надеюсь.) Я проверил много словосочетаний, и это выполнялось последовательно.
Когда текст рисуется без полной высоты шрифта, может произойти отсечение. Как отметил gnud, используя такие символы, как «Aj» (я использую «Fj»), вы избегаете этой ошибки.
Всякий раз, когда слово помещается:
1) Сделайте draw.textsize (текст, шрифт = шрифт) с желаемым словом. Сохраните высоту / ширину.
2) Добавьте 'Fj' (пробелFJ) в конец слова, переделайте текст и сохраните третью высоту / ширину.
4) Вы будете фактически рисовать текст со словом из пункта 2 (с 'Fj' в конце). Наличие этого дополнения предотвратит обрезание шрифта.
4) Прежде чем вы начнете рисовать текст, обрежьте изображение в том месте, где приземлится 'Fj' (crop.load () требуется, чтобы избежать ленивого копирования). Затем нарисуйте текст и поместите обрезанное изображение обратно на «Fj».
Этот процесс позволяет избежать обрезки, кажется достаточно производительным и дает полный незафиксированный текст. Ниже приведена копия / вставка раздела кода Python, который я использую для этого. Частичный пример, но, надеюсь, это добавляет понимание.
# note: xpos & ypos were previous set = coordinates for text draw
# the hard-coded addition of 4 to c_x likely will vary by font
# (I only use one font in this process, so kludged it.)
width, height = draw.textsize(word, font=font)
word2 = word + ' Fj'
width2, height2 = draw.textsize(word2, font=font)
# crop to overwrite ' Fj' with previous image bits
c_w = width2 - width
c_h = height2
c_x = xpos + width + 4
c_y = ypos
box = (c_x, c_y, c_x + c_w, c_y + c_h)
region = img.crop(box)
region.load()
draw.text((xpos, ypos), word2, (0,0,0), font=font)
img.paste(region, box)