我目前正在尝试用另一个 docx 中的标题图像替换 docx 中的标题,我遵循了 ms 文档中的 example,但它似乎并非旨在将图像从源文档的标题传输到另一个。
这是目标 docx 发生的情况:
我打开目标 docx zip 并与源 docx 进行比较,发现目标 docx 中缺少多个元素,例如 /media 文件夹和图像、header.xml.rels 以及 [Content_types].xml 文件中的一些详细信息。当我手动移动此副本/编辑此文件时,我能够正确看到图像。
所以我的问题是,如何以编程方式传输这些元素?
这是我当前使用的代码:
using DocumentFormat.OpenXml.Packaging;
using DocumentFormat.OpenXml.Wordprocessing;
class Program
{
static void Main(string[] args)
{
string filepathFrom = "path";
string filepathTo = "path";
AddHeaderFromTo(filepathFrom, filepathTo);
}
public static void AddHeaderFromTo(string filepathFrom, string filepathTo)
{
// Replace header in target document with header of source document.
using (WordprocessingDocument
wdDoc = WordprocessingDocument.Open(filepathTo, true))
{
MainDocumentPart mainPart = wdDoc.MainDocumentPart;
// Delete the existing header part.
mainPart.DeleteParts(mainPart.HeaderParts);
// Create a new header part.
HeaderPart headerPart = mainPart.AddNewPart<HeaderPart>();
// Get Id of the headerPart.
string rId = mainPart.GetIdOfPart(headerPart);
// Feed target headerPart with source headerPart.
using (WordprocessingDocument wdDocSource = WordprocessingDocument.Open(filepathFrom, true))
{
HeaderPart firstHeader = wdDocSource.MainDocumentPart.HeaderParts.FirstOrDefault();
wdDocSource.MainDocumentPart.HeaderParts.FirstOrDefault();
if (firstHeader != null)
{
headerPart.FeedData(firstHeader.GetStream());
}
}
// Get SectionProperties and Replace HeaderReference with new Id.
IEnumerable<SectionProperties> sectPrs = mainPart.Document.Body.Elements<SectionProperties>();
foreach (var sectPr in sectPrs)
{
// Delete existing references to headers.
sectPr.RemoveAllChildren<HeaderReference>();
//Adding Title Page property
sectPr.PrependChild(new TitlePage());
// Create the new header reference node.
sectPr.AppendChild(new HeaderReference() { Id = rId, Type = HeaderFooterValues.First });
}
}
}
}
我已经尝试了很多事情,并在标题中的图像上浪费了很多时间,对我来说,处理标题中的图像是从标题中已有图像的模板文档开始,用新的复制该文件命名,然后根据需要进行编辑。
我认为库的一部分 open xml 没有制作,自 2021 年 10 月以来在他们的官方 github 中打开了一个相关的问题 https://github.com/dotnet/Open-XML-SDK/issues/1040
我正在重新审视这个问题,并在这个答案中找到了对我有用的东西:
https://stackoverflow.com/a/38745157/11213291
这个名为 OpenXmlPowerTools 的库有一个函数 (DocumentBuilder),可用于将页眉和页脚从文档 (Source2.docx) 传输到另一个文档 (Source1.docx)。这是代码:
// Copyright (c) Microsoft. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using DocumentFormat.OpenXml.Packaging;
using DocumentFormat.OpenXml.Validation;
using OpenXmlPowerTools;
namespace DocumentBuilderExample
{
class DocumentBuilderExample
{
static void Main(string[] args)
{
var n = DateTime.Now;
var tempDi = new DirectoryInfo(string.Format("ExampleOutput-{0:00}-{1:00}-{2:00}-{3:00}{4:00}{5:00}", n.Year - 2000, n.Month, n.Day, n.Hour, n.Minute, n.Second));
tempDi.Create();
string source1 = "../../Source1.docx";
string source2 = "../../Source2.docx";
List<Source> sources = null;
// Create new document from 10 paragraphs starting at paragraph 5 of Source1.docx
sources = new List<Source>()
{
new Source(new WmlDocument(source1), false),
new Source(new WmlDocument(source2), true),
};
DocumentBuilder.BuildDocument(sources, Path.Combine(tempDi.FullName, "Out1.docx"));
}
}
}
甚至还有一个视频解释了一切:https://www.youtube.com/watch?v=VCShcq8qOg0