Sign in to follow this  
Followers 0
Alexxander

Camera motion detection

9 posts in this topic

#1 ·  Posted (edited)

hi all

i want to make a camera motion detection system and know the place of the motion.

i'm thinking of making a script that take a picture from the usb camera every 1 second then detect if their is changes in the picture

my  idea is to make it take a picture in second 1 and store that pic in a temp folder 

in second 2 it takes another pic and save it 

then it detect the visual pixel changes between the 2 images . if their is difference then their is a motion in the environment

image.jpg

image.jpg

 

my question is how can i do the image dividing and how to compare the visual Columns ?

is my idea good or their is a better methods to do this ?

any help/ideas is much appreciated 

Edited by Alexxander

Share this post


Link to post
Share on other sites



#2 ·  Posted (edited)

There have been a few discussed on the forum, none very good or reliable.

I'd say out loud that AutoIt is not the language to develop such an application.

But, of course, best of luck.

EDIT:

For example a cloud moves, the sun casts a new shadow, the lighting changes in any way, a bug crawls past etcetera.

EDIT2:

I believe OpenCV is what you could use.

EDIT3:

>Link to some AutoIt code using OpenCV

Edited by JohnOne
1 person likes this

AutoIt Absolute Beginners    Require a serial    Pause Script    Video Tutorials by Morthawt   ipify 

Monkey's are, like, natures humans.

Share this post


Link to post
Share on other sites

#3 ·  Posted (edited)

http://sourceforge.net/projects/opencvlibrary/

not sure if anyone has tried to call those functions from AutoIT

this is not fast enough

'?do=embed' frameborder='0' data-embedContent>>

and maybe search the form for bitblt or GDI

BTW: more, less light will give every second a different bitmap due to light effects

Edited by junkew

Share this post


Link to post
Share on other sites

If you want to do this in pure autoit my recommendation is to get the pixel data for each image and then split the data into arrays, comparing each element.

This would return a % of the image that had changed.

Then you would simply need to only save the file if more n% has changed. 

Share this post


Link to post
Share on other sites

You could go even further to compensate for lighting changes by comparing the percentage of change between each hexidecimal value of each pixel, and then averaging the total difference(this way if the light increases/decreases by a small amount, the returned % will be the amount of change that occured in the lighting, where-as the original situation I presented would return the percentage of the whole image that changed as a result of the lighting effect)..

Share this post


Link to post
Share on other sites

I reckon large video images would have quite a lot of pixels, and would take quite some time, to collect the data.

$Timer = TimerInit()
For $y = 0 To @DesktopHeight
    For $x = 0 To @DesktopWidth
        PixelGetColor($x, $y)
    Next
Next
MsgBox(0,0,Round(TimerDiff($Timer),2))

While being just as unreliable on a video stream as the faster PixelChecksum.

$Timer = TimerInit()
PixelChecksum(0, 0, @DesktopWidth, @DesktopHeight)
MsgBox(0, 0, Round(TimerDiff($Timer), 2))
Exit

However here is an example using PixelChecksum.

Move mouse over button, (cursor is not detected).

#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <File.au3>
#include <Array.au3>

$hGUI = GUICreate("", 100, 100, 200, 200)
$hButton = GUICtrlCreateButton("x", 0, 0, 100, 100)

GUISetState()

$winpos = WinGetPos($hGUI)
Sleep(250)

$psum = PixelChecksum($winpos[0], $winpos[1], $winpos[0] + $winpos[2], $winpos[1] + $winpos[3])

Do
    _Detect()
Until GUIGetMsg() = $GUI_EVENT_CLOSE

Func _Detect()
    If PixelChecksum($winpos[0], $winpos[1], $winpos[0] + $winpos[2], $winpos[1] + $winpos[3]) <> $psum Then
        Exit MsgBox(0, 0, 'Change')
    EndIf
EndFunc   ;==>_Detect

AutoIt Absolute Beginners    Require a serial    Pause Script    Video Tutorials by Morthawt   ipify 

Monkey's are, like, natures humans.

Share this post


Link to post
Share on other sites

@JohnOne The idea was for a slightly improved accuracy by getting the actual percent of pixels changed. And getting pixels could be faster with gdi. (:

Share this post


Link to post
Share on other sites

#9 ·  Posted (edited)

Here's a function I wrote to compare two colors in hexadecimal format. 

 

To make use of this make an array/string of all the pixels in each image. You can pass values of any length to the _colorcompare() function, so it's possible to pass all the pixels for both images to the function as a string, or you can process it in chunks of 6/12/24 or however you want to do it, though the less times you call the function, the faster the end result will be.

ConsoleWrite(_colorcompare('ffffff', 'eeeeee')&@CRLF)

func _colorcompare($color1, $color2)
    Local $difference
$color1 = StringSplit($color1, "")
$color2 = StringSplit($color2, "")
$difference = 0
for $i=1 to $color1[0]
if $color1[$i] <> $color2[$i] Then
    $difference += Abs(_hextonum($color1[$i]) - _hextonum($color2[$i]))
EndIf
Next
$difference = (($difference/$color1[0])/15)*100
Return $difference
EndFunc
Edit: Fixed a bug in the percentage calculation, had two numbers backwards.

Seems decently fast Takes about 100ms on a 1000 pixel image (500x500)

Edited by nullschritt

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!


Register a new account

Sign in

Already have an account? Sign in here.


Sign In Now
Sign in to follow this  
Followers 0