Emacs Intro

Материал из MediaWiki
Перейти к навигации Перейти к поиску

Как начать жить с Emacs.

Изучаем Emacs за 10 лет. (шутка, хе-хе, но с долей правды)

Эта статья из категории 'быстрый старт', если вы хотите основательно узнать про Emacs всё, возможно вам следует начать со списка официальной документации(для GNU Emacs manual есть перевод на русский язык).

Одной картинкой.

Сейчас (03.02.2015) стабильной версией Emacs'a является 24.4, которая доступна для скачивания в интернете (например с официального сайта) и является основной в большинстве дистрибутивов.


Получаем и устанавливаем Emacs.

debian/ubuntu
apt-get install emacs
archlinux
pacman -S emacs
fedora
yum install emacs
Сборка последней версии исходников(рекомендую этот путь)
Клонируем trunk
cd ~/projects; #Ну или где у вас место для сбора программ.


  • bzr
bzr branch bzr://bzr.savannah.gnu.org/emacs/trunk emacs
  • git
git clone git://git.savannah.gnu.org/emacs.git emacs
Собираем/пересобираем и устанавливаем:
cd emacs;
# bzr pull; или git pull;
./configure # --enable-link-time-optimization --with-x-toolkit=lucid --without-makeinfo --prefix=~/bin/emacs_dir --bindir=~/bin;
make;
make install;

Введение.

Emacs -- легендарный текстовый редактор.

Основные понятия.

frame
'фрэйм' -- оно же 'окно' в терминологии WM. У одного процесса Emacs может быть несколько фреймов.
window
'окно' -- область фрейма, в которой непосредственно происходит отображение и редактирование текста буфера. В одном фрэйме может быть несколько окон.
buffer
'буфер' -- объект, содержащий текст. Может быть привязан к файлу и его содержимому или вводу/выводу процесса или просто содержать текст, сгенерированный или введённый пользователем.
*Messages* buffer
специальный буфер, что-то вроде stdout и stderr, Emacs выводит туда различные сообщения. Последнее сообщение также отображается в echo area.
echo area
область внизу фрейма, в которой отображаются сообщения.
minibuffer
область внизу фрейма(там же где echo area), используется когда интерактивной команде нужен ввод от пользователя.
point
'точка ввода', точка в буфере, в которой находится 'текстовый курсор'('каретка'), позиция в буфере, в которую производится ввод текста.
mark
'метка', может использоваться как 'закладка' для быстрого перемещения на позицию в буфере, используется некоторыми командами(например копирование текста производится между mark и point).
region
область буфера между двумя 'позициями'(зачастую между mark и point).
major-mode
'основной режим', задаёт подсветку синтаксиса/специфические команды для определённых типов файлов/языков программирования, может быть активирован как автоматически, так и вручную. Для буфера может быть активен лишь один и всегда есть хотя бы один активный major-mode. Для каждого буфера может быть свой major-mode.
minor-mode
'минорный режим', задаёт дополнительные функции, может быть активно несколько (или ни одного) minor-mode. Для каждого буфера может быть активирован свой набор 'минорных режимов', минорные режимы могут быть 'глобальными'(активными для всех буферов).
mode-line
'строка режимов' -- строка внизу окна, отображающая различную информацию(активные режимы, размер буфера и т.д.)
header-line
строка вверху окна. По умолчанию ничего не отображает и используется редко(например tabbar-mode использует header-line).
load-path
путь в котором Emacs ищет *.el и *.elc файлы с elisp кодом.
kill-ring
список или 'история', куда помещается скопированный/вырезанный текст.
command
'команда', 'интерактивная функция'(interactive command) -- elisp функция, предназначенная для вызова пользователем(например для привязки к клавишам), которая содержит специальную elisp форму (interactive) и может принимать ввод от пользователя как аргумент.


Некоторые полезные ключи запуска

-Q
запустить Emacs без загрузки файлов конфигурации ~/.emacs(и некоторых других файлов).
--debug-init
запустить Emacs в режиме отладки.
--eval EXPR
выполнить EXPR, как выражение Emacs Lisp.
-nw
запустить в режиме текстового терминала.


Обозначения клавиш/сочетаний в Emacs.

