7

Can I filter what Flyspell may check in the buffer? I don't want it to spell-check code in Markdown mode.

Maybe I can use the font-face at point for that? Something like this:

(let ((get-char-property (point) 'face))
  (when (equal face "markdown-pre-face")
    ;; no spell-check
    ))

This question is similar, but the solution there works only for Org-mode.

2
  • You can use C-u C-x = to inspect the faces at point inside a Markdown code block.
    – user227
    Commented Feb 12, 2016 at 11:47
  • @lunaryorn in my markdown-mode, the code is all the same font (markdown-pre-face). The question is how to pass that info to Flyspell.
    – katspaugh
    Commented Feb 12, 2016 at 12:34

2 Answers 2

6

The accepted answer for org-mode is written by me. org-mode is tricky because its own check-word-predicate is already defined.

markdown is simpler because it uses default predicate provided by flyspell-mode,

(defun flyspell-generic-textmode-verify ()
  "Used for `flyspell-generic-check-word-predicate' in text modes."
  ;; (point) is next char after the word. Must check one char before.
  (let ((f (get-text-property (- (point) 1) 'face)))
    (not (memq f '(markdown-pre-face)))))

(setq flyspell-generic-check-word-predicate 'flyspell-generic-textmode-verify)
(flyspell-mode 1)

By the way, M-x describe-function ENTER flyspell-prog-mode ENTER, you will find similar setup.

Use the Source, Luke.

3
  • How cool! Actually, I did describe-function with Helm and filtered by flyspell verify, but somehow missed flyspell-generic-textmode-verify. Thanks!
    – katspaugh
    Commented Feb 12, 2016 at 12:35
  • flyspell-generic-textmode-verify does not exist in flyspell-mode, it's defined by me. So you need insert its definition into ~/.emacs.
    – chen bin
    Commented Feb 12, 2016 at 12:41
  • Oh, true. I've checked it, and it works beautifully. Thank you!
    – katspaugh
    Commented Feb 12, 2016 at 12:42
3

Thanks to chen bin, I have added a flyspell-generic-check-word-predicate function to Markdown mode. If you're using the latest development version, or use the next release version, then you won't have to use local modifications to achieve this.

For those curious, perhaps to implement a predicate for another mode, the current function is below. It checks for code blocks, inline code, and comments using functions defined by Markdown mode. It also checks for certain faces to ignore: reference labels, Markdown markup, and URLs.

    (defun markdown-flyspell-check-word-p ()
      "Return t if `flyspell' should check word just before point.
    Used for `flyspell-generic-check-word-predicate'."
      (save-excursion
        (goto-char (1- (point)))
        (not (or (markdown-code-block-at-point-p)
                 (markdown-inline-code-at-point-p)
                 (markdown-in-comment-p)
                 (let ((faces (get-text-property (point) 'face)))
                   (if (listp faces)
                       (or (memq 'markdown-reference-face faces)
                           (memq 'markdown-markup-face faces)
                           (memq 'markdown-url-face faces))
                     (memq faces '(markdown-reference-face
                                   markdown-markup-face
                                   markdown-url-face))))))))

Note that the face property may be a list, so this function handles that case as well.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.