Corona Touch Listener - lua

I am learning corona sdk
This is the following code
when the two objects overlaps it becomes 1 objects(Moves together), i have no clue whats going on...
-----------------------------------------------------------------------------------------
--
-- main.lua
--
-----------------------------------------------------------------------------------------
-- Your code here
local physics = require( "physics" )
physics.start()
local crate1 = display.newImage( "crate.png", display.contentCenterX, 100 )
crate1.name = "crate1"
local crate2 = display.newImage( "crate.png", display.contentCenterX + 100, 100 )
crate2.name = "crate2"
crate1:scale(0.2, 0.2)
crate2:scale(0.2, 0.2)
local bodyTouched = function(event)
if(crate1.name == event.target.name and event.phase == "moved")
then
print("Moved " , event.target.name )
crate1.x = event.x
crate1.y = event.y
elseif (crate2.name == event.target.name and event.phase == "moved")
then
print( "Moved ", event.target.name )
crate2.x = event.x
crate2.y = event.y
end
end
physics.addBody( crate1, "static")
physics.addBody( crate2, "static")
crate1:addEventListener( "touch", bodyTouched )
crate2:addEventListener( "touch", bodyTouched )

Please refer to the Corona SDK documentation.
https://docs.coronalabs.com/daily/guide/events/detectEvents/index.html#TOC
Section: Understanding Hit Events
In general you should read the documentation on anything you use.
Your touch event will propagate through all display objects that intersect with the event coordinate. The event will trigger all registered event listeners on its way.
To avoid having multiple listeners triggered your event listener bodyTouch has to return true which will tell Corona that you handled the event and no further listeners should be invoked.

Related

Add Listener to an Image in Corona APK

I created a new project in CoronaLabs Studio with Physics-Based Game starting options and everything loaded up as a beginner I don't get where should I put addEventListener() so I can make the box to be clickable or to be destroyed on click?
I tried a bunch of different ways to just place this line of code inside the script to make the box clickable virus:applyLinearImpulse( 0, -0.25, virus.x, virus.y )
Here is the level1.lua script.
In this case, I have
require("toast")
local composer = require( "composer" )
local scene = composer.newScene()
-- include Corona's "physics" library
local physics = require("physics")
--------------------------------------------
tapCount = 0
tapText = display.newText( tapCount, display.contentCenterX, 20, native.systemFont, 40 )
--------------------------------------------
local screenW, screenH, halfW = display.actualContentWidth, display.actualContentHeight, display.contentCenterX
function scene:create( event )
-- Called when the scene's view does not exist.
-- INSERT code here to initialize the scene e.g. add display objects to 'sceneGroup', add touch listeners, etc.
local sceneGroup = self.view
physics.start()
physics.pause()
local background = display.newImageRect("game-background.png", 1170, 658)
background.x = display.contentCenterX
background.y = display.contentCenterY
-- OFFSCREEN BOX, position it, and rotate slightly
local box = display.newImageRect( "box.png", 40, 40 )
box.x, box.y = 160, -100
box.rotation = 33
-- add physics
physics.addBody( box, { density=1.0, friction=0.3, bounce=0.2 } )
-- create a grass object and add physics (with custom shape)
local grass = display.newImageRect( "grass.png", screenW, 82 )
grass.anchorX = 0
grass.anchorY = 1
-- draw the grass at the very bottom of the screen
grass.x, grass.y = display.screenOriginX, display.actualContentHeight + display.screenOriginY
local grassShape = { -halfW,-34, halfW,-34, halfW,34, -halfW,34 }
physics.addBody( grass, "static", { friction=0.3, shape=grassShape } )
sceneGroup:insert( background )
sceneGroup:insert( grass )
sceneGroup:insert( box )
end
function scene:show( event )
local sceneGroup = self.view
local phase = event.phase
if phase == "will" then
-- Called when the scene is still off-screen and is about to move on screen
elseif phase == "did" then
-- Called when the scene is now on-screen
physics.start()
end
end
function scene:hide( event )
local sceneGroup = self.view
local phase = event.phase
if event.phase == "will" then
-- Called when the scene is on-screen and is about to move off-screen
physics.stop()
elseif phase == "did" then
-- Called when the scene is now off-screen
end
end
function scene:destroy( event )
-- Called prior to the removal of scene's "view" (sceneGroup)
local sceneGroup = self.view
package.loaded[physics] = nil
physics = nil
end
---------------------------------------------------------------------------------
-- Listener setup
scene:addEventListener( "create", scene )
scene:addEventListener( "show", scene )
scene:addEventListener( "hide", scene )
scene:addEventListener( "destroy", scene )
-----------------------------------------------------------------------------------------
return scene
If I have understood your question correctly,here's an example where you can click a box and destroy it.
function scene:create(event)
local function destroyMe(event)
display.remove(event.target)
event.target=nil
end
local box = display.newImageRect( "box.png", 40, 40 )
box.x, box.y = 160, 100
box.rotation = 33
-- add physics
physics.addBody( box, { density=1.0, friction=0.3, bounce=0.2 } )
box:addEventListener("tap",destroyMe)
end
If you're using touch event,then that event will have three phases.Hence be cautious.

