Android Question move camera position x y change

scsjc

Well-Known Member
Licensed User
Longtime User
It is possible to detect if the camera moves up, down, or left, right when it is taking the picture.

that is to say, set an initial position and what moves indicates position variables x and y

thanks
 

DonManfred

Expert
Licensed User
Longtime User
I guess only by capturing and analizing the sensor-data.
 
Upvote 0

scsjc

Well-Known Member
Licensed User
Longtime User
I guess only by capturing and analizing the sensor-data.
thanks for you fast reply.
my idea is send a laser point and analizing the picture to get the position.

can you tell me any idea about code to start investigate that

thanks
 
Upvote 0

josejad

Expert
Licensed User
Longtime User
Check the Color Blob detection sample... it could be a starting point.
If you donate, Jordi provides more advanced samples as I can see
 
Upvote 0

William Lancee

Well-Known Member
Licensed User
Longtime User
what moves indicates position variables x and y
It is easy to detect the location of a bright spot in a image using BitmapCreator.
By comparing two images, you can know if the camera (or target) moved up/down/left/right

However, how much it moved (accurately) is complicated and dependent on distance from target, zoom level, focal length, initial position red point, and distance along the sweeping arc. Although if most of these are constant, and you do some experimentation with the dot and camera, it will be possible.

So it depends on your context.

@JordiCP 's system is masterful and much more general.
 
Upvote 0

William Lancee

Well-Known Member
Licensed User
Longtime User
To detect a red dot...

Center is at 300 300
Dot is at 413 150

redDot.jpg

B4X:
Sub Class_Globals
    Private Root As B4XView
    Private xui As XUI
  
    Private cv As B4XCanvas
    Private bc As BitmapCreator
End Sub

Public Sub Initialize
End Sub

Private Sub B4XPage_Created (Root1 As B4XView)
    Root = Root1
    cv.Initialize(Root)
    Dim cvRect As B4XRect
    cvRect.Initialize(0, 0, Root.Width, Root.Height)
    bc.Initialize(cvRect.Width, cvRect.Height)

    cv.DrawRect(cvRect, xui.Color_RGB(180, 180, 255), True, 0)
  
    'Dim position() As Int = Array As Int(cvRect.centerX, cvRect.centerY)    'try different positions
    'Dim position() As Int = Array As Int(120, 300)
    Dim position() As Int = Array As Int(413, 150)
  
    For i = 25 To 5 Step - 1
        cv.DrawCircle(position(0), position(1), i, xui.Color_RGB(255 - 5 * i, 0, 0), True, 0)
    Next
    Dim xy() As Int = whereIsDot
    Log("Center is at " & TAB & cvRect.CenterX & TAB & cvRect.CenterY)
    Log("Dot is at " & TAB & xy(0) & TAB & xy(1))
End Sub

'I tweaked the color threshold, but you need to do it also for your situation
Private Sub whereIsDot As Int()
    'Find centroid of all points matching color
    bc.CopyPixelsFromBitmap(cv.CreateBitmap)
    Dim Sumx, Sumy, N As Float
    Dim arg As ARGBColor
    For i = 0 To bc.mWidth - 1
        For j = 0 To bc.mHeight - 1
            bc.GetARGB(i, j, arg)
            If arg.g < 200 And arg.b < 200 And arg.r > 200 Then
                Sumx = Sumx + i
                Sumy = Sumy + j
                N = N + 1
            End If
        Next
    Next
    If N = 0 Then Return Array As Int(-1, -1) Else Return Array As Int(Ceil(Sumx / N), Ceil(Sumy / N))  '-1 is unknown
End Sub
 
Last edited:
Upvote 0

William Lancee

Well-Known Member
Licensed User
Longtime User
It is a stormy day here and I have time on my hands. I did some time trials.
It took 11 milliseconds to find the red dot on a 600x600 screen. For 50 dots it took about 550 milliseconds.
The blue dots mark the path of the red dot. Run the attached to see the animation.

In real life the image is much more complicated but I would think that it would be easy to define what a red laser dot is.
I Googled, and RGB(237, 47, 50) seems to be accepted. Also, the image is probably compressed, that means that the edges of the dot are messy.
Using the centroid corrects for that.

dotTracking.jpg
 

Attachments

  • dotTracking.zip
    8.8 KB · Views: 58
Upvote 0

scsjc

Well-Known Member
Licensed User
Longtime User
It is a stormy day here and I have time on my hands. I did some time trials.
It took 11 milliseconds to find the red dot on a 600x600 screen. For 50 dots it took about 550 milliseconds.
The blue dots mark the path of the red dot. Run the attached to see the animation.

In real life the image is much more complicated but I would think that it would be easy to define what a red laser dot is.
I Googled, and RGB(237, 47, 50) seems to be accepted. Also, the image is probably compressed, that means that the edges of the dot are messy.
Using the centroid corrects for that.

View attachment 143698
really nice
you think that's is possible with a camera on real time?
 
Upvote 0

TILogistic

Expert
Licensed User
Longtime User
?
 
Upvote 0

William Lancee

Well-Known Member
Licensed User
Longtime User
It depends on how you capture the images and on the speed of your device.
The time trials I did are on my fairly fast desktop.

I guess you can always take multiple still pictures - say 5 per second or less - which may give you enough time to track the dot.
It really depends in what you need.
 
Upvote 0

William Lancee

Well-Known Member
Licensed User
Longtime User
@TILogistic

I am familiar with that post. The thing the algorithm is looking for must be in the image pixel for pixel.

Since the code above eliminates most pixels as the wrong color and since it doesn't care about the exact shape of the dot,
it can accurately find the dot's position fast, even when the image is reconstituted from a compressed state - making the shape inexact.

It also doesn't depend too much on the camera's position, since we can compute relative movement.
 
Upvote 0

scsjc

Well-Known Member
Licensed User
Longtime User
?
ohhhhhhhhhhhh
 
Upvote 0

DonManfred

Expert
Licensed User
Longtime User
ohhhhhhhhhhhh
it only works if the image to find in a picture is an exact copy of an Image available. Size, colors.

I guess it will not work with a camerapicture showing a pointer on a wall. The pointyou see must be an exact copy of an image. Guess it will not work if the dimensions are not exact.
 
Upvote 0

scsjc

Well-Known Member
Licensed User
Longtime User
it only works if the image to find in a picture is an exact copy of an Image available. Size, colors.

I guess it will not work with a camerapicture showing a pointer on a wall. The pointyou see must be an exact copy of an image. Guess it will not work if the dimensions are not exact.
Yes, I already understood, but I really liked the code :)
 
Upvote 0

William Lancee

Well-Known Member
Licensed User
Longtime User
@Johan Schoeman uses a timer to scan bar codes with the camera. He manages to get more than 3 images per second, and checks for valid bar codes.
That task is much more complex than finding the position of a laser dot. So yes, I think it is possible to do what you want. You may also eliminate the timer and just get as many pictures as you can and process them, one after the other, and track the time when a change occurs.

https://www.b4x.com/android/forum/t...g-for-live-scan-of-1d-and-2d-barcodes.116227/
 
Upvote 0

kimstudio

Active Member
Licensed User
Longtime User
It took 11 milliseconds to find the red dot on a 600x600 screen. For 50 dots it took about 550 milliseconds.
For this special case, if the first red pixel is found then exit the loop and only find other pixels in a small area around the first found pixel could be faster.
 
Upvote 0
Top