- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我想使用正则表达式 (java RegEx) 在 MS Word (.docx) 文档中进行替换:
Example:
…, с одной стороны, и %SOME_TEXT% именуемое в дальнейшем «Заказчик», в
лице %SOME_TEXT% действующего на основании %SOME_TEXT% с другой стороны,
заключили настоящий Договор о нижеследующем: …
我尝试使用 Apache POI - XWPF 获取文本模板(如 %SOME_TEXT%)并替换文本,但不能保证替换,因为 POI 分隔 运行 => 我得到这样的东西(System.out.println(run.getText(0))
):
…
, с одной стороны, и
%
SOME_TEXT
%
именуемое
в дальнейшем «Заказчик», в лице
%
SOME
_
TEXT
%
代码示例:
FileInputStream fis = new FileInputStream(new File("document.docx"));
XWPFDocument document = new XWPFDocument(fis);
List<XWPFParagraph> paragraphs = document.getParagraphs();
paragraphs.forEach(para -> {
para.getRuns().forEach(run -> {
String text = run.getText(0);
if (text != null) {
System.out.println(text);
// text replacement process
// run.setText(newText,0);
}
});
});
我发现了很多类似的问题(例如“ Replacing a text in Apache POI XWPF ”),但没有找到我的问题的答案(在这里回答“ Seperated text line in Apache POI XWPFRun object ”提供了不方便的解决方案)。
我尝试使用docx4j,此示例=>“docx4j find and replace”,但docx4j的工作原理类似。
For docx4j, see stackoverflow.com/questions/17093781/… – JasonPlutext
我尝试使用 docx4j => documentPart.variableReplace(mappings);
,但不能保证替换( plutext/docx4j )。
Did you use VariablePrepare? stackoverflow.com/a/17143488/1031689 – JasonPlutext
是的,没有结果:
WordprocessingMLPackage wordMLPackage = WordprocessingMLPackage.load(new File("test.docx"));
HashMap<String, String> mappings = new HashMap<>();
VariablePrepare.prepare(wordMLPackage);//see notes
mappings.put("SOME_TEXT", "XXXX");
wordMLPackage.getMainDocumentPart().variableReplace(mappings);
wordMLPackage.save(new File("out.docx"));
输入\输出文本:
Input:
…, с одной стороны, и ${SOME_TEXT} именуемое в дальнейшем «Заказчик» ...
Output:
…, с одной стороны, и SOME_TEXT именуемое в дальнейшем «Заказчик» ...
To see your runs after VariablePrepare, turn on INFO level logging for VariablePrepare, or just
System.out.println(wordMLPackage.getMainDocumentPart().getXML())
我知道模板被分离到不同的运行,但主题的主要问题是如何不将模板分离到不同的运行。我使用 System.out.println(wordMLPackage.getMainDocumentPart().getXML()) 并看到:
<w:r>
<w:t xml:space="preserve">, с одной стороны, и </w:t>
</w:r>
<w:r><w:t>$</w:t></w:r>
<w:r><w:t>{</w:t></w:r>
<w:r>
<w:rPr>
<w:rFonts w:eastAsia="Times-Roman"/>
<w:color w:val="000000" w:themeColor="text1"/>
<w:lang w:val="en-US"/>
</w:rPr>
<w:t>SOME</w:t> <!-- First part of template: "SOME" -->
</w:r>
<w:r>
<w:rPr>
<w:rFonts w:eastAsia="Times-Roman"/>
<w:color w:val="000000" w:themeColor="text1"/>
</w:rPr>
<w:t>_</w:t> <!-- Second part of template: "_" -->
</w:r>
<w:r>
<w:rPr>
<w:rFonts w:eastAsia="Times-Roman"/>
<w:color w:val="000000" w:themeColor="text1"/>
<w:lang w:val="en-US"/>
</w:rPr>
<w:t>TEXT</w:t> <!-- Third part of template: "TEXT" -->
</w:r>
<w:r>
<w:rPr>
<w:rFonts w:eastAsia="Times-Roman"/>
<w:color w:val="000000" w:themeColor="text1"/>
</w:rPr>
<w:t>}</w:t>
</w:r>
,该模板位于不同的 xml 标记中,我不明白为什么......
请帮助我找到替换文本的便捷方法......
最佳答案
如您所见,“使用正则表达式 (java RegEx) 在 MS Word (.docx) 文档中进行替换”的方法并不是很好,因为您永远无法确定要替换的文本是否会一起出现在一个文本中-运行。更好的方法是在 Word 中使用字段(合并字段或表单字段)或内容控件。
对于此类要求,我最喜欢的仍然是 Word
中良好的旧表单字段。
第一个优点是,即使没有文档保护,也无法将表单字段内容的部分格式设置为不同的格式,从而将表单字段内容拆分为不同的运行(但请参阅注释 1)。第二个优点是,由于灰色背景,表单字段在文档内容中清晰可见。另一个优点是可以应用文档保护,以便仅填写表单字段,即使在 Word 的 GUI 中也是如此。这对于保护此类契约(Contract)文档免遭不必要的更改非常有用。
(注释 1):至少 Word
可以防止表单字段内容的部分格式不同,从而将表单字段内容分成不同的部分。但其他文字处理软件(例如 Writer
)可能不遵守此限制。
所以我会有像这样的Word模板:
灰色字段是 Word
中良好的旧格式 Textfields,名为 Text1
、Text2
和 文本3
。 文本字段 block 看起来像:
<xml-fragment w:rsidR="00833656"
...
xmlns:w="http://schemas.openxmlformats.org/wordprocessingml/2006/main"
... >
<w:rPr>
<w:rFonts w:eastAsia="Times-Roman"/>
<w:color w:themeColor="text1" w:val="000000"/>
<w:lang w:val="en-US"/>
</w:rPr>
<w:fldChar w:fldCharType="begin">
<w:ffData>
<w:name w:val="Text1"/>
<w:enabled w:val="0"/>
<w:calcOnExit w:val="0"/>
<w:textInput>
<w:default w:val="<введите заказчика>"/>
</w:textInput>
</w:ffData>
</w:fldChar>
</xml-fragment>
</xml-fragment>
然后是以下代码:
import java.io.FileOutputStream;
import java.io.FileInputStream;
import org.apache.poi.xwpf.usermodel.*;
import org.apache.xmlbeans.XmlObject;
import org.apache.xmlbeans.XmlCursor;
import org.apache.xmlbeans.SimpleValue;
import javax.xml.namespace.QName;
public class WordReplaceTextInFormFields {
private static void replaceFormFieldText(XWPFDocument document, String ffname, String text) {
boolean foundformfield = false;
for (XWPFParagraph paragraph : document.getParagraphs()) {
for (XWPFRun run : paragraph.getRuns()) {
XmlCursor cursor = run.getCTR().newCursor();
cursor.selectPath("declare namespace w='http://schemas.openxmlformats.org/wordprocessingml/2006/main' .//w:fldChar/@w:fldCharType");
while(cursor.hasNextSelection()) {
cursor.toNextSelection();
XmlObject obj = cursor.getObject();
if ("begin".equals(((SimpleValue)obj).getStringValue())) {
cursor.toParent();
obj = cursor.getObject();
obj = obj.selectPath("declare namespace w='http://schemas.openxmlformats.org/wordprocessingml/2006/main' .//w:ffData/w:name/@w:val")[0];
if (ffname.equals(((SimpleValue)obj).getStringValue())) {
foundformfield = true;
} else {
foundformfield = false;
}
} else if ("end".equals(((SimpleValue)obj).getStringValue())) {
if (foundformfield) return;
foundformfield = false;
}
}
if (foundformfield && run.getCTR().getTList().size() > 0) {
run.getCTR().getTList().get(0).setStringValue(text);
foundformfield = false;
//System.out.println(run.getCTR());
}
}
}
}
public static void main(String[] args) throws Exception {
XWPFDocument document = new XWPFDocument(new FileInputStream("WordTemplate.docx"));
replaceFormFieldText(document, "Text1", "Моя Компания");
replaceFormFieldText(document, "Text2", "Аксель Джоачимович Рихтер");
replaceFormFieldText(document, "Text3", "Доверенность");
FileOutputStream out = new FileOutputStream("WordReplaceTextInFormFields.docx");
document.write(out);
out.close();
document.close();
}
}
此代码需要所有架构 ooxml-schemas-1.3.jar
的完整 jar,如 FAQ-N10025 中所述。 .
产品:
关于java - 替换 .docx 中的文本模板(Apache POI、Docx4j 或其他),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49678959/
我有一个来自 C# 库的 Paragraph 对象 DocX并尝试设置 LineSpacing 属性但没有任何效果? internal static Paragraph StandardFormat(
我正在寻找一种方法来提取文档中每个单词的位置 (x, y) 和属性(字体/大小)。 从 python-docx 文档中,我知道: Conceptually, Word documents have t
我有一个带有空表的 .docx 模板,我要在其中添加值: def manipulate_table(): table = doc.tables[0] table.cell(0, 0).text = '
我目前正在开发一个将 docx 文件作为输入并使用它来构建 html 页面的库,由于 docx 的模糊和缺乏文档,我不得不严重依赖示例输出来决定如何处理某些事情。其中之一是超链接。 就我目前所见,do
使用以下代码,我尝试创建一个文档,其中第 2 页和第 3 页为横向,而其他页为纵向。所有尺寸都应为 8.5"x 11"。 using (System.IO.MemoryStream ms = new
我使用了 python-docx 中的示例,在运行代码后,我找不到 docx 文件在哪里,我可以指出要添加的特定路径吗? from docx import Document from docx.sha
我对 python-docx 中“运行级别内容”的概念有些困惑。我明白,如果我想检查一个段落是否以粗体显示,我需要检查 run.bold,但究竟是什么它? 官方定义是:运行是与内联内容最密切相关的对象
我了解到 .docx 文件基本上是二进制文件。但我不知道下面的结构。 .docx 文件的基本结构是什么?比如,标题有多长?实际的文档内容从什么时候开始?最后有签名吗? 基本上,.docx 文件的结构是
我正在尝试将 .adoc 文件转换为 .docx 实际上我正在使用: asciidoctor file.adoc -o file.html pandoc -s -S file.html -o outp
我可能错过了一些东西或犯了一个错误,无论如何,我似乎无法访问 .docx 模板中字典中的数据。文档说它的工作方式类似于 jinja2,但使用 {{ dict['dict_key'] }} 即使在 if
我遇到了有关如何使用 C# 合并 docx 文件的解决方案: Append multiple DOCX files together 在此解决方案中,他遍历文件并将正文“outerxml”复制到新文档
我正在使用 Docx dll 获取段落信息但无法获取段落格式(字体大小-字体名称-字体颜色) 这是我的代码: using (DocX document = DocX.Load("Tes
使用 Markdown 代码块时,DOCX 文档中生成的等宽字体大小太大。 我可以通过指定自定义 template.docx 文件来调整段落的字体大小,但由于某种原因,生成的代码块不使用段落样式,这与
doc=Document() table = doc.add_table(rows = 13, cols = 5) table.style = 'Table Grid' row = table.row
我想打开一个现有的 Word 文档,我已经在其中添加了页码,然后向其中添加了一些文本和标题。 这是我如何尝试实现目标的基本示例 #!/usr/bin/env python from docx impo
我想使用 DocX Library 将图像添加到 C# 中的 Word 文件中.问题是我在网上找不到任何东西。 情况 我知道如何创建文件,我知道如何在文件中写入文本。遗憾的是,图书馆的文档非常小。希望
我已经下载并开始使用 DocX library .我有一个名为 template.docx 的文档正在加载到内存中。我在该文档中有一个表,其中包含 id = 241。我想通过它的 id 获取该表并向其
是否可以使用应用了样式的 python-docx 将 HTML 插入到文档中?我唯一需要做的就是斜体。 例如如何插入"Today is Saturday."星期六实际上是用斜体插入的吗? 谢谢! 最佳
我想在命令行 (Linux) 中执行此操作,这样我就可以自动执行它,而无需在中间设置用户界面。 最佳答案 WordprocessingML 中没有明确的页面布局模型。 但是,如果文件最后是由 Word
我必须以 docx 格式存储一些文档,但无法忍受使用 msword:我想编辑某种纯文本标记,除了基于 XML 的东西(我也不喜欢那样)和从/到那个到/从 docx 转换。 有什么选择吗? 编辑:由于人
我是一名优秀的程序员,十分优秀!