aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorFabián Ezequiel Gallina2012-05-17 00:03:25 -0300
committerFabián Ezequiel Gallina2012-05-17 00:03:25 -0300
commitfc6c545e4c61b341fd433f994c193ec6f61abbdd (patch)
treed6332bc5521691b64bb008fa83a0deb9beea363b
parent1faf2911d613ac1c208e7ffca52e484804d3b0bb (diff)
downloademacs-fc6c545e4c61b341fd433f994c193ec6f61abbdd.tar.gz
emacs-fc6c545e4c61b341fd433f994c193ec6f61abbdd.zip
Added simple way of jumping to current buffer's class/function definitions
The new `python-nav-jump-to-defun' function allows a user to jump fast and easy to a function or class definition in the current buffer. For this a entry in the menu and the C-c C-j keybinding have been introduced. New functions: + `python-nav-list-defun-positions' + `python-nav-read-defun' + `python-nav-jump-to-defun' The new function `python-nav-list-defun-positions' does the same as a relevant part of the `python-imenu-create-index' so the latter has been refactored to use it.
-rw-r--r--lisp/progmodes/python.el89
1 files changed, 67 insertions, 22 deletions
diff --git a/lisp/progmodes/python.el b/lisp/progmodes/python.el
index fe026a8da1a..05e999a6bef 100644
--- a/lisp/progmodes/python.el
+++ b/lisp/progmodes/python.el
@@ -49,14 +49,16 @@
49;; causes the current line to be dedented automatically if needed. 49;; causes the current line to be dedented automatically if needed.
50 50
51;; Movement: `beginning-of-defun' and `end-of-defun' functions are 51;; Movement: `beginning-of-defun' and `end-of-defun' functions are
52;; properly implemented. Also there are specialized 52;; properly implemented. There are also specialized
53;; `forward-sentence' and `backward-sentence' replacements 53;; `forward-sentence' and `backward-sentence' replacements
54;; (`python-nav-forward-sentence', `python-nav-backward-sentence' 54;; (`python-nav-forward-sentence', `python-nav-backward-sentence'
55;; respectively). Extra functions `python-nav-sentence-start' and 55;; respectively). Extra functions `python-nav-sentence-start' and
56;; `python-nav-sentence-end' are included to move to the beginning and 56;; `python-nav-sentence-end' are included to move to the beginning and
57;; to the end of a setence while taking care of multiline definitions. 57;; to the end of a setence while taking care of multiline definitions.
58;; `python-nav-jump-to-defun' is provided and allows jumping to a
59;; function or class definition quickly in the current buffer.
58 60
59;; Shell interaction: is provided and allows you easily execute any 61;; Shell interaction: is provided and allows you to execute easily any
60;; block of code of your current buffer in an inferior Python process. 62;; block of code of your current buffer in an inferior Python process.
61 63
62;; Shell completion: hitting tab will try to complete the current 64;; Shell completion: hitting tab will try to complete the current
@@ -213,6 +215,7 @@
213 (substitute-key-definition 'forward-sentence 215 (substitute-key-definition 'forward-sentence
214 'python-nav-forward-sentence 216 'python-nav-forward-sentence
215 map global-map) 217 map global-map)
218 (define-key map "\C-c\C-j" 'python-nav-jump-to-defun)
216 ;; Indent specific 219 ;; Indent specific
217 (define-key map "\177" 'python-indent-dedent-line-backspace) 220 (define-key map "\177" 'python-indent-dedent-line-backspace)
218 (define-key map (kbd "<backtab>") 'python-indent-dedent-line) 221 (define-key map (kbd "<backtab>") 'python-indent-dedent-line)
@@ -247,16 +250,17 @@
247 ["Shift region right" python-indent-shift-right :active mark-active 250 ["Shift region right" python-indent-shift-right :active mark-active
248 :help "Shift region right by a single indentation step"] 251 :help "Shift region right by a single indentation step"]
249 "-" 252 "-"
250 ["Mark def/class" mark-defun
251 :help "Mark outermost definition around point"]
252 "-"
253 ["Start of def/class" beginning-of-defun 253 ["Start of def/class" beginning-of-defun
254 :help "Go to start of outermost definition around point"] 254 :help "Go to start of outermost definition around point"]
255 ["End of def/class" end-of-defun 255 ["End of def/class" end-of-defun
256 :help "Go to end of definition around point"] 256 :help "Go to end of definition around point"]
257 "-" 257 ["Mark def/class" mark-defun
258 :help "Mark outermost definition around point"]
259 ["Jump to def/class" python-nav-jump-to-defun
260 :help "Jump to a class or function definition"]
261 "--"
258 ("Skeletons") 262 ("Skeletons")
259 "-" 263 "---"
260 ["Start interpreter" run-python 264 ["Start interpreter" run-python
261 :help "Run inferior Python process in a separate buffer"] 265 :help "Run inferior Python process in a separate buffer"]
262 ["Switch to shell" python-shell-switch-to-shell 266 ["Switch to shell" python-shell-switch-to-shell
@@ -272,7 +276,7 @@
272 ["Eval file" python-shell-send-file 276 ["Eval file" python-shell-send-file
273 :help "Eval file in inferior Python session"] 277 :help "Eval file in inferior Python session"]
274 ["Debugger" pdb :help "Run pdb under GUD"] 278 ["Debugger" pdb :help "Run pdb under GUD"]
275 "-" 279 "----"
276 ["Check file" python-check 280 ["Check file" python-check
277 :help "Check file for errors"] 281 :help "Check file for errors"]
278 ["Help on symbol" python-eldoc-at-point 282 ["Help on symbol" python-eldoc-at-point
@@ -898,7 +902,7 @@ With numeric ARG, just insert that many colons. With
898 902
899(defvar python-nav-beginning-of-defun-regexp 903(defvar python-nav-beginning-of-defun-regexp
900 (python-rx line-start (* space) defun (+ space) (group symbol-name)) 904 (python-rx line-start (* space) defun (+ space) (group symbol-name))
901 "Regular expresion matching beginning of class or function. 905 "Regexp matching class or function definition.
902The name of the defun should be grouped so it can be retrieved 906The name of the defun should be grouped so it can be retrieved
903via `match-string'.") 907via `match-string'.")
904 908
@@ -1024,6 +1028,51 @@ With negative argument, move backward repeatedly to start of sentence."
1024 (forward-line -1) 1028 (forward-line -1)
1025 (setq arg (1+ arg)))) 1029 (setq arg (1+ arg))))
1026 1030
1031(defun python-nav-list-defun-positions (&optional include-type)
1032 "Make an Alist of defun names and point markers for current buffer.
1033When optional argument INCLUDE-TYPE is non-nil the type is
1034included the defun name."
1035 (let ((defs))
1036 (save-restriction
1037 (widen)
1038 (save-excursion
1039 (goto-char (point-max))
1040 (while (re-search-backward python-nav-beginning-of-defun-regexp nil t)
1041 (when (and (not (python-info-ppss-context 'string))
1042 (not (python-info-ppss-context 'comment))
1043 (not (python-info-ppss-context 'parent)))
1044 (add-to-list
1045 'defs (cons
1046 (python-info-current-defun include-type)
1047 (point-marker)))))
1048 defs))))
1049
1050(defun python-nav-read-defun ()
1051 "Read a defun name of current buffer and return its point marker.
1052A cons cell with the form (DEFUN-NAME . POINT-MARKER) is returned
1053when defun is completed, else nil."
1054 (let ((defs (python-nav-list-defun-positions)))
1055 (minibuffer-with-setup-hook
1056 (lambda ()
1057 (setq minibuffer-completion-table (mapcar 'car defs)))
1058 (let ((stringdef
1059 (read-from-minibuffer
1060 "Jump to definition: " nil
1061 minibuffer-local-must-match-map)))
1062 (when (not (string= stringdef ""))
1063 (assoc-string stringdef defs))))))
1064
1065(defun python-nav-jump-to-defun (def)
1066 "Jump to the definition of DEF in current file."
1067 (interactive
1068 (list (python-nav-read-defun)))
1069 (when (not (called-interactively-p 'interactive))
1070 (setq def (assoc-string def (python-nav-list-defun-positions))))
1071 (let ((def-marker (cdr def)))
1072 (when (markerp def-marker)
1073 (goto-char (marker-position def-marker))
1074 (back-to-indentation))))
1075
1027 1076
1028;;; Shell integration 1077;;; Shell integration
1029 1078
@@ -2223,7 +2272,7 @@ Argument PLAIN-INDEX is the calculated plain index used to build the tree."
2223 full-element plain-index)))) 2272 full-element plain-index))))
2224 2273
2225(defun python-imenu-make-tree (index) 2274(defun python-imenu-make-tree (index)
2226"Build the imenu alist tree from plain INDEX. 2275 "Build the imenu alist tree from plain INDEX.
2227 2276
2228The idea of this function is that given the alist: 2277The idea of this function is that given the alist:
2229 2278
@@ -2249,21 +2298,17 @@ This tree gets built:
2249 2298
2250Internally it uses `python-imenu-make-element-tree' to create all 2299Internally it uses `python-imenu-make-element-tree' to create all
2251branches for each element." 2300branches for each element."
2252(setq python-imenu-index-alist nil) 2301 (setq python-imenu-index-alist nil)
2253(mapc (lambda (element) 2302 (mapc (lambda (element)
2254 (python-imenu-make-element-tree element element index)) 2303 (python-imenu-make-element-tree element element index))
2255 (mapcar (lambda (element) 2304 (mapcar (lambda (element)
2256 (split-string (car element) "\\." t)) index)) 2305 (split-string (car element) "\\." t)) index))
2257python-imenu-index-alist) 2306 python-imenu-index-alist)
2258 2307
2259(defun python-imenu-create-index () 2308(defun python-imenu-create-index ()
2260 "`imenu-create-index-function' for Python." 2309 "`imenu-create-index-function' for Python."
2261 (let ((index)) 2310 (let ((index
2262 (goto-char (point-max)) 2311 (python-nav-list-defun-positions python-imenu-include-defun-type)))
2263 (while (python-beginning-of-defun-function 1 t)
2264 (let ((defun-dotted-name
2265 (python-info-current-defun python-imenu-include-defun-type)))
2266 (push (cons defun-dotted-name (point)) index)))
2267 (if python-imenu-make-tree 2312 (if python-imenu-make-tree
2268 (python-imenu-make-tree index) 2313 (python-imenu-make-tree index)
2269 index))) 2314 index)))