Python中使用pywin32com操作PPT幻灯片图形复制或删除的问题请教

小弟使用的是 python3.7 里面的 win32com,想用 python 将 ppt 里的一页幻灯片( slides )中一个图形( shapes )复制到另一页幻灯片中。

通过查找网上的一些资料,可以实现将 ppt 里面的 shapes 属性赋值,但没有办法删除或者复制。查看了一下 msdn 发现 vb 实现如下,https://docs.microsoft.com/zh-cn/office/vba/api/powerpoint.shape.copy 但是在 python 中不知道如何调用 ActivePresentation,求各位大哥帮忙看看,究竟如何实现复制或者删除。

import win32com
from win32com.client import Dispatch, constants

ppt = win32com.client.Dispatch(‘PowerPoint.Application’) ppt.Visible = 1 pptSel = ppt.Presentations.Open(“c:\code\pptx\test.pptx”)

下面两行可以实现

print(pptSel.Slides(1).Shapes.Count) pptSel.Slides(1).Shapes(4).TextFrame.TextRange.Text=“1”

脑洞的写下如此代码,想实现第一张幻灯片图片复制到第 2 个幻灯片中,但系统不会报错,也不运行。

pptSel.Slides(1).Shapes(1).Copy pptSel.Slides(2).Shapes.Paste

删除也不运行

pptSel.Slides(1).Shapes(2).Delete


Python中使用pywin32com操作PPT幻灯片图形复制或删除的问题请教

12 回复

还不如直接用微软系的语言写, 用 python 就没意思了


我最近也在用pywin32com操作PPT,处理图形复制和删除确实有几个坑。

复制图形的关键是要获取正确的形状对象,然后使用Duplicate()方法:

import win32com.client

ppt = win32com.client.Dispatch("PowerPoint.Application")
presentation = ppt.Presentations.Open(r"C:\path\to\your.pptx")
slide = presentation.Slides(1)  # 第一页

# 假设要复制第一个形状
shape_to_copy = slide.Shapes(1)
copied_shape = shape_to_copy.Duplicate()

# 调整新图形位置
copied_shape.Left = copied_shape.Left + 50
copied_shape.Top = copied_shape.Top + 50

presentation.Save()
presentation.Close()
ppt.Quit()

删除图形更简单,直接调用Delete()就行:

# 删除第二个形状
slide.Shapes(2).Delete()

注意点:

  1. 图形索引从1开始,遍历时建议用for i in range(1, slide.Shapes.Count + 1)
  2. 操作前最好先判断形状类型,避免误删文本框等元素
  3. 批量删除时建议从后往前删,因为删除后索引会变

总结:复制用Duplicate(),删除用Delete(),注意索引变化。

同意!另外多去学习一下 com 组件,你会发现一个新世界。

据说 PowerShell 比较适合这么干?

微软系的语言不懂啊,凭兴趣了解了一点 python,其它的语言都没玩过。

学习语言的时间比较长,我也仅仅遇到点 ppt 批量导入几十页数据,成本上不是太划算。各位大哥有什么简单的方法不?

我觉得原因是你拿到了一个 function 但是你没有 call。

这就类似

def func(): # 你们知道下面应该有缩进的,据说会被吃掉?
print(‘hello, world’)

func

不会发生任何事情一样。

你应该写 pptSel.Slides(1).Shapes(1).Copy() 和 Paste() 和 Delete() 等。我没有尝试过。

#1 #3

COM 是语言和平台无关的。

大哥你是对的。刚才测试了一下正常了。但感觉有点奇怪,如 pptSel.Slides(1).Shapes.Count,TextRange.Text 等等没有()就可以运行,但不明白为什么 Copy Paste 需要()。

谢谢,是这个。刚才 geelaw 已提点我了,已成功解决。

#7 那些是 properties,就像 Python 的 properties 也不需要括号就能访问 getter/setter。

任何正常的语言都会把 COM 绑定到该语言最合适的构造。

VBA 代码不需要括号,是因为 BASIC 里面调用 sub/function 并丢弃返回值(也就是整个语句是一个调用的时候)的语法就是

被调用者的名字 参数 1, 参数 2, …

没有参数就没有列表,所以后面是空的。

懂了,谢谢!

用 vba 直接写吧

回到顶部