Skip to content

Instantly share code, notes, and snippets.

@abo-abo
Created November 7, 2013 21:55

Revisions

  1. abo-abo created this gist Nov 7, 2013.
    67 changes: 67 additions & 0 deletions calign.el
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,67 @@
    (defun extract-argument-positions (str)
    "Given a single line C/C++ string, return list of arguments in form:
    \(start-position end-position string\) for each argument"
    (let ((args (list))
    (pos 0))
    (while (string-match "\\(?: [^ (\n]+\\)\\(?:,[\n ]\\|)\\|,$\\|;$\\|[ ]+=[ ]+\\)" str pos)
    (push (list (match-beginning 0)
    (match-end 0)
    (substring (match-string-no-properties 0 str) 0 -1))
    args)
    (setq pos (match-end 0)))
    (reverse args)))

    (defun selected-lines ()
    "Returns list of pairs (beginning-of-line-position . string)
    for each line selected"
    (interactive)
    (when (region-active-p)
    (let ((start (save-excursion (goto-char (region-beginning))
    (line-beginning-position)))
    (end (save-excursion (goto-char (region-end)) (line-end-position)))
    (lines nil)
    tstr)
    (goto-char start)
    (while (< (point) end)
    (setq tstr (buffer-substring-no-properties
    (point)
    (line-end-position)))
    (unless (string= tstr "")
    (push (cons (point) tstr)
    lines))
    (beginning-of-line 2))
    lines)))

    (defun c-align-function-arguments ()
    "Aligns selected C/C++ arguments list with spaces"
    (interactive)
    (let ((lines (selected-lines)))
    (when (> (length lines) 1)
    (let* ((pts-begin (mapcar #'car lines))
    (pts-arg-rel (mapcar (lambda (x)
    (caar
    (extract-argument-positions
    (cdr x))))
    lines))
    (pt-arg-max (apply #'max pts-arg-rel)))
    (cl-mapcar (lambda (b x)
    (goto-char (+ b x))
    (insert (make-string (- pt-arg-max x) ? )))
    pts-begin
    pts-arg-rel)))))

    (defmacro define-key-regionp (keymap key command)
    "In KEYMAP, define KEY as DEF.
    DEF is called only when mark is active.
    Otherwise, KEY is inserted."
    `(define-key ,keymap ,key (lambda()(interactive)
    (if (region-active-p)
    (call-interactively ,command)
    (if (eq major-mode 'org-mode)
    (org-self-insert-command 1)
    (self-insert-command 1))))))
    (setq-default indent-tabs-mode nil)
    (add-hook
    'c-mode-common-hook
    (lambda ()
    (define-key-regionp c-mode-base-map "3" 'c-align-function-arguments)))