I'm using an UndoManager
to capture changes in my JTextArea
.
The method setText()
however deletes everything and then pastes the text. When I undo I firstly see an empty area and then it would show which text it had before.
How to reproduce:
- Run the following code
- Click the
setText()
button - Press CTRL+Z to undo (you'll see an empty textarea!)
- Press CTRL+Z to undo (you'll see the actual previous text)
I want to skip 3).
import javax.swing.AbstractAction;
import javax.swing.JFrame;
import javax.swing.JTextArea;
import javax.swing.KeyStroke;
import javax.swing.event.UndoableEditEvent;
import javax.swing.event.UndoableEditListener;
import javax.swing.text.Document;
import javax.swing.undo.CannotRedoException;
import javax.swing.undo.CannotUndoException;
import javax.swing.undo.UndoManager;
import java.awt.event.ActionEvent;
import javax.swing.JButton;
import java.awt.event.ActionListener;
@SuppressWarnings("serial")
public class JTextComponentSetTextUndoEvent extends JFrame
{
JTextArea area = new JTextArea();
public JTextComponentSetTextUndoEvent()
{
setSize(300, 300);
setDefaultCloseOperation(EXIT_ON_CLOSE);
getContentPane().setLayout(null);
area.setText("Test");
area.setBounds(0, 96, 146, 165);
getContentPane().add(area);
JButton btnSettext = new JButton("setText()");
btnSettext.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent arg0)
{
area.setText("stackoverflow.com");
}
});
btnSettext.setBounds(0, 28, 200, 50);
getContentPane().add(btnSettext);
final UndoManager undoManager = new UndoManager();
Document doc = area.getDocument();
doc.addUndoableEditListener(new UndoableEditListener()
{
public void undoableEditHappened(UndoableEditEvent evt)
{
undoManager.addEdit(evt.getEdit());
}
});
area.getActionMap().put("Undo", new AbstractAction("Undo")
{
public void actionPerformed(ActionEvent evt)
{
try
{
if (undoManager.canUndo())
{
undoManager.undo();
}
} catch (CannotUndoException e)
{
}
}
});
area.getInputMap().put(KeyStroke.getKeyStroke("control Z"), "Undo");
area.getActionMap().put("Redo", new AbstractAction("Redo")
{
public void actionPerformed(ActionEvent evt)
{
try
{
if (undoManager.canRedo())
{
undoManager.redo();
}
} catch (CannotRedoException e)
{
}
}
});
area.getInputMap().put(KeyStroke.getKeyStroke("control Y"), "Redo");
}
public static void main(String[] args)
{
new JTextComponentSetTextUndoEvent().setVisible(true);
}
}
.undo
in the code twice? – NoddlegetText
to see if the area is empty if so undo again else do nothing? – Noddle