corona + collision not working

I am learning Corona and I am trying to use the collision event.
The target of the following program is that the rock is moving towards to the car using transition.to. And print a line to report the collision where it occurs.
However, it does not work. Moreover, I even cannot receive the message "enterenter", what is the reason why the program cannot even get into the enter function?
My code is as follow. Thank you in advance.
local composer = require( "composer" )
local scene = composer.newScene()
local physics = require "physics"
physics.start(); physics.pause()
local function onLocalCollision( self, event )
if ( event.phase == "began" ) then
print( self.myName .. ": collision began with " .. event.other.myName )
elseif ( event.phase == "ended" ) then
print( self.myName .. ": collision ended with " .. event.other.myName )
end
end
local widget = require "widget"
function scene:create( event )
print("entercreate")
local sceneGroup = self.view
local backgrd = display.newImage("background2.png",0,260)
backgrd:scale(3,3)
local car = display.newImage("car2.png",80,270)
physics.addBody(car,"static")
car.myName="Car"
local rock = display.newImage("rock.jpg",520,280)
rock:scale(0.05,0.05)
physics.addBody(rock,"static")
rock.myName="rock"
sceneGroup:insert(backgrd)
sceneGroup:insert(car)
sceneGroup:insert(rock)
transition.to(backgrd,{time=24000, x=-1800,onComplete=endScroll})
transition.to(rock,{time=4000, delay=2500,x=-40})
end
function scene:enter( event )
print("enterenter")
physics.start()
local sceneGroup = self.view
Runtime:addEventListener( "collision", onLocalCollision )
end
scene:addEventListener( "create", scene )
scene:addEventListener( "enter", scene )
return scene
Working code with a local and a global (Runtime) listener:
local widget = require "widget"
local composer = require( "composer" )
local scene = composer.newScene()
local physics = require "physics"
physics.start()
physics.setGravity( 0,0 )
local function onGlobalCollision( event )
local target = event.object1
local other = event.object2
if ( event.phase == "began" ) then
print( "GLOBAL: " .. target.name .. ": collision began with " .. other.name )
elseif ( event.phase == "ended" ) then
print( "GLOBAL: " .. target.name .. ": collision ended with " .. other.name )
end
end
local function onLocalCollision( event )
local target = event.target
local other = event.other
if ( event.phase == "began" ) then
print( "LOCAL: " .. other.name .. ": collision began with " .. target.name )
elseif ( event.phase == "ended" ) then
print( "LOCAL: " .. other.name .. ": collision ended with " .. target.name )
end
end
function scene:create( event )
print("scene:create")
local sceneGroup = self.view
local car = display.newRect( 100, 100, 100, 100 )
car.name = "car"
physics.addBody( car )
local rock = display.newRect( 250, 250, 100, 100 )
rock.name = "rock"
rock:setFillColor( 0.5, 0.5, 0.5 )
physics.addBody( rock )
rock:addEventListener( "collision", onLocalCollision )
sceneGroup:insert(car)
sceneGroup:insert(rock)
transition.to(rock,{time=4000, x = -40, y = -100})
Runtime:addEventListener( "collision", onGlobalCollision )
end
function scene:enter( event )
print("scene:enter")
local sceneGroup = self.view
end
scene:addEventListener( "create", scene )
scene:addEventListener( "enter", scene )
return scene
The problem that you have with your code is that the two bodies are static and two static bodies can't collide with each other and that there is nothing called scene:enter in composer (so that's why it doesn't gets called and therefor not the onLocalListener).
Some body types will — or will not — collide with other body types. In
a collision between two physical objects, at least one of the objects
must be dynamic, since this is the only body type which collides with
any other type. See the Physics Bodies guide for details on body
types.
https://docs.coronalabs.com/daily/guide/physics/collisionDetection/index.html
Here is some information about the Composer API and you'll that you should probably use scene:show:
https://coronalabs.com/blog/2014/01/21/introducing-the-composer-api-plus-tutorial/

