Docsity
Docsity

Prepara i tuoi esami
Prepara i tuoi esami

Studia grazie alle numerose risorse presenti su Docsity


Ottieni i punti per scaricare
Ottieni i punti per scaricare

Guadagna punti aiutando altri studenti oppure acquistali con un piano Premium


Guide e consigli
Guide e consigli


GUI Java - Programmazione ad Oggetti, Appunti di Programmazione Java

Spiegazione di come è composta la GUI in Java e come si usa, con esempi. In fine link utili per il progetto.

Tipologia: Appunti

2020/2021

In vendita dal 06/03/2021

Informatico-UPO
Informatico-UPO 🇮🇹

4.4

(34)

42 documenti

1 / 16

Toggle sidebar

Questa pagina non è visibile nell’anteprima

Non perderti parti importanti!

bg1
GUI (Graphical User Interface)
Il primo package Java che gestisce gli elementi di una GUI1 è awt. Gli elementi di una GUI si distinguono in
oggetti di due tipi:
oggetti contenitori
oggetti componenti
Java usa un sistema generico per gestire la grafica, in modo da costruire programmi eseguibili su varie
piattaforme e con ambienti grafici differenti. Il secondo pakage che gestisce gli elementi di una GUI, detto
swing, è un'estensione di awt e permette la vera indipendenza dalla piattaforma.
Tra i tipici oggetti contenitori il package awt rende disponibili:
frame (finestra): la classica finestra costituita da un’area rettangolare e da una barra del titolo
panel (pannello): la forma più comune di contenitore che può essere visualizzato sullo schermo.
canvas (area di disegno): una semplice superficie di disegno particolarmente utile per visualizzare
immagini o per effettuare altre operazioni grafiche.
I componenti sono oggetti con una propria rappresentazione grafica. Alcuni importanti componenti della
GUI di Java sono:
Label (etichette)
Button (pulsanti)
TextField (campi di testo)
TextArea (aree di testo)
Checkbox (caselle di controllo)
pf3
pf4
pf5
pf8
pf9
pfa
pfd
pfe
pff

Anteprima parziale del testo

Scarica GUI Java - Programmazione ad Oggetti e più Appunti in PDF di Programmazione Java solo su Docsity!

GUI (Graphical User Interface)

Il primo package Java che gestisce gli elementi di una GUI1 è awt. Gli elementi di una GUI si distinguono in oggetti di due tipi:

  • oggetti contenitori
  • oggetti componenti Java usa un sistema generico per gestire la grafica, in modo da costruire programmi eseguibili su varie piattaforme e con ambienti grafici differenti. Il secondo pakage che gestisce gli elementi di una GUI, detto swing, è un'estensione di awt e permette la vera indipendenza dalla piattaforma. Tra i tipici oggetti contenitori il package awt rende disponibili:
  • frame (finestra): la classica finestra costituita da un’area rettangolare e da una barra del titolo
  • panel (pannello): la forma più comune di contenitore che può essere visualizzato sullo schermo.
  • canvas (area di disegno): una semplice superficie di disegno particolarmente utile per visualizzare immagini o per effettuare altre operazioni grafiche. I componenti sono oggetti con una propria rappresentazione grafica. Alcuni importanti componenti della GUI di Java sono:
  • Label (etichette)
  • Button (pulsanti)
  • TextField (campi di testo)
  • TextArea (aree di testo)
  • Checkbox (caselle di controllo)

Creazione e uso dei contenitori standard

La classe JFrame ha i seguenti metodi costruttori:

  • JFrame() Crea una finestra senza titolo
  • JFrame(“Stringa”) Crea una finestra senza titolo specificato in Stringa Altri metodi che si applicano ad un oggetto della classe JFrame:
  • setSize(larghezza, altezza) Dimensiona la finestra
  • setLocation( x, y) Posiziona la finestra (coordinate del punto in alto a sinistra)
  • pack() Ottimizza le dimensioni della finestra a seconda del contenuto
  • setVisible(boolean) Per rendere visibile la finestra se true (deprecato il metodo show())
  • setResizable(boolean) Per rendere ridimensionabile con mouse se true
  • dispose() Per chiudere la finestra, deallocando le risorse La classe JPanel ha il seguente metodo costruttore:
  • JPanel () Crea un pannello per inserire componenti GUI L’inserimento degli oggetti all’interno dei contenitori si realizza con il metodo add() con la sintassi: oggettoContenitore.add (oggettoDaAggiungere) Tale metodo è polimorfo cioè opera su argomenti di diverse classi.

