【发布时间】:2018-08-19 01:19:39
【问题描述】:
我有这个类是为了使用 JTree 在叶子中显示多种颜色...
班级是TextPaneDefaultTreeCellRenderer
import java.awt.*;
import java.util.*;
import javax.swing.*;
import javax.swing.text.*;
import javax.swing.tree.*;
public class TextPaneDefaultTreeCellRenderer extends DefaultTreeCellRenderer {
TextPaneTreeCellRenderer textPaneScrollPane = new TextPaneTreeCellRenderer();
public TextPaneDefaultTreeCellRenderer() {
initialize();
}
private void initialize() {
textPaneScrollPane.setBackgroundNonSelectionColor(getBackgroundNonSelectionColor());
textPaneScrollPane.setBackgroundSelectionColor(getBackgroundSelectionColor());
textPaneScrollPane.setTextNonSelectionColor(getTextNonSelectionColor());
textPaneScrollPane.setTextSelectionColor(getTextSelectionColor());
}
@Override
public Component getTreeCellRendererComponent(JTree tree,
Object value, boolean selected, boolean expanded, boolean leaf,
int row, boolean hasFocus) {
if (leaf) {
DefaultMutableTreeNode node = (DefaultMutableTreeNode) value;
Object obj = node.getUserObject();
if (obj != null) {
if (obj instanceof DecoratedText || obj instanceof DecoratedText[]) {
if (textPaneScrollPane == null) {
System.out.println("textPaneScrollPane:" + textPaneScrollPane);
}
return textPaneScrollPane.getTreeCellRendererComponent(tree, value,
selected, expanded, leaf, row, hasFocus);
}
}
}
return super.getTreeCellRendererComponent(tree, value, selected,
expanded, leaf, row, hasFocus);
}
}
class TextPaneTreeCellRenderer extends DefaultTreeCellRenderer {
JTextPane textPane;
public TextPaneTreeCellRenderer() {
textPane = new JTextPane();
add(textPane);
}
@Override
public void setBackgroundNonSelectionColor(Color color) {
this.backgroundNonSelectionColor = color;
}
@Override
public void setBackgroundSelectionColor(Color color) {
this.backgroundSelectionColor = color;
}
@Override
public void setTextNonSelectionColor(Color color) {
this.textNonSelectionColor = color;
}
@Override
public void setTextSelectionColor(Color color) {
this.textSelectionColor = color;
}
@Override
public Component getTreeCellRendererComponent(JTree tree,
Object value, boolean selected, boolean expanded, boolean leaf,
int row, boolean hasFocus) {
DefaultMutableTreeNode node = (DefaultMutableTreeNode) value;
Object object = node.getUserObject();
if (selected) {
setForeground(textSelectionColor);
setBackground(backgroundSelectionColor);
textPane.setForeground(textSelectionColor);
textPane.setBackground(backgroundSelectionColor);
} else {
setForeground(textNonSelectionColor);
setBackground(backgroundNonSelectionColor);
textPane.setForeground(textNonSelectionColor);
textPane.setBackground(backgroundNonSelectionColor);
}
textPane.setText("");
Document doc = textPane.getStyledDocument();
if (object != null && object instanceof DecoratedText) {
DecoratedText decText = (DecoratedText) object;
try {
doc.insertString(doc.getLength(), decText.getText(), getAttributeSet(decText));
} catch (BadLocationException ex) {
Logger.getLogger(TextPaneTreeCellRenderer.class.getName()).log(Level.SEVERE, null, ex);
}
} else if (object != null && object instanceof DecoratedText[]) {
DecoratedText[] arrayDecText = (DecoratedText[]) object;
for (DecoratedText decText : arrayDecText) {
try {
//doc.insertString(doc.getLength(), decText.getText(), getAttributeSet(decText));
doc.insertString(doc.getLength(), decText.getText(), decText.getAttributeSet(textPane));
} catch (BadLocationException ex) {
System.out.println("decText:" + decText);
System.out.println("arrayDecText:" + arrayDecText);
System.out.println("doc:" + doc.getLength());
Logger.getLogger(TextPaneTreeCellRenderer.class.getName()).log(Level.SEVERE, null, ex);
}
}
} else {
return new DefaultTreeCellRenderer().getTreeCellRendererComponent(tree,
value, leaf, expanded, leaf, row, hasFocus);
}
return textPane;
}
private SimpleAttributeSet getAttributeSet(DecoratedText decoratedText) {
SimpleAttributeSet attrSet = new SimpleAttributeSet();
if (decoratedText != null) {
if (decoratedText.getBackground() != null) {
StyleConstants.setBackground(attrSet, decoratedText.getBackground());
} else {
StyleConstants.setBackground(attrSet, textPane.getBackground());
}
if (decoratedText.getForeground() != null) {
StyleConstants.setForeground(attrSet, decoratedText.getForeground());
} else {
StyleConstants.setForeground(attrSet, textPane.getForeground());
}
Font font;
if (decoratedText.getFont() != null) {
font = decoratedText.getFont();
} else {
font = textPane.getFont();
}
StyleConstants.setFontFamily(attrSet, font.getFamily());
StyleConstants.setItalic(attrSet, font.isItalic());
StyleConstants.setBold(attrSet, font.isBold());
StyleConstants.setFontSize(attrSet, font.getSize());
}
return attrSet;
}
}
替代类是TreeCellRendererTextPane
import java.awt.Component;
import java.util.logging.*;
import javax.swing.*;
import javax.swing.text.*;
import javax.swing.tree.*;
public class TreeCellRendererTextPane extends JTextPane implements TreeCellRenderer {
@Override
public Component getTreeCellRendererComponent(JTree tree,
Object value, boolean selected, boolean expanded, boolean leaf,
int row, boolean hasFocus) {
if (leaf) {
DefaultMutableTreeNode node = (DefaultMutableTreeNode) value;
Object obj = node.getUserObject();
if (obj != null) {
if (obj instanceof DecoratedText || obj instanceof DecoratedText[]) {
this.setText("");
Document doc = this.getStyledDocument();
if (obj instanceof DecoratedText) {
DecoratedText decText = (DecoratedText) obj;
try {
doc.insertString(doc.getLength(), decText.getText(), decText.getAttributeSet(this));
} catch (BadLocationException ex) {
Logger.getLogger(TextPaneTreeCellRenderer.class.getName()).log(Level.SEVERE, null, ex);
}
}
if (obj instanceof DecoratedText[]) {
DecoratedText[] arrayDecText = (DecoratedText[]) obj;
for (DecoratedText decText : arrayDecText) {
try {
doc.insertString(doc.getLength(), decText.getText(), decText.getAttributeSet(this));
} catch (BadLocationException ex) {
System.out.println("decText:" + decText);
System.out.println("arrayDecText:" + arrayDecText);
System.out.println("doc:" + doc.getLength());
Logger.getLogger(TextPaneTreeCellRenderer.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
} else {
return new DefaultTreeCellRenderer().getTreeCellRendererComponent(tree,
value, leaf, expanded, leaf, row, hasFocus);
}
}
}
return this;
}
}
如你所见(不是叶子没有正确显示,文件夹被省略,单词只显示第一个字母)
我的另一个班级是DecoratedText:
import java.awt.*;
import javax.swing.JTextPane;
import javax.swing.text.*;
public class DecoratedText {
private String text;
private Color background;// = new JLabel().getBackground();
private Color foreground;// = new JLabel().getForeground();
private Font font;// = new JLabel().getFont();
public DecoratedText(String text) {
this.text = text;
}
public DecoratedText(String text, Font font) {
this.text = text;
this.font = font;
}
public DecoratedText(String text, Color foreground) {
this.text = text;
this.foreground = foreground;
}
public DecoratedText(String text, Color foreground, Font font) {
this.text = text;
this.foreground = foreground;
this.font = font;
}
public DecoratedText(Color background, String text) {
this.background = background;
this.text = text;
}
public DecoratedText(Color background, String text, Font font) {
this.background = background;
this.text = text;
this.font = font;
}
public DecoratedText(Color background, String text, Color foreground) {
this.background = background;
this.text = text;
this.foreground = foreground;
}
public DecoratedText(Color background, String text, Color foreground, Font font) {
this.background = background;
this.text = text;
this.foreground = foreground;
this.font = font;
}
public String getText() {
return text;
}
public void setText(String text) {
this.text = text;
}
public Color getBackground() {
return background;
}
public void setBackground(Color background) {
this.background = background;
}
public Color getForeground() {
return foreground;
}
public void setForeground(Color foreground) {
this.foreground = foreground;
}
public Font getFont() {
return font;
}
public void setFont(Font font) {
this.font = font;
}
@Override
public String toString() {
return "DecoratedText{" + "text=" + text + ", background=" + background
+ ", foreground=" + foreground + ", font=" + font + "}";
}
public SimpleAttributeSet getAttributeSet(JTextPane textPane) {
SimpleAttributeSet attrSet = new SimpleAttributeSet();
if (getBackground() != null) {
StyleConstants.setBackground(attrSet, getBackground());
} else {
StyleConstants.setBackground(attrSet, textPane.getBackground());
}
if (getForeground() != null) {
StyleConstants.setForeground(attrSet, getForeground());
} else {
StyleConstants.setForeground(attrSet, textPane.getForeground());
}
Font font;
if (getFont() != null) {
font = getFont();
} else {
font = textPane.getFont();
}
StyleConstants.setFontFamily(attrSet, font.getFamily());
StyleConstants.setItalic(attrSet, font.isItalic());
StyleConstants.setBold(attrSet, font.isBold());
StyleConstants.setFontSize(attrSet, font.getSize());
return attrSet;
}
}
第一个类 (TextPaneDefaultTreeCellRenderer) 的问题是这个 nullpointerexception 使用 nimbus LAF,但使用另一个 LAF,aqua、metal、motif、gtk和windows都没有出现问题。
并且尝试分而治之,这个问题不是关于什么失败了? 否则我的课程实施得很好吗?
Discover Reason of NullPointerException in Java Native Classes, SynthTreeUI using LAF Nimbus
【问题讨论】:
标签: java swing jtree jtextpane nimbus