I’ve ben doing a decent amount of C and C++ coding recently - both for courses and for hacking on emacs. I ended up doing a bit of work on my C configuration, though probably not as much as I should.
Part of these efforts included improving h-file-create, the function that is automatically run whenever I create a new header file. Previously, it only created the #ifndef guards; While these are the only things I’ll always need, the vast majority of time I also wanted to define a class, and so I programmed the class to be inserted automatically.
(defun h-file-create () "Create a new h file. Insert a infdef/define/endif block" (interactive) (if (or (equal (substring (buffer-name (current-buffer)) -2 ) ".h") (equal (substring (buffer-name (current-buffer)) -4 ) ".hpp")) (let* ((buffer-name (buffer-name (current-buffer))) (class-name (substring buffer-name 0 (string-match "\\." buffer-name)))) (when (equal "" (buffer-string)) (insert "#ifndef " (upcase class-name) "_H\n#define " (upcase class-name) "_H\n\nclass " (capitalize class-name) " {\npublic:\n\n\nprivate:\n\n\n};" "\n\n#endif") (search-backward "public:\n") (next-line)))))
Another function I ended up needing was to insert includes to header files or forward declarations of classes. Previously, I’d have to go to the top of my file, interrupting whatever I was doing, and maneuver back. This was just an annoyance, so I wrote the following functions that would either include or forward declare something, defaulting to the current word at point. Since whether I #included or forward declared often depended on whether I was in a header or implementation file, so I wrote another function that delegates to one of the other two depending on which file you were in. String-match-any is a utility function I wrote to help do this.
(defun string-match-any (regexp-list string &optional start) "Returns whether the given string, starting at position start, matches any regexp in the list" (if regexp-list (let ((result (string-match (car regexp-list) string start))) (if result result (string-match-any (cdr regexp-list) string start))))) (defun-my c-include (interactive) (save-excursion (goto-char (point-min)) (if (search-forward "#include" nil t) (progn (beginning-of-line) (insert (concat "#include \"" (downcase arg) ".hpp\"\n"))) (search-forward "\n\n") (insert "#include \"" (downcase arg) ".hpp\"\n\n")))) (defun-my c-forward-declare (interactive) (save-excursion (goto-char (point-min)) (if (re-search-forward "class [a-zA-Z]*;" nil t) (insert (concat "\nclass " (capitalize arg) ";")) (search-forward "\n\n") (insert "class " (capitalize arg) ";\n\n")))) (defun-my c-fwdinclude (interactive) (let ((buffer-name (buffer-name (current-buffer)))) (if (string-match-any (list "\.h" "\.hpp") buffer-name ) (c-forward-declare arg) (c-include arg)))) (define-key c-mode-base-map (kbd "C-c c f") 'my-c-fwdinclude)
I’ve also been using c-eldoc-mode more. It’s pretty awesome, but there is one problem with it: its speed. On a large project like emacs, it will frequently lock the input for some time. It’s useful enough that I’d for it to be faster. If there’s a later version that fixes this that you know of, please tell me; the latest I’ve found is v0.4. Otherwise, I’m going to look into it further to see if I can figure out how to speed it up some more.