Skip to content
Closed
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions src/browser/ReactEventEmitter.js
Original file line number Diff line number Diff line change
Expand Up @@ -113,6 +113,12 @@ var topEventMapping = {
topMouseOver: 'mouseover',
topMouseUp: 'mouseup',
topPaste: 'paste',
topPointerCancel: 'pointercancel',
topPointerDown: 'pointerdown',
topPointerMove: 'pointermove',
topPointerOut: 'pointerout',
topPointerOver: 'pointerover',
topPointerUp: 'pointerup',
topScroll: 'scroll',
topSelectionChange: 'selectionchange',
topTextInput: 'textInput',
Expand Down
72 changes: 59 additions & 13 deletions src/browser/eventPlugins/EnterLeaveEventPlugin.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@
var EventConstants = require('EventConstants');
var EventPropagators = require('EventPropagators');
var SyntheticMouseEvent = require('SyntheticMouseEvent');
var SyntheticPointerEvent = require('SyntheticPointerEvent');

var ReactMount = require('ReactMount');
var keyOf = require('keyOf');
Expand All @@ -43,6 +44,20 @@ var eventTypes = {
topLevelTypes.topMouseOut,
topLevelTypes.topMouseOver
]
},
pointerEnter: {
registrationName: keyOf({onPointerEnter: null}),
dependencies: [
topLevelTypes.topPointerOut,
topLevelTypes.topPointerOver
]
},
pointerLeave: {
registrationName: keyOf({onPointerLeave: null}),
dependencies: [
topLevelTypes.topPointerOut,
topLevelTypes.topPointerOver
]
}
};

