diff options
| author | Bill Wohler | 2013-02-18 10:11:43 -0800 |
|---|---|---|
| committer | Bill Wohler | 2013-02-18 10:11:43 -0800 |
| commit | 21733e4f154f8830fa568a347a0d6dbd59793c2b (patch) | |
| tree | 3170dbbcdfafeb42f6c381d6b80b251e9f31b788 /lisp/progmodes/python.el | |
| parent | 6d14beddb06b5ae86f9dd770a1661ebd24846f28 (diff) | |
| parent | 587feed443522f738b65b57b22a31cc8a25525c5 (diff) | |
| download | emacs-21733e4f154f8830fa568a347a0d6dbd59793c2b.tar.gz emacs-21733e4f154f8830fa568a347a0d6dbd59793c2b.zip | |
Merge from trunk; up to 2013-02-18T01:30:27Z!monnier@iro.umontreal.ca.
Diffstat (limited to 'lisp/progmodes/python.el')
| -rw-r--r-- | lisp/progmodes/python.el | 277 |
1 files changed, 171 insertions, 106 deletions
diff --git a/lisp/progmodes/python.el b/lisp/progmodes/python.el index a2c8453a011..eadb06fa61e 100644 --- a/lisp/progmodes/python.el +++ b/lisp/progmodes/python.el | |||
| @@ -1,6 +1,6 @@ | |||
| 1 | ;;; python.el --- Python's flying circus support for Emacs | 1 | ;;; python.el --- Python's flying circus support for Emacs |
| 2 | 2 | ||
| 3 | ;; Copyright (C) 2003-2012 Free Software Foundation, Inc. | 3 | ;; Copyright (C) 2003-2013 Free Software Foundation, Inc. |
| 4 | 4 | ||
| 5 | ;; Author: Fabián E. Gallina <fabian@anue.biz> | 5 | ;; Author: Fabián E. Gallina <fabian@anue.biz> |
| 6 | ;; URL: https://github.com/fgallina/python.el | 6 | ;; URL: https://github.com/fgallina/python.el |
| @@ -54,8 +54,13 @@ | |||
| 54 | ;; `python-nav-beginning-of-statement', `python-nav-end-of-statement', | 54 | ;; `python-nav-beginning-of-statement', `python-nav-end-of-statement', |
| 55 | ;; `python-nav-beginning-of-block' and `python-nav-end-of-block' are | 55 | ;; `python-nav-beginning-of-block' and `python-nav-end-of-block' are |
| 56 | ;; included but no bound to any key. At last but not least the | 56 | ;; included but no bound to any key. At last but not least the |
| 57 | ;; specialized `python-nav-forward-sexp' allows easy | 57 | ;; specialized `python-nav-forward-sexp' allows easy navigation |
| 58 | ;; navigation between code blocks. | 58 | ;; between code blocks. If you prefer `cc-mode'-like `forward-sexp' |
| 59 | ;; movement, setting `forward-sexp-function' to nil is enough, You can | ||
| 60 | ;; do that using the `python-mode-hook': | ||
| 61 | |||
| 62 | ;; (add-hook 'python-mode-hook | ||
| 63 | ;; (lambda () (setq forward-sexp-function nil))) | ||
| 59 | 64 | ||
| 60 | ;; Shell interaction: is provided and allows you to execute easily any | 65 | ;; Shell interaction: is provided and allows you to execute easily any |
| 61 | ;; block of code of your current buffer in an inferior Python process. | 66 | ;; block of code of your current buffer in an inferior Python process. |
| @@ -155,7 +160,10 @@ | |||
| 155 | ;; dabbrev. If you have `dabbrev-mode' activated and | 160 | ;; dabbrev. If you have `dabbrev-mode' activated and |
| 156 | ;; `python-skeleton-autoinsert' is set to t, then whenever you type | 161 | ;; `python-skeleton-autoinsert' is set to t, then whenever you type |
| 157 | ;; the name of any of those defined and hit SPC, they will be | 162 | ;; the name of any of those defined and hit SPC, they will be |
| 158 | ;; automatically expanded. | 163 | ;; automatically expanded. As an alternative you can use the defined |
| 164 | ;; skeleton commands: `python-skeleton-class', `python-skeleton-def' | ||
| 165 | ;; `python-skeleton-for', `python-skeleton-if', `python-skeleton-try' | ||
| 166 | ;; and `python-skeleton-while'. | ||
| 159 | 167 | ||
| 160 | ;; FFAP: You can find the filename for a given module when using ffap | 168 | ;; FFAP: You can find the filename for a given module when using ffap |
| 161 | ;; out of the box. This feature needs an inferior python shell | 169 | ;; out of the box. This feature needs an inferior python shell |
| @@ -204,7 +212,6 @@ | |||
| 204 | 212 | ||
| 205 | (require 'ansi-color) | 213 | (require 'ansi-color) |
| 206 | (require 'comint) | 214 | (require 'comint) |
| 207 | (eval-when-compile (require 'cl-lib)) | ||
| 208 | 215 | ||
| 209 | ;; Avoid compiler warnings | 216 | ;; Avoid compiler warnings |
| 210 | (defvar view-return-to-alist) | 217 | (defvar view-return-to-alist) |
| @@ -221,7 +228,7 @@ | |||
| 221 | (defgroup python nil | 228 | (defgroup python nil |
| 222 | "Python Language's flying circus support for Emacs." | 229 | "Python Language's flying circus support for Emacs." |
| 223 | :group 'languages | 230 | :group 'languages |
| 224 | :version "23.2" | 231 | :version "24.3" |
| 225 | :link '(emacs-commentary-link "python")) | 232 | :link '(emacs-commentary-link "python")) |
| 226 | 233 | ||
| 227 | 234 | ||
| @@ -529,7 +536,7 @@ is used to limit the scan." | |||
| 529 | (while (and (< i 3) | 536 | (while (and (< i 3) |
| 530 | (or (not limit) (< (+ point i) limit)) | 537 | (or (not limit) (< (+ point i) limit)) |
| 531 | (eq (char-after (+ point i)) quote-char)) | 538 | (eq (char-after (+ point i)) quote-char)) |
| 532 | (cl-incf i)) | 539 | (setq i (1+ i))) |
| 533 | i)) | 540 | i)) |
| 534 | 541 | ||
| 535 | (defun python-syntax-stringify () | 542 | (defun python-syntax-stringify () |
| @@ -608,6 +615,12 @@ It makes underscores and dots word constituent chars.") | |||
| 608 | :group 'python | 615 | :group 'python |
| 609 | :safe 'booleanp) | 616 | :safe 'booleanp) |
| 610 | 617 | ||
| 618 | (defcustom python-indent-trigger-commands | ||
| 619 | '(indent-for-tab-command yas-expand yas/expand) | ||
| 620 | "Commands that might trigger a `python-indent-line' call." | ||
| 621 | :type '(repeat symbol) | ||
| 622 | :group 'python) | ||
| 623 | |||
| 611 | (define-obsolete-variable-alias | 624 | (define-obsolete-variable-alias |
| 612 | 'python-indent 'python-indent-offset "24.3") | 625 | 'python-indent 'python-indent-offset "24.3") |
| 613 | 626 | ||
| @@ -906,20 +919,21 @@ Uses the offset calculated in | |||
| 906 | indicated by the variable `python-indent-levels' to set the | 919 | indicated by the variable `python-indent-levels' to set the |
| 907 | current indentation. | 920 | current indentation. |
| 908 | 921 | ||
| 909 | When the variable `last-command' is equal to | 922 | When the variable `last-command' is equal to one of the symbols |
| 910 | `indent-for-tab-command' or FORCE-TOGGLE is non-nil it cycles | 923 | inside `python-indent-trigger-commands' or FORCE-TOGGLE is |
| 911 | levels indicated in the variable `python-indent-levels' by | 924 | non-nil it cycles levels indicated in the variable |
| 912 | setting the current level in the variable | 925 | `python-indent-levels' by setting the current level in the |
| 913 | `python-indent-current-level'. | 926 | variable `python-indent-current-level'. |
| 914 | 927 | ||
| 915 | When the variable `last-command' is not equal to | 928 | When the variable `last-command' is not equal to one of the |
| 916 | `indent-for-tab-command' and FORCE-TOGGLE is nil it calculates | 929 | symbols inside `python-indent-trigger-commands' and FORCE-TOGGLE |
| 917 | possible indentation levels and saves it in the variable | 930 | is nil it calculates possible indentation levels and saves it in |
| 918 | `python-indent-levels'. Afterwards it sets the variable | 931 | the variable `python-indent-levels'. Afterwards it sets the |
| 919 | `python-indent-current-level' correctly so offset is equal | 932 | variable `python-indent-current-level' correctly so offset is |
| 920 | to (`nth' `python-indent-current-level' `python-indent-levels')" | 933 | equal to (`nth' `python-indent-current-level' |
| 934 | `python-indent-levels')" | ||
| 921 | (or | 935 | (or |
| 922 | (and (or (and (eq this-command 'indent-for-tab-command) | 936 | (and (or (and (memq this-command python-indent-trigger-commands) |
| 923 | (eq last-command this-command)) | 937 | (eq last-command this-command)) |
| 924 | force-toggle) | 938 | force-toggle) |
| 925 | (not (equal python-indent-levels '(0))) | 939 | (not (equal python-indent-levels '(0))) |
| @@ -1181,16 +1195,36 @@ Returns nil if point is not in a def or class." | |||
| 1181 | (forward-line -1)))) | 1195 | (forward-line -1)))) |
| 1182 | (point-marker)) | 1196 | (point-marker)) |
| 1183 | 1197 | ||
| 1184 | (defun python-nav-end-of-statement () | 1198 | (defun python-nav-end-of-statement (&optional noend) |
| 1185 | "Move to end of current statement." | 1199 | "Move to end of current statement. |
| 1200 | Optional argument NOEND is internal and makes the logic to not | ||
| 1201 | jump to the end of line when moving forward searching for the end | ||
| 1202 | of the statement." | ||
| 1186 | (interactive "^") | 1203 | (interactive "^") |
| 1187 | (while (and (goto-char (line-end-position)) | 1204 | (let (string-start bs-pos) |
| 1188 | (not (eobp)) | 1205 | (while (and (or noend (goto-char (line-end-position))) |
| 1189 | (when (or | 1206 | (not (eobp)) |
| 1190 | (python-info-line-ends-backslash-p) | 1207 | (cond ((setq string-start (python-syntax-context 'string)) |
| 1191 | (python-syntax-context 'string) | 1208 | (goto-char string-start) |
| 1192 | (python-syntax-context 'paren)) | 1209 | (if (python-syntax-context 'paren) |
| 1193 | (forward-line 1)))) | 1210 | ;; Ended up inside a paren, roll again. |
| 1211 | (python-nav-end-of-statement t) | ||
| 1212 | ;; This is not inside a paren, move to the | ||
| 1213 | ;; end of this string. | ||
| 1214 | (goto-char (+ (point) | ||
| 1215 | (python-syntax-count-quotes | ||
| 1216 | (char-after (point)) (point)))) | ||
| 1217 | (or (re-search-forward (rx (syntax string-delimiter)) nil t) | ||
| 1218 | (goto-char (point-max))))) | ||
| 1219 | ((python-syntax-context 'paren) | ||
| 1220 | ;; The statement won't end before we've escaped | ||
| 1221 | ;; at least one level of parenthesis. | ||
| 1222 | (condition-case err | ||
| 1223 | (goto-char (scan-lists (point) 1 -1)) | ||
| 1224 | (scan-error (goto-char (nth 3 err))))) | ||
| 1225 | ((setq bs-pos (python-info-line-ends-backslash-p)) | ||
| 1226 | (goto-char bs-pos) | ||
| 1227 | (forward-line 1)))))) | ||
| 1194 | (point-marker)) | 1228 | (point-marker)) |
| 1195 | 1229 | ||
| 1196 | (defun python-nav-backward-statement (&optional arg) | 1230 | (defun python-nav-backward-statement (&optional arg) |
| @@ -1295,7 +1329,7 @@ backward to previous block." | |||
| 1295 | "Safe version of standard `forward-sexp'. | 1329 | "Safe version of standard `forward-sexp'. |
| 1296 | When ARG > 0 move forward, else if ARG is < 0." | 1330 | When ARG > 0 move forward, else if ARG is < 0." |
| 1297 | (or arg (setq arg 1)) | 1331 | (or arg (setq arg 1)) |
| 1298 | (let ((forward-sexp-function nil) | 1332 | (let ((forward-sexp-function) |
| 1299 | (paren-regexp | 1333 | (paren-regexp |
| 1300 | (if (> arg 0) (python-rx close-paren) (python-rx open-paren))) | 1334 | (if (> arg 0) (python-rx close-paren) (python-rx open-paren))) |
| 1301 | (search-fn | 1335 | (search-fn |
| @@ -1320,13 +1354,10 @@ backwards." | |||
| 1320 | 're-search-backward)) | 1354 | 're-search-backward)) |
| 1321 | (context-type (python-syntax-context-type))) | 1355 | (context-type (python-syntax-context-type))) |
| 1322 | (cond | 1356 | (cond |
| 1323 | ((eq context-type 'string) | 1357 | ((memq context-type '(string comment)) |
| 1324 | ;; Inside of a string, get out of it. | 1358 | ;; Inside of a string, get out of it. |
| 1325 | (while (and (funcall re-search-fn "[\"']" nil t) | 1359 | (let ((forward-sexp-function)) |
| 1326 | (python-syntax-context 'string)))) | 1360 | (forward-sexp dir))) |
| 1327 | ((eq context-type 'comment) | ||
| 1328 | ;; Inside of a comment, just move forward. | ||
| 1329 | (python-util-forward-comment dir)) | ||
| 1330 | ((or (eq context-type 'paren) | 1361 | ((or (eq context-type 'paren) |
| 1331 | (and forward-p (looking-at (python-rx open-paren))) | 1362 | (and forward-p (looking-at (python-rx open-paren))) |
| 1332 | (and (not forward-p) | 1363 | (and (not forward-p) |
| @@ -1349,16 +1380,16 @@ backwards." | |||
| 1349 | (save-excursion | 1380 | (save-excursion |
| 1350 | (python-nav-lisp-forward-sexp-safe dir) | 1381 | (python-nav-lisp-forward-sexp-safe dir) |
| 1351 | (point))) | 1382 | (point))) |
| 1352 | (next-sexp-context | 1383 | (next-sexp-context |
| 1353 | (save-excursion | 1384 | (save-excursion |
| 1354 | (goto-char next-sexp-pos) | 1385 | (goto-char next-sexp-pos) |
| 1355 | (cond | 1386 | (cond |
| 1356 | ((python-info-beginning-of-block-p) 'block-start) | 1387 | ((python-info-beginning-of-block-p) 'block-start) |
| 1357 | ((python-info-end-of-block-p) 'block-end) | 1388 | ((python-info-end-of-block-p) 'block-end) |
| 1358 | ((python-info-beginning-of-statement-p) 'statement-start) | 1389 | ((python-info-beginning-of-statement-p) 'statement-start) |
| 1359 | ((python-info-end-of-statement-p) 'statement-end) | 1390 | ((python-info-end-of-statement-p) 'statement-end) |
| 1360 | ((python-info-statement-starts-block-p) 'starts-block) | 1391 | ((python-info-statement-starts-block-p) 'starts-block) |
| 1361 | ((python-info-statement-ends-block-p) 'ends-block))))) | 1392 | ((python-info-statement-ends-block-p) 'ends-block))))) |
| 1362 | (if forward-p | 1393 | (if forward-p |
| 1363 | (cond ((and (not (eobp)) | 1394 | (cond ((and (not (eobp)) |
| 1364 | (python-info-current-line-empty-p)) | 1395 | (python-info-current-line-empty-p)) |
| @@ -1382,8 +1413,8 @@ backwards." | |||
| 1382 | (t (goto-char next-sexp-pos))) | 1413 | (t (goto-char next-sexp-pos))) |
| 1383 | (cond ((and (not (bobp)) | 1414 | (cond ((and (not (bobp)) |
| 1384 | (python-info-current-line-empty-p)) | 1415 | (python-info-current-line-empty-p)) |
| 1385 | (python-util-forward-comment dir) | 1416 | (python-util-forward-comment dir) |
| 1386 | (python-nav--forward-sexp dir)) | 1417 | (python-nav--forward-sexp dir)) |
| 1387 | ((eq context 'block-end) | 1418 | ((eq context 'block-end) |
| 1388 | (python-nav-beginning-of-block)) | 1419 | (python-nav-beginning-of-block)) |
| 1389 | ((eq context 'statement-end) | 1420 | ((eq context 'statement-end) |
| @@ -1635,7 +1666,11 @@ uniqueness for different types of configurations." | |||
| 1635 | 1666 | ||
| 1636 | (defun python-shell-parse-command () | 1667 | (defun python-shell-parse-command () |
| 1637 | "Calculate the string used to execute the inferior Python process." | 1668 | "Calculate the string used to execute the inferior Python process." |
| 1638 | (format "%s %s" python-shell-interpreter python-shell-interpreter-args)) | 1669 | (let ((process-environment (python-shell-calculate-process-environment)) |
| 1670 | (exec-path (python-shell-calculate-exec-path))) | ||
| 1671 | (format "%s %s" | ||
| 1672 | (executable-find python-shell-interpreter) | ||
| 1673 | python-shell-interpreter-args))) | ||
| 1639 | 1674 | ||
| 1640 | (defun python-shell-calculate-process-environment () | 1675 | (defun python-shell-calculate-process-environment () |
| 1641 | "Calculate process environment given `python-shell-virtualenv-path'." | 1676 | "Calculate process environment given `python-shell-virtualenv-path'." |
| @@ -2009,7 +2044,14 @@ Returns the output. See `python-shell-send-string-no-output'." | |||
| 2009 | (defun python-shell-send-region (start end) | 2044 | (defun python-shell-send-region (start end) |
| 2010 | "Send the region delimited by START and END to inferior Python process." | 2045 | "Send the region delimited by START and END to inferior Python process." |
| 2011 | (interactive "r") | 2046 | (interactive "r") |
| 2012 | (python-shell-send-string (buffer-substring start end) nil t)) | 2047 | (python-shell-send-string |
| 2048 | (concat | ||
| 2049 | (let ((line-num (line-number-at-pos start))) | ||
| 2050 | ;; When sending a region, add blank lines for non sent code so | ||
| 2051 | ;; backtraces remain correct. | ||
| 2052 | (make-string (1- line-num) ?\n)) | ||
| 2053 | (buffer-substring start end)) | ||
| 2054 | nil t)) | ||
| 2013 | 2055 | ||
| 2014 | (defun python-shell-send-buffer (&optional arg) | 2056 | (defun python-shell-send-buffer (&optional arg) |
| 2015 | "Send the entire buffer to inferior Python process. | 2057 | "Send the entire buffer to inferior Python process. |
| @@ -2287,15 +2329,17 @@ Argument OUTPUT is a string with the output from the comint process." | |||
| 2287 | (file-name | 2329 | (file-name |
| 2288 | (with-temp-buffer | 2330 | (with-temp-buffer |
| 2289 | (insert full-output) | 2331 | (insert full-output) |
| 2290 | (goto-char (point-min)) | 2332 | ;; When the debugger encounters a pdb.set_trace() |
| 2291 | ;; OK, this sucked but now it became a cool hack. The | 2333 | ;; command, it prints a single stack frame. Sometimes |
| 2292 | ;; stacktrace information normally is on the first line | 2334 | ;; it prints a bit of extra information about the |
| 2293 | ;; but in some cases (like when doing a step-in) it is | 2335 | ;; arguments of the present function. When ipdb |
| 2294 | ;; on the second. | 2336 | ;; encounters an exception, it prints the _entire_ stack |
| 2295 | (when (or (looking-at python-pdbtrack-stacktrace-info-regexp) | 2337 | ;; trace. To handle all of these cases, we want to find |
| 2296 | (and | 2338 | ;; the _last_ stack frame printed in the most recent |
| 2297 | (forward-line) | 2339 | ;; batch of output, then jump to the corresponding |
| 2298 | (looking-at python-pdbtrack-stacktrace-info-regexp))) | 2340 | ;; file/line number. |
| 2341 | (goto-char (point-max)) | ||
| 2342 | (when (re-search-backward python-pdbtrack-stacktrace-info-regexp nil t) | ||
| 2299 | (setq line-number (string-to-number | 2343 | (setq line-number (string-to-number |
| 2300 | (match-string-no-properties 2))) | 2344 | (match-string-no-properties 2))) |
| 2301 | (match-string-no-properties 1))))) | 2345 | (match-string-no-properties 1))))) |
| @@ -2487,12 +2531,12 @@ JUSTIFY should be used (if applicable) as in `fill-paragraph'." | |||
| 2487 | JUSTIFY should be used (if applicable) as in `fill-paragraph'." | 2531 | JUSTIFY should be used (if applicable) as in `fill-paragraph'." |
| 2488 | (let* ((marker (point-marker)) | 2532 | (let* ((marker (point-marker)) |
| 2489 | (str-start-pos | 2533 | (str-start-pos |
| 2490 | (let ((m (make-marker))) | 2534 | (set-marker |
| 2491 | (setf (marker-position m) | 2535 | (make-marker) |
| 2492 | (or (python-syntax-context 'string) | 2536 | (or (python-syntax-context 'string) |
| 2493 | (and (equal (string-to-syntax "|") | 2537 | (and (equal (string-to-syntax "|") |
| 2494 | (syntax-after (point))) | 2538 | (syntax-after (point))) |
| 2495 | (point)))) m)) | 2539 | (point))))) |
| 2496 | (num-quotes (python-syntax-count-quotes | 2540 | (num-quotes (python-syntax-count-quotes |
| 2497 | (char-after str-start-pos) str-start-pos)) | 2541 | (char-after str-start-pos) str-start-pos)) |
| 2498 | (str-end-pos | 2542 | (str-end-pos |
| @@ -2692,17 +2736,17 @@ The skeleton will be bound to python-skeleton-NAME." | |||
| 2692 | 2736 | ||
| 2693 | (python-skeleton-define def nil | 2737 | (python-skeleton-define def nil |
| 2694 | "Function name: " | 2738 | "Function name: " |
| 2695 | "def " str " (" ("Parameter, %s: " | 2739 | "def " str "(" ("Parameter, %s: " |
| 2696 | (unless (equal ?\( (char-before)) ", ") | 2740 | (unless (equal ?\( (char-before)) ", ") |
| 2697 | str) "):" \n | 2741 | str) "):" \n |
| 2698 | "\"\"\"" - "\"\"\"" \n | 2742 | "\"\"\"" - "\"\"\"" \n |
| 2699 | > _ \n) | 2743 | > _ \n) |
| 2700 | 2744 | ||
| 2701 | (python-skeleton-define class nil | 2745 | (python-skeleton-define class nil |
| 2702 | "Class name: " | 2746 | "Class name: " |
| 2703 | "class " str " (" ("Inheritance, %s: " | 2747 | "class " str "(" ("Inheritance, %s: " |
| 2704 | (unless (equal ?\( (char-before)) ", ") | 2748 | (unless (equal ?\( (char-before)) ", ") |
| 2705 | str) | 2749 | str) |
| 2706 | & ")" | -2 | 2750 | & ")" | -2 |
| 2707 | ":" \n | 2751 | ":" \n |
| 2708 | "\"\"\"" - "\"\"\"" \n | 2752 | "\"\"\"" - "\"\"\"" \n |
| @@ -2904,40 +2948,61 @@ Optional argument INCLUDE-TYPE indicates to include the type of the defun. | |||
| 2904 | This function is compatible to be used as | 2948 | This function is compatible to be used as |
| 2905 | `add-log-current-defun-function' since it returns nil if point is | 2949 | `add-log-current-defun-function' since it returns nil if point is |
| 2906 | not inside a defun." | 2950 | not inside a defun." |
| 2907 | (save-restriction | 2951 | (save-restriction |
| 2908 | (widen) | 2952 | (widen) |
| 2909 | (save-excursion | 2953 | (save-excursion |
| 2910 | (end-of-line 1) | 2954 | (end-of-line 1) |
| 2911 | (let ((names) | 2955 | (let ((names) |
| 2912 | (starting-indentation | 2956 | (starting-indentation (current-indentation)) |
| 2913 | (save-excursion | 2957 | (starting-pos (point)) |
| 2914 | (and | 2958 | (first-run t) |
| 2915 | (python-nav-beginning-of-defun 1) | 2959 | (last-indent) |
| 2916 | ;; This extra number is just for checking code | 2960 | (type)) |
| 2917 | ;; against indentation to work well on first run. | 2961 | (catch 'exit |
| 2918 | (+ (current-indentation) 4)))) | 2962 | (while (python-nav-beginning-of-defun 1) |
| 2919 | (starting-point (point))) | 2963 | (when (and |
| 2920 | ;; Check point is inside a defun. | 2964 | (or (not last-indent) |
| 2921 | (when (and starting-indentation | 2965 | (< (current-indentation) last-indent)) |
| 2922 | (< starting-point | 2966 | (or |
| 2967 | (and first-run | ||
| 2923 | (save-excursion | 2968 | (save-excursion |
| 2924 | (python-nav-end-of-defun) | 2969 | ;; If this is the first run, we may add |
| 2925 | (point)))) | 2970 | ;; the current defun at point. |
| 2926 | (catch 'exit | 2971 | (setq first-run nil) |
| 2927 | (while (python-nav-beginning-of-defun 1) | 2972 | (goto-char starting-pos) |
| 2928 | (when (< (current-indentation) starting-indentation) | 2973 | (python-nav-beginning-of-statement) |
| 2929 | (setq starting-indentation (current-indentation)) | 2974 | (beginning-of-line 1) |
| 2930 | (setq names | 2975 | (looking-at-p |
| 2931 | (cons | 2976 | python-nav-beginning-of-defun-regexp))) |
| 2932 | (if (not include-type) | 2977 | (< starting-pos |
| 2933 | (match-string-no-properties 1) | 2978 | (save-excursion |
| 2934 | (mapconcat 'identity | 2979 | (let ((min-indent |
| 2935 | (split-string | 2980 | (+ (current-indentation) |
| 2936 | (match-string-no-properties 0)) " ")) | 2981 | python-indent-offset))) |
| 2937 | names))) | 2982 | (if (< starting-indentation min-indent) |
| 2938 | (and (= (current-indentation) 0) (throw 'exit t))))) | 2983 | ;; If the starting indentation is not |
| 2939 | (and names | 2984 | ;; within the min defun indent make the |
| 2940 | (mapconcat (lambda (string) string) names ".")))))) | 2985 | ;; check fail. |
| 2986 | starting-pos | ||
| 2987 | ;; Else go to the end of defun and add | ||
| 2988 | ;; up the current indentation to the | ||
| 2989 | ;; ending position. | ||
| 2990 | (python-nav-end-of-defun) | ||
| 2991 | (+ (point) | ||
| 2992 | (if (>= (current-indentation) min-indent) | ||
| 2993 | (1+ (current-indentation)) | ||
| 2994 | 0)))))))) | ||
| 2995 | (setq last-indent (current-indentation)) | ||
| 2996 | (if (or (not include-type) type) | ||
| 2997 | (setq names (cons (match-string-no-properties 1) names)) | ||
| 2998 | (let ((match (split-string (match-string-no-properties 0)))) | ||
| 2999 | (setq type (car match)) | ||
| 3000 | (setq names (cons (cadr match) names))))) | ||
| 3001 | ;; Stop searching ASAP. | ||
| 3002 | (and (= (current-indentation) 0) (throw 'exit t)))) | ||
| 3003 | (and names | ||
| 3004 | (concat (and type (format "%s " type)) | ||
| 3005 | (mapconcat 'identity names "."))))))) | ||
| 2941 | 3006 | ||
| 2942 | (defun python-info-current-symbol (&optional replace-self) | 3007 | (defun python-info-current-symbol (&optional replace-self) |
| 2943 | "Return current symbol using dotty syntax. | 3008 | "Return current symbol using dotty syntax. |