How can I set background colour of a run (a word in line or a paragraph) in a docx file by using Apache POI? - apache-poi

I want to create a docx file by using Apache POI.
I want to set background colour of a run (i.e. a word or some parts of a paragraph).
How can I do this?
Is in possible via Apache POI or not.
Thanks in advance

Word provides two possibilities for this. There are really background colors possible within runs. But there are also so called highlighting settings.
With XWPF both possibilities are only possible using the underlying objects CTShd and CTHighlight. But while CTShd is shipped with the default poi-ooxml-schemas-3.13-...jar, for the CTHighlight the fully ooxml-schemas-1.3.jar is needed as mentioned in https://poi.apache.org/faq.html#faq-N10025.
Example:
import java.io.FileOutputStream;
import org.apache.poi.xwpf.usermodel.*;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTShd;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.STShd;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.STHighlightColor;
/*
To
import org.openxmlformats.schemas.wordprocessingml.x2006.main.STHighlightColor;
the fully ooxml-schemas-1.3.jar is needed as mentioned in https://poi.apache.org/faq.html#faq-N10025
*/
public class WordRunWithBGColor {
public static void main(String[] args) throws Exception {
XWPFDocument doc= new XWPFDocument();
XWPFParagraph paragraph = doc.createParagraph();
XWPFRun run=paragraph.createRun();
run.setText("This is text with ");
run=paragraph.createRun();
run.setText("background color");
CTShd cTShd = run.getCTR().addNewRPr().addNewShd();
cTShd.setVal(STShd.CLEAR);
cTShd.setColor("auto");
cTShd.setFill("00FFFF");
run=paragraph.createRun();
run.setText(" and this is ");
run=paragraph.createRun();
run.setText("highlighted");
run.getCTR().addNewRPr().addNewHighlight().setVal(STHighlightColor.YELLOW);
run=paragraph.createRun();
run.setText(" text.");
doc.write(new FileOutputStream("WordRunWithBGColor.docx"));
}
}

Related

JTextPane.setEditable() doesn't work if there is no text in the JTextPane yet. Why? (partially solved)

