Spawning Multiple Images with Gravity and Touch to Change Image ETC!

Hey everyone!

I am a new Corona user and as much as I love it, I am also very confused. Everything is going pretty good but there is just one thing that is driving me nuts.

I have 3 different color balloons, 2 of each color. I want them to spawn from the bottom and float up to the top of the screen. I want it to be able that when you tap on say Balloon(1A).png it changes to Balloon(1B).png. I know that doesn't sound too complex, but there has been a lot of problems. I can't seem to figure out how to make it so all 6 images will be spawned randomly, not all at once, but come up at different times. I want the balloons 1(A),2(A),3(A) versions to appear more often then balloons 1(B),2(B),3(B).

I was able to make a balloon spawn from the bottom, fly to the top, and remove when it gets there.

1
2
3
4
5
6
7
8
9
10
11
12
13
--> Balloon 1A
local listener1 = function( balloon1AObject )
    balloon1AObject:removeSelf()
end
--
                local balloon1AObject = display.newImage( "images/Balloon(1A).png" )
                balloon1AObject.x = math.random(40,300); balloon1AObject.y = 800
                balloon1AObject.myName = "balloon1A"
                balloon1AObject.transToballoon1A = transition.to(balloon1AObject, {time=7000, x=200, y=-500, onComplete=listener1 })
        
                localGroup:insert(balloon1AObject)        
end
tmrballoon1A = timer.performWithDelay( 3000, fnballoon1A, 0 )

Sprites!

Create a spritesheet with all your balloon images; it's the easiest, neatest way to cheage the balloon image when it's touched.

For spawning, you would likely use two different timers to spawn the two different balloons - one more frequently than the other.

Peach :)

Could you give me a demo of the spritesheet? They are very confusing to me, and a demo would clear it up. Thanks for your reply though, I am excited to test it out!

Take the greendude sprite out of CoronaSDK > SampleCode > Sprites > JungleScene and put it in a new project.

Test this code;

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
display.setStatusBar (display.HiddenStatusBar)
 
require "sprite"
 
-- A sprite sheet with a green dude (from JungleScene)
local sheet2 = sprite.newSpriteSheet( "greenman.png", 128, 128 )
 
local spriteSet2 = sprite.newSpriteSet(sheet2, 1, 15)
sprite.add( spriteSet2, "man", 1, 15, 200, 0 ) -- play 15 frames every 200 ms
 
local instance2 = sprite.newSprite( spriteSet2 )
instance2.x = 160
instance2.y = 100
 
local function setFrame()
        instance2.currentFrame = instance2.currentFrame + 1
end
instance2:addEventListener("tap", setFrame)

I had adjusted the code to what I thought would work..

1
2
3
4
5
6
7
8
9
10
11
12
13
local sheet2 = sprite.newSpriteSheet( "images/RedBalloonNON-Lite.png", 270, 165 )
 
local spriteSet2 = sprite.newSpriteSet(sheet2, 1, 2)
sprite.add( spriteSet2, "redballoonnl", 1, 2, 200, 0 )
 
local instance2 = sprite.newSprite( spriteSet2 )
instance2.x = 160
instance2.y = 100
 
local function setFrame()
        instance2.currentFrame = instance2.currentFrame + 1
end
instance2:addEventListener("tap", setFrame)

Yes you can transition sprites just like other images or shapes :)

The sheet error is that your frames don't match what you're telling the simulator they are - what size is your sheet? (Width and height, how many frames?)

Peach :)

Awesome!

My sheet is 270 x 165. Does it need to be a certain size like 256 x 256? The reason it is that size is because I plan on having multiple sprite sheets, one for 1A to 1B, one for 1B to 1A, and then repeat of that for balloons 2 and 3. Therefore it is only two frames in that sprite, 1A and 1B. Would it be smarter to have one big sheet with all the balloons on it and for each sprite tell it to only call frame 1A and 1B or 1B and 1A or?

Hey Matt,

You could use one big sheet but multiples works fine too. I personally prefer multiples, although that's just me being stuck in my ways - how do you want to do it?