Cannot get functions to work in Corona SDK (With TabButton)

I am completely new to Corona SDK and I am just looking at the example projects just to see how things work. I am looking at the TAB example however I have a problem.
I have a page like so (this is page2)
local composer = require( "composer" )
local scene = composer.newScene()
function scene:create( event )
local sceneGroup = self.view
-- Called when the scene's view does not exist.
--
-- INSERT code here to initialize the scene
-- e.g. add display objects to 'sceneGroup', add touch listeners, etc.
-- create a white background to fill screen (things go in here like pictures etc)
local bg = display.newRect( 0, 0, display.contentWidth, display.contentHeight )
bg.anchorX = 0
bg.anchorY = 0
bg:setFillColor( 0 ) -- white
-- this will create the thing that you drag (the function is after)
local tracker = display.newRect( 568, 340, 50, 50 )
tracker:setFillColor( 1 )
-- all objects must be added to group (e.g. self.view)
sceneGroup:insert( bg )
sceneGroup:insert( tracker )
end
function scene:show( event )
local sceneGroup = self.view
local phase = event.phase
if phase == "will" then
-- Called when the scene is still off screen and is about to move on screen
elseif phase == "did" then
-- Called when the scene is now on screen
--
-- INSERT code here to make the scene come alive
-- e.g. start timers, begin animation, play audio, etc.
end
end
function scene:hide( event )
local sceneGroup = self.view
local phase = event.phase
if event.phase == "will" then
-- Called when the scene is on screen and is about to move off screen
--
-- INSERT code here to pause the scene
-- e.g. stop timers, stop animation, unload sounds, etc.)
elseif phase == "did" then
-- Called when the scene is now off screen
end
end
function scene:destroy( event )
local sceneGroup = self.view
-- Called prior to the removal of scene's "view" (sceneGroup)
--
-- INSERT code here to cleanup the scene
-- e.g. remove display objects, remove touch listeners, save state, etc.
end
function tracker:touch( event )
if event.phase == "began" then
self.markX = self.x --stores x location
self.markY = self.y --stores y location
elseif event.phase == "moved" then
local x = (event.x - event.xStart) + self.markX
local y = (event.y - event.yStart) + self.markY
self.x, self.y = x, y -- moves the object from things above
end
end
---------------------------------------------------------------------------------
-- Listener setup
scene:addEventListener( "create", scene )
scene:addEventListener( "show", scene )
scene:addEventListener( "hide", scene )
scene:addEventListener( "destroy", scene )
tracker:addEventListneer( "touch", tracker)
-----------------------------------------------------------------------------------------
return scene
Anyway to simplify things the changes I have done are:
local tracker = display.newRect( 568, 340, 50, 50 )
tracker:setFillColor( 1 )
This will create a new box which I am trying to make so you can drag it around the screen (I have used this function):
function tracker:touch( event )
if event.phase == "began" then
self.markX = self.x --stores x location
self.markY = self.y --stores y location
elseif event.phase == "moved" then
local x = (event.x - event.xStart) + self.markX
local y = (event.y - event.yStart) + self.markY
self.x, self.y = x, y -- moves the object from things above
end
end
So overall it creates a box and I am trying to add a function to it so that you can drag it around the screen. However it does not work and gives me an error saying that tracker on that start of the function line function tracker:touch( event ) is wrong? Any help, because I think that this is in the wrong place.
P.S I also have a tracker:addEventListneer( "touch", tracker) listener.
-Thanks
You are creating the local tracker as a local variable inside your scene:create function. This means this variable will only be available within the scope of said function.
You need to move the function tracker:touch(event) inside the scene:create function for the tracker to be reachable.
And you need to move the listener to the bottom of the scene:create function.
Never mind. I have fixed it. I should always check my spelling xD (I spelled the tracker:addEventListener( "touch", tracker) wrong). Such a noob mistake. Thanks for the help guys.

Perspective Virtual Camera library issue Corona SDK