esempio di Applicazione con uso di oggetti GUI in ambiente JCreator

public class Finestra { private JFrame f ; private Container c; private JPanel p; public Finestra () { // costruttore f = new JFrame("Visualizza sfondo colorato"); // crea frame o cornice invisibile c = f.getContentPane(); // recupera il "muro grezzo", cioè il riquadro dei contenuti senza barra dei menù // per impostare le dimensioni e la posizione: f.setSize(300,150); // misure in pixel: larghezza, altezza f.setLocation(200,100); // (0,0) angolo sup. sin p = new JPanel(); p.setBackground(Color. lightGray); // sfondo del pannello colorato

JLabel l1 = new JLabel ("Etichetta con sfondo colorato"); JLabel l2 = new JLabel ("Allineata al centro", JLabel.CENTER); JLabel l3 = new JLabel ("Allineata a sinistra", JLabel.LEFT); JLabel l4 = new JLabel ("Allineata a destra", JLabel.RIGHT); l1.setBackground (Color.cyan); l1.setOpaque(true); // per vedere sfondo su sfondo p.add(l2); // aggiunge al pannello un'etichetta allineata al centro p.add(l3); // aggiunge al pannello un'etichetta allineata a sinistra p.add(l4); // aggiunge al pannello un'etichetta allineata a destra p.add(l1); // aggiunge al pannello un'etichetta con sfondo colorato c.add(p); // aggiunge il pannello setVisible(true); // mostra il frame (dimensioni 300x150) setDefaultCloseOperation (JFrame.EXIT_ON_CLOSE); } public static void main(String [] args) { MiaFinestra o = new MiaFinestra(); // creo oggetto che "ha" componenti Gui } }

Disegnare in un componente java

Ogni componente Java possiede il metodo: void paint(Graphics g) che ridisegna il componente usato dal sistema per ridisegnare il componente.

Personalizzare il disegno

Per personalizzare la grafica di un componente, occorre definire una sottoclasse con una nuova implementazione del metodo paint. Scegliere la classe di componente adatta (es Button), in modo da ereditare tutti i comportamenti previsti da tale classe. Esempi:

  • Per bottone la capacità di catturare ActionEvent
  • Se non sono necessari comportamenti particolari si può usare un semplice pannello Ridefinire il metodo paint o paintComponent inserendovi il codice per compiere il disegnamento voluto. Chiamare sempre super.paint o super.paintComponent all'inizio in modo da effettuare anche tutto il redisegmanento previsto di default (es. pulitura dello sfondo).

Classi per disegnare

Il metodo paint / paintComponent ha come argomento un oggetto di classe Graphics che viene passato automaticamente dal sistema. void paint/paintComponent ( Graphics g ) { .... } Tutto il disegno si fa chiamando metodi della classe Graphics sull'oggetto g. La classe Graphics contiene:

