1

我是 Python 新手,我正在尝试访问 Google 的 QuickDraw 数据库并根据用户输入的列和行排列大量图像(矢量线),然后以 .svg 文件格式导出。到目前为止,我只设法将每个图像保存为 .gif 并显示它。如何以 3x3 网格和 .svg 格式排列它们?

这是我到目前为止的代码:

from PIL import Image, ImageDraw
from quickdraw.data import QuickDrawData

rows = int(input("How many rows do you want? "))
columns = int(input("How many columns do you want? "))
rows_columns = rows * columns
name_var = 0

for image in range(0,rows_columns):
    
    qd = QuickDrawData()
    duck = qd.get_drawing("duck")
    duck_image = Image.new("RGB", (255,255), color = (255,255,255))
    duck_drawing = ImageDraw.Draw(duck_image)

    for stroke in duck.strokes:

        for coordinate in range(len(stroke)-1):
            x1 = stroke[coordinate][0]
            y1 = stroke[coordinate][1]
            x2 = stroke[coordinate+1][0]
            y2 = stroke[coordinate+1][1]
            duck_drawing.line((x1,y1,x2,y2), fill=(0,0,0), width=2)

    duck_image.show()
    name_var += 1
    duck.image.save(f"my_duck{name_var}.gif")

理想情况下,结果应该是 .svg 文件格式。

4

1 回答 1

0

您将需要一个可以输出 SVG 文件的 python 库。

不幸的是,我没有时间用刚刚运行的代码片段提供详细的答案,但希望我能提供一些指导。

有多个 python 模块来编写 SVG 文件:svgwrite是其中之一(文档示例)。

基于示例代码段:

import svgwrite

dwg = svgwrite.Drawing('test.svg', profile='tiny')
dwg.add(dwg.line((0, 0), (10, 0), stroke=svgwrite.rgb(10, 10, 16, '%')))
dwg.add(dwg.text('Test', insert=(0, 0.2), fill='red'))
dwg.save()

您应该能够执行以下操作:

from PIL import Image, ImageDraw
from quickdraw.data import QuickDrawData
import svgwrite

dwg = svgwrite.Drawing('test.svg', profile='tiny')

rows = int(input("How many rows do you want? "))
columns = int(input("How many columns do you want? "))
rows_columns = rows * columns
name_var = 0

for image in range(0,rows_columns):
    
    qd = QuickDrawData()
    duck = qd.get_drawing("duck")
    duck_image = Image.new("RGB", (255,255), color = (255,255,255))
    duck_drawing = ImageDraw.Draw(duck_image)

    for stroke in duck.strokes:

        for coordinate in range(len(stroke)-1):
            x1 = stroke[coordinate][0]
            y1 = stroke[coordinate][1]
            x2 = stroke[coordinate+1][0]
            y2 = stroke[coordinate+1][1]
            duck_drawing.line((x1,y1,x2,y2), fill=(0,0,0), width=2)
            # you many need to offset dwg.line using row/col grid index and drawing size
            dwg.add(dwg.line((x1, y1), (x2, y2), stroke=svgwrite.rgb(10, 10, 16, '%')))

    duck_image.show()
    name_var += 1
    duck.image.save(f"my_duck{name_var}.gif")
# save svg of all ducks (grid)
dwg.save()
    

请记住,上面的代码未经测试,但希望它说明了这一点。如果您是该模块的新手,我推荐一步一步的方法:

  1. 编写基本 svg 的基本测试脚本(例如示例代码段):确保模块安装正确且工作正常
  2. 使用 quickdraw 和 svgwrite 绘制单只鸭子的基本脚本
  3. 绘制鸭子网格的脚本

这个想法是,如果任何步骤失败,单独调试/修复会更容易。

我怀疑您可能还需要计算出每只鸭子的尺寸/边界框,并将网格缩放/对齐到相同大小的矩形,然后偏移每条线的坐标。从理论上讲,您可以将每只鸭子绘制为一个组,然后简单地 SVG 转换每个组,使其对齐为网格(而不是所有鸭子重叠)

此外,您可能会发现 sketch-rnn 很有趣,因为它使用了 quickdraw 数据集。特别是查看 David Ha 的Sketch-RNN Colab 笔记本或他的sketch-rnn/utils.py脚本。尽管 QuickDraw 笔画格式与 sketch-rnn 笔画格式略有不同,但仍有很多相似之处,并且上面的链接包含用于绘制 svg 网格的实用函数。他们需要适应 QuickDraw 的格式。

如果您不仅限于 Python 并且对一些 JavaScript 感到满意,那么 QuickDraw 数据集 README 已经包含指向d3.js SVG 演示的链接

于 2021-12-17T01:37:18.053 回答