Solved

JList custom Cell Renderer refresh

Posted on 2016-11-17
15
76 Views
Last Modified: 2016-11-23
I have a JList with a custom cell renderer (the background color changes).  How do you refresh a JList, applying this renderer automatically?  I have the JList on a tab in a JFrame.  If I select another tab, and come back to the tab the JList is on, it refreshes.  But I need to have the JList's background color refresh without having me change tabs.  (Or, at least have it refresh every 5 seconds or so).  I need this to happen without strange GUI glitches (which would probably happen if I have to clear/repopulate the JList)  Thanks.
0
Comment
Question by:MarkLoveExEx
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 6
  • 4
  • 3
  • +1
15 Comments
 

Author Comment

by:MarkLoveExEx
ID: 41892012
I added a ListDataListener, but I still need to "click" the List for it to update.  Still looking for a solution to have it update with no user interaction.
0
 

Author Comment

by:MarkLoveExEx
ID: 41892164
Would the solution involve a swing worker?
0
 
LVL 37

Assisted Solution

by:zzynx
zzynx earned 125 total points
ID: 41892593
But I need to have the JList's background color refresh without having me change tabs.
I assume that the background color is determined somehow by the data.
So, there's no need to refresh eg. every 5 seconds (if the data isn't changed)
You only need to refresh when the data has changed. In that light, adding a ListDataListener was defintely a good step.

...but I still need to "click" the List for it to update.
How do you mean?

You know, helping you without having a single piece of code is nearly impossible. Could you please post your code?

Did you already try something like this:

in your ListDataListener's method

void contentsChanged(ListDataEvent e) {
     JList theList = (JList)e.getSource();
     theList.invalidate();
     theList.doLayout();
}

Open in new window

0
[Live Webinar] The Cloud Skills Gap

As Cloud technologies come of age, business leaders grapple with the impact it has on their team's skills and the gap associated with the use of a cloud platform.

Join experts from 451 Research and Concerto Cloud Services on July 27th where we will examine fact and fiction.

 
LVL 16

Accepted Solution

by:
krakatoa earned 250 total points
ID: 41892795
This is an appalling hack, and requires not only considerable questioning, but more oop-ness all 'round. Nevertheless, it may help point you in some direction you are seeking, given that, as zzynx says, we don't really know the full context of what you are doing, nor why.

import javax.swing.*;
import java.util.*;
import java.awt.*;


class Cellular extends JFrame{

static JList jlist;
static DefaultListCellRenderer dlcr;
static JTabbedPane tabs;
static Cellular cell;

public static void main(String[] args){

	jlist = new JList();
		
	cell = new Cellular();
	
	//.......
	tabs = new JTabbedPane();
         
        tabs.addTab("Main",new JLabel());
        tabs.addTab("Advanced",new JLabel());
        tabs.addTab("Privacy",new JLabel());
        tabs.addTab("eMail",new JLabel());
        tabs.addTab("Security",new JLabel());
        tabs.setSize(300, 100);
        tabs.setVisible(true);

	
	//.......
	
	dlcr = (DefaultListCellRenderer)jlist.getCellRenderer();
	
	
	tabs.add(new JLabel("1"));
	tabs.add(jlist);
	jlist.setVisible(true);
	
	cell.add(tabs);
	cell.setSize(new Dimension(400,175));
	cell.setVisible(true);
	new Thread(new Timing()).start();

}

  static class Timing extends TimerTask{

		public Timing(){
			
			java.util.Timer t = new java.util.Timer();
            t.scheduleAtFixedRate(this, 10, 5000);
			tabs.setSelectedComponent(jlist);
		}
			
   public void run(){
   
	 
					jlist.setBackground(new java.awt.Color((int)(Math.random()*100),(int)(Math.random()*100),(int)(Math.random()*100)));
					
					if(!cell.isVisible()){System.exit(0);}
					dlcr.update(jlist.getGraphics());
					
			     
	}

  }

}

Open in new window

0
 

Author Comment

by:MarkLoveExEx
ID: 41892872
Thank you for the input. I will be back working on this problem on Monday, where I will try your suggestions. I will see what I can do about posting some code. My programs average 6000 lines and 30 classes which all interact, so sometimes it is difficult to know exactly what to post.  For this particular problem, I don't think I'm doing anything strange. It is just a basic JList with its model. You're right, the data is changing, and the custom cell renderer accesses that data, but the background color of the JList just won't change unless I have some GUI interaction, such as a change of tab or simply clicking on the JList. Again, thank you for your suggestions so far, but I have to put this on hold until Monday.
0
 
LVL 37

Expert Comment

by:zzynx
ID: 41893071
You're right, the data is changing, and the custom cell renderer accesses that data, but the background color of the JList just won't change unless I have some GUI interaction
Try what I posted.

Again, thank you for your suggestions so far,  
You're welcome
but I have to put this on hold until Monday.
No problem. Keep us up to date whenever you have new information.
0
 
LVL 16

Expert Comment

by:krakatoa
ID: 41895193
Here's a bit more code you can try for size :

import javax.swing.*;
import java.util.*;
import java.awt.*;
import java.io.*;
import javax.swing.event.*;
import java.awt.event.*;