Expand Down Expand Up @@ -71,15 +86,29 @@ var EnterLeaveEventPlugin = {
topLevelTarget,
topLevelTargetID,
nativeEvent) {
if (topLevelType === topLevelTypes.topMouseOver &&
(nativeEvent.relatedTarget || nativeEvent.fromElement)) {
var isMouseEvent = (
topLevelType === topLevelTypes.topMouseOut ||
topLevelType === topLevelTypes.topMouseOver
);
var isPointerEvent = (
topLevelType === topLevelTypes.topPointerOut ||
topLevelType === topLevelTypes.topPointerOver
);
if (!isMouseEvent && !isPointerEvent) {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

if you move isOverEvent and isOutEvent up, I think this can just be if (isOverEvent || isOutEvent)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@spicyj It can be, but I still need to be able to separate isMouseEvent from isPointerEvent further down below. I guess we technically can save one unnecessary evaluation if we exit early at line 105. But other than that it should be identical, doesn't hurt though I guess :)

// Must not be a mouse/pointer in or out - ignoring.
return null;
}
if (topLevelType !== topLevelTypes.topMouseOut &&
topLevelType !== topLevelTypes.topMouseOver) {
// Must not be a mouse in or mouse out - ignoring.
var isOverEvent = (
topLevelType === topLevelTypes.topMouseOver ||
topLevelType === topLevelTypes.topPointerOver
);
if (isOverEvent && (nativeEvent.relatedTarget || nativeEvent.fromElement)) {
return null;
}
var isOutEvent = (
topLevelType === topLevelTypes.topMouseOut ||
topLevelType === topLevelTypes.topPointerOut
);

var win;
if (topLevelTarget.window === topLevelTarget) {
Expand All @@ -96,7 +125,7 @@ var EnterLeaveEventPlugin = {
}

var from, to;
if (topLevelType === topLevelTypes.topMouseOut) {
if (isOutEvent) {
from = topLevelTarget;
to =
getFirstReactDOM(nativeEvent.relatedTarget || nativeEvent.toElement) ||
Expand All @@ -114,21 +143,38 @@ var EnterLeaveEventPlugin = {
var fromID = from ? ReactMount.getID(from) : '';
var toID = to ? ReactMount.getID(to) : '';

var leave = SyntheticMouseEvent.getPooled(
eventTypes.mouseLeave,
var syntheticEventInterface,
leaveEventType,
enterEventType,
eventTypePrefix;

if (isMouseEvent) {
syntheticEventInterface = SyntheticMouseEvent;
leaveEventType = eventTypes.mouseLeave;
enterEventType = eventTypes.mouseEnter;
eventTypePrefix = 'mouse';
} else if (isPointerEvent) {
syntheticEventInterface = SyntheticPointerEvent;
leaveEventType = eventTypes.pointerLeave;
enterEventType = eventTypes.pointerEnter;
eventTypePrefix = 'pointer';
}

var leave = syntheticEventInterface.getPooled(
leaveEventType,
fromID,
nativeEvent
);
leave.type = 'mouseleave';
leave.type = eventTypePrefix + 'leave';
leave.target = from;
leave.relatedTarget = to;

var enter = SyntheticMouseEvent.getPooled(
eventTypes.mouseEnter,
toID,
var enter = syntheticEventInterface.getPooled(
enterEventType,
fromID,
nativeEvent
);
enter.type = 'mouseenter';
enter.type = eventTypePrefix + 'enter';
enter.target = to;
enter.relatedTarget = from;

Expand Down
115 changes: 83 additions & 32 deletions src/browser/eventPlugins/SimpleEventPlugin.js
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ var SyntheticDragEvent = require('SyntheticDragEvent');
var SyntheticTouchEvent = require('SyntheticTouchEvent');
var SyntheticUIEvent = require('SyntheticUIEvent');
var SyntheticWheelEvent = require('SyntheticWheelEvent');
var SyntheticPointerEvent = require('SyntheticPointerEvent');

var invariant = require('invariant');
var keyOf = require('keyOf');
Expand Down Expand Up @@ -201,6 +202,42 @@ var eventTypes = {
captured: keyOf({onPasteCapture: true})
}
},
pointerCancel: {
phasedRegistrationNames: {
bubbled: keyOf({onPointerCancel: true}),
captured: keyOf({onPointerCancelCapture: true})
}
},
pointerDown: {
phasedRegistrationNames: {
bubbled: keyOf({onPointerDown: true}),
captured: keyOf({onPointerDownCapture: true})
}
},
pointerMove: {
phasedRegistrationNames: {
bubbled: keyOf({onPointerMove: true}),
captured: keyOf({onPointerMoveCapture: true})
}
},
pointerOut: {
phasedRegistrationNames: {
bubbled: keyOf({onPointerOut: true}),
captured: keyOf({onPointerOutCapture: true})
}
},
pointerOver: {
phasedRegistrationNames: {
bubbled: keyOf({onPointerOver: true}),
captured: keyOf({onPointerOverCapture: true})
}
},
pointerUp: {
phasedRegistrationNames: {
bubbled: keyOf({onPointerUp: true}),
captured: keyOf({onPointerUpCapture: true})
}
},
reset: {
phasedRegistrationNames: {
bubbled: keyOf({onReset: true}),
Expand Down Expand Up @@ -252,41 +289,47 @@ var eventTypes = {
};

var topLevelEventsToDispatchConfig = {
topBlur: eventTypes.blur,
topClick: eventTypes.click,
topBlur: eventTypes.blur,
topClick: eventTypes.click,
topContextMenu: eventTypes.contextMenu,
topCopy: eventTypes.copy,
topCut: eventTypes.cut,
topCopy: eventTypes.copy,
topCut: eventTypes.cut,
topDoubleClick: eventTypes.doubleClick,
topDrag: eventTypes.drag,
topDragEnd: eventTypes.dragEnd,
topDragEnter: eventTypes.dragEnter,
topDragExit: eventTypes.dragExit,
topDragLeave: eventTypes.dragLeave,
topDragOver: eventTypes.dragOver,
topDragStart: eventTypes.dragStart,
topDrop: eventTypes.drop,
topError: eventTypes.error,
topFocus: eventTypes.focus,
topInput: eventTypes.input,
topKeyDown: eventTypes.keyDown,
topKeyPress: eventTypes.keyPress,
topKeyUp: eventTypes.keyUp,
topLoad: eventTypes.load,
topMouseDown: eventTypes.mouseDown,
topMouseMove: eventTypes.mouseMove,
topMouseOut: eventTypes.mouseOut,
topMouseOver: eventTypes.mouseOver,
topMouseUp: eventTypes.mouseUp,
topPaste: eventTypes.paste,
topReset: eventTypes.reset,
topScroll: eventTypes.scroll,
topSubmit: eventTypes.submit,
topDrag: eventTypes.drag,
topDragEnd: eventTypes.dragEnd,
topDragEnter: eventTypes.dragEnter,
topDragExit: eventTypes.dragExit,
topDragLeave: eventTypes.dragLeave,
topDragOver: eventTypes.dragOver,
topDragStart: eventTypes.dragStart,
topDrop: eventTypes.drop,
topError: eventTypes.error,
topFocus: eventTypes.focus,
topInput: eventTypes.input,
topKeyDown: eventTypes.keyDown,
topKeyPress: eventTypes.keyPress,
topKeyUp: eventTypes.keyUp,
topLoad: eventTypes.load,
topMouseDown: eventTypes.mouseDown,
topMouseMove: eventTypes.mouseMove,
topMouseOut: eventTypes.mouseOut,
topMouseOver: eventTypes.mouseOver,
topMouseUp: eventTypes.mouseUp,
topPaste: eventTypes.paste,
topPointerCancel: eventTypes.pointerCancel,
topPointerDown: eventTypes.pointerDown,
topPointerMove: eventTypes.pointerMove,
topPointerOut: eventTypes.pointerOut,
topPointerOver: eventTypes.pointerOver,
topPointerUp: eventTypes.pointerUp,
topReset: eventTypes.reset,
topScroll: eventTypes.scroll,
topSubmit: eventTypes.submit,
topTouchCancel: eventTypes.touchCancel,
topTouchEnd: eventTypes.touchEnd,
topTouchMove: eventTypes.touchMove,
topTouchStart: eventTypes.touchStart,
topWheel: eventTypes.wheel
topTouchEnd: eventTypes.touchEnd,
topTouchMove: eventTypes.touchMove,
topTouchStart: eventTypes.touchStart,
topWheel: eventTypes.wheel
};

for (var topLevelType in topLevelEventsToDispatchConfig) {
Expand Down Expand Up @@ -366,6 +409,14 @@ var SimpleEventPlugin = {
case topLevelTypes.topMouseUp:
EventConstructor = SyntheticMouseEvent;
break;
case topLevelTypes.topPointerCancel:
case topLevelTypes.topPointerDown:
case topLevelTypes.topPointerMove:
case topLevelTypes.topPointerOut:
case topLevelTypes.topPointerOver:
case topLevelTypes.topPointerUp:
EventConstructor = SyntheticPointerEvent;
break;
case topLevelTypes.topDrag:
case topLevelTypes.topDragEnd:
case topLevelTypes.topDragEnter:
Expand Down
52 changes: 52 additions & 0 deletions src/browser/syntheticEvents/SyntheticPointerEvent.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
/**
* Copyright 2013-2014 Facebook, Inc.
*
* Licensed under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* @providesModule SyntheticPointerEvent
* @typechecks static-only
*/

"use strict";

var SyntheticMouseEvent = require('SyntheticMouseEvent');
var ViewportMetrics = require('ViewportMetrics');

/**
* @interface PointerEvent
* @see http://www.w3.org/TR/DOM-Level-3-Events/
*/
var PointerEventInterface = {
pointerId: null,
width: null,
height: null,
pressure: null,
tiltX: null,
tiltY: null,
pointerType: null,
isPrimary: null
};

/**
* @param {object} dispatchConfig Configuration used to dispatch this event.
* @param {string} dispatchMarker Marker identifying the event target.
* @param {object} nativeEvent Native browser event.
* @extends {SyntheticMouseEvent}
*/
function SyntheticPointerEvent(dispatchConfig, dispatchMarker, nativeEvent) {
SyntheticMouseEvent.call(this, dispatchConfig, dispatchMarker, nativeEvent);
}

SyntheticMouseEvent.augmentClass(SyntheticPointerEvent, PointerEventInterface);

module.exports = SyntheticPointerEvent;
8 changes: 8 additions & 0 deletions src/event/EventConstants.js
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,14 @@ var topLevelTypes = keyMirror({
topMouseOver: null,
topMouseUp: null,
topPaste: null,
topPointerCancel: null,
topPointerDown: null,
topPointerEnter: null,
topPointerLeave: null,
topPointerMove: null,
topPointerOut: null,
topPointerOver: null,
topPointerUp: null,
topReset: null,
topScroll: null,
topSelectionChange: null,
Expand Down
4 changes: 4 additions & 0 deletions src/event/EventPluginUtils.js
Original file line number Diff line number Diff line change
Expand Up @@ -48,16 +48,20 @@ var topLevelTypes = EventConstants.topLevelTypes;

function isEndish(topLevelType) {
return topLevelType === topLevelTypes.topMouseUp ||
topLevelType === topLevelTypes.topPointerUp ||
topLevelType === topLevelTypes.topPointerCancel ||
topLevelType === topLevelTypes.topTouchEnd ||
topLevelType === topLevelTypes.topTouchCancel;
}

function isMoveish(topLevelType) {
return topLevelType === topLevelTypes.topMouseMove ||
topLevelType === topLevelTypes.topPointerMove ||
topLevelType === topLevelTypes.topTouchMove;
}
function isStartish(topLevelType) {
return topLevelType === topLevelTypes.topMouseDown ||
topLevelType === topLevelTypes.topPointerDown ||
topLevelType === topLevelTypes.topTouchStart;
}

Expand Down