Merge pull request #1028 from mzgoddard/motion-detect-4

Motion detect 4
This commit is contained in:
Andrew Sliwinski 2018-04-13 08:16:34 -04:00 committed by GitHub
commit 3ac2922a07
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
4 changed files with 77 additions and 64 deletions

View file

@ -7,6 +7,32 @@ const Video = require('../../io/video');
const VideoMotion = require('./library'); const VideoMotion = require('./library');
/**
* Sensor attribute video sensor block should report.
* @readonly
* @enum {string}
*/
const SensingAttribute = {
/** The amount of motion. */
MOTION: 'motion',
/** The direction of the motion. */
DIRECTION: 'direction'
};
/**
* Subject video sensor block should report for.
* @readonly
* @enum {string}
*/
const SensingSubject = {
/** The sensor traits of the whole stage. */
STAGE: 'Stage',
/** The senosr traits of the area overlapped by this sprite. */
SPRITE: 'this sprite'
};
/** /**
* States the video sensing activity can be set to. * States the video sensing activity can be set to.
* @readonly * @readonly
@ -176,59 +202,54 @@ class Scratch3VideoSensingBlocks {
return motionState; return motionState;
} }
static get SensingAttribute () {
return SensingAttribute;
}
/** /**
* An array of choices of whether a reporter should return the frame's * An array of choices of whether a reporter should return the frame's
* motion amount or direction. * motion amount or direction.
* @type {object[]} an array of objects. * @type {object[]} an array of objects
* @param {string} name - the translatable name to display in the drums menu. * @param {string} name - the translatable name to display in sensor
* @param {string} fileName - the name of the audio file containing the drum sound. * attribute menu
* @param {string} value - the serializable value of the attribute
*/ */
get MOTION_DIRECTION_INFO () { get ATTRIBUTE_INFO () {
return [ return [
{ {
name: 'motion' name: 'motion',
value: SensingAttribute.MOTION
}, },
{ {
name: 'direction' name: 'direction',
value: SensingAttribute.DIRECTION
} }
]; ];
} }
static get MOTION () { static get SensingSubject () {
return 1; return SensingSubject;
}
static get DIRECTION () {
return 2;
} }
/** /**
* An array of info about each drum. * An array of info about the subject choices.
* @type {object[]} an array of objects. * @type {object[]} an array of objects
* @param {string} name - the translatable name to display in the drums * @param {string} name - the translatable name to display in the subject menu
* menu. * @param {string} value - the serializable value of the subject
* @param {string} fileName - the name of the audio file containing the
* drum sound.
*/ */
get STAGE_SPRITE_INFO () { get SUBJECT_INFO () {
return [ return [
{ {
name: 'stage' name: 'stage',
value: SensingSubject.STAGE
}, },
{ {
name: 'sprite' name: 'sprite',
value: SensingSubject.SPRITE
} }
]; ];
} }
static get STAGE () {
return 1;
}
static get SPRITE () {
return 2;
}
/** /**
* States the video sensing activity can be set to. * States the video sensing activity can be set to.
* @readonly * @readonly
@ -272,17 +293,17 @@ class Scratch3VideoSensingBlocks {
{ {
opcode: 'videoOn', opcode: 'videoOn',
blockType: BlockType.REPORTER, blockType: BlockType.REPORTER,
text: 'video [MOTION_DIRECTION] on [STAGE_SPRITE]', text: 'video [ATTRIBUTE] on [SUBJECT]',
arguments: { arguments: {
MOTION_DIRECTION: { ATTRIBUTE: {
type: ArgumentType.NUMBER, type: ArgumentType.NUMBER,
menu: 'MOTION_DIRECTION', menu: 'ATTRIBUTE',
defaultValue: Scratch3VideoSensingBlocks.MOTION defaultValue: SensingAttribute.MOTION
}, },
STAGE_SPRITE: { SUBJECT: {
type: ArgumentType.NUMBER, type: ArgumentType.NUMBER,
menu: 'STAGE_SPRITE', menu: 'SUBJECT',
defaultValue: Scratch3VideoSensingBlocks.STAGE defaultValue: SensingSubject.STAGE
} }
} }
}, },
@ -322,8 +343,8 @@ class Scratch3VideoSensingBlocks {
} }
], ],
menus: { menus: {
MOTION_DIRECTION: this._buildMenu(this.MOTION_DIRECTION_INFO), ATTRIBUTE: this._buildMenu(this.ATTRIBUTE_INFO),
STAGE_SPRITE: this._buildMenu(this.STAGE_SPRITE_INFO), SUBJECT: this._buildMenu(this.SUBJECT_INFO),
VIDEO_STATE: this._buildMenu(this.VIDEO_STATE_INFO) VIDEO_STATE: this._buildMenu(this.VIDEO_STATE_INFO)
} }
}; };
@ -353,11 +374,11 @@ class Scratch3VideoSensingBlocks {
this.detect.analyzeFrame(); this.detect.analyzeFrame();
let state = this.detect; let state = this.detect;
if (Number(args.STAGE_SPRITE) === Scratch3VideoSensingBlocks.SPRITE) { if (args.SUBJECT === SensingSubject.SPRITE) {
state = this._analyzeLocalMotion(util.target); state = this._analyzeLocalMotion(util.target);
} }
if (Number(args.MOTION_DIRECTION) === Scratch3VideoSensingBlocks.MOTION) { if (args.ATTRIBUTE === SensingAttribute.MOTION) {
return state.motionAmount; return state.motionAmount;
} }
return state.motionDirection; return state.motionDirection;

View file

@ -611,21 +611,13 @@ const parseBlock = function (sb2block, addBroadcastMsg, getVariableId, extension
if (shadowObscured) { if (shadowObscured) {
fieldValue = 1; fieldValue = 1;
} }
} else if (expectedArg.inputOp === 'videoSensing.menu.MOTION_DIRECTION') { } else if (expectedArg.inputOp === 'videoSensing.menu.ATTRIBUTE') {
if (shadowObscured) { if (shadowObscured) {
fieldValue = 1; fieldValue = 'motion';
} else if (fieldValue === 'motion') {
fieldValue = 1;
} else if (fieldValue === 'direction') {
fieldValue = 2;
} }
} else if (expectedArg.inputOp === 'videoSensing.menu.STAGE_SPRITE') { } else if (expectedArg.inputOp === 'videoSensing.menu.SUBJECT') {
if (shadowObscured) { if (shadowObscured) {
fieldValue = 2; fieldValue = 'this sprite';
} else if (fieldValue === 'Stage') {
fieldValue = 1;
} else if (fieldValue === 'this sprite') {
fieldValue = 2;
} }
} else if (expectedArg.inputOp === 'videoSensing.menu.VIDEO_STATE') { } else if (expectedArg.inputOp === 'videoSensing.menu.VIDEO_STATE') {
if (shadowObscured) { if (shadowObscured) {

View file

@ -614,13 +614,13 @@ const specMap = {
argMap: [ argMap: [
{ {
type: 'input', type: 'input',
inputOp: 'videoSensing.menu.MOTION_DIRECTION', inputOp: 'videoSensing.menu.ATTRIBUTE',
inputName: 'MOTION_DIRECTION' inputName: 'ATTRIBUTE'
}, },
{ {
type: 'input', type: 'input',
inputOp: 'videoSensing.menu.STAGE_SPRITE', inputOp: 'videoSensing.menu.SUBJECT',
inputName: 'STAGE_SPRITE' inputName: 'SUBJECT'
} }
] ]
}, },

View file

@ -337,8 +337,8 @@ test('videoOn returns value dependent on arguments', t => {
sensing.detect.addFrame(frames.left); sensing.detect.addFrame(frames.left);
const motionAmount = sensing.videoOn({ const motionAmount = sensing.videoOn({
MOTION_DIRECTION: VideoSensing.MOTION, ATTRIBUTE: VideoSensing.SensingAttribute.MOTION,
STAGE_SPRITE: VideoSensing.STAGE SUBJECT: VideoSensing.SensingSubject.STAGE
}, fakeBlockUtility); }, fakeBlockUtility);
t.ok( t.ok(
motionAmount > 10, motionAmount > 10,
@ -346,8 +346,8 @@ test('videoOn returns value dependent on arguments', t => {
); );
const localMotionAmount = sensing.videoOn({ const localMotionAmount = sensing.videoOn({
MOTION_DIRECTION: VideoSensing.MOTION, ATTRIBUTE: VideoSensing.SensingAttribute.MOTION,
STAGE_SPRITE: VideoSensing.SPRITE SUBJECT: VideoSensing.SensingSubject.SPRITE
}, fakeBlockUtility); }, fakeBlockUtility);
t.ok( t.ok(
localMotionAmount > 10, localMotionAmount > 10,
@ -355,8 +355,8 @@ test('videoOn returns value dependent on arguments', t => {
); );
const motionDirection = sensing.videoOn({ const motionDirection = sensing.videoOn({
MOTION_DIRECTION: VideoSensing.DIRECTION, ATTRIBUTE: VideoSensing.SensingAttribute.DIRECTION,
STAGE_SPRITE: VideoSensing.STAGE SUBJECT: VideoSensing.SensingSubject.STAGE
}, fakeBlockUtility); }, fakeBlockUtility);
t.ok( t.ok(
isNearAngle(motionDirection, -90), isNearAngle(motionDirection, -90),
@ -364,8 +364,8 @@ test('videoOn returns value dependent on arguments', t => {
); );
const localMotionDirection = sensing.videoOn({ const localMotionDirection = sensing.videoOn({
MOTION_DIRECTION: VideoSensing.DIRECTION, ATTRIBUTE: VideoSensing.SensingAttribute.DIRECTION,
STAGE_SPRITE: VideoSensing.SPRITE SUBJECT: VideoSensing.SensingSubject.SPRITE
}, fakeBlockUtility); }, fakeBlockUtility);
t.ok( t.ok(
isNearAngle(localMotionDirection, -90), isNearAngle(localMotionDirection, -90),