Lekce 5 - Layouty v Java Swing
V minulé lekci, Java GUI, jsme si ukázali GridBagLayout a také to, jak obsluhovat více tlačítek.
V dnešním tutoriálu si popíšeme práci s tzv. layouty. Java má pro lepší práci s komponentami k dispozici 8 layoutů. Každý má svůj vlastní účel a hodí se na něco jiného. Jejich seznam je následující:
- FlowLayout
- BoxLayout
- BorderLayout
- CardLayout
- GridBagLayout
- GridLayout
- GroupLayout
- SpringLayout
Všechny výše zmiňované layouty si postupně popíšeme a pokusím se zmínit hlavně jejich výhody.
FlowLayout

Tento layout staví komponenty vedle sebe na řádek. Pokud šířka komponentů přesáhne šířku okna, řádek se zalomí a komponenty se začnou řadit na dalším řádku.
Konstruktor:
FlowLayout fl = new FlowLayout(); // základní nastavení komponenty centruje na střed FlowLayout fl = new FlowLayout(argument); //druhá verze konstruktoru
Argument může nabývat následujících hodnot:
- FlowLayout.LEFT = komponenty se řadí od levé strany.
- FlowLayout.RIGHT = komponenty se řadí na pravou stranu.
- FlowLayout.CENTER = komponenty se řadí na střed. (základní nastavení)
Existují ještě argumenty (FlowLayout.LEADING - řazení od horní strany a FlowLayout.TRAILING - řazení od dolní strany).
FlowLayout fl = new FlowLayout(argument, int horizontal, int vertical); // tretí verze konstruktoru.
- horizontal = vodorovná mezera mezi jednotlivými komponentami a mezera mezi komponentami a postranním rámem kontejneru.
- vertical = svislá mezera mezi komponentami a horním rámem kontejneru.
BoxLayout

Tento layout rovná komponenty vedle sebe, nebo za sebou podle nastavení.
Konstruktor:
Container pane = this.getContentPane(); pane.setLayout(new BoxLayout(pane, args));
args = rozložení komponentů. Může nabývat následujících hodnot:
- BoxLayout.PAGE_AXIS - seřadí komponenty od shora dolů.
- BoxLayout.LINE_AXIS - seřadí komponenty vedle sebe.
Vlastnosti:
rigid area = pevná plocha - použijeme, pokud chceme zaplnit velikost mezi dvěma komponentami. Slouží k tomu příkaz: Box.createRigidArea(new Dimension(x,y)); Zkusme si následující příklad:
Container pane = this.getContentPane(); pane.setLayout(new BoxLayout(pane, BoxLayout.PAGE_AXIS)); JButton prvni = new JButton("prvni"); JButton druhy = new JButton("druhy"); pane.add(prvni); pane.add(Box.createRigidArea(new Dimension(5,10))); pane.add(druhy);
glue - Použijeme, když chceme komponenty od sebe roztáhnout. Každou komponentu na jinou stranu. Slouží k tomu dva příkazy:
- Box.createHorizontalGlue(); // vodorovné odsazení
- Box.createVerticalGlue(); // svislé odsazení
Opět uvedu příklad:
Container pane = this.getContentPane(); pane.setLayout(new BoxLayout(pane, BoxLayout.PAGE_AXIS)); JButton prvni = new JButton("prvni"); JButton druhy = new JButton("druhy"); pane.add(prvni); pane.add(Box.createVerticalGlue()); pane.add(druhy);
custom Box.Filler - nastavuje se zde minimální, preferovaná a maximální velikost. Např:
Container pane = this.getContentPane(); pane.setLayout(new BoxLayout(pane, BoxLayout.PAGE_AXIS)); pane.add(prvni); Dimension min = new Dimension(5, 5O); Dimension pref = new Dimension(5, 100); Dimension max = new Dimension(20, 100); pane.add(new Box.Filler(min, pref, max)); pane.add(druhy);
BorderLayout
BorderLayout je rozdělen na 5 částí (tzv. oblasti), do kterých můžeme přidávat komponenty a to následující:
- PAGE_START
- LINE_START
- CENTRUM
- LINE_END
- PAGE_END
Pro lepší představu vám přikládám obrázek, který vystihuje rozložení všech pěti částí BorderLayoutu.

