Bug 990310 - Remove SurfaceDescriptor from media and GrallocImage r=nical,cajbir
[gecko.git] / widget / MouseEvents.h
blobd209cea9d5440d6b6e65d9cdb0ff7bceebcaa768
1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* This Source Code Form is subject to the terms of the Mozilla Public
3 * License, v. 2.0. If a copy of the MPL was not distributed with this
4 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 #ifndef mozilla_MouseEvents_h__
7 #define mozilla_MouseEvents_h__
9 #include <stdint.h>
11 #include "mozilla/BasicEvents.h"
12 #include "mozilla/MathAlgorithms.h"
13 #include "mozilla/dom/DataTransfer.h"
14 #include "nsCOMPtr.h"
15 #include "nsIDOMMouseEvent.h"
16 #include "nsIDOMWheelEvent.h"
18 /******************************************************************************
19 * nsDragDropEventStatus
20 ******************************************************************************/
22 enum nsDragDropEventStatus
24 // The event is a enter
25 nsDragDropEventStatus_eDragEntered,
26 // The event is exit
27 nsDragDropEventStatus_eDragExited,
28 // The event is drop
29 nsDragDropEventStatus_eDrop
32 namespace mozilla {
34 namespace dom {
35 class PBrowserParent;
36 class PBrowserChild;
37 } // namespace dom
39 /******************************************************************************
40 * mozilla::WidgetPointerHelper
41 ******************************************************************************/
43 class WidgetPointerHelper
45 public:
46 bool convertToPointer;
47 uint32_t pointerId;
48 uint32_t tiltX;
49 uint32_t tiltY;
51 WidgetPointerHelper() : convertToPointer(true), pointerId(0), tiltX(0), tiltY(0) {}
53 void AssignPointerHelperData(const WidgetPointerHelper& aEvent)
55 convertToPointer = aEvent.convertToPointer;
56 pointerId = aEvent.pointerId;
57 tiltX = aEvent.tiltX;
58 tiltY = aEvent.tiltY;
62 /******************************************************************************
63 * mozilla::WidgetMouseEventBase
64 ******************************************************************************/
66 class WidgetMouseEventBase : public WidgetInputEvent
68 private:
69 friend class dom::PBrowserParent;
70 friend class dom::PBrowserChild;
72 protected:
73 WidgetMouseEventBase()
77 WidgetMouseEventBase(bool aIsTrusted, uint32_t aMessage, nsIWidget* aWidget,
78 nsEventStructType aStructType) :
79 WidgetInputEvent(aIsTrusted, aMessage, aWidget, aStructType),
80 button(0), buttons(0), pressure(0),
81 inputSource(nsIDOMMouseEvent::MOZ_SOURCE_MOUSE)
85 public:
86 virtual WidgetMouseEventBase* AsMouseEventBase() MOZ_OVERRIDE { return this; }
88 virtual WidgetEvent* Duplicate() const MOZ_OVERRIDE
90 MOZ_CRASH("WidgetMouseEventBase must not be most-subclass");
91 return nullptr;
94 /// The possible related target
95 nsCOMPtr<nsISupports> relatedTarget;
97 enum buttonType
99 eLeftButton = 0,
100 eMiddleButton = 1,
101 eRightButton = 2
103 // Pressed button ID of mousedown or mouseup event.
104 // This is set only when pressing a button causes the event.
105 int16_t button;
107 enum buttonsFlag {
108 eLeftButtonFlag = 0x01,
109 eRightButtonFlag = 0x02,
110 eMiddleButtonFlag = 0x04,
111 // typicall, "back" button being left side of 5-button
112 // mice, see "buttons" attribute document of DOM3 Events.
113 e4thButtonFlag = 0x08,
114 // typicall, "forward" button being right side of 5-button
115 // mice, see "buttons" attribute document of DOM3 Events.
116 e5thButtonFlag = 0x10
119 // Flags of all pressed buttons at the event fired.
120 // This is set at any mouse event, don't be confused with |button|.
121 int16_t buttons;
123 // Finger or touch pressure of event. It ranges between 0.0 and 1.0.
124 float pressure;
126 // Possible values at nsIDOMMouseEvent
127 uint16_t inputSource;
129 void AssignMouseEventBaseData(const WidgetMouseEventBase& aEvent,
130 bool aCopyTargets)
132 AssignInputEventData(aEvent, aCopyTargets);
134 relatedTarget = aCopyTargets ? aEvent.relatedTarget : nullptr;
135 button = aEvent.button;
136 buttons = aEvent.buttons;
137 pressure = aEvent.pressure;
138 inputSource = aEvent.inputSource;
142 * Returns true if left click event.
144 bool IsLeftClickEvent() const
146 return message == NS_MOUSE_CLICK && button == eLeftButton;
150 /******************************************************************************
151 * mozilla::WidgetMouseEvent
152 ******************************************************************************/
154 class WidgetMouseEvent : public WidgetMouseEventBase, public WidgetPointerHelper
156 private:
157 friend class mozilla::dom::PBrowserParent;
158 friend class mozilla::dom::PBrowserChild;
160 public:
161 enum reasonType
163 eReal,
164 eSynthesized
167 enum contextType
169 eNormal,
170 eContextMenuKey
173 enum exitType
175 eChild,
176 eTopLevel
179 protected:
180 WidgetMouseEvent()
184 WidgetMouseEvent(bool aIsTrusted, uint32_t aMessage, nsIWidget* aWidget,
185 nsEventStructType aStructType, reasonType aReason) :
186 WidgetMouseEventBase(aIsTrusted, aMessage, aWidget, aStructType),
187 acceptActivation(false), ignoreRootScrollFrame(false),
188 reason(aReason), context(eNormal), exit(eChild), clickCount(0)
190 switch (aMessage) {
191 case NS_MOUSE_MOVE:
192 mFlags.mCancelable = false;
193 break;
194 case NS_MOUSEENTER:
195 case NS_MOUSELEAVE:
196 mFlags.mBubbles = false;
197 mFlags.mCancelable = false;
198 break;
199 default:
200 break;
204 public:
205 virtual WidgetMouseEvent* AsMouseEvent() MOZ_OVERRIDE { return this; }
207 WidgetMouseEvent(bool aIsTrusted, uint32_t aMessage, nsIWidget* aWidget,
208 reasonType aReason, contextType aContext = eNormal) :
209 WidgetMouseEventBase(aIsTrusted, aMessage, aWidget, NS_MOUSE_EVENT),
210 acceptActivation(false), ignoreRootScrollFrame(false),
211 reason(aReason), context(aContext), exit(eChild), clickCount(0)
213 switch (aMessage) {
214 case NS_MOUSE_MOVE:
215 mFlags.mCancelable = false;
216 break;
217 case NS_MOUSEENTER:
218 case NS_MOUSELEAVE:
219 mFlags.mBubbles = false;
220 mFlags.mCancelable = false;
221 break;
222 case NS_CONTEXTMENU:
223 button = (context == eNormal) ? eRightButton : eLeftButton;
224 break;
225 default:
226 break;
230 #ifdef DEBUG
231 virtual ~WidgetMouseEvent()
233 NS_WARN_IF_FALSE(message != NS_CONTEXTMENU ||
234 button ==
235 ((context == eNormal) ? eRightButton : eLeftButton),
236 "Wrong button set to NS_CONTEXTMENU event?");
238 #endif
240 virtual WidgetEvent* Duplicate() const MOZ_OVERRIDE
242 MOZ_ASSERT(eventStructType == NS_MOUSE_EVENT,
243 "Duplicate() must be overridden by sub class");
244 // Not copying widget, it is a weak reference.
245 WidgetMouseEvent* result =
246 new WidgetMouseEvent(false, message, nullptr, reason, context);
247 result->AssignMouseEventData(*this, true);
248 result->mFlags = mFlags;
249 return result;
252 // Special return code for MOUSE_ACTIVATE to signal.
253 // If the target accepts activation (1), or denies it (0).
254 bool acceptActivation;
255 // Whether the event should ignore scroll frame bounds during dispatch.
256 bool ignoreRootScrollFrame;
258 reasonType reason : 4;
259 contextType context : 4;
260 exitType exit;
262 /// The number of mouse clicks.
263 uint32_t clickCount;
265 void AssignMouseEventData(const WidgetMouseEvent& aEvent, bool aCopyTargets)
267 AssignMouseEventBaseData(aEvent, aCopyTargets);
268 AssignPointerHelperData(aEvent);
270 acceptActivation = aEvent.acceptActivation;
271 ignoreRootScrollFrame = aEvent.ignoreRootScrollFrame;
272 clickCount = aEvent.clickCount;
276 * Returns true if the event is a context menu event caused by key.
278 bool IsContextMenuKeyEvent() const
280 return message == NS_CONTEXTMENU && context == eContextMenuKey;
284 * Returns true if the event is a real mouse event. Otherwise, i.e., it's
285 * a synthesized event by scroll or something, returns false.
287 bool IsReal() const
289 return reason == eReal;
293 /******************************************************************************
294 * mozilla::WidgetDragEvent
295 ******************************************************************************/
297 class WidgetDragEvent : public WidgetMouseEvent
299 public:
300 virtual WidgetDragEvent* AsDragEvent() MOZ_OVERRIDE { return this; }
302 WidgetDragEvent(bool aIsTrusted, uint32_t aMessage, nsIWidget* aWidget) :
303 WidgetMouseEvent(aIsTrusted, aMessage, aWidget, NS_DRAG_EVENT, eReal),
304 userCancelled(false), mDefaultPreventedOnContent(false)
306 mFlags.mCancelable =
307 (aMessage != NS_DRAGDROP_EXIT_SYNTH &&
308 aMessage != NS_DRAGDROP_LEAVE_SYNTH &&
309 aMessage != NS_DRAGDROP_END);
312 virtual WidgetEvent* Duplicate() const MOZ_OVERRIDE
314 MOZ_ASSERT(eventStructType == NS_DRAG_EVENT,
315 "Duplicate() must be overridden by sub class");
316 // Not copying widget, it is a weak reference.
317 WidgetDragEvent* result = new WidgetDragEvent(false, message, nullptr);
318 result->AssignDragEventData(*this, true);
319 result->mFlags = mFlags;
320 return result;
323 // The dragging data.
324 nsCOMPtr<dom::DataTransfer> dataTransfer;
326 // If this is true, user has cancelled the drag operation.
327 bool userCancelled;
328 // If this is true, the drag event's preventDefault() is called on content.
329 bool mDefaultPreventedOnContent;
331 // XXX Not tested by test_assign_event_data.html
332 void AssignDragEventData(const WidgetDragEvent& aEvent, bool aCopyTargets)
334 AssignMouseEventData(aEvent, aCopyTargets);
336 dataTransfer = aEvent.dataTransfer;
337 // XXX userCancelled isn't copied, is this instentionally?
338 userCancelled = false;
339 mDefaultPreventedOnContent = aEvent.mDefaultPreventedOnContent;
343 /******************************************************************************
344 * mozilla::WidgetMouseScrollEvent
346 * This is used for legacy DOM mouse scroll events, i.e.,
347 * DOMMouseScroll and MozMousePixelScroll event. These events are NOT hanbled
348 * by ESM even if widget dispatches them. Use new WidgetWheelEvent instead.
349 ******************************************************************************/
351 class WidgetMouseScrollEvent : public WidgetMouseEventBase
353 private:
354 WidgetMouseScrollEvent()
358 public:
359 virtual WidgetMouseScrollEvent* AsMouseScrollEvent() MOZ_OVERRIDE
361 return this;
364 WidgetMouseScrollEvent(bool aIsTrusted, uint32_t aMessage,
365 nsIWidget* aWidget) :
366 WidgetMouseEventBase(aIsTrusted, aMessage, aWidget, NS_MOUSE_SCROLL_EVENT),
367 delta(0), isHorizontal(false)
371 virtual WidgetEvent* Duplicate() const MOZ_OVERRIDE
373 MOZ_ASSERT(eventStructType == NS_MOUSE_SCROLL_EVENT,
374 "Duplicate() must be overridden by sub class");
375 // Not copying widget, it is a weak reference.
376 WidgetMouseScrollEvent* result =
377 new WidgetMouseScrollEvent(false, message, nullptr);
378 result->AssignMouseScrollEventData(*this, true);
379 result->mFlags = mFlags;
380 return result;
383 // The delta value of mouse scroll event.
384 // If the event message is NS_MOUSE_SCROLL, the value indicates scroll amount
385 // in lines. However, if the value is nsIDOMUIEvent::SCROLL_PAGE_UP or
386 // nsIDOMUIEvent::SCROLL_PAGE_DOWN, the value inducates one page scroll.
387 // If the event message is NS_MOUSE_PIXEL_SCROLL, the value indicates scroll
388 // amount in pixels.
389 int32_t delta;
391 // If this is true, it may cause to scroll horizontally.
392 // Otherwise, vertically.
393 bool isHorizontal;
395 void AssignMouseScrollEventData(const WidgetMouseScrollEvent& aEvent,
396 bool aCopyTargets)
398 AssignMouseEventBaseData(aEvent, aCopyTargets);
400 delta = aEvent.delta;
401 isHorizontal = aEvent.isHorizontal;
405 /******************************************************************************
406 * mozilla::WidgetWheelEvent
407 ******************************************************************************/
409 class WidgetWheelEvent : public WidgetMouseEventBase
411 private:
412 friend class mozilla::dom::PBrowserParent;
413 friend class mozilla::dom::PBrowserChild;
415 WidgetWheelEvent()
419 public:
420 virtual WidgetWheelEvent* AsWheelEvent() MOZ_OVERRIDE { return this; }
422 WidgetWheelEvent(bool aIsTrusted, uint32_t aMessage, nsIWidget* aWidget) :
423 WidgetMouseEventBase(aIsTrusted, aMessage, aWidget, NS_WHEEL_EVENT),
424 deltaX(0.0), deltaY(0.0), deltaZ(0.0),
425 deltaMode(nsIDOMWheelEvent::DOM_DELTA_PIXEL),
426 customizedByUserPrefs(false), isMomentum(false), isPixelOnlyDevice(false),
427 lineOrPageDeltaX(0), lineOrPageDeltaY(0), scrollType(SCROLL_DEFAULT),
428 overflowDeltaX(0.0), overflowDeltaY(0.0),
429 mViewPortIsOverscrolled(false)
433 virtual WidgetEvent* Duplicate() const MOZ_OVERRIDE
435 MOZ_ASSERT(eventStructType == NS_WHEEL_EVENT,
436 "Duplicate() must be overridden by sub class");
437 // Not copying widget, it is a weak reference.
438 WidgetWheelEvent* result = new WidgetWheelEvent(false, message, nullptr);
439 result->AssignWheelEventData(*this, true);
440 result->mFlags = mFlags;
441 return result;
444 // NOTE: deltaX, deltaY and deltaZ may be customized by
445 // mousewheel.*.delta_multiplier_* prefs which are applied by
446 // EventStateManager. So, after widget dispatches this event,
447 // these delta values may have different values than before.
448 double deltaX;
449 double deltaY;
450 double deltaZ;
452 // Should be one of nsIDOMWheelEvent::DOM_DELTA_*
453 uint32_t deltaMode;
455 // Following members are for internal use only, not for DOM event.
457 // If the delta values are computed from prefs, this value is true.
458 // Otherwise, i.e., they are computed from native events, false.
459 bool customizedByUserPrefs;
461 // true if the event is caused by momentum.
462 bool isMomentum;
464 // If device event handlers don't know when they should set lineOrPageDeltaX
465 // and lineOrPageDeltaY, this is true. Otherwise, false.
466 // If isPixelOnlyDevice is true, ESM will generate NS_MOUSE_SCROLL events
467 // when accumulated pixel delta values reach a line height.
468 bool isPixelOnlyDevice;
470 // If widget sets lineOrPageDelta, EventStateManager will dispatch
471 // NS_MOUSE_SCROLL event for compatibility. Note that the delta value means
472 // pages if the deltaMode is DOM_DELTA_PAGE, otherwise, lines.
473 int32_t lineOrPageDeltaX;
474 int32_t lineOrPageDeltaY;
476 // When the default action for an wheel event is moving history or zooming,
477 // need to chose a delta value for doing it.
478 int32_t GetPreferredIntDelta()
480 if (!lineOrPageDeltaX && !lineOrPageDeltaY) {
481 return 0;
483 if (lineOrPageDeltaY && !lineOrPageDeltaX) {
484 return lineOrPageDeltaY;
486 if (lineOrPageDeltaX && !lineOrPageDeltaY) {
487 return lineOrPageDeltaX;
489 if ((lineOrPageDeltaX < 0 && lineOrPageDeltaY > 0) ||
490 (lineOrPageDeltaX > 0 && lineOrPageDeltaY < 0)) {
491 return 0; // We cannot guess the answer in this case.
493 return (Abs(lineOrPageDeltaX) > Abs(lineOrPageDeltaY)) ?
494 lineOrPageDeltaX : lineOrPageDeltaY;
497 // Scroll type
498 // The default value is SCROLL_DEFAULT, which means EventStateManager will
499 // select preferred scroll type automatically.
500 enum ScrollType
502 SCROLL_DEFAULT,
503 SCROLL_SYNCHRONOUSLY,
504 SCROLL_ASYNCHRONOUSELY,
505 SCROLL_SMOOTHLY
507 ScrollType scrollType;
509 // overflowed delta values for scroll, these values are set by
510 // nsEventStateManger. If the default action of the wheel event isn't scroll,
511 // these values always zero. Otherwise, remaning delta values which are
512 // not used by scroll are set.
513 // NOTE: deltaX, deltaY and deltaZ may be modified by EventStateManager.
514 // However, overflowDeltaX and overflowDeltaY indicate unused original
515 // delta values which are not applied the delta_multiplier prefs.
516 // So, if widget wanted to know the actual direction to be scrolled,
517 // it would need to check the deltaX and deltaY.
518 double overflowDeltaX;
519 double overflowDeltaY;
521 // Whether or not the parent of the currently overscrolled frame is the
522 // ViewPort. This is false in situations when an element on the page is being
523 // overscrolled (such as a text field), but true when the 'page' is being
524 // overscrolled.
525 bool mViewPortIsOverscrolled;
527 void AssignWheelEventData(const WidgetWheelEvent& aEvent, bool aCopyTargets)
529 AssignMouseEventBaseData(aEvent, aCopyTargets);
531 deltaX = aEvent.deltaX;
532 deltaY = aEvent.deltaY;
533 deltaZ = aEvent.deltaZ;
534 deltaMode = aEvent.deltaMode;
535 customizedByUserPrefs = aEvent.customizedByUserPrefs;
536 isMomentum = aEvent.isMomentum;
537 isPixelOnlyDevice = aEvent.isPixelOnlyDevice;
538 lineOrPageDeltaX = aEvent.lineOrPageDeltaX;
539 lineOrPageDeltaY = aEvent.lineOrPageDeltaY;
540 scrollType = aEvent.scrollType;
541 overflowDeltaX = aEvent.overflowDeltaX;
542 overflowDeltaY = aEvent.overflowDeltaY;
543 mViewPortIsOverscrolled = aEvent.mViewPortIsOverscrolled;
547 /******************************************************************************
548 * mozilla::WidgetPointerEvent
549 ******************************************************************************/
551 class WidgetPointerEvent : public WidgetMouseEvent
553 friend class mozilla::dom::PBrowserParent;
554 friend class mozilla::dom::PBrowserChild;
556 WidgetPointerEvent()
560 public:
561 virtual WidgetPointerEvent* AsPointerEvent() MOZ_OVERRIDE { return this; }
563 WidgetPointerEvent(bool aIsTrusted, uint32_t aMsg, nsIWidget* w)
564 : WidgetMouseEvent(aIsTrusted, aMsg, w, NS_POINTER_EVENT, eReal)
565 , width(0)
566 , height(0)
567 , isPrimary(true)
569 UpdateFlags();
572 WidgetPointerEvent(const WidgetMouseEvent& aEvent)
573 : WidgetMouseEvent(aEvent)
574 , width(0)
575 , height(0)
576 , isPrimary(true)
578 eventStructType = NS_POINTER_EVENT;
579 UpdateFlags();
582 void UpdateFlags()
584 switch (message) {
585 case NS_POINTER_ENTER:
586 case NS_POINTER_LEAVE:
587 mFlags.mBubbles = false;
588 mFlags.mCancelable = false;
589 break;
590 case NS_POINTER_CANCEL:
591 case NS_POINTER_GOT_CAPTURE:
592 case NS_POINTER_LOST_CAPTURE:
593 mFlags.mCancelable = false;
594 break;
595 default:
596 break;
600 virtual WidgetEvent* Duplicate() const MOZ_OVERRIDE
602 MOZ_ASSERT(eventStructType == NS_POINTER_EVENT,
603 "Duplicate() must be overridden by sub class");
604 // Not copying widget, it is a weak reference.
605 WidgetPointerEvent* result =
606 new WidgetPointerEvent(false, message, nullptr);
607 result->AssignPointerEventData(*this, true);
608 result->mFlags = mFlags;
609 return result;
612 uint32_t width;
613 uint32_t height;
614 bool isPrimary;
616 // XXX Not tested by test_assign_event_data.html
617 void AssignPointerEventData(const WidgetPointerEvent& aEvent,
618 bool aCopyTargets)
620 AssignMouseEventData(aEvent, aCopyTargets);
622 width = aEvent.width;
623 height = aEvent.height;
624 isPrimary = aEvent.isPrimary;
628 } // namespace mozilla
630 #endif // mozilla_MouseEvents_h__