Hangman adding pictures Swing - java

I am 'relatively' new to java creating a Hangman game in Java (Eclipse) using Swing. I have got all the components relating to the word done.
However I want that in the middle of the screen a Hangman image to be shown and when you get a guess wrong it updated with a different image (Of a more complete hangman).
However I am unsure of how to do this, whether I would need ImageIcon or just images and using paintComponent etc. Any Help appreciated, my code is below. I am unsure of how to do it in a efficient method that allows me to change it every time variable guess goes down. Please Suggest a method for doing this and the basics of how it might work.
public class Test extends JTextField {
private JFrame frame;
JTextField userInput;
private JTextField textField;
private String inputString;
private String total="";
private static char[] pass = Hangmangame.word.getPassword();
private static String passString = new String(pass);
private String []wordch = new String[passString.length()];
private String []astri = new String[passString.length()];
private int guess;
private boolean letter = false;
private JTextField txtGuesses;
private JPanel PicturePanel;
public static void start() {
EventQueue.invokeLater(new Runnable() {
public void run() {
try {
Test window = new Test();
window.frame.setVisible(true);
} catch (Exception e) {
e.printStackTrace();
}
}
});
}
public Test() {
initialize();
}
public void initialize() {
for (int i = 0; i < passString.length(); i++) {
astri[i]="*";
wordch[i]=passString.substring(i, i+1);
total =total+ astri[i];
guess =10;
}
//------------------------------------------------
frame = new JFrame();
frame.setBounds(300, 100, 1000, 600);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().setLayout(new BorderLayout(0, 0));
//------------------------------------
JLabel Hangman = new JLabel("Hangman");
Hangman.setFont(new Font("Tahoma", Font.BOLD, 46));
Hangman.setHorizontalAlignment(SwingConstants.CENTER);
frame.getContentPane().add(Hangman, BorderLayout.NORTH);
//----------------------------------
textField = new JTextField(total);
textField.setBorder(null);
textField.setHorizontalAlignment(SwingConstants.CENTER);
textField.setFont(new Font("Tahoma", Font.BOLD, 46));
frame.getContentPane().add(textField, BorderLayout.SOUTH);
textField.setColumns(10);
//------------------------------------------
userInput = new JTextField();
userInput.setBorder(new LineBorder(new Color(0, 0, 0)));
userInput.setFont(new Font("Tahoma", Font.PLAIN, 22));
userInput.setHorizontalAlignment(SwingConstants.CENTER);
frame.getContentPane().add(userInput, BorderLayout.EAST);
userInput.setColumns(10);
TextFieldListener tfListener = new TextFieldListener();
userInput.addActionListener(tfListener);
//----------------------------------------------
txtGuesses = new JTextField();
txtGuesses.setBorder(null);
txtGuesses.setHorizontalAlignment(SwingConstants.LEFT);
txtGuesses.setFont(new Font("Tahoma", Font.BOLD, 20));
txtGuesses.setText("Guesses:"+guess);
frame.getContentPane().add(txtGuesses, BorderLayout.WEST);
txtGuesses.setColumns(10);
//-------------------------------
PicturePanel = new JPanel();
PicturePanel.setBackground(new Color(255, 255, 255));
frame.getContentPane().add(PicturePanel, BorderLayout.CENTER);
//----------------------------------------------
}
public class TextFieldListener implements ActionListener
{ public void actionPerformed(ActionEvent evt)
{ inputString = userInput.getText();
userInput.setText("");
checkcorrect();
}
}
private void checkcorrect() {
//runs it as many times as there are letters
for (int i = 0; i < passString.length(); i++) {
if(wordch[i].equals(inputString)) {
astri[i]=wordch[i];
total="";
// rewrites the *** with the letter added in same as code for setting up the astrixs.
for (int x = 0; x < passString.length(); x++) {
total =total+ astri[x];
}
textField.setText(total);
letter = true;
}
}
if(letter==true) {
letter=false;
}else {
guess=guess-1;
txtGuesses.setText("Guesses:"+guess);
if(guess==0) {
if(JOptionPane.showConfirmDialog(frame,"You Lose","Hangman",
JOptionPane.PLAIN_MESSAGE ) == JOptionPane.YES_OPTION ) {
System.exit(0);
}
}
}
if(total.equals(passString)) {
if(JOptionPane.showConfirmDialog(frame,"You Win","Hangman",
JOptionPane.PLAIN_MESSAGE ) == JOptionPane.YES_NO_OPTION ) {
System.exit(0);
}
}
}
private void Image() {
// My images
ImageIcon icon1 = new ImageIcon("P:\\Profiles\\workspace\\Games\\Images\\files\\0");
ImageIcon icon2 = new ImageIcon("P:\\Profiles\\workspace\\Games\\Images\\files\\1");
ImageIcon icon3 = new ImageIcon("P:\\Profiles\\workspace\\Games\\Images\\files\\2");
ImageIcon icon4 = new ImageIcon("P:\\Profiles\\workspace\\Games\\Images\\files\\3");
ImageIcon icon5 = new ImageIcon("P:\\Profiles\\workspace\\Games\\Images\\files\\4");
ImageIcon icon6 = new ImageIcon("P:\\Profiles\\workspace\\Games\\Images\\files\\5");
ImageIcon icon7 = new ImageIcon("P:\\Profiles\\workspace\\Games\\Images\\files\\6");
ImageIcon icon8 = new ImageIcon("P:\\Profiles\\workspace\\Games\\Images\\files\\7");
ImageIcon icon9 = new ImageIcon("P:\\Profiles\\workspace\\Games\\Images\\files\\8");
ImageIcon icon10 = new ImageIcon("P:\\Profiles\\workspace\\Games\\Images\\files\\9");
ImageIcon icon11 = new ImageIcon("P:\\Profiles\\workspace\\Games\\Images\\files\\10");
}
}