C
Ctrl
M
Meta(левый альт, обычно. Что считать альтом можно поменять с помощью (setq x-alt-keysym 'meta))
S
Shift
SPC
Space
ESC
Escape
RET
Return(оно же Enter)
tab
Tab
<f7>
F7
C-h
Ctrl+h (удерживая Ctrl нажать h)
C-x x l
значит нажать последовательно сначала 'Ctrl+x', затем раздельно 'x' и затем 'l'.
C-x C-x l
2 раза C-x и затем l.
M-x revert-buffer RET
значит нажать Alt+x, напечатать revert-buffer и нажать Enter.


Запускаем и используем Emacs первый раз.(с дефолтными настройками)

Вот примерный скриншот, того что мы видим при первом запуске с дефолтными настройками: http://yadi.sk/d/Rc3GcV_iJmYrX

ASCII версия скриншота:

   Emacs frame
.______________________________________________________________________________.
|File Edit Options Buffers Tools Lisp-Interaction Help                         |<-- menu-bar
|------------------------------------------------------------------------------|
| button | button | button | . . . |                                           |<-- tool-bar
|______________________________________________________________________________|
|;; This buffer is for notes you don't want to save, and for Lisp evaluation.  |\
|;; If you want to create a file, visit that file with C-x C-f,                | \
|;; then enter the text in that file's own buffer.                             |  \ __ window
|                                                                              |  /
|                                                                              | /
|______________________________________________________________________________|/
|-UUU:----F1  *scratch*      All L5     (Lisp Interaction) --------------------|<-- mode-line
|------------------------------------------------------------------------------|
|For information about GNU Emacs and the GNU system, type C-h C-a.             |<-- echo-area
'------------------------------------------------------------------------------'

Далее нажимаем C-h (Ctrl+h), примерно через 1-2 секунды, внизу(в echo-area) появится надпись: "C-h (Type ? for further options) -", нажимаем '?', будет показан список вариантов. Нажимайте 't' чтобы пройти tutorial. Он не сложный и не длинный, но полезный.

menu-bar и tool-bar чаще всего отключают за ненадобностью:

 (tool-bar-mode 0)
 (menu-bar-mode 0)

Скроллы тоже отключают:

 (scroll-bar-mode 0)

А так же отрубают назойливый 'стартовый экран' и всякие ненужные сообщения:

 (setq inhibit-startup-message t
       inhibit-startup-echo-area-message t)


Частоиспользуемые сочетания клавиш.

C-x C-c
выйти из Emacs.
M-x [имя команды]
execute-extended-command -- Будет предложено ввести имя интерактивной функции для исполнения.
C-g
выход/отмена текущей команды/операции(или если вы начали вводить сочетание клавиш, но передумали или ошиблись и Emacs ждёт от вас продолжения или ввода).
C-q [любая кнопка]
вводит тот символ который по умолчанию вводится [любой кнопкой] даже если она переназначена.
C-u
Задаёт universal prefix argument -- это такой специальный аргумент, который могут принимать команды и менять своё поведение. Может быть дополнен знаком '-' или числом, например C-u - или С-u 3 или C-u 300. Например C-u 3 M-x next-line RET -- перейдёт на следующую строку 3 раза, т.е. перейдёт на 3ю строку от курсора(текущего положения point).
C-j
Вставляет перевод строки. В общем если у вас где-нибудь не работает Enter(перевод строки или запуск команды или вам нужно вставить перевод строки без нажатия Enter), пробуем C-j, если не работает -- С-q RET, если и это не помогает -- C-q C-j.

Работа со встроенной документацией.

C-h ?
посмотреть все варианты справки
C-h f [имя функции]
посмотреть документацию о функции.(так же там есть ссылка на исходник, если доступен)
C-h k [сочетание клавиш]
посмотреть какая функция привязана к сочетанию клавиш.
C-h v [имя переменной]
посмотреть информацию о переменной.

Операции с файлами:

С-x C-f
открыть файл.(будет создан новый буфер, связанный с файлом и отображающий его содержимое в текущем окне)
C-x C-s
сохранить файл.(сохраняет содержимое буфера в связанный файл)
C-x C-w
сохранить как.(сохранить текущий буфер в файл с именем)

Для 'закрытия' файла нужно убить связанный с ним буфер.

Операции с буферами:

C-x b
переключить текущий буфер окна на другой.
C-x k
убить буфер.

Операции над окнами:

C-x 0
удалить текущее окно
C-x 1
удалить все окна, кроме текущего
C-x 2
разделить текущее окно по горизонтали(получается два окна, одно сверху, другое -- снизу)
C-x 3
разделить текущее окно по вертикали(-- одно слева, другое справа)
C-x o
перейти к следующему окну.

Для большего удобства можно использовать

 (windmove-default-keybindings 'super)
 (setq windmove-wrap-around t)

Тогда из окна в окно можно перемещаться с помощью стрелочек(некоторые пользователи считают это и любые манипуляции стрелочками и с отрывом руки от буквенной клавиатуры не труЪ), зажав соответствующую клавишу-модификатор, указанную как аргумент к windmove-default-keybindings ('meta, 'shift(по умолчанию, если запустить функцию без аргумента считается 'shift)).

Операции с точкой ввода/меткой:

C-a
переместиться в начало строки.
C-e
переместиться в конец строки.
C-M-n или С-M-f или C-M-<right>
перескочить в конец выражения в скобках.
C-M-p или C-M-b или C-M-<left>
перескочить в начало выражения в скобках.
C-M-u или C-M-<up>
подняться на уровень вверх по вложенным скобкам
C-M-d или C-M-<down>
спуститься на уровень вложенности вниз
M-<
перейти в начало буфера.
M->
перейти в конец буфера.
С-SPC
установить 'метку'.
C-x C-x
поменять местами point и mark
M-w
копировать текст между меткой и точкой ввода (или выделенный в transient-mark-mode).
C-w
вырезать текст вежду меткой и точкой ввода.
C-y
вставить вырезанный/копированный текст.
M-y
Используется после 'вставки' (C-y) циклически заменяет вставляемый текст из 'истории' копированного/вырезанного текста (kill-ring).
C-x u
undo

Виндузятники (и не только) почувствуют себя как дома после

 (cua-mode 1)

Этот режим включает некоторые привычные сочетания клавиш, как C-x (вырезать), C-v (вставить), C-z (отмена) и некоторые другие.

C-s
инкрементный поиск по буферу. Рекомендуется ознакомиться с C-h k C-s, т.к. во время поиска доступно множество вспомогательных сочетаний.

Дополнение кода/завершение введённого слова:

M-/
dabbrev-expand -- дополняет из ранее встречавшегося.
M-tab
completion-at-point -- пытается дополнить что-то осмысленное разными методами, пользователь или режим(minor-, major- mode) может предоставлять свои функции для дополнения.
M-;
Закомментировать/раскомментировать строку/регион.


Полезные команды/режимы.

Напомним, что команды Emacs можно выполнять через сочетание M-x (Alt+x).

eval-region
выполняет регион, выделенную область буфера между mark и point, как Emacs Lisp код.
rgrep
рекурсивный grep по файлам.
redo
противоположность undo.
ielm
Emacs Lisp REPL.
load-file
Выполнить файл, как код Emacs Lisp.
show-paren-mode
Подсвечивание парных скобок.


Конфигурация.

Рекомендуется ознакомится с Emacs Lisp.

По умолчанию Emacs при запуске исполняет файл ~/.emacs (а сейчас и ~/.emacs.d/init.el или другой, указанный в переменной user-init-file во время запуска), который может содержать любой elisp код(смотри C-h r i init file).


Customize

В Emacs есть специальный интерфейс для изменения настроек. M-x customize RET и дальше переходите по ссылкам и настраивайте. Если вы знаете что вам нужно конкретно настраивать, то M-x customize-group RET имя-группы RET, имя-группы обычно совпадает с названием режима или elisp библиотеки/файла которые вы хотите настроить. Впрочем, не всегда и не всё можно настроить через этот интерфейс. Настройки сделанные через этот интерфейс по умолчанию сохраняются в специальном блоке вашего файла инициализации (который ~/.emacs по умолчанию), но этого поведение может быть изменено(см. переменную custom-file).


Пакетная Система Emacs

В Emacs 24.3 появился встроенный 'менеджер 'пакетов'(сторонних модулей)', что достаточно упростило установку, удаление, компиляцию, загрузку стороннего elisp кода. Для того чтобы загружать пакеты при запуске Emacs, нужно добавить в файл инициализации следующие строки:

(require 'package)
;; Задаём список репозиториев.
(setq package-archives '(;; ("ELPA" . "http://tromey.com/elpa/") 
                         ;; ("gnu" . "http://elpa.gnu.org/packages/")
                         ;; ("marmalade" . "http://marmalade-repo.org/packages/")
                         ("MELPA" . "http://melpa.milkbox.net/packages/")))
(package-initialize)

Рекомендую использовать только MELPA, т.к. он содержит большое количество популярных пакетов и автоматически обновляет их из github и других репозиториев.

Для просмотра списка доступных пакетов есть команда:

M-x package-list-packages RET
скачивает и выводит список пакетов доступных на сервере.

В буфере со списком переназначены следующие клавиши:

r
обновляет список доступных пакетов.
U
'update'(обновить), отмечает для установки новые версии установленных пакетов(а устаревшие отмечает для удаления)
I
отметить пакет, на строке которого стоит курсор, для установки
d
отметить для удаления
u
снять отметку
x
начать установку/удаление отмеченных пакетов.
q
выход.

Если вы точно знаете название пакета, можно сделать проще: M-x package-install [имя пакета] RET.

Можно установить elisp модуль и в 'оффлайне', с вашего жёсткого диска/карты памяти, для этого тоже есть команда: M-x package-install-file [путь к файлу] RET.

Список полезных 'плагинов' и их настройки см Emacs Packages.


Авто -дополнение, -завершение кода, автокомплит

company-mode

auto-complete-mode


Использование сторонних elisp модулей без пакетной системы

Emacs Lisp и модули.


Привязка функций к клавишам

(global-set-key "\C-xl" #'make-symbolic-link)

Привязали make-symbolic-link к C-x l глобально.

(define-key lisp-mode-map "\C-xl" #'make-symbolic-link)

То же самое, но только для режима lisp-mode.

(global-unset-key "\C-x\C-v")

Разбиндиваем сочетание C-x C-v.(есть также local-unset-key)

Также для простоты написания сочетаний клавиш есть функция kbd:

(global-set-key (kbd "C-x l") #'make-symbolic-link)
(global-unset-key (kbd "C-x C-v"))

Привязать к клавише можно только интерактивную команду, т.е. функцию, первым выражением которой явлется

(interactive)

с параметрами или без.

Например для лямбд:

 (global-set-key [tab] #'(lambda () (interactive) (insert "    ")))

Также по историческим причинам в емакс есть два способа для обозначения клавиши табуляции:

  1. с помощью [tab] -- означает табуляцию в графическом режиме.(в иксах)
  2. с помощью (kbd "TAB") -- для режима текстового терминала

(источник https://github.com/company-mode/company-mode/issues/75#issuecomment-37341730)


Если что-то не работает или Debug

Emacs Lisp и Debug.


Примеры готовых конфигураций

https://github.com/Bad-ptr/.emacs.d


Emacs daemon

Emacs может быть запущен в режиме демона. Например, чтобы каждый раз не запускать Emacs заново, особенно когда в вашем конфигурационном файле накапливается много кода и Emacs стартует довольно медленно, ну или для совместного редактирования файла по сети или ещё для чего. Делается это так: emacs --daemon Дальше для редактирования файлов следует использовать клиент: emacsclient /path_to/file или emacsclient -c для создания графического фрейма или emacsclient -nw для фрейма в текстовом терминале. emacsclient также имеет параметр -a, задающий команду, которая будет запущена если сервер не найден, если параметр не задан или равен ''(пустая строка), то сначала будет запущен сервер.

Это упрощённый сценарий. На самом деле можно запустить несколько демонов для этого нужно задать им имена, делается это так:

emacs --daemon=test

Этой командой мы запустили демон емакса с именем тест. Кстати по умолчанию, если имя через = не задавать, оно считается =server, т.е.:

emacs --daemon

тоже самое, что

emacs --daemon=server

Теперь подключаемся к серверу test:

emacsclient --socket-name=test -c

(вместо --socket-name можно -s)

По умолчанию Emacs использует unix сокет для коммуникации между сервером и клиентом. Однако возможно наладить связь через TCP соединение, для этого демон запускаем так:

emacs --daemon=test --eval '(setq server-use-tcp t)'

(в этом случае появляется файл с именем сервера в ~/.emacs.d/server/test, а (setq server-use-tcp t) можно конечно же поместить в ~/.emacs, вместо передачи через --eval) Теперь демон будет ждать клиентов на tcp порту, который тоже можно задать с помощью:

(setq server-port 40444);;например

И подключаться клиентом так:

emacsclient --server-file=test -c

(вместо --server-file можно -f)

Всё это можно оформить в виде bash скрипта:

#!/bin/bash
# https://gist.github.com/Bad-ptr/7628186

DAEMON='server';

if [ -n "$1" ];
then
    DAEMON="$1"
fi

emacsclient -f "$DAEMON" -a false -e 't';

if [ "$?" -eq 1 ];
then
    #rm ~/.emacs.desktop.lock
    rm "~/.emacs.d/server/$DAEMON"
    emacs --daemon="$DAEMON" --eval '(setq server-use-tcp t)' "${@:2}" </dev/null
else
    emacsclient -f "$DAEMON" -a false -e '(kill-emacs)' </dev/null 
fi

Использовать так:

./startkillemacsd test

Запустит Emacs демон test, если он ещё не запущен, если уже запущен -- то завершит его.

Подключится к серверу test можно так: emacsclient -f test -c .

Полезные ссылки

видеоуроки на русском от некоего Дмитрия Бушенко

emacslife.com

emacs.sexy

emacswiki.org

Emacs mini manual

masteringemacs.org

How to Edit Lisp Code with Emacs от Xah Lee

Emacs сообщество в G+

emacs-strip-tease

rectangular-selection в Emacs 24.4

Emacs и Java с помощью emacs-eclim

effective-emacs

single-file-master-emacs-configuration