How to close JFrame while operation is still in progress - java

In my swings windows application after click the run button some operation is executed. If i am try to close window when operation is still in progress, close operation is not working. After complete the execution of process then only close window operation is working. Otherwise it will not responds the close operations.
I have already tried below mentioned codes. But that one is not stopped working
addWindowListener(new WindowAdapter()
{
public void windowClosing(WindowEvent we)
{
System.exit(0);
or
System.exit(1);
or
setDefaultCloseOperation(EXIT_ON_CLOSE);
or
setDefaultCloseOperation(3);
or
dispose();
}
});
JButton jb = new JButton("Run");
add(jb);
jb.setBounds(10, 30, 100, 30);
setSize(150,150);
setLayout(null);
setVisible(true);
setDefaultCloseOperation(EXIT_ON_CLOSE);
addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent we) {
System.exit(0);
}
});
jb.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent e)
{
// some operations . For Example here i'm add 1E5 data,s in my collection object. again i will replace data's places of each element.
for(int i=0;i<1E5;i++)
{
ll.add(i);
}
for(int i=0;i<1E5;i++)
{
ll.add(1,i);
}
for(int i=0;i<1E5;i++)
{
ll.add(0,i);
}
System.out.println(ll);
}
});
If I am clicking close button, my window terminate the currently executed process and Close the window.

class MyThread extends Thread {
public void run() {
// some operations . For Example here i'm add 1E5 data,s in my collection object
..
..
}
}
Then in your actionPerformed method on your JButton actionlistener you just start the thread :
public void actionPerformed(ActionEvent e) {
new MyThread().start();
}

Related

Java - delay between events after entering the value into JTextArea

I prepared a simple form (javax.swing.JFrame) on which JTextArea is located.
After entering the "TAB" value, I would like to see a visible JPanel on the form for a few seconds. Unfortunately, when I have the following events:
<br>
JPanel.setVisible (true); <br>
TimeUnit.SECONDS.sleep (3); <br>
JPanel.setVisible (false); <br>
in keyPressed for JTextArea.KeyListener ()
they don't execute one after another - first I get sleep, then JPanel.setVisible (true) and JPanel.setVisible (false)
public class Form1 extends JFrame {
JTextArea txt1 = new JTextArea();
JPanel pnl2 = new JPanel();
public Form1() {
txt1.setLocation(10, 10);
txt1.setSize(100, 30);
txt1.addKeyListener(new KeyListener() {
#Override
public void keyPressed(KeyEvent e
) {
if (e.getKeyCode() == KeyEvent.VK_TAB) {
e.consume();
pnl2.setVisible(true);
try {
TimeUnit.SECONDS.sleep(3);
} catch (InterruptedException ex) {
Logger.getLogger(Form1.class.getName()).log(Level.SEVERE, null, ex);
}
pnl2.setVisible(false);
}
}
#Override
public void keyTyped(KeyEvent e) {
}
#Override
public void keyReleased(KeyEvent e
) {
}
});
add(txt1);
pnl2.setLayout(null);
pnl2.setLocation(10, 150);
pnl2.setSize(100, 100);
pnl2.setBorder(BorderFactory.createEtchedBorder());
pnl2.setVisible(false);
add(pnl2);
}
}
Main class:
public class Main {
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
Form1 f = new Form1()
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.setSize(500, 400);
f.setLocationRelativeTo(null);
f.setResizable(false);
f.setLayout(null);
f.setVisible(true);
}
}
);
}
}
How can I get the effect of showing the panel on the form for a few seconds after entering the "TAB" button on TextArea?
Don't block the AWT Event Dispatch Thread (EDT).
Instead, set a javax.swing.Timer (get the package right - not the other one!). The Swing Timer may create another thread to do the timing, but posts the event back through the EDT (via java.awt.EventQueue.invokeLater or similar). The code executed after the sleep should be move to an action listener.
pnl2.setVisible(true);
javax.swing.Timer timer =
new javax.swing.Timer(3000, event -> {
pnl2.setVisible(false);
});
timer.setRepeats(false);
timer.start();
(I have used the fully qualified name to emphasize the right Timer. Sometimes I forget that by default it will repeat, which would be confusing.)

Process doesn't terminate when closing

I'm working on a programm and have a problem with closing it.
I added the following to listeners:
KeyListener kl = new KeyAdapter() {
public void keyPressed(KeyEvent evt) {
if(evt.getKeyCode()== KeyEvent.VK_ESCAPE) {
shutdown();
}
}
};
WindowListener wl = new WindowAdapter() {
public void windowClosing(WindowEvent e){
shutdown();
}
};
public void shutdown()
{
frame.dispose();
System.exit(0);
//dispose of a buffer
}
I also set:
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
If I run the the programm in eclipse both listeners close the programm and terminate the process. However if I run it with the runnable .jar only the keylistener works correctly. Closing the window normally does close it, but the process isn't terminated. Why is this and how do I fix this?

JButton not invoking actionPerformed on any subsequent click in same GUI instance