Related

Java Swing GridLayout Change Grid Sizes

I'm trying to create a program that lists movies in a Netflix style to learn Front-End coding.
How I want it to look in the end:
My guess is that every movie is a button component with an image a name label and a release year label.
I'm struggling to recreate this look. This is how it looks when I try it:
The navigationbar in my image is at the page start of a border layout. Below the navigationbar the movie container is in the center of the border layout.
My idea was creating a GridLayout and then create a button for each movie and adding it to the GridLayout.
You can recreate this with this code:
public class Main {
private static JFrame frame;
public static void main(String[] args) throws HeadlessException {
frame = new JFrame();
frame.setLayout(new BorderLayout());
frame.setBackground(new Color(32, 32, 32));
JPanel navigationPanel = createNavigationBar();
frame.add(navigationPanel, BorderLayout.PAGE_START);
JPanel moviePanel = createMoviePanel();
frame.add(moviePanel, BorderLayout.CENTER);
frame.setPreferredSize(new Dimension(1920, 1080));
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setTitle("Example App");
frame.pack();
frame.setExtendedState(JFrame.MAXIMIZED_BOTH);
frame.setVisible(true);
}
public static JPanel createMoviePanel() {
JPanel moviePanel = new JPanel();
GridLayout layout = new GridLayout(0, 10);
layout.setHgap(3);
layout.setVgap(3);
moviePanel.setLayout(layout);
moviePanel.setBackground(new Color(32, 32, 32));
ArrayList<String> exampleList = new ArrayList<>();
// Add stuff to the example list
for(int i = 0; i < 120; i++) {
exampleList.add(Integer.toString(i));
}
final File root = new File("");
for(final String movie : exampleList) {
JLabel picLabel = new JLabel();
try {
File imageFile = new File(root.getAbsolutePath() + "\\src\\images\\" + "imageName.jpg"); // Try to find the cover image
if(imageFile.exists()) {
BufferedImage movieCover = ImageIO.read(imageFile);
picLabel = new JLabel(new ImageIcon(movieCover));
} else {
BufferedImage movieCover = ImageIO.read(new File(root.getAbsolutePath() + "\\src\\images\\temp.jpg")); // Get a temp image
picLabel = new JLabel(new ImageIcon(movieCover));
}
} catch (IOException e) {
e.printStackTrace();
}
JLabel movieName = new JLabel("New Movie");
movieName.setForeground(Color.WHITE);;
JButton movieButton = new JButton();
movieButton.setLayout(new GridLayout(0, 1));
//movieButton.setContentAreaFilled(false);
//movieButton.setBorderPainted(false);
//movieButton.setFocusPainted(false);
movieButton.add(picLabel);
movieButton.add(movieName);
moviePanel.add(movieButton);
}
return moviePanel;
}
public static JPanel createNavigationBar() {
JPanel navBar = new JPanel();
navBar.setLayout(new FlowLayout(FlowLayout.LEFT, 30, 20));
navBar.setBackground(new Color(25, 25, 25));
JButton homeButton = new JButton("Home");
homeButton.setContentAreaFilled(false);
homeButton.setBorderPainted(false);
homeButton.setFocusPainted(false);
JButton movieButton = new JButton("Movies");
movieButton.setContentAreaFilled(false);
movieButton.setBorderPainted(false);
movieButton.setFocusPainted(false);
// Add all the buttons to the navbar
navBar.add(homeButton);
navBar.add(movieButton);
return navBar;
}
}
I noticed that the GridLayout always tries to fit everything onto the window.
All that's needed is a properly configured JButton in a GridLayout.
E.G.
public static JPanel createMoviePanel() {
JPanel movieLibraryPanel = new JPanel(new GridLayout(0, 10, 3, 3));
movieLibraryPanel.setBackground(new Color(132, 132, 132));
int m = 5;
BufferedImage image = new BufferedImage(9 * m, 16 * m, BufferedImage.TYPE_INT_RGB);
for (int ii = 1; ii < 21; ii++) {
JButton picButton = new JButton("Mov " + ii, new ImageIcon(image));
picButton.setMargin(new Insets(0,0,0,0));
picButton.setForeground(Color.WHITE);
picButton.setContentAreaFilled(false);
picButton.setHorizontalTextPosition(JButton.CENTER);
picButton.setVerticalTextPosition(JButton.BOTTOM);
movieLibraryPanel.add(picButton);
}
return movieLibraryPanel;
}
Here is a complete source for the above with a tweak to put the year on a new line. It uses HTML in the JButton to break the button text into two lines.
The input focus is on the first button, whereas the mouse hovers over the '2009' movie:
import java.awt.*;
import java.awt.image.*;
import javax.swing.*;
class MovieGrid {
MovieGrid() {
JFrame f = new JFrame("Movie Grid");
f.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
f.setLocationByPlatform(true);
f.add(createMoviePanel());
f.pack();
f.setVisible(true);
}
public static JPanel createMoviePanel() {
JPanel movieLibraryPanel = new JPanel(new GridLayout(0, 10, 3, 3));
movieLibraryPanel.setBackground(new Color(132, 132, 132));
int m = 5;
BufferedImage image = new BufferedImage(
9 * m, 16 * m, BufferedImage.TYPE_INT_RGB);
for (int ii = 2001; ii < 2021; ii++) {
JButton picButton = new JButton(
"<html>Movie<br>" + ii, new ImageIcon(image));
picButton.setMargin(new Insets(0,0,0,0));
picButton.setForeground(Color.WHITE);
picButton.setContentAreaFilled(false);
picButton.setHorizontalTextPosition(JButton.CENTER);
picButton.setVerticalTextPosition(JButton.BOTTOM);
movieLibraryPanel.add(picButton);
}
return movieLibraryPanel;
}
public static void main(String[] args) {
Runnable r = new Runnable() {
#Override
public void run() {
new MovieGrid();
}
};
SwingUtilities.invokeLater(r);
}
}
Same idea's from Andrew Thompson answer but with some minor text alignment changes and hover effect
final class Testing
{
public static void main(String[] args)
{
JFrame frame=new JFrame("NEFLIX");
frame.setContentPane(new GridDisplay());
frame.pack();
frame.setResizable(false);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
}
private static final class GridDisplay extends JPanel implements ActionListener
{
private GridDisplay()
{
super(new GridLayout(0,5,20,20));
setBackground(new Color(0,0,0,255));
BufferedImage image=new BufferedImage(150,200,BufferedImage.TYPE_INT_RGB);
Graphics2D g2d=(Graphics2D)image.getGraphics();
g2d.setColor(Color.BLUE);
g2d.fillRect(0,0,image.getWidth(),image.getHeight());
HoverPainter painter=new HoverPainter();
for(int i=0;i<10;i++)
{
TVShowCard card=new TVShowCard(image,"Show "+i,"199"+i);
card.addMouseListener(painter);
add(card);
}
}
//highlight only on hover
private final class HoverPainter extends MouseAdapter
{
#Override
public void mouseExited(MouseEvent e) {
((TVShowCard)e.getSource()).setBorderPainted(false);
}
#Override
public void mouseEntered(MouseEvent e) {
((TVShowCard)e.getSource()).setBorderPainted(true);
}
}
private final class TVShowCard extends JButton
{
private TVShowCard(BufferedImage preview,String name,String year)
{
super();
setContentAreaFilled(false);
setBackground(new Color(0,0,0,0));
setFocusPainted(false);
setBorderPainted(false);
//I didn't use image icon & text horizontal alignment because the text always horizontally centered aligned but from the expected output it was left so created 2 labels for the job
setLayout(new GridBagLayout());
addIcon(preview);
addLabel(name,year);
addActionListener(GridDisplay.this);
}
private void addIcon(BufferedImage preview)
{
JLabel icon=new JLabel();
icon.setIcon(new ImageIcon(preview));
add(icon,new GridBagConstraints(0,0,1,1,1.0f,0.0f,GridBagConstraints.WEST,GridBagConstraints.NONE,new Insets(0,0,0,0),0,0));
}
private void addLabel(String name,String year)
{
JLabel label=new JLabel("<html><body>"+name+"<br>"+year+"</body></html>");
label.setForeground(Color.white);
label.setBackground(new Color(0,0,0,0));
add(label,new GridBagConstraints(0,1,1,1,1.0f,1.0f,GridBagConstraints.SOUTHWEST,GridBagConstraints.NONE,new Insets(5,0,0,0),0,0));
}
}
#Override
public void actionPerformed(ActionEvent e)
{
TVShowCard card=(TVShowCard)e.getSource();
//do stuff with it
}
}
}

