1a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;;; Clang Code-Completion minor mode, for use with C/Objective-C/C++. 2a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 3a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;;; Commentary: 4a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 5a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; This minor mode uses Clang's command line interface for code 6a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; completion to provide code completion results for C, Objective-C, 7a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; and C++ source files. When enabled, Clang will provide 8a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; code-completion results in a secondary buffer based on the code 9a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; being typed. For example, after typing "struct " (triggered via the 10a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; space), Clang will provide the names of all structs visible from 11a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; the current scope. After typing "p->" (triggered via the ">"), 12a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Clang will provide the names of all of the members of whatever 13a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; class/struct/union "p" points to. Note that this minor mode isn't 14a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; meant for serious use: it is meant to help experiment with code 15a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; completion based on Clang. It needs your help to make it better! 16a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; 17a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; To use the Clang code completion mode, first make sure that the 18d240724926ca8bb06a1e0c2c19b33b51d7de484bDouglas Gregor;; "clang" variable below refers to the "clang" executable, 19a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; which is typically installed in libexec/. Then, place 20a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; clang-completion-mode.el somewhere in your Emacs load path. You can 21a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; add a new load path to Emacs by adding some like the following to 22a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; your .emacs: 23a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; 24a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; (setq load-path (cons "~/.emacs.d" load-path)) 25a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; 26a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Then, use 27a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; 28a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; M-x load-library 29a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; 30a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; to load the library in your Emacs session or add the following to 31a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; your .emacs to always load this mode (not recommended): 32a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; 33a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; (load-library "clang-completion-mode") 34a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; 35a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Finally, to try Clang-based code completion in a particular buffer, 36a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; use M-x clang-completion-mode. When "Clang-CC" shows up in the mode 37a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; line, Clang's code-completion is enabled. 38a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; 39a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Clang's code completion is based on parsing the complete source 40a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; file up to the point where the cursor is located. Therefore, Clang 41a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; needs all of the various compilation flags (include paths, dialect 42a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; options, etc.) to provide code-completion results. Currently, these 43d240724926ca8bb06a1e0c2c19b33b51d7de484bDouglas Gregor;; need to be placed into the clang-flags variable in a format 44d240724926ca8bb06a1e0c2c19b33b51d7de484bDouglas Gregor;; acceptable to clang. This is a hack: patches are welcome to 45a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; improve the interface between this Emacs mode and Clang! 46a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; 47a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 48a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;;; Code: 49d240724926ca8bb06a1e0c2c19b33b51d7de484bDouglas Gregor;;; The clang executable 50d240724926ca8bb06a1e0c2c19b33b51d7de484bDouglas Gregor(defcustom clang "clang" 51d240724926ca8bb06a1e0c2c19b33b51d7de484bDouglas Gregor "The location of the Clang compiler executable" 52a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor :type 'file 53a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor :group 'clang-completion-mode) 54a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 55d240724926ca8bb06a1e0c2c19b33b51d7de484bDouglas Gregor;;; Extra compilation flags to pass to clang. 56ed37836bbbf023c4b6015128b131e1238398c7dfDouglas Gregor(defcustom clang-flags nil 57a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor "Extra flags to pass to the Clang executable. 58a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas GregorThis variable will typically contain include paths, e.g., -I~/MyProject." 59ed37836bbbf023c4b6015128b131e1238398c7dfDouglas Gregor :type '(repeat (string :tag "Argument" "")) 60a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor :group 'clang-completion-mode) 61a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 62a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;;; The prefix header to use with Clang code completion. 63a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(setq clang-completion-prefix-header "") 64a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 65a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;;; The substring we will use to filter completion results 66a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(setq clang-completion-substring "") 67a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 68a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;;; The current completion buffer 69a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(setq clang-completion-buffer nil) 70a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 71d240724926ca8bb06a1e0c2c19b33b51d7de484bDouglas Gregor(setq clang-result-string "") 72a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 73a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;;; Compute the current line in the buffer 74a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(defun current-line () 75a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor "Return the vertical position of point..." 76a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (+ (count-lines (point-min) (point)) 77a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (if (= (current-column) 0) 1 0) 78a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor -1)) 79a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 80a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;;; Set the Clang prefix header 81a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(defun clang-prefix-header () 82a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (interactive) 83a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (setq clang-completion-prefix-header 84a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (read-string "Clang prefix header> " "" clang-completion-prefix-header 85a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor ""))) 86a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 87a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Process "filter" that keeps track of the code-completion results 88a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; produced. We store all of the results in a string, then the 89a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; sentinel processes the entire string at once. 90a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(defun clang-completion-stash-filter (proc string) 91d240724926ca8bb06a1e0c2c19b33b51d7de484bDouglas Gregor (setq clang-result-string (concat clang-result-string string))) 92a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 93a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Filter the given list based on a predicate. 94a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(defun filter (condp lst) 95a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (delq nil 96a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (mapcar (lambda (x) (and (funcall condp x) x)) lst))) 97a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 98a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Determine whether 99a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(defun is-completion-line (line) 100a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (or (string-match "OVERLOAD:" line) 101a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (string-match (concat "COMPLETION: " clang-completion-substring) line))) 102a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 103a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(defun clang-completion-display (buffer) 104d240724926ca8bb06a1e0c2c19b33b51d7de484bDouglas Gregor (let* ((all-lines (split-string clang-result-string "\n")) 105a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (completion-lines (filter 'is-completion-line all-lines))) 106a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (if (consp completion-lines) 107a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (progn 108a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor ;; Erase the process buffer 109a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (let ((cur (current-buffer))) 110a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (set-buffer buffer) 111a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (goto-char (point-min)) 112a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (erase-buffer) 113a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (set-buffer cur)) 114a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 115a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor ;; Display the process buffer 116a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (display-buffer buffer) 117a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 118a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor ;; Insert the code-completion string into the process buffer. 119a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (with-current-buffer buffer 120a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (insert (mapconcat 'identity completion-lines "\n"))) 121a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor )))) 122a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 123a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Process "sentinal" that, on successful code completion, replaces the 124a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; contents of the code-completion buffer with the new code-completion results 125a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; and ensures that the buffer is visible. 126a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(defun clang-completion-sentinel (proc event) 127d240724926ca8bb06a1e0c2c19b33b51d7de484bDouglas Gregor (let* ((all-lines (split-string clang-result-string "\n")) 128a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (completion-lines (filter 'is-completion-line all-lines))) 129a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (if (consp completion-lines) 130a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (progn 131a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor ;; Erase the process buffer 132a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (let ((cur (current-buffer))) 133a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (set-buffer (process-buffer proc)) 134a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (goto-char (point-min)) 135a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (erase-buffer) 136a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (set-buffer cur)) 137a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 138a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor ;; Display the process buffer 139a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (display-buffer (process-buffer proc)) 140a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 141a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor ;; Insert the code-completion string into the process buffer. 142a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (with-current-buffer (process-buffer proc) 143a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (insert (mapconcat 'identity completion-lines "\n"))) 144a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor )))) 145a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 146a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(defun clang-complete () 1477ae4373bde78acf912d7c33423fd2c33606ee851John McCall (let* ((cc-point (concat (buffer-file-name) 1487ae4373bde78acf912d7c33423fd2c33606ee851John McCall ":" 1497ae4373bde78acf912d7c33423fd2c33606ee851John McCall (number-to-string (+ 1 (current-line))) 1507ae4373bde78acf912d7c33423fd2c33606ee851John McCall ":" 1517ae4373bde78acf912d7c33423fd2c33606ee851John McCall (number-to-string (+ 1 (current-column))))) 1527ae4373bde78acf912d7c33423fd2c33606ee851John McCall (cc-pch (if (equal clang-completion-prefix-header "") nil 1537ae4373bde78acf912d7c33423fd2c33606ee851John McCall (list "-include-pch" 1547ae4373bde78acf912d7c33423fd2c33606ee851John McCall (concat clang-completion-prefix-header ".pch")))) 1557ae4373bde78acf912d7c33423fd2c33606ee851John McCall (cc-flags (if (listp clang-flags) clang-flags nil)) 1567ae4373bde78acf912d7c33423fd2c33606ee851John McCall (cc-command (append `(,clang "-cc1" "-fsyntax-only") 1577ae4373bde78acf912d7c33423fd2c33606ee851John McCall cc-flags 1587ae4373bde78acf912d7c33423fd2c33606ee851John McCall cc-pch 1597ae4373bde78acf912d7c33423fd2c33606ee851John McCall `("-code-completion-at" ,cc-point) 1607ae4373bde78acf912d7c33423fd2c33606ee851John McCall (list (buffer-file-name)))) 1617ae4373bde78acf912d7c33423fd2c33606ee851John McCall (cc-buffer-name (concat "*Clang Completion for " (buffer-name) "*"))) 162a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor ;; Start the code-completion process 163a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (if (buffer-file-name) 164a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (progn 165a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor ;; If there is already a code-completion process, kill it first. 166a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (let ((cc-proc (get-process "Clang Code-Completion"))) 167a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (if cc-proc 168a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (delete-process cc-proc))) 169a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 170a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (setq clang-completion-substring "") 171d240724926ca8bb06a1e0c2c19b33b51d7de484bDouglas Gregor (setq clang-result-string "") 172a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (setq clang-completion-buffer cc-buffer-name) 173a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 1747ae4373bde78acf912d7c33423fd2c33606ee851John McCall (let ((cc-proc (apply 'start-process 1757ae4373bde78acf912d7c33423fd2c33606ee851John McCall (append (list "Clang Code-Completion" cc-buffer-name) 1767ae4373bde78acf912d7c33423fd2c33606ee851John McCall cc-command)))) 177a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (set-process-filter cc-proc 'clang-completion-stash-filter) 178a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (set-process-sentinel cc-proc 'clang-completion-sentinel) 179a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor ))))) 180a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 181a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Code-completion when one of the trigger characters is typed into 182a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; the buffer, e.g., '(', ',' or '.'. 183a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(defun clang-complete-self-insert (arg) 184a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (interactive "p") 185a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (self-insert-command arg) 186a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (save-buffer) 187a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (clang-complete)) 188a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 189a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; When the user has typed a character that requires the filter to be 190a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; updated, do so (and update the display of results). 191a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(defun clang-update-filter () 192a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (setq clang-completion-substring (thing-at-point 'symbol)) 193a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (if (get-process "Clang Code-Completion") 194a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor () 195a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (clang-completion-display clang-completion-buffer) 196a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor )) 197a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 198a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Invoked when the user types an alphanumeric character or "_" to 199a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; update the filter for the currently-active code completion. 200a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(defun clang-filter-self-insert (arg) 201a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (interactive "p") 202a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (self-insert-command arg) 203a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (clang-update-filter) 204a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor ) 205a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 206a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Invoked when the user types the backspace key to update the filter 207a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; for the currently-active code completion. 208a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(defun clang-backspace () 209a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (interactive) 210a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (delete-backward-char 1) 211a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (clang-update-filter)) 212a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 213a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Invoked when the user types the delete key to update the filter 214a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; for the currently-active code completion. 215a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(defun clang-delete () 216a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (interactive) 217a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (delete-backward-char 1) 218a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (clang-update-filter)) 219a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 220a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Set up the keymap for the Clang minor mode. 221a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(defvar clang-completion-mode-map nil 222a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor "Keymap for Clang Completion Mode.") 223a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 224a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(if (null clang-completion-mode-map) 225a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (fset 'clang-completion-mode-map 226a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (setq clang-completion-mode-map (make-sparse-keymap)))) 227a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 228a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(if (not (assq 'clang-completion-mode minor-mode-map-alist)) 229a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (setq minor-mode-map-alist 230a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (cons (cons 'clang-completion-mode clang-completion-mode-map) 231a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor minor-mode-map-alist))) 232a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 233a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Punctuation characters trigger code completion. 234a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(dolist (char '("(" "," "." ">" ":" "=" ")" " ")) 235a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (define-key clang-completion-mode-map char 'clang-complete-self-insert)) 236a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 237a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Alphanumeric characters (and "_") filter the results of the 238a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; currently-active code completion. 239a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(dolist (char '("A" "B" "C" "D" "E" "F" "G" "H" "I" "J" "K" "L" "M" "N" "O" 240a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor "P" "Q" "R" "S" "T" "U" "V" "W" "X" "Y" "Z" 241a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor "a" "b" "c" "d" "e" "f" "g" "h" "i" "j" "k" "l" "m" "n" "o" 242a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor "p" "q" "r" "s" "t" "u" "v" "w" "x" "y" "z" 243a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor "_" "0" "1" "2" "3" "4" "5" "6" "7" "8" "9")) 244a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor (define-key clang-completion-mode-map char 'clang-filter-self-insert)) 245a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 246a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Delete and backspace filter the results of the currently-active 247a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; code completion. 248a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(define-key clang-completion-mode-map [(backspace)] 'clang-backspace) 249a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(define-key clang-completion-mode-map [(delete)] 'clang-delete) 250a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 251a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor;; Set up the Clang minor mode. 252a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor(define-minor-mode clang-completion-mode 253a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor "Clang code-completion mode" 254a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor nil 255d240724926ca8bb06a1e0c2c19b33b51d7de484bDouglas Gregor " Clang" 256a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor clang-completion-mode-map) 257a584fb353aa8496ace9cc2903e38c3c76bd127ebDouglas Gregor 258