1

When I add this post-command-hook:

(defun insert-into-a-buffer ()
  (with-current-buffer
      (get-buffer-create "some-buffer")
    (insert "a")))

(add-hook 'post-command-hook 'insert-into-a-buffer :local)

I cannot mark text regions. This appears to be because some of the commands I use in my post-command-hook function internally set the deactivate-mark to t, which causes the (deactivate-mark) function to be run after I run my post-command-hook function.

I have tried multiple different methods of getting at the stack trace to show me how and why the (deactivate-mark) function is called, but no method has given me a stack trace that includes its caller, so it appears that (deactivate-mark) is the top-level function that is being run. This corroborates with the answer to this question, which explains that the deactivate-mark variable can be set to t during a command in order for mark to be deactivate after the command.

Exact steps to reproduce:

  • Run emacs -Q
  • (optional) Press C-SPC to set mark. Move point around. Observe that the region between point and mark is visually highlighted.
  • Enter the above code, and evaluate it.
  • Press C-SPC to set mark. Move point around. Region between point and mark is not highlighted.

Expected behavior: Region between point and mark is visually highlighted, even after evaluating those 2 lines of elisp. Actual behavior: Region between point and mark is not highlighted.


The answer linked says that as a possible fix, (setq deactivate-mark nil) can be placed at the end of your command to prevent mark from being deactivated. However, some commands such as kill-region intentionally and quite correctly set it to t. If I set (setq deactivate-mark nil) at the end of my command, I interfere with those commands' correctly deactivating mark once they are run.

That answer also says C-h v deactivate-mark says Automatically becomes buffer-local when set regarding the deactivate-mark variable, but when I run C-h v deactivate-mark, that is not mentioned. Has this been changed? I guess I'll need to do a git bisect...

  • The question is unclear. What do you mean by "I cannot mark text regions"? Be specific. Provide a recipe to repro what you see, starting from emacs -Q (no init file). Say what you see at each step, and what you expected to see instead. – Drew Mar 30 '18 at 23:46
  • @Drew See edits - added exact steps to reproduce the behavior. – jcarpenter2 Mar 30 '18 at 23:58
  • Thanks. But in that case it appears to be a duplicate question. I retracted my vote to close because it was unclear, but now it should be closed because it is a duplicate. (I can't vote for that now, myself, but others can.) – Drew Mar 31 '18 at 1:25
  • 1
    "changed between 2016 and today" - I see the usual Automatically becomes buffer-local when set. in the doc, using the latest Emacs version from emacs-26 and master compiled in the last few days. – npostavs Mar 31 '18 at 4:59
  • 1
    Note that (add-hook 'post-command-hook 'insert-into-a-buffer :local) makes the APPEND argument non-nil, not the LOCAL argument. – phils Mar 31 '18 at 10:50
1

What didn't work in Keep region activated upon completion of my command does seem to work here. You want to ignore the changes that the code you're running might make to deactivate-mark. So arrange for these changes to affect only a local variable that will no longer exist when your hook returns.

(defun insert-into-a-buffer ()
  (let (deactivate-mark)
    (with-current-buffer
        (get-buffer-create "some-buffer")
      (insert "a"))))
  • 1
    For the record this did work, however I also updated to the latest version of emacs where deactivate-mark is now a buffer-local variable, so this solution is no longer needed! – jcarpenter2 Mar 31 '18 at 21:08

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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