GNUEmacsManual:31

From 흡혈양파의 번역工房
Jump to: navigation, search
다양한 명령어(Miscellaneous Commands)

Contents

다양한 명령어(Miscellaneous Commands)

이번 장에서는 다른 장에서 다루지 않는 간략한 주제, 즉 "문서 파일" 보기, Usenet 뉴스 읽기, 셸 명령어와 셸 하위프로세스 실행하기, 에디터를 하위프로세스로 실행할 것으로 기대하는 유틸리티들이 공유하는 하나의 Emacs 사용하기, 하드카피 출력하기, 텍스트 정렬하기, 바이너리 파일 편집하기, 추후 Emacs 세션을 재개하기 위해 저장하기, 하이퍼링크 따라가기, 다른 에디터 에뮬레이트하기, 다양한 편의(diversion) 및 오락 기능(amusement)을 다루고자 한다.

Gnus

Gnus 는 주로 Usenet 뉴스를 읽고 포스팅하도록 설계된 패키지다. 이메일, 원격 디렉터리, 다이제스트(digests) 등의 많은 등에서 소스에서 메시지를 읽고 그에 응답하는 데에 사용되기도 한다. Gnus 를 소개하고 여러 기본 기능을 설명하고자 한다. Gnus 에 대한 상세한 내용은 C-h i 를 입력한 후 Gnus 매뉴얼을 선택한다.

Gnus 버퍼(Gnus Buffers)

Gnus는 정보를 표시하고 명령어를 수신하기 위해 여러 버퍼를 사용한다. 가장 자주 사용되는 Gnus 버퍼 3개는 그룹 버퍼(group buffer), 서머리 버퍼(summary buffer), 아티클 버퍼(article buffer)이다.


그룹 버퍼는 아티클 소스의 (예: 뉴스그룹과 이메일 받은 편지함) 목록을 포함하는데, 이를 모두 그룹이라고 부른다. 이는 Gnus 가 시작될 때 처음으로 표시하는 버퍼다. 보통 사용자가 구독하는 그룹과 읽지 않은 아티클을 포함하는 그룹만 표시한다. 이 버퍼에서 읽을 그룹을 선택할 수 있다.


서머리 버퍼는 아티클을 하나의 그룹에 열거하고 라인별로 하나의 아티클을 표시한다. 기본적으로는 각 아티클의 작성자, 제목, 라인 번호를 표시한다. 서머리 버퍼는 사용자가 그룹 버퍼에서 그룹을 선택하면 생성되며, 그룹을 종료하면 제거된다.


자신이 살펴볼 아티클을 서머리 버퍼에서 선택할 수도 있다. 아티클은 아티클 버퍼에 표시된다. 일반적인 Gnus의 사용 시에는 이 버퍼를 볼 수는 있지만 선택해서는 안 되는 것이, 유용한 Gnus 명령어들이 모두 서머리 버퍼로부터 호출될 수 있기 때문이다. 하지만 아티클 버퍼를 실행한 후 원한다면 그로부터 Gnus 명령어를 실행할 수는 있다.


Gnus가 시작될 때(When Gnus Starts Up)

시스템이 Usenet 뉴스를 읽을 준비가 되면 Gnus를 시작하기란 쉬운데, 그저 M-x gnus 를 입력하면 된다.


Gnus 는 시작 시 뉴스 초기화 파일을 읽는데, 이 파일은 Usenet 뉴스그룹과 구독을 열거하는 홈 디렉터리에
.newsrc
란 이름으로 된 파일이다(이 파일은 Gnus 에만 유일한 파일은 아니며 다른 여러 뉴스리더 프로그램에서 사용된다). 이후 시스템의 기본 뉴스 서버로 접촉을 시도하는데, 이는
NNTPSERVER
환경 변수에 의해 명시되는 것이 보통이다.


시스템이 기본 뉴스 서버를 갖고 있지 않거나 사용자가 이메일을 읽는 데에 Gnus 를 사용하길 원할 경우 M-x gnus 를 호출하기 전에 Gnus 에게 뉴스 또는 메일을 가져올 장소를 알릴 필요가 있다. 이를 위해서는
gnus-select-method
gnus-secondary-select-methods
변수를 적절하게 맞춤화해야 한다. 상세한 내용은 Gnus 매뉴얼을 참고한다.


Gnus 가 시작되면 그룹 버퍼를 표시한다. 기본적으로 그룹 버퍼는 소수의 구독하는 그룹만 표시한다. 그 외 상태, 즉 구독하지 않음(unsubscribed), 제거됨(killed) 또는 좀비(zombie) 상태의 그룹은 숨겨진다. Gnus를 처음으로 시작했다면 당신이 구독하지 않는 그룹은 모두 제거된(killed) 그룹으로 만들어지고, 잇따라 뉴스 서버에 표시되는 그룹은 모두 좀비 그룹이 된다.


진행하려면 그룹 버퍼 내 그룹을 선택하여 해당 그룹에 대한 서머리 버퍼를 열어야 하고, 그리고 나면 서머리 버퍼에서 아티클을 선택하여 그 아티클 버퍼를 다른 창에서 확인한다. 다음에 소개할 절들은 이에 그룹 및 서머리 버퍼를 사용하는 방법을 설명한다.


Gnus 를 종료하려면 그룹 버퍼에서 q 를 입력한다. 이는
.newsrc
.newsrc.eld
파일에서 당신의 그룹 상태를 자동으로 기록하므로 향후 Gnus 세션에서도 효력을 발휘한다.


Gnus 그룹 버퍼 사용하기

Gnus 그룹 버퍼에서 이용할 수 있는 명령어는 다음과 같다.


SPC
현재 행에 그룹에 대한 서머리 버퍼로 전환한다.


l
As
그룹 버퍼에서 사용자가 구독하는 그룹과 읽지 않은 아티클을 포함하는 그룹만 열거한다(이것이 기본 리스팅이다).


L
A u
구독한 그룹과 구독하지 않은 그룹을 모두 열거하되 제거된 그룹이나 좀비 그룹은 열거하지 않는다.


A k
제거된 그룹을 열거한다.


A z
좀비 그룹을 열거한다.


u
현재 행에 그룹의 구독 상태를 토글한다(예: 구독하는 그룹을 구독하지 않은 그룹으로, 또는 그 반대로 전환한다). 제거된 그룹 또는 좀비 그룹에서 이 명령어를 호출할 경우 구독하지 않은 그룹으로 상태를 바꾼다.


C-k
현재 행에 그룹을 제거한다. 제거된 그룹은
.newsrc
파일에 기록되지 않고
l
또는
L
리스팅에 표시되지도 않는다.


DEL
읽지 않은 아티클을 포함하는 이전 그룹으로 포인트를 이동한다.


n
읽지 않은 다음 그룹으로 포인트를 이동한다.


p
읽지 않은 이전 그룹으로 포인트를 이동한다.


q
Gnus 설정을 업데이트하고 Gnus 를 종료한다.


Gnus 서머리 버퍼 사용하기(Using the Gnus Summary Buffer)

Gnus 서머리 버퍼에서 이용할 수 있는 명령어는 다음과 같다.


SPC
선택된 아티클이 없다면 현재 행에서 아티클을 선택하고 그 아티클 버퍼를 표시한다. 선택된 아티클이 있다면 그 창에서 선택된 아티클 버퍼를 스크롤하고, 버퍼의 끝에 도달하면 읽지 않은 다음 아티클을 선택한다.
따라서 SPC를 반복 입력하여 모든 아티클을 읽을 수 있다.


DEL
아티클의 텍스트를 역방향으로 스크롤한다.


n
읽지 않은 다음 아티클을 선택한다.


p
읽지 않은 이전 아티클을 선택한다.


s
사용자가 버퍼로 전환하여 C-s 를 입력한 것처럼 선택된 아티클 버퍼에서 증분 검색을 실행한다(90 페이지의 12.1절 [증분 검색(Incremental Search)] 참고).


M-s regexp RET
regexp에 대한 일치 결과를 포함하는 아티클을 순방향으로 검색한다.


q
서머리 버퍼를 종료하고 그룹 버퍼로 돌아간다.


문서 보기(Document Viewing)

DocView 모드는 DVI, PostScript(PS), PDF, OpenDocument, Microsoft Office 문서를 보기 위한 주 모드이다. 또한 슬라이싱, 확대 축소(zooming), 문서 내 검색과 같은 기능들을 제공한다. 이는
gs
(GhostScript) 또는
mudraw
/
pdfdraw
(MuPDF) 명령어 및 다른 외부 툴[1]을 이용해 문서를 이미지 집합으로 변환하여 그러한 이미지를 표시함으로써 작동한다.


사용자가 DocView 모드로 표시 가능한 문서 파일을 방문하면 Emacs는 자동으로 DocView[2] 모드를 사용한다. 단 PostScript 파일을 방문하면 Emacs 가 PstScript 파일을 텍스트로서 편집하는 주 모드인 PS 모드로 전환되는 경우는 제외되나, DocView 부 모드 역시 켜기 때문에 DocView 로 문서를 보려면 C-c C-c 를 입력하면 된다. DocView 모드든 DocView 부 모드든 C-c C-c (
doc-view-toggle-display
)를 반복하면 DocView와 기본 파일 내용을 토글한다.


보통 DocView 모드로 처리되는 파일을 방문하지만 일부 요구조건이 충족되지 않으면 (예: PNG 지원이 되지 않는 emacs 또는 터미널 프레임에서 실행 중일 때), 문서의 내용을 일반 텍스트로 보길 원하는지 질문을 받을 것이다. 이에 확인(confirm)하면 버퍼가 텍스트 모드(text mode)에 놓이고 DocView 부 모드가 활성화된다. 따라서 폴백(fallback) 모드로 전환하려면 C-c C-c 를 입력하면 된다. 다시 C-c C-c 를 입력하면 DocView 모드로 돌아간다. C-c C-t (
doc-view-open-text
)를 입력하면 DocView 모드 내에서 일반 텍스트 내용을 표시할 수도 있다.


M-x doc-view-mode 명령어를 이용해 DocView 모드를 직접 켤 수도 있다. DocView 부 모드는 M-x doc-view-minor-mode 로 토글할 수 있다.


DocView 모드가 시작되면 환영하는 화면을 표시하고 파일의 페이지마다 포맷팅을 시작한다. 포맷팅이 완료되면 첫 페이지를 표시한다.


DocView 버퍼를 죽이(kill)려면 k (doc-view-kill-proc-and-buffer)를 입력한다. 또한 bury를 위해서는 q (
quit-window
)를 입력한다.


DocView 탐색(DocView Navigation)

DocView 모드에서는 일반 Emacs 움직임 키, 즉 C-p, C-n, C-b, C-f, 화살표 키를 이용해 현재 페이지를 스크롤할 수 있다.


기본적으로 라인 움직임 키인 C-pC-n 은 각각 현재 페이지의 시작과 끝에서 스크롤을 중단한다. 하지만
doc-view-continuous
변수를
nil
이 아닌 값으로 설정하면 현재 페이지의 시작 위치에 이미 있을 때 C-p 를 입력하면 이전 페이지를 표시하고, 현재 페이지의 끝에 있을 때 C-n 을 입력하면 다음 페이지를 표시한다.


