Pagina 1 di 2 1 2 ultimoultimo
Visualizzazione dei risultati da 1 a 10 su 11
  1. #1
    Utente di HTML.it
    Registrato dal
    Oct 2011
    Messaggi
    347

    Evitare freeze interfaccia grafica

    Ho un'applicazione che deve dare dei messaggi in una text area, finchè non finisce un certo processo che può durare qualche secondo, ma quando parte il processo l'interfaccia rimane in uno stato di congelamento totale! Come lo evito?
    Grazie

  2. #2
    Utente di HTML.it
    Registrato dal
    Dec 2009
    Messaggi
    1,123
    Utilizzando i Thread.

  3. #3
    Utente di HTML.it
    Registrato dal
    Oct 2011
    Messaggi
    347
    ok, ma chi dovrebbe estendere Thread?
    O forse intendevi di creare un thread a parte che gestisca questi messaggi?

  4. #4
    E' un problema più volte trattato in questo forum qui c'è uno dei thread in cui è stato discussa la cosa.

  5. #5
    Utente di HTML.it
    Registrato dal
    Oct 2011
    Messaggi
    347
    ok mi sono letto il post; mi è venuto in mente un'idea: creare una classe thread contenente una coda, il cui metodo run non fa altro che prelevare stringhe dalla coda e "appenderle" nella text area.
    Ho un'altra domanda: quando viene avviata un'applicazione, compresa di gui, quanti thread sono attivi premettendo che non ce ne siano creati dal programmatore? e perchè molte operazioni sono gestite dall'EDT e non dal thread principale dell'applicazione?

  6. #6
    Utente di HTML.it
    Registrato dal
    Sep 2012
    Messaggi
    707
    My 2 cents. Se ho capito (perché non mi è del tutto chiaro):
    - hai una applicazione grafica
    - l'applicazione fa partire un processo esterno (non hai specificato come, con un bottone, un timer? e poi con cosa lo esegui? Runtime.exec?)
    - questo processo genera un output che tu vuoi visualizzare in una text area (almeno così ho capito)

    Ora, sempre che abbia capito, tu vorresti far scrivere il processo in una coda di messaggi, e poi creare
    un thread che svuota la coda e popola la textarea.

    Ora, (1) il problema, se è così, permane, perché è l'esecuzione del processo (la Process.getInputStream in particolare se usi quest API) che ti blocca la GUI e (2) si risolve facilmente mettendo tutta l'esecuzione del processo in un thread, senza code.

  7. #7
    Moderatore di Programmazione L'avatar di LeleFT
    Registrato dal
    Jun 2003
    Messaggi
    17,320
    Originariamente inviato da John360
    Ho un'altra domanda: quando viene avviata un'applicazione, compresa di gui, quanti thread sono attivi premettendo che non ce ne siano creati dal programmatore?
    Questo semplice programmino, ti fa vedere quanti thread sono in esecuzione all'avvio del programma stesso, che non fa uso di GUI:

    codice:
    public class NumeroThread {
       public static void main(String[] args) {
          // Ottengo il ThreadGroup padre di tutto
          ThreadGroup mainGroup = Thread.currentThread( ).getThreadGroup( );
          ThreadGroup parentGroup;
          while ( ( parentGroup = mainGroup.getParent() ) != null ) {
              mainGroup = parentGroup;
          }
    
          // Stampo la stima del numero di thread attualmente attivi
          System.out.println("In totale ci sono circa " + mainGroup.activeCount() + " threads attivi.\n");
    
          // Vediamoli
          Thread[] totThreads = new Thread[ mainGroup.activeCount() ];
          while ( mainGroup.enumerate(totThreads, true) == totThreads.length ) {
              totThreads = new Thread[ totThreads.length * 2 ];
          }
          
          for(Thread t : totThreads) if (t != null) System.out.println( t.getName() );
       }
    }
    Eseguendolo si dovrebbe ottenre questo output:

    codice:
    In totale ci sono circa 5 threads attivi.
    
    Reference Handler
    Finalizer
    Signal Dispatcher
    Attach Listener
    main
    Questo dovrebbe darti un'idea di quanti thread ci siano sottobanco che girano.

    e perchè molte operazioni sono gestite dall'EDT e non dal thread principale dell'applicazione?
    L'EDT è il thread che si occupa di gestire gli eventi utente (generati dall'interfaccia grafica). Si occupa di prendere in carico gli eventi e distribuirli ai componenti predisposti a riceverli, nonchè di ridisegnare (di conseguenza) l'intera interfaccia grafica in risposta a tali eventi.

    Ciao.
    "Perchè spendere anche solo 5 dollari per un S.O., quando posso averne uno gratis e spendere quei 5 dollari per 5 bottiglie di birra?" [Jon "maddog" Hall]
    Fatti non foste a viver come bruti, ma per seguir virtute e canoscenza

  8. #8
    Utente di HTML.it
    Registrato dal
    Oct 2011
    Messaggi
    347
    grazie lele XD come sempre molto paziente a spiegare tutto per bene!
    Rispondendo a coder: no, non c'è nessun processo esterno, semplicemente alla pressione di un pulsante l'applicazione dei fare dei determinati calcoli, e mostrare(o aggiornare) di volta in volta quello che ottiene su una text area, il tutto finchè non termina tutta l'operazione. Questa operazione viene eseguita da un oggetto istanziato e fatto partire nel metodo action performed(proprio alla pressione di quel preciso pulsante.
    Scusami ma non ho ben capito cosa vuoi dire... spero di essere stato più chiaro ora, gentilmente potresti spiegarmi la tua soluzione?

  9. #9
    Utente di HTML.it
    Registrato dal
    Sep 2012
    Messaggi
    707
    Ti faccio "gentilmente" un esempio guarda se ti può andare bene.

    codice:
    import java.awt.*;
    import java.awt.event.*;
    import javax.swing.*;
    
    class MioCalcolo implements Runnable {
        private Thread thread;
        private JTextArea jta;
        
        public MioCalcolo(JTextArea jta) {
            this.jta = jta;
        }
    
        public boolean esegui() {
            if (thread != null && thread.isAlive())
                return false;
        
            thread = new Thread(this);
            thread.start();
    
            return true;
        }
        
        public void run() {
            for (int i = 0; i < 3; i++) {
                jta.append("Calcolo in fase: " + i + "\n");
                try {
                    Thread.sleep(1000);
                } catch (InterruptedException ie) {
                }
            }
        }
    }
    
    class Demo extends JFrame {
        private MioCalcolo mc;
        private JTextArea jta;
    
        public Demo() {
            // jtextarea
            jta = new JTextArea(5, 20);
            // jbutton
            mc = new MioCalcolo(jta);	    
            JButton start = new JButton("Start");
            start.addActionListener(new ActionListener() {
                 public void actionPerformed(ActionEvent ae) {
                    boolean ret = mc.esegui();
                    if (!ret)
                        jta.append("Ancora in esecuzione\n");
                 }
            });
            // jframe        
            getContentPane().setLayout(new BoxLayout(getContentPane(), BoxLayout.PAGE_AXIS));
            jta.setAlignmentX(Component.CENTER_ALIGNMENT);
            start.setAlignmentX(Component.CENTER_ALIGNMENT);                
            add(jta);
            add(start);		
            setSize(400, 300);
        }
    
        public static void main(String args[]) {
           new Demo().setVisible(true);
       }
    }
    Ho fatto una piccola correzione, ora è ok.

  10. #10
    Utente di HTML.it
    Registrato dal
    Oct 2011
    Messaggi
    347
    benissimo! ho capito, fai una sorta di wrap della text area praticamente!
    Grazie per la spiegazione

Permessi di invio

  • Non puoi inserire discussioni
  • Non puoi inserire repliche
  • Non puoi inserire allegati
  • Non puoi modificare i tuoi messaggi
  •  
Powered by vBulletin® Version 4.2.1
Copyright © 2025 vBulletin Solutions, Inc. All rights reserved.