[英]How would I calculate the X coordinate required to keep space between 2 drawn sentences in PIL?
I'm trying to make a Python script to generate a fake Discord message, and this is my code so far:我正在尝试制作 Python 脚本来生成假的 Discord 消息,这是我到目前为止的代码:
from PIL import Image, ImageFont, ImageDraw
text = "Hello"
name = "A username...."
date = "Today at 10:30 AM"
comment = Image.open("message.png")
text_font = ImageFont.truetype("whitneybook.otf", 31)
name_font = ImageFont.truetype("whitneymedium.otf", 32)
date_font = ImageFont.truetype("whitneymedium.otf", 25)
draw = ImageDraw.Draw(comment)
draw.text((129, 70), text, (215, 215, 215), font=text_font)
draw.text((129, 25), name, (250, 250, 250), font=name_font)
draw.text((356, 32), date, (120, 120, 120), font=date_font)
comment.show()
And this is the result:这是结果:
This code works, but I want the time and name to be able to be dynamic.此代码有效,但我希望时间和名称能够是动态的。 If I change the
name
variable to "A very long username", I get this result:如果我将
name
变量更改为“A very long username”,我会得到以下结果:
How can I calculate the X-coordinate required to stop the username and date from overlapping?如何计算阻止用户名和日期重叠所需的 X 坐标?
Font objects have a getsize
method, which should serve your purpose.字体对象有一个
getsize
方法,应该可以满足您的目的。 One way or another, this solves all your problems.一种或另一种方式,这解决了你所有的问题。
In the simplest case, you just want to find the x-coordinate for the date:在最简单的情况下,您只想找到日期的 x 坐标:
date_x = name_font.getsize(name)[0] + 129 + 32
draw.text((date_x, 32), date, (120, 120, 120), font=date_font)
The offset in date_x
is 129 for the left offset of the text, and 32 for the name-date padding. date_x
中的偏移量对于文本的左偏移量是 129,对于名称日期填充是 32。
Now you probably don't want to run your date off the edge of the image.现在您可能不想在图像边缘运行您的日期。 In fact, let's say you want to always ensure a 10px right margin for it.
事实上,假设您希望始终确保 10 像素的右边距。 In that case, you may need to adjust the x-coordinate a bit by inserting the following between the other two lines:
在这种情况下,您可能需要通过在其他两行之间插入以下内容来稍微调整 x 坐标:
max_date_x = comment.width - 10 - date_font.getsize(date)[0]
date_x = min(date_x, max_date_x)
Finally, you may want to truncate the username if it exceeds a certain length.最后,如果用户名超过一定长度,您可能希望截断用户名。 This is a bit less trivial, since each letter is a different size.
这有点不重要,因为每个字母的大小不同。 The amount of space you are targetting is
date_x - 129
, but also accounting for an ellipsis after the truncated name and some padding.您要定位的空间量是
date_x - 129
,但还要考虑截断名称和一些填充后的省略号。 Let's do a linear search:让我们做一个线性搜索:
name_width = name_font.getsize(name)[0]
name_space = date_x - 129 - 10
n = 0
while name_width > name_space:
n += 1
name_width = name_font.getsize(name[:-n] + '...')
display_name = name[:-n] + '...' if n else name
You could do the same thing with a binary search for the correct value of n
.您可以对
n
的正确值进行二进制搜索来执行相同的操作。 Don't forget to draw display_name
instead of name
in this version.不要忘记在这个版本中绘制
display_name
而不是name
。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.