diff --git a/content/base/src/nsContentUtils.cpp b/content/base/src/nsContentUtils.cpp
--- a/content/base/src/nsContentUtils.cpp
+++ b/content/base/src/nsContentUtils.cpp
@@ -502,7 +502,11 @@ nsContentUtils::InitializeEventTable() {
     { &nsGkAtoms::onMozRotateGestureUpdate,      { NS_SIMPLE_GESTURE_ROTATE_UPDATE, EventNameType_None } },
     { &nsGkAtoms::onMozRotateGesture,            { NS_SIMPLE_GESTURE_ROTATE, EventNameType_None } },
     { &nsGkAtoms::onMozTapGesture,               { NS_SIMPLE_GESTURE_TAP, EventNameType_None } },
-    { &nsGkAtoms::onMozPressTapGesture,          { NS_SIMPLE_GESTURE_PRESSTAP, EventNameType_None } }
+    { &nsGkAtoms::onMozPressTapGesture,          { NS_SIMPLE_GESTURE_PRESSTAP, EventNameType_None } },
+    
+    { &nsGkAtoms::onMozTouchDown,                { NS_MOZTOUCH_DOWN, EventNameType_None } },
+    { &nsGkAtoms::onMozTouchMove,                { NS_MOZTOUCH_MOVE, EventNameType_None } },
+    { &nsGkAtoms::onMozTouchRelease,             { NS_MOZTOUCH_RELEASE, EventNameType_None } }
   };
 
   sEventTable = new nsDataHashtable<nsISupportsHashKey, EventNameMapping>;
diff --git a/content/base/src/nsGkAtomList.h b/content/base/src/nsGkAtomList.h
--- a/content/base/src/nsGkAtomList.h
+++ b/content/base/src/nsGkAtomList.h
@@ -1498,6 +1498,10 @@ GK_ATOM(onMozRotateGesture, "onMozRotate
 GK_ATOM(onMozTapGesture, "onMozTapGesture")
 GK_ATOM(onMozPressTapGesture, "onMozPressTapGesture")
 
+GK_ATOM(onMozTouchDown, "onMozTouchDown")
+GK_ATOM(onMozTouchMove, "onMozTouchMove")
+GK_ATOM(onMozTouchRelease, "onMozTouchRelease")
+
 
 //---------------------------------------------------------------------------
 // Special atoms
diff --git a/content/events/public/nsIPrivateDOMEvent.h b/content/events/public/nsIPrivateDOMEvent.h
--- a/content/events/public/nsIPrivateDOMEvent.h
+++ b/content/events/public/nsIPrivateDOMEvent.h
@@ -115,4 +115,6 @@ NS_NewDOMNotifyPaintEvent(nsIDOMEvent** 
                           const nsRegion* aCrossDocRegion = nsnull);
 nsresult
 NS_NewDOMSimpleGestureEvent(nsIDOMEvent** aInstancePtrResult, nsPresContext* aPresContext, class nsSimpleGestureEvent* aEvent);
+nsresult
+NS_NewDOMMozTouchEvent(nsIDOMEvent** aInstancePtrResult, nsPresContext* aPresContext, class nsMozTouchEvent* aEvent);
 #endif // nsIPrivateDOMEvent_h__
diff --git a/content/events/src/Makefile.in b/content/events/src/Makefile.in
--- a/content/events/src/Makefile.in
+++ b/content/events/src/Makefile.in
@@ -97,6 +97,7 @@ CPPSRCS		= \
 		nsDOMNotifyPaintEvent.cpp \
 		nsDOMSimpleGestureEvent.cpp \
 		nsDOMEventTargetHelper.cpp \
+		nsDOMMozTouchEvent.cpp \
 		$(NULL)
 
 # we don't want the shared lib, but we want to force the creation of a static lib.
diff --git a/content/events/src/nsDOMEvent.cpp b/content/events/src/nsDOMEvent.cpp
--- a/content/events/src/nsDOMEvent.cpp
+++ b/content/events/src/nsDOMEvent.cpp
@@ -91,7 +91,10 @@ static const char* const sEventNames[] =
   "MozRotateGestureUpdate",
   "MozRotateGesture",
   "MozTapGesture",
-  "MozPressTapGesture"
+  "MozPressTapGesture",
+  "MozTouchDown",
+  "MozTouchMove",
+  "MozTouchRelease"
 };
 
 static char *sPopupAllowedEvents;
