Create a gist now

Instantly share code, notes, and snippets.

Start Emacs.app from CLI
#!/usr/bin/perl
# Emacs starter for Emacs mac port
# Thanks to Aquamacs Project and David Reitter
my $args = "";
my $tmpfiles = "";
for my $f (@ARGV) {
$args .= '"'.$f.'" ';
$tmpfiles .= '"'.$f.'" ' if (! -e $f);
}
system("touch $args") if ($tmpfiles);
system("open -a /Applications/Emacs.app $args");
# delay deletion because AE drag&drop doesn't work with non-existing documents
system("(sleep 3; rm $tmpfiles) &") if ($tmpfiles);
exit;
@ptb
ptb commented May 19, 2015

I rewrote this as a shell script and added the capability to accommodate filenames with spaces:

#!/bin/sh

if [ -e '/Applications/Emacs.app' ]; then
  t=()

  if [ ${#@} -ne 0 ]; then
    while IFS= read -r file; do
      [ ! -f "$file" ] && t+=("$file") && /usr/bin/touch "$file"
      file=$(echo $(cd $(dirname "$file") && pwd -P)/$(basename "$file"))
      $(/usr/bin/osascript <<-END
        if application "Emacs.app" is running then
          tell application id (id of application "Emacs.app") to open POSIX file "$file"
        else
          tell application ((path to applications folder as text) & "Emacs.app")
            activate
            open POSIX file "$file"
          end tell
        end if
END
      ) &  # Note: END on the previous line may be indented with tabs but not spaces
    done <<<"$(printf '%s\n' "$@")"
  fi

  if [ ! -z "$t" ]; then
    $(/bin/sleep 10; for file in "${t[@]}"; do
      [ ! -s "$file" ] && /bin/rm "$file";
    done) &
  fi
else
  vim -No "$@"
fi

Since I switched from vi, I can't help but to type vi filename every time, so I saved this script as /usr/local/bin/vi. In the off chance I haven't yet installed Emacs.app, it uses the built in system vim instead.

@railwaycat
Owner

Thanks @ptb :)

@lmartins
lmartins commented Jun 8, 2015

Sorry to ask guys, how can I install this?

@InAbsentia

@lmartins Paste into a file named emacs (or whatever you want the command to be) in a directory in your path (ahead of the location of the existing emacs command). Then chmod +x /path/to/emacs.

@jasonm23
jasonm23 commented Oct 1, 2016

It'd be better to use emacsclient (and kick off Emacs.app as the alternate editor if it's not running already.)

@tasmo
tasmo commented Oct 25, 2016

The command open with the argument -a does not need the full application path. It's not useless but if you have installed Emacs in a different location I would consider just to use

system("open -a Emacs $args");
@mwolson
mwolson commented Nov 24, 2016

Here's a variation that ensures Emacs.app is launched, waits for it to be ready, and then uses emacsclient to open the file in a GUI frame and wait for edits to be completed.

#!/bin/sh

CLIENT=/Applications/Emacs.app/Contents/MacOS/bin/emacsclient

$(/usr/bin/osascript <<-END
  tell application ((path to applications folder as text) & "Emacs.app")
    activate
  end tell
END
)

while ! "$CLIENT" -e '"pass"' 2>&1 | grep '"pass"' > /dev/null; do
    sleep 0.3
done

if test "$#" -gt 0; then
    exec "$CLIENT" -c $@
fi
@railwaycat
Owner

Hi @mwolson, thanks for the update. I believe your starter script works for Nextstep port (although I haven't verify that by myself), but it not works for Mac port. Because Emacs Mac port lacks multi-tty support, which means, emacsclient from mac port can only able to create tty frames but not GUI frames.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment