python-docx是用来处理word文档的一个python库,用他可以很方便的操作Word2017及以后的文档。可以对Word做新建和编辑操作。
官方帮助文档地址:python-docx — python-docx 1.1.0 documentation
1、python-docx安装
打开命令行,输入以下命令按回车
pip install python-docx
2、Demo
使用pycharm创建一个python工程,或者使用vscode创建一个python文件,复制下面的代码,然后
运行,会在运行python文件的同级目录,生成一个名为demo.docx的Word文档。
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='Intense Quote')
document.add_paragraph(
'first item in unordered list', style='List Bullet'
)
document.add_paragraph(
'first item in ordered list', style='List Number'
)
document.add_picture('monty-truth.png', width=Inches(1.25))
records = (
(3, '101', 'Spam'),
(7, '422', 'Eggs'),
(4, '631', 'Spam, spam, eggs, and spam')
)
table = document.add_table(rows=1, cols=3)
hdr_cells = table.rows[0].cells
hdr_cells[0].text = 'Qty'
hdr_cells[1].text = 'Id'
hdr_cells[2].text = 'Desc'
for qty, id, desc in records:
row_cells = table.add_row().cells
row_cells[0].text = str(qty)
row_cells[1].text = id
row_cells[2].text = desc
document.add_page_break()
document.save('demo.docx')
Demo生成的Word文档打开如下图,Demo的演示中包括:标题,段落,一级标题,无序列表,有序列表,图片,表格,分页。
3、理解python-docx
3.1、Document对象(文档)
Document是一个Word文档对象,每一个Word文档,对应一个Document对象,Word文档里面的段落、表格、图片等都是基于Document对象去处理的。
在python-docx中,创建一个新的Document对象,然后保存,就生成一个空白文档。
document = Document()
document.save('demo.docx')
创建一个新的Document对象的时候,指定一个Word文档,就把Word读取到了Document对象中。保存时指定一个新的名称,就会生成一份新的文档,相当于做了一个复制。
document = Document(r'C:\Python\test.docx)
document.save(r'demo.docx')
3.2、Section对象(节)
Word文档里有一个【节】的概念,即文档中具有相同页面布局设置(如页边距和页面方向、页眉页脚)的部分。比如,一个文档中可以包含一些纵向布局的页面,和一些横向布局的页面,并且这些页面可以有自己的页眉和页脚。这种效果就是通过【节】实现的。
大部分Word文档默认只有一个部分,而且大多数文档无需更改默认页边距或其他页面布局。但是,当需要更改页面布局时,需要使用Section对象才能实现。
Document对象新建时默认没有段落,但默认有一个【节】。
3.2.1、添加和获取节
from docx import Document
from docx.enum.section import WD_SECTION_START
document = Document()
# 添加 节
document.add_section(start_type=WD_SECTION_START.NEW_PAGE)
# 获取 节
sections = document.sections
# WD_SECTION_START.CONTINUOUS 连续分节符,枚举值0
# WD_SECTION_START.NEW_COLUMN 新列分节符,枚举值1
# WD_SECTION_START.NEW_PAGE 新页分节符,枚举值2
# WD_SECTION_START.EVEN_PAGE 偶数页分节符,枚举值3
# WD_SECTION_START.ODD_PAGE 奇数页分节符,枚举值4
如果插入【节】的时候不指定节的类型,默认是WD_SECTION_START.NEW_PAGE,即从新页开始一个【节】。
3.2.2、设置节的大小(即设置纸张的大小)
from docx import Document
from docx.shared import Cm
document = Document("demo.docx")
default_section = document.sections[0]
# 默认宽度和高度
print(default_section.page_width.cm)
print(default_section.page_height.cm)
# 可以修改宽度和高度,即自定义纸张大小
default_section.page_width = Cm(30)
default_section.page_height = Cm(20)
3.2.3、设置纸张方向
from docx.enum.section import WD_ORIENTATION
print(default_section.orientation) # 默认是PORTRAIT,纵向
default_section.orientation = WD_ORIENTATION.LANDSCAPE # 横向
# 手动互换高度和宽带
origin_width = default_section.page_width
origin_height = default_section.page_height
default_section.page_width = origin_height
default_section.page_height = origin_width
Section对象的orientation控制纸张的方向,WD_ORIENTATION枚举类型有PORTRAIT和LANDSCAPE两个,分别表示纵向和横向,可以用数字0和1代替。
默认是纵向(PORTRAIT),如果要改为横向,除了修改orientation还需要手动调换一下Section的宽度和高度。
3.2.4、设置页边距
print(default_section.top_margin.cm)
print(default_section.right_margin.cm)
print(default_section.bottom_margin.cm)
print(default_section.left_margin.cm)
# 修改页边距
default_section.top_margin = Cm(2)
default_section.right_margin = Cm(3)
default_section.bottom_margin = Cm(2)
default_section.left_margin = Cm(3)
3.2.4、设置页眉页脚
# 页眉
header = default_section.header # 获取节的页眉
header.paragraphs[0].add_run("这是页眉") # 添加页眉文本
header.paragraphs[0].alignment = WD_PARAGRAPH_ALIGNMENT.CENTER # 页眉样式,居中对齐
print(default_section.header_distance.cm) # 页眉到顶端的距离
default_section.header_distance = Cm(1) # 修改页眉到顶端的距离
# 页脚
footer = default_section.footer # 获取节的页脚
footer.paragraphs[0].add_run("这是页脚") # 添加页脚文本
footer.paragraphs[0].alignment = WD_PARAGRAPH_ALIGNMENT.LEFT # 页脚,居左对齐
print(default_section.footer_distance.cm) # 页脚到底端的距离
default_section.footer_distance = Cm(1) # 修改页脚到底端的距离
Section对象的header属性和footer属性可以获取到页眉和页脚。
3.3、Paragraph对象(段落)
Paragraph表示文档中的段落,可以理解为一个回车就是一段,内容(比如文字)输出在【段】里。
使用方式一:直接添加Paragraph和内容
document.add_paragraph('A plain paragraph having some ')
这样会把内容直接输出为一段,后面带一个回车
问题是文字的样式会使用Document的默认样式,通常不是我们想要的
使用方式二:添加Paragraph,获得Paragraph对象,然后再对该对象添加内容和样式等
p = document.add_paragraph()
p.add_run('A plain paragraph having some ')
p.add_run('bold').bold = True
p.add_run(' and some ')
p.add_run('italic.').italic = True
这样可以对内容做更详细的处理,比如某几个字加粗,某几个字改变颜色,某几个字加下划线等。
这种详细的处理,是通过add_run()方法实现的,add_run()会返回一个Run对象,这个Run对象就是最小的处理单元了。
3.4、Run对象(内容)
Run对象是通过 Paragraph对象调用 add_run() 方法获得的,也就是 Run对象是基于 Paragraph对象产生的。一个Paragraph对象可以产生多个Run对象。
针对产生的Run对象,可以做详细具体的设置。
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
p1 = document.add_paragraph()
r1 = p1.add_run()
r1.text = 'run2'
r1.bold = True
运行效果:
3.5、插入图片
示例:插入图片
document.add_picture('demo_pic.png', width=Inches(1.25), height=Inches(1.25))
# 或
pic = document.add_picture('demo_pic.png')
pic.width = Inches(1.25)
pic.height = Inches(1.25)
效果:
方法说明:
[source]
def add_picture(
self,
image_path_or_stream: str | IO[bytes],
width: int | Length | None = None,
height: int | Length | None = None,
):
run = self.add_paragraph().add_run()
return run.add_picture(image_path_or_stream, width, height)
'''
第一个参数 image_path_or_stream :必填,图片路径或stream bytes
第二个参数 width,可选
第三个参数 height,可选
'''
注意:
可以在 document中插入图片,也可以在 paragraph中插入图片,也可以在 run中插入图片。
3.6、插入表格
示例:创建一个四行三列的表格,没有样式(边框、对齐等)
records = (
(3, '101', 'Spam'),
(7, '422', 'Eggs'),
(4, '631', 'Spam, spam, eggs, and spam')
)
table = document.add_table(rows=1, cols=3)
hdr_cells = table.rows[0].cells
hdr_cells[0].text = 'Qty'
hdr_cells[1].text = 'Id'
hdr_cells[2].text = 'Desc'
for qty, id, desc in records:
row_cells = table.add_row().cells
row_cells[0].text = str(qty)
row_cells[1].text = id
row_cells[2].text = desc
效果:
方法说明:
[source]
def add_table(self, rows: int, cols: int, style: str | _TableStyle | None = None):
table = self._body.add_table(rows, cols, self._block_width)
table.style = style
return table
"""
第一个参数 rows:必填,创建的表格的行数
第二个参数 cols:必填,创建的表格的列数
第三个参数 style:选填
"""
注意:
rows 和 cols 是必填项,可以设置为0,即创建一个空的表格。之后再对返回的table对象进行设置
table = document.add_table(rows=0, cols=0)
3.7、换页
'''
第一个段落输出结束后
在段落后面产生一个新页面
'这是第二个段落' 即输出在新页面上
'''
document.add_paragraph('这是第一个段落')
document.add_page_break()
document.add_paragraph('这是第二个段落')
'''
指定位置分页
'''
from docx.enum.text import WD_BREAK
paragraph1 = document.add_paragraph("这是一个段落,这是其中一节") # 添加一个段落
paragraph1.runs[-1].add_break(WD_BREAK.PAGE) # 在段落的最后一节后面添加分页
常用的python-docx对象就是以上几个,上面对python-docx做了简单介绍,让大家了解python-docx可以做什么,有哪些主要对象和组成部分,对python-docx有了一个初步的认识和基本的概念。
实际使用中,往往不像demo这么简单,比如样式,字体大小,颜色等等都有要求,这就需要对细节做详细的介绍。
下一节对Paragraph对象做详细介绍。