c# - 使用 openxml SDK 从 Word 文档中提取字段值

标签 c# ms-word openxml-sdk

我正在尝试从 word 文档中提取表单域。 Word 文档使用一些文本框和复选框来创建一种表单。我想以编程方式能够使用 C# 提取控件中的值。我认为 OpenXML 可能会允许这样做,但我一直没弄明白。

这是 MS Word 文档中示例表单的屏幕截图:

enter image description here

最佳答案

使用DocumentFormat.OpenXml Nuget包;

示例代码:

using (var doc = WordprocessingDocument.Open("OpenXMLTest.docx", false))
{
    Console.WriteLine("Title = " + doc.ExtendedFilePropertiesPart.Properties.TitlesOfParts.InnerText);
    Console.WriteLine("Subject = " + doc.PackageProperties.Subject);
    {
        foreach (var control in doc.ContentControls())
        {
            Console.WriteLine( control.Title + "==>" + control.Value);
        }
    }
}

和包含的扩展:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using DocumentFormat.OpenXml;
using DocumentFormat.OpenXml.Packaging;
using DocumentFormat.OpenXml.Wordprocessing;

public static class ContentControlExtensions
{

    public static IEnumerable<ContentControl> ContentControls(this OpenXmlPart part)
    {
        var results = new List<ContentControl>();

        IEnumerable<OpenXmlElement> parents = part.RootElement
            .Descendants()
             .Where(e => e is SdtProperties)
             .Select(p => p.Parent);

        foreach(var parent in parents)
        {
            ParseContentControl(results, parent);

        }

        return results;
    }

    private static void ParseContentControl(List<ContentControl> results, OpenXmlElement parent)
    {
        var sdtAlias = parent.ChildElements.Where(p => p is SdtProperties).FirstOrDefault()
                .ChildElements.Where(c => c is SdtAlias).FirstOrDefault();

        if (sdtAlias != null)
        {
            string value = string.Empty;
            var name = ((SdtAlias)sdtAlias).Val;

            var sdtContentCell = parent.ChildElements.Where(p => p is SdtContentCell).FirstOrDefault();

            if (sdtContentCell != null)
            {
                value = sdtContentCell.InnerText;
                if (value == "Click or tap here to enter text.")
                {
                    value = null;
                }
            }

            var sdtid = parent.ChildElements.Where(p => p is SdtProperties).FirstOrDefault()
                .ChildElements.Where(c => c is SdtId).FirstOrDefault();
            var id = ((SdtId)sdtid).Val;


            var sdtTag = parent.ChildElements.Where(p => p is SdtProperties).FirstOrDefault()
                    .ChildElements.Where(c => c is Tag).FirstOrDefault();
            var tag = ((Tag)sdtTag).Val;

            results.Add(new ContentControl() { Title = name, Value = value, id = id, Tag = tag });
        }
    }

    public static IEnumerable<ContentControl> ContentControls(
    this WordprocessingDocument doc)
    {
        foreach (var cc in doc.MainDocumentPart.ContentControls())
            yield return cc;
        foreach (var header in doc.MainDocumentPart.HeaderParts)
            foreach (var cc in header.ContentControls())
                yield return cc;
        foreach (var footer in doc.MainDocumentPart.FooterParts)
            foreach (var cc in footer.ContentControls())
                yield return cc;
        if (doc.MainDocumentPart.FootnotesPart != null)
            foreach (var cc in doc.MainDocumentPart.FootnotesPart.ContentControls())
                yield return cc;
        if (doc.MainDocumentPart.EndnotesPart != null)
            foreach (var cc in doc.MainDocumentPart.EndnotesPart.ContentControls())
                yield return cc;
    }

    public class ContentControl
    {
        public string Title {get; set; }
        public string Value { get; set; }
        public string Tag { get; set; }
        public string id { get; set; }

    }
}

关于c# - 使用 openxml SDK 从 Word 文档中提取字段值,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29808744/

相关文章:

c# - 在 C# 的 OpenXml SDK 中使用 MergeField FieldCodes 时,为什么字段代码会消失或碎片化?

c# - 无法设置 session 变量

c# - ASP.NET : Error - Server Error in '/' Application

c# - MS Word 2010 (VSTO) 以编程方式更改页面颜色

sql - 如何通过sql向access数据库插入超链接?

windows - Microsoft Word 命令行实用程序

c# - OpenXML - 获取图像替代文本标题

c# - 如何将桌面图标设置为 C# Windows 窗体

c# - 具有动态可编辑列的 DataGrid

c# - 使用 OpenXml 创建分页符