*** empty log message ***
[bpt/emacs.git] / leim / quail / uni-input.el
CommitLineData
7115232b
DL
1;;; uni-input.el --- Hex Unicode input method
2
3;; Copyright (C) 2001 Free Software Foundation, Inc.
4
5;; Author: Dave Love <fx@gnu.org>
6;; Keywords: i18n
7
8;; This file is free software; you can redistribute it and/or modify
9;; it under the terms of the GNU General Public License as published by
10;; the Free Software Foundation; either version 2, or (at your option)
11;; any later version.
12
13;; This file is distributed in the hope that it will be useful,
14;; but WITHOUT ANY WARRANTY; without even the implied warranty of
15;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16;; GNU General Public License for more details.
17
18;; You should have received a copy of the GNU General Public License
19;; along with GNU Emacs; see the file COPYING. If not, write to
20;; the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
21;; Boston, MA 02111-1307, USA.
22
23;;; Commentary:
24
25;; Provides an input method for entering characters by hex unicode in
26;; the form `uxxxx', similarly to the Yudit editor.
27
28;; This is not really a Quail method, but uses some Quail functions.
29;; There is probably A Better Way.
30
31;; Compare `ucs-insert', which explicitly inserts a unicoded character
32;; rather than supplying an input method.
33
34;;; Code:
35
36(require 'quail)
37
38;; Maybe stolen from Mule-UCS -- I don't remember.
39(define-ccl-program utf-8-ccl-encode
40 `(4 (if (r0 < ?\x80)
41 ((write r0))
42 (if (r0 < #x800)
43 ((write ((r0 >> 6) | ?\xC0))
44 (write ((r0 & ?\x3F) | ?\x80)))
45 (if (r0 < #x10000)
46 ((write ((r0 >> 12) | ?\xE0))
47 (write (((r0 >> 6) & ?\x3F) | ?\x80))
48 (write ((r0 & ?\x3F) | ?\x80)))
49 (if (r0 < #x200000)
50 ((write ((r0 >> 18) | ?\xF0))
51 (write (((r0 >> 12) & ?\3F) | ?\x80))
52 (write (((r0 >> 6) & ?\x3F) | ?\x80))
53 (write ((r0 & ?\x3F) | ?\x80)))
54 (if (r0 < #x4000000)
55 ((write ((r0 >> 24) | ?\xF8))
56 (write (((r0 >> 18) & ?\x3F) | ?\x80))
57 (write (((r0 >> 12) & ?\x3F) | ?\x80))
58 (write (((r0 >> 6) & ?\x3F) | ?\x80))
59 (write ((r0 & ?\x3f) | ?\x80)))
60 ((write ((r0 >> 30) | ?\xFC))
61 (write (((r0 >> 24) & ?\x3F) | ?\x80))
62 (write (((r0 >> 18) & ?\x3F) | ?\x80))
63 (write (((r0 >> 12) & ?\x3F) | ?\x80))
64 (write (((r0 >> 6) & ?\x3F) | ?\x80))
65 (write ((r0 & ?\x3f) | ?\x80))))))))))
66
67(defun ucs-input-method (key)
68 (if (or buffer-read-only
69 (and (/= key ?U) (/= key ?u)))
70 (list key)
71 (quail-setup-overlays nil)
72 (let ((current-prefix-arg)
73 (last-command-char key))
74 (call-interactively 'self-insert-command))
75 (let ((modified-p (buffer-modified-p))
76 (buffer-undo-list t)
77 (input-method-function nil)
78 (echo-keystrokes 0)
79 (help-char nil)
80 (events (list key))
81 (str " "))
82 (unwind-protect
83 (catch 'non-digit
84 (progn
85 (dotimes (i 4)
86 (let ((seq (read-key-sequence nil))
87 key)
88 (if (and (stringp seq)
89 (= 1 (length seq))
90 (setq key (aref seq 0))
91 (memq key '(?0 ?1 ?2 ?3 ?4 ?5 ?6 ?7 ?8 ?9 ?a
92 ?b ?c ?d ?e ?f ?A ?B ?C ?D ?E ?F)))
93 (progn
94 (push key events)
95 (let ((last-command-char key)
96 (current-prefix-arg))
97 (call-interactively 'self-insert-command)))
98 (let ((last-command-char key)
99 (current-prefix-arg))
100 (condition-case nil
101 (call-interactively (key-binding seq))))
102 (quail-delete-region)
103 (throw 'non-digit (append (reverse events)
104 (listify-key-sequence seq))))))
105 (quail-delete-region)
106 (let* ((n (string-to-number (apply 'string
107 (cdr (nreverse events)))
108 16))
109 (c (decode-char 'ucs n))
110 (status (make-vector 9 nil)))
111 (if c
112 (list c)
113 (aset status 0 n)
114 (string-to-list (ccl-execute-on-string
115 'utf-8-ccl-encode status ""))))))
116 (quail-delete-overlays)
117 (set-buffer-modified-p modified-p)
118 (run-hooks 'input-method-after-insert-chunk-hook)))))
119
120(defun ucs-input-activate (&optional arg)
121 "Activate UCS input method.
122With arg, activate UCS input method if and only if arg is positive.
123
124While this input method is active, the variable
125`input-method-function' is bound to the function `ucs-input-method'."
126 (if (and arg
127 (< (prefix-numeric-value arg) 0))
128 (unwind-protect
129 (progn
130 (quail-hide-guidance-buf)
131 (quail-delete-overlays)
132 (setq describe-current-input-method-function nil))
133 (kill-local-variable 'input-method-function))
134 (setq inactivate-current-input-method-function 'ucs-input-inactivate)
135 (setq describe-current-input-method-function 'ucs-input-help)
136 (quail-delete-overlays)
137 (if (eq (selected-window) (minibuffer-window))
138 (add-hook 'minibuffer-exit-hook 'quail-exit-from-minibuffer))
139 (add-hook 'kill-buffer-hook 'quail-kill-guidance-buf nil t)
140 (set (make-local-variable 'input-method-function)
141 'ucs-input-method)))
142
143(defun ucs-input-inactivate ()
144 "Inactivate UCS input method."
145 (interactive)
146 (ucs-input-activate -1))
147
148(defun ucs-input-help ()
149 (interactive)
150 (with-output-to-temp-buffer "*Help*"
151 (princ "\
152Input method: ucs (mode line indicator:U)
153
154Input as Unicode: U<hex> or u<hex>, where <hex> is a four-digit hex number.")))
155
156(register-input-method "ucs" "UTF-8" 'ucs-input-activate "U+"
157 "Unicode input as hex in the form Uxxxx.")
158
159(provide 'uni-input)
160
161;;; uni-input.el ends here