How can I have emacs start and be in the middle of a command input? Particularly, I want emacs to start in the middle of a command input find-file with a message in the small buffer saying:
Find file: ~/
and the cursor at the last character of it so that I can continue typing the remaining path to open the file I want.
You can execute one of the following commands on the command prompt or make a shell script containing it appropriately:
$ emacs -f find-file # if you want to start Emacs in the current direcoty
$ (cd ~; emacs -f find-file) # if you want to start Emacs in your home diretory
From the emacs(1) man page:
-f function, --funcall function
Excute the lisp function function
I have to admit that my lisp is a bit rusty, but this works for me. Drop it in your ~/.emacs file (or whatever init file you are using):
(add-hook 'emacs-startup-hook
(lambda ()
(if (= (length command-line-args) 1)
(call-interactively 'find-file))))
If you call emacs with no arguments, like this:
sawa#localhost:~$ emacs
It will invoke find-file for you. If, on the other hand, you invoke emacs with an argument, such as a filename, like this:
sawa#localhost:~$ emacs somefile.txt
It will default to just visiting somefile.txt
Related
How can I tell emacs not to pop up the *Shell Command Output* buffer when calling a shell command like this?
(shell-command MY_COMMAND)
Currently emacs splits the current window into two, showing the (mostly irrelevant) output buffer. To me it would be completely sufficient if I could look it up later if I feel like it.
Maybe using shell-command was the root of the problem. I think I found a solution with call-process which works, although there may be a more elegant way:
(call-process-shell-command
"cat ~/.emacs.d/init.el"
nil "*Shell Command Output*" t
)
shell-command takes an optional argument OUTPUT-BUFFER where you can specify the buffer to output to. If it is t (actually not a buffer-name and not nil) it will be output in the current buffer. So we wrap this into a with-temp-buffer and will never have to bother with it:
(with-temp-buffer
(shell-command "cat ~/.emacs.d/init.el" t))
In my experience, if the shell command itself produces no output, then the emacs *Shell Command Output* buffer won't pop open.
Therefore, to avoid the output buffer, silence the output of the command.
One easy way is:
add " > /dev/null 2>&1" to the end of any shell command.
(Caveat: I'm unsure if /dev/null exists on 100% of platforms where one can run emacs, but on every Linux distro it should be fine.)
If the call to elisp function shell-command is in an elisp script, then you could change this:
(shell-command cmd)
to this:
(shell-command (concat cmd " > /dev/null 2>&1"))
If you occasionally do want to monitor the output, then you could create one wrapper function that suppresses the output via /dev/null, and one wrapper function with no suppression, and toggle between them as you wish.
The above advice was tested on: GNU Emacs 24.5.1 (x86_64-pc-linux-gnu, GTK+ Version 3.18.9) of 2017-09-20 on lcy01-07, modified by Debian
This utility function might help. It returns the actual value of the shell command
(defun shell-command-as-string (cmd)
(with-temp-buffer
(shell-command-on-region (point-min) (point-max)
cmd t)
(buffer-string)))
What's even better, is to use
(shell-command (concat cmd " 1>&2") t t)
This way, the output is saved in the error buffer, should you want to look at it. But it does not pop up automatically.
I want to write an emacs function that does the following -
1) Start a new shell named "abc".
2) Change the dir "/opt/abc"
3) In the dir run a shell command "python abc.py"
I have written the following function -
(defun abc-server ()
(interactive)
(shell-command "cd /opt/abc/")
(shell-command "python abc.py"))
The problem with the above -
1) It doesnt start a new shell
2) It doesnt change the dir.
3) When the cmd executes, it opens a browser window, which completely blocks any usage of emacs.
From shell-command's docstring (C-h f shell-command):
If COMMAND ends in ampersand, execute it asynchronously.
The output appears in the buffer `Async Shell Command'.
That buffer is in shell mode.
Also, combine it all into one command line. shell-command makes a new shell every time, so the pwd will not persist from one invocation to another.
(defun abc-server ()
(interactive)
(shell-command "cd /opt/abc/; python abc.py &"))
While #jpkotta's answer is good enough, a proper solution would use the anync primitives of Emacs. For one thing, you can only have one async shell command running at a time, whereas you can have a large number of named subprocesses.
(defun abc-server ()
(interactive)
;; Create buffer ahead of time so we can change its default directory
(save-excursion
(get-buffer-create "*abc-server*")
(cd "/opt/abc") )
(start-process "abc" "*abc-server*" "python" "abc.py") )
(I'm not altogether happy with the save-excursion hoop. I was hoping I could simply let-bind default-directory, but that didn't seem to work as I had expected. Alternatively, you could (start-process "abc" "*abc-server*" "sh" "-c" "cd /opt/abc; python abc.py").)
If you need to extend the command further, I would argue that this is a more scalable platform than the quick and dirty async shell command approach, but if this is all you are ever going to need, it doesn't matter much.
I have followed instructions from How can I run Cygwin Bash Shell from within Emacs? this question and I have gone further and added the (setq explicit-bash-args '("--login" "-i")) command, however emacs continues to only display the dos prompt when I type M-x shell. In summery my .emacs file looks like this:
(defun cygwin-shell ()
"Run cygwin bash in shell mode."
(interactive)
(let ((explicit-shell-file-name "C:/cygwin/bin/bash"))
(call-interactively 'shell)))
(setq explicit-bash-args '("--login" "-i"))`
Please be gentle with the answers as I am right at the bottom of the famous vertical emacs learning curve!
If you implemented the answer from that question, note that you have to do M-x cygwin-shell to start bash. If you want to use it for every M-x shell you need to call
(setq explicit-shell-file-name "C:/cygwin/bin/bash")
Since you stated that you are learning, here's a few tips when trying this out.
type C-x C-f ~/.emacs to open your .emacs file in your user path.
Enter your function above at the end
M-x load-file [RET] .emacs: loads the buffer (no need to restart emacs)
C-h a: If you are interested in some specific action, you can look it up
C-h v [RET] variable: can inspect the variable, check the value of explicit-bash-args for instance
And, btw, I'm not sure what the "--login -i" does, but someone stated in a comment that you should have that so "ls" would work. If you have your cygwin bin path in your PATH environment variable, bash will find ls anyway. No need to escape the path variable either, this is handled by bash (do an echo $PATH in bash when you get it working and you'll see).
I relise that I have to add something like:
shell
: to my .emacs file. But then how can I get it to do shell commands like:
cd /mydirectory
: and other shell actions
This is a function which does what you want. You can add it (customizing the actions), or just add the body:
(defun shell-and-stuff ()
"run a shell, then do some extra stuff"
(interactive)
(let ((shell-buf (get-buffer-create "*shell*")))
(shell shell-buf)
(comint-send-string
(get-buffer-process shell-buf)
"cd some-directory
ls
touch frog
")))
(shell-and-stuff)
The cd part is easy, just let bind the variable default-directory. See this question for some possible solutions.
Trey Jackson's idea looks good. Also note that the manual (info "(emacs) Interactive Shell") says
Emacs sends the new shell the contents of the file
~/.emacs_SHELLNAME as input, if it exists, where SHELLNAME is the
name of the file that the shell was loaded from. For example, if you
use bash, the file sent to it is ~/.emacs_bash. If this file is not
found, Emacs tries to fallback on ~/.emacs.d/init_SHELLNAME.sh.
So you could put your commands in that file.
The symptom of the problem looks like "[0m[27m[24m[J[34;1" which on a terminal translates into the color blue.
-A
I've got the following in my .emacs
(add-hook 'shell-mode-hook 'ansi-color-for-comint-mode-on)
The solution that is currently giving me some success is to redefine the shell function as an ansi term:
;; shell-mode
(defun sh ()
(interactive)
(ansi-term "/bin/zsh"))
For the "ignore" alternative, put something like "alias ls=ls" or "unset LS_COLORS" in your ~/.emacs_{bash,tsch,whatever-your-shell-is-called} file. This file is executed in all subordinate shells created by emacs.
Emacs sends the new shell the contents of the file ~/.emacs_shellname as input, if it exists, where shellname is the name of the file that the shell was loaded from. For example, if you use bash, the file sent to it is ~/.emacs_bash. If this file is not found, Emacs tries to fallback on ~/.emacs.d/init_shellname.sh.
The following should work in your .bash_profile or .bashrc
case $TERM in
xterm-color)
export PS1='\[\e]0;\W\007\]\[\e[34;1m\]\W\[\e[0m\]\$ '
;;
*)
export PS1='\W\$ '
;;
esac