Reputation: 3
I made the following class which contains information about users - name, age photo.
public class User{
private int age;
private String name;
ImageIcon icon;
JLabel image;
public int getAge() {
return age;
}
public String getName() {
return name;
}
public User(){
this.age = 0;
this.name = "";
}
public User(int age, String name){
this.age = age;
this.name = name;
icon = new ImageIcon(name + ".jpg");
image = new JLabel(icon, JLabel.Center);
}
}
I want to create the set of images with users' faces on JPanel. I want to get details of each user after clicking on his photo. So I put this code in the main class:
MouseListener myClick = new MouseListener(){
@Override
public void mouseClicked(MouseEvent e)
{
User selected = new User();
selected.image = (JLabel) e.getComponent();
System.out.println(selected.getAge() + " " + selected.getName());
}
};
and
User[] users = new User[32];
for (int i = 0; i < 32; i++)
{
panel.add(users[i].image);
users[i].image.addMouseListener(myClick);
}
I know- it is totally wrong. I cannot obtain data about the certain user, because I get values from "selected", which contains only JLabel with image (no values for age or name). What should I do to get the name and age of the certain user?
Upvotes: 0
Views: 120
Reputation: 54649
There are several ways of achieving what you want to do. (I'm not entirely sure what this is, but I'm sure that there are several ways ;-)).
One interesting question might be who determines the bounds of the images / labels. Are they put into a panel that has a certain layout? When they are, for example, contained in a panel with a GridLayout
then you can just compute the index of the image based on the "grid cell" that corresponds to a certain mouse position on the panel. If they are positioned freely (on a panel with null
layout), then you might create a simple map like
class ImageMap<T>
{
private final Map<Rectangle2D, T> map;
ImageMap()
{
map = new LinkedHashMap<Rectangle2D, T>();
}
public T get(double x, double y)
{
for (Entry<Rectangle2D, T> entry : map.entrySet())
{
Rectangle2D key = entry.getKey();
if (key.contains(new Point2D.Double(x,y)))
{
return entry.getValue();
}
}
return null;
}
void setBounds(T t, Rectangle2D r)
{
Rectangle2D copy = new Rectangle2D.Double(
r.getX(), r.getY(), r.getWidth(), r.getHeight());
map.put(copy, t);
}
}
Then you can fill this map with the information from the users:
ImageMap<User> map = new ImageMap<User>();
List<User> users = ...;
for (User user : users)
{
map.setBounds(user, user.getImage().getBounds());
}
And when you receive a mouse event, you can query this
MouseEvent e = ...;
User user = map.get(e.getX(), e.getY());
But whether this is appropriate really depends on your use-case. Maybe a JList with an appropriate CellRenderer would better suit your needs.
Upvotes: 0
Reputation: 324128
Not an answer to the question but:
The constructor of a class, by convention, is defined before the methods of the class.
Why did you create a User class with methods getName()
and getAge()
but you did not define a getImage()
method? Be consistent! You should not access variables directly and should define a "getter" method when you want to access data from a class.
Learn from examples and don't make up your own standards.
To follow up on Andrew's comment, you should create a custom renderer to display the Icon from the User class in a JList. Read the section from the Swing tutorial on Writing a Custom Cell Renderer for more information and an example of displaying an Icon. The example uses a JComboBox, but the concept is the same for a JList.
Then you can use a ListSelectionListener to handle selections of the image. This a better approach because this will work when the user uses the mouse or the keyboard.
Upvotes: 1
Reputation: 53
I had a similiar issue with a game I'm working on, and I made a tilePane class. The TilePane class extends a JPanel and has fields for name, age, photo, etc (or just contains a user field). When a photo is clicked, get the parent tilePane, and then get the tilePane's appropriate field. Here's a snippet of my code:
public void mouseClick(MouseEvent e) {
...
} else if (e.getSource() instanceof TilePane) {
TilePane clickPane = (TilePane) e.getSource();
...
Upvotes: 0