Tento layout funguje tak, že oblast CENTRUM se roztáhne tolik, kolik je jí dovoleno a ostatní oblasti se roztáhnou jen natolik, kolik je potřeba. Ukážeme si jak to vypadá v praxi.
Container pane = this.getContentPane(); pane.setLayout(new BorderLayout()); JButton prvni = new JButton("prvni"); JButton druhy = new JButton("druhy"); JButton treti = new JButton("treti"); pane.add(prvni, BorderLayout.PAGE_START); pane.add(druhy, BorderLayout.CENTER); pane.add(treti, BorderLayout.LINE_END);
Tenhto layout je hodně používaný, protože do jednotlivých částí můžeme přidat jiné layouty. Např do části LINE_END můžeme přidat BoxLayout. Do části PAGE_START můžeme přidat CardLayout atd.
CardLayout

Tento layout slouží k přepínání komponent, které sdílí v jednom programu stejný prostor. Vidět je pouze jeden panel. Pokud si do panelu s cardLayoutem uložíme třeba 10 panelů, které budou obsahovat rozdílné komponenty, můžeme přepínat, ale viditelný bude vždy jen jeden.
Tentokrát uvedu trochu rozsáhlejší příklad. Doufám, že to z něj pochopíte. Nejdříve si napíšeme třídu MyFrame, ve které si nadefinujeme náš formulář.
import javax.swing.*; import javax.swing.border.*; // importotváno kvůli rámu import java.awt.*; import java.awt.event.*; // importováno kvůli nastavení událostí public class MyFrame extends JFrame { JPanel card; JPanel hlavniPanel; JPanel panel1, panel3; JPanel panel2; CardLayout cards; JButton dalsi,predchozi; JLabel a; JButton o, but; public MyFrame() { this.setTitle("cardLayout"); this.setSize(500, 300); this.setKomponents(); this.setListeners(); } public void setKomponents(){ Container pane = this.getContentPane(); pane.setLayout(new BorderLayout()); Border outline = BorderFactory.createLineBorder(Color.black); // nastavení borderu this.hlavniPanel = new JPanel(); this.hlavniPanel.setBorder(outline); this.dalsi = new JButton(">>"); this.predchozi = new JButton("<<"); this.hlavniPanel.add(this.predchozi); this.hlavniPanel.add(this.dalsi); pane.add(this.hlavniPanel, BorderLayout.PAGE_START); cards = new CardLayout(); card = new JPanel(); card.setLayout(cards); cards.show(card, "Vybíráme"); /** * definice panelů a komponentů uvnitř CardLayoutu */ panel1 = new JPanel(); panel1.setBackground(Color.YELLOW); this.a = new JLabel("blablabla"); this.a.setBackground(Color.GREEN); panel1.add(this.a); panel2 = new JPanel(); panel2.setBackground(Color.RED); this.o = new JButton("pokus"); panel2.add(this.o); panel3 = new JPanel(); panel3.setBackground(Color.BLUE); this.but = new JButton("pokusU2"); panel3.add(this.but); /** * přidání panelů */ card.add(panel1, "první"); card.add(panel2, "druhý"); card.add(panel3, "třetí"); pane.add(card, BorderLayout.CENTER); } public void setListeners(){ this.dalsi.addActionListener( new ActionListener() { public void actionPerformed(ActionEvent e){ cards.next(card); } }); this.predchozi.addActionListener( new ActionListener(){ public void actionPerformed(ActionEvent e){ cards.previous(card); } }); } public static Frame nastav(){ MyFrame i = new MyFrame(); i.setLocationRelativeTo(null); i.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); i.setVisible(true); return i; } }
Poté spustíme program přes třídu Start, kterou si teď nastavíme:
public class Start { public static void main(String args[]){ MyFrame.nastav(); } }
Můžeme si samozřejmě nastavit více druhů ovládání. Přepínat panely po jednom, nebo dokonce na začátek a na konec. To se může hodit, pokud by náš Cardlayout obsahoval větší množství panelů. Pro přehlednost vypíšu všechny funkce:
- first() - přepne na první panel
- previous() - přepne na předchozí panel
- next() - přepne na následující panel
- last() - přepne na poslední panel
- show () - můžeme volat konkrétní panel pomocí příkazů show(param); param = název panelu, který se má zobrazit.
Všechny obrázky které jsem použil(kromě obrázku BorderLayoutu), pochází ze stránky http://docs.oracle.com/…/visual.html
Ostatní layouty si ukážeme v dalším díle, Layouty v Javě (podruhé). Pro úplnost přikládám zdrojový kód k poslední ukázce práce s CardLayoutem.
Měl jsi s čímkoli problém? Stáhni si vzorovou aplikaci níže a porovnej ji se svým projektem, chybu tak snadno najdeš.
Stáhnout
Stažením následujícího souboru souhlasíš s licenčními podmínkami
Staženo 346x (5.13 kB)
Aplikace je včetně zdrojových kódů v jazyce Java