正如問題所述,如何成功將多個圖標放在JTextPane
的同一行文本中?每次我嘗試更改actionText
的值時,結果都非常不可預測。作爲一個例子,這是事情我想達到那種:(Java Swing)如何在同一行上創建帶有多個圖標的JTextPane?
如果我通過只是圖標令牌創建圖標(」」,例如),他們只是堆頂彼此(或者可能不會,很難說)。如果我把「,」或「和」放在第一行,第一行出現第一個戰鬥機圖標,而第二行出現逗號和其他戰鬥機圖標。
我目前正在嘗試使用基於oracle教程構建的解決方案JTextPane
:JTextPane tutorial。這是我的代碼塊創建我的自定義文本窗格。
public final class GameTextPaneFactory {
private static final String[] ADVENTURER_TOKENS = {"<FIGHTER>", "<CLERIC>", "<WIZARD>", "<ROGUE>"};
private static final int TEXT_PANE_WIDTH = 30;
public static JTextPane createActionTextPane(String actionText) {
ArrayList<String>[] wordsAndStyles = parseActionText(actionText);
JTextPane actionTextPane = new JTextPane();
StyledDocument doc = actionTextPane.getStyledDocument();
addStylesToDocument(doc);
try {
for (int i=0; i < wordsAndStyles[0].size(); i++) {
doc.insertString(doc.getLength(), wordsAndStyles[0].get(i),
doc.getStyle(wordsAndStyles[1].get(i)));
}
} catch (BadLocationException ble) {
System.err.println("Couldn't insert initial text into text pane.");
}
actionTextPane.setEditable(false);
return actionTextPane;
}
private static void addStylesToDocument(StyledDocument doc) {
// TODO add images (styles) here
Style def = StyleContext.getDefaultStyleContext().getStyle(StyleContext.DEFAULT_STYLE);
Style regular = doc.addStyle("regular", def);
Style icons = doc.addStyle("fighterIcon", regular);
StyleConstants.setAlignment(icons, StyleConstants.ALIGN_CENTER);
ImageIcon fighterIcon = new ImageIcon("images/fighter_image.png", "fighter");
StyleConstants.setIcon(icons, fighterIcon);
icons = doc.addStyle("clericIcon", regular);
StyleConstants.setAlignment(icons, StyleConstants.ALIGN_CENTER);
ImageIcon clericIcon = new ImageIcon("images/cleric_image.png", "cleric");
StyleConstants.setIcon(icons, clericIcon);
icons = doc.addStyle("wizardIcon", regular);
StyleConstants.setAlignment(icons, StyleConstants.ALIGN_CENTER);
ImageIcon wizardIcon = new ImageIcon("images/wizard_image.png", "wizard");
StyleConstants.setIcon(icons, wizardIcon);
icons = doc.addStyle("rogueIcon", regular);
StyleConstants.setAlignment(icons, StyleConstants.ALIGN_CENTER);
ImageIcon rogueIcon = new ImageIcon("images/rogue_image.png", "rogue");
StyleConstants.setIcon(icons, rogueIcon);
}
private static ArrayList<String>[] parseActionText(String text) {
String[] words = text.split(" ");
ArrayList<String> outputStrings = new ArrayList<String>();
ArrayList<String> outputStyles = new ArrayList<String>();
StringBuilder nextStringBuilder = new StringBuilder();
int currentLineLength = TEXT_PANE_WIDTH;
for(String word : words) {
if(Arrays.asList(ADVENTURER_TOKENS).contains(word)) {
if(nextStringBuilder.length() != 0) {
outputStrings.add(nextStringBuilder.toString());
outputStyles.add("regular");
nextStringBuilder = new StringBuilder();
}
outputStrings.add(" "); // this is ignored, but cannot be empty
switch(word) {
case "<FIGHTER>":
outputStyles.add("fighterIcon");
break;
case "<CLERIC>":
outputStyles.add("clericIcon");
break;
case "<WIZARD>":
outputStyles.add("wizardIcon");
break;
case "<ROGUE>":
outputStyles.add("rogueIcon");
break;
}
currentLineLength += 3; // an icon is about 3 characters in length
} else {
if(currentLineLength + word.length() + 1 > TEXT_PANE_WIDTH) {
nextStringBuilder.append("\n");
currentLineLength = 0;
}
nextStringBuilder.append(" " + word);
currentLineLength += word.length() + 1;
}
}
if(nextStringBuilder.length() != 0) {
outputStrings.add(nextStringBuilder.toString());
outputStyles.add("regular");
}
@SuppressWarnings("unchecked")
ArrayList<String>[] output = new ArrayList[2];
output[0] = outputStrings;
output[1] = outputStyles;
return output;
}
}
如果有人有更好的解決辦法,我洗耳恭聽。謝謝!
你可以添加你的'textpane'圖片嗎? –