How to call enlarge-window function depends on current window in Emacs - emacs

I set keybinding like following.
(global-set-key [M-down] 'shrink-window)
(global-set-key [M-up] 'enlarge-window)
So with M-up I can enlarge-window and with M-down otherwise.
But I want to enlarge window with M-up if current window is lower side.
And if current window is upper side with M-up I want to call shrink-window function.
Likewise I want to shrink window with M-down if current window is lower side and enlarge if current window is upper side.
In other words, I want to indicate the direction of window separator.
How can I write the function?

I was just finishing this code as the answer came up. Oh well.
(require 'windmove)
(global-set-key [M-up]
(lambda() (interactive)
(call-interactively
(if (windmove-find-other-window 'up)
'enlarge-window
'shrink-window))))
(global-set-key [M-down]
(lambda() (interactive)
(call-interactively
(if (not (windmove-find-other-window 'up))
'enlarge-window
'shrink-window))))

Taking advantage of windmove being part of emacs, this is what you can do:
(require 'windmove)
(defun move-separator-up (arg)
(interactive "p")
(if (< (cdr (windmove-other-window-loc 'up)) 0)
(shrink-window arg)
(enlarge-window arg)))
(defun move-separator-down (arg)
(interactive "p")
(if (< (cdr (windmove-other-window-loc 'up)) 0)
(enlarge-window arg)
(shrink-window arg)))
When you have 3 windows, enlarge-window and shrink-window rules might not do always what you want, so some further customization might be needed.

Related

How to hide emacs buffers (for good) [duplicate]

I'd like to make a simple change to Emacs so that the next-buffer and previous-buffer commands (which I have bound to C-x <RIGHT> and C-x <LEFT> will skip over the *Messages* buffer.
I'm using Emacs 24 and the Emacs Starter Kit.
I've read the following related questions and answers, but they are not what I want:
Buffer cycling in Emacs: avoiding scratch and Messages buffer
Emacs disable *Messages* buffer
Emacs Lisp Buffer out of focus function?
Here are some of the reasons why they don't work:
I'd like to keep it as simple as possible. Fewer configuration changes are better.
I don't want to kill or prevent *Messages* altogether.
(add-to-list 'ido-ignore-buffers "^\*Messages\*" helps with my C-x b (ido-switch-buffer) but does not change how next-buffer and previous-buffer behave.
This way you can avoid the infinite loop:
(defun next-code-buffer ()
(interactive)
(let (( bread-crumb (buffer-name) ))
(next-buffer)
(while
(and
(string-match-p "^\*" (buffer-name))
(not ( equal bread-crumb (buffer-name) )) )
(next-buffer))))
(global-set-key [remap next-buffer] 'next-code-buffer)
This code loops over non-starred buffers ("^\*"). For your case (only avoid *Messages*) it would be:
(defun next-code-buffer ()
(interactive)
(let (( bread-crumb (buffer-name) ))
(next-buffer)
(while
(and
(equal "*Messages*" (buffer-name))
(not ( equal bread-crumb (buffer-name) )) )
(next-buffer))))
(global-set-key [remap next-buffer] 'next-code-buffer)
You can write previous-code-buffer just replacing every next-buffer with previous-buffer.
The simplest I can think of is defining an advice for both functions. Here it is for next-buffer. Similarly would be for previous-buffer. You can also define a configuration variable to enable/disable the behavior (or activating/deactivating the advice):
(defadvice next-buffer (after avoid-messages-buffer-in-next-buffer)
"Advice around `next-buffer' to avoid going into the *Messages* buffer."
(when (string= "*Messages*" (buffer-name))
(next-buffer)))
;; activate the advice
(ad-activate 'next-buffer)
Maybe you can compare buffers in some other way instead of its string name, but that will work. The code for previous buffer is almost the same. I don't know either if there is a way of calling the original function without triggering the advice once inside the advice itself, but again, the code will work even if the name of the buffer is tested afterwards (will fail if you just have one buffer, and it is the messages buffer; some code can check if there is just one buffer and don't call next-buffer again).
If you want to use a standalone function that does the same thing:
(defun my-next-buffer ()
"next-buffer, only skip *Messages*"
(interactive)
(next-buffer)
(when (string= "*Messages*" (buffer-name))
(next-buffer)))
(global-set-key [remap next-buffer] 'my-next-buffer)
(global-set-key [remap previous-buffer] 'my-next-buffer)
This is what I'm using, based on Diego's answer:
(setq skippable-buffers '("*Messages*" "*scratch*" "*Help*"))
(defun my-next-buffer ()
"next-buffer that skips certain buffers"
(interactive)
(next-buffer)
(while (member (buffer-name) skippable-buffers)
(next-buffer)))
(defun my-previous-buffer ()
"previous-buffer that skips certain buffers"
(interactive)
(previous-buffer)
(while (member (buffer-name) skippable-buffers)
(previous-buffer)))
(global-set-key [remap next-buffer] 'my-next-buffer)
(global-set-key [remap previous-buffer] 'my-previous-buffer)
It is not great yet, because it will hang if there are no buffers other than the skippable-buffers I list. I use C-g to break out of the loop when it happens as a hackaround.
As RubenCaro's answer points out, the other answers can enter infinite loops. I thought David James' approach of a skippable buffers list was a bit nicer, though, so here's a variant of that.
(setq my-skippable-buffers '("*Messages*" "*scratch*" "*Help*"))
(defun my-change-buffer (change-buffer)
"Call CHANGE-BUFFER until current buffer is not in `my-skippable-buffers'."
(let ((initial (current-buffer)))
(funcall change-buffer)
(let ((first-change (current-buffer)))
(catch 'loop
(while (member (buffer-name) my-skippable-buffers)
(funcall change-buffer)
(when (eq (current-buffer) first-change)
(switch-to-buffer initial)
(throw 'loop t)))))))
(defun my-next-buffer ()
"`next-buffer' that skips `my-skippable-buffers'."
(interactive)
(my-change-buffer 'next-buffer))
(defun my-previous-buffer ()
"`previous-buffer' that skips `my-skippable-buffers'."
(interactive)
(my-change-buffer 'previous-buffer))
(global-set-key [remap next-buffer] 'my-next-buffer)
(global-set-key [remap previous-buffer] 'my-previous-buffer)

How to highlight a particular line in emacs?

I need to highlight facility for emacs in order to mark some lines in file while working with it.
It should be smth like M-s h l but should work based on line number, not on a regexp. I want to highlight a current line, but the hl-line-mode is not suitable, as I need to highlight many lines, every time I press a specific key on each of them.
I just quickly wrote the following:
(defun find-overlays-specifying (prop pos)
(let ((overlays (overlays-at pos))
found)
(while overlays
(let ((overlay (car overlays)))
(if (overlay-get overlay prop)
(setq found (cons overlay found))))
(setq overlays (cdr overlays)))
found))
(defun highlight-or-dehighlight-line ()
(interactive)
(if (find-overlays-specifying
'line-highlight-overlay-marker
(line-beginning-position))
(remove-overlays (line-beginning-position) (+ 1 (line-end-position)))
(let ((overlay-highlight (make-overlay
(line-beginning-position)
(+ 1 (line-end-position)))))
(overlay-put overlay-highlight 'face '(:background "lightgreen"))
(overlay-put overlay-highlight 'line-highlight-overlay-marker t))))
(global-set-key [f8] 'highlight-or-dehighlight-line)
(Here find-overlays-specifying came from the manual page)
It will highlight current line, and when used again it will remove it.
Maybe the following could be useful as well: removing all your highlight from the buffer (could be dangerous, you might not want it if you highlight important things)
(defun remove-all-highlight ()
(interactive)
(remove-overlays (point-min) (point-max))
)
(global-set-key [f9] 'remove-all-highlight)
You can use bm.el. You can install bm.el from MELPA.
bm.el provides bm-toggle to highlight and unhighlight current line.
bm.el also provides bm-bookmark-regexp which highlights only matched lines.
And you can jump between highlighted lines by bm-previous and bm-next
Following is sample configuration of bm.el
(require 'bm)
(global-set-key (kbd "<f5>") 'bm-toggle)
(global-set-key (kbd "<f6>") 'bm-previous)
(global-set-key (kbd "<f7>") 'bm-next)
(global-set-key (kbd "<f8>") 'bm-bookmark-regexp)
Bookmark+ does what you are asking for. Use C-x p RET (by default) to set a bookmark at point. And you can configure the kind of highlighting you want for such bookmarks. This is similar to what bm.el offers (syohex's answer), but more flexible.

Make emacs next-buffer skip *Messages* buffer

I'd like to make a simple change to Emacs so that the next-buffer and previous-buffer commands (which I have bound to C-x <RIGHT> and C-x <LEFT> will skip over the *Messages* buffer.
I'm using Emacs 24 and the Emacs Starter Kit.
I've read the following related questions and answers, but they are not what I want:
Buffer cycling in Emacs: avoiding scratch and Messages buffer
Emacs disable *Messages* buffer
Emacs Lisp Buffer out of focus function?
Here are some of the reasons why they don't work:
I'd like to keep it as simple as possible. Fewer configuration changes are better.
I don't want to kill or prevent *Messages* altogether.
(add-to-list 'ido-ignore-buffers "^\*Messages\*" helps with my C-x b (ido-switch-buffer) but does not change how next-buffer and previous-buffer behave.
This way you can avoid the infinite loop:
(defun next-code-buffer ()
(interactive)
(let (( bread-crumb (buffer-name) ))
(next-buffer)
(while
(and
(string-match-p "^\*" (buffer-name))
(not ( equal bread-crumb (buffer-name) )) )
(next-buffer))))
(global-set-key [remap next-buffer] 'next-code-buffer)
This code loops over non-starred buffers ("^\*"). For your case (only avoid *Messages*) it would be:
(defun next-code-buffer ()
(interactive)
(let (( bread-crumb (buffer-name) ))
(next-buffer)
(while
(and
(equal "*Messages*" (buffer-name))
(not ( equal bread-crumb (buffer-name) )) )
(next-buffer))))
(global-set-key [remap next-buffer] 'next-code-buffer)
You can write previous-code-buffer just replacing every next-buffer with previous-buffer.
The simplest I can think of is defining an advice for both functions. Here it is for next-buffer. Similarly would be for previous-buffer. You can also define a configuration variable to enable/disable the behavior (or activating/deactivating the advice):
(defadvice next-buffer (after avoid-messages-buffer-in-next-buffer)
"Advice around `next-buffer' to avoid going into the *Messages* buffer."
(when (string= "*Messages*" (buffer-name))
(next-buffer)))
;; activate the advice
(ad-activate 'next-buffer)
Maybe you can compare buffers in some other way instead of its string name, but that will work. The code for previous buffer is almost the same. I don't know either if there is a way of calling the original function without triggering the advice once inside the advice itself, but again, the code will work even if the name of the buffer is tested afterwards (will fail if you just have one buffer, and it is the messages buffer; some code can check if there is just one buffer and don't call next-buffer again).
If you want to use a standalone function that does the same thing:
(defun my-next-buffer ()
"next-buffer, only skip *Messages*"
(interactive)
(next-buffer)
(when (string= "*Messages*" (buffer-name))
(next-buffer)))
(global-set-key [remap next-buffer] 'my-next-buffer)
(global-set-key [remap previous-buffer] 'my-next-buffer)
This is what I'm using, based on Diego's answer:
(setq skippable-buffers '("*Messages*" "*scratch*" "*Help*"))
(defun my-next-buffer ()
"next-buffer that skips certain buffers"
(interactive)
(next-buffer)
(while (member (buffer-name) skippable-buffers)
(next-buffer)))
(defun my-previous-buffer ()
"previous-buffer that skips certain buffers"
(interactive)
(previous-buffer)
(while (member (buffer-name) skippable-buffers)
(previous-buffer)))
(global-set-key [remap next-buffer] 'my-next-buffer)
(global-set-key [remap previous-buffer] 'my-previous-buffer)
It is not great yet, because it will hang if there are no buffers other than the skippable-buffers I list. I use C-g to break out of the loop when it happens as a hackaround.
As RubenCaro's answer points out, the other answers can enter infinite loops. I thought David James' approach of a skippable buffers list was a bit nicer, though, so here's a variant of that.
(setq my-skippable-buffers '("*Messages*" "*scratch*" "*Help*"))
(defun my-change-buffer (change-buffer)
"Call CHANGE-BUFFER until current buffer is not in `my-skippable-buffers'."
(let ((initial (current-buffer)))
(funcall change-buffer)
(let ((first-change (current-buffer)))
(catch 'loop
(while (member (buffer-name) my-skippable-buffers)
(funcall change-buffer)
(when (eq (current-buffer) first-change)
(switch-to-buffer initial)
(throw 'loop t)))))))
(defun my-next-buffer ()
"`next-buffer' that skips `my-skippable-buffers'."
(interactive)
(my-change-buffer 'next-buffer))
(defun my-previous-buffer ()
"`previous-buffer' that skips `my-skippable-buffers'."
(interactive)
(my-change-buffer 'previous-buffer))
(global-set-key [remap next-buffer] 'my-next-buffer)
(global-set-key [remap previous-buffer] 'my-previous-buffer)

Emacs: scroll buffer not point

Is it possible to scroll the entire visible portion of the buffer in Emacs, but leave point where it is. Example: point is towards the bottom of the window and I want to see some text which has scrolled off the top of the window without moving point.
Edit: I suppose C-l C-l sort of does what I wanted.
try these. Change M-n and M-p key bindings according to your taste
;;; scrollers
(global-set-key "\M-n" "\C-u1\C-v")
(global-set-key "\M-p" "\C-u1\M-v")
;;;_*======================================================================
;;;_* define a function to scroll with the cursor in place, moving the
;;;_* page instead
;; Navigation Functions
(defun scroll-down-in-place (n)
(interactive "p")
(previous-line n)
(unless (eq (window-start) (point-min))
(scroll-down n)))
(defun scroll-up-in-place (n)
(interactive "p")
(next-line n)
(unless (eq (window-end) (point-max))
(scroll-up n)))
(global-set-key "\M-n" 'scroll-up-in-place)
(global-set-key "\M-p" 'scroll-down-in-place)
This might be of use. According to the EmacsWiki page on Scrolling;
The variable scroll-preserve-screen-position may be useful to some.
When you scroll down, and up again, point should end up at the same
position you started out with. The value can be toggled by the built
in mode M-x scroll-lock-mode.
I think this is better:
(defun gcm-scroll-down ()
(interactive)
(scroll-up 1))
(defun gcm-scroll-up ()
(interactive)
(scroll-down 1))
(global-set-key [(control down)] 'gcm-scroll-down)
(global-set-key [(control up)] 'gcm-scroll-up)
reference : emacs wiki
;; Preserve the cursor position relative to the screen when scrolling
(setq scroll-preserve-screen-position 'always)
;; Scroll buffer under the point
;; 'scroll-preserve-screen-position' must be set to a non-nil, non-t value for
;; these to work as intended.
(global-set-key (kbd "M-p") #'scroll-down-line)
(global-set-key (kbd "M-n") #'scroll-up-line)
Based on Bilal's answer:
(global-set-key [(meta down)] (lambda () (interactive) (scroll-down 1)))
(global-set-key [(meta up)] (lambda () (interactive) (scroll-up 1)))

Emacs tab between buffers

Is there a way to switch between buffers without having to go through the
buffer-list, or writing the name of the buffer that I want to switch to? More specific I wonder if emacs can tab between buffers much like how it is working in notepad++
Emacs 22.1 and higher supports the previous-buffer (C-x <left arrow>) and next-buffer (C-x <right arrow>) commands.
These two commands can be added to older Emacsen using this script.
I've never ended up using C-x <right> or C-x <C-right> much, because I find them cumbersome to repeat if I want to cycle past more than one buffer, so I've just written a couple of functions to let you continue to switch to next/previous-buffer with <C-right> and <C-left> if the last command was also a next/previous-buffer command.
e.g. C-x <C-left> <C-left> <C-left> <C-right> <C-left> would take you back three buffers, forward one, and backward again.
I've made the assumption that <C-left> & <C-right> are usually bound to forward/backward-word, and am calling those explicitly as the fallback.
(defun my-forward-word-or-buffer-or-windows (&optional arg)
"Enable <C-left> to call next-buffer if the last command was
next-buffer or previous-buffer, and winner-redo if the last
command was winner-undo or winner-redo."
(interactive "p")
(cond ((memq last-command (list 'next-buffer 'previous-buffer))
(progn (next-buffer)
(setq this-command 'next-buffer)))
((memq last-command (list 'winner-redo 'winner-undo))
(progn (winner-redo)
(setq this-command 'winner-redo)))
(t ;else
(progn (forward-word arg)
(setq this-command 'forward-word)))))
(defun my-backward-word-or-buffer-or-windows (&optional arg)
"Enable <C-left> to call previous-buffer if the last command
was next-buffer or previous-buffer, and winner-undo if the last
command was winner-undo or winner-redo."
(interactive "p")
(cond ((memq last-command (list 'next-buffer 'previous-buffer))
(progn (previous-buffer)
(setq this-command 'previous-buffer)))
((memq last-command (list 'winner-redo 'winner-undo))
(progn (winner-undo)
(setq this-command 'winner-undo)))
(t ;else
(progn (backward-word arg)
(setq this-command 'backward-word)))))
(global-set-key (kbd "<C-left>") 'my-backward-word-or-buffer-or-windows)
(global-set-key (kbd "<C-right>") 'my-forward-word-or-buffer-or-windows)
(I use Icicles for buffer switching, myself, but...)
If you want to repeat the previous command any number of times, just use C-x z z z z z z... In this case, e.g., C-x left C-x z z z...
If that's too cumbersome, bind (next|previous)-buffer to other, repeatable keys, as others have suggested.
But repeatable keys are in great demand. If you don't want to waste any, you can even put such commands on a prefix key, so that, e.g., you can do, e.g., C-x left left left... Here's a trick to do that (taken from the Bookmark+ code):
(defun my-repeat-command (command)
"Repeat COMMAND."
(let ((repeat-message-function 'ignore))
(setq last-repeatable-command command)
(repeat nil)))
(defun my-next-whatever-repeat (arg) ; `C-x right'
"Jump to the Nth-next whatever.
N defaults to 1, meaning the next whatever.
Plain `C-u' means start over at the first whatever (and no repeat)."
(interactive "P")
(require 'repeat)
(my-repeat-command 'next-whatever))
(define-key ctl-x-map [right] 'my-next-whatever-repeat
Although the following suggestion does use the buffer-list, Ivy (or Helm) and evil, I think it is a nice, nearly equivalent alternative to the common Ctrl-TAB way (incl. updating the buffer list) when using e.g. Spacemacs.
Of course the commands can be adapted to your personal config (vanilla Emacs)
(evil-global-set-key 'motion (kbd "<C-tab>") 'ivy-switch-buffer)
(evil-global-set-key 'insert (kbd "<C-iso-lefttab>") 'ivy-switch-buffer)
(define-key ivy-mode-map (kbd "<C-tab>") 'ivy-next-line-and-call)
(define-key ivy-mode-map (kbd "<C-iso-lefttab>") 'ivy-previous-line-and-call)
or for the equivalent for Helm
(evil-global-set-key 'motion (kbd "<C-tab>") 'helm-buffers-list)
(evil-global-set-key 'motion (kbd "<C-iso-lefttab>") 'helm-buffers-list)
(define-key helm-map (kbd "<C-tab>") 'helm-follow-action-forward)
(define-key helm-map (kbd "<C-iso-lefttab>") 'helm-follow-action-backward)
The keystring for the last command means Ctrl-Shift-tab in my keyboard. You can find the one to use with C-h k C-S-tab.
Indeed you still need to press RET or C-l after releasing <C-tab>.
For evil users using Helm, a possibly even nicer alternative is to bind helm-buffers-list to C-j and C-k, then set helm-follow-mode-persistent to t, and in the helm-buffers-list buffer activate helm-follow-mode with C-c C-f. Now you can switch (and preview) buffers with C-j and C-k.