Help with perspective and camera?

Hello,

I have been working on a game for a while, now. I have run into a problem, and cant seem to find the solution. My app has the user draw a line on the screen. If you draw the line, it appears in a different place:
http://i.imgur.com/ker5vGu.png

I want the line to appear where it is drawn.

Here is my code:

[code]

– main.lua

print(system.getInfo(“maxTextureSize”))

local perspective = require(“perspective”)
local camera = perspective.createView()

– physics.setDrawMode(“hybrid”)

local physics = require(“physics”)

physics.start()

physics.setScale( 60 )

physics.setGravity(0, 10)

display.setStatusBar( display.HiddenStatusBar )

local background = display.newImage(“images/clouds.png”, -100, -1000)

– Create player and set location
local player = display.newImage(“images/fred.png”)
player.x = display.contentWidth / 2
player.y = display.contentHeight / 6

– Turn player into physics body
physics.addBody(player, { radius = 30 } );

– Create walls on the left and right
local leftWall = display.newRect (-100, -1500, 1, display.contentHeight * 100000000000);
local rightWall = display.newRect (display.contentWidth, -1500, 1, display.contentHeight * 100000000000);

– Add physics to the walls. They will not move so they will be static
physics.addBody (leftWall, “static”, { bounce = 1.0 } );
physics.addBody (rightWall, “static”, { bounce = 1.0 } );

– Floor with physics
local bottomFloor = display.newRect(0, 500, display.contentWidth, 20)
physics.addBody(bottomFloor, “static”, { bounce = 1.0, } )

_W = display.contentWidth;
_H = display.contentHeight;

local lineLengthConstraint = 128
local lines = {}

local function getLength(x1, x2, y1, y2)
local x = x1 - x2
local y = y1 - y2
local length = math.sqrt(x*x + y*y)
return length
end

local function drawLine(event)

if event.phase == “began” then

– inTouch state.

inTouch = true

– X/Y Coordinates of initial touch.

initialX = event.x
initialY = event.y

– Create our line.

ourLine = display.newLine(initialX, initialY, initialX, initialY+getLength(initialX, event.x, initialY, event.y))
ourLine:setColor(0,255,0)
ourLine.width = 8
ourLine.rotation = math.deg(math.atan2(event.y - initialY, event.x - initialX)) - 90

elseif event.phase == “moved” and inTouch then

– Recreate our line, in the case that it is shorter than the length constraint.

if getLength(initialX, event.x, initialY, event.y) <= lineLengthConstraint then

– Remove old version of our line.

display.remove(ourLine)
ourLine = nil

– Create new version of our line.

ourLine = display.newLine(initialX, initialY, initialX, initialY+getLength(initialX, event.x, initialY, event.y))
ourLine:setColor(0,255,0)
ourLine.width = 8

– Store limited line length.

limitedLineLength = getLength(initialX, event.x, initialY, event.y)

– Physics

–local physShape = { (ourLine.width/2),0, (ourLine.width/2),limitedLineLength, -(ourLine.width/2),limitedLineLength, -(ourLine.width/2),0 }
–physics.addBody(ourLine, “static”, {bounce=1.5, shape=physShape})

end

– Set rotation of our line.

ourLine.rotation = math.deg(math.atan2(event.y - initialY, event.x - initialX)) - 90

elseif event.phase == “ended” and inTouch then

– inTouch state.

inTouch = false

– Physics

local physShape = { (ourLine.width/2),0, (ourLine.width/2),limitedLineLength, -(ourLine.width/2),limitedLineLength, -(ourLine.width/2),0 }
physics.addBody(ourLine, “static”, {bounce=1.5, shape=physShape})

– Remove line from the screen when there’s one or more stored in the table.
if #lines >= 1 then
for i=1,#lines do
display.remove(lines[i])
lines[i] = nil
end
end

– Store our line in a table, just in case we need to reference or remove it later.

