Approccio migliore per l'azione a due stati
-
13-09-2019 - |
Domanda
Ho recentemente implementato un Action
che attiva lo stato di attivazione di una funzione aziendale. Ogni volta che l'utente richiama l'azione Ho impostato un flag booleano: " willEnable " per determinare se la prossima invocazione sarà abilitare o disabilitare la funzione. Allo stesso modo è possibile aggiornare il nome dell'azione, breve descrizione e l'icona per riflettere il nuovo stato. Poi nel mio metodo actionPerformed(...)
prendo un'azione diversa in base allo stato di willEnable
.
- E 'questo l'approccio corretto o può
Qualcuno consiglia uno migliore (come ho
sospetto che questo è un problema comune)?
(Vedo che gli atti
JToggleButton
come un pulsante a due stati, ma voglio questa azione per essere visibile su unaJMenuBar
nonché unJButton
, quindi non penso che questo sia appropriato).
Modifica
In particolare, come fanno le applicazioni come affare idea con questo? Avrebbero utilizzare le azioni multi-stato (come sopra), o avrebbero dovuto scambiare una Action
diverso in un dato JButton
utilizzando setAction(Action)
? Forse questo approccio è migliore?
- Quando si aggiornano le proprietà di un azione
posso contare su componenti GUI
inizializzato con quella
Action
(ad esempioJButton
) riverniciatura automaticamente loro stessi? Cosa succede se ilJButton
modifiche di dimensione di conseguenza? Dovrei essere riconvalida contenimentoJPanel
me stesso? - Sta cambiando il nome della azione di una cattiva
cose da fare? Questo è l'unico modo che ho
può apportare la modifica del testo JButton, ma sono consapevole che il nome dovrebbe probabilmente rimanere costante se l'azione viene posta in un
ActionMap
.
Grazie in anticipo.
Soluzione
Mi aspetto che ogni componente GUI che viene creato con un po 'di dati "modello" (I includerebbe un Action
come un modello di dati) dovrebbe registrarsi come un listener per quel modello. E ' deve adottare opportune, ehm, azione su un PropertyChangeEvent
essere licenziato:. Qualsiasi altro comportamento costituirebbe un errore, a mio parere
La cosa discutibile è se è legittimo cambiare il nome dell'azione; Penso che non è legittimo . La vostra azione logicamente è ToggleEnabledStatus e questo non cambia perché l'azione è stata invocata. Qualsiasi componente che ha bisogno di visualizzare qualsiasi altro testo dovrebbe registrarsi come un listener al Action
e quindi controllare la vostra bandiera willEnable
a prendere il caso, ehm, l'azione.
In alternativa si potrebbe scrivere la propria classe che ha recepito ToggleButtonModel
e Action
allo stesso tempo e controllato gli eventi di modifica all'interno di esso. Si tratta di un sacco di codice, tuttavia, per così poco beneficio
Altri suggerimenti
Si consiglia di guardare ai href="http://en.wikipedia.org/wiki/State_pattern" state pattern .
In sostanza, si crea un'interfaccia e due (o più) implementazioni di esso per ogni stato. Come semplice esempio, lo stato di disabilitazione potrebbe semplicemente implementare l'interfaccia di non fare nulla mentre lo stato abilitato fa alcune azioni. Per cambiare lo stato si sarebbe semplicemente fare
interface IState {
void doAction();
boolean isEnabled();
}
class EnabledState implement IState {
void doAction() {
setState(new DisabledState());
// do something
}
boolean isEnabled() {return true;}
}
class DisabledState implement IState {
void doAction() {
setState(new EnabledState());
// do nothing
}
boolean isEnabled() {return false;}
}
private IState state = new DisabledState(); // default is disabled
private PropertyChangeSupport support = new PropertyChangeSupport(this);
void setState(IState state) {
if (this.state != state) {
IState oldState = this.state;
this.state = state;
support.firePropertyChange("enabled", oldState.isEnabled(), state.isEnabled());
}
}
void doAction() {
state.doAction();
}
Anche se è un po 'in testa per un singolo metodo, vale la pena certamente di non appena si dispone di diversi metodi che cambiano il suo comportamento in funzione di un singolo stato.