python批量生成word文档

一.python-docx

这是一个很强大的包,可以用来创建docx文档,包含段落、分页符、表格、图片、标题、样式等几乎所有的word文档中能常用的功能都包含了,这个包的主要功能便是用来创建文档,相对来说用来修改功能不是很强大,官网文档

安装
pip install python-docx
新建文档
from docx import Document

document = Document()
添加段落
from docx import Document

document = Document()
paragraph = document.add_paragraph('Lorem ipsum dolor sit amet.')
document.save('00.docx')

这里写图片描述


from docx import Document

document = Document()
paragraph = document.add_paragraph('Lorem ipsum dolor sit amet.')
document.add_paragraph('Lorem ipsum dolor sit amet.', style='ListBullet')
prior_paragraph = paragraph.insert_paragraph_before('Lorem ipsum')
document.save('00.docx')

这里写图片描述

添加标题
from docx import Document

document = Document()
document.add_heading('The REAL meaning of the universe',0)
document.add_heading('The role of dolphins', level=0)
document.add_heading('The role of dolphins', level=1)
document.add_heading('The role of dolphins', level=2)
document.add_heading('The role of dolphins', level=3)
document.add_heading('The role of dolphins', level=4)
document.save('00.docx')

这里写图片描述

新起一页
document.add_page_break()
添加表格
from docx import Document

document = Document()
##创建带边框的表格
table = document.add_table(rows=2, cols=2,style='Table Grid')
cell = table.cell(0, 1)
#第一行第二列
cell.text = 'parrot, possibly dead'

document.save('00.docx')

这里写图片描述

from docx import Document

document = Document()
##创建带边框的表格
table = document.add_table(rows=2, cols=2,style='Table Grid')
#第二行
row = table.rows[1]
row.cells[0].text = 'Foo bar to you.'
row.cells[1].text = 'And a hearty foo bar to you too sir!'

document.save('00.docx')

这里写图片描述

from docx import Document

document = Document()


##创建带边框的表格
table = document.add_table(1, 3,style='Table Grid')
#设置表格样式
table.style = 'LightShading-Accent1'
# populate header row 
heading_cells = table.rows[0].cells
heading_cells[0].text = 'Qty'
heading_cells[1].text = 'SKU'
heading_cells[2].text = 'Description'

# add a data row for each item
for i in  range(2):
    cells = table.add_row().cells
    cells[0].text = str(i)
    cells[1].text = str(i)
    cells[2].text = str(i)
document.save('00.docx')

这里写图片描述

取出表格内容
from docx import Document

document = Document('00.docx')
tables = document.tables
for table in tables:
    for row in table.rows:
        for cell in row.cells:
            print(cell.text)
print("#"*50)
row_count = len(tables[0].rows)
col_count = len(tables[0].columns)
print(row_count)
print(col_count)
运行结果:


Foo bar to you.
And a hearty foo bar to you too sir!
##################################################
2
2
综合应用


from docx import Document
from docx.shared import Inches

document = Document()

document.add_heading('Document Title', 0)

p = document.add_paragraph('A plain paragraph having some ')
p.add_run('bold').bold = True
p.add_run(' and some ')
p.add_run('italic.').italic = True

document.add_heading('Heading, level 1', level=1)
document.add_paragraph('Intense quote', style='IntenseQuote')

document.add_paragraph(
    'first item in unordered list', style='ListBullet'
)
document.add_paragraph(
    'first item in ordered list', style='ListNumber'
)

document.add_picture('img.gif', width=Inches(2.25))

table = document.add_table(rows=1, cols=3)
table.style = 'LightShading-Accent1'
hdr_cells = table.rows[0].cells
hdr_cells[0].text = 'Qty'
hdr_cells[1].text = 'Id'
hdr_cells[2].text = 'Desc'
for item in range(6):
    row_cells = table.add_row().cells
    row_cells[0].text = str(item)
    row_cells[1].text = str(item)
    row_cells[2].text = str(item)

