X-Git-Url: https://code.delx.au/gnu-emacs-elpa/blobdiff_plain/7584ed95ed7da7c0d1d39308a0f765cd7a5a450a..779de03e226b161a00c3428ffdadd89ecbc422d0:/company-dabbrev-code.el diff --git a/company-dabbrev-code.el b/company-dabbrev-code.el index 1ca67e2af..9331087ab 100644 --- a/company-dabbrev-code.el +++ b/company-dabbrev-code.el @@ -1,116 +1,104 @@ -;;; company-dabbrev-code.el --- a dabbrev-like company-mode back-end for code -;; -;; Copyright (C) 2009 Nikolaj Schumacher -;; -;; This file is part of company 0.3.1. -;; -;; This program is free software; you can redistribute it and/or -;; modify it under the terms of the GNU General Public License -;; as published by the Free Software Foundation; either version 2 -;; of the License, or (at your option) any later version. -;; -;; This program is distributed in the hope that it will be useful, +;;; company-dabbrev-code.el --- dabbrev-like company-mode backend for code -*- lexical-binding: t -*- + +;; Copyright (C) 2009, 2011, 2014 Free Software Foundation, Inc. + +;; Author: Nikolaj Schumacher + +;; This file is part of GNU Emacs. + +;; GNU Emacs is free software: you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; GNU Emacs is distributed in the hope that it will be useful, ;; but WITHOUT ANY WARRANTY; without even the implied warranty of ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ;; GNU General Public License for more details. -;; + ;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . +;; along with GNU Emacs. If not, see . + + +;;; Commentary: +;; + +;;; Code: (require 'company) -(eval-when-compile (require 'cl)) +(require 'company-dabbrev) +(require 'cl-lib) + +(defgroup company-dabbrev-code nil + "dabbrev-like completion backend for code." + :group 'company) (defcustom company-dabbrev-code-modes - '(asm-mode batch-file-mode c++-mode c-mode cperl-mode csharp-mode css-mode - emacs-lisp-mode erlang-mode espresso-mode f90-mode fortran-mode - haskell-mode java-mode javascript-mode jde-mode js2-mode lisp-mode - lua-mode objc-mode perl-mode php-mode python-mode ruby-mode scheme-mode - shell-script-mode) - "*Modes that use `company-dabbrev-code'. -In all these modes `company-dabbrev-code' will complete only symbols, not text -in comments or strings. In other modes `company-dabbrev-code' will pass control -to other back-ends \(e.g. `company-dabbrev'\). -Value t means complete in all modes." - :group 'company - :type '(choice (repeat (symbol :tag "Major mode")) - (const tag "All modes" t))) - -(defcustom company-dabbrev-code-other-buffers .5 - "*Determines whether `company-dabbrev-code' should search other buffers. -If t, search all buffers with the same major-mode. A numeric value means -search other buffers for that many seconds and then return." - :group 'company + '(prog-mode + batch-file-mode csharp-mode css-mode erlang-mode haskell-mode jde-mode + lua-mode python-mode) + "Modes that use `company-dabbrev-code'. +In all these modes (and their derivatives) `company-dabbrev-code' will +complete only symbols, not text in comments or strings. In other modes +`company-dabbrev-code' will pass control to other backends +\(e.g. `company-dabbrev'\). Value t means complete in all modes." + :type '(choice (repeat :tag "Some modes" (symbol :tag "Major mode")) + (const :tag "All modes" t))) + +(defcustom company-dabbrev-code-other-buffers t + "Determines whether `company-dabbrev-code' should search other buffers. +If `all', search all other buffers, except the ignored ones. If t, search +buffers with the same major mode. If `code', search all buffers with major +modes in `company-dabbrev-code-modes', or derived from one of them. See +also `company-dabbrev-code-time-limit'." :type '(choice (const :tag "Off" nil) (const :tag "Same major mode" t) + (const :tag "Code major modes" code) + (const :tag "All" all))) + +(defcustom company-dabbrev-code-time-limit .1 + "Determines how long `company-dabbrev-code' should look for matches." + :type '(choice (const :tag "Off" nil) (number :tag "Seconds"))) -(defmacro company-dabrev-code--time-limit-while (test start limit &rest body) - (declare (indent 3) (debug t)) - `(let ((company-time-limit-while-counter 0)) - (catch 'done - (while ,test - ,@body - (and ,limit - (eq (incf company-time-limit-while-counter) 25) - (setq company-time-limit-while-counter 0) - (> (float-time (time-since ,start)) ,limit) - (throw 'done 'company-time-out)))))) - -(defsubst company-dabbrev-code--make-regexp (prefix) +(defcustom company-dabbrev-code-everywhere nil + "Non-nil to offer completions in comments and strings." + :type 'boolean) + +(defcustom company-dabbrev-code-ignore-case nil + "Non-nil to ignore case when collecting completion candidates." + :type 'boolean) + +(defun company-dabbrev-code--make-regexp (prefix) (concat "\\_<" (if (equal prefix "") "\\([a-zA-Z]\\|\\s_\\)" (regexp-quote prefix)) "\\(\\sw\\|\\s_\\)*\\_>")) -(defun company-dabbrev-code--buffer-symbols (regexp pos &optional symbols - start limit) - (save-excursion - (goto-char (point-min)) - (let (match) - (company-dabrev-code--time-limit-while (re-search-forward regexp nil t) - start limit - (setq match (match-string-no-properties 0)) - (if (company-in-string-or-comment) - (re-search-forward "\\s>\\|\\s!\\|\\s\"" nil t) - (unless (eq (match-end 0) pos) ;; ignore match before point - (push match symbols)))) - symbols))) - -(defun company-dabbrev-code--symbols (regexp &optional limit) - (let ((start (current-time)) - (symbols (company-dabbrev-code--buffer-symbols regexp (point)))) - (dolist (buffer (delq (current-buffer) (buffer-list))) - (and (eq (buffer-local-value 'major-mode buffer) major-mode) - (with-current-buffer buffer - (setq symbols - (company-dabbrev-code--buffer-symbols regexp nil symbols - start limit)))) - (and limit - (> (float-time (time-since start)) limit) - (return))) - symbols)) - ;;;###autoload (defun company-dabbrev-code (command &optional arg &rest ignored) - "A dabbrev-like `company-mode' back-end for code. -The back-end looks for all symbols in the current buffer that aren't in + "dabbrev-like `company-mode' backend for code. +The backend looks for all symbols in the current buffer that aren't in comments or strings." (interactive (list 'interactive)) - (case command - ('interactive (company-begin-backend 'company-dabbrev-code)) - ('prefix (and (or (eq t company-dabbrev-code-modes) - (apply 'derived-mode-p company-dabbrev-code-modes)) - (not (company-in-string-or-comment)) - (or (company-grab-symbol) 'stop))) - ('candidates (let ((case-fold-search nil) - (regexp (company-dabbrev-code--make-regexp prefix))) - (if company-dabbrev-code-other-buffers - (company-dabbrev-code--symbols - arg - (when (numberp company-dabbrev-code-other-buffers) - company-dabbrev-code-other-buffers)) - (company-dabbrev-code--buffer-symbols arg (point))))) - ('duplicates t))) + (cl-case command + (interactive (company-begin-backend 'company-dabbrev-code)) + (prefix (and (or (eq t company-dabbrev-code-modes) + (apply #'derived-mode-p company-dabbrev-code-modes)) + (or company-dabbrev-code-everywhere + (not (company-in-string-or-comment))) + (or (company-grab-symbol) 'stop))) + (candidates (let ((case-fold-search company-dabbrev-code-ignore-case)) + (company-dabbrev--search + (company-dabbrev-code--make-regexp arg) + company-dabbrev-code-time-limit + (pcase company-dabbrev-code-other-buffers + (`t (list major-mode)) + (`code company-dabbrev-code-modes) + (`all `all)) + t))) + (ignore-case company-dabbrev-code-ignore-case) + (duplicates t))) (provide 'company-dabbrev-code) ;;; company-dabbrev-code.el ends here