apache poi 3.17
XWPFDocument document = new XWPFDocument(new FileInputStream("test.docx"));
Iterator<IBodyElement> iterator = document.getBodyElementsIterator();
while (iterator.hasNext()) {
IBodyElement iBodyElement = iterator.next();
switch (iBodyElement.getElementType()) {
case PARAGRAPH:
XWPFParagraph paragraph = (XWPFParagraph) iBodyElement;
for(XWPFRun run :paragraph.getRuns()){
for(XWPFPicture picture : run.getEmbeddedPictures()){
System.out.println(picture.getPictureData().getFileName());
}
}
break;
}
}
output
image3.png
image4.png
image5.png
image6.png
image7.png
image8.png
image9.png
image10.png
image11.png
image12.png
image13.png
image14.png
enter image description here
image1.emf and image2.emf are gone
document.getAllPictures() can get all the pictures, but it's XWPFPictureData
I want to takepicture.GetCTPicture().getSpPr().getXfrm().getExt().getCx();
document.getAllPictures() can get all the pictures.
I found CTObject and I can get the width and the height.
but how can I know which CTObject correspond XWPFPictureData?
Related
In my project, I'm creating word document (.docx) with apache poi. When the document created, project sending it to approvers via e-mail. I want to add a approver's signature picture to specific place to previously created word document, when the approver is approved the document. But I couldn't figure it out how to do it on previously created word document.
Can I add a picture to previously created word document or do i have to rebuilt it?
UPDATE
I tried this code part
FileInputStream docxFile=new FileInputStream(System.getProperty("jboss.server.data.dir")+"/corrolog/TestWS/"+strSO+" Test Workscope "+revision+".docx");
FileInputStream approverFile=new FileInputStream(approvers);
XWPFDocument doc = new XWPFDocument(docxFile);
List<XWPFParagraph> xwpfParagraphList = doc.getParagraphs();
for (XWPFParagraph xwpfParagraph : xwpfParagraphList) {
for (XWPFRun xwpfRun : xwpfParagraph.getRuns()) {
String text = xwpfRun.getText(0);
System.out.println(text);
if (text == "approved signature" && text.equals("approved signature")) {
text.replace("approved signature", "");
xwpfRun.setText(text);
xwpfRun.addPicture(approverFile, XWPFDocument.PICTURE_TYPE_PNG, "approved", Units.toEMU(130), Units.toEMU(55));
}
}
}
FileOutputStream out = new FileOutputStream(System.getProperty("jboss.server.data.dir")+"/corrolog/TestWS/"+strSO+" Test Workscope "+revision+" Approved.docx");
doc.write(out);
out.close();
But it doesn't add picture to XWPFRun.
SOLUTION
String approvers=v2500Service.getApproverSignatures(approver).get(0).getImagePath();
FileInputStream approverFile=new FileInputStream(approvers);)
XWPFDocument doc = new XWPFDocument(Files.newInputStream(Paths.get(System.getProperty("jboss.server.data.dir")+"/corrolog/TestWS/EV13077-04 Test Workscope Rev0.docx")));
Iterator<IBodyElement> iter = doc.getBodyElementsIterator();
while (iter.hasNext()) {
IBodyElement elem = iter.next();
if (elem instanceof XWPFTable) {
for(XWPFTableRow rows:((XWPFTable) elem).getRows())
{
for(XWPFTableCell cell:rows.getTableCells())
{
text=cell.getText();
System.out.println(text);
if(text.equals("approved signature"))
{
text.replace("approved signature", "");
cell.getParagraphArray(0).removeRun(0);
cell.getParagraphArray(0).createRun();
cell.getParagraphArray(0).getRuns().get(0).addPicture(approverFile, XWPFDocument.PICTURE_TYPE_PNG, "approved", Units.toEMU(130), Units.toEMU(55));
}
}
}
System.out.println(((XWPFTable) elem).getRow(0).getCell(0).getText());
}
}
It was about XWPFParagraph, it has to be iterate XWPFTable.
Good morning
I try to add a Table of Content to my doc generated with apache-poi.
I followed this solution
Code url
and it works great.
I have only a problem. By default the header of the TOC is "Table of Content" as you can see from the following image
TOC HEADER IMAGE
I would like to change it with another text. Is it possible?
Thanks
Regards
Good morning
Thanks to Axel Richter advice this is the correct code that generate index without the automatic title Table of Content.
I rewrote the code with custom title of TOC
public class App {
public static void main(String[] args) throws Exception {
XWPFDocument doc= new XWPFDocument();
addCustomHeadingStyle(doc, "heading 1", 1);
addCustomHeadingStyle(doc, "heading 2", 2);
// the body content
XWPFParagraph paragraph = doc.createParagraph();
XWPFRun run=paragraph.createRun();
// set custom title of TOC
run.setBold(true);
run.setFontSize(30);
run.setText("INDEX"); //or whatever other text
CTP ctP = paragraph.getCTP();
CTSimpleField toc = ctP.addNewFldSimple();
toc.setInstr("TOC \\h");
toc.setDirty(STOnOff.TRUE);
run.setText("The Body:");
paragraph = doc.createParagraph();
run=paragraph.createRun();
run.setText("Lorem ipsum");
paragraph.setStyle("heading 1");
paragraph = doc.createParagraph();
run=paragraph.createRun();
run.addBreak(BreakType.PAGE);
run.setText("Lorem ipsum");
paragraph.setStyle("heading 2");
paragraph = doc.createParagraph();
run=paragraph.createRun();
run.addBreak(BreakType.PAGE);
run.setText("Lorem ipsum");
FileOutputStream fos = new FileOutputStream("D:\\toc.docx");
doc.write(fos);
}
private static void addCustomHeadingStyle(XWPFDocument docxDocument, String strStyleId, int headingLevel) {
CTStyle ctStyle = CTStyle.Factory.newInstance();
ctStyle.setStyleId(strStyleId);
CTString styleName = CTString.Factory.newInstance();
styleName.setVal(strStyleId);
ctStyle.setName(styleName);
CTDecimalNumber indentNumber = CTDecimalNumber.Factory.newInstance();
indentNumber.setVal(BigInteger.valueOf(headingLevel));
// lower number > style is more prominent in the formats bar
ctStyle.setUiPriority(indentNumber);
CTOnOff onoffnull = CTOnOff.Factory.newInstance();
ctStyle.setUnhideWhenUsed(onoffnull);
// style shows up in the formats bar
ctStyle.setQFormat(onoffnull);
// style defines a heading of the given level
CTPPr ppr = CTPPr.Factory.newInstance();
ppr.setOutlineLvl(indentNumber);
ctStyle.setPPr(ppr);
XWPFStyle style = new XWPFStyle(ctStyle);
// is a null op if already defined
XWPFStyles styles = docxDocument.createStyles();
style.setType(STStyleType.PARAGRAPH);
styles.addStyle(style);
}
}
Good morning!
I'm using the iText library to create a pdf template and Primefaces to display the content on a web application.
When I ran the first test to see if all the libraries were all set, it was displayed normally. But then I made some changes, and it seems that something is caching my first test in memory and it is the only thing displayed, no matter what changes I make it keeps the same first content. I´ve already cleaned up my netbeans project, closed the IDE and also restarted the computer.
Thats is my tag on the jsf page:
<p:media value="#{atividadeController.pdfContent}" player="pdf" width="100%" height="700px"/>
And here is my method in the managed bean, which is a SessionScoped:
public String preparePdf()
{
try {
ByteArrayOutputStream output = new ByteArrayOutputStream();
Font fontHeader = new Font(Font.FontFamily.HELVETICA, 20, Font.BOLD);
Font fontLine = new Font(Font.FontFamily.TIMES_ROMAN, 14);
Font fontLineBold = new Font(Font.FontFamily.TIMES_ROMAN, 14, Font.BOLD);
Document document = new Document();
PdfWriter.getInstance(document, output);
document.open();
//Writing document
Chunk preface = new Chunk("GERAL", fontHeader);
document.add(preface);
Calendar cal = Calendar.getInstance();
cal.setTime(current.getData());
int year = cal.get(Calendar.YEAR);
int month = 1 + cal.get(Calendar.MONTH);
int day = cal.get(Calendar.DAY_OF_MONTH);
String dateStr = day+"/"+month+"/"+year;
Paragraph dataAndHour = new Paragraph(dateStr, fontLine);
document.add(dataAndHour);
document.close();
pdfContent = new DefaultStreamedContent(new ByteArrayInputStream(output.toByteArray()), "application/pdf");
} catch (Exception e) {
e.printStackTrace();
}
return "/views/view_atividade_pdf";
}
There is no exception on the server log.
I really aprecciate any help. Thanks in advance
I am working with JavaFX2.0.I need to show the thumbnail images in listview.I am writing the code as below.
ObservableList<BufferedImage> imageList = FXCollections.observableArrayList();
try {
for (int i = 1; i <= pdf.getPageCount(); i++) {
BufferedImage pageImage = pdf.getPageAsImage(i);
imageList.add(pageImage);
} catch (PdfException e) {
_logger.error("Error :" + e.getMessage());
}
thumbnailsList.setItems(imageList);
Here thumbnailsList is the fx:id of the listview.But if i use this code i am getting image object and not an image.Can any one tell me that how can i get the image in listview.
Thank You.
You could use a sample from
http://docs.oracle.com/javafx/2/ui_controls/list-view.htm
which is called "Example 11-4 Creating a Cell Factory".
You have to set custom cell factory. And instead of Rectangle, put an ImageView there.
Is it possible to add mergefields to an existing .docx document without using interop, only handling with open SDK from CodeBehind?
Yes this is possible, I've created a little method below where you simply pass through the name you want to assign to the merge field and it creates it for you.
The code below is for creating a new document but it should be easy enough to use the method to append to an existing document, hope this helps you:
using System;
using DocumentFormat.OpenXml;
using DocumentFormat.OpenXml.Packaging;
using DocumentFormat.OpenXml.Wordprocessing;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
using (WordprocessingDocument package = WordprocessingDocument.Create("D:\\ManualMergeFields.docx", WordprocessingDocumentType.Document))
{
package.AddMainDocumentPart();
Paragraph nameMergeField = CreateMergeField("Name");
Paragraph surnameMergeField = CreateMergeField("Surname");
Body body = new Body();
body.Append(nameMergeField);
body.Append(surnameMergeField);
package.MainDocumentPart.Document = new Document(new Body(body));
}
}
static Paragraph CreateMergeField(string name)
{
if (!String.IsNullOrEmpty(name))
{
string instructionText = String.Format(" MERGEFIELD {0} \\* MERGEFORMAT", name);
SimpleField simpleField1 = new SimpleField() { Instruction = instructionText };
Run run1 = new Run();
RunProperties runProperties1 = new RunProperties();
NoProof noProof1 = new NoProof();
runProperties1.Append(noProof1);
Text text1 = new Text();
text1.Text = String.Format("«{0}»", name);
run1.Append(runProperties1);
run1.Append(text1);
simpleField1.Append(run1);
Paragraph paragraph = new Paragraph();
paragraph.Append(new OpenXmlElement[] { simpleField1 });
return paragraph;
}
else return null;
}
}
}
You can download the Open Xml Productivity Tool from this url(if you do not already have it)http://www.microsoft.com/download/en/details.aspx?id=5124
This tool has a "Reflect Code" functionality.So you can manually create a merge field in an MS Word document and then open up the document with the Productivity Tool
and see a C# code sample on how to do this in code!It's very effective an I've used this exact tool to create the sample above.Good luck