diff --git a/core/contextmenu_items.ts b/core/contextmenu_items.ts index 8e42284dd2a..ef29a1920e1 100644 --- a/core/contextmenu_items.ts +++ b/core/contextmenu_items.ts @@ -47,7 +47,7 @@ export function registerUndo() { return 'disabled'; }, callback(scope: Scope) { - scope.workspace!.undo(false); + scope.workspace!.undo(); }, scopeType: ContextMenuRegistry.ScopeType.WORKSPACE, id: 'undoWorkspace', @@ -71,7 +71,7 @@ export function registerRedo() { return 'disabled'; }, callback(scope: Scope) { - scope.workspace!.undo(true); + scope.workspace!.redo(); }, scopeType: ContextMenuRegistry.ScopeType.WORKSPACE, id: 'redoWorkspace', diff --git a/core/shortcut_items.ts b/core/shortcut_items.ts index f8c95500770..077409f859c 100644 --- a/core/shortcut_items.ts +++ b/core/shortcut_items.ts @@ -338,7 +338,7 @@ export function registerUndo() { callback(workspace, e) { // 'z' for undo 'Z' is for redo. (workspace as WorkspaceSvg).hideChaff(); - workspace.undo(false); + workspace.undo(); e.preventDefault(); return true; }, @@ -377,7 +377,7 @@ export function registerRedo() { callback(workspace, e) { // 'z' for undo 'Z' is for redo. (workspace as WorkspaceSvg).hideChaff(); - workspace.undo(true); + workspace.redo(); e.preventDefault(); return true; }, diff --git a/core/workspace.ts b/core/workspace.ts index 88745f4205c..48a05fc37a4 100644 --- a/core/workspace.ts +++ b/core/workspace.ts @@ -728,7 +728,7 @@ export class Workspace { * * @param redo False if undo, true if redo. */ - undo(redo: boolean) { + undo(redo = false) { const inputStack = redo ? this.redoStack_ : this.undoStack_; const outputStack = redo ? this.undoStack_ : this.redoStack_; const inputEvent = inputStack.pop(); @@ -762,6 +762,13 @@ export class Workspace { } } + /** + * Redoes the previous action. + */ + redo() { + this.undo(true); + } + /** Clear the undo/redo stacks. */ clearUndo() { this.undoStack_.length = 0; diff --git a/tests/mocha/comment_deserialization_test.js b/tests/mocha/comment_deserialization_test.js index f834eb0f301..8299b8215d2 100644 --- a/tests/mocha/comment_deserialization_test.js +++ b/tests/mocha/comment_deserialization_test.js @@ -88,7 +88,7 @@ suite('Comment Deserialization', function () { this.block.checkAndDelete(); assert.equal(this.workspace.getAllBlocks().length, 0); // Undo. - this.workspace.undo(false); + this.workspace.undo(); assert.equal(this.workspace.getAllBlocks().length, 1); // Check comment. assertComment(this.workspace, 'test text'); @@ -97,12 +97,12 @@ suite('Comment Deserialization', function () { // Create block. this.block = createBlock(this.workspace); // Undo & undo. - this.workspace.undo(false); - this.workspace.undo(false); + this.workspace.undo(); + this.workspace.undo(); assert.equal(this.workspace.getAllBlocks().length, 0); // Redo & redo. - this.workspace.undo(true); - this.workspace.undo(true); + this.workspace.redo(); + this.workspace.redo(); assert.equal(this.workspace.getAllBlocks().length, 1); // Check comment. assertComment(this.workspace, 'test text'); diff --git a/tests/mocha/comment_test.js b/tests/mocha/comment_test.js index a7b2635b99f..f0c876bd25a 100644 --- a/tests/mocha/comment_test.js +++ b/tests/mocha/comment_test.js @@ -174,7 +174,7 @@ suite('Comments', function () { assert.isNotNull(block.getIcon(Blockly.icons.IconType.COMMENT)); assert.equal(block.getCommentText(), ''); - this.workspace.undo(false); + this.workspace.undo(); assert.isUndefined(block.getIcon(Blockly.icons.IconType.COMMENT)); assert.isNull(block.getCommentText()); @@ -183,8 +183,8 @@ suite('Comments', function () { test('Adding an empty comment can be redone', function () { const block = this.workspace.newBlock('empty_block'); block.setCommentText(''); - this.workspace.undo(false); - this.workspace.undo(true); + this.workspace.undo(); + this.workspace.redo(); assert.isNotNull(block.getIcon(Blockly.icons.IconType.COMMENT)); assert.equal(block.getCommentText(), ''); @@ -196,7 +196,7 @@ suite('Comments', function () { assert.isNotNull(block.getIcon(Blockly.icons.IconType.COMMENT)); assert.equal(block.getCommentText(), 'hey there'); - this.workspace.undo(false); + this.workspace.undo(); assert.isUndefined(block.getIcon(Blockly.icons.IconType.COMMENT)); assert.isNull(block.getCommentText()); @@ -205,8 +205,8 @@ suite('Comments', function () { test('Adding a non-empty comment can be redone', function () { const block = this.workspace.newBlock('empty_block'); block.setCommentText('hey there'); - this.workspace.undo(false); - this.workspace.undo(true); + this.workspace.undo(); + this.workspace.redo(); assert.isNotNull(block.getIcon(Blockly.icons.IconType.COMMENT)); assert.equal(block.getCommentText(), 'hey there'); diff --git a/tests/mocha/contextmenu_items_test.js b/tests/mocha/contextmenu_items_test.js index 52f4428ba7d..b7b8dc5afc2 100644 --- a/tests/mocha/contextmenu_items_test.js +++ b/tests/mocha/contextmenu_items_test.js @@ -93,7 +93,7 @@ suite('Context Menu Items', function () { test('Enabled when something to redo', function () { // Create a new block, then undo it, which means there is something to redo. this.workspace.newBlock('text'); - this.workspace.undo(false); + this.workspace.undo(); const precondition = this.redoOption.preconditionFn(this.scope); assert.equal( precondition, @@ -105,7 +105,7 @@ suite('Context Menu Items', function () { test('Redoes adding new block', function () { // Add a new block, then undo it, then redo it. this.workspace.newBlock('text'); - this.workspace.undo(false); + this.workspace.undo(); assert.equal(this.workspace.getTopBlocks(false).length, 0); this.redoOption.callback(this.scope); assert.equal( diff --git a/tests/mocha/shortcut_items_test.js b/tests/mocha/shortcut_items_test.js index dfbae3f0901..c501803d196 100644 --- a/tests/mocha/shortcut_items_test.js +++ b/tests/mocha/shortcut_items_test.js @@ -443,7 +443,6 @@ suite('Keyboard Shortcut Items', function () { test(testCaseName, function () { this.injectionDiv.dispatchEvent(keyEvent); sinon.assert.calledOnce(this.undoSpy); - sinon.assert.calledWith(this.undoSpy, false); sinon.assert.calledOnce(this.hideChaffSpy); }); }); @@ -473,7 +472,7 @@ suite('Keyboard Shortcut Items', function () { suite('Redo', function () { setup(function () { - this.redoSpy = sinon.spy(this.workspace, 'undo'); + this.redoSpy = sinon.spy(this.workspace, 'redo'); this.hideChaffSpy = sinon.spy( Blockly.WorkspaceSvg.prototype, 'hideChaff', @@ -503,7 +502,6 @@ suite('Keyboard Shortcut Items', function () { test(testCaseName, function () { this.injectionDiv.dispatchEvent(keyEvent); sinon.assert.calledOnce(this.redoSpy); - sinon.assert.calledWith(this.redoSpy, true); sinon.assert.calledOnce(this.hideChaffSpy); }); }); diff --git a/tests/mocha/test_helpers/workspace.js b/tests/mocha/test_helpers/workspace.js index 452933c081a..221d54b47f7 100644 --- a/tests/mocha/test_helpers/workspace.js +++ b/tests/mocha/test_helpers/workspace.js @@ -1278,7 +1278,7 @@ export function testAWorkspace() { assertVariableValues(this.workspace, 'name1', 'type1', 'id1'); assert.isNull(this.workspace.getVariableById('id2')); - this.workspace.undo(true); + this.workspace.redo(); // Expect that variable 'id2' is recreated assertVariableValues(this.workspace, 'name1', 'type1', 'id1'); @@ -1288,7 +1288,7 @@ export function testAWorkspace() { this.workspace.undo(); assert.isNull(this.workspace.getVariableById('id1')); assert.isNull(this.workspace.getVariableById('id2')); - this.workspace.undo(true); + this.workspace.redo(); // Expect that variable 'id1' is recreated assertVariableValues(this.workspace, 'name1', 'type1', 'id1'); @@ -1350,7 +1350,7 @@ export function testAWorkspace() { assert.isNull(this.workspace.getVariableById('id1')); assertVariableValues(this.workspace, 'name2', 'type2', 'id2'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); // Expect that both variables are deleted assert.isNull(this.workspace.getVariableById('id1')); @@ -1363,7 +1363,7 @@ export function testAWorkspace() { assertVariableValues(this.workspace, 'name1', 'type1', 'id1'); assertVariableValues(this.workspace, 'name2', 'type2', 'id2'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); // Expect that variable 'id2' is recreated assert.isNull(this.workspace.getVariableById('id1')); @@ -1385,7 +1385,7 @@ export function testAWorkspace() { assert.isNull(this.workspace.getVariableById('id1')); assertVariableValues(this.workspace, 'name2', 'type2', 'id2'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); // Expect that both variables are deleted assert.equal(this.workspace.getTopBlocks(false).length, 0); @@ -1401,7 +1401,7 @@ export function testAWorkspace() { assertVariableValues(this.workspace, 'name1', 'type1', 'id1'); assertVariableValues(this.workspace, 'name2', 'type2', 'id2'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); // Expect that variable 'id2' is recreated assertBlockVarModelName(this.workspace, 0, 'name2'); @@ -1429,12 +1429,12 @@ export function testAWorkspace() { assertVariableValues(this.workspace, 'name1', 'type1', 'id1'); // Redo delete - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assert.isNull(this.workspace.getVariableById('id1')); // Redo delete, nothing should happen - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assert.isNull(this.workspace.getVariableById('id1')); }); @@ -1463,13 +1463,13 @@ export function testAWorkspace() { assertVariableValues(this.workspace, 'name1', 'type1', 'id1'); // Redo delete - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assert.equal(this.workspace.getTopBlocks(false).length, 0); assert.isNull(this.workspace.getVariableById('id1')); // Redo delete, nothing should happen - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assert.equal(this.workspace.getTopBlocks(false).length, 0); assert.isNull(this.workspace.getVariableById('id1')); @@ -1489,7 +1489,7 @@ export function testAWorkspace() { this.clock.runAll(); assertVariableValues(this.variableMap, 'name1', 'type1', 'id1'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assertVariableValues(this.variableMap, 'name2', 'type1', 'id1'); }); @@ -1504,7 +1504,7 @@ export function testAWorkspace() { assertBlockVarModelName(this.workspace, 0, 'name1'); assertVariableValues(this.variableMap, 'name1', 'type1', 'id1'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assertBlockVarModelName(this.workspace, 0, 'name2'); assertVariableValues(this.variableMap, 'name2', 'type1', 'id1'); @@ -1518,7 +1518,7 @@ export function testAWorkspace() { this.clock.runAll(); assertVariableValues(this.variableMap, 'name1', 'type1', 'id1'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assertVariableValues(this.variableMap, 'Name1', 'type1', 'id1'); }); @@ -1533,7 +1533,7 @@ export function testAWorkspace() { assertBlockVarModelName(this.workspace, 0, 'name1'); assertVariableValues(this.variableMap, 'name1', 'type1', 'id1'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assertBlockVarModelName(this.workspace, 0, 'Name1'); assertVariableValues(this.variableMap, 'Name1', 'type1', 'id1'); @@ -1550,7 +1550,7 @@ export function testAWorkspace() { assertVariableValues(this.variableMap, 'name1', 'type1', 'id1'); assertVariableValues(this.variableMap, 'name2', 'type1', 'id2'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assertVariableValues(this.variableMap, 'name2', 'type1', 'id2'); assert.isNull(this.variableMap.getVariableById('id1')); @@ -1573,7 +1573,7 @@ export function testAWorkspace() { assertVariableValues(this.variableMap, 'name1', 'type1', 'id1'); assertVariableValues(this.variableMap, 'name2', 'type1', 'id2'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assertVariableValues(this.variableMap, 'name2', 'type1', 'id2'); assert.isNull(this.variableMap.getVariableById('id1')); @@ -1589,7 +1589,7 @@ export function testAWorkspace() { assertVariableValues(this.variableMap, 'name1', 'type1', 'id1'); assertVariableValues(this.variableMap, 'name2', 'type1', 'id2'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assertVariableValues(this.variableMap, 'Name2', 'type1', 'id2'); assert.isNull(this.variableMap.getVariable('name1')); @@ -1608,7 +1608,7 @@ export function testAWorkspace() { assertVariableValues(this.variableMap, 'name1', 'type1', 'id1'); assertVariableValues(this.variableMap, 'name2', 'type1', 'id2'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assertVariableValues(this.variableMap, 'Name2', 'type1', 'id2'); assert.isNull(this.variableMap.getVariableById('id1')); @@ -1626,7 +1626,7 @@ export function testAWorkspace() { assertVariableValues(this.variableMap, 'name1', 'type1', 'id1'); assertVariableValues(this.variableMap, 'name2', 'type2', 'id2'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assertVariableValues(this.variableMap, 'name2', 'type1', 'id1'); assertVariableValues(this.variableMap, 'name2', 'type2', 'id2'); @@ -1645,7 +1645,7 @@ export function testAWorkspace() { assertBlockVarModelName(this.workspace, 0, 'name1'); assertBlockVarModelName(this.workspace, 1, 'name2'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assertVariableValues(this.variableMap, 'name2', 'type1', 'id1'); assertVariableValues(this.variableMap, 'name2', 'type2', 'id2'); @@ -1663,7 +1663,7 @@ export function testAWorkspace() { assertVariableValues(this.workspace, 'name1', 'type1', 'id1'); assertVariableValues(this.workspace, 'name2', 'type2', 'id2'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assertVariableValues(this.variableMap, 'Name2', 'type1', 'id1'); assertVariableValues(this.variableMap, 'name2', 'type2', 'id2'); @@ -1682,7 +1682,7 @@ export function testAWorkspace() { assertBlockVarModelName(this.workspace, 0, 'name1'); assertBlockVarModelName(this.workspace, 1, 'name2'); - this.workspace.undo(true); + this.workspace.redo(); this.clock.runAll(); assertVariableValues(this.variableMap, 'Name2', 'type1', 'id1'); assertVariableValues(this.variableMap, 'name2', 'type2', 'id2');