Reportlab生成PDF文件

项目列表bullet在段落样式Paragraph Style和XML标签都有设置参数,然而一个我也没试验成功,最后还是用了ListFlowable这种flowable做出想要的项目列表来的。

方法是先生成文档对象,而后用ListFlowable()生成项目列表对象,加进放flowable的列表变量。然后用文档对象的build()把flowable列表灌进PDF文件。

单独拎出生成项目列表对象的ListFlowable,第一个参数是列表,放项目条目。项目条目如果没有什么特殊要求,就用Paragraph()直接生成项目条目:

t = ListFlowable(
    [
        Paragraph("沁芳亭", style),
        Paragraph("荼蘼架", style),
    ]
    其它项目列表参数
    )

如果项目条目有特殊要求,比如缩进、调整项目顺序之类就得用ListItem()生成条目:

t = ListFlowable(
    [
        ……
        ListItem(Paragraph('潇湘馆', style),
                 bulletColor='red',    # 项目符号为红色
                 value='diamondwx',    # 指定项目符号的样式
                 leftIndent=50         # 项目左缩进50
                 ),
        ……
     ]

回到listFlowable,除了第一个参数列表定义项目条目外,还可以指定影响整个项目列表的参数,比如项目符号类型,项目符号与项目之间的间距等等。

先来试试各参数,效果图见图一,代码随后:

图一 生成项目列表的参数效果

from reportlab.platypus import ListFlowable, ListItem, Paragraph, SimpleDocTemplate
from myStyle import *    # 从自己定义的段落格式文件myStyle.py中引入段落格式

doc = SimpleDocTemplate(filename="bulletExample1.pdf")  # 生成文档对象
Story = []          # 存放flowables的列表
style = styles['text']    # 自己定义的段落格式

t = ListFlowable(      # 生成项目列表对象
  [
    Paragraph(" 沁芳亭", style),
    # 使用默认项目条目格式,"沁芳亭"使用styles['text']的段落格式
    ListItem(  # 不使用默认项目格式
          Paragraph("荼蘼架", style),
          bulletColor="green",value=7
          # 项目符号颜色绿色,项目序号为7
        ),
    ListFlowable([  # 又是一个项目列表
      Paragraph("稻香村 square", style),
      ListItem(Paragraph('潇湘馆 diamondwx', style),
           bulletColor='red',  # 项目符号颜色为红色
           value='diamondwx',  # 项目符号效果见图1
           ),
      ListItem(Paragraph('蘅芜苑 bulletchar', style),
           value='bulletchar'
           ),
      ListItem(Paragraph('怡红院 circle', style),
           value='circle',
           leftIndent=100
           # 怡红院 circle这个条目左缩进100
           ),
      ListItem(Paragraph('秋爽斋 blackstar', style),
           bulletColor='red',
           value='blackstar',
           leftIndent=150
           # 秋爽斋 blackstar这个条目左缩进150
           ),
      ListItem(Paragraph('缀锦阁 diamond', style),
           value='diamond',
           ),
      ListItem(Paragraph('蓼风轩 rarrowhead', style),
           value='rarrowhead',
           ),
      ListItem(Paragraph('栊翠庵 加大了的sparkle', style),
           value='sparkle',
           bulletFontSize=20,
           # 项目符号增大到20
           ),
      ListItem(Paragraph('芭蕉坞 squarelrs', style),
           value='squarelrs',
           )
          ],
          # 以下是这个子项目列表缺省的项目设置
          bulletType='bullet',  # 用项目符号
          start='square',      # 缺省项目符号是方块
          leftIndent=20
          # 注意这个不是左缩进,而是项目标号与文字的间距
          ),
    Paragraph("编花牖", style),
  ],
  # 以下是这个项目列表缺省的项目设置
  leftIndent = 30,  # 注意这个不是左缩进,而是项目标号与文字的间距
  bulletType='i',    # 项目编号:I, II, III, IV
  # bulletType='I',  # 项目编号:i, ii, iii, iv
  # bulletType='1',  # 项目编号:1,2,3..
  # bulletType='A',  # 项目编号:A,B,C
  # bulletType='a'  # 项目编号:a,b,c
)
Story.append(t)      # 将项目列表对象添加进Story
doc.build(Story)    # 写入PDF文件

接下来生成一个带子列表的项目列表,图二是效果图,代码随后:

图二 两层项目列表

from reportlab.platypus import ListFlowable, ListItem, Paragraph, SimpleDocTemplate
from myStyle import *

doc = SimpleDocTemplate(filename="bulletExample2.pdf")  # 生成文档对象
Story = []                # 存放flowables的列表
style = styles['text']          # myStyle.py里定义的段落格式

Story.append(ListFlowable(
    [
        Paragraph("沁芳亭", style),    # 项目条目
        Paragraph("荼蘼架", style),
    ],
    bulletType ='1',  # 项目编号:1、2、3……
))

Story.append(ListFlowable(      # 子项目列表
    [
        ListItem(Paragraph("稻香村", style),
                 leftIndent=50    # 子项目条目左缩进,只能在这里设定
                 ),
        ListItem(Paragraph('潇湘馆', style),
                 leftIndent=50
                 ),
        ListItem(Paragraph('蘅芜苑', style),
                leftIndent = 50
                 ),
        ListItem(Paragraph('怡红院', style),
                 leftIndent=50
                 ),
        ListItem(Paragraph('秋爽斋', style),
                 leftIndent=50  # 标号的左间距
                 ),
        ListItem(Paragraph('缀锦阁', style),
                 leftIndent=50
                 ),
        ListItem(Paragraph('蓼风轩', style),
                 leftIndent=50
                 ),
        ListItem(Paragraph('栊翠庵', style),
                 leftIndent=50
                 ),
        ListItem(Paragraph('芭蕉坞', style),
                 leftIndent=50
                 )
    ],
  # 子项目的缺省设置
    bulletType = 'bullet',    # 用项目符号
  bulletColor = 'red',    # 项目符号用红色
    start = 'sparkle',      # 指定项目符号
    leftIndent = 20 ))       # 设定项目符号与文字之间距离

Story.append(ListFlowable(
    [
        ListItem(
                    Paragraph("编花牖", style),
                    value=3,  # 项目序号从3开始
                ),
    ],
    bulletType = '1'))  # 项目编号:1、2、3……

doc.build(Story)     # 写入PDF文件

最后就是myStyle.py关于这里用到的段落格式的部分,myStyle.py所在路径要加进Python解释器的搜索路径内才找得到:

from reportlab.lib.styles import ParagraphStyle, getSampleStyleSheet
from reportlab.pdfbase.ttfonts import TTFont
from reportlab.pdfbase import pdfmetrics
# 注册中文字体
pdfmetrics.registerFont(TTFont('lively', '/Library/Fonts/Chinese/ChaoZiSheZengYuBoShouShuJian-2.ttf'))
ttf'))
styles = {
   ……
  'text':ParagraphStyle('text', fontName='lively', fontSize=18,
              leading=30)  # 定义段落格式
   ……
   }