From 17d38e19a16f030870c8cd58f5d1c93e22984b09 Mon Sep 17 00:00:00 2001 From: jmoenig Date: Thu, 21 Oct 2021 15:12:42 +0200 Subject: [PATCH] replaced BROADCAST block variants with SEND block variants --- HISTORY.md | 2 + src/blocks.js | 11 ++--- src/objects.js | 37 ++++++++-------- src/threads.js | 113 +++++++++++++------------------------------------ 4 files changed, 56 insertions(+), 107 deletions(-) diff --git a/HISTORY.md b/HISTORY.md index e2383582..7ec364a1 100755 --- a/HISTORY.md +++ b/HISTORY.md @@ -19,6 +19,7 @@ * libraries no longer rely on the JSF primitive, project may need to re-import their libraries to run without having to enable JS extensions * bulk hide/show arbitrary blocks in the palette via the palette's context menu (instead of the primitive blocks' context menus) * hidden blocks don't appear in search results / keyboard input options + * renamed BROADCAST to SEND and added a second input for message receivers, default is "all" * "when I receive 'any message'" hat scripts are threadsafe (uninterruptable by other messages) * retired Leap Motion library, took out Hummingbird library (get the current one from Birdbrain) * display blocks with their error messages for custom blocks, thanks, Michael! @@ -47,6 +48,7 @@ * threads: enabled sending atomic lists to other scenes * threads: took out broadcasting a 2-item list to mean a message directed to a particular sprite * blocks, objects, threads: added "all" option to the receiver-dropdown of the SEND block +* objects, blocks, threads: replaced BROADCAST block variants with SEND block variants ### 2021-10-20 * blocks: enable sending green-flag events when switching scenes diff --git a/src/blocks.js b/src/blocks.js index ff7f48a6..4b855294 100644 --- a/src/blocks.js +++ b/src/blocks.js @@ -3133,7 +3133,7 @@ BlockMorph.prototype.userMenu = function () { return menu; } if (contains( - ['doBroadcast', 'doSend', 'doBroadcastAndWait', 'receiveMessage', + ['doSend', 'doSendAndWait', 'receiveMessage', 'receiveOnClone', 'receiveGo'], this.selector )) { @@ -3228,15 +3228,12 @@ BlockMorph.prototype.isSending = function (message, receiverName, known = []) { } if ((morph.selector) && contains( - ['doBroadcast', 'doBroadcastAndWait', 'doSend'], + ['doSend', 'doSendAndWait'], morph.selector) ) { event = morph.inputs()[0].evaluate(); - if (morph.selector === 'doSend') { - eventReceiver = morph.inputs()[1].evaluate(); - } - return ((morph.selector !== 'doSend') || - (receiverName === eventReceiver)) && + eventReceiver = morph.inputs()[1].evaluate(); + return receiverName === eventReceiver && ((event === message) || (message instanceof Array && message[0] === 'any message')); diff --git a/src/objects.js b/src/objects.js index c04d3f37..ea40fad1 100644 --- a/src/objects.js +++ b/src/objects.js @@ -751,16 +751,6 @@ SpriteMorph.prototype.initBlocks = function () { category: 'control', spec: 'when %b' }, - doBroadcast: { - type: 'command', - category: 'control', - spec: 'broadcast %msg' - }, - doBroadcastAndWait: { - type: 'command', - category: 'control', - spec: 'broadcast %msg and wait' - }, getLastMessage: { // retained for legacy compatibility dev: true, type: 'reporter', @@ -773,6 +763,12 @@ SpriteMorph.prototype.initBlocks = function () { spec: 'send %msg to %rcv', defaults: [null, ['all']] }, + doSendAndWait: { + type: 'command', + category: 'control', + spec: 'send %msg to %rcv and wait', + defaults: [null, ['all']] + }, doWait: { type: 'command', category: 'control', @@ -1655,6 +1651,16 @@ SpriteMorph.prototype.initBlockMigrations = function () { selector: 'reportListAttribute', inputs: [['length']], offset: 1 + }, + doBroadcast: { + selector: 'doSend', + inputs: [null, ['all']], + offset: 0 + }, + doBroadcastAndWait: { + selector: 'doSendAndWait', + inputs: [null, ['all']], + offset: 0 } }; }; @@ -1726,9 +1732,8 @@ SpriteMorph.prototype.blockAlternatives = { setSize: ['changeSize'], // control: - doBroadcast: ['doBroadcastAndWait', 'doSend'], - doBroadcastAndWait: ['doBroadcast', 'doSend'], - doSend: ['doBroadcast', 'doBroadcastAndWait'], + doSend: ['doSendAndWait'], + doSendAndWait: ['doSend'], doIf: ['doIfElse', 'doUntil'], doIfElse: ['doIf', 'doUntil'], doRepeat: ['doUntil', ['doForever', -1], ['doFor', 2], ['doForEach', 1]], @@ -2517,9 +2522,8 @@ SpriteMorph.prototype.blockTemplates = function ( blocks.push(block('receiveCondition')); blocks.push('-'); blocks.push(block('receiveMessage')); - blocks.push(block('doBroadcast')); - blocks.push(block('doBroadcastAndWait')); blocks.push(block('doSend')); + blocks.push(block('doSendAndWait')); blocks.push('-'); blocks.push(block('doWarp')); blocks.push('-'); @@ -8764,9 +8768,8 @@ StageMorph.prototype.blockTemplates = function ( blocks.push(block('receiveCondition')); blocks.push('-'); blocks.push(block('receiveMessage')); - blocks.push(block('doBroadcast')); - blocks.push(block('doBroadcastAndWait')); blocks.push(block('doSend')); + blocks.push(block('doSendAndWait')); blocks.push('-'); blocks.push(block('doWarp')); blocks.push('-'); diff --git a/src/threads.js b/src/threads.js index 4ba1e113..e93db002 100644 --- a/src/threads.js +++ b/src/threads.js @@ -3657,89 +3657,6 @@ Process.prototype.checkURLAllowed = function (url) { // Process event messages primitives -Process.prototype.doBroadcast = function (message) { - var stage = this.homeContext.receiver.parentThatIsA(StageMorph), - rcvrs = stage.children.concat(stage), - msg = this.inputOption(message), - procs = []; - - if (!this.canBroadcast) { - return []; - } - if (msg !== '') { - stage.lastMessage = message; // the actual data structure - rcvrs.forEach(morph => { - if (isSnapObject(morph)) { - morph.allHatBlocksFor(msg).forEach(block => { - var varName, varFrame; - if (block.selector === 'receiveMessage') { - varName = block.inputs()[1].evaluate()[0]; - if (varName) { - varFrame = new VariableFrame(); - varFrame.addVar(varName, message); - } - procs.push(stage.threads.startProcess( - block, - morph, - stage.isThreadSafe || // make "any msg" threadsafe - block.inputs()[0].evaluate() instanceof Array, - null, // exportResult (bool) - null, // callback - null, // isClicked - null, // rightAway - null, // atomic - varFrame - )); - } else { - procs.push(stage.threads.startProcess( - block, - morph, - stage.isThreadSafe - )); - } - }); - } - }); - (stage.messageCallbacks[''] || []).forEach(callback => - callback(msg) // for "any" message, pass it along as argument - ); - (stage.messageCallbacks[msg] || []).forEach(callback => - callback() // for a particular message - ); - } - return procs; -}; - -Process.prototype.doBroadcastAndWait = function (message) { - if (!this.context.activeSends) { - this.context.activeSends = this.doBroadcast(message); - if (this.isRunning()) { - this.context.activeSends.forEach(proc => - proc.runStep() - ); - } - } - this.context.activeSends = this.context.activeSends.filter(proc => - proc.isRunning() - ); - if (this.context.activeSends.length === 0) { - return null; - } - this.pushContext('doYield'); - this.pushContext(); -}; - -Process.prototype.getLastMessage = function () { - var stage; - if (this.homeContext.receiver) { - stage = this.homeContext.receiver.parentThatIsA(StageMorph); - if (stage) { - return stage.getLastMessage(); - } - } - return ''; -}; - Process.prototype.doSend = function (message, target) { var stage = this.homeContext.receiver.parentThatIsA(StageMorph), thisObj, @@ -3818,6 +3735,36 @@ Process.prototype.doSend = function (message, target) { return procs; }; +Process.prototype.doSendAndWait = function (message, target) { + if (!this.context.activeSends) { + this.context.activeSends = this.doSend(message, target); + if (this.isRunning()) { + this.context.activeSends.forEach(proc => + proc.runStep() + ); + } + } + this.context.activeSends = this.context.activeSends.filter(proc => + proc.isRunning() + ); + if (this.context.activeSends.length === 0) { + return null; + } + this.pushContext('doYield'); + this.pushContext(); +}; + +Process.prototype.getLastMessage = function () { + var stage; + if (this.homeContext.receiver) { + stage = this.homeContext.receiver.parentThatIsA(StageMorph); + if (stage) { + return stage.getLastMessage(); + } + } + return ''; +}; + // Process type inference Process.prototype.reportIsA = function (thing, typeString) {