Python win32com - كلمة أتمتة - كيفية استبدال النص في مربع نص؟
سؤال
أحاول أتمتة Word لاستبدال النص في مستند Word باستخدام Python. (أنا على Word 2003 إذا كان هذا مهمًا و Python 2.4)
يعمل الجزء الأول من طريقة الاستبدال أدناه على كل شيء باستثناء النص في مربعات النص. النص فقط لا يتم تحديده. لاحظت عندما أذهب إلى Word يدويًا وأضغط على Ctrl-A يتم تحديد كل النص باستثناء مربع النص.
هذا هو الكود الخاص بي حتى الآن:
class Word:
def __init__(self,visible=0,screenupdating=0):
pythoncom.CoInitialize()
self.app=gencache.EnsureDispatch(WORD)
self.app.Visible = visible
self.app.DisplayAlerts = 0
self.app.ScreenUpdating = screenupdating
print 'Starting word'
def open(self,doc):
self.opendoc=os.path.basename(doc)
self.app.Documents.Open(FileName=doc)
def replace(self,source,target):
if target=='':target=' '
alltext=self.app.Documents(self.opendoc).Range(Start=0,End=self.app.Documents(self.opendoc).Characters.Count) #select all
alltext.Find.Text = source
alltext.Find.Replacement.Text = target
alltext.Find.Execute(Replace=1,Forward=True)
#Special handling to do replace in text boxes
#http://word.tips.net/Pages/T003879_Updating_a_Field_in_a_Text_Box.html
for shp in self.app.Documents(self.opendoc).Shapes:
if shp.TextFrame.HasText:
shp.TextFrame.TextRange.Find.Text = source
shp.TextFrame.TextRange.Find.Replacement.Text = target
shp.TextFrame.TextRange.Find.Execute(Replace=1,Forward=True)
#My Usage
word=Word(visible=1,screenupdating=1)
word.open(r'C:\Invoice Automation\testTB.doc')
word.replace('[PGN]','1')
لـ shp in self.app .. القسم هو محاولتي لضرب مربعات النص. يبدو أنه يجد مربع النص ، لكنه لا يحل محل أي شيء.
المحلول
عندما أضيف مربعات نصية إلى مستند Word ، تتم إضافتها داخل قماش الرسم. لذلك فإن الشكل العلوي هو القماش ، ويتم احتواء مربعات النص داخل القماش. يجب عليك استخدام CanvasItems
طريقة للوصول إلى الكائنات في القماش ، أي مربعات النص
المثال التالي يعمل بالنسبة لي. لقد قمت بإنشاء مستند Word مع مربع نص واحد.
import win32com.client
word = win32com.client.Dispatch("Word.Application")
canvas = word.ActiveDocument.Shapes[0]
for item in canvas.CanvasItems:
print item.TextFrame.TextRange.Text
تحديث: الرد على تعليق OP.
أعتقد أن المشكلة في الكود الخاص بك هي أن كل سطر من الكود مع Find
يخلق جديدًا Find
هدف. عليك إنشاء وربط أ Find
اعترض على اسم ، ثم قم بتعديل سماته وتنفيذها. لذلك في الكود الخاص بك يجب أن يكون لديك:
find = shp.TextFrame.TextRange.Find
find.Text = source
find.Replacement.Text = target
find.Execute(Replace=1, Forward=True)
أو سطر واحد:
shp.TextFrame.TextRange.Find.Execute(FindText=source, ReplaceWith=target, Replace=1, Forward=True)
كل من هذه الطرق تعمل في رمز الاختبار الخاص بي.