我的目标是将用户编写的关键字的蓝色着色实现到JTextPane中。这就是我的代码的样子:
private class DocumentHandler implements DocumentListener {
@Override
public void changedUpdate(DocumentEvent ev) {
}
@Override
public void insertUpdate(DocumentEvent ev) {
highlight();
}
@Override
public void removeUpdate(DocumentEvent ev) {
highlight();
}
private void highlight() {
String code = codePane.getText();
SimpleAttributeSet defSet = new SimpleAttributeSet();
StyleConstants.setForeground(defSet, Color.BLACK);
doc.setCharacterAttributes(0, code.length(), defSet, true);
SimpleAttributeSet set = new SimpleAttributeSet();
StyleConstants.setForeground(set, Color.BLUE);
for (String keyword : keywords) {
Pattern pattern = Pattern.compile(keyword + "(\\[\\])*");
Matcher matcher = pattern.matcher(code);
while (matcher.find()) {
//Just for test
System.out.print("Start index: " + matcher.start());
System.out.print(" End index: " + matcher.end());
System.out.println(" Found: " + matcher.group());
doc.setCharacterAttributes(matcher.start(), keyword.length(), set, true);
}
}
}
}
在窗格中输入任何内容后,我得到:
Exception in thread "AWT-EventQueue-0" java.lang.IllegalStateException: Attempt to mutate in notification
at javax.swing.text.AbstractDocument.writeLock(AbstractDocument.java:1338)
at javax.swing.text.DefaultStyledDocument.setCharacterAttributes(DefaultStyledDocument.java:500)
at jnotepad.MainPanel$DocumentHandler.highlight(MainPanel.java:121)
at jnotepad.MainPanel$DocumentHandler.insertUpdate(MainPanel.java:108)
at javax.swing.text.AbstractDocument.fireInsertUpdate(AbstractDocument.java:202)
at javax.swing.text.AbstractDocument.handleInsertString(AbstractDocument.java:749)
如何解决我的问题?也许我应该使用DocumentListener以外的东西?
答案 0 :(得分:19)
您需要从Event Dispatcher Thread调用对文档的更改。
试试这个:
private void highlight() {
Runnable doHighlight = new Runnable() {
@Override
public void run() {
// your highlight code
}
};
SwingUtilities.invokeLater(doHighlight);
}
答案 1 :(得分:0)
我有同样的问题,我用这个来解决它:
expiration_timeTF.getDocument().addDocumentListener(
new DocumentListener() {
@Override
public void removeUpdate(DocumentEvent e) {
System.out.println("remove");
}
private void assistDateText() {
Runnable doAssist = new Runnable() {
@Override
public void run() {
// when input "2013",will add to "2013-";when
// input "2013-10",will add to "2013-10-"
String input = expiration_timeTF.getText();
if (input.matches("^[0-9]{4}")) {
expiration_timeTF.setText(input + "-");
} else if (input.matches("^[0-9]{4}-[0-9]{2}")) {
expiration_timeTF.setText(input + "-");
}
}
};
SwingUtilities.invokeLater(doAssist);
}
@Override
public void insertUpdate(DocumentEvent e) {
// System.out.println("insert");
assistDateText();
}
@Override
public void changedUpdate(DocumentEvent e) {
// System.out.println("change");
}
});