Update (Oct 12 2015)
Below calc-yank
implementation is now added to emacs trunk.
It will be available in the next stable emacs release.
I reviewed the original definition of calc-yank
and the good thing is that it does not have any argument. So I added my own argument, radix
, and slightly modified how the let-bound var thing
is derived.
By default, the below modified function will work the exact same as the original calc-yank
.
But if you want to yank the value in the kill ring as a hexadecimal number, you will be able to now do so now by doing C-u 6 C-y
or C-6 C-y
or M-6 C-y
.
To test it, copy 1000
to the kill-ring.
Then,
C-2 C-y
will paste 8
(2#1000
),
C-8 C-y
will paste 512
(8#1000
),
C-0 C-y
will paste 1000
(10#1000
),
C-6 C-y
will paste 4096
(16#1000
)
.. and C-y
will paste 1000
(1000
).
(defun calc-yank (radix)
"Yank a value into the Calculator buffer.
Valid numeric prefixes for RADIX: 0, 2, 6, 8
No radix notation is prepended for any other numeric prefix.
If RADIX is 2, prepend "2#" - Binary.
If RADIX is 8, prepend "8#" - Octal.
If RADIX is 0, prepend "10#" - Decimal.
If RADIX is 6, prepend "16#" - Hexadecimal.
If RADIX is a non-nil list (created using \[universal-argument]), the user
will be prompted to enter the radix in the minibuffer.
If RADIX is nil or if the yanked string already has a calc radix prefix, the
yanked string will be passed on directly to the Calculator buffer without any
alteration."
(interactive "P")
(calc-wrapper
(calc-pop-push-record-list
0 "yank"
(let* (radix-num
radix-notation
valid-num-regexp
(thing-raw
(if (fboundp 'current-kill)
(current-kill 0 t)
(car kill-ring-yank-pointer)))
(thing
(if (or (null radix)
;; Match examples: -2#10, 10\n(10#10,01)
(string-match-p "^[-(][0-9]\{1,2\}#" thing-raw))
thing-raw
(progn
(if (listp radix)
(progn
(setq radix-num
(read-number
"Set radix for yanked content (2-36): "))
(when (not (and (integerp radix-num)
(<= 2 radix-num)
(>= 36 radix-num)))
(error (concat "The radix has to be an "
"integer between 2 and 36."))))
(setq radix-num
(cond ((eq radix 2) 2)
((eq radix 8) 8)
((eq radix 0) 10)
((eq radix 6) 16)
(t (message
(concat "No radix prepended "
"for invalid numeric* "
"prefix %0d.")
radix)
nil))))
(if radix-num
(progn
(setq radix-notation
(concat (number-to-string radix-num) "#"))
(setq valid-num-regexp
(cond
;; radix 2 to 10
((and (<= 2 radix-num)
(>= 10 radix-num))
(concat "[0-"
(number-to-string (1- radix-num))
"]+"))
;; radix 11
((= 11 radix-num) "[0-9aA]+")
;; radix 12+
(t
(concat "[0-9"
"a-" (format "%c" (+ 86 radix-num))
"A-" (format "%c" (+ 54 radix-num))
"]+"))))
;; Ensure that the radix-notation is prefixed
;; correctly even for multi-line yanks like below,
;; 111
;; 1111
(replace-regexp-in-string
valid-num-regexp
(concat radix-notation "\&")
thing-raw))
thing-raw)))))
(if (eq (car-safe calc-last-kill) thing)
(cdr calc-last-kill)
(if (stringp thing)
(let ((val (math-read-exprs (calc-clean-newlines thing))))
(if (eq (car-safe val) 'error)
(progn
(setq val (math-read-exprs thing))
(if (eq (car-safe val) 'error)
(error "Bad format in yanked data")
val))
val))))))))
deadbeef
is a valid Calc identifier, i.e. it could just name a variable or a function, so it would be wrong to interpret it as a number. – wvxvw Jun 25 '15 at 21:4616#deadbeef
it doesn't interpret it as an identifier... Why does it do so when I yank the textdeadbeef
after typing16#
? – mgalgs Jun 25 '15 at 22:11