n, next, C-x ] (
doc-view-next-page
) 중 하나를 입력하여 다음 페이지를 표시할 수도 있다. 이전 페이지는 p, prior, C-x [ (
doc-view-previous-page
) 중 하나를 입력하여 표시한다.


SPC (
doc-view-scroll-up-or-next-page
) 는 문서를 편리하게 넘기는(advance through) 방법이다. 이는 현재 페이지 내에서 스크롤하거나 다음 페이지로 넘긴다(advance). DEL 은 이와 비슷한 방식으로 역방향 이동한다(
doc-view-scroll-down-or-previous-page
).


첫 번째 페이지로 이동하려면 M-< (
doc-view-first-page
) 를 입력하고, 마지막 페이지로 이동하려면 M-> (
doc-view-last-page
)를 입력한다. 페이지 번호를 이용해 페이지로 점프하려면 M-g M-g 또는 M-g g (
doc-view-goto-page
)를 입력한다.


+ (
doc-view-enlarge
) 그리고 - (
doc-view-shrink
)를 이용해 문서를 확대하거나 축소시킬 수도 있다. 이러한 명령어들은 문서를 새로운 크기로 복구시켜 작동한다. DocView 에 기본 크기를 명시하려면
doc-view-resolution
변수를 맞춤화한다.


DocView 검색하기(DocView Searching)

DocView 모드에서는 파일의 텍스트에서 정규 표현식을 검색할 수 있다(97 페이지의 12.6절 [Regexps] 참고). 검색을 위한 인터페이스는 isearch의 영향을 받는다(90 페이지의 12.1절 [증분 검색(Incremental Search)] 참고).


검색을 시작하려면 C-s (
doc-view-search
) 또는 C-r (
doc-view-search-backward
) 를 입력한다. 이는 미니버퍼를 이용해 정규 표현식을 읽은 후 문서에서 발견된 일치 결과의 수를 반영(echo)한다. C-sC-r 을 입력하여 일치 결과들을 전방향 또는 역방향으로 이동할 수도 있다. DocView 모드에는 페이지 이미지 내에서 일치 결과를 표시할 방법이 없으며, 대신 현재 페이지에 일치하는 행을 모두 열거하는 툴팁을 (마우스 위치에) 표시한다. 강제로 이러한 툴팁을 표시하려면 C-t (
doc-view-show-tooltip
) 을 입력한다.


새로운 검색을 시작하기 위해서는 접두 인자와 함께 검색 명령어를 사용한다(예: 순방향 검색은 C-u C-s, 역방향 검색은 C-u C-r).


DocView 슬라이싱(DocView Slicing)

보통 문서에는 출력을 위해 넓은 여백이 있다. 그런데 화면에서는 공간을 차지하여 불편한 스크롤링을 야기하기 때문에 화면에서 문서를 읽을 때에는 불편하기 짝이 없다.


DocView 모드를 이용하면 표시할 페이지의 슬라이스(slice)를 선택함으로써 이러한 여백을 숨길 수 있다. 슬라이스는 페이지 영역 내 직사각형으로, DocView에서 슬라이스를 명시했다면 사용자가 어떤 페이지를 바라보는지에도 적용된다.


슬라이스를 수치적으로 명시하려면 s s (
doc-view-set-slice
) 를 입력한 후 상단 좌측 픽셀 위치와 슬라이스의 너비 및 높이를 입력한다.


슬라이스를 그래픽 방식으로 좀 더 편리한 명시하는 방법은 s m (
doc-view-set-slice-using-mouse
) 를 이용하는 방법으로, 마우스를 이용하여 슬라이스를 선택할 수 있다. 슬라이스에 포함시키려는 영역의 상단 자측 모서리에 왼쪽 마우스 버튼을 누르고 있다가 마우스 포인트를 하단 우측 모서리로 이동시킨 후 놓는다.


가장 편리한 방법은 s b (
doc-view-set-slice-from-bounding-box
) 를 입력하여 자동으로 결정된 BoundingBox 정보를 이용함으로써 최적의 슬라이스를 설정하는 것이다.


선택된 슬라이스를 취소하려면 s r (
doc-view-reset-slice
) 을 입력한다. 이후 DocView는 전체 여백을 포함하여 전체 페이지를 표시한다.


DocView 변환(DocView Conversion)

효율성을 위해 DocView는 gs가 생성한 이미지를 캐시 저장(cache)한다. 해당 디렉터리 이름은
doc-view-cache-directory
변수에 의해 주어진다. 캐시 디렉터리는 M-x doc-view-clear-cache 를 이용해 지울 수 있다.


최근에 본 문서를 강제로 재변환하려면 r 또는 g (revert-buffer)를 입력한다. 현재 버퍼와 관련된 컨버터 프로세스를 제거하려면 K (
doc-view-kill-proc
)를 입력한다. k (
doc-view-kill-proc-and-buffer
) 명령어는 컨버터 프로세스와 DocView 버퍼를 제거한다.


EWW를 이용한 웹 브라우징(Web Browsing with EWW)

Emacs Web Wowser 의 줄임말인 EWW 는 Emacs 용 웹 브라우저 패키지다. 이는 Emacs 버퍼 내에서 URL을 볼 수 있도록 해준다. M-x eww 명령어를 이용하면 URL을 열거나 웹을 검색한다. M-x eww-open-file 명령어를 이용하면 파일을 열 수 있다.
browse-url
에 대한 웹 브라우저로 EWW 를 이용할 수도 있는데, 이는 405 페이지의 31.11.1절 [Browse-URL]을 참고한다. 전체적인 내용은 The Emacs Web Browser Manual 을 참고한다.


Emacs로부터 셸 명령어 실행하기(Running Shell Commands from Emacs)

Emacs는 단일 명령 행을 셸 하위프로세스로 전달하고, 셸을 Emacs 버퍼에 대한 입출력을 상호작용적으로 실행하며, 터미널 에뮬레이터 창에서 셸을 실행하기 위한 명령어들을 제공한다.


M-! cmd RET
cmd 라는 셸 명령어를 실행하여 출력을 표시한다(
shell-command
).


M-| cmd RET
영역 내용을 입력(input)으로 하여 cmd 라는 셸 명령어를 실행하고, 선택적으로는 영역은 출력(output)으로 대체한다(
shell-command-on-region
).


M-& cmd RET
셸 명령어 cmd 를 비동기식으로 실행하고 출력을 표시한다(
async-shell-command
).


M-x shell
Emacs 버퍼를 통해 입출력을 이용해 하위셸을 실행한다. 이후 대화형으로 명령어를 제공할 수 있다.


M-x term
Emacs 버퍼를 통해 입출력을 이용해 하위셸을 실행한다. 이후 대화형으로 명령어를 제공할 수 있다. 터미널 에뮬레이션을 전체적으로 이용 가능하다.


실행 가능 프로그램에 상대 파일명을 (위의 명령어들 중 하나에 대한 cmd 인자에서 또는 다른 컨텍스트에) 명시할 때마다 Emacs 는
exec-path
변수가 명시하는 디렉터리에서 프로그램을 검색한다. 이 변수의 값은 디렉터리명으로 된 목록이어야 하고, 기본값은 Emacs 가 시작될 때 환경 변수
PATH
로부터 초기화된다(483 페이지의 C.4.1절 [일반 변수(General Variables)] 참고).


M-x eshell 은 Emacs 에서 전적으로 실행되는 셸을 호출한다. 이것은 자체 매뉴얼에 문서화된다. Emacs 와 함께 배포되는 Eshell Info 매뉴얼을 참고한다.


단일 셸 명령어(Single Shell Commands)

M-! (
shell-command
)는 미니버퍼를 이용해 텍스트의 라인을 읽고 해당 명령어를 위해서만 만들어진 하위셸에서 셸 명령어로서 라인을 실행한다. 명령어에 대한 표준 입력은 null 장치로부터 온다. 셸 명령어가 어떤 출력을 생성하든 출력은 에코 영역 (짧을 경우) 또는 다른 창에 표시된
*Shell Command Output*
이라는 Emacs 버퍼에 (출력이 길 경우) 나타난다.


예를 들어
foo.gz
라는 파일을 압축 해제하는 한 가지 방법은 M-! gunzip foo.gz RET 를 입력하는 방법이다. 해당 셸 명령어는 보통
foo
파일을 생성하고 어떠한 터미널 출력도 생성하지 않는다.


shell-command
에 대한 수치적 인자(예: M-1 M-!)는 별도의 버퍼가 아니라 현재 버퍼로 터미널 출력을 삽입하도록 야기한다. 이는 출력 앞에 포인트를 위치시키고, 출력 다음에 마크를 설정한다. 예를 들어 M-1 M-! gunzip < foo.gz RET
foo.gz
파일의 압축 해제된 형태를 현재 버퍼로 삽입할 것이다.


명시된 셸 명령어가 '
&
' 로 끝나지 않을 경우 동기식으로 실행되므로 Emacs 의 사용을 계속하려면 그것이 종료될 때까지 기다려야 한다. 대기를 중단하려면 C-g 를 입력하여 중단하면 되는데, 이런 경우 셸 명령어를 중단시키는
SIGINT
시그널이 전송된다(이는 C-c 가 셸에서 일반적으로 생성하는 것과 동일한 시그널이다). Emacs 는 그러면 명령어가 실제로 중단될 때까지 기다린다. (
SIGINT
시그널을 무시하여) 셸 명령어가 중단되지 않을 경우, C-g 를 다시 입력하면 무시하는 것이 불가능한
SIGKILL
시그널을 명령어로 전송할 것이다.


'
&
'로 끝나는 셸 명령어는 비동기식으로 실행되므로 그것이 실행되는 동안 사용자는 Emacs를 계속해서 사용할 수 있다. M-& (
async-shell-command
)를 입력하면 셸 명령어를 비동기식으로 실행하는데, '
&
' 가 불필요하다는 점만 제외하면 끝에 '
&
' 가 달린 M-! 를 호출하는 것과 정확히 동일하다. 비동기식 셸 명령어에 대한 기본 출력 버퍼는 '
*Async Shell Command*
' 로 명명된다. Emacs는 버퍼가 창에 표시되는 여부와 상관없이 출력이 들어오면 이 버퍼로 삽입한다.


동시에 하나 이상의 비동기식 셸 명령어를 실행하길 원할 경우 출력 버퍼를 경쟁하게 될 수도 있다.
async-shell-command-buffer
옵션을 이용해 이런 상황을 어떻게 처리할 것인지 명시하는데, 가령 기존에 존재하던 출력 버퍼를 재명명하거나 새로운 명령어에 대해 새로운 버퍼를 사용하는 방법이 있다. 그 외의 방법은 변수에 대한 문서를 참고한다.


M-| (
shell-command-on-region
)은 M-! 와 같지만 입력이 없는 것이 아니라 (no input) 영역의 내용을 표준 입력으로 하여 셸 명령어로 전달한다. 수치적 인자를 이용하면 오래된 영역을 삭제하고 그것을 셸 명령어로부터 받은 출력으로 대체한다.


예를 들어 버퍼에 어떠한 키가 있는지 확인하려면 gpg 프로그램의 도움으로 M-| 을 사용할 수 있다. 버퍼가 GnuPG 키를 포함할 경우 C-x h M-| gpg RET 를 입력하여 전체 버퍼 내용을 gpg 로 feed한다. 그러면 키 목록이
*Shell Command Output*
버퍼로 출력될 것이다.


위의 명령어들은
shell-fill-name
변수가 명시한 셸을 사용한다. 그 기본값은 Emacs 가 시작될 때 SHELL 환경 변수로 결정된다. 파일명이 상대명일 경우 Emacs 는
exec-path
에 열거된 디렉터리를 검색한다(383 페이지의 31.4절 [셸(Shell)] 참고).


M-! 또는 M-l 에 대한 코딩 시스템을 명시하기 위해서는 바로 직전에 C-x RET c 명령어를 사용한다. 관련 내용은 189 페이지의 19.10절 [통신 코딩(Communication Coding)]을 참고한다.


기본적으로 오류 출력은 출력 버퍼에서 일반 출력과 섞인다. 하지만
shell-command-default-error-buffer
변수의 값을 문자열로 변경하면 오류 출력이 해당 이름으로 된 버퍼로 삽입된다.


대화형 하위셸(Interactive Subshell)

하위셸을 대화형으로 실행하기 위해서는 M-x shell 을 입력한다. 이는
*shell*
이라는 버퍼를 생성(또는 재사용)하고, 해당 버퍼로 향하는 출력과 그로부터 나오는 입력을 이용해 셸 하위프로세스를 실행한다. 이는 하위셸로부터 나오는 터미널 출력이 버퍼로 들어가고, 포인트를 advance 하며, 하위셸에 대한 터미널 입력은 모두 버퍼 내 텍스트로부터 비롯된다는 의미다. 하위셸에 입력 값을 제공하려면 버퍼 끝으로 가서 입력 값을 입력한 후 RET 를 입력하여 마친다.


하위셸이 명령어를 기다리거나 실행 중일 때에는 창 또는 버퍼를 전환하여 Emacs 에서 다른 편집을 실행할 수 있다. Emacs는 하위셸로부터 출력을 처리할 시기가 될 때마다 (예: 키보드 입력을 기다릴 때) Shell 버퍼로 삽입한다.


Shell 버퍼에서 프롬프트는
comint-highlight-prompt
겉모습(face)으로 표시되고, 제출된 입력 라인은
comint-highlight-input
겉모습(face)을 이용해 표시된다. 이로 인해 셸 출력으로부터 입력 라인을 구별하기가 쉬워진다. 74 페이지의 11.8절 [겉모습(Faces)]를 참고한다.


여러 개의 하위셸을 만들기 위해서는 접두 인자를 이용해 M-x shell 을 호출한다(예: C-c M-x shell). 그러면 명령어는 버퍼명을 읽고 해당 버퍼에서 하위셸을 생성(또는 재사용)할 것이다. M-x rename-uniquely 를 이용해
*shell*
버퍼를 재명명하고, 일반 M-x shell 을 이용해 새로운
*shell*
버퍼를 생성할 수도 있다. 여러 다른 버퍼 내 하위셸은 독립적으로 그리고 동시에 실행된다.


M-x shell 이 사용하는 셸 파일명을 명시하기 위해서는
explicit-shell-file-name
변수를 맞춤화한다. 그 값이
nil
일 경우 (기본값) Emacs 는 환경 변수 ESHELL 이 존재하면 그것을 사용한다. 그 외의 경우에는 주로
shell-file-name
변수를 사용하지만 (383 페이지의 31.4.1절 [단일 셸(Single Shell)] 참고) 기본 디렉터리가 원격일 경우 (142 페이지의 15.13절 [원격 파일(Remote Files)] 참고) 사용자에게 셸 파일명을 입력하도록 요한다.


Emacs 는
~/.emacs_shellname
이란 파일이 존재하면 그 내용을 입력으로 하여 새로운 셸로 전송하는데, 이름에서 shellname 은 셸을 로딩하는 파일명을 나타낸다. 가령 배시를 사용할 경우 배시로 전송된 파일은
~/.emacs_bash
이다. 이 파일을 찾을 수 없다면 Emacs 는
~/.emacs.d/init_shellname.sh
를 시도한다.


셸에 대한 코딩 시스템을 명시하기 위해서는 M-x shell 직전에 C-x RET c 명령어를 사용할 수 있다. 셸 버퍼에서 C-x RET p 를 입력하면 실행 중인 하위셸에 대한 코딩 시스템을 변경할 수도 있다. 189 페이지의 19.10절 [통신 코딩(Communication Coding)]을 참고한다.


Emacs 는 하위셸 내에
INSIDE_EMACS
환경 변수를 '
version, comint
'로 설정하는데, 여기서 version 은 Emacs 버전을 의미한다(예: '24.1'). 프로그램은 그것이 Emacs 하위셸 안에서 실행 중인지 결정할 때 해당 변수를 확인할 수 있다. (이는 해당 환경 변수가 이미 정의되지 않은 경우
EMACS
환경 변수를
t
로 설정하기도 한다. 하지만 이 환경 변수는 더 이상 사용하지 않으며 이를 사용하는 프로그램들은 대신
INSIDE_EMACS
를 사용한다.)


셸 모드(Shell Mode)

Shell 버퍼에 대한 주 모드는 Shell 모드이다. 그 특수 명령어들 중 다수는 C-c 접두어에 바인딩되어 있고 일반 셸에 존재하는 편집 및 작업 제어 문자와 닮았는데, 사용자가 C-c 를 먼저 입력해야 한다는 점이 다르다. Shell 모드 명령어의 목록을 아래에 소개하겠다:


RET
현재 행을 하위셸에 대한 입력 값으로 전송한다(
comint-send-input
). 행의 시작에 있는 셸 프롬프트는 모두 생략된다(387 페이지의 31.4.4절 [셸 프롬프트(Shell Prompt)] 참고). 포인트가 버퍼의 끝에 있을 경우 이것은 일반 대화형 셸에서 명령어를 제출하는 것과 같다. 하지만 현재 행을 입력 값으로 제출하려면 셸 버퍼 아무데서나 RET를 호출할 수 있다.


