我正在尝试使用 openxml SDK 从 Word 和 PowerPoint 文件中删除所有嵌入对象。我是 Open XML 新手,不确定我这样做是否正确。下面是我的代码。我的目的是删除嵌入的任何对象并删除嵌入的图像。执行时这两个代码都会出错。
我尝试删除文档中所有嵌入项目的代码。
using (var wdDoc = WordprocessingDocument.Open(wordFilePath, true))
{
var docPart = wdDoc.MainDocumentPart;
var document = docPart.Document;
var embeddedObjectsCount = docPart.EmbeddedObjectParts.Count();
while (embeddedObjectsCount > 0)
{
docPart.DeletePart(docPart.EmbeddedObjectParts.FirstOrDefault());
embeddedObjectsCount = docPart.EmbeddedObjectParts.Count();
}
}
我尝试删除文档中所有图像的代码。 (如果我没有在文档中嵌入任何对象,这会部分起作用。)
using (var wdDoc = WordprocessingDocument.Open(wordFilePath, true))
{
var docPart = wdDoc.MainDocumentPart;
var document = docPart.Document;
var imageObjectsCount = docPart.ImageParts.Count();
while (imageObjectsCount > 0)
{
docPart.DeletePart(docPart.ImageParts.FirstOrDefault());
imageObjectsCount = docPart.ImageParts.Count();
}
}
当我运行上面的代码时,我使用的文件被损坏。我想知道如何从 Word 中删除所有嵌入对象而不损坏文件。
我还没有在PowerPoint上做过任何事情,但我希望它能类似于Word文档。
我设法找到解决问题的方法。我必须深入研究 Open XML SDK 的概念才能理解这一点。但是,我不太确定这是否是最佳解决方案。
目标
删除 PowerPoint 和 Word 中的所有嵌入对象。
删除 PowerPoint 和 Word 中的所有图像。
对于文字
//using Ovml = DocumentFormat.OpenXml.Vml.Office;
//Determine whether there are any Embedded Objects in the document
using (var wdDoc = WordprocessingDocument.Open(wordFilePath, true))
{
var docPart = wdDoc.MainDocumentPart;
var docHasEmbeddedOleObjects = document.Body.Descendants<Ovml.OleObject>().Any();
if (docHasEmbeddedOleObjects)
{
foreach (var oleObj in document.Body.Descendants<Ovml.OleObject>())
{
oleObj.Remove(); //Remove each ole object in the document. This will remove the object from view in word.
}
//Delete the embedded objects. This will remove the actual attached files from the document.
docPart.DeleteParts(docPart.EmbeddedObjectParts);
//Delete all picture in the document
docPart.DeleteParts(docPart.ImageParts);
}
}
对于PowerPoint
using (var ppt = PresentationDocument.Open(powerPointFilePath, true))
{
foreach (var slide in slides)
{
//Remove Ole Objects
var oleObjectCount = slide.Slide.Descendants<OleObject>().Count();
while (oleObjectCount > 0)
{
var oleObj = slide.Slide.Descendants<OleObject>().FirstOrDefault();
var oleObjGraphicFrame = oleObj?.Ancestors<GraphicFrame>().FirstOrDefault();
if (oleObjGraphicFrame != null)
{
oleObjGraphicFrame.RemoveAllChildren();
oleObjGraphicFrame.Remove();
}
oleObjectCount = slide.Slide.Descendants<OleObject>().Count();
}
//Delete embedded objects
slide.DeleteParts(slide.EmbeddedObjectParts);
//Delete all pictures
slide.DeleteParts(slide.ImageParts);
}
}
根据我的经验,“破坏”OpenXML 文档的最快方法是使用错误的关系指针。处理这些神秘错误消息背后的内容的最快方法是直接访问原始 OpenXML 标记。
了解正在发生的事情:
A.docx
B.docx
A.docx
和 B.docx
重命名为 A.zip
和 B.zip
调查源文件
首先,在
A.zip
内部,打开名为[Content_Types].xml
的文件。记下您要移除的部件。将此文件视为对字处理器的声明,说明它将在子目录中遇到的文件类型。
文档内容(
word/document.xml
)或脚注部分(word/footnotes.xml
)等部分都有自己的关系部分,名为[part path here].rels
。
例如,
document.xml.rels
将保存document.xml
中的图表、超链接和图像等关系信息;同样,footnotes.xml.rels
保存有关 footnotes.xml
中的超链接等信息。
调查结果文件
现在打开
B.zip
并比较 [Content_Types].xml
文件。您看到那里有您想要删除的部分吗?是否有遗漏的部分是您不打算删除的?
在
word
的 B.zip
子目录中,您是否看到 [Content_Types].xml
文件中未列出的任何嵌入文件?如果您查看原始标记,并且没有发现错误,请随时评论有关您的文件结构的更多详细信息,我们可以从那里进行故障排除。