document.add_page_break()

document.save('demo.docx')

这里写图片描述

二.python-docx-template

和python中的jinja2模板语言一样,有上下文,有模板,然后进行变量的替换,这个包的主要功能是修改word文档。
这个包中使用了两个主要的包:
python-docx:读写word文档
jinja2:基于python的模板引擎,Flask使用jinja2作为框架的模板系统

动态生成表格
from docxtpl import DocxTemplate

tpl=DocxTemplate('test_files/dynamic_table_tpl.docx')

context = {
    'col_labels' : ['fruit', 'vegetable', 'stone', 'thing'],
    'tbl_contents': [
        {'label': 'yellow', 'cols': ['banana', 'capsicum', 'pyrite', 'taxi']},
        {'label': 'red', 'cols': ['apple', 'tomato', 'cinnabar', 'doubledecker']},
        {'label': 'green', 'cols': ['guava', 'cucumber', 'aventurine', 'card']},
        ]
}

tpl.render(context)
tpl.save('dynamic_table.docx')

模板文件dynamic_table_tpl.docx
这里写图片描述
生成文件dynamic_table.docx
这里写图片描述

动态改变单元格的背景色

from docxtpl import DocxTemplate, RichText

tpl=DocxTemplate('test_files/cellbg_tpl.docx')

context = {
    'alerts' : [
        {'date' : '2015-03-10', 'desc' : RichText('Very critical alert',color='FF0000', bold=True), 'type' : 'CRITICAL', 'bg': 'FF0000' },
        {'date' : '2015-03-11', 'desc' : RichText('Just a warning'), 'type' : 'WARNING', 'bg': 'FFDD00' },
        {'date' : '2015-03-12', 'desc' : RichText('Information'), 'type' : 'INFO', 'bg': '8888FF' },
        {'date' : '2015-03-13', 'desc' : RichText('Debug trace'), 'type' : 'DEBUG', 'bg': 'FF00FF' },
    ],
}

tpl.render(context)
tpl.save('cellbg.docx')

模板文件cellbg_tpl.docx
这里写图片描述
生成文件cellbg.docx
这里写图片描述

动态生成页眉;页脚及标题
from docxtpl import DocxTemplate

tpl=DocxTemplate('test_files/header_footer_tpl.docx')

sd = tpl.new_subdoc()
p = sd.add_paragraph('This is a sub-document to check it does not break header and footer')

context = {
    'title' : 'Header and footer test',
    'company_name' : 'The World Wide company',
    'date' : '2016-03-17',
    'mysubdoc' : sd,
}

tpl.render(context)
tpl.save('header_footer.docx')

模板文件header_footer_tpl.docx
这里写图片描述
生成文件header_footer.docx
这里写图片描述

替换图片
from docxtpl import DocxTemplate

DEST_FILE = 'replace_picture.docx'

tpl=DocxTemplate('test_files/replace_picture_tpl.docx')

context = {}

tpl.replace_pic('python_logo.png','test_files/python.png')
tpl.render(context)
tpl.save(DEST_FILE)

模板文件replace_picture_tpl.docx
这里写图片描述
生成文件replace_picture.docx
这里写图片描述

替换页眉中的图片


from docxtpl import DocxTemplate

DEST_FILE = 'header_footer_image.docx'

tpl=DocxTemplate('test_files/header_footer_image_tpl.docx')

context = {
    'mycompany' : 'The World Wide company',
}
tpl.replace_media('test_files/dummy_pic_for_header.png','test_files/python.png')
tpl.render(context)
tpl.save(DEST_FILE)

模板文件header_footer_image_tpl.docx
这里写图片描述
生成文件header_footer_image.docx
这里写图片描述

段落和表格中插入图片

from docxtpl import DocxTemplate, InlineImage
# for height and width you have to use millimeters (Mm), inches or points(Pt) class :
from docx.shared import Mm, Inches, Pt
import jinja2
from jinja2.utils import Markup

