It looks like you're new here. If you want to get involved, click one of these buttons!
I created a class for handling sprites the purpose is to choose symbols from a menu and drag them to positions on the screen. But it seems to not work all the time, or theres got to be a better way to do this.
here is the touch part of the class.
ScaledSprite = class()
function ScaledSprite:init(mySprite,Ssize,x,y)
self.pos = vec2(x,y)
self.mySprite = mySprite
self.Ssize = Ssize
self.Sw,self.Sh = spriteSize(self.mySprite)
self.action = nil
self.selected = false
end
function ScaledSprite:draw()
-- Codea does not automatically call this method
factor = self.Ssize / 100
sprite(self.mySprite,self.pos.x,self.pos.y,self.Sw * factor,self.Sh * factor)
end
function ScaledSprite:touched(touch)
-- Codea does not automatically call this method
if touch.state == MOVING then
if (math.abs(self.pos.x - touch.x) <= (self.Sw/2)
and math.abs(self.pos.y - touch.y) <= (self.Sh/2)) then
if flying ~= "none" then
self.selected = true
else
self.selected = false
end
elseif touch.state == ENDED then
if self.selected == true and self.action then
self.selected = false
self.action()
end
end
end
As I explained sometimes it gets the ENDED condition but sometimes it doesn't.
From Main this were I called the class action: (Fliying is a control variable to indicate that I hit symbol from the menu)
if (flying == "P1") then
if CurrentTouch.y > 680 then
fixedy = 680
elseif CurrentTouch.y < 100 then
fixedy = 100
else
fixedy = CurrentTouch.y
end
ssP1 = ScaledSprite("Dropbox:symbol-P1",symbSize * vsmFactor,CurrentTouch.x,fixedy)
ssP1.action = function() btnSymbPRO1pressed() end
ssP1:draw()
dragging = true
end
Action function that's is called after the touch ENDED is detected
function btnSymbPRO1pressed()
iSymbol = iSymbol + 1
flying = "none"
dragging = false
aSx[iSymbol] = CurrentTouch.x
aSy[iSymbol] = CurrentTouch.y
fw, fh = spriteSize("Dropbox:symbol-P1")
aSw[iSymbol] = fw * (symbSize / 100) * vsmFactor
aSh[iSymbol] = fh * (symbSize / 100) * vsmFactor
end
Comments
Perhaps related to the other touch problem thread.
Can you check if you get any touch event at all by simply printing t.state? Especially look out for the undocumented state CANCELLED (which equals to 3 on Codea 1.5) and verrrrry unlikely STATIONARY (4 on Codea 1.5).
Codeslinger I tried what you recommended so I added the code
if(touch.state ~= touchvar) then
print(touchstate)
touchvar = touch.state
end
the tracking is working I am getting 0 when start, 1 when moving and 2 when ended. But the ended doesnt triggers on time the function.
dumb question: are you passing the touch parameter from the main draw() loop?
I don't fully understand your question (I am new working with objects and classes) but here is where I call the class
And I use the currentTouch property for dragging the sprite on the screen and when I release the touch it suppose to save the position in a table it sometimes does it but sometimes don't
CurrentTouch is a strange beast : it works as long as you never plan to do more than a single touch and you can depend on that. Otherwise, CurrentTouch gets the last touch, which in a multitouch scenario would be bad for your code; you might not get the ended state if there's a new or different touch id involved.
Nonetheless, I don't see anywhere you call ssP1:touched(touch), and use the touch.state property in your sprite class, but based on your previous commentary, you must call it at so e point.
Here is where I called the touch
Here is the state property being used inside the sprite class
This is driving me nuts, because it works a 50% of the time, but I cannot move forward with this app until I find a workaround which I think could be a timing issue of the execution.
I fix it with a walk around I added this conditional in the touched function
It's a particular solution but Codea doesn't handle well the touch.state triggering during runtime
I've read your post too hastily the first time, let's go on with a more profound analysis that tries to unravel your wrongdoing since I won't let you go with a comment like "Codea doesn't handle well the touch.state triggering during runtime" (except for an edge case that I look at a moment before).
Like aciolino mentioned you should avoid the CurrentTouch variable or at least make sure with a simple test program that it fulfills your needs. What we're not really seeing is the full program flow, starting with the global functions draw() and touched().
Look at this part of the code:
Where do you execute this? When? I hope not when flying == "P1", in this case you would call this very often. Or do you set flying to a different value later on? Is it necessary to draw ssP1 after creation? There should be a separate code section concerned with drawing the sprite that is independent of the code section where it is created.
Your work around operates diffently from your original intention.
Original (abbreviated):
You original solution requires you to move your finger and not just touch the sprite to execute the action.
Your work around:
You're calling btnSymbPRO1pressed (why not the associated sprite action?) now when the touch ended which includes tapping without dragging. I thought this was somewhat essential.
I assume you've got a wrong event flow in mind, so please provide more context so we have a chance to repair it.
Codeslinger thanks for your response; I agree with your statement that this could be generated by a wrong event flow made by me.
But let me try to explain what I am trying to do. The app has a menu with different symbols (a total of 9) each symbol is a Class treated as a Button, my intention is to select each sprite by dragging them out of the menu, then you move around the screen to select a position. When you release your finger (touch.state == ENDED) condition stores the position and id of each symbol on a table.
So my issue was that when I released the symbol sometimes the class action was executed and sometimes didn’t.
Answering your questions...
1) flying == "P1", is part of the Global Draw function, flying is just a control var to enable the drawing of the dragged symbol. Fixedy is just a modification to avoid drawing the symbol over the menu bars.
2) btnSymbPRO1pressed() is the function that is called with the action associated to the Class action I just added as a Plan B in case that the function was not triggered by the touch state condition.
You say when the touch.state == ENDED, you save the position and ID. Is the ID you're saving the touch.id . Once the touch state ends, the id isn't valid for anything anymore. Another touch can use the same id as a previous one that's ended. Even if you touch the same button, a new id or sometimes the same id will be used. The touch.id is valid only as long as the touch is in progress. I'm not sure if that might be your problem, but keep that in mind when using touch.id.
Not Dave the id is table I use to identify each symbol I am not using Multitouch.
Try this.
Thanks Mark let me try to go on that direction
Oh, and it would have probably been neater if I'd done the iteration in draw and touched using using for each. As in
Good luck!