I have a PPT containing values in the format: {VALUES}. I would like to replace the text of the file containing {SAMPLE} to SARAN and so on using Java. Earlier I tried with Apache poi and I had no solution but I could find that in Docx4j there is an method variableReplace() which will replace the text. I tried one sample but I don't see any text being replaced.
My code:
public static void main(String[] args) throws IOException, Docx4JException, Pptx4jException, JAXBException
{
String inputfilepath = "C:\\Work\\SampleTemplate.pptx";
PresentationMLPackage pptPackage
= PresentationMLPackage.load(new File(inputfilepath));
ThemePart themeSlidePart = (ThemePart)
pptPackage.getParts().getParts().get(new PartName("/ppt/theme/theme1.xml"));
Theme themeOfSlides = (Theme)themeSlidePart.getJaxbElement();
SlidePart slide = pptPackage.getMainPresentationPart().getSlide(0);
HashMap h = new HashMap<String, String>();
h.put("SlideTitleName", "SARANYA");
slide.variableReplace(h);
String outputfilepath = "C:\\Work\\24Jan2018_CheckOut\\dhl\\PPT-TRAILS\\SampleTemplate.pptx";
PresentationMLPackage pptPackagetoApply
= PresentationMLPackage.load(new File(outputfilepath));
ThemePart themeSlidePartToApply
= (ThemePart) pptPackagetoApply.getParts().getParts()
.get(new PartName("/ppt/theme/theme1.xml"));
themeSlidePartToApply.setJaxbElement(themeOfSlides);
SaveToZipFile saver = new SaveToZipFile(pptPackagetoApply);
saver.save(outputfilepath);
}
But still text is not being replaced. I tried with a new PPTX file with only text "${SlideTitleName}" inside it. But still it's not working.
I would like to add many rows to my pptx template using for loop, I tried the below,
Java:
if(majorAchievements.size()>0){
System.out.println("majorAchievements Size in Servlet is : "+majorAchievements.size() + " and value of get(0) is : "+ majorAchievements.get(0) );
for(int i=0;i<majorAchievements.size();i++){
achievements=(String) majorAchievements.get(i);
}
}
mappings.put("MajorAchievementText", achievements);
and inside my ppt file ,
i haved added two rows with same ${MajorAchievementText}.
The above list fetches 2 rows. But inside ppt it is not replace.
Please help me how to replace an text by iterating.
With Regards,
Saranya C
Related
My goal is to insert a docx (with keeping the style / formatting) into another docx's specific row. In the second docx there is a word, "placeholder" and first, I have to find this word, and then change it to first docx text, keeping the inserted docx styles and formats.
I have an idea. Maybe I should create a new docx, divide the second docx with the "placeholder", put the first part to the new docx, then put the whole docx, and then put the second part of the second docx. But how can I keep the styles and formats? I don't have images / tablets or anything, just texts and formatting stuff, like lists, tabs, text style, etc.
Currently I am using apache POI and java. (I tried docx4j, but I had less success)
The example code does a simple merging but nothing more. How can I find the "placeholder" word and insert my docx there?
public static void merge(InputStream src1, InputStream src2, OutputStream dest) throws Exception {
OPCPackage src1Package = OPCPackage.open(src1);
OPCPackage src2Package = OPCPackage.open(src2);
XWPFDocument src1Document = new XWPFDocument(src1Package);
CTBody src1Body = src1Document.getDocument().getBody();
XWPFDocument src2Document = new XWPFDocument(src2Package);
CTBody src2Body = src2Document.getDocument().getBody();
appendBody(src1Body, src2Body);
src1Document.write(dest);
}
private static void appendBody(CTBody src, CTBody append) throws Exception {
XmlOptions optionsOuter = new XmlOptions();
optionsOuter.setSaveOuter();
String appendString = append.xmlText(optionsOuter);
String srcString = src.xmlText();
String prefix = srcString.substring(0, srcString.indexOf(">") + 1);
String mainPart = srcString.substring(srcString.indexOf(">") + 1, srcString.lastIndexOf("<"));
String suffix = srcString.substring(srcString.lastIndexOf("<"));
String addPart = appendString.substring(appendString.indexOf(">") + 1, appendString.lastIndexOf("<"));
CTBody makeBody = CTBody.Factory.parse(prefix + mainPart + addPart + suffix);
src.set(makeBody);
}
Re docx4j you can insert a docx at a specific location (eg in a table cell) using MergeDocx in our commercial Docx4j Enterprise.
You can get a trial version from https://www.plutext.com/m/index.php/products
Then see the MergeIntoTableCell sample and documentation.
Other solution is: in my example in mainPart, we can find the text (using indexof / lastindexof / substring are better, than using regex) and add (and replace the text to) the addPart and ready to go.
2 possible problem:
1: if we have numbered lists / bulleted lists in addPart, that can be be messy after adding to the other document.
2: inserting picture is not possible in this way, it has to be handle in other way.
I want to compare 2 file PDF and now I am using PdfUtil library.
But I have a problem,PdfUtil still works like expected if files have a same format.If not,The result image will highlight everything and I can't see the difference of content between 2 file.
So,How can I compare only content like TEXT_Mode but still get result image with highlight the difference like VISUAL_MODE
Thanks .
This is my simple code
public static void main(String[] args) throws IOException {
String result ="/Users/abc/Downloads/Test";
String pdf1 = "/Users/abc/Downloads/pdf1.pdf";
String pdf2 = "/Users/abc/Downloads/pdf2.pdf";
PDFUtil pdfUtil = new PDFUtil();
pdfUtil.setCompareMode(CompareMode.VISUAL_MODE);
pdfUtil.highlightPdfDifference(true);
pdfUtil.setImageDestinationPath(result);
boolean abc =pdfUtil.compare(pdf1,pdf2);
System.out.print(abc);
}
You could try https://github.com/lumpchen/xdiff.ncc, a pdf compare tool based on pdfbox.
I'm messing around with itext, and I was changing the fontsize and as a result I end up with some weirdly spaced text in my pdf:
Which I'd like to turn into something like this: (Excuse the poor image editing)
This is the code I use to enter the text:
private fun setBaseInfo(info: ArrayList<String>): PdfPCell
{
val cell = PdfPCell()
val glue = Chunk(VerticalPositionMark())
val p = Paragraph()
p.font.size = 8.0f
for (str in info)
{
p.add(glue)
p.add(str)
p.add("\n")
}
cell.border = Rectangle.NO_BORDER
cell.addElement(p)
return cell
}
And this is the info I feed it:
private fun foo(): ArrayList<String>
{
val array = ArrayList<String>()
array.add("Hi")
array.add("StackOverflow")
array.add("I'd Like")
array.add("This")
array.add("text")
array.add("to be closer")
array.add("together!")
return array
}
When removing p.add("\n") this is the output:
Full disclosure: former iText employee here
This is how I would do it:
public static void main(String[] args) throws IOException {
// create a temp file to hold the output
File outputFile = File.createTempFile("stackoverflow",".pdf");
PdfDocument pdfDocument = new PdfDocument(new PdfWriter(outputFile));
Document layoutDocument = new Document(pdfDocument);
String[] lines = {"Hi","StackOverflow","I'd like","this","text","to","be","closer","together!"};
for(String line : lines){
layoutDocument.add(new Paragraph(line)
.setMultipliedLeading(0.5f)); // this is where the magic happens
}
layoutDocument.close();
pdfDocument.close();
// display the temp file with the default PDF viewer
Desktop.getDesktop().open(outputFile);
}
I changed a couple of things:
Use the latest version of iText whenever possible. You want to benefit from several years of bugfixes and a newer architecture.
Do not use tables to solve layout issues.
Use leading (either MultipliedLeading or FixedLeading) on Paragraph objects to fix your issue.
I am required to replace a word in an existing PDF AcroField with another word. I am using PDFStamper of iTEXTSHARP to do the same and it is working fine. But, in doing so it is required to create a new PDF and i would like the change to be reflected in the existing PDF itself. If I am setting the destination filename same as the original filename then no change is being reflected.I am new to iTextSharp , is there anything I am doing wrong? Please help.. I am providing the piece of code I am using
private void ListFieldNames(string s)
{
try
{
string pdfTemplate = #"z:\TEMP\PDF\PassportApplicationForm_Main_English_V1.0.pdf";
string newFile = #"z:\TEMP\PDF\PassportApplicationForm_Main_English_V1.0.pdf";
PdfReader pdfReader = new PdfReader(pdfTemplate);
for (int page = 1; page <= pdfReader.NumberOfPages; page++)
{
PdfReader reader = new PdfReader((string)pdfTemplate);
using (PdfStamper stamper = new PdfStamper(reader, new FileStream(newFile, FileMode.Create, FileAccess.ReadWrite)))
{
AcroFields form = stamper.AcroFields;
var fieldKeys = form.Fields.Keys;
foreach (string fieldKey in fieldKeys)
{
//Replace Address Form field with my custom data
if (fieldKey.Contains("Address"))
{
form.SetField(fieldKey, s);
}
}
stamper.FormFlattening = true;
stamper.Close();
}
}
}
As documented in my book iText in Action, you can't read a file and write to it simultaneously. Think of how Word works: you can't open a Word document and write directly to it. Word always creates a temporary file, writes the changes to it, then replaces the original file with it and then throws away the temporary file.
You can do that too:
read the original file with PdfReader,
create a temporary file for PdfStamper, and when you're done,
replace the original file with the temporary file.
Or:
read the original file into a byte[],
create PdfReader with this byte[], and
use the path to the original file for PdfStamper.
This second option is more dangerous, as you'll lose the original file if you do something that causes an exception in PdfStamper.
To start, no this is not a homework assignment. I am fresh out of highschool and am trying to do some personal projects before college. I've been trying to populate an ArrayList with elements from a document. The document looks like:
item1
item2
item3
...
itemN
After failing many times on my own, I tried different solutions from this website. Most recently, this one got me the closest to what I desire:
public static void main(String[] args) throws IOException {
List<String> names = new ArrayList<String>();
BufferedReader reader = null;
try {
reader = new BufferedReader(new FileReader("/Users/MyName/Desktop/names.txt"));
String line = null;
while ((line = reader.readLine()) != null) {
names.add(line);
}
} finally {
reader.close();
}
for(int i = 0; i<names.size(); i++){
System.out.println(names.get(i));
}
//String[] array = (String[]) names.toArray(); Not necessary that it is in an array
}
The only problem is that this returns something rather ugly in the console:
{\rtf1\ansi\ansicpg1252\cocoartf1347\cocoasubrtf570
{\fonttbl\f0\froman\fcharset0 Times-Roman;}
{\colortbl;\red255\green255\blue255;}
\margl1440\margr1440\vieww10800\viewh8400\viewkind0
\pard\tx577\tx1155\tx1733\tx2311\tx2889\tx3467\tx4045\tx4623\tx5201\tx5779\tx6357\tx6935\tx7513\tx8091\tx8669\tx9247\tx9825\tx10403\tx10981\tx11559\tx12137\tx12715\tx13293\tx13871\tx14449\tx15027\tx15605\tx16183\tx16761\tx17339\tx17917\tx18495\tx19072\tx19650\tx20228\tx20806\tx21384\tx21962\tx22540\tx23118\tx23696\tx24274\tx24852\tx25430\tx26008\tx26586\tx27164\tx27742\tx28320\tx28898\tx29476\tx30054\tx30632\tx31210\tx31788\tx32366\tx32944\tx33522\tx34100\tx34678\tx35256\tx35834\tx36412\tx36990\tx37567\tx38145\tx38723\tx39301\tx39879\tx40457\tx41035\tx41613\tx42191\tx42769\tx43347\tx43925\tx44503\tx45081\tx45659\tx46237\tx46815\tx47393\tx47971\tx48549\tx49127\tx49705\tx50283\tx50861\tx51439\tx52017\tx52595\tx53173\tx53751\tx54329\tx54907\tx55485\tx56062\tx56640\tx57218\tx57796\li577\fi-578
\f0\fs24 \cf0 \CocoaLigature0 item1\
item2\
item3\
...
itemN\
}
How can i get it to read from the file but not include all of the back-slashes and formatting info?
you just need to really save the file as text file. Your file looks like an RTF file at the moment. Open Pages application and open that file. Go to File... Export to... Plain Text... and save it into a new file.
Looks like your names.txt file got saved as RTF (Rich Text Format). Make sure you convert it to plain text.