I'm working in this program in this the user is asked, for different types of data, but each type of data depends of the previous ones. So I created three frames, in which I place the first quiz, and now what I want is to open a new window, when the user press a button (Next) which at the same time close the first one. What I've tried so far is to change a Boolean variable when the user press that button (Next), however, I don't know how to make reference to this last variable from a new class. I'm putting the trouble in context because may you can give me a better approach tho solve this.
Opening and closing windows isn't complicated and involves nothing more than creating the window instances (such as a JFrame or JDialog) and calling setVisible(true) or setVisible(false) on them. But having said that, how many commercial applications do you use where windows are thrown willy nilly at the user? Few because it's a user interface nightmare. Instead do your user's a favor and swap views with a CardLayout, and for the instance where you occasionally need to get information modally ,use a modal dialog such as a JDialog set to modal or a JOptionPane.
I think you can do it by typing these lines in (Next) button's ActionListener method:
dispose();
NewJFrame n = NweJFrame();
n.setVisible(true);
The line dispose(); will close your previous window and your another new window suppose named NewJFrame will be opened by this two line
NewJFrame n = NweJFrame();
n.setVisible(true);
But before that you must have to write the code of NewJFrame as you have written for your previous window.
this code was only half successfull.
Form2 f2 = new Form2();
if (f2 is Form2)
{
f2.Show();
this.Close();
}
else
{
Form1 f1 = new Form1();
f1.Show();
}
Related
I have written an application in Java that has a JFrame with options. I now want a certain action to be executed when the user has confirmed the dialog with "Ok". I was recommended to add a return value to JFrame.
Unfortunately, I don't have any experience and need some help. Here are the details.
I want to extend JFrame so that I can have an Enum "DialogResult" when closing a JFrame like in the .Net Framework. Well, the Enum is no problem. My problem is to replicate the ShowDialog method from WinForms of the .Net Framework working in Java for the class JFrame.
Below is an example code in C#:
// DlgOptions : Form
DlgOptions dlg = new DlgOptions();
if(dlg.ShowDialog() == DialogResult.Ok)
{
// do something only when "Ok" was clicked
}
Here's a link from MSDN with the behavior I want to replicate:
https://msdn.microsoft.com/de-de/library/c7ykbedk(v=vs.110).aspx
How can I best implement this? Thanks in advance.
EDIT:
I changed my DlgOptions class so it doesn't extend JFrame but JDialog. I also added an enumeration DialogResult and added a public property of this type in my DlgOptions. But I still have a problem. When I use this code:
// executed when user clicked a JMenuItem in a JMenuBar
DlgOptions dlg = new DlgOptions();
dlg.setModal(true);
dlg.setVisible(true);
if(dlg.DialogResult == DialogResult.OK)
{
// do something
}
the program continues running before the user closed the modal dialog. What can I do?
EDIT 2:
My JDialog contains two JButtons; one to confirm changes that were made and one to abort changing the preferences for the program. I have several JCheckBoxes the user can check or uncheck.
So a JOptionPane would not be what I want / need (as far as I know). That's why I need a modal JDialog. But my Java code above doesn't work as I want it to. I read on a German website of a Java book that a JDialog set to modal with
setModal(true);
would cause the program to wait until the dialog is closed. The problem is, that the code continues too early.
I have a problem about modify button background. I am using netbeans gui builder for build form. I am trying change button background when the second frame is open and turn it back when second frame close.
public void update(boolean x){
if(x==true){
circleButton.setOpaque(true);
circleButton.setBackground(new java.awt.Color(0, 0, 0));
System.out.println("testoutput");
}
}
this is my update method from first class.
I added window listener to second frame.
private void formWindowOpened(java.awt.event.WindowEvent evt) {
isitopen = true;
//this is first class which includes button
homework hwork = new homework();
hwork.update(isitopen);
System.out.println("testoutput2");
}
I got 2 testoutput but color of the button didn't change.
What can i do to fix this issue ?
You're creating a new homework object in your formWindowOpened(...) method, one completely unrelated to the homework object that is displayed, and changing the state of the new object will have no effect on the displayed one.
A simple and WRONG solution is to use static fields or methods.
Instead one simple solution is to give the calss with your formWindowOpened(...) method a valid reference to the displayed homework object, something that can be done with a constructor parameter or a setHomework(...) method.
A much better and even simpler solution:
Make the 2nd window a modal JDialog, not a JFrame
This way homework will know when the window is open and can set its own button colors. When the 2nd window opens, program flow in the calling class is put on hold, and only resumes when the 2nd window closes -- just like using a JOptionPane.
For more on this, please see The Use of Multiple JFrames, Good/Bad Practice?
As an aside, you will want to learn and use Java naming conventions. Variable names should all begin with a lower letter while class names with an upper case letter. Learning this and following this will allow us to better understand your code, and would allow you to better understand the code of others.
Using reflection, I've managed to invoke the main method of another java application that uses swing to create windows. I've also been able to grab those windows and manipulate them. When I get to a certain point, I loop through the actionListeners of a certain JMenuItem and I call their actionPerformed telling them the button has been pressed. This works exactly as intended, and opens a new window. When this window opens, however, I want to do something similar to it by first getting the window and then the components inside of it.
However, as soon as the event is fired, the window is created and my program is put in a busy loop waiting for the window I want to interact with to close. This is caused by the application I am invoking, and I have no control over this, nor do I have an opportunity to do anything about it.
Here's how I am doing that event firing
for (ActionListener a : nc.getActionListeners()) {
a.actionPerformed(new ActionEvent(nc, ActionEvent.ACTION_PERFORMED,null) {});
}
What I'm thinking is I might want to have another thread that's looking for the window, but I'm not even sure if that will work..
Window has static method
public static Window[] getWindows() {
return getWindows(AppContext.getAppContext());
}
Frame has similar one
public static Frame[] getFrames()
So you can get copy of the created windows (frames) before your click emulation and compare with the new list after click to find the newly created one.
I'm writing a Java app (Swing GUI) that periodically pops up a JFrame.
Is it possible somehow to bring the window to front (foo.setAlwaysOnTop(true) would be even better) but without having it focus?
Some people move their eyes away from the screen from time to time to look at their keyboard while typing, and I'm sure that if this window would always capture the keyboard focus people would get really annoyed as it's causing them to lose quite a few keystrokes every time it pops up unnoticed.
In other cases, even when the user is actually capable of typing without looking at the keyboard all the time, having a window pop up and get focus could cause unwanted actions from the pop-up window itself (some Tab+Enter combination for example, where the user accidentally selects an option she really wouldn't had selected otherwise).
Thanks in advance!
Update
As Jonas suggests, foo.setFocusableWindowState(false); seems to work if called after the window has been rendered (tested on Gnome only).
This does not work:
foo.setFocusableWindowState(false);
foo.setVisible(true);
foo.setFocusableWindowState(true);
However, this does:
foo.setFocusableWindowState(false);
foo.setVisible(true);
Thread.sleep(1000);
foo.setFocusableWindowState(true);
I'll have to see if there's an event I can catch/listen to that allows me to do foo.setFocusableWindowStatue(true); when appropriate.
I consider my problem solved.
This may work:
foo.setFocusableWindowState(false);
As of Java 1.7 you can call
frame.setAutoRequestFocus(false);
I recently ran into the same problem, and the tentative solution has been:
JFrame frame = ...;
frame.setExtendedState(JFrame.NORMAL);
frame.setAlwaysOnTop(true);
frame.requestFocus();
frame.setAlwaysOnTop(false);
Suggestion: In the GUI Component that creates the Frame, put 2 consecutive calls:
frameJustCreated.requestFocus();
this.requestFocus();
1st one bring the window of the new JFrame to the top, 2nd one keeps the window where the user is typing at the top.
If you want to call setFocusableWindowState(true) in an event (so, not to wait e.g. 1 second), you can add a WindowListener (e.g. derived from WindowAdapter) that changes the property:
appFrame.addWindowListener(new WindowAdapter() {
#Override
public void windowOpened(WindowEvent e) {
super.windowOpened(e);
e.getWindow().setFocusableWindowState(true);
}
});
appFrame.setFocusableWindowState(false);
appFrame.setVisible(true);
JInternalFrame toFront() calls to moveToFront()
Override moveToFront()
public void moveToFront() {
Window window = SwingUtilities.getWindowAncestor(this);
Component focusOwner = (window != null) ? window.getFocusOwner() :
null;
boolean descendant = false;
if (window != null && focusOwner != null &&
SwingUtilities.isDescendingFrom(focusOwner, this)) {
descendant = true;
requestFocus();
}
super.moveToFront();
if (descendant) {
focusOwner.requestFocus();
}
}
the fix is in moveToFront to check if a child has focus, if it does, then temporarily request focus on the internal frame. After the internal frame has movthe ed to front, then request focus back on the previously focused component. This will ensure the appropriate events are generated.
refer
https://bugs.openjdk.java.net/browse/JDK-4309079
I have a JDialog that takes a name from the user. Behind the JDialog, is an applet. I dont want the user to access that applet until he has entered the name. I tried JDialog.setAlwaysOnTop(true), but the applet throws an AccessException error. So what I did was keep a while loop that will execute JDialog.setVisible(true) till the JtextField(input for user name) is empty (""). But for some reason this works really slow, meaning the JDialog loads, but it takes time to focus on the JTextField and even when the user types his name, it comes really slow... like one character in 2 seconds... Is there any other way for me to force the user to enter the name before accessing the applet?
Use a modal JDialog. For example the code in your init(...) method of JApplet might include:
JDialog dialog = new JDialog(SwingUtilities.windowForComponent(this));
dialog.setModal(true);
dialog.setSize(...);
dialog.setVisible( true );
Or you can just use a JOptionPane.showInputDialog(). Again you would just specify "this" as the parent component of the option pane.
Another option would be:
frame.setAlwaysOnTop(true);
It forces the dialog on top of any other.
It runs slowly because the program is processing that foo loop
What you can do is to add a window listener and then the jdialog lost it's focus ( or the applet gains it ) return the focus to the jdialog.
This should perform much better than the for loop you're using right now