How to update 2 JCombo Boxs - java

I have 2 Jcombo Boxs: which is combo1 and combo2
I choose combo1 and I can get information for combo2 but The problem is I can get informatiob for combo2 but it is not updated. I also try to use updata.UI() but it doesn't help.
This is the code in side
public void actionPerformed(ActionEvent e) {
JComboBox cb = (JComboBox)e.getSource();
String uname1 = (String)cb.getSelectedItem();
combo2 = update(uname1);
combo2.updateUI();
}
This is code inside update
protected JComboBox update(String name) {
JComboBox tmp = new JComboBox();
//Read Content from XML file (University is bigger than Year)
NodeList nList = doc.getElementsByTagName("University");
System.out.println("Inside Fn " + name);
for(int i = 0 ; i < nList.getLength();i++) {
Element el = (Element)nList.item(i);
if(name.contentEquals(el.getAttributeNode("name").getNodeValue()))
{
NodeList tmpyList = el.getElementsByTagName("Year");
for(int j = 0 ; j < tmpyList.getLength();j++)
{
Element yl = (Element)tmpyList.item(j);
System.out.println(yl.getAttribute("yr"));
tmp.addItem(yl.getAttribute("yr"));
}
}
}
return tmp; //Return ComboBox to combo2
}
Thank you for your kindness, I try to use your code but it is not work (It still not update), please help me
This is my constructor
public JFrameExample() {
String[] comboboxdefault = { "Select" };
JComboBox combo1 = Universitylist();
JComboBox combo2 = new JComboBox(comboboxdefault);
JComboBox combo3 = new JComboBox(comboboxdefault);
uList.addActionListener(this);
yList.addActionListener(this);
dList.addActionListener(this);
JPanel student_information = new JPanel(new GridLayout(0,1));
uList.setName("University List");
yList.setName("Year List");
// University List
student_information.add(combo1);
// Database Year List
student_information.add(combo2);
// Programme List
student_information.add(combo3);
//Add Components to this container, using the default FlowLayout.
add(student_information);
}
This is the combo2 Update it is return String Array
protected String[] updateyList(String name)
{
String[] tmp = null;
//Read from XML file
for(int i = 0 ; i < nList.getLength();i++) {
Element el = (Element)nList.item(i);
if(name.contentEquals(el.getAttributeNode("name").getNodeValue()))
{
NodeList tmpyList = el.getElementsByTagName("Year");
tmp = new String[tmpyList.getLength()];
for(int j = 0 ; j < tmpyList.getLength();j++)
{
Element yl = (Element)tmpyList.item(j);
//Add to String Array
tmp[j] = yl.getAttribute("yr");
}
}
}
return tmp;
}
In the Action Perform
public void actionPerformed(ActionEvent e) {
JComboBox cb = (JComboBox)e.getSource();
String uname1 = (String)cb.getSelectedItem();
System.out.println(cb.getName()); // To make sure I got the combo1.
try {
//I change to the model method
DefaultComboBoxModel model = new DefaultComboBoxModel( updateyList(uname1) );
System.out.println(model.getSize());
combo2 = new JComboBox(); // If I don't have this line it will throw error Exception in thread "AWT-EventQueue-0" java.lang.NullPointerException
combo2.setModel(model);
} catch (ParserConfigurationException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
} catch (SAXException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
} catch (IOException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
}
And this is for creating GUI function
private static void createAndShowLoginGUI() {
//Create and set up the window.
JFrame frame = new JFrame("Login");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
//Create and set up the content pane.
JFrameExample newContentPane = new JFrameExample();
newContentPane.setOpaque(true); //content panes must be opaque
frame.setContentPane(newContentPane);
//Display the window.
frame.pack();
frame.setVisible(true);
}
This is main function
public static void main(String[] args)
{
//Schedule a job for the event-dispatching thread:
//creating and showing this application's GUI.
javax.swing.SwingUtilities.invokeLater(new Runnable() {
public void run() {
createAndShowLoginGUI();
}
});
}
I think I did something wrong but I don't know where

There is no need to use the updateUI() method.
If you want to change the data in the second combo box then you should change the model (DON'T create a new combo box):
comboBox2.setModel(...);
It will repaint itself automaitcally. You can create a DefaultComboBoxModel and add the data directly to it.
Edit:
import java.awt.*;
import java.awt.event.*;
import java.util.*;
import javax.swing.*;
public class ComboBoxTwo extends JFrame implements ActionListener
{
private JComboBox mainComboBox;
private JComboBox subComboBox;
private Hashtable subItems = new Hashtable();
public ComboBoxTwo()
{
String[] items = { "Select Item", "Color", "Shape", "Fruit" };
mainComboBox = new JComboBox( items );
mainComboBox.addActionListener( this );
// prevent action events from being fired when the up/down arrow keys are used
mainComboBox.putClientProperty("JComboBox.isTableCellEditor", Boolean.TRUE);
getContentPane().add( mainComboBox, BorderLayout.WEST );
// Create sub combo box with multiple models
subComboBox = new JComboBox();
subComboBox.setPrototypeDisplayValue("XXXXXXXXXX"); // JDK1.4
getContentPane().add( subComboBox, BorderLayout.EAST );
String[] subItems1 = { "Select Color", "Red", "Blue", "Green" };
subItems.put(items[1], subItems1);
String[] subItems2 = { "Select Shape", "Circle", "Square", "Triangle" };
subItems.put(items[2], subItems2);
String[] subItems3 = { "Select Fruit", "Apple", "Orange", "Banana" };
subItems.put(items[3], subItems3);
// mainComboBox.setSelectedIndex(1);
}
public void actionPerformed(ActionEvent e)
{
String item = (String)mainComboBox.getSelectedItem();
Object o = subItems.get( item );
if (o == null)
{
subComboBox.setModel( new DefaultComboBoxModel() );
}
else
{
subComboBox.setModel( new DefaultComboBoxModel( (String[])o ) );
}
}
public static void main(String[] args)
{
JFrame frame = new ComboBoxTwo();
frame.setDefaultCloseOperation( EXIT_ON_CLOSE );
frame.pack();
frame.setLocationRelativeTo( null );
frame.setVisible( true );
}
}

As you do now, you recreate the combo box every time (by returning the tmp in update method). This as it seems is not reflecting in the UI and maybe others will post the reason. But if you can change to update the combo values (changing the model or deleting the current values and adding the new ones) instead of recreating, then the following post can help you Dynamically change JComboBox

Related

Is possible that a JCombobox has 2 ItemListeners?

I have 3 JComboBoxes. The first shows the school year of a kid. The second shows the class of the kid and the third shows the children of that school year and of that class. I want that when I select an option of the first JComboBox, at the second JComboBox appears one option or another (depending of the selection of the first JComboBox). The problem is that also, I want select an option in the second JComboBox and in the third appears one option or another (depending of the selection of the second JComboBox). I have tried it a lot and I don't know how to do it. I have tried actionlisteners too, but it didn't work. Please, I'd appreciate any help.
Here is an example that shows how you can populate a second combo box based on the selection in the first combo box:
import java.awt.*;
import java.awt.event.*;
import java.util.*;
import javax.swing.*;
public class ComboBoxTwo extends JPanel implements ActionListener
{
private JComboBox<String> mainComboBox;
private JComboBox<String> subComboBox;
private Hashtable<String, String[]> subItems = new Hashtable<String, String[]>();
public ComboBoxTwo()
{
String[] items = { "Select Item", "Color", "Shape", "Fruit" };
mainComboBox = new JComboBox<String>( items );
mainComboBox.addActionListener( this );
// prevent action events from being fired when the up/down arrow keys are used
mainComboBox.putClientProperty("JComboBox.isTableCellEditor", Boolean.TRUE);
add( mainComboBox );
// Create sub combo box with multiple models
subComboBox = new JComboBox<String>();
subComboBox.setPrototypeDisplayValue("XXXXXXXXXX"); // JDK1.4
add( subComboBox );
String[] subItems1 = { "Select Color", "Red", "Blue", "Green" };
subItems.put(items[1], subItems1);
String[] subItems2 = { "Select Shape", "Circle", "Square", "Triangle" };
subItems.put(items[2], subItems2);
String[] subItems3 = { "Select Fruit", "Apple", "Orange", "Banana" };
subItems.put(items[3], subItems3);
}
public void actionPerformed(ActionEvent e)
{
String item = (String)mainComboBox.getSelectedItem();
Object o = subItems.get( item );
if (o == null)
{
subComboBox.setModel( new DefaultComboBoxModel() );
}
else
{
subComboBox.setModel( new DefaultComboBoxModel( (String[])o ) );
}
}
private static void createAndShowUI()
{
JFrame frame = new JFrame("SSCCE");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add( new ComboBoxTwo() );
frame.setLocationByPlatform( true );
frame.pack();
frame.setVisible( true );
}
public static void main(String[] args)
{
EventQueue.invokeLater(new Runnable()
{
public void run()
{
createAndShowUI();
}
});
}
}
I'm going to try to explain a little my code. I receive for another class a JSon object, because the information is in a database. The other classes are ClasInf and StudentsInf. It's a JSon object so I have to get the object and then change it to a String, for put it on the jcombobox. All the JCombobox are in the same class. Please if you don't understand something tell me it. I have tried to translate the whole answer
This is my first JCombobox.
for(int c=0;c<arrayClassroom.size();c++){
JsonObject clas = arrayClassroom.getJsonObject(c);
comboBoxYear.addItem(clas.getString("name"));
}
And this is the second and the third
ItemListener itemlistener= new ItemListener() {
public void itemStateChanged(ItemEvent eventCombo){
comboBoxYear.removeAllItems();
comboBoxYear.addItem("Class");
clase = new ClasInf();
String cursoPru = comboBoxYear.getSelectedItem().toString();
arrayClas = clase.getclase(cursoPru);
for(int c=0;c<arrayClas.size();c++){
JsonObject curso = arrayClas.getJsonObject(c);
comboBoxYear.addItem(curso.getString("name_class"));
}
comboBoxStudents.removeAllItems();
comboBoxStudents.addItem("Students");
students= new StudentsInf();
String clases = comboBoxClase.getSelectedItem().toString();
arrayStudent = student.getStudent(clases);
for(int j=0;j<arrayStudent.size();j++){
JsonObject clase = arrayStudent.getJsonObject(j);
comboBoxStudents.addItem(clase.getString("nombre"));
}
}
};
comboBoxYear.addItemListener(itemlistener);

Trouble with listener in Java. I have a drop down box not passing the users selection like I need

I have a project for class due this Wednesday and am having trouble with a few things: I have two if else statements that control the values presented in two different drop down menus. To me, it appears I'm not getting the information of of the previous drop down(there are two drop downs in which affects the values presented in the next).
Here's my code thus far:
///Occupancy///
JLabel label2 = new JLabel("Please Select the Number of Occupants");
JComboBox occupancy_list = new JComboBox(occupancy_string);
occupancy_list.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent event)//Listener for Occupancy Drop Down
{
JComboBox cb = (JComboBox)event.getSource(); //grab the user selection
String selection = (String) cb.getSelectedItem();
int number = Integer.parseInt((String) selection);
}
});
String selection = (String) occupancy_list.getSelectedItem();
int number = Integer.parseInt((String) selection);
if(number>2)
{
style=(style2);
}
else
{
style=(style1);
}
///Room Type///
JLabel label3 = new JLabel("Please Select a Room Style");
//Creates RoomStyle Drop Down
JComboBox room_type = new JComboBox(style);
roomtype_string=(String) room_type.getSelectedItem();
room_type.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent event)//Listener for Room Style Drop Down
{
JComboBox cb = (JComboBox)event.getSource(); //grab the user selection
String selection = (String) cb.getSelectedItem();
}
});
String selection2 = (String) room_type.getSelectedItem();
if(selection2.equals("Cabin"))
{
room_number=(cabin_string);
}
else
{
room_number=(suite_string);
}
///Room Selection///
JLabel label4 = new JLabel("Please Select a Room");
//Creates RoomNumber Drop Down
JComboBox room_list = new JComboBox(room_number);
roomselected = (String) room_list.getSelectedItem();
room_list.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent event)//Listener for Occupancy Drop Down
{
JComboBox cb = (JComboBox)event.getSource(); //grab the user selection
String selection = (String) cb.getSelectedItem();
}
});
String selection3 = (String) room_list.getSelectedItem();
//Dining
JLabel label5 = new JLabel("Please Select a Dining Time");
JComboBox dining_list = new JComboBox(dining_string);
dining_list.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent event)//Listener for Occupancy Drop Down
{
JComboBox cb = (JComboBox)event.getSource(); //grab the user selection
String selection = (String) cb.getSelectedItem();
}
});
String selection4 = (String) dining_list.getSelectedItem();
NOTE: I have since rewritten my code, still no dice:
` //Creates subPanel2 with Occupancy, Room Type, Room, and Dining Time request
JPanel subpanel = new JPanel();
///Occupancy///
JLabel label2 = new JLabel("Please Select the Number of Occupants");
JComboBox occupancy_list = new JComboBox(occupancy_string);
Occupancy_Listener occupancy = new Occupancy_Listener();
occupancy_list.addActionListener(occupancy);
//updateStyle(occupancy_string[occupancy_list.getSelectedIndex()]);
///Room Type///
JLabel label3 = new JLabel("Please Select a Room Style");
//Creates RoomStyle Drop Down
JComboBox room_type = new JComboBox(style);
Style_Listener styleListen = new Style_Listener();
room_type.addActionListener(styleListen);
//updateNumber(style[room_type.getSelectedIndex()]);
///Room Selection///
JLabel label4 = new JLabel("Please Select a Room");
//Creates RoomNumber Drop Down
JComboBox room_list = new JComboBox(room_number);
Room_Listener room = new Room_Listener();
room_list.addActionListener(room);
//updateRoom(room_number[room_list.getSelectedIndex()]);
//Dining
JLabel label5 = new JLabel("Please Select a Dining Time");
JComboBox dining_list = new JComboBox(dining_string);
Din_Listener dining = new Din_Listener();
dining_list.addActionListener(dining);
//updateDin(dining_string[dining_list.getSelectedIndex()]);
...
...
...
...
...
}
private class Occupancy_Listener implements ActionListener
{
public void actionPerformed(ActionEvent event)//Listener for Occupancy Drop Down
{
JComboBox cb = (JComboBox)event.getSource(); //grab the user selection
String selection = (String) cb.getSelectedItem();
System.out.println(selection);
System.out.println(style[0]);
System.out.println(room_number[0]);
updateStyle(selection);
}
}
private class Style_Listener implements ActionListener
{
public void actionPerformed(ActionEvent event)//Listener for Occupancy Drop Down
{
JComboBox cb = (JComboBox)event.getSource(); //grab the user selection
String selection = (String) cb.getSelectedItem();
updateNumber(selection);
}
}
private class Room_Listener implements ActionListener
{
public void actionPerformed(ActionEvent event)//Listener for Occupancy Drop Down
{
JComboBox cb = (JComboBox)event.getSource(); //grab the user selection
String selection = (String) cb.getSelectedItem();
updateRoom(selection);
}
}
private class Din_Listener implements ActionListener
{
public void actionPerformed(ActionEvent event)//Listener for Occupancy Drop Down
{
JComboBox cb = (JComboBox)event.getSource(); //grab the user selection
String selection = (String) cb.getSelectedItem();
updateDin(selection);
}
}
protected void updateStyle(String pick)
{
String[] style1 ={"Cabin", "Suite"};
String[] style2 ={"Suite"};
//ocu_string=pick;
number = Integer.parseInt(pick);
if(number>2)
{
style=style2;
}
else
{
style=style1;
}
}
protected void updateNumber(String pick)
{
String[] cabin_string = {"11-1","11-2","11-3","11-4","11-5","11-6","11-7","11-8","11-9","11-10"};
String[] suite_string = {"11-S1","11-S2"};
type=pick;
if(type.equals("cabin"))
{
room_number=cabin_string;
}
else
{
room_number=suite_string;
}
}
protected void updateRoom(String pick)
{
room_num=pick;
}
protected void updateDin(String pick)
{
din_time=pick;
}
//public String getPopulation()
{
//return ocu_string;
}
This might be what your are asking. You select an item from the first combo box and it populates items in a second combo box:
import java.awt.*;
import java.awt.event.*;
import java.util.*;
import javax.swing.*;
public class ComboBoxTwo extends JPanel implements ActionListener
{
private JComboBox<String> mainComboBox;
private JComboBox<String> subComboBox;
private Hashtable<String, String[]> subItems = new Hashtable<String, String[]>();
public ComboBoxTwo()
{
String[] items = { "Select Item", "Color", "Shape", "Fruit" };
mainComboBox = new JComboBox<String>( items );
mainComboBox.addActionListener( this );
// prevent action events from being fired when the up/down arrow keys are used
mainComboBox.putClientProperty("JComboBox.isTableCellEditor", Boolean.TRUE);
add( mainComboBox );
// Create sub combo box with multiple models
subComboBox = new JComboBox<String>();
subComboBox.setPrototypeDisplayValue("XXXXXXXXXX"); // JDK1.4
add( subComboBox );
String[] subItems1 = { "Select Color", "Red", "Blue", "Green" };
subItems.put(items[1], subItems1);
String[] subItems2 = { "Select Shape", "Circle", "Square", "Triangle" };
subItems.put(items[2], subItems2);
String[] subItems3 = { "Select Fruit", "Apple", "Orange", "Banana" };
subItems.put(items[3], subItems3);
}
public void actionPerformed(ActionEvent e)
{
String item = (String)mainComboBox.getSelectedItem();
Object o = subItems.get( item );
if (o == null)
{
subComboBox.setModel( new DefaultComboBoxModel() );
}
else
{
subComboBox.setModel( new DefaultComboBoxModel( (String[])o ) );
}
}
private static void createAndShowUI()
{
JFrame frame = new JFrame("SSCCE");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add( new ComboBoxTwo() );
frame.setLocationByPlatform( true );
frame.pack();
frame.setVisible( true );
}
public static void main(String[] args)
{
EventQueue.invokeLater(new Runnable()
{
public void run()
{
createAndShowUI();
}
});
}
}
You may be confused by the fact that code inside anonymous classes (or local classes) is not executed at the same time as the code around it.
So in a code that looks like:
A a = new A();
a.setSomething( new B() {
public void bMethod() {
// Run stuff
}
} );
C c = a.getSomething();
The "Run stuff" part is not ran now. An object is created, with a method that can be used later inside it, and that object is passed into a. The method is not going to run until something specifically calls it. When you get to the getSomething(), the "Run stuff" part has not run.
So in your code:
JComboBox occupancy_list = new JComboBox(occupancy_string);
occupancy_list.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent event)//Listener for Occupancy Drop Down
{
JComboBox cb = (JComboBox)event.getSource(); //grab the user selection
String selection = (String) cb.getSelectedItem();
int number = Integer.parseInt((String) selection);
}
});
String selection = (String) occupancy_list.getSelectedItem();
You create the occupancy list, you create an action listener for it, and store that action listener inside your occupancy list. But none of the stuff written inside the actionPerformed() method is going to run until the GUI is displayed, the user selects something, and the event is fired.
GUI programming is different than console programming where you call "scan()" and then the program just stops and waits for something to be entered. You first prepare the GUI, and when you display it, the various listeners are called based on what the user does.
So your code jumps straight to the occupancy_list.getSelectedItem() before the list has even been added to the GUI, and of course, nothing is selected, nothing is displayed, yet, so the other drop-down lists are created way before the user even sees the GUI.
This is true for all the action listeners in the code.
The proper way to write an action listener is to think what will be the conditions when the GUI is already running. Your action listeners merely set values in local variables that are going to be discarded. Instead, they should do the things that you want to do when the user makes a selection, right inside the action listener.
This means that the action listener for this combo box will have to create the other lists and add them to the GUI, revalidate and repaint it. Or it may simply modify the other lists which will be created already, depending on what you think is best. But they will have to access those lists, and therefore the lists have to be defined as fields of the surrounding class, and accessed inside the action listener. Note that you can also define a method that does this and call it from inside the action listener.
My suggestion would be to create a simple GUI first with just the first combo box and make it change something simple based on the selection. You can follow the Oracle Tutorial, for example. After you understand how to write an action listener that changes something simple, expand your program to add the other lists and manipulate them from the action listener.

Why won't JTable with DefaultTableModel Refreshed?

basically what i am trying to do is, i have a JList which contain a list of available drive, if one of that drive selected by user then i will show all html files which located in selected drive in a JTable, so i put an event listener for my JList and then i create a JTable and put all data there and show it in the container. the code look like this:
static class HtmlListing implements ListSelectionListener
{
public void valueChanged(ListSelectionEvent event)
{
if (!event.getValueIsAdjusting())
{ //trying to remove and re-add controls in container.
EastCont.removeAll();
globarr = new ArrayList<File>(); // global variable
FileListing fl = new FileListing();
fl.walk(fileList1.getSelectedValue() + "work\\airasia\\html", 500, 0);
//if(globarr.size() > 0)
//{
Object[][] data = new Object[globarr.size()][globarr.size()];
for(int i = 0; i < globarr.size(); i++)
{
if(globarr.get(i).isFile())
{
String filename = globarr.get(i).getName().toString();
String date = sdf.format(globarr.get(i).lastModified());
Object[] obj = new Object[] {filename, filename.substring(filename.lastIndexOf(".") + 1), date, globarr.get(i).getAbsolutePath()};
data[i] = obj;
}
}
Object[] column = new Object[]{"name ", "type", "date modified", "path"};
DefaultTableModel model = new DefaultTableModel(data, column);
model.fireTableDataChanged();
table = new JTable(model)
{
private static final long serialVersionUID = 1L;
public boolean isCellEditable(int row, int column)
{
return false;
};
};
table.addMouseListener(new MouseAdapter()
{
public void mouseClicked(MouseEvent e)
{
if (e.getClickCount() == 2)
{
int rowIdx = table.getSelectedRow(); // path to your new file
TableModel tm = table.getModel();
String path = tm.getValueAt(rowIdx, 3).toString();
File htmlFile = new File(path);
try // open the default web browser for the HTML page
{
Desktop.getDesktop().browse(htmlFile.toURI());
//Desktop.getDesktop().open(htmlFile);
}
catch (IOException e1)
{
// TODO Auto-generated catch block
e1.printStackTrace();
}
}
}
});
table.removeColumn(table.getColumnModel().getColumn(3)); //hide column path from display
table.setFillsViewportHeight(true);
table.setIntercellSpacing(new Dimension(0, 5));
table.setShowGrid(false);
scrollPane = new JScrollPane(table);
EastCont = new JPanel();
EastCont.setLayout(new BorderLayout());
EastCont.add(scrollPane);
EastCont.setPreferredSize(new Dimension(1050, 1000));
//EastCont.repaint();
//EastCont.revalidate();
gui.add(EastCont, BorderLayout.EAST);
gui.revalidate();
gui.repaint();
// }
// else
// {
// EastCont.remove(table);
// gui.remove(EastCont);
// gui.revalidate();
// gui.repaint();
// }
}
this code work only for first time, but does not working for second time and so on, so what i miss here? any help would be great. thank you.
DefaultTableModel model = new DefaultTableModel(data, column);
//model.fireTableDataChanged();
//table = new JTable(model)
table.setModel( model );
Don't create a new table change reset the model of your current table. The rest of the code in that method is not necessary either since you are not creating any new GUI components.
Also, never invoke a fireXXX method. That is the responsibility of the TableModel.

JComboBox show value

Need help with JComboBox component. I've load data from MySQL database and write this data into combo. I use four combo boxes with ItemListener. When one combo box change all children combo boxes reload data from database. First and two works fine but third and four don't show value normal, but good value is there. Only I don't show it. When I select empty field in combo box after then I see good result.
Source code:
public class Vyhladat extends Okno {
private static final long serialVersionUID = 1L;
JComboBox nominalBOX,statBOX,podpisBOX,tlacDoskaBOX;
Font sherif = new Font("Sherif",Font.BOLD,20);
Font normal = new Font("Sherif",Font.PLAIN,20);
JFrame uh = new JFrame();
private String adresa="jdbc:mysql://localhost:3306/jarodb";
private String meno="JKARAK";
private String heslo="bankovka";
String nominal,stat,podpis,tlacDoska,statH;
private String nominalSQL = "SELECT DISTINCT(nominal) FROM prehlad";
private String statSQL = "SELECT DISTINCT(concat(stat,'/',seria)) FROM prehlad WHERE nominal=? ORDER BY stat";
private String podpisSQL = "SELECT DISTINCT(podpis) FROM prehlad WHERE nominal=? AND stat=? ";
private String tlacDoskaSQL = "SELECT DISTINCT(doska) FROM prehlad WHERE nominal=? AND stat=? AND podpis=? ";
Vector nominalV=new Vector();
Vector statV=new Vector();
Vector podpisV=new Vector();
Vector tlacDoskaV=new Vector();
Vyhladat()
{
vlozPopis(nominalLAB,"NOMIN\u00C1L EUROBANKOVKY: ",0,0,sherif);
vlozPopis(statLAB,"\u0160T\u00C1T/S\u00C9RIA:",0,1,sherif);
vlozPopis(podpisLAB,"PODPIS:",0,2,sherif);
vlozPopis(tlacDoskaLAB,"TLA\u010COV\u00C1 DOSKA:",0,3,sherif);
gbc.gridx=1;
gbc.gridy=0;
nacitajVyber(nominalSQL,nominalBOX,nominalV,false,false,false);
nominalBOX = new JComboBox(nominalV);
nominalBOX.addItemListener(new ItemListener()
{
public void itemStateChanged(ItemEvent e)
{
nominal = (String)nominalBOX.getSelectedItem();
if(nominal!=" ")
{
nacitajVyber(statSQL,statBOX,statV,true,false,false);
}
else{
statBOX.removeAllItems();
podpisBOX.removeAllItems();
tlacDoskaBOX.removeAllItems();
}
}
});
nominalBOX.setPrototypeDisplayValue("500");
nominalBOX.setFont(normal);
nominalBOX.setSelectedIndex(0);
nominalBOX.setToolTipText("Vyber z mo\u017Enost\u00ED nomin\u00E1lu bankoviek 5,10,20,50.");
add(nominalBOX,gbc);
gbc.gridx=1;
gbc.gridy=1;
statV.add(" ");
statBOX= new JComboBox(statV);
statBOX.addItemListener(new ItemListener()
{
public void itemStateChanged(ItemEvent e)
{
stat = (String)statBOX.getSelectedItem();
if(stat!=null)
{
String [] statM= stat.split("/");
statH = statM[0];
}
if(stat!=" " & stat!=null)
{
nacitajVyber(podpisSQL,podpisBOX,podpisV,false,true,false);
}
else{
podpisBOX.removeAllItems();
tlacDoskaBOX.removeAllItems();
}
}
});
statBOX.setPrototypeDisplayValue("Portugalsko/E");
statBOX.setFont(normal);
statBOX.setSelectedIndex(0);
statBOX.setToolTipText("Vyber z mo\u017Enost\u00ED \u0161t\u00E1t/s\u00E9riu.");
add(statBOX,gbc);
gbc.gridx=1;
gbc.gridy=2;
podpisV.add(" ");
podpisBOX = new JComboBox(podpisV);
podpisBOX.addItemListener(new ItemListener()
{
public void itemStateChanged(ItemEvent e)
{
podpis = (String)podpisBOX.getSelectedItem();
if(podpis!=" " & podpis!=null)
{
nacitajVyber(tlacDoskaSQL,tlacDoskaBOX,tlacDoskaV,false,false,true);
}
else{
tlacDoskaBOX.removeAllItems();
}
}
});
podpisBOX.setPrototypeDisplayValue("Jean-Claude Trichet ");
podpisBOX.setFont(normal);
podpisBOX.setSelectedIndex(0);
podpisBOX.setToolTipText("Vyber z mo\u017Enost\u00ED troch podpisov.");
add(podpisBOX,gbc);
gbc.gridx=1;
gbc.gridy=3;
tlacDoskaV.add(" ");
tlacDoskaBOX = new JComboBox(tlacDoskaV);
tlacDoskaBOX.addItemListener(new ItemListener()
{
public void itemStateChanged(ItemEvent e)
{
tlacDoska = (String)tlacDoskaBOX.getSelectedItem();
if((nominal!=" " & nominal!=null) & (statH!=" " & statH!=null) & (podpis!=" " & podpis!=null) & (tlacDoska!=" " & tlacDoska!=null))
{
zobraz.setEnabled(true);
}
}
});
tlacDoskaBOX.setPrototypeDisplayValue("E010");
tlacDoskaBOX.setFont(normal);
tlacDoskaBOX.setSelectedIndex(0);
tlacDoskaBOX.setToolTipText("Vyber z mo\u017Enost\u00ED tla\u010Dov\u00FDch dosiek.");
add(tlacDoskaBOX,gbc);
}
private void nacitajVyber(String sqlDotaz, JComboBox chr,Vector v,
boolean jedna,boolean dva, boolean tri)
{
try
{
Class.forName("com.mysql.jdbc.Driver");
Connection conn = DriverManager.getConnection(adresa,meno,heslo);
PreparedStatement stmt = conn.prepareStatement(sqlDotaz);
if(jedna==true)
{
chr.removeAllItems();
stmt.setString(1, nominal);
}
if(dva==true)
{
chr.removeAllItems();
stmt.setString(1, nominal);
stmt.setString(2, statH);
}
if(tri==true)
{
chr.removeAllItems();
stmt.setString(1, nominal);
stmt.setString(2, statH);
stmt.setString(3, podpis);
}
ResultSet rs = stmt.executeQuery();
v.addElement(" ");
while (rs.next())
{v.addElement(rs.getString(1).trim());
System.out.println(rs.getString(1));}
validate();
rs.close();
stmt.close();
conn.close();
}
catch(Exception e){
JOptionPane.showMessageDialog(uh,e.toString(),
"Chyba pripojenia",
JOptionPane.ERROR_MESSAGE);
}
}
}
JComboBox doesn't know somehow then underlaying Vector is changed, have to reinitialize this array for JComboBox on the fly, but this is wrong way,
for any changes on the runtime to use XxxComboBoxModel for storing Items for JComboBox
for JDBC or FileIO there could be Concurency issue, Swing JComponents required to all updates (in this case JComboBox and its XxxComboBoxModel) must be done on EDT
invoke Database event from the Runnable#Thread or SwingWorker, redirect this (potentionally) hard and long running task to the Workers Thread, otherwise Swing GUi will be freeze or unresponsive (for mouse and key events) untill JDBC ended
SwingWorkers methods publish(), process() and done() quite good quaranteed that all output wil be done on EDT
for example
import java.awt.*;
import java.awt.event.*;
import java.util.*;
import javax.swing.*;
public class ComboBoxTwo extends JFrame implements ActionListener, ItemListener {
private static final long serialVersionUID = 1L;
private JComboBox mainComboBox;
private JComboBox subComboBox;
private Hashtable<Object, Object> subItems = new Hashtable<Object, Object>();
public ComboBoxTwo() {
String[] items = {"Select Item", "Color", "Shape", "Fruit"};
mainComboBox = new JComboBox(items);
mainComboBox.addActionListener(this);
mainComboBox.addItemListener(this);
//prevent action events from being fired when the up/down arrow keys are used
//mainComboBox.putClientProperty("JComboBox.isTableCellEditor", Boolean.TRUE);
getContentPane().add(mainComboBox, BorderLayout.WEST);
subComboBox = new JComboBox();// Create sub combo box with multiple models
subComboBox.setPrototypeDisplayValue("XXXXXXXXXX"); // JDK1.4
subComboBox.addItemListener(this);
getContentPane().add(subComboBox, BorderLayout.EAST);
String[] subItems1 = {"Select Color", "Red", "Blue", "Green"};
subItems.put(items[1], subItems1);
String[] subItems2 = {"Select Shape", "Circle", "Square", "Triangle"};
subItems.put(items[2], subItems2);
String[] subItems3 = {"Select Fruit", "Apple", "Orange", "Banana"};
subItems.put(items[3], subItems3);
// mainComboBox.setSelectedIndex(1);
}
#Override
public void actionPerformed(ActionEvent e) {
String item = (String) mainComboBox.getSelectedItem();
Object o = subItems.get(item);
if (o == null) {
subComboBox.setModel(new DefaultComboBoxModel());
} else {
subComboBox.setModel(new DefaultComboBoxModel((String[]) o));
}
}
#Override
public void itemStateChanged(ItemEvent e) {
if (e.getStateChange() == ItemEvent.SELECTED) {
if (e.getSource() == mainComboBox) {
if (mainComboBox.getSelectedIndex() != 0) {
FirstDialog firstDialog = new FirstDialog(ComboBoxTwo.this,
mainComboBox.getSelectedItem().toString(), "Please wait, Searching for ..... ");
}
}
}
}
private class FirstDialog extends JDialog { //sipmle simulation of JDBC events, by using Swing Timer
private static final long serialVersionUID = 1L;
FirstDialog(final Frame parent, String winTitle, String msgString) {
super(parent, winTitle);
setModalityType(Dialog.ModalityType.APPLICATION_MODAL);
JLabel myLabel = new JLabel(msgString);
JButton bNext = new JButton("Stop Processes");
add(myLabel, BorderLayout.CENTER);
add(bNext, BorderLayout.SOUTH);
bNext.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent evt) {
setVisible(false);
}
});
javax.swing.Timer t = new javax.swing.Timer(1000, new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
setVisible(false);
}
});
t.setRepeats(false);
t.start();
setLocationRelativeTo(parent);
setSize(new Dimension(400, 100));
setVisible(true);
}
}
public static void main(String[] args) {
JFrame frame = new ComboBoxTwo();
frame.setDefaultCloseOperation(EXIT_ON_CLOSE);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
}
The GUI probably can't redraw properly. You are doing all of your hard work on the Event Dispatch Thread. This thread calls your itemStateChanged. But this thread is also responsible for redrawing the GUI. You are stopping it from doing that, because you are making it do your hard work in the database.
Instead, you can use a different thread to do your hard work.
public void itemStateChanged(ItemEvent e)
{
new Thread(new Runnable() {
public void run() {
.... your code...
}
}).start();
}
Or take a look at SwingWorker, which does this in a nicer way.
Also, itemStateChanged could be called twice for each selection - this might be causing you problems. Use "e.getStateChange()" to check what TYPE of event you just received. You should receive a selected and an unselected (from the old item).

Java Swing Combobox removeAllItems calling ItemStateChanged also?

My code is quite simple actually. I saw a simple and similar code was from this article.
At first, I have 1 combobox. I have a listener on it called itemStateChanged(). My purpose to add into this listener is that; "to execute some code when user click (select) an item from its dropbox".
Cmb_ItemCategory = new javax.swing.JComboBox();
Cmb_ItemCategory.setModel(new javax.swing.DefaultComboBoxModel(new String[] { "Loading..." }));
Cmb_ItemCategory.addItemListener(new java.awt.event.ItemListener() {
public void itemStateChanged(java.awt.event.ItemEvent evt) {
Cmb_ItemCategoryItemStateChanged(evt);
}
});
private void Cmb_ItemCategoryItemStateChanged(java.awt.event.ItemEvent evt) {
if(evt.getStateChange() == java.awt.event.ItemEvent.SELECTED){
System.err.println("Sombody click or change my model content");
}
}
Behind the code, I grab some data, and then calling a method of removeAllItems() .
And then I set a new Model (from new data) into it.
-- at another line of code ---
Cmb_ItemCategory.removeAllItems();
Cmb_ItemCategory.setModel(newModel);
I juz realized that my itemStateChanged() is called when i do the removeAllItem() method. called once.
So, How to make it only called once user Click (select) only AND not when removeAllItems() called?
it similar to this article. But it's not removingItems case. CMIIW.
Here check this code out, this works flawlessly, might be you doing something wrong where you calling removeAllItems() :
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class ComboState
{
private void createAndDisplayGUI()
{
JFrame frame = new JFrame("Combo State Testing : ");
frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
final JComboBox cbox = new JComboBox();
cbox.addItem("One");
cbox.addItem("Two");
cbox.addItem("Three");
cbox.addItem("Four");
cbox.addItemListener(new ItemListener()
{
public void itemStateChanged(ItemEvent ie)
{
if (ie.getStateChange() == ItemEvent.SELECTED)
{
System.out.println("Item Selected is : " + ie.getItem());
}
/*else
{
System.out.println("I am called for other reasons.");
}*/
}
});
/*
* Click me to remove JComboBox's items.
*/
JButton removeButton = new JButton("REMOVE");
removeButton.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent ae)
{
cbox.removeAllItems();
}
});
frame.add(cbox, BorderLayout.CENTER);
frame.add(removeButton, BorderLayout.PAGE_END);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new ComboState().createAndDisplayGUI();
}
});
}
}
As nIcE cOw already illustrated in his example, it should certainly work when you use a DefaultComboBoxModel (which is the case in his sample code, although it happens behind the screens).
I could explain the behavior you encounter for the non-DefaultComboBoxModel case, although your code snippet suggests you use one. Looking at the source code for JComboBox#removeAllItems there is a different code path since the removeAllElements method is not part of the MutableComboBoxModel interface
public void removeAllItems() {
checkMutableComboBoxModel();
MutableComboBoxModel<E> model = (MutableComboBoxModel<E>)dataModel;
int size = model.getSize();
if ( model instanceof DefaultComboBoxModel ) {
((DefaultComboBoxModel)model).removeAllElements();
}
else {
for ( int i = 0; i < size; ++i ) {
E element = model.getElementAt( 0 );
model.removeElement( element );
}
}
selectedItemReminder = null;
if (isEditable()) {
editor.setItem(null);
}
}
So with a non-DefaultComboBoxModel you are going to remove the items one by one. This means that at a certain point in time, you will remove the selected element. A possible implementation of your model might change the selected element at that point. If you look for example at the implementation in DefaultComboBoxModel (although this code will not be triggered) you can clearly see it changes the selection.
public void removeElementAt(int index) {
if ( getElementAt( index ) == selectedObject ) {
if ( index == 0 ) {
setSelectedItem( getSize() == 1 ? null : getElementAt( index + 1 ) );
}
else {
setSelectedItem( getElementAt( index - 1 ) );
}
}
objects.removeElementAt(index);
fireIntervalRemoved(this, index, index);
}
Perhaps your model does something similar, which explains the event. Just for making this post complete, the code behind the DefaultComboBoxModel#removeAllElements where you can clearly see it sets the selection to null and does not select another object. Only weird thing in that code is that it does not fire a DESELECTED event first, although you know the selection has changed if you listen for the intervalRemoved event ... but that is not really relevant to your problem
public void removeAllElements() {
if ( objects.size() > 0 ) {
int firstIndex = 0;
int lastIndex = objects.size() - 1;
objects.removeAllElements();
selectedObject = null;
fireIntervalRemoved(this, firstIndex, lastIndex);
} else {
selectedObject = null;
}
}
So to conclude: I say the solution for your problem is located in your model, and not in the code you posted
One quick way to do is to have a bool set to true before you call removeAllItem() and back false after. Execute the code in your itemStateChanged() only if the bool variable is false.
Ideally you could override the removeAllItem() function.
not clear from whole discusion,
you have to remove all Listener(s) from JComboBox before removing all Items, after Items are removed you can add Listener(s) back,
still not sure if you want to add & remove Items dynamically, or you can set whatever value for another JComponent(s),
(against complicating simple things) did you see there remove,
.
import java.awt.*;
import java.awt.event.*;
import java.util.*;
import javax.swing.*;
public class ComboBoxTwo extends JFrame implements ActionListener, ItemListener {
private static final long serialVersionUID = 1L;
private JComboBox mainComboBox;
private JComboBox subComboBox;
private Hashtable<Object, Object> subItems = new Hashtable<Object, Object>();
public ComboBoxTwo() {
String[] items = {"Select Item", "Color", "Shape", "Fruit"};
mainComboBox = new JComboBox(items);
mainComboBox.addActionListener(this);
mainComboBox.addItemListener(this);
//prevent action events from being fired when the up/down arrow keys are used
//mainComboBox.putClientProperty("JComboBox.isTableCellEditor", Boolean.TRUE);
getContentPane().add(mainComboBox, BorderLayout.WEST);
subComboBox = new JComboBox();// Create sub combo box with multiple models
subComboBox.setPrototypeDisplayValue("XXXXXXXXXX"); // JDK1.4
subComboBox.addItemListener(this);
getContentPane().add(subComboBox, BorderLayout.EAST);
String[] subItems1 = {"Select Color", "Red", "Blue", "Green"};
subItems.put(items[1], subItems1);
String[] subItems2 = {"Select Shape", "Circle", "Square", "Triangle"};
subItems.put(items[2], subItems2);
String[] subItems3 = {"Select Fruit", "Apple", "Orange", "Banana"};
subItems.put(items[3], subItems3);
// mainComboBox.setSelectedIndex(1);
}
#Override
public void actionPerformed(ActionEvent e) {
String item = (String) mainComboBox.getSelectedItem();
Object o = subItems.get(item);
if (o == null) {
subComboBox.setModel(new DefaultComboBoxModel());
} else {
subComboBox.setModel(new DefaultComboBoxModel((String[]) o));
}
}
#Override
public void itemStateChanged(ItemEvent e) {
if (e.getStateChange() == ItemEvent.SELECTED) {
if (e.getSource() == mainComboBox) {
if (mainComboBox.getSelectedIndex() != 0) {
FirstDialog firstDialog = new FirstDialog(ComboBoxTwo.this,
mainComboBox.getSelectedItem().toString(), "Please wait, Searching for ..... ");
}
}
}
}
private class FirstDialog extends JDialog {
private static final long serialVersionUID = 1L;
FirstDialog(final Frame parent, String winTitle, String msgString) {
super(parent, winTitle);
setModalityType(Dialog.ModalityType.APPLICATION_MODAL);
JLabel myLabel = new JLabel(msgString);
JButton bNext = new JButton("Stop Processes");
add(myLabel, BorderLayout.CENTER);
add(bNext, BorderLayout.SOUTH);
bNext.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent evt) {
setVisible(false);
}
});
javax.swing.Timer t = new javax.swing.Timer(1000, new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
setVisible(false);
}
});
t.setRepeats(false);
t.start();
setLocationRelativeTo(parent);
setSize(new Dimension(400, 100));
setVisible(true);
}
}
public static void main(String[] args) {
JFrame frame = new ComboBoxTwo();
frame.setDefaultCloseOperation(EXIT_ON_CLOSE);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
}
The method removeAllItems does not call ItemStateChanged, but it call actionPerformed, you can check it by running this simple code:
public class Tuto {
public static void main(String[] args) {
//create the main frame
JFrame frame = new JFrame();
frame.setResizable(false);
frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
frame.setLayout(null);
frame.setLocation(new Point(10, 10));
frame.setPreferredSize(new Dimension(400, 300));
JComboBox<String> combo = new JComboBox();
combo.addItem("item 1");
combo.addItem("item 2");
combo.addItem("item 3");
combo.setBounds(50, 30, 300, 20);
combo.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent ae) {
System.out.println(" action Performed ");
}
});
frame.add(combo);
JButton button = new JButton("Remove");
button.setBounds(50, 100, 100, 30);
button.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent ae) {
combo.removeAllItems();
}
});
frame.add(button);
frame.pack();
frame.setVisible(true);
}
}

Categories