How to change images with a JButton

How can I change between the pictures with help of clicking the button.
I made a x variable because then I could make different if-statements but that didn't work for me, probably because I did something wrong... Here is my code so far:
public class Main extends JFrame{
private JButton changePic;
private JPanel panel;
private JLabel pic1;
private JLabel pic2;
private JLabel pic3;
private JLabel picture;
private int x = 0;
public Main(){
panel = new JPanel();
add(panel);
changePic = new JButton("Change Button");
panel.add(changePic);
pic1 = new JLabel(new ImageIcon("pic1.png"));
pic2 = new JLabel(new ImageIcon("pic.png"));
pic3 = new JLabel(new ImageIcon("pic3.png"));
panel.add(pic1);
panel.add(pic2);
panel.add(pic3);
changePic.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e){
if(e.getSource() == changePic){
}
}
});
getContentPane().setBackground(Color.white);
setSize(300, 300);
setVisible(true);
setDefaultCloseOperation(EXIT_ON_CLOSE);
}
public static void main(String[] args){
Main fr = new Main();
}
}
public class Main extends JFrame{
private JButton changePic;
private JPanel panel;
private JLabel pic1;
private int x = 0;
public Main(){
panel = new JPanel();
add(panel);
changePic = new JButton("Change Button");
panel.add(changePic);
pic1 = new JLabel();
panel.add(pic1);
ImageIcon icon1 = new ImageIcon("pic1.gif");
ImageIcon icon2 = new ImageIcon("pic2.gif");
ImageIcon icon3 = new ImageIcon("pic3.gif");
changePic.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e){
if(e.getSource() == changePic){
if(x == 0){
pic1.setIcon(icon1);
}else if(x == 1){
pic1.setIcon(icon2);
}else if(x == 2){
pic1.setIcon(icon3);
}
Main.this.pack();
x++;
if(x > 2) x = 0;
}
}
});
getContentPane().setBackground(Color.white);
setSize(300, 300);
setVisible(true);
setDefaultCloseOperation(EXIT_ON_CLOSE);
}
public static void main(String[] args){
Main fr = new Main();
}
}
you don't need multiple JLabels, use 3 ImageIcons instead.
you need to call JFrame's pack() every time you had UI Changes (in
this case, changing image)