  • informazioni sullo stato del sistema grafico (attributi pittorici, trasformazioni)
  • primitive per disegnare (varie forme geometriche)
  • metodi per agire sullo stato (leggere e impostare i valori) In realtà l'oggetto g che viene passato dal sistema a paint non è semplicemente di classe Graphics, ma in particolare è della sottoclasse Graphics2D.
  • Classe Graphics contiene funzionalità grafiche più semplici, in genere sufficienti a disegnare l'aspetto dei componenti java
  • Classe Graphics2D contiene funzionalità grafiche più avanzate Essendo di classe Graphics2D (sottoclasse), g è anche di classe Graphics (superclasse), e normalmente si usa come se fosse di classe Graphics Se voglio vederlo come oggetto di classe Graphics2D (per poter vedere le funzionalità avanzate), devo fare una conversione esplicita (cast): Graphics2D g2 = (Graphics2D)g; dopo di che in g2 ho sempre g ma visto come oggetto di classe Graphics2D Noi vedremo le funzionalita' di Graphics2D.

pieno. User space Sistema di coordinate logico in cui il programmatore esprime le primitive da disegnare. Una trasformazione affine determina come portare le primitive da User space a Device space. Di default la trasformazione e' l'identita' (nessuna trasformazione, i due spazi di coordinate coincidono). Quindi se la finestra e' di 300x200 pixel io devo definire primitive che abbiano coordinate entro questi limiti, le (parti di) primitive che cadono fuori non saranno visibili. Se l'utente cambia dimensioni alla finestra, la scena puo' rimenere decentrata e/o in parte tagliata fuori. Posso invece impostare trasformazioni personalizzate: traslazioni, rotazioni, scalature e shear. In questo modo definisco le primitive con coordinate entro limiti che decido io, poi affido alle trasformazioni il compito di "farle stare" nella finestra, in base alle dimensioni correnti di questa. Nota: Graphics2D ha trasformazioni e quindi distinzione tra device space e user space. Invece Graphics non ha trasformazioni e devo esprimere le primitive direttamente in device space. Primitive e attributi Primitive ("che cosa" posso disegnare):

  • Primitive 1-dimensionali (linee): nomi dei metodi che le disegnano iniziano con "draw"
  • Primitive 2-dimensionali (aree piene): nomi dei metodi che le disegnano iniziano con "fill"
  • Stringhe di caratteri
  • Immagini Vedremo dopo in dettaglio le primitive. Attributi pittorici ("come" lo posso disegnare):
  • COLOR = colore con cui disegno
  • STROKE = stile del tratto (spessore, tratteggio, modo di unire gli angoli) per le primitive 1- dimensionali
  • PAINT = trama di riempimento (uniforme, sfumata, con tessitura) per le primitive 2-dimensionali
  • FONT per le stringhe Modo di composizione del colore Quando due primitive vanno a sovrapporsi sulla stessa area della finestra, quale delle due "vince"? Lo stabilisce il modo di composizione del colore:
  • la primitiva disegnata per ultima copre la precedente (default)
  • la primitiva disegnata per prima copre la seguente
  • di ciascuna delle due e' disegnata solo la parte esterna all'altra, mentre la parte intersezione non e' disegnata affatto
  • altre modalita'... Clipping Clip = tagliare via (qui: dal disegno). Non disegnare quello che cade fuori da una certa area specificata da un perimetro di clipping ( clipping path ). Di norma il perimetro di clipping e' la finestra: cio' che ha coordinate che eccedono i limiti delle coordinate di device e' tagliato via e non si vede. Posso specificare perimetri di clipping (clipping path) aggiuntivi. Allora anche cio' che cade dentro la finestra ma fuori dal perimetro di clipping sara' tagliato. Primitive disponibili
  • Metodi della classe Graphics2D per tracciare (draw) o riempire (fill) direttamente una figura geometrica dati dei parametri numerici che la descrivono. Molti di questi metodi sono comuni alla superclasse Graphics.
  • Classe Shape apposita per rappresentare figure geometriche, che si possono poi disegnare chiamando metodi (draw o fill) della classe Graphics2D.

Disegno diretto

Metodi per disegnare direttamente una figura. I parametri sono interi esprimenti numero di pixel, cioè le primitive vanno fornite direttamente in device space.

