Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Adding JLabel dynamically in a pattern but last one is not working correctly

I'm trying to creating 40 dynamical JLabels in a pattern, which is working quite good but the last JLabel is not placing according to the pattern. Can anyone tell me what I did wrong ?

Here what I have done so far:

public class Booking2 {

    public static void main(String[] args) {
        JFrame jf = new JFrame();
        jf.setVisible(true);
        jf.setDefaultCloseOperation(jf.EXIT_ON_CLOSE);

        jf.setSize(700, 400);
        jf.setLocationRelativeTo(null);
        int c1 = 40;
        int count = 0, count2 = 0, count3 = 0, count4 = 0, x;
        JLabel[] jl = new JLabel[c1];

        for (int i = 0; i <= c1 - 1; i++) {
            jl[i] = new JLabel();

            if (i <= 9) {
                x = 25 * count;
                jl[i].setBounds(x, 50, 20, 30);
                count++;
            }
            if (i >= 10 && i <= 19) {
                x = 25 * count2;
                jl[i].setBounds(x, 80, 20, 20);
                count2++;
            }
            if (i >= 20 && i <= 29) {
                x = 25 * count3;
                jl[i].setBounds(x, 110, 20, 20);
                count3++;
            }
            if (i >= 30 && i <= 39) {
                x = 25 * count4;
                jl[i].setBounds(x, 130, 20, 20);
                count4++;
            }
            // jl[i].setIcon(new
            // ImageIcon(Booking2.class.getResource("booked.png")));
            jl[i].setText("O");
            jf.add(jl[i]);
        }
    }
}

enter image description here

like image 603
Arpan Avatar asked Jan 08 '23 02:01

Arpan


2 Answers

you are using absolute positioning / null layout but you haven't set layout to null .default layout of jframe is Border layout.

add this line

jf.setLayout(null);

and after you add all components call revalidate() and repaint() method of jframe.

example

public class Booking2 {

    public static void main(String[] args) {
        JFrame jf = new JFrame();
        jf.setVisible(true);
        jf.setDefaultCloseOperation(jf.EXIT_ON_CLOSE);

        jf.setLayout(null); // this is important 

        jf.setSize(700, 400);

        int c1 = 40;
        int count = 0, count2 = 0, count3 = 0, count4 = 0, x;
        JLabel[] jl = new JLabel[c1];

        for (int i = 0; i <= c1 - 1; i++) {
            jl[i] = new JLabel();

            if (i <= 9) {
                x = 25 * count;
                jl[i].setBounds(x, 50, 20, 20);
                count++;
            }
            if (i >= 10 && i <= 19) {
                x = 25 * count2;
                jl[i].setBounds(x, 80, 20, 20);
                count2++;
            }
            if (i >= 20 && i <= 29) {
                x = 25 * count3;
                jl[i].setBounds(x, 110, 20, 20);
                count3++;
            }
            if (i >= 30 && i <= 39) {
                x = 25 * count4;
                jl[i].setBounds(x, 130, 20, 20);
                count4++;
            }
            //jl[i].setIcon(new ImageIcon(Booking2.class.getResource("booked.png")));
            jl[i].setText("O");
            jf.add(jl[i]);
        }
         jf.revalidate();
        jf.setVisible(true);
    }

}

output

enter image description here

Note

1) you should avoid null layout .use a layout GRID layout seems good for your case .and also if this is a kind of a game /animation you should look at these example https://www3.ntu.edu.sg/home/ehchua/programming/java/J8a_GameIntro-BouncingBalls.html. you can use paintComponent() method to draw this grid in a jpanel which is efficient and you can draw any kind of pattern .think if you make a big grid,for instance 100*100 using jlables it's not good

2) it's better to add components to jpanel instead of add directly to jframe .you can use setContentPane() method for that

like image 68
Madhawa Priyashantha Avatar answered Jan 26 '23 11:01

Madhawa Priyashantha


It would be much better to use layout, for example GridLayout:

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

public class Booking2 {

    public static void main(String[] args) {
        JFrame jf = new JFrame();
        jf.setVisible(true);
        jf.setDefaultCloseOperation(jf.EXIT_ON_CLOSE);
        jf.setLayout(new GridLayout(4,10));
        jf.setSize(700, 400);
        jf.setLocationRelativeTo(null);
        int c1=40;
        JLabel[] jl = new JLabel[c1];

        for(int i=c1-1; i>=0; i--){
            jl[i]=new JLabel();
            jl[i].setText("O");
            jf.add(jl[i]);
        }
    }
}

It is more elegant way. But, if you are determined to use setBound() you should set JFrame (or other container with your JLabels) layout to null:

jf.setLayout(null);

This will allow for absolute positioning inside container. It seems that default JFrames BorderLoyout distorted your setBounds() settings.

However it is generally not recomended to use null layout, and it is considered a bad programming practice. It is better idea to use LayoutMenagers!

like image 23
m.cekiera Avatar answered Jan 26 '23 13:01

m.cekiera