Odpowiedzi:
Wypróbuj tę funkcję z .emacs Steve'a Yegge :
;; źródło: http://steve.yegge.googlepages.com/my-dot-emacs-file (unikaj zmiany nazwy pliku i bufora (nowa nazwa) „Zmienia nazwę zarówno bieżącego bufora, jak i pliku, który odwiedza na NEW-NAME”. (interaktywny „sNew name:”) (let ((nazwa (nazwa bufora)) (nazwa pliku (nazwa-pliku-bufora))) (jeśli (nie nazwa pliku) (nazwa „Bufor '% s' nie odwiedza pliku!”) (if (get-buffer new-name) (komunikat „Bufor o nazwie„% s ”już istnieje!” new-name) (progn (zmień nazwę pliku nazwa_pliku nowa-nazwa 1) (rename-buffer new-name) (set-visit-file-name new-name) (set-buffer-zmodyfikowany-p zero))))))
Spójrz na tę stronę, jest tam jeszcze jedna bardzo przydatna pokrewna funkcja, zwana „plikiem bufora ruchu”.
(set-buffer-modified-p nil)
wydaje się niepotrzebne. Jeśli wywołałeś rename-file-and-buffer
zmodyfikowany bufor, a następnie próbowałeś go zabić, chętnie zrobiłby to bez ostrzeżenia o niezapisanych zmianach.
Tak, w dired
trybie możesz:
C-x d
otworzyć diredRET
aby wybrać katalog bieżącego plikuC-x C-j
( dired-jump
do nazwy bieżącego pliku, w Dired)R
zmienić nazwę pliku (lub dired-do-rename
).q
wrócić do bufora pliku (o zmienionej nazwie)Zmiana nazwy jest równoważna powłoce mv
, ale zaktualizuje również wszystkie otwarte bufory i, w przeciwieństwie do mv
tego, nie zmieni czasu dostępu ani modyfikacji pliku w systemie plików.
C-x C-j
jest to dla mnie domyślnie związane. Robienie tego M-x load-library RET dired-x RET
najpierw wiąże.
C-x C-j
jest niezwiązana, jest po prostu M-x dired-jump
za pierwszym razem. Zostanie automatycznie załadowany dired-x
(co również spowoduje, C-x C-j
że zostanie zdefiniowane od tego momentu).
Dla kompletności, ponieważ niektórzy ludzie mogą odwiedzić tę stronę, myśląc, że otrzymają odpowiedź na funkcję „zapisz jako” Emacsa, to Cx Cw dla otwartego pliku.
File > Save as...
Moim ulubionym jest ten z Magnars (sławnych screencastów z Emacsa Rocka ).
W przeciwieństwie do innych alternatyw, nie musisz wpisywać nazwy od zera - musisz zmienić obecną nazwę.
(defun rename-current-buffer-file ()
"Renames current buffer and file it is visiting."
(interactive)
(let* ((name (buffer-name))
(filename (buffer-file-name))
(basename (file-name-nondirectory filename)))
(if (not (and filename (file-exists-p filename)))
(error "Buffer '%s' is not visiting a file!" name)
(let ((new-name (read-file-name "New name: " (file-name-directory filename) basename nil basename)))
(if (get-buffer new-name)
(error "A buffer named '%s' already exists!" new-name)
(rename-file filename new-name 1)
(rename-buffer new-name)
(set-visited-file-name new-name)
(set-buffer-modified-p nil)
(message "File '%s' successfully renamed to '%s'"
name (file-name-nondirectory new-name)))))))
Dzięki Jamesowi Yangowi za poprawną wersję.
Oto bardziej solidna wersja zaadaptowana ze Steveya.
;; Originally from stevey, adapted to support moving to a new directory.
(defun rename-file-and-buffer (new-name)
"Renames both current buffer and file it's visiting to NEW-NAME."
(interactive
(progn
(if (not (buffer-file-name))
(error "Buffer '%s' is not visiting a file!" (buffer-name)))
;; Disable ido auto merge since it too frequently jumps back to the original
;; file name if you pause while typing. Reenable with C-z C-z in the prompt.
(let ((ido-auto-merge-work-directories-length -1))
(list (read-file-name (format "Rename %s to: " (file-name-nondirectory
(buffer-file-name))))))))
(if (equal new-name "")
(error "Aborted rename"))
(setq new-name (if (file-directory-p new-name)
(expand-file-name (file-name-nondirectory
(buffer-file-name))
new-name)
(expand-file-name new-name)))
;; Only rename if the file was saved before. Update the
;; buffer name and visited file in all cases.
(if (file-exists-p (buffer-file-name))
(rename-file (buffer-file-name) new-name 1))
(let ((was-modified (buffer-modified-p)))
;; This also renames the buffer, and works with uniquify
(set-visited-file-name new-name)
(if was-modified
(save-buffer)
;; Clear buffer-modified flag caused by set-visited-file-name
(set-buffer-modified-p nil)))
(setq default-directory (file-name-directory new-name))
(message "Renamed to %s." new-name))
Oto kolejna wersja, która jest dość solidna i świadoma VC:
(defun rename-file-and-buffer ()
"Rename the current buffer and file it is visiting."
(interactive)
(let ((filename (buffer-file-name)))
(if (not (and filename (file-exists-p filename)))
(message "Buffer is not visiting a file!")
(let ((new-name (read-file-name "New name: " filename)))
(cond
((vc-backend filename) (vc-rename-file filename new-name))
(t
(rename-file filename new-name t)
(set-visited-file-name new-name t t)))))))
Możesz przeczytać więcej na ten temat tutaj .
Jeśli korzystasz z Spacemacs , otrzymasz takie zachowanie za darmo, ponieważ ma ono implementację rename-current-buffer-file
(opartą na magnarach), która domyślnie jest z nią związana SPC-f-R
.
Jest bardzo prosty sposób, naciśnij komendę Mx i wpisz vc-rename-file , po czym musisz tylko wybrać swój aktualny plik w katalogu, a następnie wybrać nową nazwę. Buff, który ma zmieniony plik zostanie odświeżony.
Źródło: https://www.gnu.org/software/emacs/manual/html_node/emacs/VC-Delete_002fRename.html
w oparciu o wersję magnars, zmodyfikowałem jak poniżej, naprawiłem część nazwy pliku INIT:
(defun rename-current-buffer-file ()
"Renames current buffer and file it is visiting."
(interactive)
(let* ((name (buffer-name))
(filename (buffer-file-name))
(basename (file-name-nondirectory filename)))
(if (not (and filename (file-exists-p filename)))
(error "Buffer '%s' is not visiting a file!" name)
(let ((new-name (read-file-name "New name: " (file-name-directory filename) basename nil basename)))
(if (get-buffer new-name)
(error "A buffer named '%s' already exists!" new-name)
(rename-file filename new-name 1)
(rename-buffer new-name)
(set-visited-file-name new-name)
(set-buffer-modified-p nil)
(message "File '%s' successfully renamed to '%s'"
name (file-name-nondirectory new-name)))))))
Można to osiągnąć przez kopiowanie. Shift + C na pliku, a emacs poprosi cię o wskazanie nazwy ścieżki, w tym nazwy pliku, więc po prostu podaj nową nazwę i wpisz ... oczywiście, musisz usunąć poprzednią.
(setq uniquify-buffer-name-style 'forward)
znaczeniem, jeśli masz bufor o nazwieusers\index.html
(ponieważ masz już inny buforposts\index.html
), zmiana nazwy nie powiedzie się