i = #lines+1
lines[i] = ourLine
camera:add(lines[i], 1, false)

end

end

Runtime:addEventListener(“touch”, drawLine)

camera.x, camera.y = 100, 100
camera:add(player, 1, true)
camera:add(rightWall, 5)
camera:add(leftWall, 5)
camera:add(bottomFloor, 5)
camera:setFocus(player)
camera:add(background, 2, false)
– camera.offsetX, camera.offsetY = 150, 150
camera:setBounds(0, 0, -1000, 1000000000)
camera.damping = 10
camera:track()
[/code] [import]uid: 188277 topic_id: 36014 reply_id: 336014[/import]

If you’re tracking an object with Perspective, for position-specific events, you must subtract the camera’s scrollX and scrollY to get it in the right place. So [lua]event.x[/lua] becomes [lua]event.x-camera.scrollX[/lua] and [lua]event.y[/lua] becomes [lua]event.y-camera.scrollY[/lua].

Caleb [import]uid: 147322 topic_id: 36014 reply_id: 143165[/import]

When your rendering requires perspective I always recommend using a camera rather than using View, Display, Perspective. Cameras give you more accurate control over the viewing position and by manipulating the field of view box size/focal length and changing the camera position relative to the model you can change the perspective with significant control. If the perspective that you get from a camera is not enough to give you the fish eye effect you are looking for, what some people do in reality and in rendering is to position a camera.
Business VoIP Providers [import]uid: 228622 topic_id: 36014 reply_id: 143167[/import]

Thanks Guys!
Caleb, I was wondering where I would put event.x-camera.scrollx? The stuff that I have for camera has no event.x…

Thanks!
[import]uid: 188277 topic_id: 36014 reply_id: 143193[/import]

When you’re storing your coordinates: [lua]initialX=event.x[/lua] and [lua]initialY=event.y[/lua] becomes [lua]initialX=event.x-camera.scrollX[/lua] and [lua]initialY=event.y-camera.scrollY[/lua]. Here’s a modified version of your code from the top of my head:
[lua]
local function drawLine(event)

if event.phase == “began” then

– inTouch state.

inTouch = true

– X/Y Coordinates of initial touch.

initialX = event.x-camera.scrollX
initialY = event.y-camera.scrollY

– Create our line.

ourLine = display.newLine(initialX, initialY, initialX, initialY+getLength(initialX, event.x-camera.scrollX, initialY, event.y-camera.scrollY))
ourLine:setColor(0,255,0)
ourLine.width = 8
ourLine.rotation = math.deg(math.atan2((event.y-camera.scrollY) - initialY, (event.x-camera.scrollX) - initialX)) - 90

elseif event.phase == “moved” and inTouch then

– Recreate our line, in the case that it is shorter than the length constraint.

if getLength(initialX, event.x-camera.scrollX, initialY, event.y-camera.scrollY) <= lineLengthConstraint then

– Remove old version of our line.

display.remove(ourLine)
ourLine = nil

– Create new version of our line.

ourLine = display.newLine(initialX, initialY, initialX, initialY+getLength(initialX, event.x-camera.scrollX, initialY, event.y-camera.scrollY))
ourLine:setColor(0,255,0)
ourLine.width = 8

– Store limited line length.

limitedLineLength = getLength(initialX, event.x-camera.scrollX, initialY, event.y-camera.scrollY)

– Physics

–local physShape = { (ourLine.width/2),0, (ourLine.width/2),limitedLineLength, -(ourLine.width/2),limitedLineLength, -(ourLine.width/2),0 }
–physics.addBody(ourLine, “static”, {bounce=1.5, shape=physShape})

end

– Set rotation of our line.

ourLine.rotation = math.deg(math.atan2(event.y - initialY, event.x - initialX)) - 90

elseif event.phase == “ended” and inTouch then

– inTouch state.

inTouch = false

– Physics

