Store the originating target for a touch (i.e. calculated in touchstart) in a hash map, so that we can use that originating target as the target for future move/end/cancel events that that touch generates.

This matches the behaviour that the iPhone exhibits.

Change-Id: Iff5e29c795b8ae6128e67ad5d42a959b61f966f2
diff --git a/WebCore/page/EventHandler.cpp b/WebCore/page/EventHandler.cpp
index 51cf675..2563149 100644
--- a/WebCore/page/EventHandler.cpp
+++ b/WebCore/page/EventHandler.cpp
@@ -2595,6 +2595,20 @@
         int adjustedPageX = lroundf(pagePoint.x() / m_frame->pageZoomFactor());
         int adjustedPageY = lroundf(pagePoint.y() / m_frame->pageZoomFactor());
 
+        // ANDROID
+        // The touch event should act on the originating touch target, not the current target
+        // TODO: Upstream this fix to webkit.org (see webkit bug 34585)
+        int touchPointId = point.id();
+        if (point.state() == PlatformTouchPoint::TouchPressed)
+            m_originatingTouchPointTargets.set(touchPointId, target);
+
+        EventTarget* touchTarget = m_originatingTouchPointTargets.get(touchPointId).get();
+        ASSERT(touchTarget);
+
+        RefPtr<Touch> touch = Touch::create(doc->frame(), touchTarget, touchPointId,
+                                            point.screenPos().x(), point.screenPos().y(),
+                                            adjustedPageX, adjustedPageY);
+
         if ((event.type() == TouchStart
 #if PLATFORM(ANDROID)
             || event.type() == TouchDoubleTap
@@ -2606,13 +2620,6 @@
             m_firstTouchPagePos = pagePoint;
         }
 
-        // ANDROID
-        // The touch event should act on m_touchEventTarget, not target
-        // TODO: Upstream this fix to webkit.org
-        RefPtr<Touch> touch = Touch::create(doc->frame(), m_touchEventTarget.get(), point.id(),
-                                            point.screenPos().x(), point.screenPos().y(),
-                                            adjustedPageX, adjustedPageY);
-
         if (point.state() == PlatformTouchPoint::TouchReleased)
             releasedTouches->append(touch);
         else if (point.state() == PlatformTouchPoint::TouchCancelled)
diff --git a/WebCore/page/EventHandler.h b/WebCore/page/EventHandler.h
index 861dce9..e871f61 100644
--- a/WebCore/page/EventHandler.h
+++ b/WebCore/page/EventHandler.h
@@ -37,12 +37,17 @@
 class NSView;
 #endif
 
+#if ENABLE(TOUCH_EVENTS) // ANDROID addition, needs to be upstreamed. (see webkit bug 34585)
+#include <wtf/HashMap.h>
+#endif
+
 namespace WebCore {
 
 class AtomicString;
 class Clipboard;
 class Cursor;
 class Event;
+class EventTarget;
 class FloatPoint;
 class Frame;
 class HitTestRequest;
@@ -423,6 +428,9 @@
     int m_activationEventNumber;
 #endif
 #if ENABLE(TOUCH_EVENTS)
+    // ANDROID fix to be upstreamed, see webkit bug 34585.
+    typedef HashMap<int, RefPtr<EventTarget> > TouchTargetMap;
+    TouchTargetMap m_originatingTouchPointTargets;
     RefPtr<Node> m_touchEventTarget;
     IntPoint m_firstTouchScreenPos;
     IntPoint m_firstTouchPagePos;