From 50c0669c84b04db12c668cb8850c1f2ed8e316a4 Mon Sep 17 00:00:00 2001 From: Fox Kiester Date: Sat, 9 Apr 2022 11:09:25 -0400 Subject: [PATCH 1/2] Add :general-config and add FAQ entry on avoiding performance issues Fixes #502. --- README.org | 101 +++++++++++++++++++++++++++++++++++++--- general.el | 13 ++++++ tests/general-delay2.el | 7 +++ tests/test-general.el | 12 +++++ 4 files changed, 126 insertions(+), 7 deletions(-) create mode 100644 tests/general-delay2.el diff --git a/README.org b/README.org index 721d411..dda6c0e 100644 --- a/README.org +++ b/README.org @@ -36,7 +36,7 @@ Please switch to ~general-key~ or ~general-simulate-key~. Note that keyword argu - [[#dependency-versions][Dependency Versions]] - [[#key-features][Key Features]] - [[#reading-recommendations][Reading Recommendations]] -- [[#usage-recommendations-and-documentation-clarifications][Usage Recommendations and Documentation Clarifications]] +- [[#best-practices][Best Practices]] - [[#basic-examples][Basic Examples]] - [[#general-examples][General Examples]] - [[#evil-examples][Evil Examples]] @@ -68,6 +68,7 @@ Please switch to ~general-key~ or ~general-simulate-key~. Note that keyword argu - [[#integration-with-other-packages][Integration with Other Packages]] - [[#use-package-keywords][Use-package Keywords]] - [[#general-keyword][:general Keyword]] + - [[#general-config-keyword][:general-config Keyword]] - [[#no-autoload-keyword][:no-autoload Keyword]] - [[#hook-keywords][Hook Keywords]] - [[#ghook-keyword][:ghook Keyword]] @@ -84,6 +85,7 @@ Please switch to ~general-key~ or ~general-simulate-key~. Note that keyword argu - [[#worf-integration-wrapping-worf-define-key][Worf Integration/ Wrapping ~worf-define-key~]] - [[#other-provided-definers][Other Provided Definers]] - [[#faq][FAQ]] + - [[#will-generalel-slow-my-initialization-time][Will general.el slow my initialization time?]] - [[#how-do-i-prevent-key-sequence-starts-with-non-prefix-key-errors][How do I prevent =Key sequence starts with non-prefix key= errors?]] - [[#why-dont-some-evil-keybindings-work-immediately][Why don't some evil keybindings work (immediately)?]] @@ -113,7 +115,7 @@ Please use MELPA and not MELPA stable for installing optional dependencies (e.g. - Allows using an arbitrary number of prefix keys or "leaders" of any length (but does not require prefix keys like) (unlike =evil-leader.el=) - Allows for automatically creating prefix commands (but does not require creating them like ~bind-key~ does) - Allows for buffer-local keybindings (unlike ~local-set-key~) -- Allows deferring keybindings until the specified keymap exists (no need to use ~(with-)eval-after-load~) (like ~evil-define-key~) +- Allows deferring keybindings until the specified keymap exists (no need to use ~(with-)eval-after-load~) (like ~evil-define-key~) though it is slow compared to ~eval-after-load~ and therefore not recommended - Allows displaying defined keys (like =bind-key.el=) - Provides integration with other packages such as =key-chord.el= and =which-key.el= (unique) - Provides other helpers for keybindings (unique): @@ -131,14 +133,25 @@ If you are also using evil, you should first be familiar with how ~evil-define-k A large number of issues opened on this repository are not specifically related to =general.el= (e.g. user usage or syntax errors that would also occur without ~general-define-key~). While I don't mind generic questions about keybinding issues, you may save yourself some time if you first determine whether or not an issue is related to ~general-define-key~ by, if possible, testing with an equivalent ~define-key~, ~evil-define-key~, etc. statement. -See also the [[#faq][FAQ]] for commonly asked questions. - -* Usage Recommendations and Documentation Clarifications -To facilitate extensibility and easy creation of wrappers, ~general-define-key~ uses keyword arguments to specify everything besides the key definitions, including for the =:states= and =:keymaps=. Since users will most often specify one or both of these keyword arguments, ~general-define-key~ is often less concise than ~define-key~ or ~evil-define-key~. It is for this reason that it is recommended that ~general-define-key~ not be used directly. =general.el= provides wrappers around ~general-define-key~ that take positional arguments, and it is recommended that you use these instead of ~general-define-key~. ~general-create-definer~ can also be used to create a new definer with certain default settings (e.g. prefix settings). For clarity and consistency, examples in the documentation usually use ~general-define-key~ unless the example is explicitly for a wrapper. However, [[#positional-argument-wrappers][~general-def~]] is recommended over ~general-define-key~ as it is more flexible and concise. Positional arguments are /optional but not required/, so ~general-def~ can basically act as a drop-in replacement for many key definers (including ~general-define-key~, ~define-key~, and ~evil-define-key~). Note that ~general-create-definer~ and the =:general= keyword argument for ~use-package~ use ~general-def~. I personally only use ~general-def~. +* Best Practices +To facilitate extensibility and easy creation of wrappers, ~general-define-key~ uses keyword arguments to specify everything besides the key definitions, including for the =:states= and =:keymaps=. Since users will most often specify one or both of these keyword arguments, ~general-define-key~ is often less concise than ~define-key~ or ~evil-define-key~. It is for this reason that it is recommended that ~general-define-key~ not be used directly. =general.el= provides wrappers around ~general-define-key~ that take positional arguments like ~define-key~ and ~evil-define-key~ (~general-emacs-define-key~, ~general-evil-define-key~, and ~general-def~). It is recommended that you use these instead of ~general-define-key~. ~general-create-definer~ can also be used to create a new definer with certain default settings (e.g. prefix settings). For clarity and consistency, examples in the documentation usually use ~general-define-key~ unless the example is explicitly for a wrapper. However, [[#positional-argument-wrappers][~general-def~]] is recommended over ~general-define-key~ as it is more flexible and concise. Positional arguments are /optional but not required/, so ~general-def~ can mostly act as a drop-in replacement for many key definers (including ~general-define-key~, ~define-key~, and ~evil-define-key~). Note that ~general-create-definer~ and the =:general= keyword argument for ~use-package~ use ~general-def~. I personally only use ~general-def~. Since it is more common for commands to not be sharp quoted in key definitions, this package's examples use single quotes for commands. I personally prefer to always properly sharp quote functions, so commands in the actual non-example code are always sharp quoted. -Although ~general-define-key~ will automatically defer keybindings until the specified keymaps exist, you can still use it with ~with-eval-after-load~ or use-package's =:config= keyword whenever it makes sense to. If you have a lot of keybindings, this could potentially shave some fraction of a second off of your startup time. +Although ~general-define-key~ will automatically defer keybindings until the specified keymaps exist, it is recommended you use it with ~with-eval-after-load~ or use-package's =:config= keyword instead. This is because while the deferring mechanism works, it is much slower than using ~eval-after-load~. See [[#will-generalel-slow-my-initialization-time][Will general.el slow my initialization time?]] for more information on ensuring you are not unnecessarily slowing down Emacs initialization. + +See also the rest of [[#faq][FAQ]] for commonly asked questions + +To summarize, my recommended usage of general.el looks like this: +- Use ~general-def~, other positional definers, and your own definers created with ~general-create-definer~ +- Use =use-package= +- Use =:general= for keybindings meant to load a package +- Use =:general-config= or =:config= for other keybindings +- Follow the other recommendations in [[#will-generalel-slow-my-initialization-time][Will general.el slow my initialization time?]] + +From a stylistic perspective (completely personal preference) I: +- Explicitly use the command name with =:general=, e.g. ~:general (general-def ...)~ instead of ~:general ( ...)~. This allows individually evaling the forms or moving them elsewhere without having to change them. +- Sharp quote commands (e.g. ~#'execute-extended-command~) but not lambdas * Basic Examples ** General Examples @@ -399,6 +412,9 @@ General is flexible in allowing you to choose how you write things, so if the ab (my-normal-and-insert-define-key "/" 'swiper) #+end_src +If you will be creating a definer and making a lot of keymaps it is recommended you use a prefix keymap instead of just the prefix keywords for performance reasons (see the example in + [[#will-generalel-slow-my-initialization-time][Will general.el slow my initialization time?]]). + The =:infix= keyword can be used to sandwich keys in between all of the specified prefix keys and the keys in each mapping. This is mainly useful when using multiple prefix keywords and especially when using wrappers. For example, if you wanted to define several keys that were prefixed with =SPC g= in normal state and =M-SPC g= in insert state, you could use the previous wrapper with =:infix= instead of re-specifying both =:prefix= and =:non-normal-prefix=: #+begin_src emacs-lisp (my-normal-and-insert-define-key :infix "g" ) @@ -1010,6 +1026,9 @@ One annoyance you may encounter is that the default function for indentation wil This is an annoyance you may have using other emacs packages as well and can be fixed by modifying =lisp-indent-function= (see [[http://emacs.stackexchange.com/q/10230/5278][this emacs stackexchange question]] and Fuco1's modified ~lisp-indent-function~ in one of the answers there). +*** :general-config Keyword +=:general-config= is the same as =:general= except it will be run after loading the package (after anything in =:config= is run) and will never generate any autoloads. You can use =:general= for keybindings meant to load the package and =:general-config= for keybindings only needed after the package is loaded. This will reduce Emacs initialization time if you make a lot of keybindings. + *** :no-autoload Keyword If generating autoloads for commands is not desirable, it can be disabled globally (with the =general-use-package-emit-autoloads= option), on a per-binding basis, or on a per-form basis. To skip generating autoloads for a command, use the extended command definition and set the =:no-autoload= option to non-nil. This can be particularly handy when binding to functions defined in the same use-package block, otherwise the byte-compiler complains about multiple definitions of the same function: #+begin_src emacs-lisp @@ -1407,6 +1426,74 @@ To use ~worf-define-key~ to make the definitions, =:definer 'worf= can be specif To use ~lpy-define-key~ to make the definitions, =:definer 'lpy= can be specified. * FAQ +** Will general.el slow my initialization time? +There is an open issue where I talk about improving performance when rewriting general.el (and a "no overhead" experiment), but using general.el should not cause a major increase in startup time if you follow the guidelines listed here (see #180 and #502 for the original issues). + +1. Don't use general.el's deferred keybinding functionality + +General.el borrows a generic keybinding deferring mechanism from ~evil-define-key~. If a specified keymap does not exist when ~general-define-key~ is called, it will repeatedly check if that keymap now exists after loading something new until it does (e.g. see issue #180). It is much more efficient to use ~with-eval-after-load~ or the =use-package= =:config= or =:general-config= keywords. + +#+begin_src emacs-lisp +;; If you don't load evil (or any package) immediately, do one of these +(with-eval-after-load 'evil + (general-def 'normal ";" #'evil-ex)) + +(use-package evil + :general-config + ('normal ";" #'evil-ex)) + +(use-package evil + :config + (general-def 'normal ";" #'evil-ex)) + +;; not this! +(general-def 'normal ";" #'evil-ex) +#+end_src + +2. Bind keys in a prefix map instead of always using =:prefix=, =:non-normal-prefix=, and/or =:global-prefix= + +This applies even if you are not using evil and only use =:prefix=, though it will not be nearly as much of an issue (unless you are binding in multiple keymaps). Where possible, you may have some improvements by using prefix keymaps so general.el does not have to concatenate the prefix to every key. + +In addition to requiring concatenating each prefix to all keys, the prefix keywords also require making separate keybindings for every single listed keymap. Having 2+ prefix keywords will also double the number of keybindings required (e.g. if you specify =:global-prefix= and =:prefix=, it will create 1 keybinding for each in normal state). This means if you have 3 states and 2 or 3 prefix keywords, 6x the keybindings will be required. + +Make prefix keybindings in a named prefix keymap when possible instead so that only a single ~define-key~ is required under the hood: +#+begin_src emacs-lisp +;; this will bind the prefixes to `my-prefix-map' +(general-define-key + :states '(emacs insert normal) + :prefix-map 'my-prefix-map + :global-prefix "C-c" + :non-normal-prefix "M-SPC" + :prefix "SPC") + +(general-create-definer my-map + :keymaps 'my-prefix-map) + +;; this will make one binding that will result in all the following keys being +;; bound to 'foo: +;; - C-c f in all states +;; - SPC f in normal state +;; - M-SPC f in emacs and insert states +(my-map "f" 'foo) + +;; don't do this (6x the keybindings)! +(general-create-definer my-map + :states '(emacs insert normal) + :prefix-map 'my-prefix-map + :global-prefix "C-c" + :non-normal-prefix "M-SPC" + :prefix "SPC") +(my-map "f" 'foo) +#+end_src + +3. Defer your keybindings and configuration where possible + +This applies regardless of whether you are using general.el but should be mentioned for completeness. Only use =:general= for keybindings that are meant to load a package (e.g. ~magit-status-here~). For keybindings that cannot be used or are not needed immediately (e.g. ~magit-stage~), use ~with-eval-after-load~, =:config=, or =:general-config= to defer making them until the package has loaded. If you have a lot of keybindings/packages, this will shave some time off initialization. + +4. Set =general-emit-autoloads= to =nil= (this may not significantly improve startup time) + +While this may not have a significant impact, this functionality should not be needed for most packages. If a package does not properly create autoloads for its commands already, you should make an issue asking the maintainer to add autoload cookies. + ** How do I prevent =Key sequence starts with non-prefix key= errors? By default, emacs does not support binding a key sequence where a subsequence of the key is already bound in the same keymap (e.g. you cannot bind =C-a a= to a command in a keymap where =C-a= is already bound to a command). diff --git a/general.el b/general.el index 61e374e..8c4da3a 100644 --- a/general.el +++ b/general.el @@ -2636,6 +2636,19 @@ Return something like '((some-command-to-autoload . command) ...)." :package ',name))) args)))) + ;; ** :general-config Keyword + (setq use-package-keywords + (cl-loop for item in use-package-keywords + if (eq item :config) + collect :config and collect :general-config + else + ;; don't add duplicates + unless (eq item :general-config) + collect item)) + (defalias 'use-package-normalize/:general-config + #'use-package-normalize/:general) + (defalias 'use-package-handler/:general-config #'use-package-handler/:general) + ;; ** :ghook and :gfhook Keyword (setq use-package-keywords ;; should go in the same location as :bind diff --git a/tests/general-delay2.el b/tests/general-delay2.el new file mode 100644 index 0000000..0550150 --- /dev/null +++ b/tests/general-delay2.el @@ -0,0 +1,7 @@ +;;; general-delay2.el --- For testing delayed keybindings. +;;; Commentary: +;;; Code: +(defvar general-delay2-map (make-sparse-keymap)) + +(provide 'general-delay2) +;;; general-delay2.el ends here diff --git a/tests/test-general.el b/tests/test-general.el index 2fdc32f..c8b4636 100644 --- a/tests/test-general.el +++ b/tests/test-general.el @@ -1061,6 +1061,18 @@ Return t if successful or a cons corresponding to the failed key and def." '(:def symbol/command :wk "replacement" :no-autoload t)) :to-equal nil))) +;; *** :general-config +(describe "the :general-config use-package keyword" + (it "should work like :general but after a package is loaded" + (use-package general-delay2 + :defer t + :general-config + (general-def general-delay2-map "a" #'a)) + (expect (not (boundp 'general-delay2-map))) + (require 'general-delay2) + (expect (general-test-keys nil general-delay2-map + "a" #'a)))) + ;; *** :ghook (describe "the :ghook use-package keyword" (before-all From b1090d7e5097aec30504ffc5f2fa6bc63f9c3e0b Mon Sep 17 00:00:00 2001 From: Fox Kiester Date: Wed, 31 Jan 2024 09:16:29 -0500 Subject: [PATCH 2/2] Add documentation of project status and :which-key Addresses #505 and #557. --- README.org | 58 +++++++++++++++++++++++++++++++++++++++++++++++++----- 1 file changed, 53 insertions(+), 5 deletions(-) diff --git a/README.org b/README.org index dda6c0e..d214391 100644 --- a/README.org +++ b/README.org @@ -16,6 +16,41 @@ A general is a leader. -- onioncheese #+END_QUOTE +* Project Status +** General.el is Stable +#+BEGIN_QUOTE +The joke from when I worked in Google was "deprecated means stable" -- romwell +#+END_QUOTE + +General.el will eventually (maybe a decade from now) be superseded by a rewrite, or I will recommend a different package instead. However this does not mean I will "deprecate" general, only that I will not add new features and will recommend the rewrite to any newcomers. If you are already happy with general, stick with it. It has been stable for years and had very new few bug reports or feature requests. I will not remove the package from MELPA, just limit changes to bug fixes. All existing feature requests for general.el will either be implemented in the rewrite or have open issues on its tracker. If you need any new functionality, you should switch (or use both as you gradually transition, e.g. the rewrite for new keybindings or specific cases). + +** Roadmap +To rewrite general.el, I have split its functionality into separate packages that I will incrementally develop and add to MELPA roughly in this order: + +- [[https://github.com/noctuid/annalist.el][annalist]] - Replaces general's key recording/displaying utilities in a generic way (already on MELPA) +- [[https://github.com/emacs-magus/once][once]] - Better deferred evaluation utilities (like those provided in Doom); the main use case is to simplify autoloading packages (replaces general helpers like ~general-after-gui~, ~general-after-init~, and ~general-with-package~) +- [[https://github.com/emacs-magus/satch.el][satch.el]] - More convenient helpers for settings, hooks, and advice (replaces ~general-setq~, ~general-add-hook~, and ~general-advice-add~) +- [[https://github.com/emacs-magus/arcana][arcana]] - Miscellaneous key definitions helpers (to create commands/definitions not keybindings; replaces ~general-key~, ~general-simulate-key~, ~general-key-dispatch~, ~general-predicate-dispatch~, etc.) +- [[https://github.com/emacs-magus/usul][usul]] - Library/dsl for creating key definers (using context-sensitive local macros; basically [[https://www.emacswiki.org/emacs/SetupEl][setup.el]] but for keybindings) +- [[https://github.com/emacs-magus/familiar][familiar]] - general-like key definer built on top of usul + - [[https://github.com/emacs-magus/imp][imp]] - evil support for familiar + +The current status is that once.el is nearly ready to be on MELPA. If you are interested in using once.el, feel free to bump issues there to remind me to finish it/put it on MELPA. The other packages are very low priority to me, and I don't have plans to work on them for now. + +** Making the Most of General +- See [[#will-generalel-slow-my-initialization-time][Will general.el slow my initialization time?]] +- See [[#best-practices][Best Practices]] + +Eventually I will segment general, so you can optionally only load the keybinding helpers, but this won't really save much time when loading it. + +** Why Rewrite +- Breaking changes to syntax and extension system are necessary to improve the package, and I can't make breaking changes in general.el without breaking people's configurations. +- General.el does too many things. Many users think it only provides keybinding helpers or are overwhelmed by the size of this readme. It should be split into more focused packages for simplicity and clarity and so that users can use only the packages they need. +- The implementation is inflexible. Evil support, for example, is hardcoded rather than added in a separate package using the extension system. The new implementation will be built on top of a library that will do all the heavy lifting but be syntax-agnostic. The library could be used to build a definer with any syntax (e.g. ~bind-key~ syntax), so if I decided in the future that some syntax was preferable to general's, a full rewrite would not be necessary. +- General.el is not transparent. A large amount of the opened issues are questions caused by a misunderstanding normal keybindings work or how general translates to normal keybindings (e.g. questions about things that happen even if you don't use general but just ~define-key~ or ~evil-define-key~). The rewrite will provide an "instructor" (leto.el) that will generate a readable expansion given a key definition form to show you the actual code that will end up running (e.g. ~define-key~). This will help new users learn what the key definer is actually doing and will help determine whether issues are actually bugs or not. + +For a more detailed explanation, see [[https://github.com/noctuid/general.el/issues/497#issuecomment-1120235049][issue 497]]. + * Recent Breaking Changes :noexport: ** 2018-01-21 =general-default-...= variables are obsolete =general-default-prefix=, =general-default-non-normal-prefix=, =general-default-global-prefix=, =general-default-states=, and =general-default-keymaps= still work. However, they will eventually be removed, so please switch to using ~general-create-definer~ if you want to use a definer with different defaults. @@ -32,6 +67,11 @@ If you update general, please make sure that you are also using a recent version Please switch to ~general-key~ or ~general-simulate-key~. Note that keyword arguments have replaced the positional arguments of ~general-simulate-keys~. ~general-simulate-keys~ will likely be removed sometime in the future. * Table of Contents :noexport:TOC: +- [[#project-status][Project Status]] + - [[#generalel-is-stable][General.el is Stable]] + - [[#roadmap][Roadmap]] + - [[#making-the-most-of-general][Making the Most of General]] + - [[#why-rewrite][Why Rewrite]] - [[#about][About]] - [[#dependency-versions][Dependency Versions]] - [[#key-features][Key Features]] @@ -144,9 +184,10 @@ See also the rest of [[#faq][FAQ]] for commonly asked questions To summarize, my recommended usage of general.el looks like this: - Use ~general-def~, other positional definers, and your own definers created with ~general-create-definer~ -- Use =use-package= +- Use =use-package= or a similar helper - Use =:general= for keybindings meant to load a package - Use =:general-config= or =:config= for other keybindings +- Do not use use the =:which-key= extended definition keyword unless you absolutely need to (see [[#which-key-integration][Which Key Integration]] for details) - Follow the other recommendations in [[#will-generalel-slow-my-initialization-time][Will general.el slow my initialization time?]] From a stylistic perspective (completely personal preference) I: @@ -1266,6 +1307,12 @@ Using this feature, a key can be bound to a keymap that does not exist yet and s =:package= is a helper keyword that can be specified locally within the extended definition or globally. When using the use-package =:general= keyword, it will automatically be specified. ** Which Key Integration +*NOTE*: Which-key integration was added to general before which-key had [[https://github.com/justbur/emacs-which-key#keymap-based-replacement][keymap-based replacement]]. It is recommended that you *never* use general's =:which-key= when it is possible to use keymap-based replacement instead. This is because keymap-based replacement is more performant and will give correct results in cases where a basic =:which-key= will not. The exception where ~which-key-replacement-alist~ is still very useful is when you need more advanced matching/replacement capabilities or want to replace what shows up for the key, not just the definition. Most users should never need =:which-key=, and any basic =:which-key "string"= (doesn't change the text shown for the key) can definitely be swapped to use keymap-based replacement. + +To use keymap-based replacement, just bind your key to a cons cell in the form ~(cons "key description" )~, e.g. ~(general-def "" '("" . ))~. The definition can be a command, prefix map, or whatever. Please see the which-key documentation for more details. + +The rest of this section is related to general's =:which-key= keyword and should be ignored if you use keymap-based replacement. + If you are not already familiar with which-key's replacement system, please see the docstring for ~which-key-replacement-alist~ if you don't understand any of the examples or information here. There are several benefits to using general.el to add which-key replacements. The main benefit is that because the keys and definition are already specified, general.el can automatically assemble the match cons. This reuse of information saves a little space since it is not necessary to make an additional call to ~which-key-add-key-based-replacements~ with the key information. It is also useful since which-key does not currently provide any convenience function for creating a replacement that matches a binding (you have to manually add to ~which-key-replacement-alist~). However, see which-key's [[https://github.com/justbur/emacs-which-key#automatic][which-key-enable-extended-define-key]] which provides another method for automatically creating replacements and binding keys simultaneously. @@ -1431,10 +1478,11 @@ There is an open issue where I talk about improving performance when rewriting g 1. Don't use general.el's deferred keybinding functionality -General.el borrows a generic keybinding deferring mechanism from ~evil-define-key~. If a specified keymap does not exist when ~general-define-key~ is called, it will repeatedly check if that keymap now exists after loading something new until it does (e.g. see issue #180). It is much more efficient to use ~with-eval-after-load~ or the =use-package= =:config= or =:general-config= keywords. +General.el borrows a generic keybinding deferring mechanism from ~evil-define-key~. If a specified keymap does not exist when ~general-define-key~ is called, it will repeatedly check if that keymap now exists after loading something new until it does (e.g. see issue #180). It is much more efficient to use ~with-eval-after-load~, the =use-package= =:config=, the =:general-config= keyword, or any other similar functionality instead. #+begin_src emacs-lisp -;; If you don't load evil (or any package) immediately, do one of these +;; If you don't load evil (or any package that creates a keymap you are binding +;; keys in) immediately, do one of these (with-eval-after-load 'evil (general-def 'normal ";" #'evil-ex)) @@ -1469,8 +1517,8 @@ Make prefix keybindings in a named prefix keymap when possible instead so that o (general-create-definer my-map :keymaps 'my-prefix-map) -;; this will make one binding that will result in all the following keys being -;; bound to 'foo: +;; this will make one keybinding that will result in all the following keys +;; being bound to 'foo: ;; - C-c f in all states ;; - SPC f in normal state ;; - M-SPC f in emacs and insert states