Hello all I am currently developing an application that I am going to use the perspective library with. I have imported the library and have written the correct code it seems but to no avail my camera is not working properly. I am attempting to get the camera to follow the main character you are moving around with the buttons. I added him and the background and a "tree" to the camera and set him as the focus but it still will not follow him. Here is my code please tell me what I have done wrong here and how to fix it.
local storyboard = require( "storyboard" )
local scene = storyboard.newScene()
local perspective = require( "perspective" )
local camera = perspective.createView()
local physics = require( "physics" )
--physics.setDrawMode( "hybrid" )
local function start( event )
if( event.phase == "ended" ) then
end
end
local bg
local floor
local leftwall
local rightwall
local player
local button1
local button2
local pausebtn
local tree
local function b1( event )
if( event.phase == "ended" ) then
player:applyLinearImpulse( -.01, -.1 )
end
end
local function b2( event )
if( event.phase == "ended" ) then
player:applyLinearImpulse( .01, -.1 )
end
end
local function playerCollision( event )
if( event.phase == "began" ) then
storyboard.gotoScene( "gameover" )
end
end
local function pause( event )
if( event.phase == "ended" ) then
storyboard.showOverlay( "pause" )
physics.pause()
end
end
function scene:createScene( event )
local group = self.view
physics.start()
bg = display.newImage( "bg.png", display.contentWidth/2, display.contentHeight/2, display.contentWidth, display.contentHeight )
camera:add(bg, 3, false)
player = display.newImage( "player.png", display.contentWidth/2, display.contentHeight/2, display.contentWidth, display.contentHeight )
player.collision = playerCollision
camera:add(player, 1, true)
tree = display.newImage( "tree.png", 200, 200)
camera:add(tree, 2, false)
floor = display.newRect( 285, 375, 570, 1 )
button1 = display.newImage( "button1.png", 50, 275 )
button2 = display.newImage( "button2.png", 515, 275 )
leftwall = display.newRect( 0, -1000, 1, 5000 )
rightwall = display.newRect( 570, 300, 1, 5000 )
pausebtn = display.newImage( "pausebtn.png", 540, 30 )
-- Physics
physics.addBody( player )
physics.addBody( floor )
floor.bodyType = "static"
physics.addBody( rightwall )
rightwall.bodyType = "static"
physics.addBody( leftwall )
leftwall.bodyType = "static"
group:insert(bg)
group:insert(player)
group:insert(floor)
group:insert(button1)
group:insert(button2)
group:insert(rightwall)
group:insert(leftwall)
group:insert(pausebtn)
group:insert(tree)
end
function scene:enterScene( event )
print( "game" )
button1:addEventListener( "touch", b1 )
button2:addEventListener( "touch", b2 )
player:addEventListener( "collision", playerCollision )
pausebtn:addEventListener( "touch", pause )
end
function scene:exitScene()
player = nil
camera:cancel()
end
function scene:destroyScene( event )
end
scene:addEventListener( "createScene", scene )
scene:addEventListener( "enterScene", scene )
scene:addEventListener( "exitScene", scene )
scene:addEventListener( "destroyScene", scene )
return scene
Looks like you are missing the call to camera:track() (which should probably go in the enterScene handler). You might also need camera:setBounds(false).
If this still doesn't fix issue, remove all code from your post that is not required in order to duplicate the problem. If you can boil it down to a small example that I can run, I can try and post update.

Move a object by flicking

I can move the box by touching it and dragging it along the x-axis, but i like to be able to flick it from one side to the other. is there a simple solution to do this?
local box = display.newRect( 0, 0, 50, 50)
box:setFillColor( math.random(0,255), math.random(0,255), math.random(0,255) )
physics.addBody( box, { density=3.0, friction=0.5 } )
box.gravityScale = 0.0
function box:touch( event )
if event.phase == "began" then
self.markX = self.x
elseif event.phase == "moved" then
local x = (event.x - event.xStart) + self.markX
self.x = x
end
return true
end
box:addEventListener( "touch", box )
You could use transition.to, but you'll have to decide by how much to move. I'll assume you want to move it all the way to other side:
function box:touch( event )
if event.phase == "began" then
self.markX = self.x
elseif event.phase == "end" then
local targetX = 0 -- if flick left
if event.x > self.markX then -- flick right
targetX = display.contentWidth - self.width
end
local duration = 1000 -- 1 second
transition.to(self, {duration, x=targetX})
end
return true
end
Have not tested, could be syntax or other errors, but this should give you a good idea of how to proceed (if not put a comment).

Resources