britzl / defold-input

Simplify input related operations such as gesture detection, input mapping and clicking/dragging game objects
MIT License
111 stars 26 forks source link

Multi touch gesture not clears it's state #43

Open Laminariy opened 2 weeks ago

Laminariy commented 2 weeks ago

There is issue in gesture module after last commit. Two finger gesture state not properly clears.

Problem:

if action.touch then
  if settings.multi_touch then
    if #action.touch == 2 then
      local t1 = action.touch[1]
      local t2 = action.touch[2]
      if current_touch_count < 2 then
        multi_states[t1.id] = create_touch_state()
        multi_states[t2.id] = create_touch_state()
        t1.pressed = true
        t2.pressed = true
      end
      handle_multi_touch(t1, t2) -- gesture state clears here
    end
    current_touch_count = #action.touch
    -- but if we get a multi-touch with one finger, it will not be cleared here
    -- the state will be saved from the previous two-finger gesture
    return gestures  
  end
end

Possible solution:

if action.touch then
  if settings.multi_touch then
    local was_handled = false -- save if multi touch gesture was handled
    if #action.touch == 2 then
      local t1 = action.touch[1]
      local t2 = action.touch[2]
      if current_touch_count < 2 then
        multi_states[t1.id] = create_touch_state()
        multi_states[t2.id] = create_touch_state()
        t1.pressed = true
        t2.pressed = true
      end
      was_handled = true -- gesture was handled
      handle_multi_touch(t1, t2)
    end
    current_touch_count = #action.touch
    if not was_handled then -- if not we manually clear gesture state
      clear_gesture_state()
    end
    return gestures
  end
end
britzl commented 2 weeks ago

Hmm, I don't get how the recent change makes a difference? Wasn't what you describe also a problem before?

The call to handle_multi_touch() (which in turn calls clear_gesture_state) is called under the same conditions both with the new and the old code.

Laminariy commented 2 weeks ago

Before this change, the gesture result was only returned if #action.touch == 2. Now it is returned even if this condition is not met.

How it was before:

if action.touch then
  if settings.multi_touch and #action.touch == 2 then
    handle_multi_touch(action)
    return gestures
  end

So maybe it would be more correct to return result only if #action.touch == 2

britzl commented 2 weeks ago

So maybe it would be more correct to return result only if #action.touch == 2

Or if the gesture state is cleared regardless of number of touch points? Like this:

https://github.com/britzl/defold-input/pull/45