I need to run some method in Swing application in separate thread. What is the difference between using SwingWorker and SwingUtilities.invokeLater. Which one should I use to run a thread in Swing application? I couldn't find exact info in the tutorial at
http://java.sun.com/docs/books/tutorial/uiswing/concurrency/index.html
SwingUtilities.invokeLater is used if you have something that must run in the EDT.
If you have a long-running task, you instead need to use a SwingWorker, since it does not run on the EDT and therefore does not cause the GUI to freeze while it runs.
It looks like you would want to:
use SwingWorker when you need to monitor the status of a long-running background process
use SwingUtilities.invokeLater if you just want a short task to run but do not need feedback on it. Sort of like a fire-and-forget. Just keep in mind it will run in the AWT event dispatching thread, so your application would not be getting any events handled while the task is running.
Related
I am new to JavaFX and multithreading in general, so based on assylias answer to this post
Multithreading in JavaFX hangs the UI
i have created some Tasks running in Threads to avoid freezing the main UI thread.
The question:
I wonder what happens to the Thread and the Task when the Task has finished its job. I might also add that i am creating both the Thread and the Task in a method which is called when i press a button. So neither of them are instantiated or initialized globally.
I also wonder if there is a way to monitor threads and resource usage when compiling my code in IntelliJ.
Hope i can get some clarification on this :)
When I am working with AWT, after calling the Toolkit.getDefaultToolkit(), I have printed the current running threads in my program. I would like to know what is that AWT-Windows thread that is running in the background. What does it do and why does it have 6 priority.
Also, the line
Thread[AWT-Windows,6,main]
does the main mean that the thread is started in the main thread?
Thanks in advance.
AWT is the Java Abstract Window Toolkit. The AWT thread should be handling all AWT events, rendering, etc...
The 6 priority is just one above normal priority to make this scheduler bias slightly towards it.
main is the group of the thread.
EDIT
The AWT-Windows thread specifically handles polling events from the native Windows C++ API for GUIs. The specific native method that handles the events is sun.awt.windows.WToolkit.eventLoop().
In my application, some process that is started in AWT's Event Dispatching Thread (EDT) may be interrupted under particular circumstances. Then it waits for input from the user. Alas, as the process is located in the EDT, the whole application freezes and the user is unable to relaunch the process, thus creating a deadlock. Is there any way to interrupt the EDT and lauch a new event pump from another thread ? Then the user would be able to interact with the UI.
What I am trying to do looks more or less like opening a modal dialog, except that I don't want a dialog because my component is complex. I'd rather display it right inside my root pane. So I had a look at how it's done in java.awt.Dialog, and had a pretty good understanding of it, but the most important classes that are used (EventDispatchThread, SequencedEvent, ...) are protected and therefore inaccessible for me.
Thank you all for your answers.
I'll be more specific. I am actually working on an application which embeds a homegrown scripting language. I am developing a debugger for this language. The debugger (as all debuggers) would stop the script execution whenever a breakpoint is met. The scripted processes can be triggered from many places (including from the EDT) in the code so taking the the process out of the EDT is not an option. I'd like the debugger UI to be embedded in the application (in a side pane to be precise). So when a breakpoint is met I would need the current thread (possibly the EDT, not to say mainly) to be interrupted and at least the debugger's UI should still be responsive. Also I am developing atop of the JDK 1.4 so no way to use JDK7 alas.
What I am currently doing is opening a JDialog with the debugger embedded. It all works fine but as I said I am not fully satisfied by this solution because I would really want my debugger to be embedded right in my main window.
If you are using JDK7, you can use the SecondaryLoop interface. An instance of this interface can be created through the EventQueue.createSecondaryLoop method
There was an informative blog post with an example but the server seems to be offline for the moment.
A small edit as I am still not fully sure I understand your question.
If you want to wait for user input from a worker thread, you can use the SwingUtilities.invokeAndWait method and use a blocking method (e.g. show a JOptionPane to retrieve user input). Due to the invokeAndWait your worker thread will be stopped until the Runnable on the EDT is processed. If you use a blocking method on the EDT to retrieve the user input that Runnable will only be finished when the user has provided his/her input
I am using swing and in my application i needed to run many threads in parallel like checking the internet connectivity after every 5 secs, monitoring the filesystem changes, sycing files from server.
All the time consuming tasks like above are running in SwingWorker so that my GUI should not freeze.
Same time i need to run some other time consuming tasks such as uploading file to server. for this purpose i also used swingWorker. and then i submit all these swingworker to executerService for thread pooling so that they should not effect each other.
My executer service is like this. i thought 30 threads will be enough for me.
static ExecutorService threadExecutor;
threadExecutor = Executors.newFixedThreadPool(30);
and then i submit threads in the same service.
threadExecutor.submit(monitorinternetconnectivity); //submitting swingworker obejct
Some of the threads i submit at the start and some i add runtime, when i add at runtime, it does not complete the job or stop running their job, like monitoring internet connectivity.
Is there any way to have the same functionality like swing worker, or some best way to use multiple swingworker. and we should be able to add new swingwokers at runtime to executer service
SwingWorker uses it's own ThreadPool.
SwingWorker should be used for a long running task after (i.e. anything that required more than a couple of milliseconds) after which a GUI update is required.
No calls to update gui elements outside the EDT should be done (i.e. from the SwingWorker.done() method)
If you generally follow the rules of accessing Swing components form inside the EDT (look here) then you shouldn't have a problem with locking. I suspect that the problem rather lies in your code but to be sure of that we should see it.
We are experiencing a bug we cannot track down where something is freezing up our swing thread (it's been almost 2 weeks now and no real results) - we are experienced Swing programmers but we have a huge program and believe it to be in some of the legacy code
I am wondering, is there any way outside of editing the actual EventQueue class in the JDK which will allow us to view all pieces of our code currently running on the Event Dispatch Thread - maybe some type of tool which will allow us to view things as they enter or leave the event dispatch thread?
One interesting approach is to extend EventQueue and push() it, as shown here.
Logging everything that passes through the Event Dispatch Thread seems a cumbersome way to diagnose a freeze. Wouldn't it be easier to wait until the problem occurs, and then ask the Event Dispatch Thread what it's doing now? One way to do this is to enable JMX monitoring, connect to your running process with a JMX client such a VisualVM (which ships with the JDK), wait for the problem to occur, and then take a thread dump.
In case you still wish to log everything the Event Dispatch Thread is doing, you can do this by:
In Eclipse, launch the application in debug mode.
Create a breakpoint on EventQueue.dispatchEvent, right-click it, select "properties", check "condition", and enter the following "condition":
System.out.println(arg0);
return false;
It might be good idea to try BTrace to instrument the EventQueue and capture stack traces each time something gets added. I think the latest VisualVM has plugins that will allow you to instrument a running JVM with a BTrace script.
If you're using the Oracle JRE, there is a TracedEventQueue included already. You can install it as mentioned before:
EventQueue eventQueue = Toolkit.getDefaultToolkit().getSystemEventQueue();
eventQueue.push(new TracedEventQueue());
Note, this will output a lot of output...