TAB
셸 버퍼에서 포인트 앞에서 명령어 이름이나 파일명을 완성한다(
completion-at-point
). 이것은 일반적인 Emacs 완성 규칙을 이용하며 (28 페이지의 5.4절 [완성(Completion)] 참고) 완성 대안은 파일명, 환경 변수명, 셸 명령어 히스토리, 히스토리 참조가 될 수 있다(390 페이지의 31.4.5.3절 [히스토리 참조(History References)] 참고). 완성을 제어하는 옵션에 관한 내용은 390 페이지의 31.4.7절 [셸 옵션(Shell Options)]을 참고한다.


M-?
포인트 앞에 파일명으로 가능한 완성 목록을 일시적으로 표시한다(
comint-dynamic-list-filename-completions
).


C-d
문자를 삭제하거나 EOF 를 전송한다(
comint-delchar-or-maybe-eof
). 셸 버퍼 끝에서 입력할 경우 이는 EOF 를 하위셸로 전송한다. 버퍼 내 다른 위치에서 입력할 경우에는 보통처럼 문제를 삭제한다.


C-c C-a
라인 시작으로 이동하되 프롬프트가 있을 경우 프롬프트 뒤로 이동한다(
comint-bol-or-process-mark
). 라인에서 이 명령어를 두 번 반복할 경우, 두 번째 실행 시 프로세스 마크로 다시 이동하는데, 이는 하위셸로 아직 전송하지 않은 입력 값의 시작 부분이 된다. (보통 프로세스 마크는 해당 라인에서 프롬프트의 끝과 동일한 위치에 있지만
C-c SPC
를 실행하고 나면 프로세스 마크가 이전 (previous) 라인에 위치할 수도 있다).


C-c SPC
입력의 다중 행을 누적시켜 함께 전송한다. 이 명령어는 포인트 앞에 개행 문자를 삽입하지만 선행하는 텍스트를 입력으로 하여 하위셸로 전송하지는 않는다(적어도 아직은). 개행 문자 앞의 라인과 뒤의 라인은 (그것을 구분하는 라인과 함께) 사용자가 RET를 입력하면 함께 전송될 것이다.


C-c C-u
버퍼의 끝에서 입력으로 전송될 예정이지만 대기 중인 모든 텍스트를 제거한다(
comint-kill-input
). 포인트가 버퍼의 끝에 위치하지 않은 경우 이 명령어는 포인트를 선행하는 텍스트 부분만 제거한다.


C-c C-w
포인트 앞의 단어를 제거한다(
backward-kill-word
).


C-c C-c
셸 또는 셸의 현재 하위작업이 있을 경우 간섭한다(
comint-interrupt-subjob
). 이 명령어는 셸 버퍼에서 대기 중이고 전송되지 않은 셸 입력을 제거하기도 한다.


C-c C-z
셸 또는 셸의 현재 하위작업이 있을 경우 중단시킨다(
comint-stop-subjob
). 이 명령어는 셸 버퍼에서 대기 중이고 전송되지 않은 셸 입력을 제거하기도 한다.


C-c C-\
셸 또는 셸의 현재 하위작업이 있을 경우 그곳으로 중단 시그널을 전송한다(
comint-quit-subjob
). 이 명령어는 셸 버퍼에서 대기 중이고 전송되지 않은 셸 입력을 제거하기도 한다.


C-c C-o
셸 명령어로부터 마지막 출력 배치(batch)를 삭제한다(
comint-delete-output
). 셸 명령어가 방해되는 출력을 많이 보낼 때 유용하다.


C-c C-s
셸 명령어로부터 마지막 출력 배치를 파일로 쓴다(
comint-write-output
). 접두 인자를 이용해 파일을 덧붙일 수도 있다. 출력 끝에 있는 프롬프트는 작성되지 않는다.


C-c C-r
C-M-l
창의 상단에서 마지막 출력 배치의 시작을 표시하도록 스크롤하고, 커서도 그곳으로 이동한다(
comint-show-output
).


C-c C-e
버퍼의 끝을 창의 하단에 놓도록 스크롤한다(
comint-show-maximum-output
).


C-c C-f
하나의 셸 명령어를 거쳐 순방향으로 이동하되 현재 라인을 넘지는 않는다(
shell-forward-command
).
shell-command-regexp
변수는 명령어 끝을 인식하는 방법을 명시한다.


C-c C-b
하나의 명령어를 거쳐 역방향으로 이동하되 현재 라인을 넘지는 않는다(
shell-backward-command
).


M-x dirs
셸로 작업 디렉터리에 대해 질문하고 Shell 버퍼의 기본 디렉터리를 업데이트한다. 390 페이지의 31.4.6절 [디렉터리 추적(Directory Tracking)]을 참고한다.


