forked from: forked from: forked from: 動体検知 + 肌色認識
forked from forked from: forked from: 動体検知 + 肌色認識 (diff: 44)
練習中
ActionScript3 source code
/**
* Copyright tepe ( http://wonderfl.net/user/tepe )
* MIT License ( http://www.opensource.org/licenses/mit-license.php )
* Downloaded from: http://wonderfl.net/c/oKJx
*/
// forked from ikusu's forked from: forked from: 動体検知 + 肌色認識
package {
import flash.display.*;
import flash.events.Event;
import flash.geom.*;;
import flash.filters.*;
import flash.media.*;
[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 tmp:Bitmap;
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);
//addChild(tmp);
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();//今回の画像BMP
//前回との差分
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);
//tmp.bitmapData = now;
//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);
//1pixel画像
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;
}
}
}
//検出エリア描画
var color:uint = 0x00ff00;
s.graphics.lineStyle(0, color);
for (var i2:int = 0; i2 < length; i2++) {
var rectB:Rectangle = rects[i2];
s.graphics.drawRect(rectB.x, rectB.y, rectB.width, rectB.height);
}
}
}
}