2

我正在尝试在 Word 文档中查找所有 SdtElement。我使用了以下代码:

using (var wordDoc = WordprocessingDocument.Open(FilePath, true))
{
    var docSdts = wordDoc.MainDocumentPart.Document.Descendants<SdtElement>();
    // MainDocumentPart.Document.Body.Descendants<SdtElement>(); also used but same result

    MainDocumentPart mainPart = wordDoc.MainDocumentPart;
    List<SdtBlock> sdtList = mainPart.Document.Body.Descendants<SdtBlock>().ToList();

    // process all sdt
}

问题是上面的代码没有从文件中返回所有的 SdtElements。在一个文档中有 19 个 SdtElement,但它只返回 7 个。

根据文档, Descendants 方法应返回所有级别的元素:

Elements仅查找那些是直接后代的元素,即直接子元素。vs Descendants查找任何级别的孩子,即孩子、孙子等...

观察到的一件事是仅返回bodyparatable 单元格下的sdt,但是当sdt在table 单元格内的para下时,它不会返回。

我尝试了来自http://www.ericwhite.com/blog/iterating-through-all-content-controls-in-an-open-xml-wordprocessingml-document/和其他类似文章的代码。

无论嵌套级别如何,如何从整个文档中获取所有 sdt 元素?

4

1 回答 1

3

SdtElement是其他 sdt 元素的基类:

  • 存储块
  • 单细胞
  • SdtRow
  • 运行
  • SdtRunRuby

(来源:https ://docs.microsoft.com/en-us/dotnet/api/documentformat.openxml.wordprocessing.sdtelement?view=openxml-2.8.1 )

您正在尝试仅获取SdtBlock元素:

List<SdtBlock> sdtList = mainPart.Document.Body.Descendants<SdtBlock>().ToList();

如果您想获得所有SdtElements内容,则应将其更改为:

List<SdtElement> sdtList = mainPart.Document.Body.Descendants<SdtElement>().ToList();

请注意,SdtElements也可能在其他部分中WordprocessingDocument

在这种情况下,您应该遍历所有这些部分,例如:

List<SdtElement> sdtList = mainPart.Document.Body.Descendants<SdtElement>().ToList();
foreach(var part in mainPart.Document.HeaderParts)
{
   sdtList.AddRange(part.Header.Descedants<SdtElement>());
}
foreach(var part in mainPart.Document.FooterParts)
{
   sdtList.AddRange(part.Footer.Descedants<SdtElement>());
}
于 2020-01-24T12:53:03.573 回答