I am trying to stop a JTextPane from receiving specific letters to insert into its text, so I can insert different letters instead without having to delete the original ones first (and having them annoyingly blink into existence for a moment anyways). My solution so far would be having the press of the key associated with any such letter set the JTextPane uneditable, then have the release set it editable again. I was going to follow this up with changing the text so my chosen alternative letter would show up – but when I tried my code without said followup to see if it would work at all, I noticed that the JTextPane stays uneditable (or maybe disappears) if I press one of the keys in question first thing before typing anything else. (This also happens if I already typed some other text but then deleted it again)
Any ideas what could have gone wrong?
This is my code:
import javax.swing.JFrame;
import java.awt.Container;
import javax.swing.SpringLayout;
import javax.swing.JTextPane;
import java.awt.Font;
import javax.swing.Action;
import javax.swing.AbstractAction;
import java.awt.event.ActionEvent;
import javax.swing.KeyStroke;
class Mainclass
{
public static void main(String[] args)
{
JFrame frame = new JFrame();
Container pane = frame.getContentPane();
SpringLayout layout = new SpringLayout();
JTextPane line = new JTextPane();
Font font = new Font("Palatino", Font.PLAIN, 36);
line.setFont(font);
Action freeze = new AbstractAction()
{
public void actionPerformed(ActionEvent e)
{
line.setEditable(false);
}
};
Action unfreeze = new AbstractAction()
{
public void actionPerformed(ActionEvent e)
{
line.setEditable(true);
}
};
line.getActionMap().put("freeze", freeze);
line.getActionMap().put("unfreeze", unfreeze);
line.getInputMap().put(KeyStroke.getKeyStroke("I"), "freeze");
line.getInputMap().put(KeyStroke.getKeyStroke("J"), "freeze");
line.getInputMap().put(KeyStroke.getKeyStroke("released I"), "unfreeze");
line.getInputMap().put(KeyStroke.getKeyStroke("released J"), "unfreeze");
pane.setLayout(layout);
pane.add(line);
frame.setSize(1000, 250);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
line.getPreferredSize();
frame.setVisible(true);
}
}
PS: I found out that the problem does not occur if I force the JTextPane to always take up some space (stretching it out across the JFrame's contentPane using my Springlayout), but I would still like to know what caused the problem in the first place.

Generate a Word document using different languages

I want to create a Word document that uses different languages. In particular, I have a two-language original text where the language changes between English and German for each paragraph. This is what I tried:
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import org.apache.poi.xwpf.usermodel.XWPFDocument;
import org.apache.poi.xwpf.usermodel.XWPFParagraph;
import org.apache.poi.xwpf.usermodel.XWPFRun;
import org.apache.poi.xwpf.usermodel.XWPFStyles;
public class DocxCreator {
public static void createDocument(File docxOutput) throws IOException {
XWPFDocument doc = new XWPFDocument();
XWPFStyles docStyles = doc.createStyles();
docStyles.setSpellingLanguage("de-DE");
{
XWPFParagraph para = doc.createParagraph();
XWPFRun run = para.createRun();
run.setLanguage("de-DE"); // XXX: this method does not exist
para.setText("Deutsch");
}
{
XWPFParagraph para = doc.createParagraph();
XWPFRun paraRun = para.createRun();
para.setStyle("en-US");
paraRun.setText("English");
}
/*- XXX: How do I add the style “en-US” to the document and set its language to en-US”? */
/* XXX: How do I enable global grammar and spell checking? */
try (FileOutputStream fos = new FileOutputStream(docxOutput)) {
doc.write(fos);
}
}
public static void main(String[] args) throws IOException {
createDocument(new File("multilang.docx"));
}
}
I do not think this is currently supported by POI.
Generally, the language of the text is specified on the XWPFRun (XWPF) / CharacterRun (HWPF) level.
For HWPF (old binary *.doc format) there exists at least a method CharacterRun.getLanguageCode() - but no respective setter.
For XWPF (new *.docx format) I do not see such a thing at all.
The language codes are the same for *.doc and *.docx. A list is available here.

JavaFX 2 dynamic dot loading

I wanna create some loading dots like this:
At 0 second the text on the screen is: Loading.
At 1 second the text on the screen is: Loading..
At 2 second the text on the screen is: Loading...
At 3 second the text on the screen is: Loading.
At 4 second the text on the screen is: Loading..
At 5 second the text on the screen is: Loading...
and so forth until I close the Stage.
What is the best / easiest way to make that in JavaFX? I've been looking into animations/preloaders in JavaFX but that seems to complex when trying to achieve this.
I've been trying to create a loop between these three Text:
Text dot = new Text("Loading.");
Text dotdot = new Text("Loading..");
Text dotdotdot = new Text("Loading...");
but the screen stays static...
How can I make this work correctly in JavaFX? Thanks.
This question is similar to: javafx animation looping.
Here is a solution using the JavaFX animation framework - it seems pretty straight forward to me and not too complex.
import javafx.animation.*;
import javafx.application.Application;
import javafx.event.*;
import javafx.scene.*;
import javafx.scene.control.Label;
import javafx.scene.layout.VBox;
import javafx.stage.Stage;
import javafx.util.Duration;
/** Simple Loading Text Animation. */
public class DotLoader extends Application {
#Override public void start(final Stage stage) throws Exception {
final Label status = new Label("Loading");
final Timeline timeline = new Timeline(
new KeyFrame(Duration.ZERO, new EventHandler() {
#Override public void handle(Event event) {
String statusText = status.getText();
status.setText(
("Loading . . .".equals(statusText))
? "Loading ."
: statusText + " ."
);
}
}),
new KeyFrame(Duration.millis(1000))
);
timeline.setCycleCount(Timeline.INDEFINITE);
VBox layout = new VBox();
layout.getChildren().addAll(status);
layout.setStyle("-fx-background-color: cornsilk; -fx-padding: 10;");
stage.setScene(new Scene(layout, 50, 35));
stage.show();
timeline.play();
}
public static void main(String[] args) throws Exception { launch(args); }
}
Have you considered to use a Progress Indicator or a Progress Bar? I think they can be a good solution to show an animation and avoid problems.
I've been able to do it in JavaFX, not with Animations, but using the concurrency classes from JavaFX.
I let you the code here in a gist. I think it isn't very intuitive, because I prefer a progress indicator. And maybe it isn't the best solution, but maybe this will help you.
Cheers

how to recognize English sentences with SAPI5.4 on an Chinese Windows7

