]> code.delx.au - gnu-emacs-elpa/commitdiff
company-template-c-like-templatify: Support generics
authorDmitry Gutov <dgutov@yandex.ru>
Sun, 12 Oct 2014 20:41:36 +0000 (00:41 +0400)
committerDmitry Gutov <dgutov@yandex.ru>
Sun, 12 Oct 2014 20:55:04 +0000 (00:55 +0400)
Closes #201

NEWS.md
company-clang.el
company-template.el
company-tests.el

diff --git a/NEWS.md b/NEWS.md
index f563e7800b019bdadc6cbb2d5a2b9be2f5edf7e8..51cae3d7c77cb2bd61aba34cf7fc9763b1574636 100644 (file)
--- a/NEWS.md
+++ b/NEWS.md
@@ -2,6 +2,8 @@
 
 ## Next
 
+* `company-clang` and `company-template-c-like-templatify` support templated
+  functions and arguments.
 * `company-dabbrev` ignores "uninteresting" buffers by default. Depends on the
   new user option, `company-dabbrev-ignore-buffers`.
 * `company-files` checks directory's last modification time.
index 77a544f694fa230e98dff11d1992a9c0b5281efb..90757a84b957f52a05111d8ddf4333d67f1b7220 100644 (file)
@@ -110,7 +110,7 @@ or automatically through a custom `company-clang-prefix-guesser'."
 ;; TODO: Handle Pattern (syntactic hints would be neat).
 ;; Do we ever see OVERLOAD (or OVERRIDE)?
 (defconst company-clang--completion-pattern
-  "^COMPLETION: \\_<\\(%s[a-zA-Z0-9_:]*\\)\\(?: : \\(.*\\)$\\)?$")
+  "^COMPLETION: \\_<\\(%s[a-zA-Z0-9_:<>]*\\)\\(?: : \\(.*\\)$\\)?$")
 
 (defconst company-clang--error-buffer-name "*clang-error*")
 
@@ -320,7 +320,8 @@ passed via standard input."
                          (insert anno)
                          (if (string-match "\\`:[^:]" anno)
                              (company-clang-objc-templatify anno)
-                           (company-template-c-like-templatify anno)))))))
+                           (company-template-c-like-templatify
+                            (concat arg anno))))))))
 
 (provide 'company-clang)
 ;;; company-clang.el ends here
index 576b246ecdd8db682932e6aa745394e0212b21a6..bc1055cdea6d0fba29bbd768d2249fb09df2368c 100644 (file)
@@ -1,6 +1,6 @@
 ;;; company-template.el
 
-;; Copyright (C) 2009, 2010, 2013 Free Software Foundation, Inc.
+;; Copyright (C) 2009, 2010, 2014 Free Software Foundation, Inc.
 
 ;; Author: Nikolaj Schumacher
 
@@ -149,22 +149,49 @@ Leave point at the end of the field."
 (defun company-template-c-like-templatify (call)
   (let* ((end (point-marker))
          (beg (- (point) (length call)))
-         (cnt 0))
-    (when (re-search-backward ")" beg t)
-      (delete-region (match-end 0) end))
-    (goto-char beg)
-    (when (search-forward "(" end 'move)
-      (if (eq (char-after) ?\))
+         (cnt 0)
+         (templ (company-template-declare-template beg end))
+         paren-open paren-close)
+    (with-syntax-table (make-char-table 'syntax-table nil)
+      (modify-syntax-entry ?\( "(")
+      (modify-syntax-entry ?\) ")")
+      (modify-syntax-entry ?< "(")
+      (modify-syntax-entry ?> ")")
+      (when (search-backward ")" beg t)
+        (setq paren-close (point-marker))
+        (forward-char 1)
+        (delete-region (point) end)
+        (backward-sexp)
+        (forward-char 1)
+        (setq paren-open (point-marker)))
+      (when (search-backward ">" beg t)
+        (let ((angle-close (point-marker)))
           (forward-char 1)
-        (let ((templ (company-template-declare-template beg end)))
-          (while (re-search-forward (concat " *\\([^,)]*\\)[,)]") end t)
-            (let ((sig (match-string 1)))
-              (delete-region (match-beginning 1) (match-end 1))
-              (save-excursion
-                (company-template-add-field templ (match-beginning 1)
-                                            (format "arg%d" cnt) sig))
-              (cl-incf cnt)))
-          (company-template-move-to-first templ))))))
+          (backward-sexp)
+          (forward-char)
+          (setq cnt (company-template--c-like-args templ angle-close
+                                                   cnt))))
+      (when paren-open
+        (goto-char paren-open)
+        (company-template--c-like-args templ paren-close cnt)))
+    (if (overlay-get templ 'company-template-fields)
+        (company-template-move-to-first templ)
+      (company-template-remove-template templ)
+      (goto-char end))))
+
+(defun company-template--c-like-args (templ end counter)
+  (let ((last-pos (point)))
+    (while (re-search-forward "\\([^,]+\\),?" end 'move)
+      (when (zerop (car (parse-partial-sexp last-pos (point))))
+        (let ((sig (buffer-substring-no-properties last-pos (match-end 1))))
+          (save-excursion
+            (company-template-add-field templ last-pos
+                                        (format "arg%d" counter) sig)
+            (delete-region (point) (+ (point) (length sig))))
+          (skip-chars-forward " ")
+          (setq last-pos (point))
+          (cl-incf counter)))))
+  counter)
 
 (provide 'company-template)
 ;;; company-template.el ends here
index 00a6227c2a3e7622b1905bd98eb738a404ce6918..0663c71f9fef75159454d951d1565ae1cda9e5cc 100644 (file)
@@ -920,6 +920,19 @@ foo2"))
       (should (equal "foo(arg0, arg1)" (buffer-string)))
       (should (looking-at "arg0")))))
 
+(ert-deftest company-template-c-like-templatify-generics ()
+  (with-temp-buffer
+    (let ((text "foo<TKey, TValue>(int i, Dict<TKey, TValue>, long l)"))
+      (insert text)
+      (company-template-c-like-templatify text)
+      (should (equal "foo<arg0, arg1>(arg2, arg3, arg4)" (buffer-string)))
+      (should (looking-at "arg0"))
+      (should (equal "TKey" (overlay-get (company-template-field-at) 'display)))
+      (search-forward "arg3")
+      (forward-char -1)
+      (should (equal "Dict<TKey, TValue>"
+                     (overlay-get (company-template-field-at) 'display))))))
+
 ;;; Clang
 
 (ert-deftest company-clang-objc-templatify ()