how do i create a virtual keyboard that can be used to insert values in different jtextfields

So I am trying to create a virtual keyboard that can insert values in a Jtextfield of another Jframe. The problem is that the data is overlapping when editing other text fields. So, I tried renewing the object but it replaced the first Jtextfield value as well. what should i do with this, should i start from scratch or is there any other way? . Since, English is not my first language I am struggling to find the correct terminology to research the problem please enlighten me with your knowledge
import java.awt.*;
import javax.swing.*;
public class OnScreenKeyboard implements ActionListener {
JFrame keyboard;
static String keyboardKeys = "0123456789qwertyuiopasdfghjklzxcvbnm.< ";
JButton[] keys = new JButton[39];
GridLayout gl;
FlowLayout fl;
Dimension buttondimension;
JPanel panel1, panel2;
JToggleButton capslock;
private String message = "";
public String getMessage() {
return message;
}
public void setMessage(String message) {
this.message = message;
}
public OnScreenKeyboard() {
buttondimension = new Dimension(45, 40);
fl = new FlowLayout();
capslock = new JToggleButton("capslock");
panel1 = new JPanel(fl);
panel2 = new JPanel(fl);
char[] key = keyboardKeys.toCharArray();
for (int i = 0; i < 39; i++) {
keys[i] = new JButton(String.valueOf(key[i]));
keys[i].setFont(new Font("Arial", Font.PLAIN, 13));
if (i == 38) {
keys[i].setPreferredSize(new Dimension(100, 30));
} else {
keys[i].setPreferredSize(buttondimension);
}
keys[i].addActionListener(this);
}
keyboard = new JFrame("Keyboard");
keyboard.setSize(720, 220);
keyboard.setLocationRelativeTo(null);
keyboard.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
keyboard.setResizable(false);
Container content = keyboard.getContentPane();
content.setLayout(null);
panel1.setBounds(1, 1, 500, 210);
panel2.setBounds(510, 1, 200, 210);
for (int i = 0; i < 10; i++) {
panel2.add(keys[i]);
}
for (int i = 10; i < 39; i++) {
panel1.add(keys[i]);
}
panel1.add(capslock);
content.add(panel1);
content.add(panel2);
capslock.addActionListener(this);
keyboard.setVisible(true);
}
public static void main(String[] args) {
new OnScreenKeyboard();
}
public void reset(){
message = "";
}
#Override
public void actionPerformed(ActionEvent e) {
for (int i = 0; i < 36; i++) {
if (e.getSource() == keys[i]) {
setMessage(getMessage() + keys[i].getText());
break;
}
}
if (e.getSource() == capslock) {
if (capslock.isSelected()) {
for (int i = 10; i < 36; i++) {
keys[i].setFont(new Font("Arial", Font.PLAIN, 12));
keys[i].setText(keys[i].getText().toUpperCase());
}
} else if (!capslock.isSelected()) {
for (int i = 10; i < 36; i++) {
keys[i].setFont(new Font("Arial", Font.PLAIN, 13));
keys[i].setText(keys[i].getText().toLowerCase());
}
}
}
setMessage(getMessage());
//JOptionPane.showMessageDialog(null, getMessage());
}
}
this is the frame I am trying to put my values from the keyboard in
public class LoginScreen implements ActionListener, FocusListener {
JFrame frame;
Container content;
FlowLayout fl;
JTextField txtusername, txtpassword;
JLabel lblusername, lblpassword;
JPanel panel1, panel2;
JButton keyboard, signup, signin;
OnScreenKeyboard kyb;
Dimension text;
private void init() {
text =new Dimension(100, 30);
fl = new FlowLayout(FlowLayout.CENTER);
lblusername = new JLabel("enter username");
lblpassword = new JLabel("enter password");
txtusername = new JTextField();
txtpassword = new JPasswordField();
keyboard = new JButton("keyboard");
signup = new JButton("signup");
signin = new JButton("sign in");
panel1 = new JPanel(fl);
panel2 = new JPanel(fl);
keyboard = new JButton("keyboard");
txtusername.setPreferredSize(text);
txtpassword.setPreferredSize(text);
kyb = new OnScreenKeyboard();
}
public LoginScreen() {
init();
frame = new JFrame("BorderLayoutDemo");
frame.setTitle("Registration Form");
frame.setSize(300, 300);
frame.setDefaultCloseOperation(3);
frame.setLocationRelativeTo(null);
frame.setVisible(true);
content = frame.getContentPane();
content.setLayout(new GridLayout(2, 1));
panel1.add(lblusername);
panel1.add(txtusername);
panel1.add(lblpassword);
panel1.add(txtpassword);
panel2.add(signup);
panel2.add(signin);
panel2.add(keyboard);
content.add(panel1);
content.add(panel2);
keyboard.addActionListener(this);
txtusername.addFocusListener(this);
txtpassword.addFocusListener(this);
}
public static void main(String[] args) {
new LoginScreen();
}
#Override
public void actionPerformed(ActionEvent e) {
if (!kyb.keyboard.isVisible()) {
if (e.getSource() == keyboard) {
kyb = new OnScreenKeyboard();
}
}
}
#Override
public void focusGained(FocusEvent e) {
if(txtusername == e.getSource()){
txtusername.setText(kyb.getMessage());
}else if(txtpassword == e.getSource()){
kyb.reset();
txtpassword.setText(kyb.getMessage());
}
}
#Override
public void focusLost(FocusEvent e) {
}
The problem is that it's weird how/when the text is taken from the keyboard.
You use the LoginScreen both as actionListener on the keyboard and as focusListener on the 2 textfields.
The way you implemented it now is that you "type" something in on the keyboard and after that put the focus on 1 of the 2 fields. Only at the moment you click the text from the keyboard is fetched (kyb.getMessage()).
It's especially a problem on the password. If you click on the txtpassword field you first reset the kyb and then fetch the message (which you just reset so is empty).
What felt weird for me is that you don't have a way in the keyboard to notion that you are done typing. So the flow of only getting the message when the focus changes to one of the text fields is wrong.
What I would do is create a new kind of KeyboardListener. This listener is put on the txtusername OR txtpassword depending on who last took focus (so in the focusGained() you should change who is listening to the keyboard).
Then each time a key is "typed" you should notify the listener of the letter and then the txtusername/txtpassword (whichever is listening at that time) should add that letter to its text.
This means that the keyboard itself doesn't need to remember any text. It just figures out which key was pressed and then sends the corresponding letter to the listener.
You should be using a TextAction as your ActionListener. The TextAction has a method getFocusedComponent() which will return the last text component to have focus.
Then in the can add the character to the text field. So the basic code in the actionPerformed(...) method of the TextAction might be something like:
JTextComponent component = getFocusedComponent();
component.replaceSelection( the character to add );

How to set JLabel in a specific area in JFrame?

I am trying to make a desktop application in Java Swing. I am trying to create image slider in frame and I got it. Now problem in that I want to set the specific area for imagelabel in that frame. How can I do this? I want to set imagelabel in left side. I am posting my snapshot which I am getting after running my program.
Here is my code
public class ImageSlider extends JPanel implements ActionListener {
private static final int MAX = 20;
private static final Font sans = new Font("SansSerif", Font.PLAIN, 16);
private static final Border border =
BorderFactory.createMatteBorder(4, 16, 4, 16, Color.BLUE);
private List<String> list = new ArrayList<String>(MAX);
private List<ImageIcon> cache = new ArrayList<ImageIcon>(MAX);
private JLabel imageLabel = new JLabel();
//label = new JLabel( image, SwingConstants.CENTER);
private JButton prevButton = new JButton();
private JButton nextButton = new JButton();
private JComboBox favorites;
public ImageSlider() {
this.setLayout(new BorderLayout());
list.add("c.jpg");
list.add("a0.png");
list.add("yellow.png");
list.add("a0.png");
list.add("c.jpg");
for (int i = 0; i < list.size(); i++) cache.add(i, null);
ImageIcon image = new ImageIcon("E:\\SOFTWARE\\TrainPIS\\res\\drawable\\a0.png");
JLabel titleLabel = new JLabel(image, SwingConstants.CENTER);
// titleLabel.setText("ImageSlider");
titleLabel.setHorizontalAlignment(JLabel.CENTER);
titleLabel.setFont(new Font(Font.SANS_SERIF, Font.BOLD, 24));
titleLabel.setBorder(border);
this.add(titleLabel, BorderLayout.NORTH);
imageLabel.setIcon(getImage(0));
imageLabel.setAlignmentX(LEFT_ALIGNMENT);
imageLabel.setHorizontalAlignment(JLabel.CENTER);
imageLabel.setBorder(border);
this.add(imageLabel, BorderLayout.CENTER);
favorites = new JComboBox(
list.toArray(new String[list.size()]));
favorites.setActionCommand("favs");
favorites.addActionListener(this);
prevButton.setText("\u22b2Prev");
prevButton.setFont(sans);
prevButton.setActionCommand("prev");
prevButton.addActionListener(this);
nextButton.setText("Next\u22b3");
nextButton.setFont(sans);
nextButton.setActionCommand("next");
nextButton.addActionListener(this);
JPanel controlPanel = new JPanel();
controlPanel.add(prevButton);
controlPanel.add(favorites);
controlPanel.add(nextButton);
controlPanel.setBorder(border);
this.add(controlPanel, BorderLayout.SOUTH);
}
public void actionPerformed(ActionEvent ae) {
String cmd = ae.getActionCommand();
if ("favs".equals(cmd)) {
int index = favorites.getSelectedIndex();
ImageIcon image = getImage(index);
imageLabel.setIcon(image);
if (image != null) imageLabel.setText("");
else imageLabel.setText("Image not available.");
}
if ("prev".equals(cmd)) {
int index = favorites.getSelectedIndex() - 1;
if (index < 0) index = list.size() - 1;
favorites.setSelectedIndex(index);
}
if ("next".equals(cmd)) {
int index = favorites.getSelectedIndex() + 1;
if (index > list.size() - 1) index = 0;
favorites.setSelectedIndex(index);
}
}
public JButton getDefault() { return nextButton; }
// Return the (possibly cached) image having the given index.
private ImageIcon getImage(int index) {
ImageIcon image = cache.get(index);
if (image != null) return image;
String name = "/images/" + list.get(index);
URL url = ImageSlider.class.getResource(name);
if (url != null) {
image = new ImageIcon(url);
}
cache.set(index, image);
return image;
}
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
public void run() {
JFrame frame = new JFrame();
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
ImageSlider go = new ImageSlider();
frame.add(go);
frame.setTitle("ImageSlider");
// frame.setSize(400, 300);
frame.setExtendedState(JFrame.MAXIMIZED_BOTH);
frame.setUndecorated(true);
frame.setVisible(true);
go.getDefault().requestFocusInWindow();
}
});
}
}
How can I achieve my goal?
The easiest way to achieve this is to put the imageLabel into a JPanel with a FlowLayout. Then add that panel to the bigger BorderLayout.
So change:
this.add(imageLabel, BorderLayout.CENTER);
To something like:
JPanel imageConstrain = new JPanel(new FlowLayout(SwingConstants.LEFT));
imageConstrain.add(imageLabel);
this.add(imageConstrain, BorderLayout.CENTER);

