Drag problem with scrollView

Hi bro
I am training to make drag in scrollviw.the shapes inside the scroll have touch listener also. The problem is the touch of shapes response when I make drag
I want the shape touch listening just on x axis just
How can I make it ?!

this is some part of my code


local function touchListener(  event )      if (event.phase == "began") then     end    if (event.phase == "moved") then          display.getCurrentStage():setFocus( event.target)     event.target.setFocus=true          print ("event.x" ..event.x)                  local dy = math.abs( ( event.y - event.yStart ) )         -- If the touch on the button has moved more than 10 pixels,         -- pass focus back to the scroll view so it can continue scrolling          if ( dy \>10) then scrollView:takeFocus( event )    ---here my issue  always dy  give 0 ?which e.y and e,ystart have same result                      else  event.target.x=event.x ...

I hope someone out there has a solution for you that is easy, but…

In my experience, it is a lot of work.

You can look at my vScroller code to see what I do. 

First, it is an unofficial and as yet undocumented part of SSK2.

Second, it is fully functional and solves the detect a touch on an object in a scroller issue while allowing scrolling.

Third, it is a WIP.  I’m tweaking in regularly as I use it more till I’m happy that it is flexible enough to be exposed.

Fourth, it is called vScroller, but it does detect both axes.  However it won’t suit your exactly stated needs.

You’ll simply have to look at it and see if it gives you some insights or inspiration.

Essentially, I have a convoluted dance between the scrollers listener, a listener on the objects in the scroller, a private table tracking these objects, and logic to detect if a drag has occurred and thus whether to treat the drag as a scroller drag or a tap on an object.

Finally, the vScroller code passes events to the scroller and to the individual objects that are under the touch.

Did I say this complicated?

Warning: It is NOT a standalone piece of code.

Here is a high-level usage example:

 local function onScroll( self, event ) --table.dump(event) if( event.phase == "ended") then if( event.dragged ) then --print("dragged") else --print("clicked") end end end local scroller = vScroller.new( display.currentStage, 0, 0, { w = width, h = height, autoScroll = false, listener = onScroll, backFill = hexcolor("0x101010"), hideBack = false } ) local obj = display.newCircle( 200, 200, 100 ) scroller:insert( obj ) local function onPress( self, event ) -- object's listener -- manually executed by vScroller logic end scroller:addTouch( obj , onPress )

Note: I’m a late comer to using widget.* lib.

I wrote my own before it was completed and use it to this day.  Except for scrollView which is superior to any solutions I’ve made.

Thus, my knowledge of widget.* may have gaps.

So,  I hope the prior post was a waste of time and someone here will have a easy and elegant solution for you.

Thank you bro for your advice.
Your code is very huge and default to me to get understand it.but thank you for your help at all

I want to understand the concept

*your code looks wrong from the begin to move phase, look at my code and compare it, please.

this is my touch event that i use on my objects:

menu={} function menu.addTouch (parametros) local params=parametros or {} local obj = params.obj or nil if not obj then print ("needs an object to add touch event") return nil end local func=params.func or nil local alphaInicial = params.alpha or obj.alpha local alphaPressed = params.alphaPressed or 1 local scrollView=params.scrollView or nil local return\_self=params.return\_self or false local color\_selected=params.color\_selected or nil local color=params.color or nil local function touch(self, event) if event.phase == "began" then display.getCurrentStage():setFocus( self, event.id ) self.isFocus = true self.alpha=alphaPressed if color and color\_selected then self:setFillColor(unpack(color\_selected)) end elseif self.isFocus then if event.phase == "moved" then if scrollView then local dy = math.abs( ( event.y - event.yStart ) ) if ( dy \> 5 ) then scrollView:takeFocus( event ) self.alpha=alphaInicial if color and color\_selected then self:setFillColor(unpack(color)) end end end elseif event.phase == "ended" or event.phase == "cancelled" then self.alpha=alphaInicial display.getCurrentStage():setFocus( self, nil ) self.isFocus = false if color and color\_selected then self:setFillColor(unpack(color)) end if func then if return\_self then func(self) else func() end end end end return true end obj.touch = touch obj:addEventListener( "touch", obj ) end

to give touch event inside a scrollView object you should do

( where scrollView is your scrollView object, obj is your object you want the touch inside the scrollView, func is the function called when you press that object)