@@ -178,6 +181,7 @@ NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN(ns
       case NS_MOUSE_EVENT:
       case NS_MOUSE_SCROLL_EVENT:
       case NS_SIMPLE_GESTURE_EVENT:
+      case NS_MOZTOUCH_EVENT:
         static_cast<nsMouseEvent_base*>(tmp->mEvent)->relatedTarget = nsnull;
         break;
       case NS_DRAG_EVENT:
@@ -205,6 +209,7 @@ NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN(
       case NS_MOUSE_EVENT:
       case NS_MOUSE_SCROLL_EVENT:
       case NS_SIMPLE_GESTURE_EVENT:
+      case NS_MOZTOUCH_EVENT:
         NS_CYCLE_COLLECTION_NOTE_EDGE_NAME(cb, "mEvent->relatedTarget");
         cb.NoteXPCOMChild(
           static_cast<nsMouseEvent_base*>(tmp->mEvent)->relatedTarget);
@@ -675,6 +680,13 @@ nsDOMEvent::SetEventType(const nsAString
       mEvent->message = NS_SIMPLE_GESTURE_PRESSTAP;
     else if (atom == nsGkAtoms::onMozTapGesture)
       mEvent->message = NS_SIMPLE_GESTURE_TAP;
+  } else if (mEvent->eventStructType == NS_MOZTOUCH_EVENT) {
+    if (atom == nsGkAtoms::onMozTouchDown)
+      mEvent->message = NS_MOZTOUCH_DOWN;
+    else if (atom == nsGkAtoms::onMozTouchMove)
+      mEvent->message = NS_MOZTOUCH_MOVE;
+    else if (atom == nsGkAtoms::onMozTouchRelease)
+      mEvent->message = NS_MOZTOUCH_RELEASE;
   }
 
   if (mEvent->message == NS_USER_DEFINED_EVENT)
@@ -964,6 +976,14 @@ NS_METHOD nsDOMEvent::DuplicatePrivateDa
       newEvent = simpleGestureEvent;
       break;
     }
+    case NS_MOZTOUCH_EVENT:
+    {
+      newEvent = new nsMozTouchEvent(PR_FALSE, msg, nsnull,
+                                     static_cast<nsMozTouchEvent*>(mEvent)->streamId);
+      NS_ENSURE_TRUE(newEvent, NS_ERROR_OUT_OF_MEMORY);
+      isInputEvent = PR_TRUE;
+      break;
+    }
     default:
     {
       NS_WARNING("Unknown event type!!!");
@@ -1452,6 +1472,12 @@ const char* nsDOMEvent::GetEventName(PRU
     return sEventNames[eDOMEvents_MozTapGesture];
   case NS_SIMPLE_GESTURE_PRESSTAP:
     return sEventNames[eDOMEvents_MozPressTapGesture];
+  case NS_MOZTOUCH_DOWN:
+    return sEventNames[eDOMEvents_MozTouchDown];
+  case NS_MOZTOUCH_MOVE:
+    return sEventNames[eDOMEvents_MozTouchMove];
+  case NS_MOZTOUCH_RELEASE:
+    return sEventNames[eDOMEvents_MozTouchRelease];
   default:
     break;
   }
diff --git a/content/events/src/nsDOMEvent.h b/content/events/src/nsDOMEvent.h
--- a/content/events/src/nsDOMEvent.h
+++ b/content/events/src/nsDOMEvent.h
@@ -171,7 +171,10 @@ public:
     eDOMEvents_MozRotateGestureUpdate,
     eDOMEvents_MozRotateGesture,
     eDOMEvents_MozTapGesture,
-    eDOMEvents_MozPressTapGesture
+    eDOMEvents_MozPressTapGesture,
+    eDOMEvents_MozTouchDown,
+    eDOMEvents_MozTouchMove,
+    eDOMEvents_MozTouchRelease
   };
 
   nsDOMEvent(nsPresContext* aPresContext, nsEvent* aEvent);
diff --git a/content/events/src/nsDOMMozTouchEvent.cpp b/content/events/src/nsDOMMozTouchEvent.cpp
new file mode 100644
--- /dev/null
+++ b/content/events/src/nsDOMMozTouchEvent.cpp
@@ -0,0 +1,131 @@
+/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Thomas K. Dyas <tdyas@zecador.org>.
+ * Portions created by the Initial Developer are Copyright (C) 2008
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either the GNU General Public License Version 2 or later (the "GPL"), or
+ * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#include "nsDOMMozTouchEvent.h"
+#include "nsGUIEvent.h"
+#include "nsContentUtils.h"
+
+nsDOMMozTouchEvent::nsDOMMozTouchEvent(nsPresContext* aPresContext, nsMozTouchEvent* aEvent)
+  : nsDOMMouseEvent(aPresContext, aEvent ? aEvent : new nsMozTouchEvent(PR_FALSE, 0, nsnull, 0))
+{
+  NS_ASSERTION(mEvent->eventStructType == NS_MOZTOUCH_EVENT, "event type mismatch NS_MOZTOUCH_EVENT");
+
+  if (aEvent) {
+    mEventIsInternal = PR_FALSE;
+  } else {
+    mEventIsInternal = PR_TRUE;
+    mEvent->time = PR_Now();
+    mEvent->refPoint.x = mEvent->refPoint.y = 0;
+  }
+}
+
+nsDOMMozTouchEvent::~nsDOMMozTouchEvent()
+{
+  if (mEventIsInternal) {
+    delete static_cast<nsMozTouchEvent*>(mEvent);
+    mEvent = nsnull;
+  }
+}
+
+NS_IMPL_ADDREF_INHERITED(nsDOMMozTouchEvent, nsDOMMouseEvent)
+NS_IMPL_RELEASE_INHERITED(nsDOMMozTouchEvent, nsDOMMouseEvent)
+
+NS_INTERFACE_MAP_BEGIN(nsDOMMozTouchEvent)
+  NS_INTERFACE_MAP_ENTRY(nsIDOMMozTouchEvent)
+  NS_INTERFACE_MAP_ENTRY_CONTENT_CLASSINFO(MozTouchEvent)
+NS_INTERFACE_MAP_END_INHERITING(nsDOMMouseEvent)
+
+/* readonly attribute unsigned long steramId; */
+NS_IMETHODIMP
+nsDOMMozTouchEvent::GetStreamId(PRUint32 *aStreamId)
+{
+  NS_ENSURE_ARG_POINTER(aStreamId);
+  *aStreamId = static_cast<nsMozTouchEvent*>(mEvent)->streamId;
+  return NS_OK;
+}
+
+NS_IMETHODIMP
+nsDOMMozTouchEvent::InitMozTouchEvent(const nsAString& aTypeArg,
+                                                PRBool aCanBubbleArg,
+                                                PRBool aCancelableArg,
+                                                nsIDOMAbstractView* aViewArg,
+                                                PRInt32 aDetailArg,
+                                                PRInt32 aScreenX,
+                                                PRInt32 aScreenY,
+                                                PRInt32 aClientX,
+                                                PRInt32 aClientY,
+                                                PRBool aCtrlKeyArg,
+                                                PRBool aAltKeyArg,
+                                                PRBool aShiftKeyArg,
+                                                PRBool aMetaKeyArg,
+                                                PRUint16 aButton,
+                                                nsIDOMEventTarget* aRelatedTarget,
+                                                PRUint32 aStreamId)
+{
+  nsresult rv = nsDOMMouseEvent::InitMouseEvent(aTypeArg,
+                                                aCanBubbleArg,
+                                                aCancelableArg,
+                                                aViewArg,
+                                                aDetailArg,
+                                                aScreenX,
+                                                aScreenY,
+                                                aClientX,
+                                                aClientY,
+                                                aCtrlKeyArg,
+                                                aAltKeyArg,
+                                                aShiftKeyArg,
+                                                aMetaKeyArg,
+                                                aButton,
+                                                aRelatedTarget);
+  NS_ENSURE_SUCCESS(rv, rv);
+
+  nsMozTouchEvent* mozTouchEvent = static_cast<nsMozTouchEvent*>(mEvent);
+  mozTouchEvent->streamId = aStreamId;
+
+  return NS_OK;
+}
+
+nsresult NS_NewDOMMozTouchEvent(nsIDOMEvent** aInstancePtrResult,
+                                     nsPresContext* aPresContext,
+                                     nsMozTouchEvent *aEvent)
+{
+  nsDOMMozTouchEvent *it = new nsDOMMozTouchEvent(aPresContext, aEvent);
+  if (nsnull == it) {
+    return NS_ERROR_OUT_OF_MEMORY;
+  }
+  return CallQueryInterface(it, aInstancePtrResult);
+}
diff --git a/content/events/src/nsDOMMozTouchEvent.h b/content/events/src/nsDOMMozTouchEvent.h
new file mode 100644
--- /dev/null
+++ b/content/events/src/nsDOMMozTouchEvent.h
@@ -0,0 +1,60 @@
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Thomas K. Dyas <tdyas@zecador.org>.
+ * Portions created by the Initial Developer are Copyright (C) 2008
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either the GNU General Public License Version 2 or later (the "GPL"), or
+ * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+#ifndef nsDOMMozTouchEvent_h__
+#define nsDOMMozTouchEvent_h__
+
+#include "nsIDOMMozTouchEvent.h"
+#include "nsDOMMouseEvent.h"
+
+class nsPresContext;
+
+class nsDOMMozTouchEvent : public nsIDOMMozTouchEvent,
+                           public nsDOMMouseEvent
+{
+public:
+  nsDOMMozTouchEvent(nsPresContext*, nsMozTouchEvent*);
+  virtual ~nsDOMMozTouchEvent();
+
+  NS_DECL_ISUPPORTS_INHERITED
+
+  NS_DECL_NSIDOMMOZTOUCHEVENT
+
+  // Forward to base class
+  NS_FORWARD_TO_NSDOMMOUSEEVENT
+};
+
+#endif
diff --git a/content/events/src/nsDOMUIEvent.cpp b/content/events/src/nsDOMUIEvent.cpp
--- a/content/events/src/nsDOMUIEvent.cpp
+++ b/content/events/src/nsDOMUIEvent.cpp
@@ -151,6 +151,7 @@ nsDOMUIEvent::GetClientPoint()
       (mEvent->eventStructType != NS_MOUSE_EVENT &&
        mEvent->eventStructType != NS_POPUP_EVENT &&
        mEvent->eventStructType != NS_MOUSE_SCROLL_EVENT &&
+       mEvent->eventStructType != NS_MOZTOUCH_EVENT &&
        mEvent->eventStructType != NS_DRAG_EVENT &&
        mEvent->eventStructType != NS_SIMPLE_GESTURE_EVENT) ||
       !mPresContext ||
@@ -318,6 +319,7 @@ nsDOMUIEvent::GetLayerPoint()
       (mEvent->eventStructType != NS_MOUSE_EVENT &&
        mEvent->eventStructType != NS_POPUP_EVENT &&
        mEvent->eventStructType != NS_MOUSE_SCROLL_EVENT &&
+       mEvent->eventStructType != NS_MOZTOUCH_EVENT &&
        mEvent->eventStructType != NS_DRAG_EVENT &&
        mEvent->eventStructType != NS_SIMPLE_GESTURE_EVENT) ||
       !mPresContext ||
diff --git a/content/events/src/nsEventDispatcher.cpp b/content/events/src/nsEventDispatcher.cpp
--- a/content/events/src/nsEventDispatcher.cpp
+++ b/content/events/src/nsEventDispatcher.cpp
@@ -656,6 +656,9 @@ nsEventDispatcher::CreateEvent(nsPresCon
     case NS_SIMPLE_GESTURE_EVENT:
       return NS_NewDOMSimpleGestureEvent(aDOMEvent, aPresContext,
                                          static_cast<nsSimpleGestureEvent*>(aEvent));
+    case NS_MOZTOUCH_EVENT:
+      return NS_NewDOMMozTouchEvent(aDOMEvent, aPresContext,
+                                    static_cast<nsMozTouchEvent*>(aEvent));
     }
 
     // For all other types of events, create a vanilla event object.
@@ -720,6 +723,8 @@ nsEventDispatcher::CreateEvent(nsPresCon
     return NS_NewDOMBeforeUnloadEvent(aDOMEvent, aPresContext, nsnull);
   if (aEventType.LowerCaseEqualsLiteral("pagetransition"))
     return NS_NewDOMPageTransitionEvent(aDOMEvent, aPresContext, nsnull);
+  if (aEventType.LowerCaseEqualsLiteral("moztouchevent"))
+    return NS_NewDOMMozTouchEvent(aDOMEvent, aPresContext, nsnull);
 
   return NS_ERROR_DOM_NOT_SUPPORTED_ERR;
 }
diff --git a/content/events/src/nsEventStateManager.cpp b/content/events/src/nsEventStateManager.cpp
--- a/content/events/src/nsEventStateManager.cpp
+++ b/content/events/src/nsEventStateManager.cpp
@@ -1022,6 +1022,7 @@ nsEventStateManager::PreHandleEvent(nsPr
         mCurrentTargetContent = content;
     }
     break;
+
   case NS_MOUSE_SCROLL:
     {
       nsIContent* content = GetFocusedContent();
@@ -2285,6 +2286,37 @@ nsEventStateManager::SendLineScrollEvent
 }
 
 void
+nsEventStateManager::SendMozTouchEvent(nsIFrame* aTargetFrame,
+                                       nsMozTouchEvent* aEvent,
+                                       nsPresContext* aPresContext,
+                                       nsEventStatus* aStatus)
+{
+  nsCOMPtr<nsIContent> targetContent = aTargetFrame->GetContent();
+  if (!targetContent) {
+    targetContent = GetFocusedContent();
+    if (!targetContent)
+      return;
+  }
+
+  while (targetContent->IsNodeOfType(nsINode::eTEXT)) {
+    targetContent = targetContent->GetParent();
+  }
+
+  PRBool isTrusted = (aEvent->flags & NS_EVENT_FLAG_TRUSTED) != 0;
+  nsMozTouchEvent event(isTrusted, aEvent->message, nsnull, 0);
+  event.refPoint = aEvent->refPoint;
+  event.widget = aEvent->widget;
+  event.time = aEvent->time;
+  event.isShift = aEvent->isShift;
+  event.isControl = aEvent->isControl;
+  event.isAlt = aEvent->isAlt;
+  event.isMeta = aEvent->isMeta;
+  event.streamId = aEvent->streamId;
+
+  nsEventDispatcher::Dispatch(targetContent, aPresContext, &event, nsnull, aStatus);
+}
+
+void
 nsEventStateManager::SendPixelScrollEvent(nsIFrame* aTargetFrame,
                                           nsMouseScrollEvent* aEvent,
                                           nsPresContext* aPresContext,
@@ -2697,6 +2729,7 @@ nsEventStateManager::PostHandleEvent(nsP
       }
     }
     break;
+
   case NS_MOUSE_SCROLL:
   case NS_MOUSE_PIXEL_SCROLL:
     {
diff --git a/content/events/src/nsEventStateManager.h b/content/events/src/nsEventStateManager.h
--- a/content/events/src/nsEventStateManager.h
+++ b/content/events/src/nsEventStateManager.h
@@ -262,6 +262,10 @@ protected:
                             nsMouseScrollEvent* aEvent,
                             nsPresContext* aPresContext,
                             nsEventStatus* aStatus);
+  void SendMozTouchEvent(nsIFrame* aTargetFrame,
+                            nsMozTouchEvent* aEvent,
+                            nsPresContext* aPresContext,
+                            nsEventStatus* aStatus);
   typedef enum {
     eScrollByPixel,
     eScrollByLine,
diff --git a/dom/base/nsDOMClassInfo.cpp b/dom/base/nsDOMClassInfo.cpp
--- a/dom/base/nsDOMClassInfo.cpp
+++ b/dom/base/nsDOMClassInfo.cpp
@@ -462,6 +462,8 @@
 
 #include "nsIDOMNSMouseEvent.h"
 
+#include "nsIDOMMozTouchEvent.h"
+
 static NS_DEFINE_CID(kDOMSOF_CID, NS_DOM_SCRIPT_OBJECT_FACTORY_CID);
 
 static const char kDOMStringBundleURL[] =
@@ -1315,6 +1317,9 @@ static nsDOMClassInfoData sClassInfoData
   NS_DEFINE_CLASSINFO_DATA(CanvasRenderingContextGLWeb20, nsDOMGenericSH,
                            DOM_DEFAULT_SCRIPTABLE_FLAGS)
 #endif
+
+  NS_DEFINE_CLASSINFO_DATA(MozTouchEvent, nsDOMGenericSH,
+                           DOM_DEFAULT_SCRIPTABLE_FLAGS)
 };
 
 // Objects that shuld be constructable through |new Name();|
@@ -3618,6 +3623,13 @@ nsDOMClassInfo::Init()
   DOM_CLASSINFO_MAP_END
 #endif
 
+  DOM_CLASSINFO_MAP_BEGIN(MozTouchEvent, nsIDOMMozTouchEvent)
+    DOM_CLASSINFO_MAP_ENTRY(nsIDOMMozTouchEvent)
+    DOM_CLASSINFO_MAP_ENTRY(nsIDOMMouseEvent)
+    DOM_CLASSINFO_MAP_ENTRY(nsIDOMNSMouseEvent)
+    DOM_CLASSINFO_UI_EVENT_MAP_ENTRIES
+  DOM_CLASSINFO_MAP_END
+
 #ifdef NS_DEBUG
   {
     PRUint32 i = NS_ARRAY_LENGTH(sClassInfoData);
diff --git a/dom/base/nsDOMClassInfoID.h b/dom/base/nsDOMClassInfoID.h
--- a/dom/base/nsDOMClassInfoID.h
+++ b/dom/base/nsDOMClassInfoID.h
@@ -465,6 +465,8 @@ enum nsDOMClassInfoID {
   eDOMClassInfo_CanvasRenderingContextGLWeb20_id,
 #endif
 
+  eDOMClassInfo_MozTouchEvent_id,
+
   // This one better be the last one in this list
   eDOMClassInfoIDCount
 };
diff --git a/dom/interfaces/events/Makefile.in b/dom/interfaces/events/Makefile.in
--- a/dom/interfaces/events/Makefile.in
+++ b/dom/interfaces/events/Makefile.in
@@ -78,6 +78,7 @@ XPIDLSRCS =					\
 	nsIDOMNotifyPaintEvent.idl              \
 	nsIDOMSimpleGestureEvent.idl		\
 	nsIDOMNSMouseEvent.idl			\
+	nsIDOMMozTouchEvent.idl			\
 	$(NULL)
 
 include $(topsrcdir)/config/rules.mk
diff --git a/dom/interfaces/events/nsIDOMMozTouchEvent.idl b/dom/interfaces/events/nsIDOMMozTouchEvent.idl
new file mode 100644
--- /dev/null
+++ b/dom/interfaces/events/nsIDOMMozTouchEvent.idl
@@ -0,0 +1,63 @@
+/* -*- Mode: IDL; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* ***** BEGIN LICENSE BLOCK *****
+ * Version: MPL 1.1/GPL 2.0/LGPL 2.1
+ *
+ * The contents of this file are subject to the Mozilla Public License Version
+ * 1.1 (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ * http://www.mozilla.org/MPL/
+ *
+ * Software distributed under the License is distributed on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+ * for the specific language governing rights and limitations under the
+ * License.
+ *
+ * The Original Code is mozilla.org code.
+ *
+ * The Initial Developer of the Original Code is
+ * Thomas K. Dyas <tdyas@zecador.org>.
+ * Portions created by the Initial Developer are Copyright (C) 2008
+ * the Initial Developer. All Rights Reserved.
+ *
+ * Contributor(s):
+ *
+ * Alternatively, the contents of this file may be used under the terms of
+ * either the GNU General Public License Version 2 or later (the "GPL"), or
+ * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+ * in which case the provisions of the GPL or the LGPL are applicable instead
+ * of those above. If you wish to allow use of your version of this file only
+ * under the terms of either the GPL or the LGPL, and not to allow others to
+ * use your version of this file under the terms of the MPL, indicate your
+ * decision by deleting the provisions above and replace them with the notice
+ * and other provisions required by the GPL or the LGPL. If you do not delete
+ * the provisions above, a recipient may use your version of this file under
+ * the terms of any one of the MPL, the GPL or the LGPL.
+ *
+ * ***** END LICENSE BLOCK ***** */
+
+
+#include "nsIDOMMouseEvent.idl"
+
+
+[scriptable, uuid(cb68e879-f710-415d-a871-9a540860df01)]
+interface nsIDOMMozTouchEvent : nsIDOMMouseEvent
+{
+  readonly attribute unsigned long streamId;
+
+  void initMozTouchEvent(in DOMString typeArg,
+                              in boolean canBubbleArg,
+                              in boolean cancelableArg,
+                              in nsIDOMAbstractView viewArg,
+                              in long detailArg,
+                              in long screenXArg,
+                              in long screenYArg,
+                              in long clientXArg,
+                              in long clientYArg,
+                              in boolean ctrlKeyArg,
+                              in boolean altKeyArg,
+                              in boolean shiftKeyArg,
+                              in boolean metaKeyArg,
+                              in unsigned short buttonArg,
+                              in nsIDOMEventTarget relatedTargetArg,
+                              in unsigned long streamIdArg);
+};
diff --git a/layout/base/nsLayoutUtils.cpp b/layout/base/nsLayoutUtils.cpp
--- a/layout/base/nsLayoutUtils.cpp
+++ b/layout/base/nsLayoutUtils.cpp
@@ -648,6 +648,7 @@ nsLayoutUtils::GetEventCoordinatesRelati
                   aEvent->eventStructType != NS_MOUSE_SCROLL_EVENT &&
                   aEvent->eventStructType != NS_DRAG_EVENT &&
                   aEvent->eventStructType != NS_SIMPLE_GESTURE_EVENT &&
+                  aEvent->eventStructType != NS_MOZTOUCH_EVENT &&
                   aEvent->eventStructType != NS_QUERY_CONTENT_EVENT))
     return nsPoint(NS_UNCONSTRAINEDSIZE, NS_UNCONSTRAINEDSIZE);
 
