@@ -288,41 +288,81 @@ class _SanitizedDetails {
288
288
class _ButtonSanitizer {
289
289
int _pressedButtons = 0 ;
290
290
291
- // Transform html.PointerEvent.buttons to Flutter's PointerEvent buttons.
291
+ /// Transform [ html.PointerEvent.buttons] to Flutter's PointerEvent buttons.
292
292
int _htmlButtonsToFlutterButtons (int buttons) {
293
293
// Flutter's button definition conveniently matches that of JavaScript
294
294
// from primary button (0x1) to forward button (0x10), which allows us to
295
295
// avoid transforming it bit by bit.
296
296
return buttons & _kButtonsMask;
297
297
}
298
298
299
- List <_SanitizedDetails > sanitizeDownEvent ({@required int buttons}) {
300
- final List <_SanitizedDetails > result = < _SanitizedDetails > [];
301
- // TODO(flutter_web): Remove this temporary fix for right click
302
- // on web platform once context gesture is implemented.
299
+ /// Given [html.PointerEvent.button] and [html.PointerEvent.buttons] , tries to
300
+ /// infer the correct value for Flutter buttons.
301
+ int _inferDownFlutterButtons (int button, int buttons) {
302
+ if (buttons == 0 && button > - 1 ) {
303
+ // In some cases, the browser sends `buttons:0` in a down event. In such
304
+ // case, we try to infer the value from `button`.
305
+ buttons = convertButtonToButtons (button);
306
+ }
307
+ return _htmlButtonsToFlutterButtons (buttons);
308
+ }
309
+
310
+ List <_SanitizedDetails > sanitizeDownEvent ({
311
+ @required int button,
312
+ @required int buttons,
313
+ }) {
314
+ // If the pointer is already down, we just send a move event with the new
315
+ // `buttons` value.
303
316
if (_pressedButtons != 0 ) {
304
- _pressedButtons = 0 ;
305
- result.add (_SanitizedDetails (
306
- change: ui.PointerChange .up,
307
- buttons: 0 ,
308
- ));
317
+ return sanitizeMoveEvent (buttons: buttons);
309
318
}
310
- _pressedButtons = _htmlButtonsToFlutterButtons (buttons);
311
- result.add (_SanitizedDetails (
312
- change: ui.PointerChange .down,
313
- buttons: _pressedButtons,
314
- ));
315
- return result;
319
+
320
+ _pressedButtons = _inferDownFlutterButtons (button, buttons);
321
+ return < _SanitizedDetails > [
322
+ _SanitizedDetails (
323
+ change: ui.PointerChange .down,
324
+ buttons: _pressedButtons,
325
+ )
326
+ ];
316
327
}
317
328
318
329
List <_SanitizedDetails > sanitizeMoveEvent ({@required int buttons}) {
319
- _pressedButtons = _htmlButtonsToFlutterButtons (buttons);
320
- return < _SanitizedDetails > [_SanitizedDetails (
321
- change: _pressedButtons == 0
322
- ? ui.PointerChange .hover
323
- : ui.PointerChange .move,
324
- buttons: _pressedButtons,
325
- )];
330
+ final int newPressedButtons = _htmlButtonsToFlutterButtons (buttons);
331
+ // This could happen when the context menu is active and the user clicks
332
+ // RMB somewhere else. The browser sends a down event with `buttons:0`.
333
+ //
334
+ // In this case, we keep the old `buttons` value so we don't confuse the
335
+ // framework.
336
+ if (_pressedButtons != 0 && newPressedButtons == 0 ) {
337
+ return < _SanitizedDetails > [
338
+ _SanitizedDetails (
339
+ change: ui.PointerChange .move,
340
+ buttons: _pressedButtons,
341
+ )
342
+ ];
343
+ }
344
+
345
+ // This could happen when the user clicks RMB then moves the mouse quickly.
346
+ // The brower sends a move event with `buttons:2` even though there's no
347
+ // buttons down yet.
348
+ if (_pressedButtons == 0 && newPressedButtons != 0 ) {
349
+ return < _SanitizedDetails > [
350
+ _SanitizedDetails (
351
+ change: ui.PointerChange .hover,
352
+ buttons: _pressedButtons,
353
+ )
354
+ ];
355
+ }
356
+
357
+ _pressedButtons = newPressedButtons;
358
+ return < _SanitizedDetails > [
359
+ _SanitizedDetails (
360
+ change: _pressedButtons == 0
361
+ ? ui.PointerChange .hover
362
+ : ui.PointerChange .move,
363
+ buttons: _pressedButtons,
364
+ )
365
+ ];
326
366
}
327
367
328
368
List <_SanitizedDetails > sanitizeUpEvent () {
@@ -396,7 +436,11 @@ class _PointerAdapter extends _BaseAdapter with _WheelEventListenerMixin {
396
436
_addPointerEventListener ('pointerdown' , (html.PointerEvent event) {
397
437
final int device = event.pointerId;
398
438
final List <ui.PointerData > pointerData = < ui.PointerData > [];
399
- final List <_SanitizedDetails > detailsList = _ensureSanitizer (device).sanitizeDownEvent (buttons: event.buttons);
439
+ final List <_SanitizedDetails > detailsList =
440
+ _ensureSanitizer (device).sanitizeDownEvent (
441
+ button: event.button,
442
+ buttons: event.buttons,
443
+ );
400
444
_convertEventsToPointerData (data: pointerData, event: event, detailsList: detailsList);
401
445
_callback (pointerData);
402
446
});
@@ -697,10 +741,11 @@ class _MouseAdapter extends _BaseAdapter with _WheelEventListenerMixin {
697
741
void setup () {
698
742
_addMouseEventListener ('mousedown' , (html.MouseEvent event) {
699
743
final List <ui.PointerData > pointerData = < ui.PointerData > [];
700
- final bool isStartOfDrag = event.buttons == convertButtonToButtons (event.button);
701
- final List <_SanitizedDetails > sanitizedDetails = isStartOfDrag ?
702
- _sanitizer.sanitizeDownEvent (buttons: event.buttons) :
703
- _sanitizer.sanitizeMoveEvent (buttons: event.buttons);
744
+ final List <_SanitizedDetails > sanitizedDetails =
745
+ _sanitizer.sanitizeDownEvent (
746
+ button: event.button,
747
+ buttons: event.buttons,
748
+ );
704
749
_convertEventsToPointerData (data: pointerData, event: event, detailsList: sanitizedDetails);
705
750
_callback (pointerData);
706
751
});
0 commit comments