java parsing data from component

I am creating a game, and I am doing a character selection screen which has a JTextField for entering the user name, the screen also has a JButton "Create Character", which, when pressed will parse the JTextField and if any problems(space in name, begin with space, etc..) it will put some text to a JLabel next to the JTextField.
I hook up the JButton to an actionPerformed method, which calls a function that parses the data. My problem is that every time I press the button, a new label is being placed on top of the original JLabel.
I create the JLabel like this:
public static JLabel label;
label = new JLabel();
// some properties
And I call the parsing method like so:
parseCharacterSelection(nameInput, label);
where nameInput is the JTextField.
My question is, why is there a new Label being created every time I press the JButton
public void parseCharacterCreation(JTextField input, JLabel label) {
// Variable that hold whether or not
// the User Name is acceptable
player_name = input.getText();
// Make some initial checks on the
// input string
//----------------------------------
if( player_name.isEmpty() ) {
label.setText("You need to pick a username");
} else if( player_name.startsWith(" ") ) {
label.setText("Name Cannot start with a space");
} else {
pass = true;
}
// Attempt to write to file
// Catch some errors
//----------------------------------
if(pass == true) {
try {
if( player_name.contains(" ") ) {
player_name = player_name.replaceAll("\\s", "_");
player_file = new File("src/Resources/characters/" + player_name + ".properties");
}
if(!player_file.exists()) {
player_file.createNewFile();
}
FileWriter fw = new FileWriter(player_file.getAbsoluteFile());
BufferedWriter bw = new BufferedWriter(fw);
bw.write(player_name);
bw.close();
} catch( IOException e ) {
e.printStackTrace();
} finally {
System.out.println("DONE");
}
}
}
// ScreenCharacter Class
public class ScreenCharacter extends JPanel {
public static JButton create;
public static JTextField nameInput;
public static JLabel errorLabel;
public ScreenCharacter() {
this.setLayout(null);
this.add(createUserName());
this.add(createMainArea());
}
private static JPanel createUserName() {
MatteBorder matteBorder = new MatteBorder(1, 0, 1, 0, Color.decode("#222222"));
EmptyBorder emptyBorder = new EmptyBorder(10, 75, 10, 10);
CompoundBorder border = new CompoundBorder(matteBorder, emptyBorder);
JPanel userNameArea = new JPanel();
userNameArea.setLayout(new FlowLayout(FlowLayout.LEFT, 0, 0));
userNameArea.setBounds(0, 35, Engine.screenX, 50);
userNameArea.setBorder(border);
userNameArea.setBackground(new Color(255, 255, 255, 70));
JLabel nameLabel = new JLabel();
nameLabel.setText("Enter Your Username: ");
nameInput = new JTextField();
nameInput.setForeground(Color.black);
nameInput.setBorder(BorderFactory.createEmptyBorder(0, 5, 0, 0));
nameInput.setPreferredSize(new Dimension(200, 25));
errorLabel = new JLabel();
errorLabel.setText("This is a test label");
errorLabel.setBorder(BorderFactory.createEmptyBorder(0, 20, 0, 0));
errorLabel.setPreferredSize(new Dimension(200, 25));
errorLabel.setAlignmentX(JLabel.LEFT_ALIGNMENT);
userNameArea.add(nameLabel);
userNameArea.add(nameInput);
userNameArea.add(errorLabel);
return userNameArea;
}
private static JPanel createMainArea() {
JPanel resetCreatePanel = new JPanel(new GridLayout(1, 2));
resetCreatePanel.setPreferredSize(new Dimension(300, 30));
resetCreatePanel.setBackground(Color.black);
create = new JButton("Create Character");
create.setBorder(BorderFactory.createLineBorder(Color.decode("#171717")));
create.setFont(new Font("Dialog", 1, 11));
create.setBackground(Color.black);
create.setForeground(Color.white);
create.setFocusPainted(false);
create.setContentAreaFilled(false);
create.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent arg0) {
if(!errorLabel.getText().isEmpty()) {
errorLabel.setText("");
} else {
Engine.p_parser.parseCharacterCreation(nameInput, errorLabel);
}
}
});
resetCreatePanel.add(create);
}
}
// Engine
public class Engine {
public static PlayerParser p_parser;
public Engine() {
p_parser = new PlayerParser();
}
}
Thanks everyone for the help. The "problem" was that the JPanel that the components were sitting on had a semi-transparent background. And JComponents with transparency get messed up somehow, which made it appear like there are multiple labels being created. But it works fine without transparency.

Categories