In case Flash no longer exists; a copy of this site is included in the Flashpoint archive's "ultimate" collection.

Dead Code Preservation :: Archived AS3 works from wonderfl.net

動体検知 + 肌色認識

/**
 * Copyright alpicola ( http://wonderfl.net/user/alpicola )
 * MIT License ( http://www.opensource.org/licenses/mit-license.php )
 * Downloaded from: http://wonderfl.net/c/A37q
 */


package {
	import flash.display.BitmapData;
	import flash.display.Sprite;
	import flash.display.BlendMode;
	import flash.events.Event;
	import flash.geom.ColorTransform;
	import flash.geom.Matrix;
	import flash.geom.Point;
	import flash.geom.Rectangle;
	import flash.filters.ColorMatrixFilter;
	import flash.filters.ConvolutionFilter;
	import flash.media.Camera;
	import flash.media.Video;

	[SWF(width="465", height="465", backgroundColor="#ffffff", frameRate="15")] 
	
	public class MotionDetection extends Sprite {
		
		private var camera:Camera;
		private var video:Video;
		private var now:BitmapData;
		private var prev:BitmapData;
		private var rect:Rectangle;
		private var pt:Point;
		private var noiseReduction:ConvolutionFilter;
		private var grayScale:ColorMatrixFilter;
		private var skin:ColorMatrixFilter;
		private var s:Sprite;
		
		public function MotionDetection() {
			stage.align = "TL";
			stage.scaleMode = "noScale";

			camera = Camera.getCamera();
			if (camera == null) return;
			camera.setMode(465, 465, 15);
			video = new Video(camera.width, camera.height);
			video.attachCamera(camera);
			addChild(video);
			s = new Sprite();
			addChild(s);

			now = new BitmapData(camera.width, camera.height, false);
			prev = new BitmapData(camera.width, camera.height, false);
			rect = new Rectangle(0, 0, camera.width, camera.height);
			pt = new Point;
			
			noiseReduction = new ConvolutionFilter(3, 3);
			noiseReduction.bias = -(0x1000 + 0x100 * 6);
			noiseReduction.matrix = [
				1,  1, 1,
				1, 16, 1,
				1,  1, 1
			];
			grayScale = new ColorMatrixFilter([
				0.3, 0.59, 0.11, 0, 0,
				0.3, 0.59, 0.11, 0, 0,
				0.3, 0.59, 0.11, 0, 0,
				0, 0, 0, 1, 0
			]);
			skin = new ColorMatrixFilter([
				0, 0, 0, 0, 0,
				-0.43, -0.85, 1.28, 0, 198.4,
				1.28, -1.07, -0.21, 0, 108.8,
				0, 0, 0, 1, 0
			]);
			
			addEventListener(Event.ENTER_FRAME, update);
		}

		private function update(e:Event):void {
			s.graphics.clear();

			now.draw(video);
			var copy:BitmapData = now.clone();
			now.draw(prev, new Matrix(), new ColorTransform(), BlendMode.DIFFERENCE);
			prev = copy.clone();
			copy.applyFilter(now, rect, pt, skin);
			now.applyFilter(now, rect, pt, grayScale);
			now.threshold(now, rect, pt, ">", 0xff111111, 0xffffffff);
			//now.threshold(now, rect, pt, "!=", 0xffffffff, 0xff000000);
			now.threshold(copy, rect, pt, "!=", 0x008080, 0xff000000, 0x00c0c0);
			now.applyFilter(now, rect, pt, noiseReduction);

			var rects:Vector.<Rectangle> = new Vector.<Rectangle>();
			var bound:Rectangle = now.getColorBoundsRect(0xffffff, 0xffffff);
			var line:BitmapData = new BitmapData(rect.width, 1, false);
			var lineBound:Rectangle = new Rectangle(0, 0, rect.width, 1);
			while (!bound.isEmpty()) {
				lineBound.y = bound.y;
				line.copyPixels(now, lineBound, pt);
				bound = line.getColorBoundsRect(0xffffff, 0xffffff);
				now.floodFill(bound.x, lineBound.y, 0xff00ff);
				var rect:Rectangle = now.getColorBoundsRect(0xffffff, 0xff00ff);
				rect.inflate(4, 4);
				now.fillRect(rect, 0x0000ff);
				rects.push(rect);
				bound = now.getColorBoundsRect(0xffffff, 0xffffff);
			}

			var length:int = rects.length;
			for (var i:int = 0; i < length; i++) {
				var rect1:Rectangle = rects[i];
				for (var j:int = i + 1; j < length; j++) {
					var rect2:Rectangle = rects[j];
					if (rect1.intersects(rect2)) {
						rects.push(rect1.union(rect2));
						rects.splice(j, 1);
						rects.splice(i, 1);
						i--;
						length--;
						break;
					}
				}
			}
			
			s.graphics.lineStyle(0, 0x00c0c0);
			for (var i:int = 0; i < length; i++) {
				var rect:Rectangle = rects[i];
				s.graphics.drawRect(rect.x, rect.y, rect.width, rect.height);
			}
		}
	}
}