From: Keith David Bershatsky <esq@lawlist.com>
To: Eli Zaretskii <eliz@gnu.org>
Cc: 22300@debbugs.gnu.org, John Wiegley <jwiegley@gmail.com>
Subject: bug#22300: 25.1.50; Dired -- renaming folders/files to CamelCase/UPPERCASE/lowercase.
Date: Mon, 04 Jan 2016 11:45:22 -0800 [thread overview]
Message-ID: <m2mvsluo19.wl%esq@lawlist.com> (raw)
In-Reply-To: <m2a8oml6tk.wl%esq@lawlist.com>
Thank you, John, for helping me answer Eli's question about situations when OSX uses case-insensitive versus case-sensitive. I didn't have the knowledge to be able to respond properly.
Here is an unsophisticated workaround that bypasses `dired-create-files' when dealing with renaming when (1) 'darwin; (2) just one file; and, (3) the file names of to/from are equal if both are lower-cased. It doesn't do the fancy cutting/pasting of the new line in dired-mode and instead just reverts the entire buffer.
(require 'dired-aux)
(require 'cl) ;; for `lexical-let*'
(defun dired-do-create-files (op-symbol file-creator operation arg
&optional marker-char op1
how-to)
"Create a new file for each marked file.
Prompt user for a target directory in which to create the new
files. The target may also be a non-directory file, if only
one file is marked. The initial suggestion for target is the
Dired buffer's current directory (or, if `dired-dwim-target' is
non-nil, the current directory of a neighboring Dired window).
OP-SYMBOL is the symbol for the operation. Function `dired-mark-pop-up'
will determine whether pop-ups are appropriate for this OP-SYMBOL.
FILE-CREATOR and OPERATION as in `dired-create-files'.
ARG as in `dired-get-marked-files'.
Optional arg MARKER-CHAR as in `dired-create-files'.
Optional arg OP1 is an alternate form for OPERATION if there is
only one file.
Optional arg HOW-TO determines how to treat the target.
If HOW-TO is nil, use `file-directory-p' to determine if the
target is a directory. If so, the marked file(s) are created
inside that directory. Otherwise, the target is a plain file;
an error is raised unless there is exactly one marked file.
If HOW-TO is t, target is always treated as a plain file.
Otherwise, HOW-TO should be a function of one argument, TARGET.
If its return value is nil, TARGET is regarded as a plain file.
If it return value is a list, TARGET is a generalized
directory (e.g. some sort of archive). The first element of
this list must be a function with at least four arguments:
operation - as OPERATION above.
rfn-list - list of the relative names for the marked files.
fn-list - list of the absolute names for the marked files.
target - the name of the target itself.
The rest of into-dir are optional arguments.
For any other return value, TARGET is treated as a directory."
(or op1 (setq op1 operation))
(let* ((fn-list (dired-get-marked-files nil arg))
(rfn-list (mapcar (function dired-make-relative) fn-list))
(dired-one-file ; fluid variable inside dired-create-files
(and (consp fn-list) (null (cdr fn-list)) (car fn-list)))
(target-dir (dired-dwim-target-directory))
(default (and dired-one-file
(expand-file-name (file-name-nondirectory (car fn-list))
target-dir)))
(defaults (dired-dwim-target-defaults fn-list target-dir))
(target (expand-file-name ; fluid variable inside dired-create-files
(minibuffer-with-setup-hook
(lambda ()
(set (make-local-variable 'minibuffer-default-add-function) nil)
(setq minibuffer-default defaults))
(dired-mark-read-file-name
(concat (if dired-one-file op1 operation) " %s to: ")
target-dir op-symbol arg rfn-list default))))
(into-dir (cond ((null how-to)
;; Allow DOS/Windows users to change the letter
;; case of a directory. If we don't test these
;; conditions up front, file-directory-p below
;; will return t because the filesystem is
;; case-insensitive, and Emacs will try to move
;; foo -> foo/foo, which fails.
(if (and (memq system-type '(ms-dos windows-nt cygwin))
(eq op-symbol 'move)
dired-one-file
(string= (downcase
(expand-file-name (car fn-list)))
(downcase
(expand-file-name target)))
(not (string=
(file-name-nondirectory (car fn-list))
(file-name-nondirectory target))))
nil
(file-directory-p target)))
((eq how-to t) nil)
(t (funcall how-to target)))))
(if (and (consp into-dir) (functionp (car into-dir)))
(apply (car into-dir) operation rfn-list fn-list target (cdr into-dir))
(if (not (or dired-one-file into-dir))
(error "Marked %s: target must be a directory: %s" operation target))
;; rename-file bombs when moving directories unless we do this:
(or into-dir (setq target (directory-file-name target)))
;;; BEGIN modification by @lawlist
(if
(and
(eq system-type 'darwin)
dired-one-file
(equal op1 "Rename")
(equal operation "Move")
(equal (downcase (expand-file-name dired-one-file)) (downcase (expand-file-name target))))
;; Penetrate the `set-process-sentinel' with `lexical-let'.
(lexical-let* ((dired-one-file dired-one-file)
(target target))
(set-process-sentinel
(start-process "rename" nil "mv" dired-one-file target)
(lambda (p e) (when (= 0 (process-exit-status p))
(revert-buffer)
(message "Renamed %s to %s" dired-one-file target)))))
(dired-create-files
file-creator operation fn-list
(if into-dir ; target is a directory
;; This function uses fluid variable target when called
;; inside dired-create-files:
(function
(lambda (from)
(expand-file-name (file-name-nondirectory from) target)))
(function (lambda (_from) target)))
marker-char))
;;; END modification by @lawlist
)))
next prev parent reply other threads:[~2016-01-04 19:45 UTC|newest]
Thread overview: 29+ messages / expand[flat|nested] mbox.gz Atom feed top
2016-01-03 20:57 bug#22300: 25.1.50; Dired -- renaming folders/files to CamelCase/UPPERCASE/lowercase Keith David Bershatsky
2016-01-03 21:10 ` John Wiegley
2016-01-04 0:47 ` Drew Adams
2016-01-04 1:11 ` John Wiegley
2016-01-04 1:37 ` Drew Adams
2016-01-04 15:46 ` Eli Zaretskii
2016-01-04 16:15 ` Drew Adams
2016-01-04 19:22 ` John Wiegley
2016-01-04 19:27 ` Drew Adams
2016-01-04 19:45 ` Eli Zaretskii
2016-01-04 19:44 ` Eli Zaretskii
2016-01-04 19:48 ` John Wiegley
2016-01-04 20:31 ` Eli Zaretskii
2016-01-04 15:44 ` Eli Zaretskii
2016-01-04 3:31 ` Eli Zaretskii
2016-01-04 4:19 ` Keith David Bershatsky
2016-01-04 15:50 ` Eli Zaretskii
2016-01-04 17:41 ` Keith David Bershatsky
2016-01-04 19:12 ` Eli Zaretskii
2016-01-04 19:45 ` Keith David Bershatsky [this message]
2016-01-04 20:24 ` Eli Zaretskii
2016-01-04 20:51 ` Keith David Bershatsky
2016-01-05 16:46 ` Eli Zaretskii
2016-01-05 17:27 ` Keith David Bershatsky
2016-01-05 18:28 ` Eli Zaretskii
2016-01-06 3:56 ` Keith David Bershatsky
2016-01-06 15:40 ` Eli Zaretskii
2016-01-06 19:57 ` Keith David Bershatsky
[not found] <<m2a8oml6tk.wl%esq@lawlist.com>
[not found] ` <<m24meutlmk.fsf@newartisans.com>
[not found] ` <<a936bee4-3375-45cf-ab35-62e36a21f003@default>
[not found] ` <<83vb7973iy.fsf@gnu.org>
2016-01-04 16:14 ` Drew Adams
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
List information: https://www.gnu.org/software/emacs/
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=m2mvsluo19.wl%esq@lawlist.com \
--to=esq@lawlist.com \
--cc=22300@debbugs.gnu.org \
--cc=eliz@gnu.org \
--cc=jwiegley@gmail.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
Code repositories for project(s) associated with this public inbox
https://git.savannah.gnu.org/cgit/emacs.git
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).