tpl=DocxTemplate('test_files/inline_image_tpl.docx')

context = {
    'myimage' : InlineImage(tpl,'test_files/python_logo.png',width=Mm(20)),
    'myimageratio': InlineImage(tpl, 'test_files/python_jpeg.jpg', width=Mm(30), height=Mm(60)),

    'frameworks' : [{'image' : InlineImage(tpl,'test_files/django.png',height=Mm(10)),
                      'desc' : 'The web framework for perfectionists with deadlines'},

                    {'image' : InlineImage(tpl,'test_files/zope.png',height=Mm(10)),
                     'desc' : 'Zope is a leading Open Source Application Server and Content Management Framework'},

                    {'image': InlineImage(tpl, 'test_files/pyramid.png', height=Mm(10)),
                     'desc': 'Pyramid is a lightweight Python web framework aimed at taking small web apps into big web apps.'},

                    {'image' : InlineImage(tpl,'test_files/bottle.png',height=Mm(10)),
                     'desc' : 'Bottle is a fast, simple and lightweight WSGI micro web-framework for Python'},

                    {'image': InlineImage(tpl, 'test_files/tornado.png', height=Mm(10)),
                     'desc': 'Tornado is a Python web framework and asynchronous networking library.'},
                    ]
}
# testing that it works also when autoescape has been forced to True
jinja_env = jinja2.Environment(autoescape=True)
tpl.render(context, jinja_env)
tpl.save('inline_image.docx')

模板文件inline_image_tpl.docx
这里写图片描述

生成文件inline_image.docx
这里写图片描述

默认的页眉页脚

from docxtpl import DocxTemplate

tpl=DocxTemplate('test_files/header_footer_entities_tpl.docx')

context = {
    'title' : 'Header and footer test',
}

tpl.render(context)
tpl.save('header_footer_entities.docx')

模板文件header_footer_entities_tpl.docx
这里写图片描述
生成文件header_footer_entities.docx
这里写图片描述

生成账单

from docxtpl import DocxTemplate

tpl=DocxTemplate('test_files/order_tpl.docx')

context = {
    'customer_name' : 'Eric',
    'items' : [
        {'desc' : 'Python interpreters', 'qty' : 2, 'price' : 'FREE' },
        {'desc' : 'Django projects', 'qty' : 5403, 'price' : 'FREE' },
        {'desc' : 'Guido', 'qty' : 1, 'price' : '100,000,000.00' },
    ],
    'in_europe' : True,
    'is_paid': False,
    'company_name' : 'The World Wide company',
    'total_price' : '100,000,000.00'
}

tpl.render(context)
tpl.save('order.docx')

模板文件order_tpl.docx
这里写图片描述
生成文件order.docx
这里写图片描述

嵌套for循环

from docxtpl import DocxTemplate

tpl=DocxTemplate('test_files/nested_for_tpl.docx')

context = {
    'dishes' : [
        {'name' : 'Pizza', 'ingredients' : ['bread','tomato', 'ham', 'cheese']},
        {'name' : 'Hamburger', 'ingredients' : ['bread','chopped steak', 'cheese', 'sauce']},
        {'name' : 'Apple pie', 'ingredients' : ['flour','apples', 'suggar', 'quince jelly']},
    ],
    'authors' : [
        {'name' : 'Saint-Exupery', 'books' : [
            {'title' : 'Le petit prince'},
            {'title' : "L'aviateur"},
            {'title' : 'Vol de nuit'},
        ]},
        {'name' : 'Barjavel', 'books' : [
            {'title' : 'Ravage'},
            {'title' : "La nuit des temps"},
            {'title' : 'Le grand secret'},
        ]},
    ]
}

tpl.render(context)
tpl.save('nested_for.docx')

模板文件nested_for_tpl.docx
这里写图片描述
生成文件nested_for.docx
这里写图片描述
未完待续。。。。。

原文地址:https://www.cnblogs.com/feifeifeisir/p/13689553.html