I have two textfields and I control values user enters to that textfields. For both of the textfields I use focusLost. However, for example, when the user not enters any value (one of the controls) and clicks other textfield I get first and second textfields control's information message. I mean after focus lost from the first text field, the second text field's focusLost be triggered. Why this happens? How to prevent this?
import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
import javax.swing.border.*;
public class Test extends JFrame
{
private JPanel pa;
private JTextField myTF1, myTF2;
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
public void run() {
try{
Test frame = new Test();
frame.setVisible(true);
}
catch(Exception e) {
e.printStackTrace();
}
}
});
}
public Test()
{
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setBounds(100,100,450,300);
pa = new JPanel();
pa.setBorder(new EmptyBorder(5,5,5,5));
setContentPane(pa);
pa.setLayout(null);
myTF1 = new JTextField();
myTF1.addFocusListener(new FocusListener()
{
public void focusLost(FocusEvent arg)
{
if(myTF1.getText.equals(""))
JOptionPane.showMessageDialog(null, "Error1", "Error", JOptionPane.ERROR_MESSAGE);
}
public void focusGained(FocusEvent arg)
{
// This is empty.. I don't need it..
}
});
myTF1.setBounds(24,13,116,22);
pa.add(myTF1);
myTF1.setColumns(10);
myTF2 = new JTextField();
myTF2.addFocusListener(new FocusListener()
{
public void focusLost(FocusEvent arg)
{
if(myTF2.getText.equals(""))
JOptionPane.showMessageDialog(null, "Error2", "Error", JOptionPane.ERROR_MESSAGE);
}
public void focusGained(FocusEvent arg)
{
// This is empty.. I don't need it..
}
});
myTF2.setBounds(24,48,116,22);
pa.add(myTF2);
myTF2.setColumns(10);
}
}
When the option pane is opened, the option pane gains the focus, stealing it from either of the text fields that has it at that moment.
One approach to solving this is to display the error messages in a label within the main GUI. Here is an example:
import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
import javax.swing.border.*;
public class Test2 extends JFrame {
private JTextField myTF1, myTF2;
private JLabel output = new JLabel("Enter a value in both field 1 & field 2");
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
public void run() {
try {
Test2 frame = new Test2();
frame.setVisible(true);
} catch (Exception e) {
e.printStackTrace();
}
}
});
}
public Test2() {
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setLocationByPlatform(true);
JPanel gui = new JPanel(new BorderLayout(5,5));
gui.setBorder(new EmptyBorder(5, 5, 5, 5));
setContentPane(gui);
JPanel pa = new JPanel(new GridLayout(0, 1, 5, 5));
gui.add(pa, BorderLayout.LINE_START);
gui.add(output, BorderLayout.PAGE_END);
myTF1 = new JTextField(10);
myTF1.addFocusListener(new FocusListener() {
public void focusLost(FocusEvent arg) {
if (myTF1.getText().equals("")) {
output.setText("Error: Field 1 must have a value!");
}
}
public void focusGained(FocusEvent arg) {
// This is empty.. I don't need it..
}
});
myTF1.setBounds(24, 13, 116, 22);
pa.add(myTF1);
myTF2 = new JTextField(10);
myTF2.addFocusListener(new FocusListener() {
public void focusLost(FocusEvent arg) {
if (myTF2.getText().equals("")) {
output.setText("Error: Field 2 must have a value!");
}
}
public void focusGained(FocusEvent arg) {
// This is empty.. I don't need it..
}
});
myTF2.setBounds(24, 48, 116, 22);
pa.add(myTF2);
pack();
}
}
Related
I want to know how to open this JFrame form (1) when I click a button in the second JFrame (2). The problem is that I am unable to get the .setVisible method in the Form 2. Please help. Thanks & Regards ! :)
Form 1 (to be opened when a button is clicked on Form 2
public class FlightForm {
public FlightForm() {
initialize();
}
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
public void run() {
try {
FlightForm window = new FlightForm();
window.frame.setVisible(true);
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
}
Form 2
public class MainMenu{
private JFrame frame;
/**
* Launch the application.
*/
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
public void run() {
try {
MainMenu window = new MainMenu();
window.setVisible(true);
} catch (Exception e) {
e.printStackTrace();
}
}
});
}
/**
* Create the application.
*/
public MainMenu() {
frame = new JFrame("Main Menu");
setBounds(100, 100, 830, 574);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().setLayout(null);
JButton btnNewButton = new JButton("Flight Form");
);
btnNewButton.setFont(new Font("Candara", Font.BOLD, 15));
btnNewButton.setBounds(169, 328, 193, 77);
frame.getContentPane().add(btnNewButton);
JButton btnNewButton_1 = new JButton("Passenger Form");
btnNewButton_1.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
PassengerForm window = new PassengerForm();
window.setVisible(true); // This is not working
You can call setVisible(true) on PassengerForm() only if PassengerForm class extends JFrame. If no you should use something like:
PassengerForm window = new PassengerForm();
window.getFrame().setVisible(true)
I am making my first game, and the last time I asked this question, I kinda didn't explain it very well. Basically, below is the opening screen of the game. I know, not very good, but it is just a rough draft. Then I also built the game.
There are two buttons in the opening screen, for it is a 2 player game. Both players must click ready, and then I want to program to end, and to start the second program. However I'm not sure how to do that.
import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
public class OpeningScreen {
JFrame frame;
JPanel main;
JButton ready1;
JButton ready2;
JPanel bottom;
JLabel label;
public OpeningScreen(){
UIManager.put("Button.background", Color.cyan);
UIManager.put("Button.foreground", Color.magenta);
UIManager.put("ToolTip.background", Color.magenta);
frame=new JFrame("Super Tuesday");
main=new JPanel();
ready1=new JButton("CLICK IF READY");
ready2=new JButton("CLICK IF READY");
label=new JLabel("SUPER TUESDAY");
bottom=new JPanel();
label.setFont(label.getFont().deriveFont(50.0f));
frame.setSize(480, 800);
frame.setLayout(new BorderLayout());
frame.add(main, BorderLayout.CENTER);
bottom.setLayout(new BorderLayout());
ready1.setToolTipText("CLICK ME TO START THE GAME");
ready2.setToolTipText("CLICK ME TO START THE GAME");
main.setBackground(Color.gray);
label.setForeground(Color.white);
ready1.setFont(ready1.getFont().deriveFont(20.0f));
ready2.setFont(ready2.getFont().deriveFont(20.0f));
ready1.setForeground(Color.pink);
ready2.setForeground(Color.pink);
ready1.setPreferredSize(new Dimension(240,150 ));
ready2.setPreferredSize(new Dimension(240, 150));
bottom.setPreferredSize(new Dimension(600, 150));
main.setLayout(new FlowLayout());
main.add(label, BorderLayout.NORTH);
frame.add(bottom, BorderLayout.SOUTH);
bottom.add(ready1, BorderLayout.WEST);
bottom.add(ready2, BorderLayout.EAST);
MyMouseManager1 mmm1=new MyMouseManager1();
MyMouseManager2 mmm2=new MyMouseManager2();
ready1.addMouseListener(mmm1);
ready2.addMouseListener(mmm2);
frame.setVisible(true);
}
class MyMouseManager1 implements MouseListener{
public void mouseClicked(MouseEvent e) {
ready1.setBackground(Color.green);
ready1.setForeground(Color.white);
ready1.setText("READY!");
}
public void mousePressed(MouseEvent e) {
}
public void mouseReleased(MouseEvent e) {
}
public void mouseEntered(MouseEvent e) {
}
public void mouseExited(MouseEvent e) {
}
public void mouseDragged(MouseEvent e) {
}
public void mouseMoved(MouseEvent e) {
}
}
class MyMouseManager2 implements MouseListener{
public void mouseClicked(MouseEvent e) {
ready2.setBackground(Color.green);
ready2.setForeground(Color.white);
ready2.setText("READY!");
}
public void mousePressed(MouseEvent e) {
}
public void mouseReleased(MouseEvent e) {
}
public void mouseEntered(MouseEvent e) {
}
public void mouseExited(MouseEvent e) {
}
public void mouseDragged(MouseEvent e) {
}
public void mouseMoved(MouseEvent e) {
}
}
public static void main(String[] args){
OpeningScreen smartie=new OpeningScreen();
}
}
Here is the second program. Please don't copy. heh.
import javax.swing.*;
import java.awt.*;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener;
import java.applet.Applet;
public class Clickasfastasyoucan extends java.applet.Applet{
private JFrame w;
private JPanel b;
private Button p;
private JPanel d;
private int times;
private JLabel number;
JPanel n;
JFrame x;
public Clickasfastasyoucan() {
x=new JFrame(" ");
n=new JPanel();
times=0;
number=new JLabel("How fast can you click?");
w = new JFrame("My Smart Button");
w.setSize(1500, 1000);
b = new JPanel();
p = new Button("Swipe as fast as you can");
w.setSize(500, 500);
b.setPreferredSize(new Dimension(1000,1500));
d=new JPanel();
w.add(b);
b.add(p);
b.setLayout(new GridLayout(1, 1));
b.add(number, BorderLayout.CENTER);
d.setSize(500, 500);
MyMouseManager mmm = new MyMouseManager();
p.addMouseListener(mmm);
p.addMouseMotionListener(mmm);
p.setForeground(Color.white);
p.setBackground(Color.black);
p.setFont(p.getFont().deriveFont(20.0f));
p.setFont(p.getFont().deriveFont(20.0f));
b.setSize(600, 600);
w.setVisible(true);
}
class MyMouseManager implements MouseListener, MouseMotionListener {
public void mouseClicked(MouseEvent e) {
}
public void mousePressed(MouseEvent e) {
n.setBackground(Color.blue);
x.add(n);
x.setSize(500, 500);
n.setSize(500, 500);
x.setVisible(true);
}
public void mouseReleased(MouseEvent e) {
}
public void mouseEntered(MouseEvent e) {
n.setBackground(Color.blue);
}
public void mouseExited(MouseEvent e) {
n.setBackground(Color.white);
}
public void mouseDragged(MouseEvent e) {
}
public void mouseMoved(MouseEvent e) {times++;
number.setFont(number.getFont().deriveFont(100.0f));
number.setText(" "+times+" ");
if (times>=100&×<999){
b.setBackground(Color.red);
number.setFont(number.getFont().deriveFont(80.0f));
times=times+1;
}
if(times>=1000&×<10000){
b.setBackground(Color.green);
number.setFont(number.getFont().deriveFont(70.0f));
times=times+4;
}
if(times>=10000&×<50000){
b.setBackground(Color.yellow);
number.setFont(number.getFont().deriveFont(70.0f));
times=times+100;
}if(times>=50000&×<500000){
b.setBackground(Color.blue);
number.setFont(number.getFont().deriveFont(70.0f));
times=times+500;
}
if(times>=500000&×<4999999){
b.setBackground(Color.pink);
number.setFont(number.getFont().deriveFont(40.0f));
times=times+1000;
}
if(times>=5000000){
b.setBackground(Color.orange);
number.setFont(number.getFont().deriveFont(20.0f));
number.setText("WOW! YOU WON. CHECK THE OUTPUT TO SEE HOW YOU SCORED!");
System.out.println("1 day: Are you still there?");
System.out.println("24 hour: Snail speed");
System.out.println("15 hours: Fail");
System.out.println("5 hours: Slow Fingers");
System.out.println("1 hour: Fast Fingers");
System.out.println("30 minutes: Champion");
System.out.println("15 minutes: You beat me!");
System.out.println("2 minutes: Cheater");
System.out.println("1 minute: Speed of Light");
System.out.println("");
System.out.println("");
System.out.println("");
System.out.println("");
System.out.println("");
System.out.println("___________________________-");
}
}
}
public static void main(String[] args) {
Clickasfastasyoucan clickgame= new Clickasfastasyoucan();
}
}
I want this one to replace the first program. I'm not sure how to even start with this though, since this is my first attempt at any game, or anything beyond a one class program.
No, you really don't want a java.awt.Applet to replace a JFrame, trust me. They're both used in two vastly different situations, and while the Swing library that underlies JFrames is about 4 years out of date, the AWT library that underlies java.awt.Applet is about 20 years out of date. Just stay clear of Applet.
Instead your GUI classes should be geared towards creating JPanels, which can then be placed into JFrames or JDialogs, or JTabbedPanes, or swapped via CardLayouts, wherever needed. This will greatly increase the flexibility of your GUI coding, and in fact this is what I recommend -- that you swap views via a CardLayout.
Also -- don't use MouseListeners for your JButton listeners but instead use ActionListeners. MouseListeners won't respond to space bar presses, won't be disabled if the button becomes disabled, and can be capricious if you base behavior on the mouseClicked method. Use the proper tool for the job: ActionListeners, or even better, Actions.
For example:
import java.awt.BorderLayout;
import java.awt.CardLayout;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.GridBagLayout;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.geom.AffineTransform;
import javax.swing.*;
public class MainGui extends JPanel {
private CardLayout cardLayout = new CardLayout();
private StartUpPanel startUpPanel = new StartUpPanel(this);
private GamePanel gamePanel = new GamePanel(this);
public MainGui() {
setLayout(cardLayout);
add(startUpPanel, startUpPanel.getName());
add(gamePanel, gamePanel.getName());
}
public void nextCard() {
cardLayout.next(this);
}
private static void createAndShowGui() {
MainGui mainPanel = new MainGui();
JFrame frame = new JFrame("MainGui");
frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
frame.getContentPane().add(mainPanel);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
createAndShowGui();
}
});
}
}
class StartUpPanel extends JPanel {
public static final String CLICK_IF_READY = "Click If Ready";
public static String SUPER_TUESDAY = "SUPER TUESDAY";
public static final String READY = "READY";
public static final int MAX_READY = 2;
private static final float TITLE_FONT_POINTS = 40f;
public static final String START_UP_PANEL = "Startup Panel";
private static final int PREF_W = 600;
private static final int PREF_H = PREF_W;
private int readyCount = 0;
private MainGui mainGui;
public StartUpPanel(MainGui mainGui) {
this.mainGui = mainGui;
setName(START_UP_PANEL);
JLabel titleLabel = new JLabel(SUPER_TUESDAY, SwingConstants.CENTER);
titleLabel.setFont(titleLabel.getFont().deriveFont(Font.BOLD, TITLE_FONT_POINTS));
JButton button1 = new JButton(new StartupAction());
JButton button2 = new JButton(new StartupAction());
button1.setFont(button1.getFont().deriveFont(Font.BOLD, TITLE_FONT_POINTS));
button2.setFont(button1.getFont());
JPanel southPanel = new JPanel(new GridLayout(1, 0));
southPanel.add(button1);
southPanel.add(button2);
setLayout(new BorderLayout());
add(titleLabel, BorderLayout.CENTER);
add(southPanel, BorderLayout.PAGE_END);
}
#Override
public Dimension getPreferredSize() {
Dimension superSize = super.getPreferredSize();
if (isPreferredSizeSet()) {
return superSize;
}
int prefW = Math.max(superSize.width, PREF_W);
int prefH = Math.max(superSize.height, PREF_H);
return new Dimension(prefW, prefH);
}
private class StartupAction extends AbstractAction {
public StartupAction() {
super(CLICK_IF_READY);
}
#Override
public void actionPerformed(ActionEvent e) {
if (getValue(NAME).equals(CLICK_IF_READY)) { // check if button active
putValue(NAME, READY); // swap button's name
((AbstractButton) e.getSource()).setFocusable(false); // lose focus
readyCount++; // increment ready count.
if (readyCount >= MAX_READY) { // if all buttons pushed
mainGui.nextCard(); // tell main GUI to swap cards
}
}
}
}
}
// simple mock class to represent the game
class GamePanel extends JPanel {
public static final String GAME = "Game";
private static final float FONT_POINTS = 30F;
private MainGui mainGui;
public GamePanel(MainGui mainGui) {
this.mainGui = mainGui;
setName(GAME);
JLabel label = new JLabel(GAME, SwingConstants.CENTER);
label.setFont(label.getFont().deriveFont(Font.BOLD, FONT_POINTS));
setLayout(new GridBagLayout());
add(label);
}
}
When I pressed the ENTER my JTextArea starts a new row and I only want do to the doClick() method nothing else.
How should I do that?
textarea.addKeyListener(new KeyListener(){
#Override
public void keyPressed(KeyEvent e){
if(e.getKeyCode() == KeyEvent.VK_ENTER){
button.doClick();
}
}
#Override
public void keyTyped(KeyEvent e) {
}
#Override
public void keyReleased(KeyEvent e) {
}
});
Use .consume():
Consumes this event so that it will not be processed in the default
manner by the source which originated it.
public void keyPressed(KeyEvent e){
if(e.getKeyCode() == KeyEvent.VK_ENTER){
e.consume();
button.doClick();
}
}
Documentation
You should use KeyBindings with any JTextComponent in question. KeyListeners are way too low level from Swing's perspective. You are using the concept which was related to AWT, Swing uses KeyBindings to do the same task with more efficiency and provides desired results :-)
A small program for your help :
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class KeyBindingExample {
private static final String key = "ENTER";
private KeyStroke keyStroke;
private JButton button;
private JTextArea textArea;
private Action wrapper = new AbstractAction() {
#Override
public void actionPerformed(ActionEvent ae) {
button.doClick();
}
};
private void displayGUI() {
JFrame frame = new JFrame("Key Binding Example");
frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
JPanel contentPane = new JPanel(new BorderLayout(5, 5));
textArea = new JTextArea(10, 10);
keyStroke = KeyStroke.getKeyStroke(key);
Object actionKey = textArea.getInputMap(
JComponent.WHEN_FOCUSED).get(keyStroke);
textArea.getActionMap().put(actionKey, wrapper);
button = new JButton("Click Me!");
button.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent ae) {
System.out.format("Button Clicked :-)%n");
}
});
contentPane.add(textArea, BorderLayout.CENTER);
contentPane.add(button, BorderLayout.PAGE_END);
frame.setContentPane(contentPane);
frame.pack();
frame.setLocationByPlatform(true);
frame.setVisible(true);
}
public static void main(String[] args) {
Runnable r = new Runnable() {
#Override
public void run() {
new KeyBindingExample().displayGUI();
}
};
EventQueue.invokeLater(r);
}
}
I have a jdialog and want close it on confirmation after that store the data of a text box... now I have no problem to store the data from the box but,
How can I close this dialog after the operation???
Seems a simple thing but I haven't found the solution.
public class test extends JDialog {
private final JPanel contentPanel = new JPanel();
public test() {
setBounds(100, 100, 450, 300);
getContentPane().setLayout(new BorderLayout());
contentPanel.setLayout(new FlowLayout());
contentPanel.setBorder(new EmptyBorder(5, 5, 5, 5));
getContentPane().add(contentPanel, BorderLayout.CENTER);
{
JPanel buttonPane = new JPanel();
buttonPane.setLayout(new FlowLayout(FlowLayout.RIGHT));
getContentPane().add(buttonPane, BorderLayout.SOUTH);
{
JButton okButton = new JButton("OK");
okButton.setActionCommand("OK");
buttonPane.add(okButton);
getRootPane().setDefaultButton(okButton);
okButton.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent e) {
try{
int x=Integer.parseInt(textField.getText());
saver.saveN(x);
}catch(Exception ecc){
JOptionPane.showMessageDialog(Test.this,"error");
}
}
});
}
}
}
}
Either use Window#dispose or Window#setVisible(false).
if you use this dialog only once time then there is same to use dispose() as setVisible(false)
in the case that you invoke this method more than once time, then you can use HIDE_ON_CLOSE
or setVisible(false), better would be re_use this JDialog
EDIT
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import javax.swing.Timer;
import javax.swing.border.EmptyBorder;
public class Test {
private static final long serialVersionUID = 1L;
private JDialog dialog = new JDialog();
private final JPanel contentPanel = new JPanel();
private Timer timer1;
private JButton killkButton = new JButton("Kill JDialog");
public Test() {
contentPanel.setLayout(new FlowLayout());
contentPanel.setBorder(new EmptyBorder(5, 5, 5, 5));
JPanel buttonPane = new JPanel();
JButton okButton = new JButton("OK");
okButton.setActionCommand("OK");
buttonPane.add(okButton);
killkButton.setActionCommand("Kill JDialog");
buttonPane.add(killkButton);
dialog.setDefaultCloseOperation(JDialog.HIDE_ON_CLOSE);
dialog.addWindowListener(new WindowListener() {
public void windowOpened(WindowEvent e) {
}
public void windowClosing(WindowEvent e) {
startTimer();
}
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) {
}
});
dialog.setLayout(new BorderLayout());
dialog.getRootPane().setDefaultButton(okButton);
dialog.add(buttonPane, BorderLayout.SOUTH);
dialog.add(contentPanel, BorderLayout.CENTER);
dialog.pack();
dialog.setLocation(100, 100);
dialog.setVisible(true);
setKeyBindings();
}
private void setKeyBindings() {
killkButton.getInputMap(
JComponent.WHEN_ANCESTOR_OF_FOCUSED_COMPONENT).put(
KeyStroke.getKeyStroke("ENTER"), "clickENTER");
killkButton.getActionMap().put("clickENTER", new AbstractAction() {
private static final long serialVersionUID = 1L;
#Override
public void actionPerformed(ActionEvent e) {
System.exit(0);
}
});
}
private void startTimer() {
timer1 = new Timer(1000, new AbstractAction() {
private static final long serialVersionUID = 1L;
#Override
public void actionPerformed(ActionEvent e) {
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
dialog.setVisible(true);
}
});
}
});
timer1.setDelay(500);
timer1.setRepeats(false);
timer1.start();
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
Test test = new Test();
}
});
}
}
If you plan to use a jDialog again with all the field values and component states left the same when you close it, use setVisible(false).
In any other case, call dispose(), to avoid the jDialog remaining in the memory when it is no longer required.
When using JTextFields i like to set a default text.
Then i run the program and this default text will automatically be selected (at least when you have only one field). In other words, if I type a letter right away, the default text will be deleted and replaced by the new one.
My question is how I can change the default settings in a way that allows me to type a letter without deleting the default text? I would like the letter to just be added at the end of the default text.
Here's my code:
public class ButtonsNText extends JPanel implements ActionListener, KeyListener {
private JTextField TextLine;
private JToggleButton UpperCaseButton;
private JToggleButton LowerCaseButton;
private JCheckBox ContinuousButton;
private ButtonGroup myButtonGroup;
public ButtonsNText(){
TextLine = new JTextField(10);
add(TextLine); TextLine.setName("TextLine");
TextLine.setText("default text");
TextLine.setCaretPosition(TextLine.getText().length());
TextLine.addKeyListener(this);
myButtonGroup = new ButtonGroup();
UpperCaseButton = new JToggleButton("Upper case");
add(UpperCaseButton);UpperCaseButton.setName("UpperCaseButton");
LowerCaseButton = new JToggleButton("Lower case");
add(LowerCaseButton); LowerCaseButton.setName("LowerCaseButton");
ContinuousButton = new JCheckBox("Continuous?");
add(ContinuousButton); ContinuousButton.setName("ContinuousButton");
myButtonGroup.add(UpperCaseButton); myButtonGroup.add(LowerCaseButton);
UpperCaseButton.addActionListener(this);
LowerCaseButton.addActionListener(this);
ContinuousButton.addActionListener(this);
}
public static void main(String[] args) {
JFrame frame = new JFrame("Hello world example");
frame.add(new ButtonsNText());
frame.pack();
frame.setVisible(true);
}
#Override
public void actionPerformed(ActionEvent e) {
if(e.getSource() == UpperCaseButton){
TextLine.setText(TextLine.getText().toUpperCase());
}
else if(e.getSource() == LowerCaseButton){
TextLine.setText(TextLine.getText().toLowerCase());
}
}
#Override
public void keyReleased(KeyEvent k) {
if(ContinuousButton.isSelected()){
if(UpperCaseButton.isSelected()){
int pos = TextLine.getCaretPosition();
TextLine.setText(TextLine.getText().toUpperCase());
TextLine.setCaretPosition(pos);
}
else if(LowerCaseButton.isSelected()){
int pos = TextLine.getCaretPosition();
TextLine.setText(TextLine.getText().toLowerCase());
TextLine.setCaretPosition(pos);
}
}
int key = k.getKeyCode();
if(key == KeyEvent.VK_ENTER){
if(UpperCaseButton.isSelected()){
TextLine.setText(TextLine.getText().toUpperCase());
}
else if(LowerCaseButton.isSelected()){
TextLine.setText(TextLine.getText().toLowerCase());
}
}
}
}
I have tried things like isFocusable(), setFocusable(), setCaterPosition() and other similar methods, but here I think I need a different approach.
Just add one FocusListener for focus Gained, that will do for you along with tfield2.setCaretPosition(tfield2.getDocument().getLength());
Here see the code for your help :
import java.awt.event.*;
import javax.swing.*;
public class TextFieldExample extends JFrame
{
public TextFieldExample()
{
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setLocationRelativeTo(null);
JPanel contentPane = new JPanel();
JTextField tfield = new JTextField(10);
final JTextField tfield2 = new JTextField(10);
tfield2.setText("default text");
tfield2.addFocusListener(new FocusListener()
{
public void focusGained(FocusEvent fe)
{
tfield2.setCaretPosition(tfield2.getDocument().getLength());
}
public void focusLost(FocusEvent fe)
{
}
});
contentPane.add(tfield);
contentPane.add(tfield2);
setContentPane(contentPane);
pack();
setVisible(true);
}
public static void main(String... args)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new TextFieldExample();
}
});
}
}
for #Pete and will be deleted
import java.awt.*;
import javax.swing.*;
import javax.swing.text.DefaultCaret;
import javax.swing.text.DefaultHighlighter;
import javax.swing.text.Highlighter;
public class TestTextComponents extends JFrame {
private static final long serialVersionUID = 1L;
private JTextField jTextField1;
private JTextField jTextField2;
public TestTextComponents() {
initComponents();
}
private void initComponents() {
jTextField1 = new JTextField();
jTextField2 = new JTextField();
getContentPane().setLayout(new FlowLayout());
setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
setTitle("Text component persistent selection");
setResizable(false);
getContentPane().add(new JLabel(
"Please skip between text fields and watch persistent selection: "));
jTextField1.setText("jTextField1");
getContentPane().add(jTextField1);
jTextField2.setText("jTextField2");
getContentPane().add(jTextField2);
jTextField1.setCaret(new HighlightCaret());
jTextField2.setCaret(new HighlightCaret());
//Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize();
// setBounds((screenSize.width - 600) / 2, (screenSize.height - 70) / 2, 600, 70);
}
public static void main(String args[]) {
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
new TestTextComponents().setVisible(true);
}
});
}
}
class HighlightCaret extends DefaultCaret {
private static final Highlighter.HighlightPainter unfocusedPainter =
new DefaultHighlighter.DefaultHighlightPainter(new Color(230, 230, 210));
private static final long serialVersionUID = 1L;
private boolean isFocused;
#Override
protected Highlighter.HighlightPainter getSelectionPainter() {
return isFocused ? super.getSelectionPainter() : unfocusedPainter;
}
#Override
public void setSelectionVisible(boolean hasFocus) {
if (hasFocus != isFocused) {
isFocused = hasFocus;
super.setSelectionVisible(false);
super.setSelectionVisible(true);
}
}
}
How about if you moved the caret to the end?
txt.setCaretPosition(txt.getText().length());