class Cellular extends JFrame {

static JList<?> jlist;
static JTabbedPane tabs;
static Cellular cell;
static Exception exx;
static String[] sA={"A","B","C","D","E","Z"};
static ListDataEvent lde;

public static void main(String[] args) {

try{
	
	jlist = new JList<String>(sA);
	cell = new Cellular();
	tabs = new JTabbedPane();
         
        tabs.addTab("Main",new JLabel("Main"));
        tabs.addTab("Advanced",new JLabel());
        tabs.addTab("Privacy",new JLabel());
        tabs.addTab("eMail",new JLabel());
        tabs.addTab("Security",new JLabel());
        tabs.setSize(300, 100);
        tabs.setVisible(true);
	
	tabs.add(new JLabel("1"));
	tabs.add("JList",jlist);
	
	jlist.setBackground(java.awt.Color.WHITE);
	jlist.setVisible(true);
	
	cell.add(tabs);
	cell.setSize(new Dimension(450,255));
	cell.setVisible(true);
	
	int delay = 1000;
	
	ActionListener listUpdater = new ActionListener() {
	
      public void actionPerformed(ActionEvent evt) {
		
					try{
					if(!cell.isVisible()){throw new Exception(exx);}
					lde = new ListDataEvent(jlist,0,0,0);				
									
					if(jlist.getBackground()==java.awt.Color.WHITE){jlist.setForeground(new java.awt.Color(100,100,100));}
					else{jlist.setForeground(new java.awt.Color(255,255,255));}
								
					String st = (String)jlist.getModel().getElementAt(0);
					System.out.println(st);
					if(sA[0].equals("K")){sA[0]="A";}
					else{sA[0]="K";}
					if (lde.getSource()==jlist){
					jlist.setBackground(new java.awt.Color((int)(Math.random()*100),(int)(Math.random()*100),(int)(Math.random()*100)));}jlist.updateUI();
					}
					catch(Exception exx){System.exit(1);}
	  }
  };
	
	tabs.setSelectedComponent(jlist);
	new javax.swing.Timer(delay, listUpdater).start();
	
}catch(Exception t){System.exit(1);}

}

}

Open in new window

0
 
LVL 86

Assisted Solution

by:CEHJ
CEHJ earned 125 total points
ID: 41896040
You only need to refresh when the data has changed. In that light, adding a ListDataListener was defintely a good step.
The 'inner wiring' of the JList should cause its rendering to be done correctly as soon as its data is mutated with no need for extra listeners.
 The fact that it's not doing so is probably caused by some blocking of the EDT caused by incorrect thread handling
0
 

Author Closing Comment

by:MarkLoveExEx
ID: 41896316
I finally found a solution that works.  I added a timer that adds an element to the JList, and then removes that element right away.  There is probably a better way, but this seems to work.  Thank you all for your input. I am not sure how to assign points, as I did not actually end up using any suggestions.  What is the protocol for this?
0
 
LVL 16

Expert Comment

by:krakatoa
ID: 41896337
If this is real data you are dealing with then I would say that it is not really good practice to artificially insert some simply in order to fire an event. It is more than a notional compromise of integrity. But if this was an experimental / recreational / learning exercise then I guess it's fine. Did you run my last piece of code?
1
 
LVL 86

Expert Comment

by:CEHJ
ID: 41896356
Generally speaking (i think you know the quality of the workaround you just described, so i shan't comment on it) there is seldom much need to mutate a JList. What can happen is that a different model needs to be set on it, in which case, if the renderer is OK, then everything should work fine. When the new model is set, the renderer will carry on as before
0
 
LVL 37

Expert Comment

by:zzynx
ID: 41897074
I added a timer that adds an element to the JList, and then removes that element right away.
Really? That's quite a dirty workaround...
0
 

Author Comment

by:MarkLoveExEx
ID: 41898449
Really? That's quite a dirty workaround...

I know right?  But it works surprisingly well.
0
 

Author Comment

by:MarkLoveExEx
ID: 41898452
krakatoa -- I will try your latest code, maybe tomorrow.
0
 
LVL 16

Expert Comment

by:krakatoa
ID: 41898740
No big deal. All I was really referring to is the point that CEHJ made, that the threading would affect performance, and my second piece of code has a better approach to that.
0

Featured Post

On Demand Webinar: Networking for the Cloud Era

Ready to improve network connectivity? Watch this webinar to learn how SD-WANs and a one-click instant connect tool can boost provisions, deployment, and management of your cloud connection.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Go is an acronym of golang, is a programming language developed Google in 2007. Go is a new language that is mostly in the C family, with significant input from Pascal/Modula/Oberon family. Hence Go arisen as low-level language with fast compilation…
Java functions are among the best things for programmers to work with as Java sites can be very easy to read and prepare. Java especially simplifies many processes in the coding industry as it helps integrate many forms of technology and different d…
Video by: Michael
Viewers learn about how to reduce the potential repetitiveness of coding in main by developing methods to perform specific tasks for their program. Additionally, objects are introduced for the purpose of learning how to call methods in Java. Define …
The viewer will learn how to implement Singleton Design Pattern in Java.
Suggested Courses

635 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question