GridBagLayout - Anfängerprobleme

Status
Nicht offen für weitere Antworten.

Tobias

Top Contributor
Hallo,

ich baue zum ersten Mal eine Struktur mit GridBagLayout zusammen. Das Ergebnis soll eine Tastatur darstellen, die dieser hier in etwa ähnelt:

skb.gif

(Schattierungen, Zahlen und die grauen Linien bitte ignorieren, die sind nur zu Dokuzwecken da)

Ich habe mich zunächst einmal an den Buchstabenblock begeben und dort ein bißchen rumgebastelt (so Sachen wie die Abstände etc interessieren mich gerade weniger, wichtig ist erstmal nur die korrekte Ausrichtung). Da ich (wie oben zu sehen) einige Buttons habe, die eine halbe Buttonbreite in die nächste Spalte hineinragen, habe ich mir ein Raster hinter den Buttons vorgestllt, dessen Spaltenbreite halb so groß ist wie die Breite eines Buttons und dessen Zeilenhöhe der Höhe eines normalen Buttons entspricht.

So bin ich bis hierher gekommen:

skb-ist.gif

(die roten Rechtecke habe ich später zur Verdeutlichung der Probleme eingezeichnet, die weißen Quadrate mit rotem Kreuz sind Standardicons, die gewählt werden, wenn eine Grafik fehlt - einfach ignorieren)

