Python图像处理:Pillow库实现自动换行文本标注
Python凭借其丰富的开源库,已成为图像处理领域的领先编程语言。Pillow便是其中一个常用的图像处理库,它简洁易用且文档完善,常用于图像缩放、裁剪、亮度调整和标注等操作。
然而,Pillow在文本标注方面存在一个问题:当文本超过文本框宽度时,不会自动换行。Pillow库本身并没有提供此功能,需要我们自行编写逻辑实现。
本教程将演示如何使用Pillow库在Python中添加一个自动换行的文本框,从而实现正确的图像文本标注。最终效果如下:
上图是我的Dev.to个人资料截图,我们将以此为例进行讲解。绿色文本框即为我们添加的文本标注。
本教程要求您具备基本的Python编程知识,例如条件语句(if, else)、for循环等。您还需要以下工具和软件:
按照以下步骤创建一个新项目:
A. 使用终端/命令行创建新文件夹:
<code class="language-bash">mkdir image_annotation</code>
B. 使用pip安装virtualenv (如果您已安装,请跳过此步骤):
<code class="language-bash">pip install virtualenv</code>
C. 将工作目录切换到image_annotation文件夹:
<code class="language-bash">cd image_annotation</code>
D. 创建新的虚拟环境:
<code class="language-bash">virtualenv env</code>
E. 激活虚拟环境 (Windows使用命令提示符):
Windows:
<code class="language-bash">.\env\Scripts\activate</code>
Linux/macOS:
<code class="language-bash">source env/bin/activate</code>
F. 使用pip安装Pillow库:
<code class="language-bash">pip install pillow</code>
在代码编辑器中打开项目,并在项目文件夹中创建一个名为script.py
的新Python文件。
您要标注的图像即为基础图像。使用Pillow的ImageDraw
模块打开并准备图像。在script.py
文件中编写以下代码:
<code class="language-python">from PIL import Image, ImageDraw, ImageFont image_file = "path_to_image" # 请替换为您的图片路径 # 打开图像 image = Image.open(image_file) # 初始化ImageDraw draw = ImageDraw.Draw(image)</code>
Pillow可以添加纯文本和带背景填充的文本框,文本可以是单行或多行。本教程重点讲解如何添加多行文本框。
ImageDraw.multiline_text()
方法可以添加多行纯文本,但没有背景填充。ImageDraw.rectangle()
方法可以添加带背景填充的文本框。
在script.py
文件中添加以下代码:
<code class="language-bash">mkdir image_annotation</code>
这段代码设置了文本、字体和文本框宽度。x
和y
变量表示绘图的起始点,end_x
和end_y
表示文本框的右下角坐标。文本框的宽度和高度分别为200和50。
ImageDraw.rectangle()
和ImageDraw.multiline_text()
方法分别用于绘制文本框和多行文本。image.show()
方法用于显示处理后的图像。您可以使用image.save("new_image.png")
保存图像。结果如下:
上图中标注仍然存在问题,多行文本没有自动换行。下一节将讲解如何解决这个问题。
换行符n
用于指定换行位置。在之前的例子中,换行符n
之后的内容会换行。但在实际应用中,文本长度通常是动态的,很难确定换行符的位置。
Pillow的ImageDraw
模块的.textlength()
属性可以计算文本长度,将其与文本框宽度进行比较,从而确定换行位置。
在script.py
文件顶部(import语句之后)创建一个名为wrap_text()
的新函数,包含自动换行逻辑:
<code class="language-bash">pip install virtualenv</code>
在text
, font
, max_width
变量之后添加以下代码:
<code class="language-bash">cd image_annotation</code>
将draw.multiline_text()
方法替换为以下代码:
<code class="language-bash">virtualenv env</code>
从文本中删除换行符n
并运行代码:
<code class="language-bash">.\env\Scripts\activate</code>
运行结果显示文本仍然超出文本框高度。虽然文本可以根据文本框宽度自动调整,但文本框高度固定,导致文本溢出。
动态文本框高度根据文本行数确定。第一步是将文本框的end_y
变量更改为动态值:
<code class="language-bash">source env/bin/activate</code>
此公式是在多次试验后得到的,它似乎是此用例中获得动态文本框高度的最佳解决方案。wrapped_lines
列表包含所有要添加到文本框的行,因此该列表的长度等于文本框的总行数。
结果如下:
您可能需要将总行数乘以不同的值才能获得适合您用例的完美解决方案。
文本距离文本框边缘太近,影响可读性和样式。可以通过在文本框内添加填充来解决这个问题。在script.py
文件中添加一个新的padding
变量并更改文本框尺寸:
<code class="language-bash">pip install pillow</code>
这段代码允许文本和文本框边缘之间留出间距。
指针可以方便地指示标注/标签所指的图像部分。指针应该位于标注之前。这意味着指针将绘制在文本框的当前位置,而文本框将向右移动。
因此,文本框的x轴将与新的box_x
变量关联。此更改也必须反映在使用文本框x轴的其他变量中。以下是更新后的代码:
<code class="language-bash">mkdir image_annotation</code>
在上面的代码中,ImageDraw.circle()
方法(其中10是半径)用于在指定点绘制指针。box_x
变量是文本框x轴的新值。
以下是script.py
文件的完整代码:
<code class="language-bash">pip install virtualenv</code>
图像处理并不总是像看起来那么困难。虽然有些图像处理库无法直接用其模块解决您的问题,但您可以使用现有模块为您的用例实现特定解决方案。这就是编码的魅力——能够用自定义和特定解决方案来解决问题。
在本教程中,您学习了如何使用Python的Pillow库来标注图像,添加自动换行的多行文本框等。您还学习了如何编写可以帮助您进行图像处理的数学公式。
请参考Pillow文档以详细了解所用模块。
以上是使用 Python 的 Pillow 库在图像上包裹和渲染多行文本的详细内容。更多信息请关注PHP中文网其他相关文章!