2011-01-25 19 views
13

Sto scrivendo un'app Java (Swing GUI) che visualizza periodicamente un JFrame.È possibile portare JFrame in primo piano ma NON mettere a fuoco?

E 'possibile in qualche modo portare la finestra in primo piano (foo.setAlwaysOnTop (true) sarebbe ancora meglio) ma senza lo che ha lo stato attivo?

Alcune persone spostano di tanto in tanto gli occhi dallo schermo per guardare la tastiera mentre scrivono, e sono sicuro che se questa finestra catturasse sempre il focus della tastiera, le persone si arrabbiano molto perché li sta causando perdere un bel numero di tasti ogni volta che appare inosservato.

In altri casi, anche quando l'utente è in realtà in grado di battitura a macchina, senza guardare la tastiera per tutto il tempo, avere una finestra pop-up e ottenere attenzione potrebbe causare azioni indesiderate dalla finestra pop-up in sé (alcuni Tab + Enter combinazione, ad esempio, in cui l'utente seleziona accidentalmente un'opzione che in realtà non avrebbe altrimenti selezionato).

Grazie in anticipo!

Aggiornamento

Come suggerisce Jonas, foo.setFocusableWindowState(false); sembra funzionare se chiamato dopo che la finestra è stata resa (testato su Gnome solo).

Questo non funziona:

foo.setFocusableWindowState(false); 
foo.setVisible(true); 
foo.setFocusableWindowState(true); 

Tuttavia, questo fa:

foo.setFocusableWindowState(false); 
foo.setVisible(true); 
Thread.sleep(1000); 
foo.setFocusableWindowState(true); 

dovrò vedere se c'è un evento che posso prendere/me ascolto che permette di fare foo.setFocusableWindowStatue(true); quando appropriato.

Considero il mio problema risolto.

+1

hai mai trovato un evento da ascoltare quando viene eseguito il rendering del frame? – lordoku

+0

Qualcuno ha mai trovato un evento da ascoltare qui che funzionasse? – wrslatz

risposta

13

Questo può funzionare:

foo.setFocusableWindowState(false); 
+0

Questo sembra funzionare, ma dovrò impostare un timer o trovare qualche evento da ascoltare quando permetterò di impostare 'setFocusableWindowState' su' true'. –

+0

@Johann puoi anche provare a usare 'Finestra' invece di' JFrame'. Penso che tu abbia più possibilità di controllare l'attenzione allora. – Jonas

0

Suggerimento: Nel componente GUI che crea la cornice, ha messo 2 chiamate consecutive:

frameJustCreated.requestFocus(); 
this.requestFocus(); 

1 ° uno portare la finestra del nuovo JFrame verso l'alto , 2 ° mantiene la finestra in cui l'utente sta digitando in alto.

+0

Sono terribilmente dispiaciuto! Avrei dovuto dire che questa è l'unica finestra del mio programma. Le "altre" finestre sono solo altri programmi che l'utente sta eseguendo .. –

1

recente ho incontrato lo stesso problema, e la soluzione provvisoria è stata:

JFrame frame = ...; 
frame.setExtendedState(JFrame.NORMAL); 
frame.setAlwaysOnTop(true); 
frame.requestFocus(); 
frame.setAlwaysOnTop(false); 
+0

che funziona se c'è solo un JFrame, e non ci sono attività in background, per favore inizia il tuo thread (se vuoi allora con il link a questo thread), è troppo difficile da fare che senza setVisible (true/flase), ma questa azione è visibile sullo schermo, la risposta è usare JDialog, solo che (che significa Windows OS) puoi farlo senza problemi secondari – mKorbel

+1

Questo non è affatto vero , poiché ho più JFrames in esecuzione nella mia applicazione. Perché iniziare una nuova discussione quando l'utente sta descrivendo lo stesso identico problema che sto riscontrando, tuttavia la soluzione non è completa? Per quanto riguarda JDialog, non è sempre appropriato per lo scopo previsto della finestra, che è anche il mio caso. –

+0

sì forse lo faccio senza sfarfallio, ma questo codice è più lungo di questo thread, in realtà non è un buon modo, non commutare Focus tra due o più JFrames, portare un JFrame all'altro, Focus (come JFrame o JDialog) è venuto dal sistema operativo nativo ed è asincrono, quindi così difficile da gestire, – mKorbel

2

Come di Java 1.7 è possibile chiamare

frame.setAutoRequestFocus(false); 
0

Se si desidera chiamare setFocusableWindowState (vero) in un evento (quindi, per non aspettare per esempio 1 secondo), è possibile aggiungere un WindowListener (ad esempio derivato da WindowAdapter) che modifica la proprietà:

appFrame.addWindowListener(new WindowAdapter() { 
     @Override 
     public void windowOpened(WindowEvent e) { 
      super.windowOpened(e); 
      e.getWindow().setFocusableWindowState(true); 
     } 
    }); 

    appFrame.setFocusableWindowState(false); 
    appFrame.setVisible(true); 
Problemi correlati