M-x send-invisible RET text RET
text 를 에코잉 없이 읽은 후에 입력 값으로 하여 셸로 전송한다. 셸 명령어가 암호를 요구하는 프로그램을 실행 시 유용하다.
Emacs는 기본적으로 암호를 에코잉하지는 않음을 명심한다. 에코잉을 원한다면 다음 Lisp 표현식을 평가한다(278 페이지의 24.9절 [Lisp Eval] 참고).
(remove-hook 'comint-output-filter-functions
             'comint-watch-for-password-prompt)


M-x comint-continue-subjob
셸 프로세스를 계속한다. 실수로 셸 프로세스[3]를 지연시킨 경우 유용하다.


M-x comint-strip-ctrl-m
셸 출력의 현재 그룹으로부터 모든
control-M
문자를 삭제한다(discard). 이 명령어를 가장 편리하게 사용하는 방법은 사용자가 하위셸로부터 출력을 얻을 때 자동으로 실행하도록 만드는 방법이다. 이를 위해선 아래의 Lisp 표현식을 평가한다:
(add-hook 'comint-output-filter-functions 
          'comint-strip-ctrl-m)


M-x comint-truncate-buffer
이 명령어는 셸 버퍼를 정해진 최대 라인 수로 절단하는데, 이러한 수는
comint-buffer-maximum-size
변수로 명시된다. 사용자가 하위셸로부터 출력을 얻을 때마다 자동으로 이를 실행하는 방법은 다음과 같다:
(add-hook 'comint-output-filter-functions 
          'comint-truncate-buffer)


Shell 모드는 Comint 모드의 파생 모드로, 대화형 하위프로세스와 통신하는 일반 용도의 모드이다. Shell 모드의 기능 대부분은 위에 열거된 명령어에서 볼 수 있듯이 사실상 Comint 모드에서 비롯된다. Shell 모드의 특수 기능으로는 디렉터리 추적 기능과 몇 가지 사용자 명령어가 포함된다.


그 외 Comint 모드의 변형 모드를 사용하는 Emacs 기능들은 GUD 와 (266 페이지의 24.6절 [디버거(Debuggers)] 참고) M-x run-lisp 를 (279 페이지의 24.11절 [외부 Lisp(External Lisp)] 참고) 포함한다.


M-x comint-run 을 이용하면 Shell 모드를 특수화하지 않은 미수정된(unmodified) Comint 모드를 이용해 하위프로세스에서 원하는 프로그램을 아무 것이나 실행할 수 있다.


셸 프롬프트(Shell Prompts)

프롬프트는 새로운 사용자 입력을 수용할 준비가 되었음을 표시하기 위해 프로그램이 출력하는 텍스트이다. 보통 Comind 모드(따라서 Shell 모드)는 하위프로세스의 출력을 기반으로 하여 버퍼의 일부가 프롬프트임을 자동으로 알아낸다. (구체적으로 말하자면 개행 문자로 끝나지 않는 수신된 출력 라인은 프롬프트라고 추정한다.)


Comint 모드는 버퍼를 두 가지 유형의 필드(field), 바로 입력 필드(input fields; 사용자 입력을 타이핑하는)와 출력 필드(output fields; 입력 필드를 제외한 모든 필드)로 나눈다. 프롬프트는 출력 필드의 일부다. 대부분의 Emacs 움직임 명령어는 여러 라인에 걸쳐 이동하지 않는 이상 필드 경계를 넘지 않는다. 가령 포인트가 셸 명령행에서 입력 필드에 있을 때 C-a 를 사용하면 포인트를 프롬프트 다음의 입력 필드 시작에 놓는다. 내부적으로 필드는
field
텍스트 속성을 이용해 구현된다(the Emacs Lisp Reference Manual 의 "Text Properties" 절을 참고).


comint-use-prompt-regexp
변수를
nil
이 아닌 값으로 변경하면 Comint 모드는 정규 표현식을 이용해 프롬프트를 인식한다(97 페이지의 12.6절 [Regexps] 참고). Shell 모드에서 정규 표현식은
shell-prompt-pattern
변수로 명시된다.
comint-use-prompt-regexp
를 이용해 프롬프트를 인식하는 방법은 신뢰할 수 없으므로 기본값은
nil
이지만 특이한 상황에서
nil
이 아닌 값으로 설정하길 원할 수도 있다. 이런 경우 Emacs 는 Comint 버퍼를 필드로 나누지 않으므로 일반 움직임(motion) 명령어들은 텍스트의 특수 속성이 없이 버퍼에서와 마찬가지로 동작할 것이다. 하지만 편리하게 버퍼를 탐색하도록 문단 움직임 명령어를 사용할 수도 있는데 (210 페이지의 22.3절 [문단(Paragraphs)] 참고) Shell 모드에서 Emacs 는
shell-prompt-pattern
을 문단 경계로 사용한다.


셸 명령어 히스토리(Shell Command History)

Shell 버퍼는 이전 명령어를 반복하는 방법으로 세 가지를 지원한다. 미니버퍼 히스토리에 사용되는 키처럼 키를 사용할 수 있는데, 이는 대부분 미니버퍼에서와 같이 행동하므로 이전 명령어로부터 텍스트를 삽입하는 동안 포인트는 버퍼의 끝에 항상 남아 있는다. 버퍼를 이전 입력의 원래 위치로 이동한 후 다시 제출하거나 끝으로 복사할 수도 있다. 아니면 '!' 스타일의 히스토리 참조를 이용할 수도 있다.

셸 히스토리 링(Shell History Ring)
M-p
C-UP
다음으로 오래된 셸 명령어를 꺼낸다(fetch).


M-n
C-DOWN
다음으로 최근의 셸 명령어를 꺼낸다.


M-r
오래된 셸 명령어에서 증분 regexp 검색을 시작한다.


C-c C-x
히스토리에서 그 다음 명령어를 꺼낸다.


C-c .
오래된 셸 명령어에서 하나의 인자를 꺼낸다.


C-c C-l
셸 명령어에 대한 버퍼의 히스토리를 다른 창에 표시한다(
comint-dynamic-list-input-ring
).


셸 버퍼는 이전에 입력한 셸 명령어의 히스토리를 제공한다. 히스토리로부터 셸 명령어를 재사용하기 위해서는 편집 명령어 M-p, M-n, M-r, M-s 를 사용한다. 이는 미니버퍼 히스토리 명령어와 같이 작동하는데 (32 페이지의 5.5절 [미니버퍼 히스토리(Minibuffer History)] 참고) 미니버퍼가 아니라 Shell 버퍼 내에서 작동한다는 점에서 차이가 있다.


M-p 는 이전의 (earlier) 셸 명령어를 셸 버퍼의 끝으로 꺼낸다. 잇따라 M-p 를 사용할 때마다 이전 셸 명령어를 연속으로 꺼내고, 실행 시마다 이미 잠재적 셸 입력으로서 존재하였던 텍스트를 대체한다. M-n 도 동일한 일을 수행하지만 버퍼로부터 좀 더 최근의 셸 명령어를 연속하여 검색한다는 점에 차이가 있다. C-UPM-p 와 같고, C-DOWNM-n 과 같다.


히스토리 검색 명령어 M-r 은 이전 셸 명령어에 대해 정규 표현식의 증분 검색을 시작한다. M-r 을 입력한 후에는 원하는 문자열이나 정규 표현식을 입력하기 시작하고, 마지막으로 일치하는 셀 명령어가 현재 라인에 표시될 것이다. 증분 검색 명령어들은 평소와 동일한 효과를 가지므로, 가령 C-sC-r 은 다음 매칭 결과를 각각 순방향, 그리고 역방향으로 검색한다(90 페이지의 12.1절 [증분 검색(Incremental Search)] 참고). 원하는 입력 값을 찾으면 RET 를 입력하여 검색을 종료한다. 이는 명령행에 입력 값을 넣을 것이다. 히스토리 링의 시작이나 끝으로 이동하면 히스토리 목록을 탐색하기 전에 작성 중이던 부분적 입력이 복구될 것이다.


이전에 시퀀스로 실행한 여러 연속된 셸 명령어를 재실행하는 것이 유용할 때도 있다. 이를 위해서는 먼저 시퀀스의 첫 번째 명령어를 찾아서 재실행한다. 이후 C-c C-x 를 입력하면 다음 명령어, 즉 방금 반복한 명령어 뒤에 따라오는 명령어를 꺼낼 것이다. 그리고 RET 를 입력하면 이 명령어가 재실행된다. 이후부터 C-c C-x RET 를 반복 입력하면 여러 개의 연속된 명령어를 재실행할 수 있다.


C-c . (comint-input-previous-argument) 명령어는 ESC . 와 같은 개별 인자를 이전 명령어로부터 Bash로 복사한다. 가장 간단하게 사용할 경우 이전 셸 명령어의 마지막 인자를 복사한다. 수치적 인자 n 을 이용하면 대신 n 번째 인자를 복사한다. C-c . 을 반복하면 항상 n 이라는 동일한 값을 이용하여 이전 셸 명령어로부터 대신 복사한다(C-c . 명령어를 반복하여 사용할 생각이라면 접두 인자를 제공하지 말라).


이러한 명령어들은 셸 버퍼 자체가 아니라 특수 히스토리 목록에서 이전 셸 명령어의 텍스트를 얻는다. 따라서 셸 버퍼를 편집하거나 심지어 그 중 큰 부분을 죽이더라도(kill) 이러한 명령어가 접근하는 히스토리에는 영향을 미치지 않는다.


일부 셸은 파일에 명령어 히스토리를 보관하여 사용자가 이전 셸 세션의 명령어를 참조할 수 있도록 한다. Emacs는 선택된 셸에 대한 명령어 히스토리를 읽어 고유의 명령어 히스토리를 초기화한다. 파일명은 bash 의 경우
~/.bash_history
이고, ksh 의 경우
~/.sh_history
이며, 그 외의 셸은
~/.history
가 된다.


셸 히스토리 복사하기(Shell History Copying)
C-c C-p
포인트를 이전 프롬프트로 이동한다(
comint-previous-prompt
).


C-c C-n
포인트를 다음 프롬프트로 이동한다(
comint-next-prompt
).


C-c RET
포인트에 위치한 입력 명령어를 복사하여 버퍼 끝에 사본을 삽입한다(
comint-copy-old-input
). 사용자가 포인트를 이전 명령어로 다시 이동할 경우 유용하다. 명령어를 복사하고 나면 RET 를 이용해 복사본을 입력값으로 제출할 수 있다. 원한다면 다시 재출하기 전에 편집할 수도 있다. 출력 라인에서 이 명령어를 사용 시 해당 라인을 버퍼의 끝으로 복사한다.


Mouse-2
comint-use-prompt-regexp
의 값이 기본값
nil
일 경우, 사용자가 클릭하는 오래된 입력 명령어를 복사하여 버퍼의 끝에 사본을 삽입한다(comint-insert-input).
comint-use-prompt-regexp
nil
이 아닌 값이거나 클릭한 곳이 오래된 입력값이 아닌 경우 평소대로 붙여넣기(yank)를 실행한다.


이전 입력으로 이동하여 C-c RET 또는 Mouse-2 를 이용해 복사하여도 동일한 결과, 즉 동일한 버퍼 내용이 생성되는데, 이는 히스토리 목록에서 이전 입력을 꺼내기에 충분한 횟수만큼 M-p 를 입력하여 얻는 결과와 동일하다. 하지만 C-c RET 는 버퍼로부터 텍스트를 복사하기 때문에 입력 텍스트가 전송된 후 버퍼에서 텍스트를 편집할 경우 그 내용은 히스토리에 있는 내용과 다를 수 있다.


셸 히스토리 참조(Shell History References)
csh 와 bash 를 포함해 다양한 셸들이 '
!
' 와 '
^
' 로 시작하는 히스토리 참조(history references)를 지원한다. Shell 모드는 이러한 구조체를 인식하며, 사용자를 위해 히스토리 대체를 실행할 수 있다.


히스토리 참조를 삽입하여 TAB 을 입력하면 일치하는 명령어에 대해 입력 히스토리를 검색하고, 필요 시 대체를 실행하며, 버퍼에 히스토리 참조 대신 결과를 위치시킨다. 예를 들어 ! m v TAB 을 이용하면 '
mv
' 로 시작하는 가장 최근 명령어를 꺼낼 수 있다. 원하면 명령어를 편집하여 RET 를 입력함으로써 셸로 다시 제출할 수 있다.


Shell 모드는 사용자가 히스토리 참조로 셸을 전송하면 버퍼 내에서 히스토리를 확장할 수 있는 옵션을 가진다. 이를 요청하려면
comint-input-autoexpand
변수를
input
으로 설정하라.
comint-magic-space
명령어로 SPC 를 바인딩하면 SPC 가 히스토리 확장을 실행하도록 만들 수 있다.


Shell 모드는 프롬프트를 따를 때 히스토리 참조를 인식한다. Shell 모드가 프롬프트를 어떻게 인식하는지에 관한 정보는 387 페이지의 31.4.4절 [셸 프롬프트(Shell Prompts)]를 참고한다.


디렉터리 추적(Directory Tracking)

Shell 모드는 하위셸에 주어진 '
cd
', '
pushd
', '
popd
' 명령어를 추적하여 Shell 버퍼의 기본 디렉터리를 셸의 작업 디렉터리와 동일하게 유지한다(122 페이지의 15.1절 [파일명(File Names)] 참고). 또한 사용자가 전송한 입력 라인을 조사함으로써 이러한 명령어들을 인식한다.


이러한 명령어들에 대한 별칭을 사용할 경우
shell-pushd-regexp
,
shell-popd-regexp
,
shell-cd-regexp
변수를 적절한 정규 표현식으로 설정함으로써 Emacs 에게 인식하도록 알릴 수 있다(97 페이지의 12.6절 [Regexp] 참고). 예를 들어
shell-pushd-regexp
가 셸 명령행의 시작에 일치할 경우 해당하는 라인은
pushd
명령어로서 간주된다. 이러한 명령어들은 셸 명령행의 시작에서만 인식된다.


Emacs 가 하위셸의 작업 디렉터리에 일어나는 변경 사항에 대해 혼동할 경우 M-x dirs 를 입력하라. 이 명령어는 작업 디렉터리를 위한 셸을 요청하고, 그에 따라 기본 디렉터리를 업데이트한다. 가장 흔한 명령어 구문을 지원하는 셸에는 적용되지만 흔하지 않은 셸에는 적용되지 않을 수도 있다.


셸의 작업 디렉터리를 추적하는 대안적 방법을 구현하는 버퍼 로컬 부 모드인 Dirtrack 모드도 사용 가능하다. 이 방법을 사용하기 위해서는 셸 프롬프트에 항상 작업 디렉터리가 포함되어야 하며, 프롬프트의 어떤 부분이 작업 디렉터리를 포함하는지 인식하기 위해서는 정규 표현식을 제공해야 하는데, 상세한 내용은
dirtrack-list
변수의 문서를 참고한다. Dirtrack 모드를 사용하려면 Shell 버퍼에서 M-x dirtrack-mode 를 입력하거나
dirtrack-mode
shell-mode-hook
으로 추가한다(422 페이지의 33.2.2절 [훅(Hooks)] 참고).


셸 모드 옵션(Shell Mode Options)

comint-scroll-to-bottom-on-input
변수의 값이
nil
이 아닌 경우 삽입 및 붙여넣기 명령어들은 선택된 창을 삽입하기 전에 가장 아래로 스크롤할 것이다. 기본값은
nil
이다.


comint-scroll-show-maximum-output
nil
이외의 값일 경우, 포인트가 끝에 위치할 때 출력이 도달하면 텍스트의 마지막 라인을 창의 최하단 라인으로 스크롤하여 유용한 텍스트를 가능한 한 많이 표시할 것이다. (대부분 터미널의 스크롤 동작을 모방한 것이다.) 기본값은 t 이다.


comint-move-point-for-output
을 설정하면 출력이 도달할 때마다 버퍼 내 포인트가 어디에 위치하였든 상관없이 버퍼 끝으로 포인트를 점프시킬 수 있다. 값이
this
일 경우 포인트는 선택된 창에서 점프한다. 값이
nil
이면 포인트는 Comint 버퍼를 표시하는 모든 창에서 점프한다.
other
를 값으로 하는 경우 포인트는 현재 버퍼를 표시하지만 선택되지 않은 모든 창에서 점프한다. 기본값은
nil
이므로 포인트가 끝으로 점프하지 않음을 의미한다.


comint-prompt-read-only
를 설정하면 Comint 버퍼 내 프롬프트는 읽기 전용이 된다.


comint-input-ignoredups
는 동일한 입력이 연속되면 입력 히스토리에 보관되는지를 제어한다.
nil
이외의 값의 경우, 이전 입력과 동일한 입력은 생략함을 의미한다. 기본값은
nil
로, 이전 입력과 동일하더라도 보관함을 의미한다.


세 가지 변수가 파일명 완성을 맞춤화한다.
comint-completion-addsuffix
변수는 완성이 완전히 완성된 파일이나 디렉터리명을 나타내기 위해 공백 또는 슬래시를 삽입하는지를 제어한다(nil 이외의 값은 공백 또는 슬래시를 삽입함을 의미).
comint-completion-recexact
nil
값이 아닌 경우, 일반 Emacs 완성 알고리즘이 단일 문자조차 추가할 수 없다면 TAB 으로 하여금 가장 짧은 완성을 선택하도록 지시한다.
comint-completion-autolist
nil
이 아닌 값으로 설정하면 완성이 정확하지 않을 때마다 가능한 완성을 모두 열거하라고 알린다.


명령어 완성은 보통 실행 가능한 파일만 고려한다.
shell-completion-execonly
nil
로 설정할 경우 실행 불가한 파일 역시 고려한다.


shell-completion-fignore
변수는 Shell 모드 완성에서 무시해야 할 파일명 확장자 목록을 명시한다. 기본설정은
nil
이지만 일부 사용자는 '
~
', '
#
', 또는 '
%
' 로 끝나는 파일명을 무시하는 ("
~
" "
#
" "
%
")를 선호한다. 그 외 관련된 Comint 모드들은 대신
comint-completion-fignore
변수를 사용한다.


셸 명령어 완성의 몇몇 구현에 대한 세부적인 내용은
shell-dynamic-complete-command
함수의 lisp 문서에서도 찾을 수 있다.


또한 '
pushd
' 의 행위를 설정할 수도 있다. 변수들은 '
pushd
' 에 인자가 주어지면 (
shell-pushd-tohome
) '
cd
' 와 같이 동작하는지, 수치적 인자가 주어지면 (
shell-pushd-dextract
)회전이 아니라 튀어나오는지(pop), 디렉터리가 이미 스택에 위치하지 않을 경우 그곳으로 추가하는 데에 그치는지를 (
shell-pushd-dunique
) 제어한다. 사용자가 선택하는 값은 물론 기본 셸에 일치해야 한다.


Emacs 터미널 에뮬레이터(Emacs Terminal Emulator)

텍스트 터미널 에뮬레이터에서 하위셸을 실행하기 위해서는 M-x term 을 사용하라. 이는
*terminal*
이라는 버퍼를 생성(또는 재사용)하고, 키보드에서 들어오는 입력과 그 버퍼로 나가는 출력을 이용해 하위셸을 실행한다.


터미널 에뮬레이터는 두 가지 입력 모드가 있는 Term 모드를 사용한다. Line 모드에서 Term 은 기본적으로 Shell 모드와 같이 행동한다(385 페이지의 31.4.3절 [셸 모드(Shell Mode)] 참고). Char mode 에서는 각 문자가 터미널 입력값으로서 직접 하위셸로 전송되는데, 기본적으로 C-c 에 해당하는 터미널 escape 문자는 제외된다(392 페이지의 31.4.9절 [Term 모드(Term Mode)] 참고). 입력값의 에코잉은 하위셸의 의무이며, 하위셸로부터의 터미널 출력은 모두 포인트를 넘어(advancing) 버퍼로 들어간다.


일부 프로그램들은 (Emacs를 포함해) 터미널 화면의 모양을 상세하게 제어할 필요가 있다. 그리고 이러한 제어는 특수 제어 코드를 전송하여 이루어진다. Term 모드는 현재 대부분 터미널에서 수용되는 ANSI-standard VT100-style escape 시퀀스를 (
xterm
포함) 인식하고 처리한다. (따라서 Emacs Term 창 안에서 Emacs를 실행하는 것이 가능하다.)


term
의 겉모습은 터미널 에뮬레이터의 텍스트에 대한 기본 모양을 명시한다(기본값은
default
겉모습과 동일하다). 터미널 제어 코드를 이용해 텍스트의 모양을 변경하면
term-color-black
,
term-color-red
,
term-color-green
,
term-color-yellow
,
term-color-blue
,
term-color-magenta
,
term-color-cyan
,
term-color-white
,
term-color-underline
,
term-color-bold
라는 겉모습에 의해 터미널 에뮬레이터에 표현된다. 74 페이지의 11.8절 [겉모습(Faces)]를 참고한다.


Term 모드를 이용해 직렬 포트로 연결된 장치와 통신할 수도 있다. 393 페이지의 31.4.11절 [직렬 터미널(Serial Terminal)]을 참고한다.


하위셸을 로딩하는 데에 사용된 파일명은 Shell 모드에서와 동일하게 결정된다. 다중 터미널 에뮬레이터를 만들기 위해서는 Shell 모드와 마찬가지로 M-x rename-uniquely 를 이용해
*terminal*
버퍼를 뭔가 다른 이름으로 재명명한다.


Shell 모드와 달리 Term 모드는 사용자의 입력값을 조사하여 현재 디렉터리를 추적하지 않는다. 하지만 일부 셸은 Term 에게 현재 디렉터리를 알려줄 수 있다. 1.15 이상의 bash 버전에서는 이것이 자동으로 실행된다.


Term 모드(Term Mode)

터미널 에뮬레이터는 두 가지 입력 방식을 가진 Term 모드를 사용한다. Line 모드에서 Term은 기본적으로 Shell 모드와 마찬가지로 동작한다(385 페이지의 31.4.3절 [셸 모드(Shell Mode)] 참고). Char 모드에서는 각 문자마다 하위셸로 직접 전송되는데, 주로 C-c 에 해당하는 Term escape 문자는 제외된다.


Line 과 char 모드를 전환하려면 아래의 명령어를 사용하라.


C-c C-j
Line 모드로 전환한다 (
term-line-mode
). 이미 line 모드일 경우 아무 것도 실행하지 않는다.


C-c C-k
Char 모드로 전환한다 (
term-char-mode
). 이미 char 모드일 경우 아무 것도 실행하지 않는다.


아래의 명령어들은 char 모드에서만 이용 가능하다.


C-c C-c
리터럴 C-c 를 하위셸로 전송한다.


C-c char
일반 Emacs 에서 C-x char 과 동일하다. 예를 들어 C-c o 를 사용하면 C-x o 의 전역적 바인딩을 호출하는데, 이는 보통 'other-window'에 해당한다.


Term 모드는 page-at-a-time 기능을 가진다. 이 기능을 켜면 출력은 한 페이지의 끝에서 잠시 중단된다.


C-c C-q page-at-a-time 기능을 토글한다. 이 명령어는 line 과 char 모드에서 모두 작동한다. 기능을 켜면 mode-line 은 '
page
' 단어를 표시하고, Term 이 하나 이상의 출력 화면을 수신할 때마다 중지하여 모드라인에 '
**MORE**
' 를 표시한다. 다음 출력 화면을 표시하려면 SPC 를, 다른 옵션을 보려면 ? 를 입력한다. 인터페이스는
more
프로그램과 비슷하다.


원격 호스트 셸(Remote Host Shell)

일반 터미널에서 사용할 수 있는 명령어를 (예:
telnet
또는
rlogin
명령어를) 이용해 Term 창으로부터 원격 컴퓨터로 로그인이 가능하다.


암호를 요구하는 프로그램은 보통 암호의 에코잉을 억제하므로 암호가 버퍼에 나타나지 않을 것이다. 버퍼가 char 모드에 있을 경우 실제 터미널을 사용하는 것처럼 이루어질 것이다. Line 모드에 있다면 암호가 일시적으로 표시되지만 사용자가 리턴을 누르면 삭제될 것이다. (이는 자동으로 발생하므로 특수 암호 처리는 이루어지지 않는다.)


다른 머신으로 로그인하면 원격 로긴 명령어를 위한 환경에서
TERM
환경 변수를 설정하여 당신이 사용 중인 터미널 타입을 명시해야 한다. (bash를 사용 중이라면 구분하는 콤마를 사용하지 않고 원격 로긴 명령어 앞에 변수 할당을 써야 한다.) 터미널 타입 'ansi' 또는 'vt100'이라면 대부분의 시스템에서 작동할 것이다.


직렬 터미널(Serial Terminal)

컴퓨터의 직렬 포트로 연결된 장치를 갖고 있다면 M-x serial-term 을 입력하여 연결할 수 있다. 이 명령어는 직렬 포트 이름과 속도를 요구하고, 새로운 Term 모드 버퍼로 전환한다. Emacs 는 일반 Term 모드에서 터미널과 통신하든 이 버퍼를 통해 직렬 장치와 통신한다.


직렬 포트의 속도는 초당 비트로 측정된다. 가장 자주 사용되는 속도는 초당 9600 비트이다. 모드 라인을 클릭하면 속도를 변경할 수 있다.


직렬 포트는 모드 라인에서 "8N1" 을 클릭하면 더 많은 설정이 가능하다. 기본적으로 직렬 포트는 "8N1" 로 설정되는데, 바이트마다 8 데이터 비트, parity check bit 없음, 1 stopbit 로 구성됨을 의미한다.


속도나 설정이 올바르지 않을 경우 장치와 통신할 수 없고 창에는 쓰레기(garbage) 출력만 나타날 것이다.


Emacs를 서버로 사용하기(Using Emacs as a Server)

다양한 프로그램들이 사용자가 원하는 에디터를 호출하여 특정 텍스트 조각을 편집할 수 있다. 예를 들어 버전 관리 프로그램들은 버전 관리 로그(version control log)로 들어가기 위해 에디터를 호출하고 (281 페이지의 25.1절 [버전 관리(Version Control)] 참고) Unix 의
mail
유틸리티는 전송할 메시지를 입력하기 위해 에디터를 호출한다. 관습상 사용자가 선택하는 에디터는
EDITOR
라는 환경 변수에 의해 명시된다.
EDITOR
를 '
emacs
' 로 설정하면 Emacs가 호출되겠지만 새로운 Emacs 프로세스를 시작하여 호출되므로 불편한 방법이다. 새로운 Emacs 프로세스는 버퍼, 명령어 히스토리, 또는 다른 유형의 정보를 기존 Emacs 프로세스와 공유하지 않기 때문에 불편하다.


Emacs 를 편집 서버(edit server)로 설정하면 외부 편집 요청을 "듣고" 그에 따라 동작하기 때문에 이러한 문제를 해결할 수 있다. Emacs 서버를 시작하는 방법에는 두 가지가 있다:


  • 기존 Emacs 프로세스에서
    server-start
    명령어를 실행하라: M-x server-start 를 입력하거나 표현식 (
    server-start
    ) 를 init 파일에 넣어라(437 페이지의 33.4절 [Init 파일(Init File)] 참고). 기존 Emacs 프로세스는 서버이며, Emacs 를 종료하면 서버가 Emacs 프로세스와 함께 죽는다(die).
  • '
    --daemon
    ' 명령행 옵션을 이용해 Emacs 를 daemon 으로 실행하라. 관련 내용은 480 페이지의 C.2절 [초기 옵션(Initial Options)]을 참고한다. Emacs를 이러한 방식으로 사용하면 초기화 다음에 server-start를 호출하고, 초기 프레임을 여는 대신 호출하는 터미널로 제어(control)를 리턴한 후 편집 요청을 들으면서 background 에서 기다린다.


어떤 방법을 사용하든 Emacs 서버가 시작되면
emacsclient
라는 셸 명령어를 이용해 Emacs 프로세스로 연결하여 프로세스에게 파일을 열 것을 지시할 수 있다. 이제
EDITOR
환경 변수를 '
emacsclient
' 로 설정할 수 있으므로 외부 프로그램은 편집에 기존 Emacs 프로세스를 사용할 것이다.[3]


server-name
변수를 이용하면 동일한 머신에서 Emacs 서버마다 유일한 "서버명(server name)"을 부여함으로써 여러 서버를 실행할 수 있다. 예를 들어 M-x set-variable RET server-name RET foo RET 는 서버명을 '
foo
' 로 설정한다.
emacsclient
프로그램은 '
-s
' 옵션을 이용해 서버를 이름으로 명시한다(395 페이지의 31.5.2절 [emacsclient 옵션(emacsclient Options)] 참고).


서버를 유일한 서버명으로 정의하였다면
server-eval-at
함수를 이용해 다른 Emacs 인스턴스(instance)로부터 서버로 연결하여 서버상의 Lisp 표현식을 평가하는 것이 가능하다. 가령
(server-eval-at "foo" '(+1 2))
는 '
foo
' 서버에서
(+ 1 2)
표현식을 평가하여 3을 리턴한다. (그러한 이름으로 된 서버가 없을 경우 오류가 전송된다.) 현재는 개발자들에게 유용하게 사용되는 기능이다.


emacsclient 호출하기(Invoking emacsclient)

emacsclient
프로그램을 가장 간단하게 사용하는 방법은 file 이 파일명에 해당하는 '
emacsclient file
' 이라는 셸 명령어를 실행하는 것이다. 명령어를 사용하면 Emacs 서버로 연결하여 Emacs 프로세스에게 기존 프레임 (그래픽 프레임 또는 텍스트 터미널 시스템에 있는 프레임) 중 하나에 위치한 file 을 열 것을 알린다(162 페이지의 18장 [프레임(Frames)] 참고). 이제 편집을 시작할 프레임을 선택할 수 있다.


Emacs 서버가 없다면
emacsclient
프로그램은 오류 메시지와 함께 중단된다. Daemon 으로 Emacs 를 시작할 때를 비롯해 Emacs 프로세스에 기존 프레임이 없는 경우(393 페이지의 31.5절 [Emacs 서버(Emacs Server)] 참고), Emacs 는 사용자가
emacsclient
를 호출한 터미널에서 프레임을 연다.


'
-c
' 와 '
-t
' 옵션을 이용하면 그래픽 디스플레이 또는 텍스트 터미널에서
emacsclient
가 새 프레임을 강제로 열도록 만들 수도 있다. 395 페이지의 31.5.2절 [emacsclient 옵션(emacsclient Optiosn)] 참고).


단일 텍스트 터미널에서 실행 중인 경우
emacsclient
의 셸과 Emacs 서버를 전환하는 방법에 두 가지가 있다: (1) Emacs 서버와
emacsclient
를 다른 가상 터미널에서 실행하고,
emacsclient
를 호출한 후 Emacs 서버의 가상 터미널로 전환하는 방법, (2) Emacs 서버 내에서 Shell 모드 (384 페이지의 31.4.2절 [대화형 셸(Interactive Shell)] 참고) 또는 Term 모드(392 페이지의 31.4.9절 [Term 모드(Term Mode)] 참고)를 이용해
emacsclient
를 호출하는 방법으로,
emacsclient
는 Emacs에서 하위셸만 블록(block)하므로 여전히 사용자는 Emacs를 이용해 파일을 편집할 수 있다.


Emacs 서버에서 file 의 편집이 완료되면 그 버퍼에서 C-x # (
server-edit
) 을 입력한다. 이는 파일을 저장하고
emacsclient
프로그램으로 종료할 것을 알리는 메시지를 다시 전송한다.
EDITOR
를 사용하는 프로그램들은 다른 일을 시작하기 전에 "에디터(editor)"(이번 경우
emacsclient
)가 종료될 때까지 기다린다.


