Changeset 14204 in josm


Ignore:
Timestamp:
2018-08-29T23:16:52+02:00 (3 months ago)
Author:
wiktorn
Message:

Move undo handler to EDT

To prevent live-locks when undo is called outside EDT and locks DataSet, and
DrawAction.selectionChanged tries to reaquire this lock in EDT thread.

Also - add synchronized keyword to redo and clean, to be symetrical with undo.

Closes: #16679

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/org/openstreetmap/josm/data/UndoRedoHandler.java

    r14143 r14204  
    1010import org.openstreetmap.josm.data.osm.DataSet;
    1111import org.openstreetmap.josm.data.osm.OsmDataManager;
     12import org.openstreetmap.josm.gui.util.GuiHelper;
    1213import org.openstreetmap.josm.spi.preferences.Config;
    1314import org.openstreetmap.josm.tools.CheckParameterUtil;
     
    291292        if (commands.isEmpty())
    292293            return;
    293         DataSet ds = OsmDataManager.getInstance().getEditDataSet();
    294         if (ds != null) {
    295             ds.beginUpdate();
    296         }
    297         try {
    298             for (int i = 1; i <= num; ++i) {
    299                 final Command c = commands.removeLast();
    300                 c.undoCommand();
    301                 redoCommands.addFirst(c);
    302                 fireEvent(new CommandUndoneEvent(this, c));
    303                 if (commands.isEmpty()) {
    304                     break;
     294        GuiHelper.runInEDTAndWait(new Runnable() {
     295            @Override
     296            public void run() {
     297                DataSet ds = OsmDataManager.getInstance().getEditDataSet();
     298                if (ds != null) {
     299                    ds.beginUpdate();
    305300                }
     301                try {
     302                    for (int i = 1; i <= num; ++i) {
     303                        final Command c = commands.removeLast();
     304                        c.undoCommand();
     305                        redoCommands.addFirst(c);
     306                        fireEvent(new CommandUndoneEvent(UndoRedoHandler.this, c));
     307                        if (commands.isEmpty()) {
     308                            break;
     309                        }
     310                    }
     311                } finally {
     312                    if (ds != null) {
     313                        ds.endUpdate();
     314                    }
     315                }
     316                fireCommandsChanged();
    306317            }
    307         } finally {
    308             if (ds != null) {
    309                 ds.endUpdate();
    310             }
    311         }
    312         fireCommandsChanged();
     318
     319        });
    313320    }
    314321
     
    324331     * @param num The number of commands to redo
    325332     */
    326     public void redo(int num) {
     333    public synchronized void redo(int num) {
    327334        if (redoCommands.isEmpty())
    328335            return;
     
    367374     * @since 12718
    368375     */
    369     public void clean(DataSet dataSet) {
     376    public synchronized void clean(DataSet dataSet) {
    370377        if (dataSet == null)
    371378            return;
Note: See TracChangeset for help on using the changeset viewer.