local physShape = { (ourLine.width/2),0, (ourLine.width/2),limitedLineLength, -(ourLine.width/2),limitedLineLength, -(ourLine.width/2),0 }
physics.addBody(ourLine, “static”, {bounce=1.5, shape=physShape})

– Remove line from the screen when there’s one or more stored in the table.
if #lines >= 1 then
for i=1,#lines do
display.remove(lines[i])
lines[i] = nil
end
end

– Store our line in a table, just in case we need to reference or remove it later.

i = #lines+1
lines[i] = ourLine
camera:add(lines[i], 1, false)

end

end
[/lua]
Note that that might not work - I just replaced all occurrences of [lua]event.x[/lua] with [lua]event.x-camera.scrollX[/lua] and the same for Y.

Caleb [import]uid: 147322 topic_id: 36014 reply_id: 143214[/import]

Thanks for your help, Caleb!

I’m kind of stumped, here… I tried your code, and the screen went black. I tried variations of it; such as just doing event.X - camera.scrollX for initialX, and nothing else worked. Is there just a way to change the camera? I don’t think there would be, though, as there are other objects on the screen. Or could I just change initial x and y to initialX/Y - some number to try and get the line to appear where I draw it.

Thanks again for all your help! [import]uid: 188277 topic_id: 36014 reply_id: 143221[/import]

You could also try moving the line once you’ve created it, at the end of the function:
[lua]
ourLine.y=ourLine.y-camera.scrollY; ourLine.x=ourLine.x-camera.scrollX
[/lua] [import]uid: 147322 topic_id: 36014 reply_id: 143227[/import]

If you’re tracking an object with Perspective, for position-specific events, you must subtract the camera’s scrollX and scrollY to get it in the right place. So [lua]event.x[/lua] becomes [lua]event.x-camera.scrollX[/lua] and [lua]event.y[/lua] becomes [lua]event.y-camera.scrollY[/lua].

Caleb [import]uid: 147322 topic_id: 36014 reply_id: 143165[/import]

When your rendering requires perspective I always recommend using a camera rather than using View, Display, Perspective. Cameras give you more accurate control over the viewing position and by manipulating the field of view box size/focal length and changing the camera position relative to the model you can change the perspective with significant control. If the perspective that you get from a camera is not enough to give you the fish eye effect you are looking for, what some people do in reality and in rendering is to position a camera.
Business VoIP Providers [import]uid: 228622 topic_id: 36014 reply_id: 143167[/import]

Thanks Guys!
Caleb, I was wondering where I would put event.x-camera.scrollx? The stuff that I have for camera has no event.x…

Thanks!
[import]uid: 188277 topic_id: 36014 reply_id: 143193[/import]

When you’re storing your coordinates: [lua]initialX=event.x[/lua] and [lua]initialY=event.y[/lua] becomes [lua]initialX=event.x-camera.scrollX[/lua] and [lua]initialY=event.y-camera.scrollY[/lua]. Here’s a modified version of your code from the top of my head:
[lua]
local function drawLine(event)

if event.phase == “began” then

– inTouch state.

inTouch = true

– X/Y Coordinates of initial touch.

initialX = event.x-camera.scrollX
initialY = event.y-camera.scrollY

– Create our line.

ourLine = display.newLine(initialX, initialY, initialX, initialY+getLength(initialX, event.x-camera.scrollX, initialY, event.y-camera.scrollY))
ourLine:setColor(0,255,0)
ourLine.width = 8
ourLine.rotation = math.deg(math.atan2((event.y-camera.scrollY) - initialY, (event.x-camera.scrollX) - initialX)) - 90

elseif event.phase == “moved” and inTouch then

– Recreate our line, in the case that it is shorter than the length constraint.

if getLength(initialX, event.x-camera.scrollX, initialY, event.y-camera.scrollY) <= lineLengthConstraint then

– Remove old version of our line.