diff --git a/widget/public/nsEvent.h b/widget/public/nsEvent.h
--- a/widget/public/nsEvent.h
+++ b/widget/public/nsEvent.h
@@ -88,6 +88,7 @@ class nsReconversionEvent;
 class nsTooltipEvent;
 class nsMenuEvent;
 class nsSimpleGestureEvent;
+class nsMozTouchEvent;
 
 struct nsTextEventReply;
 
diff --git a/widget/public/nsGUIEvent.h b/widget/public/nsGUIEvent.h
--- a/widget/public/nsGUIEvent.h
+++ b/widget/public/nsGUIEvent.h
@@ -104,6 +104,7 @@ class nsHashKey;
 #define NS_NOTIFYPAINT_EVENT              36
 #define NS_SIMPLE_GESTURE_EVENT           37
 #define NS_SELECTION_EVENT                38
+#define NS_MOZTOUCH_EVENT                 39
 
 // These flags are sort of a mess. They're sort of shared between event
 // listener flags and event flags, but only some of them. You've been
@@ -419,6 +420,10 @@ class nsHashKey;
 // Clear any previous selection and set the given range as the selection
 #define NS_SELECTION_SET                (NS_SELECTION_EVENT_START)
 
+#define NS_MOZTOUCH_EVENT_START  3800
+#define NS_MOZTOUCH_DOWN         (NS_MOZTOUCH_EVENT_START)
+#define NS_MOZTOUCH_MOVE         (NS_MOZTOUCH_EVENT_START+1)
+#define NS_MOZTOUCH_RELEASE      (NS_MOZTOUCH_EVENT_START+2)
 /**
  * Return status for event processors, nsEventStatus, is defined in
  * nsEvent.h.
@@ -1225,6 +1230,19 @@ public:
   PRFloat64 delta;      // Delta for magnify and rotate events
 };
 
+class nsMozTouchEvent : public nsMouseEvent_base
+{
+public:
+  nsMozTouchEvent(PRBool isTrusted, PRUint32 msg, nsIWidget* w,
+                  PRUint32 streamIdArg)
+    : nsMouseEvent_base(isTrusted, msg, w, NS_MOZTOUCH_EVENT),
+      streamId(streamIdArg)
+  {
+  }
+
+  PRUint32 streamId;
+};
+
 /**
  * Event status for D&D Event
  */
diff --git a/widget/src/windows/nsWindow.cpp b/widget/src/windows/nsWindow.cpp
--- a/widget/src/windows/nsWindow.cpp
+++ b/widget/src/windows/nsWindow.cpp
@@ -4244,7 +4244,7 @@ PRBool nsWindow::ProcessMessage(UINT msg
     result = PR_TRUE;
     *aRetValue = TABLET_ROTATE_GESTURE_ENABLE;
     break;
-    
+
   case WM_GESTURE:
     result = OnGesture(wParam, lParam);
     break;
