diff options
| author | Po Lu | 2023-07-16 17:29:58 +0800 |
|---|---|---|
| committer | Po Lu | 2023-07-16 17:29:58 +0800 |
| commit | 64256d29234b0fc3012d07cb189ebeccc2dfc187 (patch) | |
| tree | 0a9d6d3a069a18d54657822ff8a1618cffdcf976 | |
| parent | 7b346b92b4c30c634d094e6162b65a22a52b93bb (diff) | |
| download | emacs-64256d29234b0fc3012d07cb189ebeccc2dfc187.tar.gz emacs-64256d29234b0fc3012d07cb189ebeccc2dfc187.zip | |
Update Android port
* doc/lispref/commands.texi (Touchscreen Events): Improve
documentation.
* lisp/tab-bar.el (tab-bar-map): Bind `[tab-bar
touchscreen-hold]'.
* lisp/touch-screen.el (touch-screen-hold, touch-screen-drag):
New functions.
(touch-screen-handle-timeout): Generate a `touchscreen-hold'
event instead.
(touch-screen-handle-point-update): Generate a
`touchscreen-drag' event upon dragging.
(touch-screen-translate-touch): Cancel touch screen timer upon
exit.
* src/keyboard.c (access_keymap_keyremap): Take unsigned int
start and end instead.
| -rw-r--r-- | doc/lispref/commands.texi | 43 | ||||
| -rw-r--r-- | lisp/tab-bar.el | 4 | ||||
| -rw-r--r-- | lisp/touch-screen.el | 159 | ||||
| -rw-r--r-- | src/keyboard.c | 2 |
4 files changed, 117 insertions, 91 deletions
diff --git a/doc/lispref/commands.texi b/doc/lispref/commands.texi index 725ca900165..025ac197feb 100644 --- a/doc/lispref/commands.texi +++ b/doc/lispref/commands.texi | |||
| @@ -2080,25 +2080,42 @@ selected, as a compromise for packages which assume | |||
| 2080 | @code{mouse-drag-region} has already set point to the location of any | 2080 | @code{mouse-drag-region} has already set point to the location of any |
| 2081 | mouse click and selected the window where it took place. | 2081 | mouse click and selected the window where it took place. |
| 2082 | 2082 | ||
| 2083 | If touch gestures are detected during translation, one of the | ||
| 2084 | following input events may be generated: | ||
| 2085 | |||
| 2086 | @table @code | ||
| 2083 | @cindex @code{touchscreen-scroll} event | 2087 | @cindex @code{touchscreen-scroll} event |
| 2088 | @item (touchscreen-scroll @var{window} @var{dx} @var{dy}) | ||
| 2084 | If a ``scrolling'' gesture is detected during the translation process, | 2089 | If a ``scrolling'' gesture is detected during the translation process, |
| 2085 | each subsequent @code{touchscreen-update} event is translated to a | 2090 | each subsequent @code{touchscreen-update} event is translated to a |
| 2086 | @code{touchscreen-scroll} event of the form: | 2091 | @code{touchscreen-scroll} event, where @var{dx} and @var{dy} specify, |
| 2087 | 2092 | in pixels, the relative motion of the touchpoint from the position of | |
| 2088 | @example | 2093 | the @code{touchscreen-begin} event that started the sequence or the |
| 2089 | @w{@code{(touchscreen-scroll @var{window} @var{dx} @var{dy})}} | 2094 | last @code{touchscreen-scroll} event, whichever came later. |
| 2090 | @end example | 2095 | |
| 2091 | 2096 | @cindex @code{touchscreen-hold} event | |
| 2092 | where @var{dx} and @var{dy} specify, in pixels, the relative motion of | 2097 | @item (touchscreen-hold @var{posn}) |
| 2093 | the tool from the position of the @code{touchscreen-begin} event that | 2098 | If the single active touchpoint remains stationary for more than |
| 2094 | started the sequence or the last @code{touchscreen-scroll} event, | 2099 | @code{touch-screen-delay} seconds after a @code{touchscreen-begin} is |
| 2095 | whichever came later. | 2100 | generated, a ``long-press'' gesture is detected during the translation |
| 2101 | process, and a @code{touchscreen-hold} event is sent, with @var{posn} | ||
| 2102 | set to a mouse position list containing the position of the | ||
| 2103 | @code{touchscreen-begin} event. | ||
| 2104 | |||
| 2105 | @cindex @code{touchscreen-drag} event | ||
| 2106 | @item (touchscreen-drag @var{posn}) | ||
| 2107 | If a ``long-press'' gesture is detected while translating the current | ||
| 2108 | touch sequence, a @code{touchscreen-drag} event is sent upon each | ||
| 2109 | subsequent @code{touchscreen-update} event, with @var{posn} set to the | ||
| 2110 | new position of the touchpoint. | ||
| 2111 | @end table | ||
| 2096 | 2112 | ||
| 2097 | @cindex handling touch screen events | 2113 | @cindex handling touch screen events |
| 2098 | @cindex tap and drag, touch screen gestures | 2114 | @cindex tap and drag, touch screen gestures |
| 2099 | Emacs provides two functions to handle touch screen events. They are | 2115 | Emacs provides two functions to handle touch screen events independent |
| 2100 | intended to be used by a command bound to @code{touchscreen-begin} to | 2116 | of gesture recognition or mouse event translation. They are intended |
| 2101 | handle common gestures. | 2117 | to be used by commands bound to @code{touchscreen-begin}, to recognize |
| 2118 | and handle common gestures. | ||
| 2102 | 2119 | ||
| 2103 | @defun touch-screen-track-tap event &optional update data | 2120 | @defun touch-screen-track-tap event &optional update data |
| 2104 | This function is used to track a single ``tap'' gesture originating | 2121 | This function is used to track a single ``tap'' gesture originating |
diff --git a/lisp/tab-bar.el b/lisp/tab-bar.el index 044337260ce..a81f42fc751 100644 --- a/lisp/tab-bar.el +++ b/lisp/tab-bar.el | |||
| @@ -493,7 +493,9 @@ appropriate." | |||
| 493 | "S-<wheel-down>" #'tab-bar-move-tab | 493 | "S-<wheel-down>" #'tab-bar-move-tab |
| 494 | "S-<wheel-left>" #'tab-bar-move-tab-backward | 494 | "S-<wheel-left>" #'tab-bar-move-tab-backward |
| 495 | "S-<wheel-right>" #'tab-bar-move-tab | 495 | "S-<wheel-right>" #'tab-bar-move-tab |
| 496 | "<touchscreen-begin>" #'tab-bar-touchscreen-begin) | 496 | "<touchscreen-begin>" #'tab-bar-touchscreen-begin |
| 497 | ;; Trying to set this in `touch-screen.el' runs afoul of the filter. | ||
| 498 | "<touchscreen-drag>" 'touchscreen-drag) | ||
| 497 | 499 | ||
| 498 | (global-set-key [tab-bar] | 500 | (global-set-key [tab-bar] |
| 499 | `(menu-item ,(purecopy "tab bar") ,(make-sparse-keymap) | 501 | `(menu-item ,(purecopy "tab bar") ,(make-sparse-keymap) |
diff --git a/lisp/touch-screen.el b/lisp/touch-screen.el index 0f584269931..ef9b14f27ce 100644 --- a/lisp/touch-screen.el +++ b/lisp/touch-screen.el | |||
| @@ -234,15 +234,69 @@ the event." | |||
| 234 | 234 | ||
| 235 | (global-set-key [touchscreen-scroll] #'touch-screen-scroll) | 235 | (global-set-key [touchscreen-scroll] #'touch-screen-scroll) |
| 236 | 236 | ||
| 237 | (defun touch-screen-hold (event) | ||
| 238 | "Handle a long press EVENT. | ||
| 239 | Beep, select the window at EVENT, set point there, and activate | ||
| 240 | the mark." | ||
| 241 | (interactive "e") | ||
| 242 | (let* ((posn (cadr event)) | ||
| 243 | (point (posn-point posn))) | ||
| 244 | (when point | ||
| 245 | (beep) | ||
| 246 | (select-window (posn-window posn)) | ||
| 247 | (set-mark point) | ||
| 248 | (goto-char point) | ||
| 249 | (activate-mark)))) | ||
| 250 | |||
| 251 | (defun touch-screen-drag (event) | ||
| 252 | "Handle a drag EVENT by setting the region to its new point. | ||
| 253 | Scroll the window if necessary." | ||
| 254 | (interactive "e") | ||
| 255 | (let* ((posn (cadr event)) ; Position of the tool. | ||
| 256 | ; Window where the tap originated. | ||
| 257 | (window (nth 1 touch-screen-current-tool))) | ||
| 258 | ;; Keep dragging. | ||
| 259 | (with-selected-window window | ||
| 260 | ;; Figure out what character to go to. If this posn is | ||
| 261 | ;; in the window, go to (posn-point posn). If not, | ||
| 262 | ;; then go to the line before either window start or | ||
| 263 | ;; window end. | ||
| 264 | (if (and (eq (posn-window posn) window) | ||
| 265 | (posn-point posn)) | ||
| 266 | (goto-char (posn-point posn)) | ||
| 267 | (let ((relative-xy | ||
| 268 | (touch-screen-relative-xy posn window))) | ||
| 269 | (let ((scroll-conservatively 101)) | ||
| 270 | (cond | ||
| 271 | ((< (cdr relative-xy) 0) | ||
| 272 | (ignore-errors | ||
| 273 | (goto-char (1- (window-start)))) | ||
| 274 | (redisplay)) | ||
| 275 | ((> (cdr relative-xy) | ||
| 276 | (let ((edges (window-inside-pixel-edges))) | ||
| 277 | (- (nth 3 edges) (cadr edges)))) | ||
| 278 | (ignore-errors | ||
| 279 | (goto-char (1+ (window-end nil t)))) | ||
| 280 | (redisplay))))))))) | ||
| 281 | |||
| 282 | (global-set-key [touchscreen-hold] #'touch-screen-hold) | ||
| 283 | (global-set-key [touchscreen-drag] #'touch-screen-drag) | ||
| 284 | |||
| 285 | ;; Bind this to most of the virtual prefix keys as well. | ||
| 286 | (global-set-key [tool-bar touchscreen-drag] #'touch-screen-drag) | ||
| 287 | (global-set-key [header-line touchscreen-drag] #'touch-screen-drag) | ||
| 288 | (global-set-key [mode-line touchscreen-drag] #'touch-screen-drag) | ||
| 289 | (global-set-key [tab-line touchscreen-drag] #'touch-screen-drag) | ||
| 290 | |||
| 237 | (defun touch-screen-handle-timeout (arg) | 291 | (defun touch-screen-handle-timeout (arg) |
| 238 | "Start the touch screen timeout or handle it depending on ARG. | 292 | "Start the touch screen timeout or handle it depending on ARG. |
| 239 | When ARG is nil, start the `touch-screen-current-timer' to go off | 293 | When ARG is nil, start the `touch-screen-current-timer' to go off |
| 240 | in `touch-screen-delay' seconds, and call this function with ARG | 294 | in `touch-screen-delay' seconds, and call this function with ARG |
| 241 | t. | 295 | t. |
| 242 | 296 | ||
| 243 | When ARG is t, beep. Then, set the fourth element of | 297 | When ARG is t, set the fourth element of |
| 244 | touch-screen-current-tool to `held', and the mark to the last | 298 | `touch-screen-current-tool' to `held', and generate a |
| 245 | known position of the tool." | 299 | `touchscreen-hold' event at the original position of that tool." |
| 246 | (if (not arg) | 300 | (if (not arg) |
| 247 | ;; Cancel the touch screen long-press timer, if it is still | 301 | ;; Cancel the touch screen long-press timer, if it is still |
| 248 | ;; there by any chance. | 302 | ;; there by any chance. |
| @@ -253,19 +307,16 @@ known position of the tool." | |||
| 253 | (run-at-time touch-screen-delay nil | 307 | (run-at-time touch-screen-delay nil |
| 254 | #'touch-screen-handle-timeout | 308 | #'touch-screen-handle-timeout |
| 255 | t))) | 309 | t))) |
| 256 | ;; Beep. | ||
| 257 | (beep) | ||
| 258 | ;; Set touch-screen-current-timer to nil. | 310 | ;; Set touch-screen-current-timer to nil. |
| 259 | (setq touch-screen-current-timer nil) | 311 | (setq touch-screen-current-timer nil) |
| 260 | (when touch-screen-current-tool | 312 | (when touch-screen-current-tool |
| 261 | ;; Set the state to `held'. | 313 | ;; Set the state to `held'. |
| 262 | (setcar (nthcdr 3 touch-screen-current-tool) 'held) | 314 | (setcar (nthcdr 3 touch-screen-current-tool) 'held) |
| 263 | ;; Go to the initial position of the touchpoint and activate the | 315 | ;; Generate an input event at the original position of the mark. |
| 264 | ;; mark. | 316 | ;; This assumes that the timer is running within |
| 265 | (select-window (cadr touch-screen-current-tool)) | 317 | ;; `touch-screen-translate-touch'. |
| 266 | (set-mark (posn-point (nth 4 touch-screen-current-tool))) | 318 | (let ((posn (nth 4 touch-screen-current-tool))) |
| 267 | (goto-char (mark)) | 319 | (throw 'input-event (list 'touchscreen-hold posn)))))) |
| 268 | (activate-mark)))) | ||
| 269 | 320 | ||
| 270 | (defun touch-screen-handle-point-update (point) | 321 | (defun touch-screen-handle-point-update (point) |
| 271 | "Notice that the touch point POINT has changed position. | 322 | "Notice that the touch point POINT has changed position. |
| @@ -297,7 +348,7 @@ If the fourth element of `touch-screen-current-tool' is | |||
| 297 | If the fourth element of `touch-screen-current-tool' is `held', | 348 | If the fourth element of `touch-screen-current-tool' is `held', |
| 298 | then the touch has been held down for some time. If motion | 349 | then the touch has been held down for some time. If motion |
| 299 | happens, cancel `touch-screen-current-timer', and set the field | 350 | happens, cancel `touch-screen-current-timer', and set the field |
| 300 | to `drag'. Then, activate the mark and start dragging. | 351 | to `drag'. Then, generate a `touchscreen-drag' event. |
| 301 | 352 | ||
| 302 | If the fourth element of `touch-screen-current-tool' is `drag', | 353 | If the fourth element of `touch-screen-current-tool' is `drag', |
| 303 | then move point to the position of POINT." | 354 | then move point to the position of POINT." |
| @@ -319,16 +370,16 @@ then move point to the position of POINT." | |||
| 319 | 'scroll) | 370 | 'scroll) |
| 320 | (setcar (nthcdr 2 touch-screen-current-tool) | 371 | (setcar (nthcdr 2 touch-screen-current-tool) |
| 321 | relative-xy) | 372 | relative-xy) |
| 322 | ;; Generate a `touchscreen-scroll' event with `diff-x' | ||
| 323 | ;; and `diff-y'. | ||
| 324 | (throw 'input-event | ||
| 325 | (list 'touchscreen-scroll | ||
| 326 | window diff-x diff-y)) | ||
| 327 | ;; Cancel the touch screen long-press timer, if it is | 373 | ;; Cancel the touch screen long-press timer, if it is |
| 328 | ;; still there by any chance. | 374 | ;; still there by any chance. |
| 329 | (when touch-screen-current-timer | 375 | (when touch-screen-current-timer |
| 330 | (cancel-timer touch-screen-current-timer) | 376 | (cancel-timer touch-screen-current-timer) |
| 331 | (setq touch-screen-current-timer nil))))) | 377 | (setq touch-screen-current-timer nil)) |
| 378 | ;; Generate a `touchscreen-scroll' event with `diff-x' | ||
| 379 | ;; and `diff-y'. | ||
| 380 | (throw 'input-event | ||
| 381 | (list 'touchscreen-scroll | ||
| 382 | window diff-x diff-y))))) | ||
| 332 | ((eq what 'scroll) | 383 | ((eq what 'scroll) |
| 333 | ;; Cancel the touch screen long-press timer, if it is still | 384 | ;; Cancel the touch screen long-press timer, if it is still |
| 334 | ;; there by any chance. | 385 | ;; there by any chance. |
| @@ -361,67 +412,17 @@ then move point to the position of POINT." | |||
| 361 | (throw 'input-event (list 'mouse-movement | 412 | (throw 'input-event (list 'mouse-movement |
| 362 | (cdr point))))) | 413 | (cdr point))))) |
| 363 | ((eq what 'held) | 414 | ((eq what 'held) |
| 364 | (let* ((posn (cdr point)) | 415 | (let* ((posn (cdr point))) |
| 365 | (relative-xy | ||
| 366 | (touch-screen-relative-xy posn window))) | ||
| 367 | (when touch-screen-current-timer | ||
| 368 | (cancel-timer touch-screen-current-timer) | ||
| 369 | (setq touch-screen-current-timer nil)) | ||
| 370 | ;; Now start dragging. | 416 | ;; Now start dragging. |
| 371 | (setcar (nthcdr 3 touch-screen-current-tool) | 417 | (setcar (nthcdr 3 touch-screen-current-tool) |
| 372 | 'drag) | 418 | 'drag) |
| 373 | (setcar (nthcdr 2 touch-screen-current-tool) | 419 | ;; Generate a (touchscreen-drag POSN) event. `touchscreen-hold' |
| 374 | relative-xy) | 420 | ;; was generated when the timeout fired. |
| 375 | (with-selected-window window | 421 | (throw 'input-event (list 'touchscreen-drag posn)))) |
| 376 | ;; Activate the mark. It should have been set by the | ||
| 377 | ;; time `touch-screen-timeout' was called. | ||
| 378 | (activate-mark) | ||
| 379 | ;; Figure out what character to go to. If this posn is | ||
| 380 | ;; in the window, go to (posn-point posn). If not, | ||
| 381 | ;; then go to the line before either window start or | ||
| 382 | ;; window end. | ||
| 383 | (if (and (eq (posn-window posn) window) | ||
| 384 | (posn-point posn)) | ||
| 385 | (goto-char (posn-point posn)) | ||
| 386 | (let ((relative-xy | ||
| 387 | (touch-screen-relative-xy posn window))) | ||
| 388 | (let ((scroll-conservatively 101)) | ||
| 389 | (cond | ||
| 390 | ((< (cdr relative-xy) 0) | ||
| 391 | (ignore-errors | ||
| 392 | (goto-char (1- (window-start)))) | ||
| 393 | (redisplay)) | ||
| 394 | ((> (cdr relative-xy) | ||
| 395 | (let ((edges (window-inside-pixel-edges))) | ||
| 396 | (- (nth 3 edges) (cadr edges)))) | ||
| 397 | (ignore-errors | ||
| 398 | (goto-char (1+ (window-end nil t)))) | ||
| 399 | (redisplay))))))))) | ||
| 400 | ((eq what 'drag) | 422 | ((eq what 'drag) |
| 401 | (let* ((posn (cdr point))) | 423 | (let* ((posn (cdr point))) |
| 402 | ;; Keep dragging. | 424 | ;; Generate a (touchscreen-drag POSN) event. |
| 403 | (with-selected-window window | 425 | (throw 'input-event (list 'touchscreen-drag posn))))))) |
| 404 | ;; Figure out what character to go to. If this posn is | ||
| 405 | ;; in the window, go to (posn-point posn). If not, | ||
| 406 | ;; then go to the line before either window start or | ||
| 407 | ;; window end. | ||
| 408 | (if (and (eq (posn-window posn) window) | ||
| 409 | (posn-point posn)) | ||
| 410 | (goto-char (posn-point posn)) | ||
| 411 | (let ((relative-xy | ||
| 412 | (touch-screen-relative-xy posn window))) | ||
| 413 | (let ((scroll-conservatively 101)) | ||
| 414 | (cond | ||
| 415 | ((< (cdr relative-xy) 0) | ||
| 416 | (ignore-errors | ||
| 417 | (goto-char (1- (window-start)))) | ||
| 418 | (redisplay)) | ||
| 419 | ((> (cdr relative-xy) | ||
| 420 | (let ((edges (window-inside-pixel-edges))) | ||
| 421 | (- (nth 3 edges) (cadr edges)))) | ||
| 422 | (ignore-errors | ||
| 423 | (goto-char (1+ (window-end nil t)))) | ||
| 424 | (redisplay)))))))))))) | ||
| 425 | 426 | ||
| 426 | (defun touch-screen-window-selection-changed (frame) | 427 | (defun touch-screen-window-selection-changed (frame) |
| 427 | "Notice that FRAME's selected window has changed. | 428 | "Notice that FRAME's selected window has changed. |
| @@ -681,7 +682,7 @@ where POSN is the position of the mouse button press or click. | |||
| 681 | 682 | ||
| 682 | where POSN is the position of the mouse click, either `mouse-2' | 683 | where POSN is the position of the mouse click, either `mouse-2' |
| 683 | if POSN is on a link or a button, or `mouse-1' otherwise." | 684 | if POSN is on a link or a button, or `mouse-1' otherwise." |
| 684 | (if (> (length current-key-remap-sequence) 0) | 685 | (unwind-protect |
| 685 | ;; Save the virtual function key if this is a mode line event. | 686 | ;; Save the virtual function key if this is a mode line event. |
| 686 | (let* ((prefix (and (> (length current-key-remap-sequence) 1) | 687 | (let* ((prefix (and (> (length current-key-remap-sequence) 1) |
| 687 | (aref current-key-remap-sequence 0))) | 688 | (aref current-key-remap-sequence 0))) |
| @@ -721,7 +722,13 @@ if POSN is on a link or a button, or `mouse-1' otherwise." | |||
| 721 | ;; the appropriate function key. | 722 | ;; the appropriate function key. |
| 722 | (vector prefix event)) | 723 | (vector prefix event)) |
| 723 | (vector event)) | 724 | (vector event)) |
| 724 | "")))) | 725 | "")) |
| 726 | ;; Cancel the touch screen long-press timer, if it is still there | ||
| 727 | ;; by any chance. If the timer is to operate correctly, it must | ||
| 728 | ;; fire within the catch block above. | ||
| 729 | (when touch-screen-current-timer | ||
| 730 | (cancel-timer touch-screen-current-timer) | ||
| 731 | (setq touch-screen-current-timer nil)))) | ||
| 725 | 732 | ||
| 726 | (define-key function-key-map [touchscreen-begin] | 733 | (define-key function-key-map [touchscreen-begin] |
| 727 | #'touch-screen-translate-touch) | 734 | #'touch-screen-translate-touch) |
diff --git a/src/keyboard.c b/src/keyboard.c index e10128def13..fa5eea31c3b 100644 --- a/src/keyboard.c +++ b/src/keyboard.c | |||
| @@ -10001,7 +10001,7 @@ typedef struct keyremap | |||
| 10001 | 10001 | ||
| 10002 | static Lisp_Object | 10002 | static Lisp_Object |
| 10003 | access_keymap_keyremap (Lisp_Object map, Lisp_Object key, Lisp_Object prompt, | 10003 | access_keymap_keyremap (Lisp_Object map, Lisp_Object key, Lisp_Object prompt, |
| 10004 | bool do_funcall, ptrdiff_t start, ptrdiff_t end, | 10004 | bool do_funcall, unsigned int start, unsigned int end, |
| 10005 | Lisp_Object *keybuf) | 10005 | Lisp_Object *keybuf) |
| 10006 | { | 10006 | { |
| 10007 | Lisp_Object next; | 10007 | Lisp_Object next; |