display.remove(ourLine)
ourLine = nil

– Create new version of our line.

ourLine = display.newLine(initialX, initialY, initialX, initialY+getLength(initialX, event.x-camera.scrollX, initialY, event.y-camera.scrollY))
ourLine:setColor(0,255,0)
ourLine.width = 8

– Store limited line length.

limitedLineLength = getLength(initialX, event.x-camera.scrollX, initialY, event.y-camera.scrollY)

– Physics

–local physShape = { (ourLine.width/2),0, (ourLine.width/2),limitedLineLength, -(ourLine.width/2),limitedLineLength, -(ourLine.width/2),0 }
–physics.addBody(ourLine, “static”, {bounce=1.5, shape=physShape})

end

– Set rotation of our line.

ourLine.rotation = math.deg(math.atan2(event.y - initialY, event.x - initialX)) - 90

elseif event.phase == “ended” and inTouch then

– inTouch state.

inTouch = false

– Physics

local physShape = { (ourLine.width/2),0, (ourLine.width/2),limitedLineLength, -(ourLine.width/2),limitedLineLength, -(ourLine.width/2),0 }
physics.addBody(ourLine, “static”, {bounce=1.5, shape=physShape})

– Remove line from the screen when there’s one or more stored in the table.
if #lines >= 1 then
for i=1,#lines do
display.remove(lines[i])
lines[i] = nil
end
end

– Store our line in a table, just in case we need to reference or remove it later.

i = #lines+1
lines[i] = ourLine
camera:add(lines[i], 1, false)

end

end
[/lua]
Note that that might not work - I just replaced all occurrences of [lua]event.x[/lua] with [lua]event.x-camera.scrollX[/lua] and the same for Y.

Caleb [import]uid: 147322 topic_id: 36014 reply_id: 143214[/import]

Thanks for your help, Caleb!

I’m kind of stumped, here… I tried your code, and the screen went black. I tried variations of it; such as just doing event.X - camera.scrollX for initialX, and nothing else worked. Is there just a way to change the camera? I don’t think there would be, though, as there are other objects on the screen. Or could I just change initial x and y to initialX/Y - some number to try and get the line to appear where I draw it.

Thanks again for all your help! [import]uid: 188277 topic_id: 36014 reply_id: 143221[/import]

You could also try moving the line once you’ve created it, at the end of the function:
[lua]
ourLine.y=ourLine.y-camera.scrollY; ourLine.x=ourLine.x-camera.scrollX
[/lua] [import]uid: 147322 topic_id: 36014 reply_id: 143227[/import]

If you’re tracking an object with Perspective, for position-specific events, you must subtract the camera’s scrollX and scrollY to get it in the right place. So [lua]event.x[/lua] becomes [lua]event.x-camera.scrollX[/lua] and [lua]event.y[/lua] becomes [lua]event.y-camera.scrollY[/lua].

Caleb [import]uid: 147322 topic_id: 36014 reply_id: 143165[/import]

When your rendering requires perspective I always recommend using a camera rather than using View, Display, Perspective. Cameras give you more accurate control over the viewing position and by manipulating the field of view box size/focal length and changing the camera position relative to the model you can change the perspective with significant control. If the perspective that you get from a camera is not enough to give you the fish eye effect you are looking for, what some people do in reality and in rendering is to position a camera.
Business VoIP Providers [import]uid: 228622 topic_id: 36014 reply_id: 143167[/import]

Thanks Guys!
Caleb, I was wondering where I would put event.x-camera.scrollx? The stuff that I have for camera has no event.x…

Thanks!
[import]uid: 188277 topic_id: 36014 reply_id: 143193[/import]

When you’re storing your coordinates: [lua]initialX=event.x[/lua] and [lua]initialY=event.y[/lua] becomes [lua]initialX=event.x-camera.scrollX[/lua] and [lua]initialY=event.y-camera.scrollY[/lua]. Here’s a modified version of your code from the top of my head:
[lua]
local function drawLine(event)

