From: Stefan Monnier Date: Fri, 16 Oct 2020 18:03:59 +0000 (-0400) Subject: * lisp/progmodes/python.el: Teach f-strings to `font-lock` X-Git-Tag: emacs-28.0.90~5590 X-Git-Url: http://git.eshelyaron.com/gitweb/?a=commitdiff_plain;h=3b3274a85c2f5df21d76d82e0d7740005aa84fdf;p=emacs.git * lisp/progmodes/python.el: Teach f-strings to `font-lock` (python--f-string-p, python--font-lock-f-strings): New functions. (python-font-lock-keywords-maximum-decoration): Use them. --- diff --git a/lisp/progmodes/python.el b/lisp/progmodes/python.el index 76baa4469c7..d1871c93a78 100644 --- a/lisp/progmodes/python.el +++ b/lisp/progmodes/python.el @@ -501,6 +501,52 @@ The type returned can be `comment', `string' or `paren'." font-lock-string-face) font-lock-comment-face)) +(defun python--f-string-p (ppss) + "Return non-nil if the pos where PPSS was found is inside an f-string." + (and (nth 3 ppss) + (let ((spos (1- (nth 8 ppss)))) + (and (memq (char-after spos) '(?f ?F)) + (or (< (point-min) spos) + (not (memq (char-syntax (char-before spos)) '(?w ?_)))))))) + +(defun python--font-lock-f-strings (limit) + "Mark {...} holes as being code. +Remove the (presumably `font-lock-string-face') `face' property from +the {...} holes that appear within f-strings." + ;; FIXME: This will fail to properly highlight strings appearing + ;; within the {...} of an f-string. + ;; We could presumably fix it by running + ;; `font-lock-fontify-syntactically-region' (as is done in + ;; `sm-c--cpp-fontify-syntactically', for example) after removing + ;; the `face' property, but I'm not sure it's worth the effort and + ;; the risks. + (let ((ppss (syntax-ppss))) + (while + (progn + (while (and (not (python--f-string-p ppss)) + (re-search-forward "\\