Domanda

Mi sto interrogando sulla pratica standard con le classi interne (in Java ma suppongo che si applichi a tutti i linguaggi OO).Quindi ho una sottoclasse JFrame ControllerWindow che contiene una sottoclasse JPanel MapPanel su cui disegno (quindi deve sovrascrivere il metodo paintComponent) e che deve implementare un ascoltatore del mouse.La mia attuale soluzione che funziona è avere MapPanel in una classe separata che implementa MouseListener ma quando l'altro giorno l'ho mostrato al ragazzo che tiene il mio corso sembrava pensare (abbiamo un po' di barriera linguistica) questo dovrebbe essere in una classe interna in ControllerWindow o almeno MouseListener dovrebbe essere una classe interna.

Quindi la mia domanda è: quale sarebbe la soluzione standard qui, mettere un MouseListener nella classe interna, il JPanel in una classe interna diversa o ancora nella sua classe separata?Il JPanel implementa MouseListener in una classe interna?E perché?

La cosa più importante per me è che funzioni, ma mi piacerebbe conoscere e comprendere le pratiche standard dietro queste cose, se possibile.

MODIFICARE:Versione molto semplificata del codice attuale di seguito.

class ControllerWindow extends JFrame{
    ...
    MapPanel drawPanel = new MapPanel();
    ...
}

e una classe separata:

class MapPanel extends JPanel implements MouseListener{

    ...

    public void paintComponent(Graphics g){
        ...//fillRects etc.
    }

    //MouseListener methods
    public void mouseReleased(MouseEvent e){
        requestFocus();
        ...
        repaint()
        ...
    }
    public void mousePressed(MouseEvent e){}
    public void mouseEntered(MouseEvent e){}
    public void mouseExited(MouseEvent e){}
    public void mouseClicked(MouseEvent e){}
}

Inoltre potrebbe essere una situazione in cui sarebbe accettabile inserire entrambe le classi nello stesso file?Non prevedo l'utilizzo MapPanel per qualsiasi cosa diversa da ControllerWindow.

È stato utile?

Soluzione

Penso che sia in qualche modo arbitrario il modo in cui procedi (come ha commentato Tom Hawtin, GUI standard = fango), dal momento che stai scambiando la complessità nel numero di classi con la complessità in una singola classe.Se vuoi produrre codice semplicemente per una dimostrazione, un singolo file potrebbe essere la soluzione più semplice.Se desideri un codice che metterai in produzione e modificherai/manterrai nel tempo, l'astrazione in classi diverse è quasi certamente la strada che vuoi percorrere.

Ad esempio, se incorpori MapPanel come classe interna in ControllerWindow e in seguito desideri sostituirlo con un tipo diverso di MapPanel, hai un aggiornamento massiccio per ControllerWindow anziché semplicemente sostituire MapPanel con un tipo di componente diverso.

Con MouseListener, sarei propenso a includerlo in MapPanel se gestisce eventi specifici per quel componente (ovvero, se solo MapPanel "sa" cosa significa un clic, dovrebbe essere lui a elaborare quel clic).Sicuramente non lo inserirei in ControllerWindow, da allora stai "perdendo" i dettagli di implementazione da MapPanel.(L'unico caso che mi viene in mente:oltre al MapPanel, hai più tipi di pannelli che devono tutti rispondere ai clic nello stesso modo, quindi invece di implementarli in ciascun pannello potresti fare in modo che ControllerWindow lo faccia.Ma anche in questo caso, non sono sicuro che il codice dovrebbe essere in ControllerWindow).

Se il listener del mouse di MapPanel sia un'implementazione della classe interna di MouseListener o se MapPanel lo implementi (come nel codice sopra) probabilmente dipende da quale stile preferisci.

Altri suggerimenti

E 'comune l'uso di classi interne anonime come ascoltatori di eventi, perché il codice è di solito abbastanza semplice (quindi una classe separata può essere eccessivo) e mantenendo il codice del gestore "vicino" al codice che registra l'ascoltatore in grado di migliorare la leggibilità per le persone cercando di capire il codice, dal momento che tutto il codice relativo alla manifestazione è in un unico luogo.

EDIT: Questo è particolarmente vero per le classi che implementano solo metodo ascoltatore. Forse meno vero per le interfacce multi-metodo come MouseListener, dal momento che una classe che implementa l'interfaccia completa sarà più prolisso.

classe interna sarebbe meglio se si ha una sintassi più semplice.

button1.click( function(event){ do something x...  } );
button2.click( function(event){ do something y...  } );
radio2.check ( function(event){ do something z... } );

Java 7 può darci qualcosa del genere e cambiare tutta la situazione. come è ora, con un sacco di classi interne annonymous può rovinare il codice e l'impossibilità di leggere. si dovrebbe scegliere quale stile che rende il codice bello e leggibile.

A causa di eventi multipli sono necessari movimentazione requisito anonimi classi interne. classe anonima può essere scritto da nessuna parte come in una classe, in un metodo, nell'argomento. Pertanto ad astenersi dal creare molte classi per ogni ascoltatore anonimo è preferito.

Ho trovato questo articolo utile: http://www.retrologic.com/innerclasses.doc3.html

In generale, quando si ha bisogno di utilizzare un puntatore metodo; estendere le classi adattatore come classi interne per semplificare il codice.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top