@@ -18,6 +18,7 @@ import {
1818 registry ,
1919 utils ,
2020 WorkspaceSvg ,
21+ ShortcutRegistry ,
2122} from 'blockly' ;
2223import * as Constants from '../constants' ;
2324import { Direction , getXYFromDirection } from '../drag_direction' ;
@@ -36,6 +37,11 @@ const UNCONSTRAINED_MOVE_DISTANCE = 20;
3637 */
3738const CONSTRAINED_ADDITIONAL_PADDING = 70 ;
3839
40+ /**
41+ * Identifier for a keyboard shortcut that commits the in-progress move.
42+ */
43+ const COMMIT_MOVE_SHORTCUT = 'commitMove' ;
44+
3945/**
4046 * Low-level code for moving blocks with keyboard shortcuts.
4147 */
@@ -140,6 +146,47 @@ export class Mover {
140146 // (otherwise dragging will break).
141147 getFocusManager ( ) . focusNode ( block ) ;
142148 block . getFocusableElement ( ) . addEventListener ( 'blur' , blurListener ) ;
149+
150+ // Register a keyboard shortcut under the key combos of all existing
151+ // keyboard shortcuts that commits the move before allowing the real
152+ // shortcut to proceed. This avoids all kinds of fun brokenness when
153+ // deleting/copying/otherwise acting on a block in move mode.
154+ const shortcutKeys = Object . values ( ShortcutRegistry . registry . getRegistry ( ) )
155+ . flatMap ( ( shortcut ) => shortcut . keyCodes )
156+ . filter ( ( keyCode ) => {
157+ return (
158+ keyCode &&
159+ ! [
160+ utils . KeyCodes . RIGHT ,
161+ utils . KeyCodes . LEFT ,
162+ utils . KeyCodes . UP ,
163+ utils . KeyCodes . DOWN ,
164+ utils . KeyCodes . ENTER ,
165+ ] . includes (
166+ typeof keyCode === 'number'
167+ ? keyCode
168+ : parseInt ( `${ keyCode . split ( '+' ) . pop ( ) } ` ) ,
169+ )
170+ ) ;
171+ } )
172+ // Convince TS there aren't undefined values.
173+ . filter ( ( keyCode ) : keyCode is string | number => ! ! keyCode ) ;
174+
175+ const commitMoveShortcut = {
176+ name : COMMIT_MOVE_SHORTCUT ,
177+ preconditionFn : ( workspace : WorkspaceSvg ) => {
178+ return ! ! this . moves . get ( workspace ) ;
179+ } ,
180+ callback : ( workspace : WorkspaceSvg ) => {
181+ this . finishMove ( workspace ) ;
182+ return false ;
183+ } ,
184+ keyCodes : shortcutKeys ,
185+ allowCollision : true ,
186+ } ;
187+
188+ ShortcutRegistry . registry . register ( commitMoveShortcut ) ;
189+
143190 return true ;
144191 }
145192
@@ -152,6 +199,8 @@ export class Mover {
152199 * @returns True iff move successfully finished.
153200 */
154201 finishMove ( workspace : WorkspaceSvg ) {
202+ ShortcutRegistry . registry . unregister ( COMMIT_MOVE_SHORTCUT ) ;
203+
155204 clearMoveHints ( workspace ) ;
156205
157206 const info = this . moves . get ( workspace ) ;
0 commit comments