Как использовать Flyspell, чтобы эффективно исправить предыдущее слово?


18

С того момента, как я начал использовать Flyspell, им всегда было больно пользоваться. Я редко проверяю весь буфер на наличие слов с ошибками, обычно я печатаю и, как только я вижу подчеркнутое слово, я хочу немедленно исправить его и продолжить ввод. Это просто потому, что я боюсь забыть исправить слово позже и потому что, когда я начинаю всестороннюю проверку буфера, iSpell выдает слишком много ложных срабатываний. Таким образом, почти всегда я исправляю слова как можно скорее, пока я печатаю.

Вот встроенные функции, о которых я знаю, и причины, по которым они неэффективны (для меня):

  • flyspell-correct-word- Это связано с щелчком мыши. Забудь об этом, я не собираюсь использовать мышь.

  • flyspell-correct-word-before-point- Я использовал это в течение некоторого времени. У него есть два недостатка:

    1. По умолчанию в нем отображается меню GUI, с которым трудно работать без мыши, и оно действительно громоздко, когда у вас есть список исправлений с более чем 10 элементами.

    2. Это не работает на слово задолго до момента. Я печатаю быстро, и когда я замечаю слово с ошибкой, у меня обычно есть одно или два слова между словом с ошибкой и точкой. Мне нужно переместить точку, исправить слово, вернуться назад. Ой.

  • flyspell-auto-correct-word - См. Пункт 2, плюс он не работает, если у вас длинный список завершений (из-за цикличности).

В: Как я могу эффективно использовать Flyspell, используя клавиатуру, имея возможность выбирать из списка завершений без зацикливания, и имея возможность исправлять даже более или менее отдаленные слова?

Приемлемые ответы включают пакеты, которые помогают перейти к предыдущему слову с ошибкой, исправить его и получить обратно или что-то в этом роде, а также небольшие фрагменты, возможно, из вашего собственного файла конфигурации, поскольку я полагаю, что другие люди придумали способы эффективного взаимодействия с Flyspell.

Ответы:


14

Встроенный flyspell-auto-correct-previous-wordработает как очарование для меня. Я связал это с, F12и я не оглядывался назад. Для меня это всегда правильно слова, независимо от того, сколько слов назад было неправильное слово.

Из документации по функции:

flyspell-auto-correct-previous-word is an interactive compiled Lisp
function in `flyspell.el'.

(flyspell-auto-correct-previous-word POSITION)

For more information check the manuals.

Auto correct the first misspelled word that occurs before point.
But don't look beyond what's visible on the screen.

Кроме того, если в первый раз автозамена не дала вам правильного слова, продолжайте нажимать свой связанный ключ ( F12в моем случае), чтобы просмотреть все варианты.

[Мой конфиг проверки орфографии]


1
Я вижу, вам все еще нужно выполнить цикл, хотя все возможные исправления. Попробуйте, ttwoнапример, хотя в моем меню я вижу 26 предложенных исправлений!
Марк Карпов

3
ttwoавтокоррекция до twoпервой попытки. Но я знаю, что вы имеете в виду. Из практического опыта, примерно в 90% случаев первая попытка дает правильное слово, вероятно, оставшиеся 9% требуют 2-3 попытки, а последний 1% - это когда flyspell просто не понимает, и мне нужно идти через 5+ попыток (или я это вручную исправляю).
Каушал Моди

Я вижу, у вашего метода есть свои преимущества (простота). Может быть, я все-таки переключусь на это.
Марк Карпов

2
Очень приятно - это то, что я ожидал найти, и пропустил, потому что привязывал ключ по умолчанию к чему-то другому. Это связано C-;по умолчанию, и вы можете настроить flyspell-auto-correct-bindingпривязку к другому ключу на карте flyspell. (Или просто связать это обычным способом, конечно.)
glucas

6

Я уверен, что другие люди придумают различные решения, которые будут полезны для будущих читателей. Однако вот как я в настоящее время справляюсь с этим.

Я думаю, что flyspell-correct-word-before-pointэто хорошее место для старта, потому что, по крайней мере, его можно вызвать нажатием клавиши, и он отображает меню возможных исправлений. Для исправления меню я написал пакет Ace Popup Menu, который использует Avy в качестве бэкэнда. Это заменяет всплывающее меню графического интерфейса пользователя, которое flyspell-correct-word-before-pointиспользует (функция вызывается x-popup-menu) текстовым всплывающим меню, которое представляет помеченные пункты меню: один или два нажатия клавиш, и все готово.

Чтобы решить вторую проблему (невозможность исправить слова «на расстоянии»), я написал этот помощник:

(defun flyspell-correct-previous (&optional words)
  "Correct word before point, reach distant words.

WORDS words at maximum are traversed backward until misspelled
word is found.  If it's not found, give up.  If argument WORDS is
not specified, traverse 12 words by default.

Return T if misspelled word is found and NIL otherwise.  Never
move point."
  (interactive "P")
  (let* ((Δ (- (point-max) (point)))
         (counter (string-to-number (or words "12")))
         (result
          (catch 'result
            (while (>= counter 0)
              (when (cl-some #'flyspell-overlay-p
                             (overlays-at (point)))
                (flyspell-correct-word-before-point)
                (throw 'result t))
              (backward-word 1)
              (setq counter (1- counter))
              nil))))
    (goto-char (- (point-max) Δ))
    result))

Это похоже на работу.


5

С помощью helm-flyspell вы можете эффективно выбирать из списка исправлений. Я использую следующий код, чтобы перейти к ошибкам и исправить их, он сохраняет положение точки, mark-ringчтобы вы могли вернуться к той позиции, где вы начали или исправили слова ранее:

(defun flyspell-goto-previous-error (arg)
  "Go to arg previous spelling error."
  (interactive "p")
  (while (not (= 0 arg))
    (let ((pos (point))
          (min (point-min)))
      (if (and (eq (current-buffer) flyspell-old-buffer-error)
               (eq pos flyspell-old-pos-error))
          (progn
            (if (= flyspell-old-pos-error min)
                ;; goto beginning of buffer
                (progn
                  (message "Restarting from end of buffer")
                  (goto-char (point-max)))
              (backward-word 1))
            (setq pos (point))))
      ;; seek the next error
      (while (and (> pos min)
                  (let ((ovs (overlays-at pos))
                        (r '()))
                    (while (and (not r) (consp ovs))
                      (if (flyspell-overlay-p (car ovs))
                          (setq r t)
                        (setq ovs (cdr ovs))))
                    (not r)))
        (backward-word 1)
        (setq pos (point)))
      ;; save the current location for next invocation
      (setq arg (1- arg))
      (setq flyspell-old-pos-error pos)
      (setq flyspell-old-buffer-error (current-buffer))
      (goto-char pos)
      (if (= pos min)
          (progn
            (message "No more miss-spelled word!")
            (setq arg 0))))))


(defun check-previous-spelling-error ()
  "Jump to previous spelling error and correct it"
  (interactive)
  (push-mark-no-activate)
  (flyspell-goto-previous-error 1)
  (call-interactively 'helm-flyspell-correct))

(defun check-next-spelling-error ()
  "Jump to next spelling error and correct it"
  (interactive)
  (push-mark-no-activate)
  (flyspell-goto-next-error)
  (call-interactively 'helm-flyspell-correct))

(defun push-mark-no-activate ()
  "Pushes `point' to `mark-ring' and does not activate the region
 Equivalent to \\[set-mark-command] when \\[transient-mark-mode] is disabled"
  (interactive)
  (push-mark (point) t nil)
  (message "Pushed mark to ring"))
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.