aboutsummaryrefslogtreecommitdiffstats
path: root/lisp/progmodes/python.el
diff options
context:
space:
mode:
authorKenichi Handa2012-10-11 20:29:47 +0900
committerKenichi Handa2012-10-11 20:29:47 +0900
commitd3e4228575e9ba9e99dc4a7dae788280ffcc4566 (patch)
tree97d35f3c0766372c166a31f3c0f7aba791a38dde /lisp/progmodes/python.el
parentcde44a7728488ca6bc6a46c18d9c5e647b160547 (diff)
parentfd2f90cf5c6a15610aa1e17e73d6d8a5f8cb1999 (diff)
downloademacs-d3e4228575e9ba9e99dc4a7dae788280ffcc4566.tar.gz
emacs-d3e4228575e9ba9e99dc4a7dae788280ffcc4566.zip
merge trunk
Diffstat (limited to 'lisp/progmodes/python.el')
-rw-r--r--lisp/progmodes/python.el475
1 files changed, 281 insertions, 194 deletions
diff --git a/lisp/progmodes/python.el b/lisp/progmodes/python.el
index 726c0b2d542..5bf64c18f99 100644
--- a/lisp/progmodes/python.el
+++ b/lisp/progmodes/python.el
@@ -235,6 +235,9 @@
235 (substitute-key-definition 'forward-sentence 235 (substitute-key-definition 'forward-sentence
236 'python-nav-forward-block 236 'python-nav-forward-block
237 map global-map) 237 map global-map)
238 (substitute-key-definition 'backward-up-list
239 'python-nav-backward-up-list
240 map global-map)
238 (define-key map "\C-c\C-j" 'imenu) 241 (define-key map "\C-c\C-j" 'imenu)
239 ;; Indent specific 242 ;; Indent specific
240 (define-key map "\177" 'python-indent-dedent-line-backspace) 243 (define-key map "\177" 'python-indent-dedent-line-backspace)
@@ -337,19 +340,28 @@
337 "==" ">=" "is" "not"))) 340 "==" ">=" "is" "not")))
338 ;; FIXME: Use regexp-opt. 341 ;; FIXME: Use regexp-opt.
339 (assignment-operator . ,(rx (or "=" "+=" "-=" "*=" "/=" "//=" "%=" "**=" 342 (assignment-operator . ,(rx (or "=" "+=" "-=" "*=" "/=" "//=" "%=" "**="
340 ">>=" "<<=" "&=" "^=" "|=")))) 343 ">>=" "<<=" "&=" "^=" "|=")))
341 "Additional Python specific sexps for `python-rx'")) 344 (string-delimiter . ,(rx (and
342 345 ;; Match even number of backslashes.
343(defmacro python-rx (&rest regexps) 346 (or (not (any ?\\ ?\' ?\")) point
344 "Python mode specialized rx macro. 347 ;; Quotes might be preceded by a escaped quote.
348 (and (or (not (any ?\\)) point) ?\\
349 (* ?\\ ?\\) (any ?\' ?\")))
350 (* ?\\ ?\\)
351 ;; Match single or triple quotes of any kind.
352 (group (or "\"" "\"\"\"" "'" "'''"))))))
353 "Additional Python specific sexps for `python-rx'")
354
355 (defmacro python-rx (&rest regexps)
356 "Python mode specialized rx macro.
345This variant of `rx' supports common python named REGEXPS." 357This variant of `rx' supports common python named REGEXPS."
346 (let ((rx-constituents (append python-rx-constituents rx-constituents))) 358 (let ((rx-constituents (append python-rx-constituents rx-constituents)))
347 (cond ((null regexps) 359 (cond ((null regexps)
348 (error "No regexp")) 360 (error "No regexp"))
349 ((cdr regexps) 361 ((cdr regexps)
350 (rx-to-string `(and ,@regexps) t)) 362 (rx-to-string `(and ,@regexps) t))
351 (t 363 (t
352 (rx-to-string (car regexps) t))))) 364 (rx-to-string (car regexps) t))))))
353 365
354 366
355;;; Font-lock and syntax 367;;; Font-lock and syntax
@@ -498,16 +510,7 @@ The type returned can be `comment', `string' or `paren'."
498 510
499(defconst python-syntax-propertize-function 511(defconst python-syntax-propertize-function
500 (syntax-propertize-rules 512 (syntax-propertize-rules
501 ((rx 513 ((python-rx string-delimiter)
502 (and
503 ;; Match even number of backslashes.
504 (or (not (any ?\\ ?\' ?\")) point
505 ;; Quotes might be preceded by a escaped quote.
506 (and (or (not (any ?\\)) point) ?\\
507 (* ?\\ ?\\) (any ?\' ?\")))
508 (* ?\\ ?\\)
509 ;; Match single or triple quotes of any kind.
510 (group (or "\"" "\"\"\"" "'" "'''"))))
511 (0 (ignore (python-syntax-stringify)))))) 514 (0 (ignore (python-syntax-stringify))))))
512 515
513(defsubst python-syntax-count-quotes (quote-char &optional point limit) 516(defsubst python-syntax-count-quotes (quote-char &optional point limit)
@@ -676,12 +679,12 @@ START is the buffer position where the sexp starts."
676 (goto-char (line-beginning-position)) 679 (goto-char (line-beginning-position))
677 (bobp)) 680 (bobp))
678 'no-indent) 681 'no-indent)
679 ;; Inside a paren
680 ((setq start (python-syntax-context 'paren ppss))
681 'inside-paren)
682 ;; Inside string 682 ;; Inside string
683 ((setq start (python-syntax-context 'string ppss)) 683 ((setq start (python-syntax-context 'string ppss))
684 'inside-string) 684 'inside-string)
685 ;; Inside a paren
686 ((setq start (python-syntax-context 'paren ppss))
687 'inside-paren)
685 ;; After backslash 688 ;; After backslash
686 ((setq start (when (not (or (python-syntax-context 'string ppss) 689 ((setq start (when (not (or (python-syntax-context 'string ppss)
687 (python-syntax-context 'comment ppss))) 690 (python-syntax-context 'comment ppss)))
@@ -710,7 +713,7 @@ START is the buffer position where the sexp starts."
710 ;; After normal line 713 ;; After normal line
711 ((setq start (save-excursion 714 ((setq start (save-excursion
712 (back-to-indentation) 715 (back-to-indentation)
713 (python-util-forward-comment -1) 716 (skip-chars-backward (rx (or whitespace ?\n)))
714 (python-nav-beginning-of-statement) 717 (python-nav-beginning-of-statement)
715 (point-marker))) 718 (point-marker)))
716 'after-line) 719 'after-line)
@@ -973,7 +976,16 @@ Called from a program, START and END specify the region to indent."
973 (back-to-indentation) 976 (back-to-indentation)
974 (setq word (current-word)) 977 (setq word (current-word))
975 (forward-line 1) 978 (forward-line 1)
976 (when word 979 (when (and word
980 ;; Don't mess with strings, unless it's the
981 ;; enclosing set of quotes.
982 (or (not (python-syntax-context 'string))
983 (eq
984 (syntax-after
985 (+ (1- (point))
986 (current-indentation)
987 (python-syntax-count-quotes (char-after) (point))))
988 (string-to-syntax "|"))))
977 (beginning-of-line) 989 (beginning-of-line)
978 (delete-horizontal-space) 990 (delete-horizontal-space)
979 (indent-to (python-indent-calculate-indentation))))) 991 (indent-to (python-indent-calculate-indentation)))))
@@ -1160,7 +1172,8 @@ Returns nil if point is not in a def or class."
1160 (python-info-line-ends-backslash-p)) 1172 (python-info-line-ends-backslash-p))
1161 (python-syntax-context 'string) 1173 (python-syntax-context 'string)
1162 (python-syntax-context 'paren)) 1174 (python-syntax-context 'paren))
1163 (forward-line -1))))) 1175 (forward-line -1))))
1176 (point-marker))
1164 1177
1165(defun python-nav-end-of-statement () 1178(defun python-nav-end-of-statement ()
1166 "Move to end of current statement." 1179 "Move to end of current statement."
@@ -1171,7 +1184,8 @@ Returns nil if point is not in a def or class."
1171 (python-info-line-ends-backslash-p) 1184 (python-info-line-ends-backslash-p)
1172 (python-syntax-context 'string) 1185 (python-syntax-context 'string)
1173 (python-syntax-context 'paren)) 1186 (python-syntax-context 'paren))
1174 (forward-line 1))))) 1187 (forward-line 1))))
1188 (point-marker))
1175 1189
1176(defun python-nav-backward-statement (&optional arg) 1190(defun python-nav-backward-statement (&optional arg)
1177 "Move backward to previous statement. 1191 "Move backward to previous statement.
@@ -1286,151 +1300,104 @@ When ARG > 0 move forward, else if ARG is < 0."
1286 (while (and (funcall search-fn paren-regexp nil t) 1300 (while (and (funcall search-fn paren-regexp nil t)
1287 (python-syntax-context 'paren))))))) 1301 (python-syntax-context 'paren)))))))
1288 1302
1289(defun python-nav--forward-sexp () 1303(defun python-nav--forward-sexp (&optional dir)
1290 "Move to forward sexp." 1304 "Move to forward sexp.
1291 (case (python-syntax-context-type) 1305With positive Optional argument DIR direction move forward, else
1292 (string 1306backwards."
1293 ;; Inside of a string, get out of it. 1307 (setq dir (or dir 1))
1294 (while (and (re-search-forward "[\"']" nil t) 1308 (unless (= dir 0)
1295 (python-syntax-context 'string)))) 1309 (let* ((forward-p (if (> dir 0)
1296 (comment 1310 (and (setq dir 1) t)
1297 ;; Inside of a comment, just move forward. 1311 (and (setq dir -1) nil)))
1298 (python-util-forward-comment)) 1312 (re-search-fn (if forward-p
1299 (paren 1313 're-search-forward
1300 (python-nav-lisp-forward-sexp-safe 1)) 1314 're-search-backward))
1301 (t 1315 (context-type (python-syntax-context-type)))
1302 (if (and (not (eobp)) 1316 (cond
1303 (= (syntax-class (syntax-after (point))) 4)) 1317 ((eq context-type 'string)
1304 ;; Looking an open-paren 1318 ;; Inside of a string, get out of it.
1305 (python-nav-lisp-forward-sexp-safe 1) 1319 (while (and (funcall re-search-fn "[\"']" nil t)
1306 (let ((block-starting-pos 1320 (python-syntax-context 'string))))
1307 (save-excursion (python-nav-beginning-of-block))) 1321 ((eq context-type 'comment)
1308 (block-ending-pos 1322 ;; Inside of a comment, just move forward.
1309 (save-excursion (python-nav-end-of-block))) 1323 (python-util-forward-comment dir))
1310 (next-block-starting-pos 1324 ((or (eq context-type 'paren)
1311 (save-excursion (python-nav-forward-block)))) 1325 (and forward-p (looking-at (python-rx open-paren)))
1312 (cond 1326 (and (not forward-p)
1313 ((not block-starting-pos) 1327 (eq (syntax-class (syntax-after (1- (point))))
1314 ;; Not inside a block, move to closest one. 1328 (car (string-to-syntax ")")))))
1315 (and next-block-starting-pos 1329 ;; Inside a paren or looking at it, lisp knows what to do.
1316 (goto-char next-block-starting-pos))) 1330 (python-nav-lisp-forward-sexp-safe dir))
1317 ((= (point) block-starting-pos) 1331 (t
1318 ;; Point is at beginning of block 1332 ;; This part handles the lispy feel of
1319 (if (and next-block-starting-pos 1333 ;; `python-nav-forward-sexp'. Knowing everything about the
1320 (< next-block-starting-pos block-ending-pos)) 1334 ;; current context and the context of the next sexp tries to
1321 ;; Beginning of next block is closer than current's 1335 ;; follow the lisp sexp motion commands in a symmetric manner.
1322 ;; end, move to it. 1336 (let* ((context
1323 (goto-char next-block-starting-pos) 1337 (cond
1324 (goto-char block-ending-pos))) 1338 ((python-info-beginning-of-block-p) 'block-start)
1325 ((= block-ending-pos (point)) 1339 ((python-info-end-of-block-p) 'block-end)
1326 ;; Point is at end of current block 1340 ((python-info-beginning-of-statement-p) 'statement-start)
1327 (let ((parent-block-end-pos 1341 ((python-info-end-of-statement-p) 'statement-end)))
1328 (save-excursion 1342 (next-sexp-pos
1329 (python-util-forward-comment) 1343 (save-excursion
1330 (python-nav-beginning-of-block) 1344 (python-nav-lisp-forward-sexp-safe dir)
1331 (python-nav-end-of-block)))) 1345 (point)))
1332 (if (and parent-block-end-pos 1346 (next-sexp-context
1333 (or (not next-block-starting-pos) 1347 (save-excursion
1334 (> next-block-starting-pos parent-block-end-pos))) 1348 (goto-char next-sexp-pos)
1335 ;; If the parent block ends before next block 1349 (cond
1336 ;; starts move to it. 1350 ((python-info-beginning-of-block-p) 'block-start)
1337 (goto-char parent-block-end-pos) 1351 ((python-info-end-of-block-p) 'block-end)
1338 (and next-block-starting-pos 1352 ((python-info-beginning-of-statement-p) 'statement-start)
1339 (goto-char next-block-starting-pos))))) 1353 ((python-info-end-of-statement-p) 'statement-end)
1340 (t (python-nav-end-of-block)))))))) 1354 ((python-info-statement-starts-block-p) 'starts-block)
1355 ((python-info-statement-ends-block-p) 'ends-block)))))
1356 (if forward-p
1357 (cond ((and (not (eobp))
1358 (python-info-current-line-empty-p))
1359 (python-util-forward-comment dir)
1360 (python-nav--forward-sexp dir))
1361 ((eq context 'block-start)
1362 (python-nav-end-of-block))
1363 ((eq context 'statement-start)
1364 (python-nav-end-of-statement))
1365 ((and (memq context '(statement-end block-end))
1366 (eq next-sexp-context 'ends-block))
1367 (goto-char next-sexp-pos)
1368 (python-nav-end-of-block))
1369 ((and (memq context '(statement-end block-end))
1370 (eq next-sexp-context 'starts-block))
1371 (goto-char next-sexp-pos)
1372 (python-nav-end-of-block))
1373 ((memq context '(statement-end block-end))
1374 (goto-char next-sexp-pos)
1375 (python-nav-end-of-statement))
1376 (t (goto-char next-sexp-pos)))
1377 (cond ((and (not (bobp))
1378 (python-info-current-line-empty-p))
1379 (python-util-forward-comment dir)
1380 (python-nav--forward-sexp dir))
1381 ((eq context 'block-end)
1382 (python-nav-beginning-of-block))
1383 ((eq context 'statement-end)
1384 (python-nav-beginning-of-statement))
1385 ((and (memq context '(statement-start block-start))
1386 (eq next-sexp-context 'starts-block))
1387 (goto-char next-sexp-pos)
1388 (python-nav-beginning-of-block))
1389 ((and (memq context '(statement-start block-start))
1390 (eq next-sexp-context 'ends-block))
1391 (goto-char next-sexp-pos)
1392 (python-nav-beginning-of-block))
1393 ((memq context '(statement-start block-start))
1394 (goto-char next-sexp-pos)
1395 (python-nav-beginning-of-statement))
1396 (t (goto-char next-sexp-pos))))))))))
1341 1397
1342(defun python-nav--backward-sexp () 1398(defun python-nav--backward-sexp ()
1343 "Move to backward sexp." 1399 "Move to backward sexp."
1344 (case (python-syntax-context-type) 1400 (python-nav--forward-sexp -1))
1345 (string
1346 ;; Inside of a string, get out of it.
1347 (while (and (re-search-backward "[\"']" nil t)
1348 (python-syntax-context 'string))))
1349 (comment
1350 ;; Inside of a comment, just move backward.
1351 (python-util-forward-comment -1))
1352 (paren
1353 ;; Handle parens like we are lisp.
1354 (python-nav-lisp-forward-sexp-safe -1))
1355 (t
1356 (let* ((block-starting-pos
1357 (save-excursion (python-nav-beginning-of-block)))
1358 (block-ending-pos
1359 (save-excursion (python-nav-end-of-block)))
1360 (prev-block-ending-pos
1361 (save-excursion (when (python-nav-backward-block)
1362 (python-nav-end-of-block))))
1363 (prev-block-parent-ending-pos
1364 (save-excursion
1365 (when prev-block-ending-pos
1366 (goto-char prev-block-ending-pos)
1367 (python-util-forward-comment)
1368 (python-nav-beginning-of-block)
1369 (python-nav-end-of-block)))))
1370 (if (and (not (bobp))
1371 (= (syntax-class (syntax-after (1- (point)))) 5))
1372 ;; Char before point is a paren closing char, handle it
1373 ;; like we are lisp.
1374 (python-nav-lisp-forward-sexp-safe -1)
1375 (cond
1376 ((not block-ending-pos)
1377 ;; Not in and ending pos, move to end of previous block.
1378 (and (python-nav-backward-block)
1379 (python-nav-end-of-block)))
1380 ((= (point) block-ending-pos)
1381 ;; In ending pos, we need to search backwards for the
1382 ;; closest point looking the list of candidates from here.
1383 (let ((candidates))
1384 (dolist (name
1385 '(prev-block-parent-ending-pos
1386 prev-block-ending-pos
1387 block-ending-pos
1388 block-starting-pos))
1389 (when (and (symbol-value name)
1390 (< (symbol-value name) (point)))
1391 (add-to-list 'candidates (symbol-value name))))
1392 (goto-char (apply 'max candidates))))
1393 ((> (point) block-ending-pos)
1394 ;; After an ending position, move to it.
1395 (goto-char block-ending-pos))
1396 ((= (point) block-starting-pos)
1397 ;; On a block starting position.
1398 (if (not (> (point) (or prev-block-ending-pos (point))))
1399 ;; Point is after the end position of the block that
1400 ;; wraps the current one, just move a block backward.
1401 (python-nav-backward-block)
1402 ;; If we got here we are facing a case like this one:
1403 ;;
1404 ;; try:
1405 ;; return here()
1406 ;; except Exception as e:
1407 ;;
1408 ;; Where point is on the "except" and must move to the
1409 ;; end of "here()".
1410 (goto-char prev-block-ending-pos)
1411 (let ((parent-block-ending-pos
1412 (save-excursion
1413 (python-nav-forward-sexp)
1414 (and (not (looking-at (python-rx block-start)))
1415 (point)))))
1416 (when (and parent-block-ending-pos
1417 (> parent-block-ending-pos prev-block-ending-pos))
1418 ;; If we got here we are facing a case like this one:
1419 ;;
1420 ;; except ImportError:
1421 ;; if predicate():
1422 ;; processing()
1423 ;; here()
1424 ;; except AttributeError:
1425 ;;
1426 ;; Where point is on the "except" and must move to
1427 ;; the end of "here()". Without this extra step we'd
1428 ;; just get to the end of processing().
1429 (goto-char parent-block-ending-pos)))))
1430 (t
1431 (if (and prev-block-ending-pos (< prev-block-ending-pos (point)))
1432 (goto-char prev-block-ending-pos)
1433 (python-nav-beginning-of-block)))))))))
1434 1401
1435(defun python-nav-forward-sexp (&optional arg) 1402(defun python-nav-forward-sexp (&optional arg)
1436 "Move forward across one block of code. 1403 "Move forward across one block of code.
@@ -1445,6 +1412,67 @@ move backward N times."
1445 (python-nav--backward-sexp) 1412 (python-nav--backward-sexp)
1446 (setq arg (1+ arg)))) 1413 (setq arg (1+ arg))))
1447 1414
1415(defun python-nav--up-list (&optional dir)
1416 "Internal implementation of `python-nav-up-list'.
1417DIR is always 1 or -1 and comes sanitized from
1418`python-nav-up-list' calls."
1419 (let ((context (python-syntax-context-type))
1420 (forward-p (> dir 0)))
1421 (cond
1422 ((memq context '(string comment)))
1423 ((eq context 'paren)
1424 (let ((forward-sexp-function))
1425 (up-list dir)))
1426 ((and forward-p (python-info-end-of-block-p))
1427 (let ((parent-end-pos
1428 (save-excursion
1429 (let ((indentation (and
1430 (python-nav-beginning-of-block)
1431 (current-indentation))))
1432 (while (and indentation
1433 (> indentation 0)
1434 (>= (current-indentation) indentation)
1435 (python-nav-backward-block)))
1436 (python-nav-end-of-block)))))
1437 (and (> (or parent-end-pos (point)) (point))
1438 (goto-char parent-end-pos))))
1439 (forward-p (python-nav-end-of-block))
1440 ((and (not forward-p)
1441 (> (current-indentation) 0)
1442 (python-info-beginning-of-block-p))
1443 (let ((prev-block-pos
1444 (save-excursion
1445 (let ((indentation (current-indentation)))
1446 (while (and (python-nav-backward-block)
1447 (> (current-indentation) indentation))))
1448 (point))))
1449 (and (> (point) prev-block-pos)
1450 (goto-char prev-block-pos))))
1451 ((not forward-p) (python-nav-beginning-of-block)))))
1452
1453(defun python-nav-up-list (&optional arg)
1454 "Move forward out of one level of parentheses (or blocks).
1455With ARG, do this that many times.
1456A negative argument means move backward but still to a less deep spot.
1457This command assumes point is not in a string or comment."
1458 (interactive "^p")
1459 (or arg (setq arg 1))
1460 (while (> arg 0)
1461 (python-nav--up-list 1)
1462 (setq arg (1- arg)))
1463 (while (< arg 0)
1464 (python-nav--up-list -1)
1465 (setq arg (1+ arg))))
1466
1467(defun python-nav-backward-up-list (&optional arg)
1468 "Move backward out of one level of parentheses (or blocks).
1469With ARG, do this that many times.
1470A negative argument means move backward but still to a less deep spot.
1471This command assumes point is not in a string or comment."
1472 (interactive "^p")
1473 (or arg (setq arg 1))
1474 (python-nav-up-list (- arg)))
1475
1448 1476
1449;;; Shell integration 1477;;; Shell integration
1450 1478
@@ -1643,6 +1671,22 @@ uniqueness for different types of configurations."
1643OUTPUT is a string with the contents of the buffer." 1671OUTPUT is a string with the contents of the buffer."
1644 (ansi-color-filter-apply output)) 1672 (ansi-color-filter-apply output))
1645 1673
1674(defvar python-shell--parent-buffer nil)
1675
1676(defvar python-shell-output-syntax-table
1677 (let ((table (make-syntax-table python-dotty-syntax-table)))
1678 (modify-syntax-entry ?\' "." table)
1679 (modify-syntax-entry ?\" "." table)
1680 (modify-syntax-entry ?\( "." table)
1681 (modify-syntax-entry ?\[ "." table)
1682 (modify-syntax-entry ?\{ "." table)
1683 (modify-syntax-entry ?\) "." table)
1684 (modify-syntax-entry ?\] "." table)
1685 (modify-syntax-entry ?\} "." table)
1686 table)
1687 "Syntax table for shell output.
1688It makes parens and quotes be treated as punctuation chars.")
1689
1646(define-derived-mode inferior-python-mode comint-mode "Inferior Python" 1690(define-derived-mode inferior-python-mode comint-mode "Inferior Python"
1647 "Major mode for Python inferior process. 1691 "Major mode for Python inferior process.
1648Runs a Python interpreter as a subprocess of Emacs, with Python 1692Runs a Python interpreter as a subprocess of Emacs, with Python
@@ -1665,7 +1709,12 @@ initialization of the interpreter via `python-shell-setup-codes'
1665variable. 1709variable.
1666 1710
1667\(Type \\[describe-mode] in the process buffer for a list of commands.)" 1711\(Type \\[describe-mode] in the process buffer for a list of commands.)"
1668 (set-syntax-table python-mode-syntax-table) 1712 (and python-shell--parent-buffer
1713 (python-util-clone-local-variables python-shell--parent-buffer))
1714 (setq comint-prompt-regexp (format "^\\(?:%s\\|%s\\|%s\\)"
1715 python-shell-prompt-regexp
1716 python-shell-prompt-block-regexp
1717 python-shell-prompt-pdb-regexp))
1669 (setq mode-line-process '(":%s")) 1718 (setq mode-line-process '(":%s"))
1670 (make-local-variable 'comint-output-filter-functions) 1719 (make-local-variable 'comint-output-filter-functions)
1671 (add-hook 'comint-output-filter-functions 1720 (add-hook 'comint-output-filter-functions
@@ -1686,10 +1735,21 @@ variable.
1686 (make-local-variable 'python-pdbtrack-tracked-buffer) 1735 (make-local-variable 'python-pdbtrack-tracked-buffer)
1687 (make-local-variable 'python-shell-internal-last-output) 1736 (make-local-variable 'python-shell-internal-last-output)
1688 (when python-shell-enable-font-lock 1737 (when python-shell-enable-font-lock
1738 (set-syntax-table python-mode-syntax-table)
1689 (set (make-local-variable 'font-lock-defaults) 1739 (set (make-local-variable 'font-lock-defaults)
1690 '(python-font-lock-keywords nil nil nil nil)) 1740 '(python-font-lock-keywords nil nil nil nil))
1691 (set (make-local-variable 'syntax-propertize-function) 1741 (set (make-local-variable 'syntax-propertize-function)
1692 python-syntax-propertize-function)) 1742 (syntax-propertize-rules
1743 (comint-prompt-regexp
1744 (0 (ignore
1745 (put-text-property
1746 comint-last-input-start end 'syntax-table
1747 python-shell-output-syntax-table)
1748 (font-lock-unfontify-region comint-last-input-start end))))
1749 ((python-rx string-delimiter)
1750 (0 (ignore
1751 (and (not (eq (get-text-property start 'field) 'output))
1752 (python-syntax-stringify))))))))
1693 (compilation-shell-minor-mode 1)) 1753 (compilation-shell-minor-mode 1))
1694 1754
1695(defun python-shell-make-comint (cmd proc-name &optional pop internal) 1755(defun python-shell-make-comint (cmd proc-name &optional pop internal)
@@ -1712,15 +1772,10 @@ killed."
1712 (let* ((cmdlist (split-string-and-unquote cmd)) 1772 (let* ((cmdlist (split-string-and-unquote cmd))
1713 (buffer (apply #'make-comint-in-buffer proc-name proc-buffer-name 1773 (buffer (apply #'make-comint-in-buffer proc-name proc-buffer-name
1714 (car cmdlist) nil (cdr cmdlist))) 1774 (car cmdlist) nil (cdr cmdlist)))
1715 (current-buffer (current-buffer)) 1775 (python-shell--parent-buffer (current-buffer))
1716 (process (get-buffer-process buffer))) 1776 (process (get-buffer-process buffer)))
1717 (with-current-buffer buffer 1777 (with-current-buffer buffer
1718 (inferior-python-mode) 1778 (inferior-python-mode))
1719 (python-util-clone-local-variables current-buffer)
1720 (setq comint-prompt-regexp (format "^\\(?:%s\\|%s\\|%s\\)"
1721 python-shell-prompt-regexp
1722 python-shell-prompt-block-regexp
1723 python-shell-prompt-pdb-regexp)))
1724 (accept-process-output process) 1779 (accept-process-output process)
1725 (and pop (pop-to-buffer buffer t)) 1780 (and pop (pop-to-buffer buffer t))
1726 (and internal (set-process-query-on-exit-flag process nil)))) 1781 (and internal (set-process-query-on-exit-flag process nil))))
@@ -1875,7 +1930,9 @@ detecting a prompt at the end of the buffer."
1875 python-shell-output-filter-buffer 1930 python-shell-output-filter-buffer
1876 (concat python-shell-output-filter-buffer string)) 1931 (concat python-shell-output-filter-buffer string))
1877 (when (string-match 1932 (when (string-match
1878 (format "\n\\(?:%s\\|%s\\|%s\\)$" 1933 ;; XXX: It seems on OSX an extra carriage return is attached
1934 ;; at the end of output, this handles that too.
1935 (format "\r?\n\\(?:%s\\|%s\\|%s\\)$"
1879 python-shell-prompt-regexp 1936 python-shell-prompt-regexp
1880 python-shell-prompt-block-regexp 1937 python-shell-prompt-block-regexp
1881 python-shell-prompt-pdb-regexp) 1938 python-shell-prompt-pdb-regexp)
@@ -2279,28 +2336,28 @@ inferior python process is updated properly."
2279 2336
2280(defcustom python-fill-comment-function 'python-fill-comment 2337(defcustom python-fill-comment-function 'python-fill-comment
2281 "Function to fill comments. 2338 "Function to fill comments.
2282This is the function used by `python-fill-paragraph-function' to 2339This is the function used by `python-fill-paragraph' to
2283fill comments." 2340fill comments."
2284 :type 'symbol 2341 :type 'symbol
2285 :group 'python) 2342 :group 'python)
2286 2343
2287(defcustom python-fill-string-function 'python-fill-string 2344(defcustom python-fill-string-function 'python-fill-string
2288 "Function to fill strings. 2345 "Function to fill strings.
2289This is the function used by `python-fill-paragraph-function' to 2346This is the function used by `python-fill-paragraph' to
2290fill strings." 2347fill strings."
2291 :type 'symbol 2348 :type 'symbol
2292 :group 'python) 2349 :group 'python)
2293 2350
2294(defcustom python-fill-decorator-function 'python-fill-decorator 2351(defcustom python-fill-decorator-function 'python-fill-decorator
2295 "Function to fill decorators. 2352 "Function to fill decorators.
2296This is the function used by `python-fill-paragraph-function' to 2353This is the function used by `python-fill-paragraph' to
2297fill decorators." 2354fill decorators."
2298 :type 'symbol 2355 :type 'symbol
2299 :group 'python) 2356 :group 'python)
2300 2357
2301(defcustom python-fill-paren-function 'python-fill-paren 2358(defcustom python-fill-paren-function 'python-fill-paren
2302 "Function to fill parens. 2359 "Function to fill parens.
2303This is the function used by `python-fill-paragraph-function' to 2360This is the function used by `python-fill-paragraph' to
2304fill parens." 2361fill parens."
2305 :type 'symbol 2362 :type 'symbol
2306 :group 'python) 2363 :group 'python)
@@ -2377,7 +2434,7 @@ SYMMETRIC:
2377 :safe (lambda (val) 2434 :safe (lambda (val)
2378 (memq val '(django onetwo pep-257 pep-257-nn symmetric nil)))) 2435 (memq val '(django onetwo pep-257 pep-257-nn symmetric nil))))
2379 2436
2380(defun python-fill-paragraph-function (&optional justify) 2437(defun python-fill-paragraph (&optional justify)
2381 "`fill-paragraph-function' handling multi-line strings and possibly comments. 2438 "`fill-paragraph-function' handling multi-line strings and possibly comments.
2382If any of the current line is in or at the end of a multi-line string, 2439If any of the current line is in or at the end of a multi-line string,
2383fill the string or the paragraph of it that point is in, preserving 2440fill the string or the paragraph of it that point is in, preserving
@@ -2396,8 +2453,7 @@ Optional argument JUSTIFY defines if the paragraph should be justified."
2396 (funcall python-fill-string-function justify)) 2453 (funcall python-fill-string-function justify))
2397 ;; Decorators 2454 ;; Decorators
2398 ((equal (char-after (save-excursion 2455 ((equal (char-after (save-excursion
2399 (back-to-indentation) 2456 (python-nav-beginning-of-statement))) ?@)
2400 (point))) ?@)
2401 (funcall python-fill-decorator-function justify)) 2457 (funcall python-fill-decorator-function justify))
2402 ;; Parens 2458 ;; Parens
2403 ((or (python-syntax-context 'paren) 2459 ((or (python-syntax-context 'paren)
@@ -2409,12 +2465,12 @@ Optional argument JUSTIFY defines if the paragraph should be justified."
2409 (t t)))) 2465 (t t))))
2410 2466
2411(defun python-fill-comment (&optional justify) 2467(defun python-fill-comment (&optional justify)
2412 "Comment fill function for `python-fill-paragraph-function'. 2468 "Comment fill function for `python-fill-paragraph'.
2413JUSTIFY should be used (if applicable) as in `fill-paragraph'." 2469JUSTIFY should be used (if applicable) as in `fill-paragraph'."
2414 (fill-comment-paragraph justify)) 2470 (fill-comment-paragraph justify))
2415 2471
2416(defun python-fill-string (&optional justify) 2472(defun python-fill-string (&optional justify)
2417 "String fill function for `python-fill-paragraph-function'. 2473 "String fill function for `python-fill-paragraph'.
2418JUSTIFY should be used (if applicable) as in `fill-paragraph'." 2474JUSTIFY should be used (if applicable) as in `fill-paragraph'."
2419 (let* ((marker (point-marker)) 2475 (let* ((marker (point-marker))
2420 (str-start-pos 2476 (str-start-pos
@@ -2484,12 +2540,12 @@ JUSTIFY should be used (if applicable) as in `fill-paragraph'."
2484 (indent-according-to-mode))))) t) 2540 (indent-according-to-mode))))) t)
2485 2541
2486(defun python-fill-decorator (&optional justify) 2542(defun python-fill-decorator (&optional justify)
2487 "Decorator fill function for `python-fill-paragraph-function'. 2543 "Decorator fill function for `python-fill-paragraph'.
2488JUSTIFY should be used (if applicable) as in `fill-paragraph'." 2544JUSTIFY should be used (if applicable) as in `fill-paragraph'."
2489 t) 2545 t)
2490 2546
2491(defun python-fill-paren (&optional justify) 2547(defun python-fill-paren (&optional justify)
2492 "Paren fill function for `python-fill-paragraph-function'. 2548 "Paren fill function for `python-fill-paragraph'.
2493JUSTIFY should be used (if applicable) as in `fill-paragraph'." 2549JUSTIFY should be used (if applicable) as in `fill-paragraph'."
2494 (save-restriction 2550 (save-restriction
2495 (narrow-to-region (progn 2551 (narrow-to-region (progn
@@ -2879,12 +2935,43 @@ parent defun name."
2879 ".") ".") 2935 ".") ".")
2880 name))))))) 2936 name)))))))
2881 2937
2882(defsubst python-info-beginning-of-block-statement-p () 2938(defun python-info-statement-starts-block-p ()
2883 "Return non-nil if current statement opens a block." 2939 "Return non-nil if current statement opens a block."
2884 (save-excursion 2940 (save-excursion
2885 (python-nav-beginning-of-statement) 2941 (python-nav-beginning-of-statement)
2886 (looking-at (python-rx block-start)))) 2942 (looking-at (python-rx block-start))))
2887 2943
2944(defun python-info-statement-ends-block-p ()
2945 "Return non-nil if point is at end of block."
2946 (let ((end-of-block-pos (save-excursion
2947 (python-nav-end-of-block)))
2948 (end-of-statement-pos (save-excursion
2949 (python-nav-end-of-statement))))
2950 (and end-of-block-pos end-of-statement-pos
2951 (= end-of-block-pos end-of-statement-pos))))
2952
2953(defun python-info-beginning-of-statement-p ()
2954 "Return non-nil if point is at beginning of statement."
2955 (= (point) (save-excursion
2956 (python-nav-beginning-of-statement)
2957 (point))))
2958
2959(defun python-info-end-of-statement-p ()
2960 "Return non-nil if point is at end of statement."
2961 (= (point) (save-excursion
2962 (python-nav-end-of-statement)
2963 (point))))
2964
2965(defun python-info-beginning-of-block-p ()
2966 "Return non-nil if point is at beginning of block."
2967 (and (python-info-beginning-of-statement-p)
2968 (python-info-statement-starts-block-p)))
2969
2970(defun python-info-end-of-block-p ()
2971 "Return non-nil if point is at end of block."
2972 (and (python-info-end-of-statement-p)
2973 (python-info-statement-ends-block-p)))
2974
2888(defun python-info-closing-block () 2975(defun python-info-closing-block ()
2889 "Return the point of the block the current line closes." 2976 "Return the point of the block the current line closes."
2890 (let ((closing-word (save-excursion 2977 (let ((closing-word (save-excursion
@@ -3109,7 +3196,7 @@ if that value is non-nil."
3109 3196
3110 (set (make-local-variable 'paragraph-start) "\\s-*$") 3197 (set (make-local-variable 'paragraph-start) "\\s-*$")
3111 (set (make-local-variable 'fill-paragraph-function) 3198 (set (make-local-variable 'fill-paragraph-function)
3112 'python-fill-paragraph-function) 3199 'python-fill-paragraph)
3113 3200
3114 (set (make-local-variable 'beginning-of-defun-function) 3201 (set (make-local-variable 'beginning-of-defun-function)
3115 #'python-beginning-of-defun-function) 3202 #'python-beginning-of-defun-function)