if event.phase == “began” then

– inTouch state.

inTouch = true

– X/Y Coordinates of initial touch.

initialX = event.x-camera.scrollX
initialY = event.y-camera.scrollY

– Create our line.

ourLine = display.newLine(initialX, initialY, initialX, initialY+getLength(initialX, event.x-camera.scrollX, initialY, event.y-camera.scrollY))
ourLine:setColor(0,255,0)
ourLine.width = 8
ourLine.rotation = math.deg(math.atan2((event.y-camera.scrollY) - initialY, (event.x-camera.scrollX) - initialX)) - 90

elseif event.phase == “moved” and inTouch then

– Recreate our line, in the case that it is shorter than the length constraint.

if getLength(initialX, event.x-camera.scrollX, initialY, event.y-camera.scrollY) <= lineLengthConstraint then

– Remove old version of our line.

display.remove(ourLine)
ourLine = nil

– Create new version of our line.

ourLine = display.newLine(initialX, initialY, initialX, initialY+getLength(initialX, event.x-camera.scrollX, initialY, event.y-camera.scrollY))
ourLine:setColor(0,255,0)
ourLine.width = 8

– Store limited line length.

limitedLineLength = getLength(initialX, event.x-camera.scrollX, initialY, event.y-camera.scrollY)

– Physics

–local physShape = { (ourLine.width/2),0, (ourLine.width/2),limitedLineLength, -(ourLine.width/2),limitedLineLength, -(ourLine.width/2),0 }
–physics.addBody(ourLine, “static”, {bounce=1.5, shape=physShape})

end

– Set rotation of our line.

ourLine.rotation = math.deg(math.atan2(event.y - initialY, event.x - initialX)) - 90

elseif event.phase == “ended” and inTouch then

– inTouch state.

inTouch = false

– Physics

local physShape = { (ourLine.width/2),0, (ourLine.width/2),limitedLineLength, -(ourLine.width/2),limitedLineLength, -(ourLine.width/2),0 }
physics.addBody(ourLine, “static”, {bounce=1.5, shape=physShape})

– Remove line from the screen when there’s one or more stored in the table.
if #lines >= 1 then
for i=1,#lines do
display.remove(lines[i])
lines[i] = nil
end
end

– Store our line in a table, just in case we need to reference or remove it later.

i = #lines+1
lines[i] = ourLine
camera:add(lines[i], 1, false)

end

end
[/lua]
Note that that might not work - I just replaced all occurrences of [lua]event.x[/lua] with [lua]event.x-camera.scrollX[/lua] and the same for Y.

Caleb [import]uid: 147322 topic_id: 36014 reply_id: 143214[/import]

Thanks for your help, Caleb!

I’m kind of stumped, here… I tried your code, and the screen went black. I tried variations of it; such as just doing event.X - camera.scrollX for initialX, and nothing else worked. Is there just a way to change the camera? I don’t think there would be, though, as there are other objects on the screen. Or could I just change initial x and y to initialX/Y - some number to try and get the line to appear where I draw it.

Thanks again for all your help! [import]uid: 188277 topic_id: 36014 reply_id: 143221[/import]

You could also try moving the line once you’ve created it, at the end of the function:
[lua]
ourLine.y=ourLine.y-camera.scrollY; ourLine.x=ourLine.x-camera.scrollX
[/lua] [import]uid: 147322 topic_id: 36014 reply_id: 143227[/import]

If you’re tracking an object with Perspective, for position-specific events, you must subtract the camera’s scrollX and scrollY to get it in the right place. So [lua]event.x[/lua] becomes [lua]event.x-camera.scrollX[/lua] and [lua]event.y[/lua] becomes [lua]event.y-camera.scrollY[/lua].

Caleb [import]uid: 147322 topic_id: 36014 reply_id: 143165[/import]