Motion Controlled Physics
Toying with an idea. Move around in front of your (required) webcam to control the purple ball...
/**
* Copyright devon_o ( http://wonderfl.net/user/devon_o )
* MIT License ( http://www.opensource.org/licenses/mit-license.php )
* Downloaded from: http://wonderfl.net/c/bcRe
*/
package {
import Box2D.Common.Math.b2Vec2;
import com.actionsnippet.qbox.QuickBox2D;
import com.actionsnippet.qbox.QuickObject;
import flash.display.MovieClip;
import flash.display.StageAlign;
import flash.display.StageScaleMode;
import flash.events.ActivityEvent;
import flash.events.Event;
import flash.events.StatusEvent;
import flash.media.Camera;
import flash.media.Video;
/**
* Just playing around with an idea...
* @author Devon O.
*/
[SWF(width='465', height='465', backgroundColor='#000000', frameRate='31')]
public class Main extends MovieClip {
public static const WORLD_RATIO:int = 30;
private var _sim:QuickBox2D;
private var _ball:QuickObject;
private var _cam:Camera;
private var _tracker:Tracker;
private var _xvel:Number = 0.0;
private var _yvel:Number = 0.0;
private var _px:Number = 0.0;
private var _py:Number = 0.0;
public function Main():void {
if (stage) init();
else addEventListener(Event.ADDED_TO_STAGE, init);
}
private function init(event:Event = null):void {
removeEventListener(Event.ADDED_TO_STAGE, init);
stage.scaleMode = StageScaleMode.NO_SCALE;
stage.align = StageAlign.TOP_LEFT;
initPhysics();
initObjects();
initVideo();
}
private function initVideo():void {
var v:Video = new Video();
var camIndex:int = 0;
for ( var i : int = 0 ; i < Camera.names.length ; i++ ) {
if ( Camera.names[ i ] == "USB Video Class Video" ) {
camIndex = i;
break;
}
}
_cam = Camera.getCamera(String(camIndex));
_cam.setMode(v.width, v.height, 25);
_cam.addEventListener(StatusEvent.STATUS, onCameraStatus);
v.attachCamera(_cam);
_tracker = new Tracker(v);
}
private function onCameraStatus(event:*):void {
if (!_cam.muted) {
addEventListener(Event.ENTER_FRAME, onFrame);
}
}
private function initPhysics():void {
_sim = new QuickBox2D(this);
_sim.createStageWalls();
_sim.start();
}
private function initObjects():void {
_ball = _sim.addCircle( { x:50 / WORLD_RATIO, y:200 / WORLD_RATIO, fillColor:0xFF00FF, restitution:.60 } );
var numBricks:int = 10;
for (var i:int = 0; i < numBricks; i++) {
_sim.addBox( { x:300 / WORLD_RATIO, y:(400 - (i * WORLD_RATIO)) / WORLD_RATIO } );
}
}
private function onFrame(event:Event):void {
_tracker.track();
_xvel = _tracker.x - _px;
_yvel = _tracker.y - _py;
if (!isNaN(_xvel) && !isNaN(_yvel))
_ball.body.ApplyImpulse(new b2Vec2(_xvel / WORLD_RATIO, _yvel / WORLD_RATIO), new b2Vec2());
_px = _tracker.x;
_py = _tracker.y;
}
}
}
import flash.display.BlendMode;
import flash.filters.BlurFilter;
import flash.display.BitmapData;
import flash.geom.Matrix;
import flash.geom.Point;
import flash.geom.Rectangle;
import flash.media.Video;
class Tracker {
public var _previous:BitmapData;
public var _current:BitmapData;
public var x:Number;
public var y:Number;
private var _blur:BlurFilter = new BlurFilter(32, 32);
private var _vid:Video;
private var _mirror:Matrix;
private var _point:Point = new Point();
private var _area:Rectangle;
private var _isMotion:Boolean = false;
public function Tracker(vid:Video) {
_vid = vid;
_mirror = new Matrix();
_mirror.scale( -1, 1);
_mirror.translate(_vid.width, 0);
_current = new BitmapData(_vid.width, _vid.height, false, 0x000000);
_previous = _current.clone();
}
public function track():void {
_current.draw(_vid, _mirror);
_current.draw(_previous, null, null, BlendMode.DIFFERENCE);
_current.applyFilter(_current, _current.rect, _point, _blur);
_current.threshold(_current, _current.rect, _point, ">", 0xFF333333, 0xFFFFFFFF);
_previous.draw(_vid, _mirror);
_area = _current.getColorBoundsRect(0xFFFFFFFF, 0xFFFFFFFF, true);
_isMotion = ( _area.width > ( _vid.width / 100) * 10 || _area.height > (_vid.height / 100) * 10 );
if ( _isMotion ) {
x = _area.x + (_area.width * .5);
y = _area.y + (_area.width * .5);
}
}
}