  • clearRect(x,y, width,height): pulisce il rettangolo indicato riempiendolo col colore di sfondo.
  • void draw/fillRect(x,y, width,height): Disegna rettangolo vuoto o pieno.
  • void draw/fillRoundRect(x,y, width,height, arcWidth,arcHeight): Disegna rettangolo con angoli smussati , vuoto o pieno.
  • void draw/fill3DRect(x,y, width,height, arcWidth,arcHeight): Disegna rettangolo con effetto di rilievo 3D , vuoto o pieno.
  • draw/fillOval(x,y, width,height): Disegna ellisse , vuoto o pieno.
  • draw/fillArc(x,y, width,height, startAngle,arcAngle): Disegna arco circolare o ellittico, vuoto o pieno. Gli angoli sono in gradi, angolo positivo significa rotazione in senso antiorario, negativo in senso
  • una tessitura, classe TexturePaint, che si crea specificando un'immagine e un rettangolo di ancoraggio: l'immagine sara' collocata inizialmente nel rettangolo e poi replicata tante volte quante occorre Font La font e' il tipo di carattere usato per tracciare le stringhe. Si legge e si imposta con Font getFont() e setFont(Font f). Una font si crea con: new Font (nome, stile, grandezza) dove
  • il nome e' una stringa che identifica la font, es: "Courier"
  • lo stile e' un intero che puo' essere una delle costanti Font.PLAIN, Font.BOLD, Font.ITALIC o un "or" tra queste (es. sia bold che italic)
  • la grandezza e' espressa in numero di pt, es: 10, 12, 24 Il default nella mia versione e' "Dialog", PLAIN, 12 pt. Per avere tutte le font disponibili sulla macchina: GraphicsEnvironment genv = GraphicsEnvironment.getLocalGraphicsEnvironment(); Font[] f = genv.getAllFonts(); Esempio Pannello con grafica personalizzato: ExDraw1.java. La funzione paintComponent riempe un rettangolo sfumato, vi disegna dentro un fumetto con scritto grande "Ciao!", traccia con tratto spesso tre linee alla base del fumetto. Classi per figure geometriche (Shape) La classe Shape fornisce nelle sue sottoclassi vari tipi di forme geometriche che posso disegnare usando i metodi della classe Graphics2D:
  • draw(Shape s): traccia il contorno
  • fill(Shape s): riempe l'interno Sottoclassi di shape:
  • Figure dotate di un rettangolo che le contiene: Arc2D, Ellispe2D, Rectangle2D, RoundRectangle2D
  • Segmenti di varia forma: Line2D (di retta), QuadCurve2D (di curva quadrica), CubicCurve2D (di curva cubica)
  • Linea spezzata formata da segmenti di tipo vario: GeneralPath
  • Figura 2D generale su cui posso eseguire operazioni insiemistiche: Area Le shape sono contenute nel package java.awt.geom, che occorre percio' importare. Alcune delle figure di cui sopra corrispondono a funzioni draw/fill gia' viste (es: drawShape di un Rectangle2D equivale a drawRect). Altre sono nuove. In piu' e' possibile esprimere le coordinate con float e double. La possibilita' di disegnare le shape esiste solo in Graphics2D, non in Graphics. Le coordinate possono essere numeri reali perche' Graphics2D ammette coordinate logiche diverse da quelle fisiche (cioe' dai pixel). L'esempio ExDraw1.java visto prima disegna sempre la scena in 300x200 pixel. Invece l'esempio ExDraw2.java disegna la scena sempre in tutta la finestra, anche quando l'utente la deforma. Fa uso di trasformazioni che vedremo dopo. Classe Area La classe Area prevede le operazioni add, subtract, intersect, exclusiveOr con argomento un'altra area. Ogni shape puo' essere trasformata in un'area. Posso costruire una forma complessa aggiungendo, sottraendo, intersecando e facendo l'OR esclusivo di forme semplici. Esempio: Mela con morso ottenuta unendo due ellissi e sottraendone un altro: MelaMorsa.java Ellipse2D.Double sinistra, destra, morso; Area a; sinistra = new Ellipse2D.Double(); sinistra.setFrame(20, 20, 60, 80); destra = new Ellipse2D.Double(); destra.setFrame(40, 20, 60, 80); morso = new Ellipse2D.Double(); morso.setFrame(80, 70, 60, 60); a = new Area();
  1. g2.translate(xC,yC);
  2. g2.rotate(ang);
  3. g2.translate(-xC,-yC); Accortezza La trasformazione va cambiata solo momentaneamente durante l'esecuzione di paint, alla fine del codice di paint bisogna ripristinare la trasformazione che c'era prima. Altrimenti si potrebbero avere effetti inaspettati. Per fare cio':
    • all'inizio di paint salvare la trasformazione in una variabile chiamando getTransform
    • poi modificarla e disegnare
    • alla fine di paint chiamare setTransform con la trasformazione salvata Animazione Animazione = cambiamento dinamico della grafica mostrata su un componente. Ad intervalli regolari (gestiti con un timer) oppure in seguito ad azioni dell'utente si ridisegna il componente cambiandone la grafica. Forzare il redisegnamento Di norma il metodo paint e' chiamato dal sistema, attraverso canali suoi, quando il sistema ritiene che il componente vada ridisegnato (es. quando la finestra che lo contiene e' mappata o torna visibile dopo essere stata oscurata da altre, quando viene ridimensionata...). L'animazione rende necessario ridisegnare anche in casi diversi da quelli previsti dal sistema. Il programma NON DEVE chiamare direttamente paint! Per provocare da programma il ridisegnamento del componente bisogna usare il metodo:
    • void repaint() che mette in coda una richiesta di redisegnamento per il componente Siccome la gestione della coda e' asincrona, puo' capitare che piu' chiamate a repaint vengano collassate in una sola chiamata a paint. L'animazione si ottiene cambiando alcuni parametri usati dentro la funzione paint e poi invocando repaint. Esempio Pannello con cerchio che scorre avanti e indietro per un pannello: MuoviCerchio.java Una variabile contiene l'ascissa corrente ed e' usata da paint per disegnare il cerchio. C'e' un timer che ogni tanti millisecondi cambia il valore della variabile e invoca repaint. Interazione con l'utente Vi sono due tipi di azioni interessanti che l'utente puo' compiere sull'area grafica:
  • Azioni sullo spazio indipendentemente dalla presenza di primitive. Esempio: Cliccare in un punto, il programma poi compiera' qualche operazione con le coordinate di quel punto (es: disegnare qualcosa in quel punto)
  • Azioni sulle primitive presenti nello spazio. Esempio: Cliccare sopra una primitiva per selezionarla, il programma poi compiera' qualche operazione sulla primitiva selezionata (es: cancellarla) Azioni sullo spazio Si catturano associando al pannello gli event listener opportuni. Nell'esempio associo un MouseListener che nel suo metodo mouseClicked compia l'operazione corrispondente. Le coordinate del punto cliccato si ottengono chiamando getX() e getY() sull'evento MouseEvent. Azioni sulle primitive Come sopra, ma in piu' richiedono un modo per conoscere che primitiva e' disegnata nel punto dove e' avvenuto il click. E' necessario aver disegnato le figure che vogliamo rendere sensibili al click usando oggetti di classe shape ed il metodo fill(Shape s) della classe Graphics2D. Si scorre la lista delle shape che sono state disegnate (e' necessario averle memorizzate) e si chiede a ognuna se e' stata interessata dal click, usando i metodi della classe Shape:
  • contains(x,y) oppure contains(Point2D p): controlla se la figura contiene il punto
  • contains(Rectangle2D r): controlla se la figura contiene completamente il rettangolo
  • intersects(x,y,w,h) oppure intersects(Rectangle2D r): controllano se la figura interseca il rettangolo specificato Esempio Programma che permette di disegnare cerchi e di cancellarli: ClickCircle.java
  • Se l'operazione corrente è "insert", cliccando su un punto appare un cerchio centrato in quel punto
  • Se l'operazione corrente è "delete", cliccando su un cerchio si cancella il cerchio

Link Utili per il Progetto

  • Open Game Art è un sito che mette a disposizione modelli e suoni open source (per creare giochi senza violare copyright ovviamente): https://opengameart.org/
  • *Guida per creare menu: https://www3.ntu.edu.sg/home/ehchua/programming/java/j4a_gui.html
  • *Guida per creare animazioni: https://gamedev.stackexchange.com/questions/53705/how-can-i-make-a-sprite-sheet-based- animation-syste
  • Colori http://colorizer.org/