fix: use derived IDs for block comments #11
Merged
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
This PR fixes gonfunko/scratch-blocks#84 in conjunction with gonfunko/scratch-blocks#227. The old version of Blockly that Scratch was historically based on (de)serialized the IDs of block comments to/from XML, which were arbitrary UIDs. Newer Blockly does not assign IDs to block comments at all, treating the comment text as just a property of the parent block.
In scratch-blocks, we introduced a manually-managed ID for them, because the various comment events needed an ID, since the VM needs the events and IDs to maintain its own internal representation of the state of the workspace.
Unfortunately, since normal Blockly block comments don't save or load an ID when (de)serializing, the IDs from saved projects had no way to be propagated to the frontend, so while the VM kept track of comments associated with the saved IDs, scratch-blocks just assigned new random IDs to the comments. As a result, even though change/resize/create/move events were fired for the comments, the VM couldn't identify the appropriate bit of internal state to update due to the ID skew.
Since Scratch <-> Blockly interop is based on XML, which doesn't have the ability to e.g. swap out the serializer like one can with the newer JSON system, there needs to be a way to keep block comment IDs in sync between -vm and -blocks. As we can't transfer data to do this, the easiest option is to synthesize IDs on both ends based on a shared value both sides are aware of: the parent block's ID. Now, block comment IDs are simply their parent block's ID with a
_commentsuffix. The VM overwrites the saved-to-disk ID when deserializing comments with this synthesized value, and -blocks synthesizes the same value when constructing block comments, so the events emitted by those comments will have the same ID that the VM knows about, and thus allow the VM to correctly update its internal state in response to comment events.