Wie an den roten Rechtecken zu erkennen ist, gibt es ein paar Probleme. Beispielsweise wird der Versatz von einer halben Buttonbreite zwischen der zweiten und der dritten Reihe nicht umgesetzt. Verantwortlich sind die zu breiten Buttons "Q" und """. Der Enter-Button ist zu breit, dafür aber nicht hoch genug - dafür ist der "-"-Button viel zu lang, der nimmt den "freigehaltenen" Platz des Enter-Buttons ein. Der Delete-Button ist glaube ich korrekt, der scheinbare Fehler wird hier wohl durch den fehlenden Versatz links ausgelöst.

Hier noch der Code, mit dem ich das Layout zusammenbaue:

Code:
private void initKeyBoard() {
		setLayout(new GridBagLayout());
		GridBagConstraints c = new GridBagConstraints();
		c.gridheight = 1;
		c.gridwidth = 2;
		c.fill = GridBagConstraints.BOTH;

		// First row
		add(layout.getButton(0, 0), c); // Button links oben - layout.getButton(Spalte, Zeile)
		add(layout.getButton(1, 0), c);
		add(layout.getButton(2, 0), c);
		add(layout.getButton(3, 0), c);
		add(layout.getButton(4, 0), c);
		add(layout.getButton(5, 0), c);
		add(layout.getButton(6, 0), c);
		add(layout.getButton(7, 0), c);
		add(layout.getButton(8, 0), c);
		add(layout.getButton(9, 0), c);
		add(layout.getButton(10, 0), c);
		add(layout.getButton(11, 0), c);
		add(layout.getButton(12, 0), c);
		c.gridwidth = GridBagConstraints.REMAINDER;
		add(layout.getButton(13, 0), c);

		// second row
		c.gridwidth = 2;
		add(layout.getButton(0, 1), c);
		add(layout.getButton(1, 1), c);
		add(layout.getButton(2, 1), c);
		add(layout.getButton(3, 1), c);
		add(layout.getButton(4, 1), c);
		add(layout.getButton(5, 1), c);
		add(layout.getButton(6, 1), c);
		add(layout.getButton(7, 1), c);
		add(layout.getButton(8, 1), c);
		add(layout.getButton(9, 1), c);
		add(layout.getButton(10, 1), c);
		add(layout.getButton(11, 1), c);
		c.gridwidth = GridBagConstraints.REMAINDER;
		add(delete, c);

		// third row
		c.gridwidth = 3;
		add(shiftLock, c);
		c.gridwidth = 2;
		add(layout.getButton(1, 2), c);
		add(layout.getButton(2, 2), c);
		add(layout.getButton(3, 2), c);
		add(layout.getButton(4, 2), c);
		add(layout.getButton(5, 2), c);
		add(layout.getButton(6, 2), c);
		add(layout.getButton(7, 2), c);
		add(layout.getButton(8, 2), c);
		add(layout.getButton(9, 2), c);
		add(layout.getButton(10, 2), c);
		add(layout.getButton(11, 2), c);
		c.gridwidth = GridBagConstraints.REMAINDER;
		c.gridheight = 2;
		add(enter, c);

		// fourth row
		c.gridwidth = 5;
		add(shift, c);
		c.gridwidth = 2;
		add(layout.getButton(2, 3), c);
		add(layout.getButton(3, 3), c);
		add(layout.getButton(4, 3), c);
		add(layout.getButton(5, 3), c);
		add(layout.getButton(6, 3), c);
		add(layout.getButton(7, 3), c);
		add(layout.getButton(8, 3), c);
		add(layout.getButton(9, 3), c);
		add(layout.getButton(10, 3), c);
		c.gridwidth = GridBagConstraints.REMAINDER;
		add(layout.getButton(11, 3), c);

		// fifth row
		c.gridwidth = GridBagConstraints.REMAINDER;
		add(space, c);
	}

Mein komplettes Testprogramm zu posten würde wohl etwas weitgehen. Ich hoffe, ihr kommt mit obigem Code klar, das Objekt "layout" wird jeweils um den Button an der gegebenen Stelle gebeten, die Parameter bedeuten (Spalte, Zeile). Wie kann ich die oben beschriebenen Fehler beheben? Ist mein Ansatz beim Umgang mit dem GridBagLayout überhaupt vernünftig?

mpG
Tobias
 
S

SlaterB

Gast
der Enter-Button scheint nicht so definiert zu sein, dass er zwei Zeilen belegt,
ohne Code kann man da nix genaues zu sagen,

---

zur Ecke Ä - Delete - Enter:
Grid-Linien sind gerade und durchgängig, da gibt es keinen Versatz,
Spalte 13 musst du also in zwei Spalten aufteilen,

ach das gilt ja für die gesamte Zeile 3, übel ;)
wahrscheinlich ist es dann besser, da ein neues unteres JPanel mit eigenen GridLayout anzulegen

> Wie an den roten Rechtecken zu erkennen ist, gibt es ein paar Probleme. Beispielsweise wird der Versatz von einer halben Buttonbreite zwischen der zweiten und der dritten Reihe nicht umgesetzt

wie glaubst du es denn in deinem Programm bisher lösen zu können?

----------

> add(layout.getButton(6, 2), c);
> add(layout.getButton(7, 2), c);
> add(layout.getButton(8, 2), c);
> add(layout.getButton(9, 2), c);
....


Tipp zur Verkürzung: schreibe dir eine Hilfsoperation, so dass du nur noch
add(6, 2, c);
add(7, 2, c);
add(8, 2, c);
add(9, 2, c);
schreiben musst,

oder wenn das layout als Parameter unverzichtbar ist, dann zumindest
add(layout, 6, 2, c);
add(layout, 7, 2, c);
add(layout, 8, 2, c);
add(layout, 9, 2, c);
 

Marco13

Top Contributor
Ob dafür nicht ein TableLayout günstiger wäre? ???:L Naja.... nur so als unwichtiger Einwurf....
 

Tobias

Top Contributor
@Marco13: Mit TableLayout habe ich noch nicht gearbeitet, ich gucke es mir gerade mal an.

@SlaterB: Mein Grid für das Layout besitzt Spalten mit einer Breite von einer halben Buttonbreite. Deshalb habe ich ganz am Anfang der Methode c.gridwidth auf 2 gesetzt. Dies ändere ich für die einzelnen Funktionstasten auf ihre entsprechenden Werte.
Beim Enter-Button habe ich gridheight auf 2 gesetzt, damit ist doch die Definition "sei zwei Zeilen hoch" abgeschlossen, oder?
Mittlerweile benutze ich Hilfsfunktionen, um mir das ständige Ändern der GridBagConstraints zu vereinfachen. Das fand ich weit anstrengender, als das bißchen layout.getButton(x, y), welches IMHO zusätzlich auch zur Lesbarkeit beiträgt. Aber danke für den Hinweis ;).

mpG
Tobias
 
S

SlaterB

Gast
> damit ist doch die Definition "sei zwei Zeilen hoch" abgeschlossen, oder?

mag sein, setzt du aber die Höhe für die anderen Elemente wieder auf 1 zurück oder sind alle dann 2 hoch?
sorgst du dafür, dass in der nächsten Zeile die Zelle direkt darunter frei bleibt?

grundsätzlich würde ich zur Sicherheit auch empfehlen, ein eigenes c-Objekt pro Button anzulegen,
(auch wenn es in diesem Fall nicht nötig ist)

ohne lauffähigen Code kann man aber bei allem nur raten,
 

Tobias

Top Contributor
Ok, ich hab mal zwei JARs gezaubert, die nicht nur lauffähig sind (sein sollten, getestet auf XP Prof), sondern auch den Quellcode enthalten. Es ist allerdings ziemlich viel Quellcode - der interessante Teil ist aber in der Klasse ScreenKeyBoard konzentriert (de.tobiasdemuth.cube.xul.renderer.basic.swing.fa.keyboard.ScreenKeyBoard), speziell in der Methode initKeyBoard() und ein bißchen in add(Component, int, int) und add(Component, int, int, int, int).

Die beiden JARs müssen im selben Ordner liegen, gestartet werden kann nur die keyboard.jar.

mpG
Tobias

P.S.: commons.jar: http://www.java-forum.org/de/userfiles/user497/commons.jar
keyboard.jar: http://www.java-forum.org/de/userfiles/user497/keyboard.jar
 
S

SlaterB

Gast
also ich warte darauf, bis du ein 150-Zeilen Programm hier im Forum postest :bae:
 

Tobias

Top Contributor
So, hat zwar knapp 200 Zeilen, aber wenn du die Kommentare streichst, kommt es in etwa hin ;):

Code:
public class KeyBoardLayoutTest extends JFrame {

	GridBagConstraints constraints = new GridBagConstraints();

	public KeyBoardLayoutTest() {
		super("KeyBoardLayoutTest");
		setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

		initKeyBoard();

		pack();
		setVisible(true);
	}

	/**
	 * Initializes the graphical representation of the keyboard.
	 */
	private void initKeyBoard() {
		setLayout(new GridBagLayout());

		// First row
		add("!", 0, 0);
		add("\"", 2, 0);
		add("§", 4, 0);
		add("$", 6, 0);
		add("%", 8, 0);
		add("&", 10, 0);
		add("/", 12, 0);
		add("(", 14, 0);
		add(")", 16, 0);
		add("=", 18, 0);
		add("?", 20, 0);
		add("#", 22, 0);
		add("€", 24, 0);
		add("ß", 26, 0);
		// Num-block
		add(",", 32, 0);
		add("/", 34, 0);
		add("*", 36, 0);
		add("-", 38, 0);

		// second row
		add("@", 0, 1);
		add("Q", 2, 1);
		add("W", 4, 1);
		add("E", 6, 1);
		add("R", 8, 1);
		add("T", 10, 1);
		add("Z", 12, 1);
		add("U", 14, 1);
		add("I", 16, 1);
		add("O", 18, 1);
		add("P", 20, 1);
		add("Ü", 22, 1);
		add("Delete", 24, 1, 4, 1);
		// Num-block
		add("7", 32, 1);
		add("8", 34, 1);
		add("9", 36, 1);
		add("+", 38, 1, 2, 2);

		// third row
		add("Lock", 0, 2, 3, 1);
		add("A", 3, 2);
		add("S", 5, 2);
		add("D", 7, 2);
		add("F", 9, 2);
		add("G", 11, 2);
		add("H", 13, 2);
		add("J", 15, 2);
		add("K", 17, 2);
		add("L", 19, 2);
		add("Ö", 21, 2);
		add("Ä", 23, 2);
		add("Enter", 25, 2, 3, 2);
		// Num-Block
		add("4", 32, 2);
		add("5", 34, 2);
		add("6", 36, 2);

		// fourth row
		add("Shift", 0, 3, 5, 1);
		add("Y", 5, 3);
		add("X", 7, 3);
		add("C", 9, 3);
		add("V", 11, 3);
		add("B", 13, 3);
		add("N", 15, 3);
		add("M", 17, 3);
		add(",", 19, 3);
		add(".", 21, 3);
		add("-", 23, 3);
		add("^", 28, 3);
		// Num-Block
		add("1", 32, 3);
		add("2", 34, 3);
		add("3", 36, 3);
		add("Ent", 38, 3, 2, 2);

		// fifth row
		add("Space", 0, 4, 26, 1);
		add("<", 26, 4);
		add("v", 28, 4);
		add(">", 30, 4);
		// Num-Block
		add("0", 32, 4, 4, 1);
		add("Del", 36, 4);
	}

	/**
	 * Resets the constraints-object.
	 * 
	 * @return the resetted constraints-object.
	 */
	private GridBagConstraints resetConstraints() {
		constraints.anchor = GridBagConstraints.CENTER;
		constraints.fill = GridBagConstraints.BOTH;
		constraints.gridheight = 1; // A normal button spans one row
		constraints.gridwidth = 2; // and two columns
		constraints.gridx = GridBagConstraints.RELATIVE;
		constraints.gridy = GridBagConstraints.RELATIVE;
		constraints.insets = new Insets(0, 0, 0, 0);
		constraints.ipadx = 10; // Just to provide a nicer layout
		constraints.ipady = 10;
		constraints.weightx = 0;
		constraints.weighty = 0;

		return constraints;
	}

	/**
	 * Adds the given component at the specified position to the grid.
	 * 
	 * @param text
	 *            the text for the label to add.
	 * @param column
	 *            the column the left edge of the component should lay in.
	 * @param row
	 *            the row the left upper edge of the component should lay in.
	 */
	private void add(String text, int column, int row) {
		resetConstraints();
		constraints.gridx = column;
		constraints.gridy = row;

		JLabel l = new JLabel(text);
		l.setHorizontalAlignment(SwingConstants.CENTER);
		l.setOpaque(true);
		l.setBackground(Color.WHITE);
		l.setBorder(BorderFactory.createMatteBorder(1, 1, 1, 1, Color.BLACK));

		add(l, constraints);
	}

	/**
	 * Adds a component at the specified position with given width and height.
	 * 
	 * @param text
	 *            the text for the JLabel to add.
	 * @param column
	 *            the column the upper left edge of the component should be
	 *            placed in.
	 * @param row
	 *            the row the upper left edge of the component should be placed
	 *            in.
	 * @param width
	 *            how much columns should the component span
	 * @param height
	 *            how much rows should the component span
	 */
	private void add(String text, int column, int row, int width, int height) {
		resetConstraints();
		constraints.gridx = column;
		constraints.gridy = row;
		constraints.gridwidth = width;
		constraints.gridheight = height;

		JLabel l = new JLabel(text);
		l.setHorizontalAlignment(SwingConstants.CENTER);
		l.setOpaque(true);
		l.setBackground(Color.WHITE);
		l.setBorder(BorderFactory.createMatteBorder(1, 1, 1, 1, Color.BLACK));

		add(l, constraints);
	}

	/**
	 * @param args
	 */
	public static void main(String[] args) {
		new KeyBoardLayoutTest();
	}

}

Die Probleme sind die selben wie oben angesprochen - der Enter-Button ist zu breit (dafür mittlerweile aber zwei Zeilen hoch) und der Versatz zwischen zweiter und dritter Zeile fehlt.

Wäre toll, wenn du mir einen Tipp geben könntest, was hier verkehrt ist ...

mpG
Tobias
 
S

SlaterB

Gast
die Buttons sind nun zwar schön versetzt, allerdings trickst Java dich aus:
die Spalten sind abwechselnd 50 Pixel und 1 Pixel breit, so dass kein Versatz zu erkennen ist

ich habe mal eine Taktgeber-Zeile unten eingebaut,
wie man das ansonsten schöner lösen kann weiß ich nicht

bin immer noch dafür, zwei unterschiedliche JPanel für diese Bereiche zu nehmen,
so dass 90% der Buttons genau eine Zelle belegen, nur Enter & Co. mehr,
bei dir sind ja ALLE zwei Felder breit..


-----

die drei Zeilen, die die Enter-Taste belegt, sind auch dann noch z.T. überproportioal breit, weil der Text 'Enter' reinpassen muss,
wenn du dem ganzen Layout genug Platz gibt, dann sind wieder alle Spalten gleich breit


-----

Code:
public class KeyBoardLayoutTest
    extends JFrame
{

    GridBagConstraints constraints = new GridBagConstraints();

    public KeyBoardLayoutTest()
    {
        super("KeyBoardLayoutTest");
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        initKeyBoard();

        setSize(800, 300);
        setVisible(true);
    }

    /**
     * Initializes the graphical representation of the keyboard.
     */
    private void initKeyBoard()
    {
        setLayout(new GridBagLayout());

        // First row
        add2("!", 0, 0);
        add2("\"", 2, 0);
        add2("§", 4, 0);
        add2("$", 6, 0);
        add2("%", 8, 0);
        add2("&", 10, 0);
        add2("/", 12, 0);
        add2("(", 14, 0);
        add2(")", 16, 0);
        add2("=", 18, 0);
        add2("?", 20, 0);
        add2("#", 22, 0);
        add2("€", 24, 0);
        add2("ß", 26, 0);
        // Num-block
        add2(",", 32, 0);
        add2("/", 34, 0);
        add2("*", 36, 0);
        add2("-", 38, 0);

        // second row
        add2("@", 0, 1);
        add2("Q", 2, 1);
        add2("W", 4, 1);
        add2("E", 6, 1);
        add2("R", 8, 1);
        add2("T", 10, 1);
        add2("Z", 12, 1);
        add2("U", 14, 1);
        add2("I", 16, 1);
        add2("O", 18, 1);
        add2("P", 20, 1);
        add2("Ü", 22, 1);
        add("Delete", 24, 1, 4, 1);
        // Num-block
        add2("7", 32, 1);
        add2("8", 34, 1);
        add2("9", 36, 1);
        add("+", 38, 1, 2, 2);

        // third row
        add("Lock", 0, 2, 3, 1);
        add2("A", 3, 2);
        add2("S", 5, 2);
        add2("D", 7, 2);
        add2("F", 9, 2);
        add2("G", 11, 2);
        add2("H", 13, 2);
        add2("J", 15, 2);
        add2("K", 17, 2);
        add2("L", 19, 2);
        add2("Ö", 21, 2);
        add2("Ä", 23, 2);
        add("Enter", 25, 2, 3, 2);
        // Num-Block
        add2("4", 32, 2);
        add2("5", 34, 2);
        add2("6", 36, 2);

        // fourth row
        add("Shift", 0, 3, 5, 1);
        add2("Y", 5, 3);
        add2("X", 7, 3);
        add2("C", 9, 3);
        add2("V", 11, 3);
        add2("B", 13, 3);
        add2("N", 15, 3);
        add2("M", 17, 3);
        add2(",", 19, 3);
        add2(".", 21, 3);
        add2("-", 23, 3);
        add2("^", 28, 3);
        // Num-Block
        add2("1", 32, 3);
        add2("2", 34, 3);
        add2("3", 36, 3);
        add("Ent", 38, 3, 2, 2);

        // fifth row
        add("Space", 0, 4, 26, 1);
        add2("<", 26, 4);
        add2("v", 28, 4);
        add2(">", 30, 4);
        // Num-Block
        add("0", 32, 4, 4, 1);
        add2("Del", 36, 4);

        for (int i = 0; i < 40; i++)
        {
            add1("", i, 5);
        }

    }

    private GridBagConstraints resetConstraints()
    {
        constraints.anchor = GridBagConstraints.CENTER;
        constraints.fill = GridBagConstraints.BOTH;
        constraints.gridheight = 1; // A normal button spans one row
        constraints.gridwidth = 2; // and two columns
        constraints.gridx = GridBagConstraints.RELATIVE;
        constraints.gridy = GridBagConstraints.RELATIVE;
        constraints.insets = new Insets(0, 0, 0, 0);
        constraints.ipadx = 10; // Just to provide a nicer layout
        constraints.ipady = 10;
        constraints.weightx = 0;
        constraints.weighty = 0;

        return constraints;
    }

    private void add1(String text, int column, int row)
    {
        resetConstraints();
        constraints.gridx = column;
        constraints.gridy = row;
        constraints.gridwidth = 1;
        constraints.weightx = 1;

        JLabel l = new JLabel(text);
        l.setHorizontalAlignment(SwingConstants.CENTER);
        l.setOpaque(true);
        l.setBackground(Color.WHITE);
        l.setBorder(BorderFactory.createMatteBorder(1, 1, 1, 1, Color.BLACK));

        add(l, constraints);
    }

    private void add2(String text, int column, int row)
    {
        resetConstraints();
        constraints.gridx = column;
        constraints.gridy = row;

        JLabel l = new JLabel(text);
        l.setHorizontalAlignment(SwingConstants.CENTER);
        l.setOpaque(true);
        l.setBackground(Color.WHITE);
        l.setBorder(BorderFactory.createMatteBorder(1, 1, 1, 1, Color.BLACK));

        add(l, constraints);
    }

    private void add(String text, int column, int row, int width, int height)
    {
        resetConstraints();
        constraints.gridx = column;
        constraints.gridy = row;
        constraints.gridwidth = width;
        constraints.gridheight = height;
        constraints.weightx = width;

        JLabel l = new JLabel(text);
        l.setHorizontalAlignment(SwingConstants.CENTER);
        l.setOpaque(true);
        l.setBackground(Color.WHITE);
        l.setBorder(BorderFactory.createMatteBorder(1, 1, 1, 1, Color.BLACK));

        add(l, constraints);
    }

    public static void main(String[] args)
    {
        new KeyBoardLayoutTest();
    }

}
 
M

Michael...

Gast
ich denke mal, dass sich für so etwas ein eigener LayoutManager lohnen könnte. Mit den StandardManagern kriegt man das nie so genau hin.
Hier mal ein unvollständiges aber kompilierbares Bsp. Es hat sicherlich noch Optimierungspotetial.
Code:
import java.awt.*;
import javax.swing.*;

public class KeyBoardLayout extends JPanel implements LayoutManager {
	private double ratio = 0.8d; //gewünschtes Seitenverhältnis einer Taste Hoehe/Breite
	private double inGap = 0.3d; //relativer Versatz von Zeile 3 und 4
	
	private JButton[] buttonLine1 = new JButton[14];
	private String[] bL1String = new String[] {"!", "\"", "§", "$", "%", "&", "/", "(", ")", "=", "?", "#", "€", "ß"};
	private JButton[] buttonLine2 = new JButton[12];
	private String[] bL2String = new String[] {"@", "Q", "W", "E", "R", "T", "Z", "U", "I", "O", "P", "Ü"};
	private JButton[] buttonLine3 = new JButton[11];
	private String[] bL3String = new String[] {"A", "S", "D", "F", "G", "H", "J", "K", "L", "Ö", "Ä"};
	
	private JButton delButton = new JButton("Delete");
	private JButton shiftLockButton = new JButton("v");
	private JButton shiftButton = new JButton("^");
	private JButton enterButton = new JButton("Enter");
	private JButton spaceButton = new JButton("Space");
	
	public KeyBoardLayout() {
		this.setLayout(this);
		for (int i=0; i<buttonLine1.length; i++) {
			buttonLine1[i] = new JButton(bL1String[i]);
			this.add(buttonLine1[i]);
		}
		for (int i=0; i<buttonLine2.length; i++) {
			buttonLine2[i] = new JButton(bL2String[i]);
			this.add(buttonLine2[i]);
		}
		for (int i=0; i<buttonLine3.length; i++) {
			buttonLine3[i] = new JButton(bL3String[i]);
			this.add(buttonLine3[i]);
		}
		this.add(delButton);
		this.add(shiftLockButton);
		this.add(shiftButton);
		this.add(enterButton);
		this.add(spaceButton);
	}
	
	private int standardWidth; // Variable für die optimale Breite normaler Tasten
	public void layoutContainer(Container container) {
		//Bestimmung der optimalen Breite
		if ((container.getBounds().getHeight()/5)/(container.getBounds().getWidth()/14)>ratio)
			standardWidth = container.getWidth()/14;
		else
			standardWidth = (int) (container.getHeight()/ratio/5);
		//Positionieren der einzelnen Tasten
		for (int i=0; i<buttonLine1.length; i++)
			buttonLine1[i].setBounds(i*standardWidth, 0, standardWidth, (int)(standardWidth*ratio));
		for (int i=0; i<buttonLine2.length; i++) {
			buttonLine2[i].setBounds(i*standardWidth, (int)(standardWidth*ratio), standardWidth, (int)(standardWidth*ratio));
		}
		for (int i=0; i<buttonLine3.length; i++) {
			buttonLine3[i].setBounds((i+1)*standardWidth +(int)(standardWidth*inGap), (int)(2*standardWidth*ratio), standardWidth, (int)(standardWidth*ratio));
		}
		
		delButton.setBounds(12*standardWidth, (int)(standardWidth*ratio), 2*standardWidth, (int)(standardWidth*ratio));
		shiftLockButton.setBounds(0, (int)(2*standardWidth*ratio), standardWidth + (int)(standardWidth*inGap), (int)(standardWidth*ratio));
		enterButton.setBounds(12*standardWidth +(int)(standardWidth*inGap), (int)(2*standardWidth*ratio), 2*standardWidth - (int)(standardWidth*inGap), 2*(int)(standardWidth*ratio));
		shiftButton.setBounds(0, (int)(3*standardWidth*ratio), 2*standardWidth + (int)(standardWidth*inGap), (int)(standardWidth*ratio));
		spaceButton.setBounds((int)(4.5d*standardWidth),4*(int)(standardWidth*ratio), 5*standardWidth, (int)(standardWidth*ratio));
	}
	public void removeLayoutComponent(Component arg0) {}
	public void addLayoutComponent(String arg0, Component arg1) {}
	public Dimension minimumLayoutSize(Container arg0) {return new Dimension(0,0);}
	public Dimension preferredLayoutSize(Container arg0) {return new Dimension(0,0);}
	
	public static void main(String[] args) {
		JFrame frame = new JFrame();
		frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		frame.getContentPane().add(new KeyBoardLayout());
		frame.setBounds(50,50,600,250);
		frame.setVisible(true);
	}
}
 

Tobias

Top Contributor
Interessanter Ansatz. Ich bin aber gerade ganz glücklich mit der GridBagLayout-Sache und werde mich vorerst anderen Problemen meines Programms zuwenden. Aber wer weiß, ob ich nicht beim nächsten Refactoring auf diese Idee zurückkomme ...

mpG
Tobias
 

Niki

Top Contributor
Ist bereits mit JButtons gelöst, es wird aber nur GridBagLayout verwendet und trifft deine Skizze sehr genau:
Code:
import java.awt.BorderLayout;
import java.awt.Container;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.Insets;

import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingConstants;
import javax.swing.WindowConstants;

public class KeyboardPanel extends JPanel {

	public KeyboardPanel() {
		Insets i = new Insets(0, 0, 0, 0);
		GridBagConstraints c = new GridBagConstraints(0, 0, 1, 1, 0.0, 0.0,
				GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, i, 0, 0);
		setLayout(new GridBagLayout());

		JPanel firstAndSecond = createFirstAndSecondRow();
		JPanel thirdAndFourth = createThirdAndFourthRow();
		JPanel fifth = createFifthRow();
		JPanel arrows = createArrowKeys();
		JPanel nums = createNumBock();
		add(firstAndSecond, c);
		c.gridy++;
		c.fill = GridBagConstraints.HORIZONTAL;
		add(thirdAndFourth, c);
		c.gridy++;
		add(fifth, c);
		c.gridx++;
		c.gridy = 0;
		c.gridheight = 3;
		c.fill = GridBagConstraints.VERTICAL;
		add(arrows, c);
		c.gridx++;
		c.fill = GridBagConstraints.NONE;
		add(nums, c);
		
	}

	private JPanel createFirstAndSecondRow() {
		JPanel p = new JPanel();
		p.setLayout(new GridBagLayout());

		String[] firstRow = new String[] { "!", "\"", "§", "$", "%", "&", "/",
				"(", ")", "=", "?", "#", "€", "ß" };
		String[] secondRow = new String[] { "@", "Q", "W", "E", "R", "T", "Z",
				"U", "I", "O", "P", "Ü", "Delete" };

		Insets i = new Insets(1, 1, 1, 1);
		GridBagConstraints c = new GridBagConstraints(0, 0, 1, 1, 0.0, 0.0,
				GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, i, 0, 0);

		for (int j = 0; j < firstRow.length; j++) {
			String s = firstRow[j];
			JButton jb = createButton(s, 25, 20);

			if (j == firstRow.length - 1)
				c.weightx = 1.0;
			p.add(jb, c);
			c.gridx++;
		}

		c.weightx = 0.0;
		c.gridx = 0;
		c.gridy++;

		for (int j = 0; j < secondRow.length - 1; j++) {
			String s = secondRow[j];
			JButton jb = createButton(s, 25, 20);
			p.add(jb, c);
			c.gridx++;
		}
		JButton jb = createButton(secondRow[secondRow.length - 1], 25, 20);
		c.gridwidth = 2;
		c.fill = GridBagConstraints.HORIZONTAL;
		p.add(jb, c);

		return p;
	}

	private JPanel createThirdAndFourthRow() {
		JPanel p = new JPanel();
		p.setLayout(new GridBagLayout());
		String[] thirdRow = new String[] { "Lock", "A", "S", "D", "F", "G",
				"H", "J", "K", "L", "Ö", "Ä" };
		String[] fourthRow = new String[] { "Shift", "Y", "X", "C", "V", "B",
				"N", "M", ",", ".", "-" };

		Insets i = new Insets(1, 1, 1, 1);
		GridBagConstraints c = new GridBagConstraints(0, 0, 1, 1, 0.0, 0.0,
				GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, i, 0, 0);

		JButton jb = createButton(thirdRow[0], 35, 20);
		p.add(jb, c);
		c.gridx++;
		for (int j = 1; j < thirdRow.length; j++) {
			String s = thirdRow[j];
			jb = createButton(s, 25, 20);
			p.add(jb, c);
			c.gridx++;
		}
		c.gridx = 0;
		c.gridy++;
		c.gridwidth = 2;
		c.fill = GridBagConstraints.HORIZONTAL;

		jb = createButton(fourthRow[0], 0, 20);
		p.add(jb, c);
		c.gridx += 2;
		c.gridwidth = 1;
		c.fill = GridBagConstraints.NONE;
		for (int j = 1; j < fourthRow.length; j++) {
			String s = fourthRow[j];
			jb = createButton(s, 25, 20);
			p.add(jb, c);
			c.gridx++;
		}

		jb = createButton("Enter", 0, 0);
		c.gridy = 0;
		c.gridheight = 2;
		c.fill = GridBagConstraints.BOTH;
		c.weightx = 1.0;
		c.weighty = 1.0;
		p.add(jb, c);

		return p;
	}

	private JPanel createFifthRow() {
		JPanel p = new JPanel();
		p.setLayout(new GridBagLayout());

		Insets i = new Insets(1, 1, 1, 1);
		GridBagConstraints c = new GridBagConstraints(0, 0, 1, 1, 0.0, 0.0,
				GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, i, 0, 0);

		JButton jb = createButton("Space", 150, 20);
		c.anchor = GridBagConstraints.NORTH;
		c.weightx = 1.0;

		p.add(jb, c);
		jb = createButton("<", 25, 20);
	
		c.anchor = GridBagConstraints.NORTHWEST;
		c.weightx = 0.0;
		c.gridx++;
		p.add(jb, c);

		return p;
	}
	
	private JPanel createArrowKeys() {
		JPanel p = new JPanel();
		p.setLayout(new GridBagLayout());

		Insets i = new Insets(1, 1, 1, 1);
		GridBagConstraints c = new GridBagConstraints(0, 0, 1, 1, 0.0, 0.0,
				GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, i, 0, 0);
		
		JButton jb = createButton("^", 25, 20);
		
		c.anchor = GridBagConstraints.SOUTHWEST;
		c.weighty = 1.0;
		p.add(jb, c);
		c.anchor = GridBagConstraints.NORTHWEST;
		c.weighty = 0.0;
		jb = createButton("v", 25, 20);
		c.gridy++;
		p.add(jb, c);
		jb = createButton(">", 25, 20);
		c.gridx++;
		p.add(jb, c);
		
		
		return p;
	}
	
	private JPanel createNumBock() {
		JPanel p = new JPanel();
		p.setLayout(new GridBagLayout());

		Insets i = new Insets(1, 1, 1, 1);
		GridBagConstraints c = new GridBagConstraints(0, 0, 1, 1, 0.0, 0.0,
				GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, i, 0, 0);
		
		String[] s = new String[]{",", "/", "*", "-", "7", "8", "9", "4", "5", "6", "1", "2", "3"};
		
		JButton jb = null;
		for(int j = 0; j < 4; j++){
			jb = createButton(s[j], 25, 20);
			p.add(jb, c);
			c.gridx++;
		}
		c.gridy++;
		c.gridx=0;
		for(int j = 4; j < 7; j++){
			jb = createButton(s[j], 25, 20);
			p.add(jb, c);
			c.gridx++;
		}
		c.gridy++;
		c.gridx=0;
		for(int j = 7; j < 10; j++){
			jb = createButton(s[j], 25, 20);
			p.add(jb, c);
			c.gridx++;
		}
		c.gridy++;
		c.gridx=0;
		for(int j = 10; j < 13; j++){
			jb = createButton(s[j], 25, 20);
			p.add(jb, c);
			c.gridx++;
		}
		
		jb = createButton("+", 25, 0);
		c.gridx = 3;
		c.gridy = 1;
		c.gridheight = 2;
		c.fill = GridBagConstraints.VERTICAL;
		p.add(jb, c);
		
		jb = createButton("0", 0, 20);
		c.gridx = 0;
		c.gridy = 4;
		c.fill = GridBagConstraints.HORIZONTAL;
		c.gridwidth = 2;
		c.gridheight = 1;
		p.add(jb, c);
		
		jb = createButton("Entf", 0, 20);
		jb.setFont(new Font("Dialog", Font.PLAIN, 10));
		c.gridx = 2;		
		c.fill = GridBagConstraints.HORIZONTAL;
		c.gridwidth = 1;
		p.add(jb, c);
		
		jb = createButton("Enter", 25, 0);
		
		jb.setFont(new Font("Dialog", Font.PLAIN, 8));
		c.gridx = 3;		
		c.gridy = 3;
		c.fill = GridBagConstraints.VERTICAL;		
		c.gridheight = 2;
		p.add(jb, c);
		
		
		return p;
	}

	private JButton createButton(String s, int w, int h) {
		Dimension dim = new Dimension(w, h);
		JButton b = new JButton(s);
		b.setHorizontalTextPosition(SwingConstants.CENTER);
		b.setMinimumSize(dim);
		b.setMaximumSize(dim);
		b.setPreferredSize(dim);
		b.setMargin(new Insets(0, 0, 0, 0));
		return b;
	}

	public static void main(String[] args) {
		JFrame f = new JFrame("Keyboard");

		Container cont = f.getContentPane();
		cont.setLayout(new BorderLayout());
		cont.add(new KeyboardPanel(), BorderLayout.CENTER);

		f.pack();
		f.setLocationRelativeTo(null);
		f.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
		f.setVisible(true);
	}
}
 
Status
Nicht offen für weitere Antworten.
Ähnliche Java Themen
  Titel Forum Antworten Datum
T GridBagLayout Anfängerprobleme AWT, Swing, JavaFX & SWT 3
S GridBagLayout Felder formatieren AWT, Swing, JavaFX & SWT 1
S GridBagLayout - Probleme mit Bilderanzeige AWT, Swing, JavaFX & SWT 3
C GridbagLayout verstehen lernen AWT, Swing, JavaFX & SWT 1
H GridBagLayout macht mich wahnsinnig :-( AWT, Swing, JavaFX & SWT 5
BabySuna darstellungsprobleme mit JTabbedPane und GridBagLayout AWT, Swing, JavaFX & SWT 8
CptK Positionieren von Elementen in GridBagLayout AWT, Swing, JavaFX & SWT 4
A Probleme mit gridheight (GridBagLayout) AWT, Swing, JavaFX & SWT 6
Mario1409 AWT GridBagLayout AWT, Swing, JavaFX & SWT 5
J LayoutManager GridBagLayout, probleme mit Anordnung von Objekten AWT, Swing, JavaFX & SWT 6
DaCrazyJavaExpert Swing Komponenten in GridBagLayout werden Falsch angeordnet AWT, Swing, JavaFX & SWT 1
T LayoutManager Anordnen der Elemente im GridBagLayout AWT, Swing, JavaFX & SWT 11
K GridBagLayout mit reponsive Design AWT, Swing, JavaFX & SWT 2
K GridBagLayout verändert die größe? AWT, Swing, JavaFX & SWT 1
D Swing Größe einer JComboBox im GridBagLayout aufgrund der maximalen Länge der enthaltenen Daten AWT, Swing, JavaFX & SWT 7
B LayoutManager GridBagLayout und JScrollPane AWT, Swing, JavaFX & SWT 5
Sin137 LayoutManager GridBagLayout Probleme AWT, Swing, JavaFX & SWT 6
L GridBagLayout Anordnung AWT, Swing, JavaFX & SWT 3
M Gridbaglayout Spaltenbreite AWT, Swing, JavaFX & SWT 3
M LayoutManager GridBagLayout passt seine größe nicht an AWT, Swing, JavaFX & SWT 3
V GridBagLayout AWT, Swing, JavaFX & SWT 4
N LayoutManager GridBagLayout - Grundlagen AWT, Swing, JavaFX & SWT 6
Neumi5694 Swing Gridbaglayout - automatische Anpassung verhindern AWT, Swing, JavaFX & SWT 1
P AWT Problem mit Platzierung (GridBagLayout) AWT, Swing, JavaFX & SWT 2
F Breite beim GridBagLayout festlegen AWT, Swing, JavaFX & SWT 2
M Swing GridBagLayout Komponentengröße festsetzen AWT, Swing, JavaFX & SWT 1
J GridBagLayout mit Hilfe einer For-Schleife befüllen AWT, Swing, JavaFX & SWT 1
W GridBagLayout Größe geben AWT, Swing, JavaFX & SWT 1
HarleyDavidson Swing Seltsames Verhalten GridBagLayout AWT, Swing, JavaFX & SWT 11
W GridBagLayout mit fester Zellgrösse AWT, Swing, JavaFX & SWT 2
N Swing GridBagLayout: Ein Pixel Versatz AWT, Swing, JavaFX & SWT 2
B Swing Gridbaglayout unterschiedliche Zeilenhöhe AWT, Swing, JavaFX & SWT 6
H LayoutManager GridBagLayout AWT, Swing, JavaFX & SWT 1
N GridBagLayout - was fehlt? AWT, Swing, JavaFX & SWT 8
S Swing rowHeight und rowWeight im GridBagLayout AWT, Swing, JavaFX & SWT 1
N Swing GUI mit GridBagLayout AWT, Swing, JavaFX & SWT 4
A jpanel mit gridbaglayout auf hintergrundbild AWT, Swing, JavaFX & SWT 7
S GridBagLayout-Frage AWT, Swing, JavaFX & SWT 1
G GridBagLayout AWT, Swing, JavaFX & SWT 6
S GridBagLayout "links-rechts-layouten" AWT, Swing, JavaFX & SWT 7
T LayoutManager GridBagLayout / erwartetes Raster fehlt AWT, Swing, JavaFX & SWT 3
X Gridbaglayout gridx + gridy auslesen? AWT, Swing, JavaFX & SWT 7
H GridBagLayout macht Probleme... AWT, Swing, JavaFX & SWT 4
N GridBagLayout - Zeitplan AWT, Swing, JavaFX & SWT 13
N Swing GridbagLayout AWT, Swing, JavaFX & SWT 4
S Swing gridbaglayout AWT, Swing, JavaFX & SWT 8
G GridBagLayout Problem AWT, Swing, JavaFX & SWT 4
Java-Insel LayoutManager Ein GridBagLayout-Objekt für mehrere Panels? AWT, Swing, JavaFX & SWT 2
X LayoutManager gridBagLayout wird nicht richtig Dargestellt AWT, Swing, JavaFX & SWT 5
das-mo Probleme mit GridBagLayout AWT, Swing, JavaFX & SWT 6
T LayoutManager GridBagLayout - zwei jTable mit unterschiedlicher Höhe AWT, Swing, JavaFX & SWT 2
N LayoutManager GridBagLayout schummeln erlaubt ? AWT, Swing, JavaFX & SWT 2
D GridBagLayout AWT, Swing, JavaFX & SWT 9
A Swing GridBagLayout - constraints.anchor scheint nicht korrekt zu funktionieren? AWT, Swing, JavaFX & SWT 7
J Swing Terminkalender Wochenansicht mit Gridbaglayout oder JTable AWT, Swing, JavaFX & SWT 16
C LayoutManager GridBagLayout - Anfängerfrage AWT, Swing, JavaFX & SWT 5
Asamandra LayoutManager GridBagLayout - Komponenten (mit fill?) vergrößern aber Proportionen dabei erhalten? AWT, Swing, JavaFX & SWT 3
R GridBagLayout in GridBagLayout AWT, Swing, JavaFX & SWT 2
H Positionierungsprobleme beim GridBagLayout AWT, Swing, JavaFX & SWT 16
Furtano AWT GridBagLayout macht mir Sorgen AWT, Swing, JavaFX & SWT 3
A GridbagLayout positionierungsproblem AWT, Swing, JavaFX & SWT 4
earlgrey_tea GridBagLayout Componenten proportional vergößern AWT, Swing, JavaFX & SWT 12
D JTable im GridBagLayout -> gridwidth AWT, Swing, JavaFX & SWT 6
T GridBagLayout Problem AWT, Swing, JavaFX & SWT 3
D Probleme mit GridBagLayout AWT, Swing, JavaFX & SWT 8
J Swing GridBagLayout: Links-nach-rechts Orientierung statt zentriert AWT, Swing, JavaFX & SWT 12
R Größe eines Labels bei GridBagLayout festlegen AWT, Swing, JavaFX & SWT 9
B GridBagLayout Problem AWT, Swing, JavaFX & SWT 3
M LayoutManager GridBagLayout AWT, Swing, JavaFX & SWT 11
E LayoutManager GridBagLayout in BorderLayout - Abstand bei Resizing AWT, Swing, JavaFX & SWT 2
Y LayoutManager Keine vollständige Darstellung der Tabelle mit GridBagLayout AWT, Swing, JavaFX & SWT 3
L LayoutManager GridBagLayout leere Zeilen AWT, Swing, JavaFX & SWT 4
H LayoutManager Layout mit GridBagLayout machbar? AWT, Swing, JavaFX & SWT 6
N GridBagLayout Problem AWT, Swing, JavaFX & SWT 6
C Swing JTable "zerstört" GridBagLayout AWT, Swing, JavaFX & SWT 9
N LayoutManager GridBagLayout Größe fixieren AWT, Swing, JavaFX & SWT 3
M GridBagLayout AWT, Swing, JavaFX & SWT 7
V Swing Gridbaglayout Leeres Fenster AWT, Swing, JavaFX & SWT 2
R LayoutManager GridBagLayout Fragen AWT, Swing, JavaFX & SWT 10
P LayoutManager Verständnis-Frage GridBagLayout AWT, Swing, JavaFX & SWT 7
M LayoutManager Einige Fragen zum GridBagLayout AWT, Swing, JavaFX & SWT 13
N GridBagLayout AWT, Swing, JavaFX & SWT 11
D Swing Problem mit Gridbaglayout bzw. Größenanpassung JPanels AWT, Swing, JavaFX & SWT 7
Y Swing GridbagLayout JTextfield zu klein AWT, Swing, JavaFX & SWT 5
L LayoutManager GridBagLayout spielt verrückt AWT, Swing, JavaFX & SWT 9
T LayoutManager GridBagLayout an Fenstergröße anpassen AWT, Swing, JavaFX & SWT 2
J Java GUI mit GridBagLayout AWT, Swing, JavaFX & SWT 3
Y LayoutManager Problem mit Gridbaglayout AWT, Swing, JavaFX & SWT 8
hdi LayoutManager GridBagLayout AWT, Swing, JavaFX & SWT 9
W GridBagLayout Falsche Größenanpassung AWT, Swing, JavaFX & SWT 6
R Swing Button-Größe in JPanel mit GridBagLayout nicht änderbar AWT, Swing, JavaFX & SWT 3
E Problem mit meiner GUI/GridbagLayout AWT, Swing, JavaFX & SWT 2
M LayoutManager GradientPaint auf GridBagLayout AWT, Swing, JavaFX & SWT 5
D LayoutManager GridBagLayout, Änderung zur Laufzeit AWT, Swing, JavaFX & SWT 4
G LayoutManager per Button GridBagLayout + Inhalt ändern AWT, Swing, JavaFX & SWT 2
M GridBagLayout zeilenweise füllen AWT, Swing, JavaFX & SWT 5
B Anzeigefehler in GridBagLayout durch paintComponent(Graphics g) AWT, Swing, JavaFX & SWT 3
hdi Swing Problem mit GridBagLayout AWT, Swing, JavaFX & SWT 2
E LayoutManager GridBagLayout kurz vorm Wahnsinn! AWT, Swing, JavaFX & SWT 22
P Swing GridBagLayout bleibt nicht so wie es ist :( AWT, Swing, JavaFX & SWT 8

Ähnliche Java Themen

Neue Themen


Oben