menu.addTouch({obj=rectangle,func=CallFunction, scrollView=scrollView)

@carloscosta,

If you use that touch listener on an object in a scrollview, are you still able to:

  • click on the object
  • drag
  • have the scrollview scroll?

I see you have  a call to getFocus() in there and return true, which tells me the scrollview will never see the touch if you touch the object.

** UPDATE **

Sorry had a little trouble reading the code because of the tabs…

I see it seems you give the focus back to the scrollview at some point.  I guess I’ll have to give this a try.  Interesting.  Thanks for answering too.  I hope this gets haroon closer to a fix. 

Thanks for sharing as this is definitely shorter than mine (as well as not having the other issues I mentioned.)

Cheers,

Ed

roaminggamer,

  1. yes

  2. yes (you need to add more code to make the drag happen since this is only an addtouch code, but will work with point 1 and 3.)

  3. yes

@carloscosta Hi , I will try your code later then i will show my result . Thanks @carloscosta , @roaminggamer

I hope someone out there has a solution for you that is easy, but…

In my experience, it is a lot of work.

You can look at my vScroller code to see what I do. 

First, it is an unofficial and as yet undocumented part of SSK2.

Second, it is fully functional and solves the detect a touch on an object in a scroller issue while allowing scrolling.

Third, it is a WIP.  I’m tweaking in regularly as I use it more till I’m happy that it is flexible enough to be exposed.

Fourth, it is called vScroller, but it does detect both axes.  However it won’t suit your exactly stated needs.

You’ll simply have to look at it and see if it gives you some insights or inspiration.

Essentially, I have a convoluted dance between the scrollers listener, a listener on the objects in the scroller, a private table tracking these objects, and logic to detect if a drag has occurred and thus whether to treat the drag as a scroller drag or a tap on an object.

Finally, the vScroller code passes events to the scroller and to the individual objects that are under the touch.

Did I say this complicated?

Warning: It is NOT a standalone piece of code.

Here is a high-level usage example:

 local function onScroll( self, event ) --table.dump(event) if( event.phase == "ended") then if( event.dragged ) then --print("dragged") else --print("clicked") end end end local scroller = vScroller.new( display.currentStage, 0, 0, { w = width, h = height, autoScroll = false, listener = onScroll, backFill = hexcolor("0x101010"), hideBack = false } ) local obj = display.newCircle( 200, 200, 100 ) scroller:insert( obj ) local function onPress( self, event ) -- object's listener -- manually executed by vScroller logic end scroller:addTouch( obj , onPress )

Note: I’m a late comer to using widget.* lib.

I wrote my own before it was completed and use it to this day.  Except for scrollView which is superior to any solutions I’ve made.

Thus, my knowledge of widget.* may have gaps.

So,  I hope the prior post was a waste of time and someone here will have a easy and elegant solution for you.

Thank you bro for your advice.
Your code is very huge and default to me to get understand it.but thank you for your help at all

I want to understand the concept

*your code looks wrong from the begin to move phase, look at my code and compare it, please.

this is my touch event that i use on my objects:

menu={} function menu.addTouch (parametros) local params=parametros or {} local obj = params.obj or nil if not obj then print ("needs an object to add touch event") return nil end local func=params.func or nil local alphaInicial = params.alpha or obj.alpha local alphaPressed = params.alphaPressed or 1 local scrollView=params.scrollView or nil local return\_self=params.return\_self or false local color\_selected=params.color\_selected or nil local color=params.color or nil local function touch(self, event) if event.phase == "began" then display.getCurrentStage():setFocus( self, event.id ) self.isFocus = true self.alpha=alphaPressed if color and color\_selected then self:setFillColor(unpack(color\_selected)) end elseif self.isFocus then if event.phase == "moved" then if scrollView then local dy = math.abs( ( event.y - event.yStart ) ) if ( dy \> 5 ) then scrollView:takeFocus( event ) self.alpha=alphaInicial if color and color\_selected then self:setFillColor(unpack(color)) end end end elseif event.phase == "ended" or event.phase == "cancelled" then self.alpha=alphaInicial display.getCurrentStage():setFocus( self, nil ) self.isFocus = false if color and color\_selected then self:setFillColor(unpack(color)) end if func then if return\_self then func(self) else func() end end end end return true end obj.touch = touch obj:addEventListener( "touch", obj ) end

to give touch event inside a scrollView object you should do

( where scrollView is your scrollView object, obj is your object you want the touch inside the scrollView, func is the function called when you press that object)

menu.addTouch({obj=rectangle,func=CallFunction, scrollView=scrollView)

@carloscosta,

If you use that touch listener on an object in a scrollview, are you still able to:

  • click on the object
  • drag
  • have the scrollview scroll?

I see you have  a call to getFocus() in there and return true, which tells me the scrollview will never see the touch if you touch the object.

** UPDATE **

Sorry had a little trouble reading the code because of the tabs…

I see it seems you give the focus back to the scrollview at some point.  I guess I’ll have to give this a try.  Interesting.  Thanks for answering too.  I hope this gets haroon closer to a fix. 

Thanks for sharing as this is definitely shorter than mine (as well as not having the other issues I mentioned.)

Cheers,

Ed

roaminggamer,

  1. yes

  2. yes (you need to add more code to make the drag happen since this is only an addtouch code, but will work with point 1 and 3.)

  3. yes

@carloscosta Hi , I will try your code later then i will show my result . Thanks @carloscosta , @roaminggamer