artembus
artembus

Reputation: 427

How to replace a word in a text with an image?

Right now I use DefaultListModel with the wanted list of strings and I display it, via JList, in a JScrollPane.

What I want is to find a specific word in this sentence and to put an imageIcon instead of this word which I will display in the said JScrollPane.

For example I want to replace the word "cat" with a cat icon and the Strings would be:

"the little cat is good"
"there is no tomorrow" 
"cat is what I need"

and my desired output will be a JScrollPane with the items:

"the little *cat icon* is good"
"there is no tomorrow" 
"*cat icon* is what I need"

What I found are suggestions to create a custom ListCellRenderer to replace the DefaultListModel. In all the examples an imageIcon was added as icon to a lable, unfortunately this only adds one icon at the beginning of the text which is not what I desire.

Here is the relevant part from one of the examples from this site:

@Override
public Component getListCellRendererComponent(
    JList list, Object value, int index, 
    boolean isSelected, boolean cellHasFocus) {

    // Get the renderer component from parent class

    JLabel label = 
        (JLabel) super.getListCellRendererComponent(list, 
            value, index, isSelected, cellHasFocus);

    // Get icon to use for the list item value

    Icon icon = icons.get(value);

    // Set icon to display for value

    label.setIcon(icon);
    return label;
}

So, how can I add an icon inside a text in a JList ?

Any suggestions would be appreciated. Thank you

Upvotes: 0

Views: 1379

Answers (2)

Petter Friberg
Petter Friberg

Reputation: 21710

You can use the html features of the JLabel, switching cat to <img src='cat.png'/>

Example

public class JListTest extends JPanel{  
  private static final long serialVersionUID = 1L;

  public JListTest(){
    this.setLayout(new BorderLayout());
    JScrollPane scrollPane = new JScrollPane();
    String[] data = {"the little cat is good", "there is no tomorrow" , "cat is what I need"};
    switchToHtml(data);
    replaceWithImage(data,"cat","cat.png");
    JList<String> list = new JList<String>(data);
    scrollPane.getViewport().add(list);
    this.add(scrollPane,BorderLayout.CENTER);       
  }

  private void replaceWithImage(String[] data, String replace, String image) {
    for (int i = 0; i < data.length; i++) {
        String text = data[i];
        if (text.contains(replace)){
            text = text.replaceAll(replace, "<img src=\"" + JListTest.class.getResource(image) + "\">");
            data[i]=text;
        }           
    }
  }

 private void switchToHtml(String[] data) {
    for (int i = 0; i < data.length; i++) {
        data[i]="<html><body>" + data[i] + "</body></html>";
    }
 }

 public static void main(String[] args) {
    JFrame frame = new JFrame("Test");
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    frame.getContentPane().setLayout(new BorderLayout());
    frame.getContentPane().add(new JListTest(),BorderLayout.CENTER);
    frame.pack();
    frame.setVisible(true);
 }
}

To test, just add a cat.png in same package as class.

The result (with a nice kitty)

Result

Upvotes: 3

camickr
camickr

Reputation: 324118

I would use a JTextPane and the insertIcon(...) method.

See the section from the Swing tutorial on Text Component Features for a working example.

The example just shows how to insert the Icon. It will be up to you to parse the text for the Strings you want to replace. Once you find the String you want to replace you can use code like:

textPane.setSelectionStart(...);
textPane.setSelectionEnd(...);
textPane.replaceSelection(...);
textPane.insertIcon(...);

Upvotes: 3

Related Questions