I am using an Chinese Windows 7 with speech recognition working fine if I use the grammar to recognize English sentences which is constructed with the object of Choice.But the object of SpeechRecognitionEngine only can arise SpeechDetectedEventArgs and doesn't arise LoadGrammarCompletedEventArgs or RecognizeCompletedEventArgs when the the object of Grammar is constructed with the object of SrgsDocement.There is my fragement of the project.
SpeechRecognitionEngine recognizer = new SpeechRecognitionEngine ( System.Globalization.CultureInfo.CreateSpecificCulture("zh-CN"));
SrgsDocument srgsdoc = new SrgsDocument(./commongreetingGrammar.grxml");
recognizer.MaxAlternates = 5;
recognizer.LoadGrammarCompleted += new EventHandler<LoadGrammarCompletedEventArgs>(recognizer_LoadGrammarCompleted);
recognizer.SpeechDetected += new EventHandler<SpeechDetectedEventArgs>(recognizer_SpeechDetected);
recognizer.RecognizeCompleted += new EventHandler<RecognizeCompletedEventArgs>(recognizer_RecognizeCompleted);
recognizer.LoadGrammar(new Grammar(srgsdoc));
recognizer.SetInputToDefaultAudioDevice();
recognizer.RecognizeAsync (RecognizeMode .Multiple);
}
catch (Exception ex)
{ Console.WriteLine(ex.Message); }
Console.ReadKey();
}
static void recognizer_SpeechDetected(object sender, SpeechDetectedEventArgs e)
{
Console.WriteLine("Detect that someone is speeching");
}
static void recognizer_LoadGrammarCompleted(object sender, LoadGrammarCompletedEventArgs e)
{
if (e.Error == null)
Console.WriteLine("complete to load grammar ");
else
Console.WriteLine("Fail to load grammar");
}
static void recognizer_RecognizeCompleted(object sender, RecognizeCompletedEventArgs e)
{
if (e.Result.Semantics["step"].Value.ToString() == "A1")
{
Console.WriteLine("A start to speak:{0}", e.Result.Text);
}
}
And there is the file named commongreetingGrammar.grxml that constructs the object of SrgsDocement named srgsdoc .(Sorry to add the image of the .grxml file instead of the plain text of the .grxml file)
![enter image description here][1]
I’m afraid that I didn’t present my problem clearly.
I try to recognize English sentences using the SpeechRecognitionEngine class ,which is part of SAPI5.4,on an Chinese Windows7 which has installed the Microsoft Speech Recognizer 8.0 for Windows (Chinese Simplified - PRC).Using the object of Grammar class constructed with the object of Choice class,the object of the SpeechRecognitionEngine class loaded the grammar can recognize some of simple English sentences,for example,”How are you ”,”yes”,”quit”.
However, using the object of Grammar class constructed with the SrgsDocement object which is constructed with .grxml file,the SpeechRecognitionEngine object loaded the grammar can’t recognize some of simple English sentences and only can detect audioinput.The fragments of code as follewed.
Luckliy,I find the solution to the problem today.
The problem is that I didn’t install the English language pack and constructed the Grammar object wrongly,which cause the SpeechRecognitionEngine object to fail to recognize the English sentences.The details of the solution I has posted in CodeProject.

Formatting text using Apache POI 3.8 (HWPF)

I am trying to insert the following text in the document using Apache POI 3.8:
[Bold][Normal],
but the output document has this:
[Bold][Normal]
The code:
import org.apache.poi.hwpf.HWPFDocument;
import org.apache.poi.hwpf.usermodel.*;
import java.io.*;
public class Main {
public static void main(String[] args) throws IOException {
final HWPFDocument doc = new HWPFDocument(new FileInputStream("empty.dot"));
final Range range = doc.getRange();
final CharacterRun cr1 = range.insertAfter("[Bold]");
cr1.setBold(true);
final CharacterRun cr2 = cr1.insertAfter("[Normal]");
cr2.setBold(false);
doc.write(new FileOutputStream("output.doc"));
}
}
What is the correct way of doing this?
I do it like this. Using POI 3.11
paragraph = doc.createParagraph();
paragraph.setStyle(DOG_HEAD_STYLE);
XWPFRun tmpRun = paragraph.createRun();
tmpRun.setText("non bold text ");
tmpRun = paragraph.createRun();
tmpRun.setBold(true);
tmpRun.setText("bold text");
tmpRun = paragraph.createRun();
tmpRun.setBold(false);
tmpRun.setText(" non bold text again");

Resources