Home | Contact Us | FAQ | Search & Site Map | Link to Us
Sign In | Join | Other 45 Sites in Network
Home
Discussion GroupsGeneralPHPASPPerlColdFusionFlashHTML, CSS, ScriptsBrowsers

Webmaster Forum / Flash / General Flash Topics / July 2008



Tip: Looking for answers? Try searching our database.

Using BitMapData for Movement Detection

Thread view: 
Enable EMail Alerts  Start New Thread
Thread rating: 
schuel2 - 13 Jul 2008 03:23 GMT
I have been through the tutorial on Webcam Motion Detection: Using the
BitmapData API in Flash 8 at
http://www.adobe.com/devnet/flash/articles/webcam_motion.html and have been
watching the bitmap rendition of diferences in my live camera video image
produced by the webcam.swf example. Now I may have naively expected the
rendition to be almost completely black if my video image remains the same.
Instead I see a glimmering of green from bright areas surrounding the main
object in my camera's view. How come?

I would like ultimately to detect movement in a 'static' image to be a
potential alarm condition so I can start recording video from that point
onwards. Does anybody know of algorithms that can be used to signal that a
video image has changed significantly in a short space of time?
:frown;
Rothrock - 13 Jul 2008 17:50 GMT
There are two things that pop to my mind which could be causing this.
Fortunately one solution will probably help with either problem.

The first is that webcams likely use some kind of compressing on the image.
Something like jpeg or the equivalent for motion. This would produce little
artifacts around the edges of things and that would show up in the moving part
of the image when you try and do your detection. Your camera may have settings
to control the quality of the image? So that could help.

The other problem that I would guess is that there is often signal noise in a
web came. These are just small off colored pixels that appear randomly all over
the place. Generally they are fairly low. The hard solution for this would be
to buy a more expensive web cam, and use liquid nitrogen or something to cool
the sensor. :)

Okay so here is the easy solution to both of the above. Use the convolution
filter. It sort of averages out little squares of pixels. So  any small
fragments will fade out and any large features will remain. Use it on your
final difference image, not the source images.

But then I have to wonder why you even need the motion detection. Unless you
are then going to pass along the detected motion for further handling, you
probably don't need to go to the trouble.

The flash Camera class has an activity level method where you can tell the
camera to be inactive until the level reaches a certain point. You can then
start your camera recording.
schuel2 - 14 Jul 2008 14:04 GMT
:wink;
Thanks for your insightful comments. The pointer to the ability of the Camera
class to do motionLevel detection was an eyeopener, however being under the
wing of mProjector I am unable to extend my app into the realm of as3. I find a
way to play with the threshold setting to lower the noise level and thereafter
I created a simple check function to count green disturbances to my black
background. It seems to give me a way of triggering a motion detection event.
Now to work out how to record in a circular buffer and throw away the old stuff
but keep the video when a motion detection triggers. Never seem to get to the
end of the tunnel...
Rothrock - 14 Jul 2008 15:37 GMT
Who said anything about AS3? The AS2 camera class has a perfectly good
onActivity event handler.

And the convolution filter is available in AS2 as well. It really will help to
remove those artifacts. Here is my definition for the filter I used.

var rows:Number = 3;
var cols:Number = 3;
var matrixC:Array = [1, 1, 1, 1, 1, 1, 1, 1, 1];
var divisor:Number = 9*2;
var convolution:ConvolutionFilter = new ConvolutionFilter(rows, cols, matrixC,
divisor);

That was only defined once and then in the part of my code that looped was:

    oldData = newData.clone();
    newData.draw(myVideo,matrix);
    myBMP.draw(oldData);
    myBMP.draw(newData,new Matrix(),new ColorTransform(),"difference");
    myBMP.applyFilter(myBMP,new Rectangle(0, 0, 320, 240),new
Point(),convolution);
    myBMP.threshold(myBMP,new Rectangle(0, 0, 320, 240),new
Point(),">",0xff101010,0xff00FF00,0xffffffff,false);
    var myRect:Rectangle = myBMP.getColorBoundsRect(0x00ffffff, 0x0000ff00, true);

But again if you aren't planning on then taking and processing myRect further
(that is the rectangle that contains the different pixels) there really is no
point.
 
Sign In
Join
My Latest Posts
My Monitored Threads
My Blog
My Photo Gallery
My Profile
My Homepage

Start New Thread
Enable EMail Alerts
Rate this Thread



©2009 Advenet LLC   Privacy Policy - Terms of Use
This website includes both content owned or controlled by Advenet as well as content owned or controlled by third parties.