다중 파일명 인자를 이용해
emacsclient
를 호출하는 것도 가능한데, '
emacsclient file1 file2...
' 는 Emacs 서버에게 file1, file2 등을 열라고 말한다. Emacs 는 file1 을 여는 버퍼를 선택하고, 버퍼 목록의 하단에 다른 버퍼들을 묻는다(bury)(147 페이지의 16장 [버퍼(Buffers)] 참고).
emacsclient
프로그램은 명시된 파일이 모두 완료되어야 종료된다(예: 각 서버 버퍼에서 C-x # 을 입력하였을 때).


서버 버퍼를 이용해 완료할 경우 버퍼를 제거하기도(kill) 하는데, 서버가 버퍼를 생성하도록 요청받기 전에 Emacs 세션에 이미 존재하였던 버퍼는 제외된다. 하지만
server-kill-new-buffers
nil
로 설정할 경우 다른 기준이 적용되어, 파일명이
server-temp-file-regexp
정규 표현식에 일치하면 서버 버퍼를 이용해 완료 시 버퍼를 제거할 것이다. 이 기능은 특정 "임시" 파일을 구별하기 위해 만들어졌다.


C-x # 을 사용할 때마다 다양한 파일을 편집하기 위해 다른 보류(pending) 상태의 외부 요청을 검사하여 그 중에서 다음 파일이 선택된다. 원한다면 수동으로 서버 버퍼로 전환할 수 있으며, 이런 경우 C-x # 을 이용하지 않아도 된다. 하지만 C-x # 을 이용하면 사용자의 작업이 완료되었음을
emacsclient
에게 알릴 수 있다.


server-window
변수의 값을 창 또는 프레임으로 설정할 경우 C-x # 은 그 창이나 그 프레임에서 항상 다음 서버 버퍼를 표시한다.


emacsclient 옵션(emacsclient Options)

아래와 같이 일부 선택적 인자를
emacsclient
프로그램으로 전달할 수 있다:
emacsclient -c +12 filel +4:3 file2


'
+line
' 또는 '
+line: column
' 인자는 다음 인자에 대한 라인 번호 또는 라인과 열 번호를 명시한다. 이들은 Emacs 자체에서 명령행 인자처럼 행동한다. 관련 내용은 478 페이지의 C.1절 [행동 인자(Action Arguments)]를 참고한다.


그 외에
emacsclient
가 인식하는 선택적 인자들을 아래에 열거하겠다:


'
-a command
'
'
--alternate-editor=command
'
emacsclient
가 Emacs와 접촉을 실패할 경우 실행할 명령어를 명시한다. 스크립트에서
emacsclient
를 실행 시 유용하다.
한 가지 특별한 예외가 있는데, command 가 빈 문자열일 경우
emacsclient
는 daemon 모드에서 (
emacs --daemon
으로) Emacs를 시작한 후 연결을 다시 시도한다.
ALTERNATE_EDITOR
환경 변수는 '
-a
' 옵션과 동일한 효과를 가진다. 두 가지가 모두 존재하면 '
-a
' 옵션이 우선시된다.


'
-c
'
기존 Emacs 프레임을 사용하는 대신 새로운 그래픽 클라이언트 프레임(client frame)을 생성한다. 클라이언트 프레임에서 C-x C-c 의 특별한 동작은 아래를 참고하라. Emacs 가 새 그래픽 프레임을 생성할 수 없는 경우 (가령 X 서버로 연결하지 못하여) '
-t
' 옵션으로 제공한 것처럼 텍스트 터미널 클라이언트 프레임의 생성을 시도할 것이다.
MS-Windows 에서 하나의 Emacs 세션은 그래픽 터미널과 텍스트 터미널 모두에 프레임을 표시할 수 없고, 여러 개의 텍스트 터미널에도 표시할 수 없다. 따라서 Emacs 서버가 텍스트 터미널에서 실행되는 경우 '
-t
' 옵션처럼 '
-c
' 옵션이 서버의 현재 텍스트 터미널 시스템에 새 프레임을 생성한다. 505 페이지의 G.1절 [윈도우 시작(Windows Startup)]을 참고한다.
'
-c
' 옵션을 제공하면서 파일명 인자를 생략할 경우 새 프레임은
*scratch*
버퍼를 기본값으로 표시한다. 이러한 동작은
initial-buffer-choice
변수를 이용해 맞춤화한다(14 페이지의 3.1절 [Emacs 들어가기(Entering Emacs)] 참고).


'
-F alist
'
'
--frame-parameters=alist
'
새로 생성된 그래픽 프레임에 대해 매개변수를 설정한다(172 페이지의 18.11절 [프레임 매개변수(Frame Parameters)] 참고).


'
-d display
'
'
--display=display
'
X 디스플레이 display 에서 주어진 파일을 열도록 Emacs 에게 지시한다(하나 이상의 X 디스플레이를 이용할 수 있는 상황으로 가정하여).


'
-e
'
'
--eval
'
Emacs에게 어떤 파일을 여는 대신 일부 Emacs Lisp 코드를 평가하라고 알린다. 이 옵션이 주어지면
emacsclient
로 제공되는 인자는 열어야 하는 파일 목록이 아니라 평가해야 할 표현식 목록으로 해석된다.


'
-f server-file
'
'
--server-file=server-file
'
TCP 를 통해 Emacs 서버로 연결하기 위한 서버 파일(server file)을 명시한다.
Emacs 서버는 주로 연결을 듣는 데에 (listen for) "로컬 소켓(local socket)"이라는 운영체제 기능을 사용한다. Microsoft Windows와 같은 일부 운영체제에서는 로컬 소켓을 지원하지 않는데, 이런 경우 서버는 TCP 를 통해
emacsclient
와 통신한다.
TCP Emacs 서버를 시작하면 Emacs는 서버로 연결하기 위해
emacsclient
가 사용하게 될 TCP 정보를 포함하는 서버 파일(server file)을 생성한다.
server-auth-dir
변수는 서버 파일을 포함하는 디렉터리를 명시하는데, 기본값은
~/.emacs.d/server/
이다.
emacsclient
에게 구체적 서버 파일로 TCP 상의 서버로 연결할 것을 알리려면 '
-f
' 또는 '
--server-file
' 옵션을 사용하거나
EMACS_SERVER_FILE
환경 변수를 설정하라.


'
-n
'
'
--no-wait
'
emacsclient
가 모든 서버 버퍼가 완료될 때까지 기다리는 대신 즉시 종료되도록 한다. Emacs 내에서 서버 버퍼를 편집하는 데에 원하는 만큼 시간을 소요할 수 있으며, 그 안에서 C-x # 을 입력하여도 제거되지 않는다.


'
--parent-id id
'
XEmbed 프로토콜을 통해 id 라는 id 로 부모 X 창에서
emacsclient
프레임을 클라이언트 프레임으로 연다. 현재 이 옵션은 개발자들에게 유용하다.


'
-q
'
'
--quiet
'
emacsclient
가 Emacs를 기다리거나 원격 서버 소켓으로 연결하는 것에 관한 메시지를 표시하지 않도록 한다.


'
-s server-name
'
'
--socket-name=server-name
'
server-name
이라는 Emacs 서버로 연결한다. 서버명은 Emacs 서버에서
server-name
변수에 의해 주어진다. 이 옵션이 누락되면
emacsclient
는 검색된 첫 번째 서버로 연결한다. (이 옵션은 MS-Windows에선 지원하지 않는다.)


'
-t
'
'
tty
'
'
-nw
'
기존 Emacs 프레임을 이용하는 대신 현재 텍스트 터미널에 새 클라이언트 프레임을 생성한다. 이는 위에서 설명한 '
-c
' 옵션과 같이 행동하는데, 텍스트 터미널 프레임을 생성한다는 차이가 있다(175 페이지의 18.19절 [Non-Windows 터미널(Non-Windows Terminals)] 참고).
MS-Windows에서 Emacs 서버가 그래픽 디스플레이를 사용할 경우 '
-t
' 는 '
-c
' 와 마찬가지로 행동하지만 Emacs 서버가 텍스트 터미널에서 실행 중이라면 현재 텍스트 터미널에 새 프레임을 생성한다.


'
-c
' 또는 '
-t
' 에 의해 생성된 텍스트 터미널 프레임이나 새로운 그래픽 터미널 프레임은 클라이언트 프레임(client frame)으로 간주된다. 클라이언트 프레임으로부터 생성하는 새 프레임 역시 클라이언트 프레임으로 간주된다. 클라이언트 프레임에서 C-x C-c (
save-buffers-kill-terminal
)를 입력할 경우 이 명령어는 평소대로 Emacs 세션을 죽이지(kill) 않을 것이다(15 페이지의 3.2절 [끝내기(Exiting)] 참고). 대신 Emacs는 클라이언트 프레임을 삭제하고, 클라이언트 프레임의 emacsclient가 통제를 다시 얻기 위해 대기 중이라면 (예: '
-n
' 옵션을 제공하지 않은 경우) Emacs는 동일한 클라이언트의 다른 프레임을 모두 삭제하고 클라이언트의 모든 서버 버퍼에서 마치 C-x # 을 입력한 것처럼 버퍼를 완료된 것으로 마크한다. 클라이언트 프레임이 삭제되고 나서 남은 프레임이 없을 경우 Emacs 세션은 종료된다.


한 가지 예외가 있는데, Emacs가 daemon으로 시작되면 모든 프레임이 클라이언트 프레임으로 간주되고 C-x C-c 를 사용 시 Emacs를 절대 죽이지(kill) 않을 것이다. Daemon 세션을 죽이려면 M-x kill-emacs 를 입력하라.


'
-t
' 와 '
-n
' 옵션은 상반됨을 주목한다. '
-t
' 는 새로운 클라이언트 프레임을 생성하기 위해 현재 텍스트 터미널 시스템을 제어하라고 알리는 반면 '
-n
' 은 텍스트 터미널 시스템을 제어하지 말라고 말한다. 두 옵션을 모두 제공하면 Emacs 는 '
-t
' 의 효과를 무효화하여 새로운 클라이언트 프레임이 아니라 기존 프레임에서 명시된 파일을 연다.


하드 카피 출력하기(Printing Hard Copies)

Emacs는 전체 버퍼 또는 버퍼의 일부에 대한 하드카피를 인쇄하는 명령어들을 제공한다. 인쇄 명령어를 아래와 같이 직접 호출하거나, 메뉴 바의 '
File
' 메뉴를 이용하는 방법이 있다.


이번 절에 설명된 명령어 외에도 Dired (320 페이지의 27.7절 [파일에 작업하기(Operating on Files] 참고) 또는 다이어리에서 (341 페이지의 28.10.1절 [다이어리 표시하기(Displaying the Diary)] 참고) 하드카피를 인쇄할 수도 있다. 현재 버퍼를 HTML 파일로 변환하여 Emacs 겉모습을 CSS 기반의 마크업(markup)으로 대체하는 M-x htmlfontify-buffer 명령어를 이용해 Emacs 버퍼를 HTML로 "출력"할 수도 있다. 나아가 Org 모드는 PDF 와 같은 다양한 포맷으로 Org 파일을 "출력"하도록 해준다(222 페이지의 22.9절 [Org 모드(Org Mode)] 참고).


M-x print-buffer
파일명과 페이지 번호를 포함한 쪽머리(page heading)와 함께 현재 버퍼의 하드카피를 출력한다.


M-x lpr-buffer
쪽머리 없이 현재 버퍼의 하드카피를 출력한다.


M-x print-region
print-buffer
와 같으나 현재 영역만 출력한다.


M-x lpr-region
lpr-buffer
와 같으나 현재 영역만 출력한다.


대부분 운영체제에서 위의 하드카피 명령어들은
lpr
프로그램을 호출함으로써 출력할 파일을 제출한다. 인쇄 프로그램을 변경하려면
lpr-command
변수를 맞춤화하라. 프린터 프로그램에 제공할 추가 스위치를 명시하려면
lpr-switches
라는 리스트 변수를 맞춤화하라. 그 값은 옵션 문자열로 된 목록이어야 하고, 각 문자열은 '
-
' 로 시작해야 한다(옵션 문자열 "
-w80
" 은 80개 열로 된 라인 너비를 명시한다). 기본값은 빈 목록인
nil
이다.


사용할 프린터를 명시하려면
printer-name
변수를 설정한다. 기본값은
nil
로, 기본 프린터를 명시한다. 이것을 프린터 이름(문자열)으로 설정하면 '
-P
' 스위치와 함께
lpr
로 이름이 전달되며,
lpr
을 사용하지 않으면
lpr-printer-switch
로 스위치를 명시해야 한다.


lpr-headers-switches
변수는 쪽머리를 만드는 데에 사용할 추가 스위치를 비슷한 방식으로 명시한다.
lpr-add-switches
변수는 프린터 프로그램에 (
lpr
에 적합한) '
-T
' 와 '
-J
' 옵션을 제공할 것인지 제어하며,
nil
은 추가하지 않음을 의미한다(프린터 프로그램이
lpr
과 호환되지 않을 경우
nil
을 값으로 해야 한다).


PostScript 하드카피(PostScript Hardcopy)

아래의 명령어들은 버퍼 내용을 PostScript 로 변환하여 출력하거나 다른 Emacs 버퍼에 남겨둔다.


M-x ps-print-buffer
현재 버퍼의 하드카피를 PostScript 형태로 출력한다.


M-x ps-print-region
현재 영역의 하드카피를 PostScript 형태로 출력한다.


M-x ps-print-buffer-with-faces
현재 버퍼의 하드카피를 PostScript 형태로 출력하고, 텍스트에 사용된 겉모습을 PostScript 기능을 이용해 표시한다.


M-x ps-print-region-with-faces
현재 영역의 하드카피를 PostScript 형태로 출력하고, 텍스트에 사용된 겉모습을 표시한다.


M-x ps-spool-buffer
현재 버퍼 텍스트에 대한 PostScript 이미지를 생성 및 스풀링(spool)한다.


M-x ps-spool-region
현재 영역에 대한 PostScript 이미지를 생성 및 스풀링(spool)한다.


M-x ps-spool-buffer-with-faces
현재 버퍼에 대한 PostScript 이미지를 생성 및 스풀링(spool)하고, 사용된 겉모습을 표시한다.


M-x ps-spool-region-with-faces
현재 영역에 대한 PostScript 이미지를 생성 및 스풀링(spool)하고, 사용된 겉모습을 표시한다.


M-x ps-despool
스풀링된 PostScript를 프린터로 전송한다.


M-x handwrite
현재 버퍼에 대한 PostScript를 손으로 작성한 것처럼 생성하고 출력한다.


ps-print-buffer
ps-print-region
명령어는 버퍼 내용을 PostScript 형태로 출력한다. 한 명령어는 전체 버퍼를 출력하고, 나머지는 영역만 출력한다.
ps-print-buffer-with-faces
ps-print-region-with-faces
명령어는 비슷하게 행동하지만 버퍼 텍스트의 겉모습(폰트와 색상)을 표시하는 데에 PostScript 기능을 사용한다.


대화형으로 접두 인자 (C-u) 를 사용하면 명령어는 사용자에게 파일명을 입력하고도 요구하고, PostScript 이미지를 프린터로 전송하는 대신 그 파일로 저장한다.


'
print
' 가 아니라 '
spool
' 이 이름에 포함된 명령어는 PostScript 출력값을 프린터로 전송하는 대신 Emacs 버퍼에서 생성한다.


스풀링된 이미지를 프린터로 전송하려면
ps-despool
명령어를 사용하라. 이 명령어는 '
-spool-
' 명령어가 생성한 PostScript 를 프린터로 전송한다(아래 명령어 참고). 접두 인자 (C-u) 를 이용하면 사용자에게 파일명을 입력하도록 요청한 후 스풀링된 PostScript 이미지를 프린터로 전송하는 대신 해당 파일에 저장한다.


M-x handwrite 는 좀 더 간단하다. 이는 현재 버퍼의 PostScript rendition 을 필기체로 쓴 문서로 생성한다. 이는
handwrite
그룹에서 맞춤화할 수 있다. 이 함수는 ISO 8859-1 문자만 지원한다.


PostScript 하드카피에 사용하는 변수(Variables for PostScript Hardcopy)

모든 PostScsript 하드카피 명령어는
ps-lpr-command
ps-lpr-switches
변수를 이용하여 출력값을 출력하는 방법을 명시한다.
ps-lpr-command
는 실행할 명령어 이름을 명시하고,
ps-lpr-switches
는 사용할 명령행 옵션,
ps-print-name
은 프린터를 명시한다. 앞의 두 변수를 직접 설정하지 않으면
lpr-command
lpr-switches
의 초기값을 취한다.
ps-printer-name
nil
값을 가진 경우
printer-name
이 사용된다.


ps-print-header
변수는 이러한 명령어들이 각 페이지에 헤더 라인을 추가하는지를 제어하는데, 헤더를 끄려면
nil
로 설정하라.


사용자의 프린터가 색상을 지원하지 않으면
ps-print-color-p
nil
로 설정하여 색상 처리를 꺼야 한다. 기본적으로 디스플레이가 색상을 지원할 경우 Emacs 는 색상 정보와 함께 하드웨어 출력을 생성하는데, 흑백 프린터에서는 색상이 회색 음영으로 에뮬레이트된다. 이로 인해 화면 색상이 회색 음영만 사용하더라도 읽기 어려운 출력을 생성할 수도 있다.


아니면 흑/백 프린터에 색상을 출력하기 위해
ps-print-color-p
black-white
로 설정할 수도 있다.


기본적으로 PostScript 출력는
ps-use-face-background
변수가
nil
값인 경우 겉모습의 배경색을 무시한다. 이는 zebra stripes 와 배경 이미지/텍스트의 원치 않는 간섭을 피하기 위함이다.


ps-paper-type
변수는 포맷팅할 용지 크기를 명시하는데, 유효 값으로는
a4
,
a3
,
a4small
,
b4
,
b5
,
executive
,
ledger
,
legal
,
letter
,
letter-small
,
statement
,
tabloid
가 있고, 기본값은
letter
이다.
ps-page-dimensions-database
변수를 변경하면 용지 크기를 추가로 정의할 수 있다.


ps-landscape-mode
변수는 페이지에 출력할 방향을 명시한다. 기본값은
nil
로, "세로(portrait)" 모드를 의미한다.
nil
을 제외한 값은 모두 "가로(landscape)" 모드를 명시한다.


ps-number-of-columns
변수는 열수를 명시하는데, 가로와 세로 모드에서 모두 적용된다. 기본값은 1이다.


ps-font-family
는 일반 텍스트를 출력 시 사용할 폰트계열(font family)을 명시한다. 유효한 값으로는
Courier
,
Helvetica
,
NewCenturySchlbk
,
Palatino
,
Times
가 있다.
ps-font-size
변수는 일반 텍스트에 대한 폰트 크기를 명시한다. 8.5 포인트를 기본값으로 한다.


Emacs 는 일반 PostScript 프린터보다 많은 스크립트와 문자를 지원한다. 따라서 버퍼 내 일부 문자는 프린터에 빌드된 폰트를 이용해 출력하지 못할 수도 있다. GNU IntlFonts 패키지에서 제공하는 폰트를 프린터에서 제공하는 폰트와 함께 사용하거나 Emacs 가 IntlFonts 만 사용하도록 지시할 수 있다.
ps-multibyte-buffer
변수가 이를 제어하는데, ASCII 와 Latin-1 문자를 출력하는 데에 적절한
nil
을 기본값으로 하며,
non-latin-printer
값은 프린터에 빌드된 ASCII, Latin-1, 일본어 한국어 문자 폰트를 가진 프린터에 적합하다.
bdf-font
값은 Intlfonts 패키지의 BDF 폰트를 모든 문자에 사용하도록 해준다. 마지막으로
bdf-font-except-latin
값은 프린트가 ASCII 와 Latin-1 문자에는 빌트인 폰트를 사용하고, 나머지 문자에는 Intlfonts BDF 폰트를 사용하도록 지시한다.


BDF 폰트를 사용할 수 있으려면 Emacs 는 어디서 폰트를 찾아야 하는지 알아야 한다.
bdf-directory-list
변수는 Emacs 가 폰트를 검색해야 할 디렉터리의 목록을 보유하는데, 기본값은 하나의 디렉터리
/usr/local/share/emacs/fonts/bdf
를 포함한다.


그 외에도 이러한 명령어에 사용할 수 있는 다른 많은 맞춤화 가능한 변수가
ps-print.el
ps-mule.el
이라는 Lisp 파일에 정의 및 설명되어 있다.


출력 패키지(Printing Package)

하드카피를 출력하는 기본 Emacs 기능은 Printing 패키지를 이용해 확장 가능하다. 이는 무엇을 출력할 것인지 선택하고, 출력 전에 PostScript 파일의 미리보기를 지원하며, 출력 헤더, 가로 또는 세로 모드, duplex 모드 등 다양한 출력 옵션을 설정하는 간편한 인터페이스를 제공한다. GNU/Linux 또는 Unix 시스템에서 Printing 패키지는
gs
gv
유틸리티에 의존하는데, 이는 GhostScript 프로그램의 일부로 배포된다. MS-Windows 에서는 Ghostscript 의
gstools
부분을 사용할 수 있다.


Printing 패키지를 사용하기 위해서는 init 파일에
(require 'printing)
을 추가하고 (437 페이지의 33.4절 [Init 파일(Init File)] 참고.) 뒤에
(pr-update-menus)
를 붙인다. 이 함수는 메뉴 바의 일반 출력 명령어를 다양한 출력 옵션이 포함된 'Printing' 하위메뉴로 대체한다. M-x pr-interface RET 를 입력할 경우 맞춤화 버퍼와 비슷한
*Printing Interface*
버퍼를 생성하여 출력 옵션을 설정할 수 있다. 무엇을 어떻게 출력할 것인지 선택하고 나면 'Print' 버튼을 이용해 출력 작업을 시작한다(버튼에서 Mouse-2 를 클릭하거나 포인트를 버튼 위로 이동시켜 RET 를 입력한다). 다양한 옵션에 대한 추가 정보는 '
Interface Help
' 버튼을 사용한다.


텍스트 정렬하기(Sorting Text)

Emacs는 버퍼에 텍스트를 정렬하는 명령어를 몇 가지 제공한다. 모든 명령어는 영역의 내용에 적용된다. 또한 영역의 텍스트를 정렬 레코드(sort records)로 나누고, 각 레코드마다 정렬 키(sort key)를 식별한 후 정렬 키로 결정되는 순서대로 레코드를 재정렬한다. 레코드는 그 키가 알파벳 순이 되도록 정렬되거나, 숫자 정렬의 경우 번호 순서대로 정렬되도록 한다. 알파벳 정렬의 경우 ASCII 문자 시퀀스에 따라 대문자 '
A
' 부터 '
Z
' 까지 먼저 온 후 소문자 '
a
' 가 따른다.


다양한 정렬 명령어들은 텍스트를 정렬 레코드로 분배하는 방식과 각 레코드의 어떤 부분이 정렬 키로 사용되는지에 차이가 있다. 대부분의 명령어는 각 라인을 구분된 정렬 레코드로 만들지만 일부 명령어들은 문단이나 페이지를 정렬 레코드로 사용한다. 정렬 명령어 대부분은 전체 정렬 레코드 각각을 고유의 정렬 키로 사용하지만 일부 명령어는 레코드의 부분만 정렬 키로 사용한다.


M-x sort-lines
영역을 라인으로 나누고 라인의 전체 텍스트를 비교하여 정렬한다. 수치적 인자는 내림순으로 정렬함을 의미한다.


M-x sort-paragraphs
영역을 문단으로 나누고 문단 전체 텍스트를 비교하여 정렬한다(빈 길잡이 선(leading line)은 제외). 수치적 인자는 내림순으로 정렬함을 의미한다.


M-x sort-pages
영역을 페이지로 나누고 페이지의 전체 텍스트를 비교하여 정렬한다(빈 길잡이 선은 제외). 수치적 인자는 내림순으로 정렬함을 의미한다.


M-x sort-fields
영역을 라인으로 나누고 각 라인에서 하나의 필드 내용을 비교하여 정렬한다. 필드는 공백으로 구분되도록 정의되므로 라인에서 연속된 비공백 문자를 처음으로 실행하면 필드 1 을 구성하고, 두 번째로 실행하면 필드 2 를 구성하는 식으로 나아간다.
정렬해야 할 필드는 수치적 인자를 이용해 명시하므로 1은 필드 1에 따라 정렬하는 식이다. 음의 인자는 왼쪽부터가 아니라 오른쪽부터 필드를 세라는 의미이므로 -1은 마지막 필드에 따라 정렬함을 의미한다. 여러 라인이 정렬되는 필드에 동일한 값을 갖고 있다면 원래 버퍼와 동일한 상대적 순서를 유지한다.


M-x sort-numeric-fields
명시된 필드가 각 라인에 대한 정수로 변환되고 숫자를 비교한다는 점만 제외하면 M-x sort-fields 와 같다. '
10
' 은 텍스트로 간주할 때는 '
2
' 앞에 오지만 숫자로 간주하면 '2' 뒤에 온다. 기본적으로 숫자는
sort-numeric-base
에 따라 해석되지만 '
0x
' 또는 '
0
' 으로 시작하는 숫자는 각각 16진수와 8진수로 해석된다.


M-x sort-columns
각 라인 내에서 비교에 사용되는 텍스트가 고정된 열 범위에서 비롯된다는 점을 제외하면 M-x sort-fields 와 같다. 설명은 아래를 참고한다.


M-x reverse-region
영역 내 라인의 순서를 반전시킨다. 필드나 열의 내림순으로 정렬할 때 유용한데, 그러한 정렬 명령어들은 이러한 기능을 갖고 있지 않기 때문이다.


가령 버퍼가 아래의 내용을 포함할 경우:

On systems where clash detection (locking of files being edited) is 
implemented, Emacs also checks the first time you modify a buffer 
whether the file has changed on disk since it was last visited or 
saved. If it has, you are asked to confirm that you want to change
the buffer.


M-x sort-lines 를 전체 버퍼로 적용하면 아래를 생성한다:

On systems where clash detection (locking of files being edited) is 
implemented, Emacs also checks the first time you modify a buffer 
saved. If it has, you are asked to confirm that you want to change 
the buffer.
whether the file has changed on disk since it was last visited or


여기서 대문자 '
O
' 는 모든 소문자 앞에서 정렬된다. C-u 2 M-x sort-fields 를 대신 사용하면 아래의 결과를 얻는다:
implemented, Emacs also checks the first time you modify a buffer 
saved. If it has, you are asked to confirm that you want to change 
the buffer.
On systems where clash detection (locking of files being edited) is 
whether the file has changed on disk since it was last visited or


여기서 정렬 키는 '
Emacs
', '
If
', '
buffer
', '
systems
', '
the
' 에 해당한다.


M-x sort-columns 는 더 많은 설명을 요한다. 사용자는 열들 중 하나에 포인트를 놓고 다른 열에 마크를 위치시킴으로써 열을 명시한다. 이는 정렬하고자 하는 텍스트의 첫 라인 시작에 마크나 포인트를 놓지 못함을 의미하므로 이 명령어는 포인트가 위치한 라인과 마크가 위치한 라인, 그 사이에 위치한 라인 모두 영역으로 간주된다는 독특한 "영역(region)"의 정의를 사용한다.


예를 들어 10번 열부터 15번 열까지 발견된 정보에 따라 테이블을 정렬하기 위해서는 마크를 테이블 첫 라인에서 10번 열에 위치시키고 포인트를 테이블 마지막 라인의 15번 열에 위치시킨 후
sort-columns
를 실행한다. 마찬가지로 첫 라인의 15번 열에 마크를 위치시키고 마지막 라인의 10번 열에 포인트를 위치시켜 실행할 수도 있다.


이것은 포인트와 마크로 명시된 직사각형을 정렬하는 작업으로 생각할 수도 있는데 단, 각 라인에서 직사각형 좌측이나 우측으로 텍스트가 직사각형 내 텍스트와 함께 이동한다는 점은 다르다. 60 페이지의 9.5절 [직사각형 영역(Rectangles)]을 참고한다.


정렬 명령어 대다수는
sort-fold-case
nil
값이 아닌 경우 비교할때 대, 소문자 차이를 무시한다.


이진 파일 편집하기(Editing Binary Files)

이진 파일의 편집에 사용할 수 있는 Hexl 모드라는 특수 주 모드가 있다. 이를 사용하려면 파일을 열 때 C-x C-f 대신 M-x hexl-find-file 을 사용하라. 이 명령어는 파일의 내용을 16진으로 변환하고 해석을 편집하도록 해준다. 사용자가 파일을 저장하면 자동으로 이진으로 변환한다.


기존 버퍼를 16진(hex)으로 해석하는 데에 M-x hexl-mode 를 사용할 수도 있다. 이는 일반적으로 파일을 방문하였는데 이진 파일임을 깨달았을 때 유용하다.


일반 텍스트 문자는 Hexl 모드에서 겹쳐쓴다(overwrite). 이는 파일 내 실수로 데이터의 줄맞춤을 망치는 위험을 줄이기 위함이다. 삽입에 사용할 특수 명령어도 있다. Hexl 모드의 명령어 목록을 아래에 소개하겠다:


C-M-d
10진으로 입력한 코드와 함께 바이트를 삽입한다.


C-M-o
8진으로 입력한 코드와 함께 바이트를 삽입한다.


C-M-x
16진으로 입력한 코드와 함께 바이트를 입력한다.


C-x [
1k-byte "페이지"의 시작으로 이동한다.


C-x ]
1k-byte "페이지"의 끝으로 이동한다.


M-g
16진으로 명시된 주소로 이동한다.


M-j
10진으로 명시된 주소로 이동한다.


C-c C-c
Hexl 모드를 끄고 사용자가
hexl-mode
를 호출하기 전에 이 버퍼의 주 모드로 돌아간다.


그 외 Hexl 명령어들은 이진 바이트의 문자열(시퀀스)을 삽입하고
short
또는
int
별로 이동하도록 해준다. 상세한 내용은 C-h a hexl-RET 를 입력한다.


Emacs 세션 저장하기(Saving Emacs Sessions)

Emacs의 세션에서 다른 세션으로 상태를 저장하려면 데스크톱 라이브러리를 사용하라. Emacs 데스크톱(버퍼, 파일명, 주 모드, 버퍼 위치 등)을 저장하고 나면 이후 Emacs 세션에서는 저장된 데스크톱을 재로딩한다. 기본적으로 데스크톱은 프레임과 창 설정까지 저장을 시도한다. 이 기능을 끄려면
desktop-restore-frames
nil
로 설정하라. (이 행위의 세부적으로 맞춤화할 수 있는 관련 옵션은 이 변수의 문서를 참고한다.)


M-x desktop-save 명령어를 이용하면 데스크톱을 수동으로 저장할 수 있다. Emacs 를 종료할 때 데스크톱의 자동 저장을 실행하고 Emacs 가 시작하면 마지막으로 저장된 데스크톱의 자동 복구를 실행하는 기능은 (412 페이지의 33.1절 [쉬운 맞춤화(Easy Customization)] 참고) 향후 세션을 위해
desktop-save-mode
t
로 설정하거나 아래의 라인을 init 파일로 추가하면 된다(437 페이지의 33.4절 [Init 파일(Init File)] 참고).
(desktop-save-mode 1)


desktop-save-mode
가 활성화되어 있고 데스크톱 파일이 존재할 경우, Emacs 는
desktop-auto-save-timeout
초마다 파일을 자동 저장하는데, 단
nil
값도 아니고 0 값도 아닐 경우에 한한다.


init 파일에서
desktop-save-mode
를 켜고 Emacs 가 시작되면 현재 디렉터리에서 저장된 데스크톱을 검색한다. (좀 더 정확히 말하자면
desktop-path
에서 명시한 디렉터리를 살펴보고 처음으로 찾는 데스크톱을 사용한다.) 따라서 다른 디렉터리에 구분되어 저장된 데스크톱을 가질 수 있으며, 시작하는 디렉터리는 Emacs 가 어떤 것을 재로딩할 것인지 결정한다. M-x desktop-change-dir 을 입력함으로써 현재 데스크톱을 저장하고 다른 디렉터리에 저장된 것을 재로딩할 수도 있다. M-x desktop-revert 는 이전에 재로딩한 데스크톱으로 되돌린다(revert).


저장된 데스크톱을 재로딩하는 것을 원하지 않는 경우 명령행에 '
--no-desktop
' 옵션을 명시하라. 그러면 현재 세션에서
desktop-save-mode
를 끈다. '
--no-init-file
' 옵션으로 Emacs 를 시작하여도
desktop-save-mode
가 주로 켜져 있는 init 파일은 우회하기(bypass) 때문에 데스크톱 재로딩을 끄게 된다.


기본적으로 데스크톱의 모든 버퍼는 한 번에 보관된다. 하지만 데스크톱에 버퍼 수가 많을 경우 속도가 느릴 수도 있다.
desktop-restore-eager
변수를 이용하면 즉시 복구할 최대 버퍼수를 명시할 수 있으며, 나머지 버퍼는 Emacs가 idle 상태일 때 "느리게(lazily)" 복구된다.


M-x desktop-clear 를 입력하면 Emacs 데스크톱을 비운다(empty). 이는 내부 버퍼를 제외한 모든 버퍼를 죽이고(kill),
desktop-globals-to-clear
에 열거된 전역 변수를 삭제한다(clear). 특정 버퍼는 유지하고 싶다면 제거하지 않을 버퍼명에 일치하는 정규 표현식을 값으로 가지는
desktop-clear-preserve-buffers-regexp
변수를 맞춤화하라.


어떤 세션에서 다른 세션으로 미니버퍼 히스토리를 저장하고 싶다면
savehist
라이브러리를 사용하라.


재귀적 편집 수준(Recursive Editing Levels)

재귀적 편집(recursive edit)이란 Emacs 명령어 중간에 임의의 편집을 실행하기 위해 다른 Emacs 명령어를 사용하는 상황을 가리킨다. 가령
query-replace
안에서 C-r 을 입력하면 현재 버퍼를 변경할 수 있는 재귀적 편집에 들어가게 된다. 재귀적 편집에서 나오면
query-replace
로 되돌아간다. 105 페이지의 12.10.4절 [쿼리 대체(Query Replace)]를 참고한다.


재귀적 편집을 끝내는 것(exiting)은 완료되지 않은 명령어로 되돌아가 실행을 계속함을 의미한다. 종료 명령어는 C-M-c (
exit-recursive-edit
)다.


재귀적 편집을 취소(abort)할 수도 있다. 취소는 끝내기와 비슷하지만 완료되지 않은 명령어를 즉시 중단한다. 이를 위해서는 C-] (
abort-recursive-edit
) 명령어를 사용하라. 443 페이지의 34.1절 [끝내기(Quitting)]를 참고한다.


모드 라인은 항상 주 모드명과 부 모드명을 둘러싼 괄호 주변에 사각 괄호를 표시함으로써 재귀적 편집에 있을 때를 보여준다. 모든 창의 모드 라인은 이러한 방식으로 표시하는데, 재귀적 편집에 있는 것은 Emacs를 특정 창이나 버퍼가 아니라 전체에 적용되기 때문이다.


재귀적 편집 안에서 다시 재귀적 편집에 들어가는 것도 가능하다. 가령
query-replace
에서 C-r 을 입력하고 나면 디버거로 들어가는 명령어를 입력할 수가 있다. 이는 C-r 에 대한 재귀적 편집 수준 내에서 디버거에 대한 재귀적 편집 수준을 시작한다. 모드 라인은 진행 중인 재귀적 편집 수준마다 한 쌍의 사각 괄호를 표시한다.


(디버거 c 명령어와 같은) 안쪽의 재귀적 편집을 종료하면 다음으로 높은(up) 수준에서 실행 중인 명령어를 재개한다. 그리고 이 명령어가 완료되면 C-M-c 를 이용해 또 다른 재귀적 편집 수준을 종료할 수 있으며 계속 이런 식으로 나아간다. 종료는 가장 안쪽 수준에만 적용된다. 취소를 이용하여도 하나의 재귀적 편집 수준만 벗어나며, 이전 재귀적 편집의 명령어 수준으로 즉시 돌아간다. 그리고 나서 원한다면 다음 재귀적 편집 수준을 취소할 수도 있다.


아니면 M-x top-level 명령어를 이용해 모든 수준의 재귀적 편집을 취소하고 최상위 수준 명령어 리더(reader)로 즉시 돌아갈 수도 있다. 미니버퍼가 활성화되어 있다면 그 역시 종료할 것이다.


재귀적 편집 내부에서 편집되는 텍스트가 최상위 수준에서 편집 중이던 텍스트와 동일할 필요는 없다. 이는 재귀적 편집의 목적에 따라 좌우된다. 재귀적 편집을 호출하는 명령어가 다른 버퍼를 먼저 선택하면 이것이 바로 사용자가 재귀적으로 편집하게 될 버퍼이다. 어떤 경우든 재귀적 편집 내부에서 일반적인 방식으로 버퍼를 전환할 수 있다(버퍼 전환 키를 재바인딩하지 않는 이상). 나머지 편집과 파일 열기 등은 재귀적 편집 안에서 실행할 수 있을 것이다. 그렇지만 가끔은 놀라운 효과를 야기하기도 한다(스택 오버플로우와 같은). 따라서 재귀적 편집이 더 이상 필요하지 않으면 종료하거나 취소할 것을 명심한다.


일반적으로 우리는 GNU Emacs 에서 재귀적 편집 수준의 사용을 최소화하려고 한다. 그 이유는 재귀적 수준이 특정 순서로, 즉 가장 안쪽 수준부터 최상위 수준으로 "되돌아가도록" 제약하기 때문이다. 가능하면 다른 활동은 구분된 버퍼에서 표현하도록 하여 사용자가 원할 때마다 전환할 수 있도록 한다. 일부 명령어는 다시 전환(switch back)하기 위한 명령어를 제공하는 새로운 주 모드로 전환하기도 한다. 이러한 접근법들은 완료하지 않은 작업에 사용자가 원하는 순서대로 돌아갈 수 있는 유연성을 제공한다.


하이퍼링크 및 탐색 기능(Hyperlinking and Navigation Features)

다음 하위절에서는 Emacs 버퍼 텍스트에서 발생하는 URLs를 비롯해 다른 유형의 링크를 처리하기 위한 편의 기능을 설명하고자 한다.

URLs 따라가기(Following URLs)

M-x browse-url RET url RET
URL을 웹 브라우저(Web browser)에 로딩한다.


Browse-URL 패키지는 Emacs 내부에서 URLs를 쉽게 따라가도록 해준다. 대부분의 URLs은 웹 브라우저를 호출하여 따라가는데, '
mailto:
' URLs 는 명시된 주소로 메일을 전송하도록 Emacs 명령어
compose-mail
을 호출하면 따라갈 수 있다(350 페이지의 29장 [메일 전송하기(Sending Mail)] 참고).


M-x browse-url 명령어는 URL 의 입력을 요청한 후 따라간다. 포인트가 실행 가능한 URL 근처에 위치할 경우 해당 URL 이 기본값으로 제시된다. Browse-URL 패키지는
browse-url-at-point
browse-url-at-mouse
처럼 키에 바인딩하고 싶어할만한 다른 명령어들도 제공한다.


browse-url
Customize 그룹의 다양한 옵션을 통해 Browse-URL 의 행위를 맞춤화할 수 있다. 특히
browse-url-mailto-function
옵션은 '
mailto:
' URLs 를 어떻게 따를 것인지 정의하도록 해주는 반면
browse-url-browser-function
은 다른 유형의 URLs를 따르는 방법을 정의하도록 해준다. 추가 정보는 C-h P browse-url RET 를 입력하여 표시되는 패키지 설명을 참고한다.


URLs 활성화하기(Activating URLs)

M-x goto-address-mode
현재 버퍼에서 URLs와 이메일 주소를 활성화한다.


M-x goto-address-mode 를 입력하면 Emacs가 URLs를 현재 버퍼에서 특별하게 표시하도록 만들 수 있다. 해당 버퍼 로컬 부 모드를 켜면 버퍼에서 모든 URLs 를 찾아 강조한 후 클릭 가능한 버튼으로 만든다. 포인트가 그 텍스트에 있을 때 C-c RET (
goto-address-at-point
) 를 입력하거나 Mouse-2 또는 Mouse-1 을 재빠르게 클릭하면 URL을 따라갈 수 있다(164 페이지의 18.3절 [마우스 참조(Mouse References)] 참고). URL 따라가기는
browse-url
을 하위루틴으로서 호출하면 가능하다(405 페이지의 31.11.1절 [Browse-URL] 참고).


모드 훅 그리고 들어오는 메시지를 표시하는 훅에
goto-address-mode
를 추가하는 것도 유용하다(예: Rmail 의 경우
rmail-show-message-hook
, MH-E 의 경우
mh-show-mode-hook
). Gnus 는 비슷한 기능을 갖고 있으므로 추가할 필요가 없다.


포인트에서 파일과 URLs 찾기(Finding Files and URLs at Point)

FFAP 패키지는 C-x C-f 처럼 파일을 찾기 위한 특정 키 바인딩을 좀 더 민감한 기본값을 제공하는 명령어로 대체한다. 이러한 명령어에 접두 인자가 주어지면 일반 명령어처럼 행동한다. 접두 인자를 제공하지 않으면 포인트 주변의 텍스트로부터 URL 또는 기본 파일명을 얻는다. 버퍼에서 발견되는 내용이 파일명 대신 URL 형태를 가진 경우 명령어는
browse-url
을 이용해 그것을 확인한다(405 페이지의 31.11.1절 [Browse-URL] 참고).


이 기능은 메일이나 뉴스 버퍼,
README
파일,
MANIFEST
파일 등에서 참조를 따라갈 때 유용하다. 상세한 정보는 C-h P ffap RET 를 입력하면 나타나는 패키지 해설을 참고한다.


FFAT 를 켜기 위해서는 M-x ffap-bindings 를 입력한다. 이는 다음과 같은 키 바인딩을 만들고, Rmail, Gnus, VM 아티클 버퍼에 추가 FFAP 기능을 위한 훅을 설치한다.


C-x C-f filename RET
filename 을 찾고 포인트 주변의 텍스트에서 기본값을 짐작한다(
find-file-at-point
).


C-x C-r
ffap-read-only
로,
find-file-read-only
와 유사하다.


C-x C-v
ffap-alternate-file
로,
find-alternate-file
과 유사하다.


C-x d directory RET
directory 에서 Dired를 시작하고 포인트에 위치한 디렉터리명을 기본값으로 한다(
dired-at-point
).


C-x C-d
ffap-list-directory
로,
list-directory
와 유사하다.


C-x 4 f
ffap-other-window
로,
find-file-other-window
와 유사하다.


C-x 4 r
ffap-read-only-other-window
로,
find-file-read-only-other-window
와 유사하다.


C-x 4 d
ffap-dired-other-window
로,
dired-other-window
와 같다.


C-x 5 f
ffap-other-frame
으로,
find-file-other-frame
과 유사하다.


C-x 5 r
ffap-read-only-other-frame
으로,
find-file-read-only-other-frame
과 유사하다.


C-x 5 d
ffap-dired-other-frame
으로,
dired-other-frame
과 유사하다.


M-x ffap-next
다음 파일명이나 URL에 해당하는 버퍼를 검색한 후 해당 파일 또는 URL 을 찾는다.


S-Mouse-3
ffap-at-mouse
는 마우스 클릭 위치 주변의 텍스트에서 짐작한 파일을 검색한다.


C-S-Mouse-3
현재 버퍼에 언급된 파일 및 URLs 의 메뉴를 표시한 후 사용자가 선택한 것을 찾는다(
ffap-menu
).


다른 흥미로운 기능(Other Amusements)

animate
패키지는 텍스트를 춤추게 만든다(예: M-x animate-birthday-present).


M-x blackbox, M-x mpuz, M-x 5x5 는 퍼즐이다.
blackbox
는 박스 안의 물체 위치를 단층 촬영(tomography)을 통해 확인하도록 해준다.
mpuz
는 사용자가 짐작해야 하는 코드 내 숫자를 의미하는 글자와 함께 곱셈 퍼즐을 표시하는데, 값을 짐작하기 위해서는 글자를 입력한 후 그것이 의미한다고 생각하는 숫자를 입력해야 한다.
5x5
의 목표는 모든 사각형을 채우는 데에 있다.


M-x bubbles 는 최소한의 이동으로 물체가 가능한 한 많은 거품을 제거하는 게임이다.


M-x decipher 는 단일자 치환법 암호로 암호화된 암호를 해독하도록 도와준다.


M-x dissociated-press 는 현재 Emacs 버퍼 내 텍스트를 단어별 또는 문자별로 움직여서 결과물을
*Dissociation*
이란 버퍼로 쓴다. 양의 인자는 문자별로 실행하도록 알리고, 중복된 (overlap) 문자의 개수를 명시한다. 음의 인자는 단어별로 실행하도록 알리고, 중복된(overlap) 단어의 개수를 명시한다. Dissociated Press는 Markov chain의 것과 꽤 유사한 결과를 생성하지만 독립적이고 독창적인 발명품으로, 각 단어나 문자 뒤로 무작위 점프하는 Markov chain과 달리 무작위 점프 사이에 표본 텍스트로부터 몇 개의 연속 문자를 복사한다. userenced 하고 properbose 하게 원한다면 문서에서 dissociwords 하게 유지하라.


M-x dunnet 는 텍스트 기반의 모험 게임을 실행한다.


좀 더 개인적 몰입을 원한다면 당신과 Go Moku 게임을 상대하는 M-x gomoku 를 실행하라.


조금 더 지루하다면 M-x hanoi 를 시도해도 좋다. 더 지루해지면 수치적 인자를 제공하라. 참을 수 없을만큼 지루해지면 인자 9를 제공하라. 그리고 앉아서 어떤 일이 일어나는지 확인하라.


M-x life 는 Conway의 "Life" cellular 자동화를 실행한다.


M-x landmark 는 네 가지 방향에서 오는 유일한 후각적 신호를 바탕으로 로봇이 창 중간에 나무를 향해 전진하는, 상대적으로 비참여적인 게임을 실행한다.


M-x morse-region 은 영역 내 텍스트를 Morse 모드로 변환하고, M-x unmorse-region 은 이를 원래대로 다시 변환한다. M-x nato-region 은 영역 내 텍스트를 NATO 음성 문자로 변환하고 M-x denato-region 은 다시 원래대로 변환한다.


M-x pong, M-x snake, M-x tetris 는 유명한 Pong, Snake, Tetris 게임의 구현이다.


M-x solitaire 는 pegs를 다른 pegs 위로 점프시키는 카드 게임(solitaire)을 실행한다.


M-x zone 명령어는 Emacs가 idle 상태일 때 디스플레이로 게임을 한다.


마지막으로 당혹스러움을 느낀다면 자신의 문제를 그 유명한 심리치료사 Eliza 에게 털어놓아라. M-x doctor 명령어를 실행하기만 하면 된다. 입력을 마칠 때마다 RET 를 두 번 입력하면 된다.


Notes

  1. PostScript 파일의 경우 GhostScript는 까다로운 요구조건이다. DVI 파일의 경우
    dvipdf
    또는
    dvipdfm
    이 필요하다. OpenDocument와 Microsoft Office 문서의 경우 unoconv 툴이 필요하다.
  2. 문서 타입에 필요한 외부 툴을 이용할 수 있어야 하고, Emacs는 그래픽 프레임에서 실행되어 PNG 이미지를 지원받아야 한다. 이러한 요구조건이 충족되지 않으면 Emacs는 다른 주 모드로 빠진다.
  3. 3.0 3.1 셸 프로세스를 지연시켜선 안 된다. 셸의 하위작업을 지연시키는 것은 일반적인 실습으로 완전히 다른 문제이며, 하위작업을 계속하려면 셸을 사용해야 하는데 이 명령어는 그러지 않을 것이다. Cite error: Invalid <ref> tag; name ".EC.A3.BC.EC.84.9D31-4" defined multiple times with different content