Ms word 使用open xml添加文本后删除内容控件

Ms word 使用open xml添加文本后删除内容控件,ms-word,ms-office,openxml,docx,openxml-sdk,Ms Word,Ms Office,Openxml,Docx,Openxml Sdk,在这里一些非常友好的社区成员的帮助下,我设法通过编程创建了一个函数,用开放式xml替换Word文档中内容控件内的文本。生成文档后,它会在替换文本后删除文本的格式 关于如何在word中保留格式并删除内容控制标记,有什么想法吗 这是我的代码: using (var wordDoc = WordprocessingDocument.Open(mem, true)) { var mainPart = wordDoc.MainDocumentPart; ReplaceTags(main

在这里一些非常友好的社区成员的帮助下,我设法通过编程创建了一个函数,用开放式xml替换Word文档中内容控件内的文本。生成文档后,它会在替换文本后删除文本的格式

关于如何在word中保留格式并删除内容控制标记,有什么想法吗

这是我的代码:

using (var wordDoc = WordprocessingDocument.Open(mem, true))
{

    var mainPart = wordDoc.MainDocumentPart;

    ReplaceTags(mainPart, "FirstName", _firstName);
    ReplaceTags(mainPart, "LastName", _lastName);
    ReplaceTags(mainPart, "WorkPhoe", _workPhone);
    ReplaceTags(mainPart, "JobTitle", _jobTitle);

    mainPart.Document.Save();
    SaveFile(mem);
}

private static void ReplaceTags(MainDocumentPart mainPart, string tagName,    string tagValue)
{
    //grab all the tag fields
    IEnumerable<SdtBlock> tagFields = mainPart.Document.Body.Descendants<SdtBlock>().Where
        (r => r.SdtProperties.GetFirstChild<Tag>().Val == tagName);

    foreach (var field in tagFields)
    {
        //remove all paragraphs from the content block
        field.SdtContentBlock.RemoveAllChildren<Paragraph>();
        //create a new paragraph containing a run and a text element
        Paragraph newParagraph = new Paragraph();
        Run newRun = new Run();
        Text newText = new Text(tagValue);
        newRun.Append(newText);
        newParagraph.Append(newRun);
        //add the new paragraph to the content block
        field.SdtContentBlock.Append(newParagraph);
    }
}
使用(var-wordDoc=WordprocessingDocument.Open(mem,true))
{
var mainPart=wordDoc.MainDocumentPart;
替换标签(主要部件,“名字”和“名字”);
替换标签(主要部件,“姓氏”,“姓氏”);
替换标签(主要部件,“工作电话”和“工作电话”);
替换标签(主要部件,“工作标题”和“工作标题”);
mainPart.Document.Save();
保存文件(mem);
}
私有静态void ReplaceTags(MainDocumentPart mainPart、字符串标记名、字符串标记值)
{
//抓取所有标记字段
IEnumerable标记字段=mainPart.Document.Body.subjects()。其中
(r=>r.SdtProperties.GetFirstChild().Val==标记名);
foreach(标记字段中的变量字段)
{
//从内容块中删除所有段落
field.SdtContentBlock.RemoveAllChildren();
//创建一个包含run和text元素的新段落
段落新段落=新段落();
运行newRun=新运行();
Text newText=新文本(tagValue);
追加(newText);
newparagration.Append(newRun);
//将新段落添加到内容块
field.SdtContentBlock.Append(新段落);
}
}

保留样式是一个棘手的问题,因为要替换的文本可能会应用多个样式。在这种情况下你应该怎么做

假设一种样式的简单情况(但可能超过多个
段落
运行
文本
)您可以保留每个
SdtBlock
遇到的第一个
Text
元素,并在该元素中放置所需的值,然后从
SdtBlock
中删除任何进一步的
Text
元素。然后将保留第一个
文本
元素的格式。显然,您可以将此理论应用于任何
文本
块;你不必使用第一个。下面的代码应该说明我的意思:

private static void ReplaceTags(MainDocumentPart mainPart, string tagName, string tagValue)
{
    IEnumerable<SdtBlock> tagFields = mainPart.Document.Body.Descendants<SdtBlock>().Where
        (r => r.SdtProperties.GetFirstChild<Tag>().Val == tagName);

    foreach (var field in tagFields)
    {
        IEnumerable<Text> texts = field.SdtContentBlock.Descendants<Text>();

        for (int i = 0; i < texts.Count(); i++)
        {
            Text text = texts.ElementAt(i);

            if (i == 0)
            {
                text.Text = tagValue;
            }
            else
            {
                text.Remove();
            }
        }
    }
}
private static void ReplaceTags(MainDocumentPart mainPart、字符串标记名、字符串标记值)
{
IEnumerable标记字段=mainPart.Document.Body.subjects()。其中
(r=>r.SdtProperties.GetFirstChild().Val==标记名);
foreach(标记字段中的变量字段)
{
IEnumerable text=field.SdtContentBlock.subjects();
对于(int i=0;i
感谢您的输入。我将对此进行测试。当文本包含段落时,text

,文本不会添加到文档文件中,但会添加单值文本,并保持它们获得的样式。你知道我如何保持多文本值文本的样式不变吗?你说的“文本”是指被替换的文本还是被替换的文本?我已经测试了这两种情况,我不能让上述任何一种都失败。对不起,错误的解释。文本被添加/替换到内容控件中,但使用html编码,如下图所示。我试图删除html编码,但是当然,如果没有段落的话,所有内容都会排在同一行,因此,我试图找出如何在不显示html-tags的情况下使用html编码的文本。我想您可以使用类似的东西来解析HTML(我会避免使用正则表达式)。或者,您可以查看一个转换器,例如。我从来没有试过,所以我不知道用它是什么感觉。