Grafiskt användargränssnitt (GUI-Graphical User Interface) intro Komponenter De komponenter som vi ska titta lite närmare på den här gången är paneler (JPanel), knappar (JButton), textfält (JTextField). Vi fortsätter att använda det mer sofistikerade Swing-paketet, därav J framför klassnamnen. Applikationsfönster (frames) är i sig en behållare och det skulle gå att lägga andra komponenter direkt i fönstret men det är ingen bra sätt att programmera på, utan det bästa här är att skapa en panel (se nedan) och lägga in i fönstret. Det ska man placera i ett lager i fönstert som kallas content pane, som vi måste ta reda på när vi skapat ett fönster. Container contentpane = frame.getcontentpane(); Men mer om detta senare i koden. Panel En panel är en yta som det går att rita och skriva på. Dessutom är den en behållare (containers) för andra komponenter. För att lägga till en panel i vårt fönster skriver vi: JPanel p = new JPanel(); Om vi vill skriva och rita i på vår yta så behöver vi också överlagra ( vi ärver den och förtydligar den) en metod med namnet paintcomponent i vår definiering av vår JPanel-klass. Ex. : class MyPanel extends Jpanel { public void paintcomponent(graphics g) { //kod för att rita och skriva När vi utnyttjar den här metoden får vi köpet med en massa intelligenta funktioner. T ex om ändrar storleken på vårt fönster så känner den av det och ritar om ytan eller om ett annat fönster(t ex vårt utvecklingsmiljöfönster) täcker vårt fönster och vi sen tar bort det så ritar den också om ytan så den alltid är up to date. Dags för första programmet med något inuti vårt fönster Vi bygger vidare på vårt terminerande fönster från förra lektionen. Vårt mål är att skriva ut Tjenare! på skärmen. Det nya är fetmarkerat. package textinwindow; import java.awt.*; import java.awt.event.*; import javax.swing.*; class MyPanel extends JPanel { public void paintcomponent(graphics g) { // för att vara säker på att "super"-klassen gör sitt // anropar vi den metoden, innan vi skriver eller ritar super.paintcomponent(g); //skriv ut en textsträng, samt ange läget i avståndet från //övre vänstra hörnet i x-led åt höger och i y-led neråt g.drawstring(" ** Tjenare kompis!! ** ", 50, 100); class TextInWindow extends JFrame { public TextInWindow() /PB Sida 1
{ settitle("text i vårt fönster"); Toolkit tk = Toolkit.getDefaultToolkit(); Dimension d = tk.getscreensize(); int screenheight = d.height; int screenwidth = d.width; setsize(screenwidth/2,screenheight/2); //(bredd,höjd) setlocation(screenwidth/4, screenheight/4); MyPanel p = new MyPanel(); setvisible(true); setdefaultcloseoperation(exit_on_close); public class TestTextInWindow { public static void main(string args[]) { JFrame mywindow = new TextInWindow(); Alltid något, sakta men säkert framåt. Nu ska vi gå igenom två komponenter i rask takt som vi sen ska placera i vårt fönster. Knappar Den typ av knappar det är frågan om här är alltså vanliga trycknappar som kan tryckas ned för att utföra kommandon eller svara på frågor, exempel på två "kändisknappar" är OK och Avbryt. För att skapa knappen okknapp med texten OK skriver man bara följande: JButton okknapp = new JButton("OK"); Texten som man vill ska stå på knappen anger man alltså som argument till klassen JButtons konstruktormetod. Tyvärr har vi ännu bara fått den visuella knappen och ingen händelse är kopplad till den. Men det kommer. För att t.ex. lägga till knappen okknapp skriver vi bara: add(okknapp); Vi behöver också en händelselyssnare som märker när vi klickar på knappen. okknapp.addactionlistener( this); samt lite mer kod för att ta hand om klicket mer om detta i själva programmet, där vi bättre ser var delarna hamnar. Dags för nästa program med tre knappar Nu ska vi lägga in tre knappar, i vårt förra program, som ställer om färgen på vår bakgrund i fönstret. Det nya är fetmarkerat. Allt det nya hamnar i vår klass MyPanel. package buttontest; import java.awt.*; import java.awt.event.*; import javax.swing.*; class MyPanel extends JPanel implements ActionListener { //Till vår panel måste vi koppla en händelselyssnare, därav "implements // ActionListener" ovan. //Vi måste deklarera våra knappar JButton redbutton; JButton yellowbutton; JButton greenbutton; /PB Sida 2
//Vi måste skapa en egen konstruktor för vår panel, som ju körs endast //när vi skapar ett objekt av denna klass. Vi vill ju att när vi skapar //panelen ska också knappar skapas automatiskt. public MyPanel() { //Skapa knapparna redbutton = new JButton("Rött"); yellowbutton = new JButton("Gult"); greenbutton = new JButton("Grönt"); //lägg till dom till det här panelobjektet add(redbutton); add(yellowbutton); add(greenbutton); //koppla på panelens händelselyssnare redbutton.addactionlistener(this); yellowbutton.addactionlistener(this); greenbutton.addactionlistener(this); //Ifall något händer dvs vi klickar på någon av knapparna, så går ett //meddelande till till vår ActionListener. OM detta inträffar så måste //vi ju ta hand om detta och göra något. Vi skriver en metod för det. public void actionperformed(actionevent evt) { Object source = evt.getsource(); //hämta händelsekälla //Definiera en variabel som innehåller en färg Color color=getbackground(); //Testa vilken av knapparna vi tryckte på och //ge variabeln color en färg if (source==redbutton) color=color.red; else if (source==yellowbutton) color=color.yellow; else if (source==greenbutton) color=color.green; setbackground(color); //sätt om färgen på aktuell panel repaint(); //rita om aktuell panel public void paintcomponent(graphics g) { // för att vara säker på att "super"-klassen gör sitt // anropar vi den metoden, innan vi skriver eller ritar super.paintcomponent(g); //skriv ut en textsträng, samt ange läget i avståndet från //övre vänstra hörnet i x-led åt höger och i y-led neråt g.drawstring(" ** Tjenare kompis!! ** ", 50, 100); class TextInWindow extends JFrame { public TextInWindow() { settitle("text i vårt fönster + 3 knappar"); Toolkit tk = Toolkit.getDefaultToolkit(); Dimension d = tk.getscreensize(); int screenheight = d.height; int screenwidth = d.width; setsize(screenwidth/2,screenheight/2); //(bredd,höjd) setlocation(screenwidth/4, screenheight/4); MyPanel p = new MyPanel(); setvisible(true); setdefaultcloseoperation(exit_on_close); /PB Sida 3
public class ButtonTest { public static void main(string args[]) { JFrame mywindow = new TextInWindow(); Som du såg så dök det upp nya saker som Object och Color. Vi går inte närmare in på dessa utan konstaterar enbart att variabeln color(här hos oss) är av typen Color och det finns ett antal standardfärger att använda med punktnotation. black, blue, cyan, darkgray, gray, green, lightgray, magenta, orange, pink, red, white, yellow Nu är det nog dags att öva lite, men för den som är snabb så kommer ytterliggare ett program. Ytterliggare utökad applikation med textfält Textfält Ett textfält är helt enkelt ett litet en raders utrymme där användaren kan skriva in text eller programmet skriva ut text. För att skapa textfältet namn med utrymme för 12 tecken skriver man: JTextField textruta = new JTextField( 12 ); När sedan användaren t.ex. skrivit in sitt namn i fältet kan man läsa in namnet till programmet genom att anropa metoden gettext, man skriver alltså: namn = textruta.gettext( ); vi kan också skriva i fältet med metoden settext om vill med textruta.settext( Här står något roligt! ); För att t.ex. lägga till textfältet textruta skriver vi: add(textruta); Nu ska vi utöka applikationen ett textfält som vi kan skriva text i från både programmet och från tangentbordet när vi kör applikationen, och sen en knapp som heter Hälsa fint. Den första textsträngen har stylats lite. Ny kod är fetmarkerad. package testtextinwindow2; import java.awt.*; import java.awt.event.*; import javax.swing.*; class MyPanel extends JPanel implements ActionListener {//Till vår panel måste vi koppla en händelselyssnare, därav "implements // ActionListener" ovan. //Vi måste deklarera våra knappar JButton redbutton; JButton yellowbutton; JButton greenbutton; JButton greetingsbutton; JTextField textruta; //Vi måste skapa en egen konstruktor för vår panel, om ju körs endast //när vi skapar ett objekt av denna klass.vi vill ju att när vi //skapar panelen ska också knappar skapas. public MyPanel() { /PB Sida 4
//Skapa knapparna redbutton = new JButton("Rött"); yellowbutton = new JButton("Gult"); greenbutton = new JButton("Grönt"); greetingsbutton = new JButton("Hälsa fint!"); //Skapa textfältet textruta = new JTextField(30); textruta.settext(" Skriv in ditt namn här! "); //lägg till färgknapparna till det här panelobjektet add(redbutton); add(yellowbutton); add(greenbutton); //lägg till textfältet och hälsningsknappen add(textruta); add(greetingsbutton); //koppla på panelens händelselyssnare redbutton.addactionlistener(this); yellowbutton.addactionlistener(this); greenbutton.addactionlistener(this); greetingsbutton.addactionlistener(this); //Ifall något händer dvs vi klickar på någon av knapparna, så går ett //meddelande till till vår ActionListener.OM detta inträffar så måste //vi ju ta hand om detta och göra något. Vi skriver en metod för det. public void actionperformed(actionevent evt) { Object source = evt.getsource(); //hämta händelsekälla //Definiera en variabel som innehåller en färg Color color=getbackground(); //Testa vilken av knapparna vi tryckte på och //ge variabeln color en färg if (source==redbutton) color=color.red; else if (source==yellowbutton) color=color.yellow; else if (source==greenbutton) color=color.green; else if (source==greetingsbutton) { color=color.magenta; String namn=textruta.gettext(); String rad=" ** Tjenare "+namn+"!! ** "; textruta.settext(rad); setbackground(color); //sätt om färgen på aktuell panel repaint(); //rita om aktuell panel public void paintcomponent(graphics g) { // för att vara säker på att "super"-klassen gör sitt // anropar vi den metoden, innan vi skriver eller ritar super.paintcomponent(g); //skriv ut en textsträng, samt ange läget i avståndet från //övre vänstra hörnet i x-led åt höger och i y-led neråt Font myfont = new Font("SansSerif",Font.BOLD,16); g.setfont(myfont); g.drawstring(" Test av knappar och textfält! ", 50, 150); class TextInWindow extends JFrame { public TextInWindow() { settitle("textfält och knappar i vårt fönster"); Toolkit tk = Toolkit.getDefaultToolkit(); Dimension d = tk.getscreensize(); /PB Sida 5
int screenheight = d.height; int screenwidth = d.width; setsize(screenwidth/2,screenheight/2); //(bredd,höjd) setlocation(screenwidth/4, screenheight/4); MyPanel p = new MyPanel(); setvisible(true); setdefaultcloseoperation(exit_on_close); public class TestTextInWindow2 { public static void main(string args[]) { JFrame mywindow = new TextInWindow(); Ja, mycket kod blir det!! /PB Sida 6
Övningar Övning 1 Skriv in koden för den första applikationen (den som skriver en textsträng på skärmen) och få det att fungera. Samt försök häng med på vad koden betyder eller åtminstone vad de olika delarna gör. Övning 2 Skriv in (komplettera din tidigare kod) koden för den andra applikationen (den med de tre knapparna) och få det att fungera. Samt försök häng med på vad koden betyder eller åtminstone vad de olika delarna gör. Övning 3 Skriv in (komplettera din tidigare kod) koden för den sista applikationen (den med textfältet och ytterliggare en knapp) och få det att fungera. Samt försök häng med på vad koden betyder eller åtminstone vad de olika delarna gör. Övning 4 Utöka applikationen från förra övningen med fler textsträngar och fler knappar. Övning 5 Lek fritt med dessa komponenter. Eventuellt titta i boken och se om du kan förstå hur man fixar ytterliggare komponenter eller via Internet. /PB Sida 7