For your sheet, 270 wide, 165 high? That's the issue. In your code you say;
local sheet2 = sprite.newSpriteSheet( "images/RedBalloonNON-Lite.png", 270, 165 )

Try changing that to;

local sheet2 = sprite.newSpriteSheet( "images/RedBalloonNON-Lite.png", 135, 165 )

This is because that should be the frame width and height, not the sheet width and height.

Let me know how that goes.

Peach :)

PS - I am assuming your images are side by side, not top to bottom, let me know if I am mistaken.

Hey Peach,

Ahhh, thank you so much! Finally got what I needed!

Since I was able to get that working thanks to you, I was wondering if we could move onto part 2 of my question. How do I get all 6 balloons to transition up at random times in random spots? I knew for having the 3 I want to appear the most to put on 1 timer, and the other 3 to a different timer, but could you give me an example of how I group these sprites into one timer while telling it to appear from the bottom at a random x position? I suppose listeners are involved? Also, what do I do to kill these balloons when they are off screen?

As far as positioning the balloons and transitioning them, this is correct, right?

1
2
balloon1AObject.x = math.random(40,300); balloon1AObject.y = 800
balloon1AObject.transToballoon1A = transition.to(balloon1AObject, {time=7000, x=200, y=-500})

Hey Matt,

You'd likely write a function around the code that you use to create the balloon, making the x random, then putting that on a timer that goes off 3 times.

If that isn't clear enough let me know and I'll try to write some simple plug and play for you if I can :)

Peach

Hey Peach,

If you could please write a plug and play, I'd greatly appreciate it!

Matt

Hey Matt,

This is very basic but should help;

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
display.setStatusBar (display.HiddenStatusBar)
 
math.randomseed(os.time())
 
local function spawnBalloon1 (event)
        ranX = math.random(20,300)
        local balloon1 = display.newCircle( ranX, 530, 20 )
        transition.to(balloon1, {time=2500, y=-50, onComplete = function() balloon1:removeSelf() end})
end
timer.performWithDelay(500, spawnBalloon1, 5)
 
local function spawnBalloon2 (event)
        ranX = math.random(20,300)
        local balloon2 = display.newCircle( ranX, 530, 20 )
        balloon2:setFillColor(255, 0, 0)
        transition.to(balloon2, {time=2700, y=-50, onComplete = function() balloon2:removeSelf() end})
end
timer.performWithDelay(600, spawnBalloon2, 5)

Hey Peach,

I know, I'm a noob. I am still trying to get this to work correctly, so what I tried was the 2nd balloon, and the sprite shows up, but it doesn't transition or show up in the right spot. I really don't understand these sprites at all.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
display.setStatusBar (display.HiddenStatusBar)
 
math.randomseed(os.time())
 
local function spawnBalloon1 (event)
        ranX = math.random(20,300)
        local balloon1 = display.newCircle( ranX, 530, 20 )
        transition.to(balloon1, {time=2500, y=-50, onComplete = function() balloon1:removeSelf() end})
end
timer.performWithDelay(500, spawnBalloon1, 5)
 
local function spawnBalloon2 (event)
        ranX = math.random(20,300)
        local balloon2 = sprite.newSprite( spriteSet2 )
        local function setFrame()
        balloons2.currentFrame = balloon2.currentFrame + 1
end
        transition.to(balloon2, {time=2700, y=-50, onComplete = function() balloon2:removeSelf() end})
end
timer.performWithDelay(600, spawnBalloon2, 5)

Try taking out lines 15 and 17 above (because it doesn't need to be a function) and changing line 16 from;
balloons2.currentFrame = balloon2.currentFrame + 1
to
balloon2.currentFrame = balloon2.currentFrame + 1

(It had a typo.)

For your last question I need you to be clearer about what you are asking - it sounds like you just want to spawn three balloons which you could do by changing 5 to 3 in the timer.

Maybe you mean you want three to spawn at once?

Let me know.

Peach :)

