gpt4 book ai didi

java - 如何在 Apache POI Word 中添加图片交叉引用?

转载 作者:行者123 更新时间:2023-12-02 09:54:01 25 4
gpt4 key购买 nike

我想使用 Apache POI 创建一个包含文本和图片的文档。文本的某些部分必须与图片交叉引用。我尝试按照这个问题的答案更改 addExternalRelationship方法addRelationship没有成功:

How to create hyperlinks in Apache POI Word?

编辑:以下是我在研究代码后的尝试:

Generate Inter-Document Hyperlink with Apache POI in Java

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.math.BigInteger;

import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
import org.apache.poi.util.Units;
import org.apache.poi.xwpf.usermodel.BreakType;
import org.apache.poi.xwpf.usermodel.UnderlinePatterns;
import org.apache.poi.xwpf.usermodel.XWPFDocument;
import org.apache.poi.xwpf.usermodel.XWPFHyperlinkRun;
import org.apache.poi.xwpf.usermodel.XWPFParagraph;
import org.apache.poi.xwpf.usermodel.XWPFRun;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTBookmark;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTHyperlink;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.STFldCharType;

public class CrossReference {
public static void main(String[] args) throws InvalidFormatException, FileNotFoundException, IOException {
XWPFDocument document = new XWPFDocument();
XWPFParagraph paragraph = document.createParagraph();
document.createParagraph();

document.createParagraph().createRun().addBreak(BreakType.PAGE);

XWPFParagraph pictureParagraph = document.createParagraph();
pictureParagraph.setSpacingAfter(0);

XWPFRun pictureRun = pictureParagraph.createRun();
String imgPath = "img.png";
pictureRun.addPicture(new FileInputStream(imgPath),
XWPFDocument.PICTURE_TYPE_PNG,
imgPath,
Units.toEMU(288),
Units.toEMU(288));

String anchor = "anchor";

XWPFParagraph captionParagraph = document.createParagraph();
XWPFRun captionRun = captionParagraph.createRun();
captionRun.setText("Figure ");
CTBookmark bookmark = captionParagraph.getCTP().addNewBookmarkStart();
bookmark.setName(anchor);
bookmark.setId(BigInteger.valueOf(0));
captionParagraph.createRun().getCTR().addNewFldChar().setFldCharType(STFldCharType.BEGIN);
captionParagraph.getCTP().addNewFldSimple().setInstr("SEQ Figure \\* ARABIC");
captionParagraph.createRun().getCTR().addNewFldChar().setFldCharType(STFldCharType.END);
captionParagraph.getCTP().addNewBookmarkEnd().setId(BigInteger.valueOf(0));

CTHyperlink ctHyperlink = paragraph.getCTP().addNewHyperlink();
ctHyperlink.setAnchor(anchor);
XWPFHyperlinkRun hyperlinkRun = new XWPFHyperlinkRun(ctHyperlink,
ctHyperlink.addNewR(), paragraph);
hyperlinkRun.setText("Figure 1");
hyperlinkRun.setUnderline(UnderlinePatterns.SINGLE);

FileOutputStream out = new FileOutputStream(new File("test.docx"));
document.write(out);
out.close();
document.close();
}
}

但是,在docx中的document.xml中,获得的段落是:

  <w:p>
<w:hyperlink w:anchor="anchor">
<w:r>
<w:rPr>
<w:u w:val="single" />
</w:rPr>
<w:t>Figure 1</w:t>
</w:r>
</w:hyperlink>
</w:p>
<w:p />

虽然我期望类似下面所示的 XML(通过使用 LibreOffice Writer 手动添加引用获得)。超链接方法的问题是它的文本是固定的,如果文档被编辑,它不会更新。

  <w:p>