I have a JButton that will not allow me to perform the same action on any subsequent click on it after the first in the same Swing GUI instance.
JButton Run = new JButton("Run");
Run.setLocation(290, 70);
Run.setSize(120, 30);
buttonPanel.add(Run);
Run.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
if (Run.isEnabled()) {
errorLabel.setText("");
Result result = JUnitCore.runClasses(Run.class);
errorMessageDisplay(result);
}
}
});
totalGUI.setOpaque(true);
return totalGUI;
}
So far I thought about and tried removing the JPanel and painting all of the buttons back on, and disabling/renabling buttons.
The errorMessageDisplay method is as follows:
public void errorMessageDisplay(Result resultPass) {
if (resultPass.getFailureCount() > 0) {
errorLabel.setForeground(Color.red);
errorLabel.setVisible(true);
errorLabel.setText(" Failed");
}
else {
errorLabel.setForeground(Color.green);
errorLabel.setText(" Passed");
errorLabel.setVisible(true);
}
}
At first glance, the JUnitCore.runClasses(Run.class); call is suspicous. Also, it would be good to know what does the errorMessageDisplay() do. I believe, the problem is with one of these methods.
You can verify this with the following experimental code. Just be careful not to push it into production.
JButton run = new JButton("Run");
run.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
if (Run.isEnabled()) {
errorLabel.setText("");
System.out.println("Run action peformed.");
}
}
Update Since the errorMessageDisplay() looks okay, it's probably a Threading problem with JUniCore. Thus I'd try the following code:
final ExecutorService executor = Executors.newFixedThreadPool(5); // this runs stuff in background
JButton run = new JButton("Run");
// ..
run.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
if (Run.isEnabled()) {
executor.execute(new Runnable() { // This is how we run stuff in background. You can use lambdas instead of Runnables.
public void run() {
final Result result = JUnitCore.runClasses(Run.class); // Run.class is different from the current JButton run.
SwingUtilities.invokeLater(new Runnable() { // Now we go back to the GUI thread
public void run() {
errorMessageDisplay(result);
}
});
}
});
}
});

Change JLabel and wait for sometime to exit

I want to change the label when I click the button, and then after 3 seconds exit the program. But if I click the button, label does not change. It just exits after 3 seconds. This is my logic
Change the label.
Sleep for 3 seconds
Then exit the program.
btnNewButton_1.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
System.out.println("Stopping the program.");
state.setText("Bye...");
state.setBackground(SystemColor.textHighlight);
doStop();
}
});
state = new JLabel("Not listening");
state.setForeground(new Color(255, 255, 255));
state.setBackground(new Color(204, 0, 51));
state.setHorizontalAlignment(SwingConstants.CENTER);
state.setBounds(10, 222, 488, 24);
state.setOpaque(true);
frame.getContentPane().add(state);
public void doStop() {
try{
Thread.sleep(3000);
} catch(InterruptedException e){
}
System.exit(0); }
Use javax.swing.Timer like:
final Timer time= new Timer(3000,new ActionListener()
{
public void actionPerformed(ActionEvent e)
{
System.exit(0);
}
});
remove you doStop method, include this your code. Your button's actionListener would be like this
System.out.println("Stopping the program.");
state.setText("Bye...");
state.setBackground(SystemColor.textHighlight);
time.start();
Doc:
Fires one or more ActionEvents at specified intervals. An example use
is an animation object that uses a Timer as the trigger for drawing
its frames.
Learn MORE
Use javax.swing.TImer insted in your doStop(). Like this
public void doStop() {
Timer t=new Timer(3000, new ActionListener() {
public void actionPerformed(ActionEvent e) {
System.exit(0);
}
});
t.start();
}
I guess the problem is the thread.sleep, try to use a timer instead.
There is an exemple :
public void doStop() {
long savedTime=System.currentTimeMillis(), actualTime=System.currentTimeMillis();
while((savedTime+3000 > actualTime) ){
actualTime=System.currentTimeMillis()
}
System.exit(0);}

Recursion causes exit to exit all JFrames (terminates app)

I have made an application that gives the user the option to open up a new spawn of the application entirely. When the user does so and closes the application the entire application terminates; not just the window.
How should I go about recursively spawning an application and then when the user exits the JFrame spawn; killing just that JFrame and not the entire instance?
Here is the relevant code:
[...]
JMenuItem newMenuItem = new JMenuItem ("New");
newMenuItem.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent e)
{
new MainWindow();
}
});
fileMenu.add(newMenuItem);
[....]
JMenuItem exit = new JMenuItem("Exit");
exit.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent e)
{
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
});
fileMenu.add(exit);
[...]
First you should try JFrame.DISPOSE_ON_CLOSE instead of JFrame.EXIT_ON_CLOSE because EXIT_ON_CLOSE shuts down the application no matter if there are active threads running or not.
If you still have issues you should consider to introduce an instance counter. To react smarter
See also this discussion
I completely removed the frame.setDefaultCloserOperation(JFrame.EXIT_ON_CLOSE); code.
I changed it to DISPOSE_ON_CLOSE and still the problem was still happening. I ended up creating a windowEvent and adding: frame.dispose(); and the behavior is what I wanted.
Here is the code:
frame.addWindowListener(new WindowListener() {
public void windowClosing(WindowEvent e) {
//Allows for multiple instances and properly closing
//only one of the Frames instead of all of them
frame.dispose();
}
public void windowOpened(WindowEvent e) {}
public void windowClosed(WindowEvent e) {}
public void windowIconified(WindowEvent e) {}
public void windowDeiconified(WindowEvent e) {}
public void windowActivated(WindowEvent e) {}
public void windowDeactivated(WindowEvent e) {}
});

Categories