Hey Peach, I changed the code as you said and it spawns in the to left and it flys up, but its already at the top, plus it automatically changes right away to what the touch use to do.

1
2
3
4
5
6
7
local function spawnBalloon2 (event)
        ranX = math.random(20,300)
        local balloon2 = sprite.newSprite( spriteSet2 )
        balloon2.currentFrame = balloon2.currentFrame + 1
        transition.to(balloon2, {time=2700, y=-500, onComplete = function() balloon2:removeSelf() end})
end
timer.performWithDelay(600, spawnBalloon2, 5)

A quick update:
I switch the code around to this

1
2
3
4
5
6
7
8
local function spawnBalloon2 (event)
        local balloon2 = sprite.newSprite( spriteSet2 )
        balloon2.x = math.random(20,300)
        balloon2.y = 800
        balloon2.currentFrame = balloon2.currentFrame + 1
        transition.to(balloon2, {time=4700, y=-50, onComplete = function() balloon2:removeSelf() end})
end
timer.performWithDelay(1000, spawnBalloon2, 5)

Can you upload a sample zip of this so I can test it? I'm pretty swamped but I can try to make time to check it out for you.

It may be a matter of spawning them in a table for unique names.

Peach :)

Here is a link to the zipped file: Click here

I just looked and am a little confused; you have two balloon images, one has a white bit the other doesn't - so two frames. If you want them spawning normal you'd do nothing, if you want them on the second frame at spawn time you'd do balloon2.currentFrame = 2

As to them spawning as though they were already touched, I don't know what that means because they don't have touch listeners on them.

If you can elaborate further I can try to help but it's a little confusing at this point because I can't envision quite what you are going for yet.

Peach :)

Hi Peach,

The reason why I had a balloon already there spawning on the screen was because from the help you gave me, I had it where it would spawn and I could click to change it to the other frame, just don't mind that one. I only adjusted one of the spawners of the circles you provided me with, I left one set of circles there and changed the other to a sprite. So I only played with this code:

1
2
3
4
5
6
7
8
9
---Spawn Balloon 2
local function spawnBalloon2 (event)
        ranX = math.random(40,300)
        local balloon2 = sprite.newSprite( spriteSet2 )
        balloon2.x = math.random(20,300)
        balloon2.y = 800
        transition.to(balloon2, {time=4700, y=-50, onComplete = function() balloon2:removeSelf() end})
end
timer.performWithDelay(1000, spawnBalloon2, 5)

Try this code;

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
--Touch Balloon 2 Function
local function touchBalloon2 (event)
        event.target.currentFrame = 2
end
 
---Spawn Balloon 2
local function spawnBalloon2 (event)
        ranX = math.random(40,300)
        local balloon2 = sprite.newSprite( spriteSet2 )
                balloon2.currentFrame = 1
        balloon2.x = math.random(20,300)
        balloon2.y = 800
                balloon2:addEventListener("tap", touchBalloon2)
        transition.to(balloon2, {time=4700, y=-50, onComplete = function() balloon2:removeSelf() end})
end
timer.performWithDelay(1000, spawnBalloon2, 5)

Awesome, thank you, the spawn balloon 2 works perfect!

As for the functions, what would I do to the spawn balloon 2 to tell it to react to that function, so that I can group 3 balloons into that function and 3 into the other? Or would i just do..

timer.performWithDelay(1000, functionName, 10)

and make it into..

timer.performWithDelay(1000, spawnballoon2, 10)

Because I want 3 balloons to fall under 1 timer, and 3 balloons to fall under the other.

Is there a way to do this?

Also, can I add to the touch function for it to update the score/star count? So not only does it change frame, but it also either minuses a point or minuses a star?

For three balloons you'd want the timer to fire three times, so;

timer.performWithDelay(1000, spawnballoon2, 3)

That would do three balloons. Then you'd do it again for spawnballoon1, or whatnot.

For the points, yes, just add the code to add or subtract a point under where you change what frame is showing.

Peach :)

views:2164 update:2012/2/8 8:46:10
corona forums © 2003-2011