<w:pPr>
<w:pStyle w:val="Normal" />
<w:rPr />
</w:pPr>
<w:r>
<w:rPr />
<w:t xml:space="preserve">Figure </w:t>
</w:r>
<w:r>
<w:rPr />
<w:fldChar w:fldCharType="begin" />
</w:r>
<w:r>
<w:rPr />
<w:instrText>REF Ref_Figure0_number_only \h</w:instrText>
</w:r>
<w:r>
<w:rPr />
<w:fldChar w:fldCharType="separate" />
</w:r>
<w:r>
<w:rPr />
<w:t>1</w:t>
</w:r>
<w:r>
<w:rPr />
<w:fldChar w:fldCharType="end" />
</w:r>
</w:p>

最佳答案

我发现问题的解决方案是通过书签而不是超链接获得的:

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.math.BigInteger;

import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
import org.apache.poi.util.Units;
import org.apache.poi.xwpf.usermodel.BreakType;
import org.apache.poi.xwpf.usermodel.XWPFDocument;
import org.apache.poi.xwpf.usermodel.XWPFParagraph;
import org.apache.poi.xwpf.usermodel.XWPFRun;
import org.apache.xmlbeans.impl.xb.xmlschema.SpaceAttribute.Space;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTBookmark;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTOnOff;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTR;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTSimpleField;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTText;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.STFldCharType;

public class CrossReference {

public static void main(String[] args) throws InvalidFormatException, IOException {
XWPFDocument document = new XWPFDocument();
XWPFParagraph paragraph = document.createParagraph();

document.createParagraph().createRun().addBreak(BreakType.PAGE);

XWPFParagraph pictureParagraph = document.createParagraph();
pictureParagraph.setSpacingAfter(0);

XWPFRun pictureRun = pictureParagraph.createRun();
String imgPath = "img.png";
pictureRun.addPicture(new FileInputStream(imgPath),
XWPFDocument.PICTURE_TYPE_PNG,
imgPath,
Units.toEMU(288),
Units.toEMU(288));

XWPFParagraph captionParagraph = document.createParagraph();
XWPFRun captionRun = captionParagraph.createRun();
CTText ctText = captionRun.getCTR().addNewInstrText();
ctText.setSpace(Space.PRESERVE);
ctText.setStringValue("Figure ");
CTBookmark bookmark = captionParagraph.getCTP().addNewBookmarkStart();
bookmark.setName("Figure-1");
bookmark.setId(BigInteger.valueOf(0));

CTSimpleField ctSimpleField = captionParagraph.getCTP().addNewFldSimple();
ctSimpleField.setInstr("SEQ Figure \\* ARABIC");
CTR ctR = ctSimpleField.addNewR();
ctR.addNewRPr().setNoProof(CTOnOff.Factory.newInstance());
ctR.addNewT().setStringValue(Integer.toString(1));

captionParagraph.getCTP().addNewBookmarkEnd().setId(BigInteger.valueOf(0));
captionParagraph.setSpacingAfter(0);

paragraph.createRun().getCTR().addNewFldChar().setFldCharType(STFldCharType.BEGIN);

ctText = paragraph.createRun().getCTR().addNewInstrText();
ctText.setSpace(Space.PRESERVE);
ctText.setStringValue("REF Figure-1 \\h");

paragraph.createRun().getCTR().addNewFldChar().setFldCharType(STFldCharType.SEPARATE);

ctText = paragraph.createRun().getCTR().addNewT();
ctText.setSpace(Space.PRESERVE);
ctText.setStringValue("Figure ");

ctR = paragraph.createRun().getCTR();
ctR.addNewRPr().setNoProof(CTOnOff.Factory.newInstance());
ctR.addNewT().setStringValue(Integer.toString(1));

paragraph.createRun().getCTR().addNewFldChar().setFldCharType(STFldCharType.END);

FileOutputStream out = new FileOutputStream(new File("test.docx"));
document.write(out);
out.close();
document.close();
}

}

关于java - 如何在 Apache POI Word 中添加图片交叉引用?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56135598/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com