aboutsummaryrefslogtreecommitdiffstats
path: root/lisp/progmodes/python.el
diff options
context:
space:
mode:
authorYuan Fu2022-11-08 20:41:58 -0800
committerYuan Fu2022-11-09 15:51:12 -0800
commit2b4d46f99be3735823666c2a6d9f058cedeb031c (patch)
tree1fb05e87489b43270cab7692b4d5fce110642fb3 /lisp/progmodes/python.el
parent5858921f409f6ee9d2e08dbdcd1719969a4f5544 (diff)
downloademacs-2b4d46f99be3735823666c2a6d9f058cedeb031c.tar.gz
emacs-2b4d46f99be3735823666c2a6d9f058cedeb031c.zip
Mimic existing python-mode beg/end-of-defun behavior better
* lisp/progmodes/python.el (python-treesit-beginning-of-defun) (python-treesit-end-of-defun): New functions. * lisp/progmodes/python.el (python-mode): Use custom beg/end-of-defun functions.
Diffstat (limited to 'lisp/progmodes/python.el')
-rw-r--r--lisp/progmodes/python.el56
1 files changed, 52 insertions, 4 deletions
diff --git a/lisp/progmodes/python.el b/lisp/progmodes/python.el
index 8db96b117f3..61f29dd005c 100644
--- a/lisp/progmodes/python.el
+++ b/lisp/progmodes/python.el
@@ -2354,6 +2354,55 @@ position, else returns nil."
2354 (ignore (goto-char point))))) 2354 (ignore (goto-char point)))))
2355 2355
2356 2356
2357;;; Tree-sitter navigation
2358
2359(defun python-treesit-beginning-of-defun (&optional arg)
2360 "Tree-sitter `beginning-of-defun' function.
2361ARG is the same as in `beginning-of-defun'."
2362 (let ((arg (or arg 1))
2363 (node (treesit-node-at (point)))
2364 (function-or-class (rx (or "function" "class") "_definition")))
2365 (if (> arg 0)
2366 ;; Go backward.
2367 (while (and (> arg 0)
2368 (setq node (treesit-search-forward-goto
2369 node function-or-class t t)))
2370 ;; Here we deviate from `treesit-beginning-of-defun': if
2371 ;; NODE is function_definition, find the top-level
2372 ;; function_definition, if NODE is class_definition, find
2373 ;; the top-level class_definition, don't mix the two like
2374 ;; `treesit-beginning-of-defun' would.
2375 (setq node (or (treesit-node-top-level node)
2376 node))
2377 (setq arg (1- arg)))
2378 ;; Go forward.
2379 (while (and (< arg 0)
2380 (setq node (treesit-search-forward-goto
2381 node function-or-class)))
2382 (setq node (or (treesit-node-top-level node)
2383 node))
2384 (setq arg (1+ arg))))
2385 (when node
2386 (goto-char (treesit-node-start node))
2387 t)))
2388
2389(defun python-treesit-end-of-defun ()
2390 "Tree-sitter `end-of-defun' function."
2391 ;; Why not simply get the largest node at point: when point is at
2392 ;; (point-min), that gives us the root node.
2393 (let* ((node (treesit-node-at (point)))
2394 (top-func (treesit-node-top-level
2395 node
2396 "function_definition"))
2397 (top-class (treesit-node-top-level
2398 node
2399 "class_definition")))
2400 ;; Prefer function_definition over class_definition: when we are
2401 ;; in a function_definition inside a class_definition, jump to the
2402 ;; end of function_definition.
2403 (goto-char (or (treesit-node-end (or top-func top-class)) (point)))))
2404
2405
2357;;; Shell integration 2406;;; Shell integration
2358 2407
2359(defcustom python-shell-buffer-name "Python" 2408(defcustom python-shell-buffer-name "Python"
@@ -6508,10 +6557,9 @@ Add import for undefined name `%s' (empty to skip): "
6508 (setq-local treesit-font-lock-settings python--treesit-settings) 6557 (setq-local treesit-font-lock-settings python--treesit-settings)
6509 (setq-local imenu-create-index-function 6558 (setq-local imenu-create-index-function
6510 #'python-imenu-treesit-create-index) 6559 #'python-imenu-treesit-create-index)
6511 (setq-local treesit-defun-type-regexp (rx bol 6560 (setq-local beginning-of-defun-function
6512 (or "function" "class") 6561 #'python-treesit-beginning-of-defun)
6513 "_definition" 6562 (setq-local end-of-defun-function #'python-treesit-end-of-defun)
6514 eol))
6515 (treesit-major-mode-setup)) 6563 (treesit-major-mode-setup))
6516 ;; Elisp. 6564 ;; Elisp.
6517 (t 6565 (t