diff options
| author | Po Lu | 2023-07-18 09:29:16 +0800 |
|---|---|---|
| committer | Po Lu | 2023-07-18 09:29:16 +0800 |
| commit | 46fd03a49617066fca87000378771caedfd150f3 (patch) | |
| tree | ffa3b4d930878d329257185821e0bd2bb63baaa3 /src | |
| parent | 324d66e3901665f1efa82650ee03b13c9b9bcfe4 (diff) | |
| parent | 9ad601e7d762f47d3469692b8135cc72b8301365 (diff) | |
| download | emacs-46fd03a49617066fca87000378771caedfd150f3.tar.gz emacs-46fd03a49617066fca87000378771caedfd150f3.zip | |
Merge remote-tracking branch 'origin/master' into feature/android
Diffstat (limited to 'src')
| -rw-r--r-- | src/keyboard.c | 20 | ||||
| -rw-r--r-- | src/termhooks.h | 6 | ||||
| -rw-r--r-- | src/xfns.c | 1 | ||||
| -rw-r--r-- | src/xterm.c | 92 | ||||
| -rw-r--r-- | src/xterm.h | 62 |
5 files changed, 157 insertions, 24 deletions
diff --git a/src/keyboard.c b/src/keyboard.c index 78105fa9e05..bd7433e584a 100644 --- a/src/keyboard.c +++ b/src/keyboard.c | |||
| @@ -6557,7 +6557,6 @@ make_lispy_event (struct input_event *event) | |||
| 6557 | } | 6557 | } |
| 6558 | 6558 | ||
| 6559 | case TOUCHSCREEN_BEGIN_EVENT: | 6559 | case TOUCHSCREEN_BEGIN_EVENT: |
| 6560 | case TOUCHSCREEN_END_EVENT: | ||
| 6561 | { | 6560 | { |
| 6562 | Lisp_Object x, y, id, position; | 6561 | Lisp_Object x, y, id, position; |
| 6563 | struct frame *f; | 6562 | struct frame *f; |
| @@ -6684,6 +6683,25 @@ make_lispy_event (struct input_event *event) | |||
| 6684 | Fcons (id, position)); | 6683 | Fcons (id, position)); |
| 6685 | } | 6684 | } |
| 6686 | 6685 | ||
| 6686 | case TOUCHSCREEN_END_EVENT: | ||
| 6687 | { | ||
| 6688 | Lisp_Object x, y, id, position; | ||
| 6689 | struct frame *f = XFRAME (event->frame_or_window); | ||
| 6690 | |||
| 6691 | id = event->arg; | ||
| 6692 | x = event->x; | ||
| 6693 | y = event->y; | ||
| 6694 | |||
| 6695 | position = make_lispy_position (f, x, y, event->timestamp); | ||
| 6696 | |||
| 6697 | return list3 (((event->kind | ||
| 6698 | == TOUCHSCREEN_BEGIN_EVENT) | ||
| 6699 | ? Qtouchscreen_begin | ||
| 6700 | : Qtouchscreen_end), | ||
| 6701 | Fcons (id, position), | ||
| 6702 | event->modifiers ? Qt : Qnil); | ||
| 6703 | } | ||
| 6704 | |||
| 6687 | case PINCH_EVENT: | 6705 | case PINCH_EVENT: |
| 6688 | { | 6706 | { |
| 6689 | Lisp_Object x, y, position; | 6707 | Lisp_Object x, y, position; |
diff --git a/src/termhooks.h b/src/termhooks.h index 99f27cd668e..d978819aeca 100644 --- a/src/termhooks.h +++ b/src/termhooks.h | |||
| @@ -308,7 +308,11 @@ enum event_kind | |||
| 308 | 308 | ||
| 309 | In TOUCHSCREEN_BEGIN_EVENT and TOUCHSCREEN_END_EVENT, ARG is the | 309 | In TOUCHSCREEN_BEGIN_EVENT and TOUCHSCREEN_END_EVENT, ARG is the |
| 310 | unique ID of the touchpoint, and X and Y are the frame-relative | 310 | unique ID of the touchpoint, and X and Y are the frame-relative |
| 311 | positions of the touchpoint. */ | 311 | positions of the touchpoint. |
| 312 | |||
| 313 | In TOUCHSCREEN_END_EVENT, non-0 modifiers means that the | ||
| 314 | touchpoint has been canceled. (See (elisp)Touchscreen | ||
| 315 | Events.) */ | ||
| 312 | 316 | ||
| 313 | , TOUCHSCREEN_UPDATE_EVENT | 317 | , TOUCHSCREEN_UPDATE_EVENT |
| 314 | , TOUCHSCREEN_BEGIN_EVENT | 318 | , TOUCHSCREEN_BEGIN_EVENT |
diff --git a/src/xfns.c b/src/xfns.c index 704f7a3f892..854a85f5306 100644 --- a/src/xfns.c +++ b/src/xfns.c | |||
| @@ -4107,6 +4107,7 @@ setup_xi_event_mask (struct frame *f) | |||
| 4107 | XISetMask (m, XI_TouchBegin); | 4107 | XISetMask (m, XI_TouchBegin); |
| 4108 | XISetMask (m, XI_TouchUpdate); | 4108 | XISetMask (m, XI_TouchUpdate); |
| 4109 | XISetMask (m, XI_TouchEnd); | 4109 | XISetMask (m, XI_TouchEnd); |
| 4110 | XISetMask (m, XI_TouchOwnership); | ||
| 4110 | 4111 | ||
| 4111 | #if defined HAVE_XINPUT2_4 && defined USE_GTK3 | 4112 | #if defined HAVE_XINPUT2_4 && defined USE_GTK3 |
| 4112 | if (FRAME_DISPLAY_INFO (f)->xi2_version >= 4) | 4113 | if (FRAME_DISPLAY_INFO (f)->xi2_version >= 4) |
diff --git a/src/xterm.c b/src/xterm.c index 75e5b07f2c0..b818609d4b5 100644 --- a/src/xterm.c +++ b/src/xterm.c | |||
| @@ -5742,6 +5742,10 @@ xi_device_from_id (struct x_display_info *dpyinfo, int deviceid) | |||
| 5742 | 5742 | ||
| 5743 | #ifdef HAVE_XINPUT2_2 | 5743 | #ifdef HAVE_XINPUT2_2 |
| 5744 | 5744 | ||
| 5745 | /* Record a touch sequence with the identifier DETAIL from the given | ||
| 5746 | FRAME on the specified DEVICE. Round X and Y and record them as | ||
| 5747 | its current position. */ | ||
| 5748 | |||
| 5745 | static void | 5749 | static void |
| 5746 | xi_link_touch_point (struct xi_device_t *device, | 5750 | xi_link_touch_point (struct xi_device_t *device, |
| 5747 | int detail, double x, double y, | 5751 | int detail, double x, double y, |
| @@ -5751,19 +5755,28 @@ xi_link_touch_point (struct xi_device_t *device, | |||
| 5751 | 5755 | ||
| 5752 | touchpoint = xmalloc (sizeof *touchpoint); | 5756 | touchpoint = xmalloc (sizeof *touchpoint); |
| 5753 | touchpoint->next = device->touchpoints; | 5757 | touchpoint->next = device->touchpoints; |
| 5754 | touchpoint->x = x; | 5758 | touchpoint->x = lrint (x); |
| 5755 | touchpoint->y = y; | 5759 | touchpoint->y = lrint (y); |
| 5756 | touchpoint->number = detail; | 5760 | touchpoint->number = detail; |
| 5757 | touchpoint->frame = frame; | 5761 | touchpoint->frame = frame; |
| 5762 | touchpoint->ownership = TOUCH_OWNERSHIP_NONE; | ||
| 5758 | 5763 | ||
| 5759 | device->touchpoints = touchpoint; | 5764 | device->touchpoints = touchpoint; |
| 5760 | } | 5765 | } |
| 5761 | 5766 | ||
| 5762 | static bool | 5767 | /* Free and remove the touch sequence with the identifier DETAIL. |
| 5763 | xi_unlink_touch_point (int detail, | 5768 | DEVICE is the device in which the touch sequence should be |
| 5764 | struct xi_device_t *device) | 5769 | recorded. |
| 5770 | |||
| 5771 | Value is 0 if no touch sequence by that identifier exists inside | ||
| 5772 | DEVICE, 1 if a touch sequence has been found but is not owned by | ||
| 5773 | Emacs, and 2 otherwise. */ | ||
| 5774 | |||
| 5775 | static int | ||
| 5776 | xi_unlink_touch_point (int detail, struct xi_device_t *device) | ||
| 5765 | { | 5777 | { |
| 5766 | struct xi_touch_point_t *last, *tem; | 5778 | struct xi_touch_point_t *last, *tem; |
| 5779 | enum xi_touch_ownership ownership; | ||
| 5767 | 5780 | ||
| 5768 | for (last = NULL, tem = device->touchpoints; tem; | 5781 | for (last = NULL, tem = device->touchpoints; tem; |
| 5769 | last = tem, tem = tem->next) | 5782 | last = tem, tem = tem->next) |
| @@ -5775,12 +5788,17 @@ xi_unlink_touch_point (int detail, | |||
| 5775 | else | 5788 | else |
| 5776 | last->next = tem->next; | 5789 | last->next = tem->next; |
| 5777 | 5790 | ||
| 5791 | ownership = tem->ownership; | ||
| 5778 | xfree (tem); | 5792 | xfree (tem); |
| 5779 | return true; | 5793 | |
| 5794 | if (ownership == TOUCH_OWNERSHIP_SELF) | ||
| 5795 | return 2; | ||
| 5796 | |||
| 5797 | return 1; | ||
| 5780 | } | 5798 | } |
| 5781 | } | 5799 | } |
| 5782 | 5800 | ||
| 5783 | return false; | 5801 | return 0; |
| 5784 | } | 5802 | } |
| 5785 | 5803 | ||
| 5786 | /* Unlink all touch points associated with the frame F. | 5804 | /* Unlink all touch points associated with the frame F. |
| @@ -5813,6 +5831,10 @@ xi_unlink_touch_points (struct frame *f) | |||
| 5813 | } | 5831 | } |
| 5814 | } | 5832 | } |
| 5815 | 5833 | ||
| 5834 | /* Return the data associated with a touch sequence DETAIL recorded by | ||
| 5835 | `xi_link_touch_point' from DEVICE, or NULL if it can't be | ||
| 5836 | found. */ | ||
| 5837 | |||
| 5816 | static struct xi_touch_point_t * | 5838 | static struct xi_touch_point_t * |
| 5817 | xi_find_touch_point (struct xi_device_t *device, int detail) | 5839 | xi_find_touch_point (struct xi_device_t *device, int detail) |
| 5818 | { | 5840 | { |
| @@ -24458,12 +24480,48 @@ handle_one_xevent (struct x_display_info *dpyinfo, | |||
| 24458 | goto XI_OTHER; | 24480 | goto XI_OTHER; |
| 24459 | } | 24481 | } |
| 24460 | 24482 | ||
| 24483 | case XI_TouchOwnership: | ||
| 24484 | { | ||
| 24485 | struct xi_device_t *device; | ||
| 24486 | struct xi_touch_point_t *touchpoint; | ||
| 24487 | XITouchOwnershipEvent *event; | ||
| 24488 | |||
| 24489 | /* All grabbing clients have decided to reject ownership | ||
| 24490 | of this touch sequence. */ | ||
| 24491 | |||
| 24492 | event = (XITouchOwnershipEvent *) xi_event; | ||
| 24493 | device = xi_device_from_id (dpyinfo, event->deviceid); | ||
| 24494 | |||
| 24495 | if (!device || device->use == XIMasterPointer) | ||
| 24496 | goto XI_OTHER; | ||
| 24497 | |||
| 24498 | touchpoint = xi_find_touch_point (device, event->touchid); | ||
| 24499 | |||
| 24500 | if (!touchpoint) | ||
| 24501 | goto XI_OTHER; | ||
| 24502 | |||
| 24503 | /* As a result, Emacs should complete whatever editing | ||
| 24504 | operations result from this touch sequence. */ | ||
| 24505 | touchpoint->ownership = TOUCH_OWNERSHIP_SELF; | ||
| 24506 | } | ||
| 24507 | |||
| 24461 | case XI_TouchUpdate: | 24508 | case XI_TouchUpdate: |
| 24462 | { | 24509 | { |
| 24463 | struct xi_device_t *device, *source; | 24510 | struct xi_device_t *device, *source; |
| 24464 | struct xi_touch_point_t *touchpoint; | 24511 | struct xi_touch_point_t *touchpoint; |
| 24465 | Lisp_Object arg = Qnil; | 24512 | Lisp_Object arg = Qnil; |
| 24466 | 24513 | ||
| 24514 | /* If flags & TouchPendingEnd, the touch sequence has | ||
| 24515 | already ended, but some grabbing clients remain | ||
| 24516 | undecided as to whether they will obtain ownership of | ||
| 24517 | the touch sequence. | ||
| 24518 | |||
| 24519 | Wait for them to make their decision, resulting in | ||
| 24520 | TouchOwnership and TouchEnd events being sent. */ | ||
| 24521 | |||
| 24522 | if (xev->flags & XITouchPendingEnd) | ||
| 24523 | goto XI_OTHER; | ||
| 24524 | |||
| 24467 | device = xi_device_from_id (dpyinfo, xev->deviceid); | 24525 | device = xi_device_from_id (dpyinfo, xev->deviceid); |
| 24468 | source = xi_device_from_id (dpyinfo, xev->sourceid); | 24526 | source = xi_device_from_id (dpyinfo, xev->sourceid); |
| 24469 | x_display_set_last_user_time (dpyinfo, xev->time, | 24527 | x_display_set_last_user_time (dpyinfo, xev->time, |
| @@ -24475,7 +24533,7 @@ handle_one_xevent (struct x_display_info *dpyinfo, | |||
| 24475 | detached, and master pointers may also represent | 24533 | detached, and master pointers may also represent |
| 24476 | dependent touch devices. */ | 24534 | dependent touch devices. */ |
| 24477 | 24535 | ||
| 24478 | if (!device) | 24536 | if (!device || device->use == XIMasterPointer) |
| 24479 | goto XI_OTHER; | 24537 | goto XI_OTHER; |
| 24480 | 24538 | ||
| 24481 | touchpoint = xi_find_touch_point (device, xev->detail); | 24539 | touchpoint = xi_find_touch_point (device, xev->detail); |
| @@ -24483,12 +24541,12 @@ handle_one_xevent (struct x_display_info *dpyinfo, | |||
| 24483 | if (!touchpoint | 24541 | if (!touchpoint |
| 24484 | /* Don't send this event if nothing has changed | 24542 | /* Don't send this event if nothing has changed |
| 24485 | either. */ | 24543 | either. */ |
| 24486 | || (touchpoint->x == (int) xev->event_x | 24544 | || (touchpoint->x == lrint (xev->event_x) |
| 24487 | && touchpoint->y == (int) xev->event_y)) | 24545 | && touchpoint->y == lrint (xev->event_y))) |
| 24488 | goto XI_OTHER; | 24546 | goto XI_OTHER; |
| 24489 | 24547 | ||
| 24490 | touchpoint->x = xev->event_x; | 24548 | touchpoint->x = lrint (xev->event_x); |
| 24491 | touchpoint->y = xev->event_y; | 24549 | touchpoint->y = lrint (xev->event_y); |
| 24492 | 24550 | ||
| 24493 | f = x_window_to_frame (dpyinfo, xev->event); | 24551 | f = x_window_to_frame (dpyinfo, xev->event); |
| 24494 | 24552 | ||
| @@ -24502,8 +24560,7 @@ handle_one_xevent (struct x_display_info *dpyinfo, | |||
| 24502 | touchpoint; touchpoint = touchpoint->next) | 24560 | touchpoint; touchpoint = touchpoint->next) |
| 24503 | { | 24561 | { |
| 24504 | if (touchpoint->frame == f) | 24562 | if (touchpoint->frame == f) |
| 24505 | arg = Fcons (list3i (lrint (touchpoint->x), | 24563 | arg = Fcons (list3i (touchpoint->x, touchpoint->y, |
| 24506 | lrint (touchpoint->y), | ||
| 24507 | lrint (touchpoint->number)), | 24564 | lrint (touchpoint->number)), |
| 24508 | arg); | 24565 | arg); |
| 24509 | } | 24566 | } |
| @@ -24520,7 +24577,7 @@ handle_one_xevent (struct x_display_info *dpyinfo, | |||
| 24520 | case XI_TouchEnd: | 24577 | case XI_TouchEnd: |
| 24521 | { | 24578 | { |
| 24522 | struct xi_device_t *device, *source; | 24579 | struct xi_device_t *device, *source; |
| 24523 | bool unlinked_p; | 24580 | int state; |
| 24524 | 24581 | ||
| 24525 | device = xi_device_from_id (dpyinfo, xev->deviceid); | 24582 | device = xi_device_from_id (dpyinfo, xev->deviceid); |
| 24526 | source = xi_device_from_id (dpyinfo, xev->sourceid); | 24583 | source = xi_device_from_id (dpyinfo, xev->sourceid); |
| @@ -24536,9 +24593,9 @@ handle_one_xevent (struct x_display_info *dpyinfo, | |||
| 24536 | if (!device || device->use == XIMasterPointer) | 24593 | if (!device || device->use == XIMasterPointer) |
| 24537 | goto XI_OTHER; | 24594 | goto XI_OTHER; |
| 24538 | 24595 | ||
| 24539 | unlinked_p = xi_unlink_touch_point (xev->detail, device); | 24596 | state = xi_unlink_touch_point (xev->detail, device); |
| 24540 | 24597 | ||
| 24541 | if (unlinked_p) | 24598 | if (state) |
| 24542 | { | 24599 | { |
| 24543 | f = x_window_to_frame (dpyinfo, xev->event); | 24600 | f = x_window_to_frame (dpyinfo, xev->event); |
| 24544 | 24601 | ||
| @@ -24546,6 +24603,7 @@ handle_one_xevent (struct x_display_info *dpyinfo, | |||
| 24546 | { | 24603 | { |
| 24547 | inev.ie.kind = TOUCHSCREEN_END_EVENT; | 24604 | inev.ie.kind = TOUCHSCREEN_END_EVENT; |
| 24548 | inev.ie.timestamp = xev->time; | 24605 | inev.ie.timestamp = xev->time; |
| 24606 | inev.ie.modifiers = state != 2; | ||
| 24549 | 24607 | ||
| 24550 | XSETFRAME (inev.ie.frame_or_window, f); | 24608 | XSETFRAME (inev.ie.frame_or_window, f); |
| 24551 | XSETINT (inev.ie.x, lrint (xev->event_x)); | 24609 | XSETINT (inev.ie.x, lrint (xev->event_x)); |
diff --git a/src/xterm.h b/src/xterm.h index e7171ba072f..cb477645bfa 100644 --- a/src/xterm.h +++ b/src/xterm.h | |||
| @@ -255,19 +255,71 @@ struct xi_scroll_valuator_t | |||
| 255 | 255 | ||
| 256 | #ifdef HAVE_XINPUT2_2 | 256 | #ifdef HAVE_XINPUT2_2 |
| 257 | 257 | ||
| 258 | /* Enum describing the ownership of a touch point. | ||
| 259 | |||
| 260 | The input extension allows other clients to intercept touch | ||
| 261 | sequences destined for a client window through passively grabbing | ||
| 262 | for touch events on a parent window. | ||
| 263 | |||
| 264 | When a passive touch grab for an XI_TouchBegin event activates, one | ||
| 265 | grabbing client is designated the ``owner'' of the touch sequence | ||
| 266 | started by the grabbed event. Touch events are then delivered to | ||
| 267 | both the grabbing client and other clients that have selected for | ||
| 268 | touch events on the subwindow. | ||
| 269 | |||
| 270 | The X server will not deliver TouchEnd events to clients other than | ||
| 271 | the owner until one grabbing client decides to take over processing | ||
| 272 | the touch event sequence, or no more grabbing clients remain. | ||
| 273 | Instead, a TouchUpdate event with the TouchPendingEnd flag is sent, | ||
| 274 | and the TouchEnd event is postponed until the decision is made and | ||
| 275 | all XI_TouchOwnership events are sent. | ||
| 276 | |||
| 277 | If the owner decides to take over processing the touch sequence, an | ||
| 278 | XI_TouchEnd event is delivered to all other clients receiving | ||
| 279 | events for the current touch sequence, who are then expected to | ||
| 280 | cancel or undo any actions which have taken place in reaction to | ||
| 281 | events from that sequence. | ||
| 282 | |||
| 283 | If the owner decides to relinquish ownership over the touch | ||
| 284 | sequence, the X server looks for another grabbing client, and | ||
| 285 | transfers touch ownership to that client instead. Nothing changes | ||
| 286 | from the perspective of clients who have merely selected for events | ||
| 287 | from the subwindow, while an XI_TouchEnd event is delivered to the | ||
| 288 | old owner, and an XI_TouchOwnership event is delivered to the new | ||
| 289 | owner. | ||
| 290 | |||
| 291 | If all grabbing clients reject ownership over the touch sequence, | ||
| 292 | the X server delivers an XI_TouchOwnership event to the client that | ||
| 293 | has selected for touch events on the subwindow, the only client | ||
| 294 | that will receive events for this touch sequence from this time | ||
| 295 | forward. */ | ||
| 296 | |||
| 297 | enum xi_touch_ownership | ||
| 298 | { | ||
| 299 | /* Emacs doesn't own this touch sequence. */ | ||
| 300 | TOUCH_OWNERSHIP_NONE, | ||
| 301 | |||
| 302 | /* Emacs owns this touch sequence. */ | ||
| 303 | TOUCH_OWNERSHIP_SELF, | ||
| 304 | }; | ||
| 305 | |||
| 258 | struct xi_touch_point_t | 306 | struct xi_touch_point_t |
| 259 | { | 307 | { |
| 260 | /* The next touch point in this list. */ | ||
| 261 | struct xi_touch_point_t *next; | ||
| 262 | |||
| 263 | /* The touchpoint detail. */ | 308 | /* The touchpoint detail. */ |
| 264 | int number; | 309 | int number; |
| 265 | 310 | ||
| 266 | /* The last known X and Y position of the touchpoint. */ | 311 | /* Whether or not Emacs has ``exclusive'' access to this touch |
| 267 | double x, y; | 312 | point. */ |
| 313 | enum xi_touch_ownership ownership; | ||
| 314 | |||
| 315 | /* The last known rounded X and Y positions of the touchpoint. */ | ||
| 316 | int x, y; | ||
| 268 | 317 | ||
| 269 | /* The frame associated with this touch point. */ | 318 | /* The frame associated with this touch point. */ |
| 270 | struct frame *frame; | 319 | struct frame *frame; |
| 320 | |||
| 321 | /* The next touch point in this list. */ | ||
| 322 | struct xi_touch_point_t *next; | ||
| 271 | }; | 323 | }; |
| 272 | 324 | ||
| 273 | #endif | 325 | #endif |