]> code.delx.au - gnu-emacs-elpa/blobdiff - packages/nameless/nameless.el
Merge commit '9e84a66b07700bebb73592fe320c19794c206ce3'
[gnu-emacs-elpa] / packages / nameless / nameless.el
index eb595a308ce168243a962460a608c3f06af7e8c0..e79b01e63aee01a6b4241dea14a983fac56fd338 100644 (file)
@@ -4,7 +4,7 @@
 
 ;; Author: Artur Malabarba <emacs@endlessparentheses.com>
 ;; Keywords: convenience, lisp
-;; Version: 0.3
+;; Version: 0.5
 ;; Package-Requires: ((emacs "24.4"))
 
 ;; This program is free software; you can redistribute it and/or modify
@@ -66,9 +66,21 @@ automatically insert `font-lock-'."
   :type '(alist string string))
 
 (defvar nameless-aliases nil
-  "Alist from namespaces to aliases.
-Samse syntax as `nameless-global-aliases', but designed to be
-used as a file-local variable.")
+  "Alist from aliases to namespaces.
+This variable takes the same syntax and has the same effect as
+`nameless-global-aliases'.  Aliases set here take priority over
+those in `nameless-global-aliases'.
+This variable is designed to be used as a file-local or dir-local
+variable.")
+(put 'nameless-aliases 'safe-local-variable
+     (lambda (x) (ignore-errors
+              (let ((safe t))
+                (mapc (lambda (cell)
+                        (unless (and (stringp (car cell))
+                                     (stringp (cdr cell)))
+                          (setq safe nil)))
+                      x)
+                safe))))
 
 (defface nameless-face
   '((t :inherit font-lock-type-face))
@@ -86,6 +98,12 @@ for it to take effect."
                  (const :tag "Don't affect indentation" nil)
                  (const :tag "Only outside strings" 'outside-strings)))
 
+(defcustom nameless-private-prefix nil
+  "If non-nil, private symbols are displayed with a double prefix.
+For instance, the function `foobar--internal-impl' will be
+displayed as `::internal-impl', instead of `:-internal-impl'."
+  :type 'boolean)
+
 \f
 ;;; Font-locking
 (defun nameless--make-composition (s)
@@ -95,16 +113,25 @@ for it to take effect."
 (defvar nameless-mode)
 (defun nameless--compose-as (display)
   "Compose the matched region and return a face spec."
-  (when nameless-mode
+  (when (and nameless-mode
+             (not (get-text-property (match-beginning 1) 'composition))
+             (not (get-text-property (match-beginning 1) 'display)))
     (let ((compose (save-match-data
                      (and nameless-affect-indentation-and-filling
-                         (or (not (eq nameless-affect-indentation-and-filling 'outside-strings))
-                             (not (nth 3 (syntax-ppss)))))))
+                          (or (not (eq nameless-affect-indentation-and-filling 'outside-strings))
+                              (not (nth 3 (syntax-ppss)))))))
           (dis (concat display nameless-prefix)))
       (when compose
-        (compose-region (match-beginning 1)
-                        (match-end 1)
-                        (nameless--make-composition dis)))
+        (if (and nameless-private-prefix
+                 (equal "-" (substring (match-string 0) -1)))
+            (progn
+              (setq dis (concat dis nameless-prefix))
+              (compose-region (match-beginning 0)
+                              (match-end 0)
+                              (nameless--make-composition dis)))
+          (compose-region (match-beginning 1)
+                          (match-end 1)
+                          (nameless--make-composition dis))))
       `(face nameless-face ,@(unless compose (list 'display dis))))))
 
 (defvar-local nameless--font-lock-keywords nil)
@@ -120,12 +147,13 @@ for it to take effect."
   (nameless--ensure))
 
 (defun nameless--add-keywords (&rest r)
-  "Add font-lock keywords displaying REGEXP as DISPLAY.
+  "Add font-lock keywords displaying ALIAS as DISPLAY.
+ALIAS may be nil, in which case it refers to `nameless-current-name'.
 
-\(fn (regexp . display) [(regexp . display) ...])"
+\(fn (alias . display) [(alias . display) ...])"
   (setq-local font-lock-extra-managed-props
               `(composition display ,@font-lock-extra-managed-props))
-  (let ((kws (mapcar (lambda (x) `(,(nameless--name-regexp (cdr x)) 1 (nameless--compose-as ,(car x)) prepend)) r)))
+  (let ((kws (mapcar (lambda (x) `(,(nameless--name-regexp (cdr x)) 1 (nameless--compose-as ,(car x)))) r)))
     (setq nameless--font-lock-keywords kws)
     (font-lock-add-keywords nil kws t))
   (nameless--ensure))
@@ -133,16 +161,18 @@ for it to take effect."
 \f
 ;;; Name and regexp
 (defvar-local nameless-current-name nil)
+(put 'nameless-current-name 'safe-local-variable #'stringp)
 
-(defun nameless--in-arglist-p ()
-  "Is point inside an arglist?"
+(defun nameless--in-arglist-p (l)
+  "Is point inside an arglist?"
   (save-excursion
+    (goto-char l)
     (ignore-errors
       (backward-up-list)
       (or (progn (forward-sexp -1)
                  (looking-at-p "[a-z-]lambda\\_>"))
           (progn (forward-sexp -1)
-                 (looking-at-p "\\(cl-\\)?def\\(un\\|macro\\|inline\\)\\*?\\_>"))))))
+                 (looking-at-p "\\(cl-\\)?def"))))))
 
 (defun nameless-insert-name (&optional noerror)
   "Insert `nameless-current-name' or the alias at point.
@@ -168,7 +198,8 @@ configured, or if `nameless-current-name' is nil."
                                    (assoc alias nameless-global-aliases))))))
         (if full-name
             (progn (delete-region l r)
-                   (insert full-name "-"))
+                   (insert full-name "-")
+                   t)
           (unless noerror
             (user-error "No name for alias `%s', see `nameless-aliases'" alias))))
     (if nameless-current-name
@@ -180,13 +211,18 @@ configured, or if `nameless-current-name' is nil."
 (defun nameless-insert-name-or-self-insert (&optional self-insert)
   "Insert the name of current package, with a hyphen."
   (interactive "P")
-  (if (or self-insert
-          (not nameless-current-name)
-          (eq (char-before) ?\\)
-          (nameless--in-arglist-p))
-      (call-interactively #'self-insert-command)
-    (or (nameless-insert-name 'noerror)
-        (call-interactively #'self-insert-command))))
+  (let ((l (point)))
+    (call-interactively #'self-insert-command)
+    (unless (or self-insert
+                (not nameless-current-name)
+                (eq (char-before l) ?\\)
+                (nameless--in-arglist-p l))
+      (undo-boundary)
+      (delete-region l (point))
+      (unless (nameless-insert-name 'noerror)
+        (call-interactively #'self-insert-command)))))
+
+(put 'nameless-insert-name-or-self-insert 'delete-selection t)
 
 (defun nameless--name-regexp (name)
   "Return a regexp of the current name."
@@ -203,13 +239,13 @@ Return S."
 ;;; Minor mode
 ;;;###autoload
 (define-minor-mode nameless-mode
-  nil nil " :" '(("_" . nameless-insert-name-or-self-insert))
+  nil nil " :" `((,(kbd "C-c C--") . nameless-insert-name))
   (if nameless-mode
       (if (or nameless-current-name
               (ignore-errors (string-match "\\.el\\'" (lm-get-package-name))))
           (progn
             (unless nameless-current-name
-              (setq nameless-current-name (replace-regexp-in-string "\\.[^.]*\\'" "" (lm-get-package-name))))
+              (setq nameless-current-name (replace-regexp-in-string "\\(-mode\\)?\\.[^.]*\\'" "" (lm-get-package-name))))
             (add-function :filter-return (local 'filter-buffer-substring-function)
                           #'nameless--filter-string)
             (apply #'nameless--add-keywords
@@ -222,5 +258,12 @@ Return S."
     (setq nameless-current-name nil)
     (nameless--remove-keywords)))
 
+;;;###autoload
+(defun nameless-mode-from-hook ()
+  "Turn on `nameless-mode'.
+Designed to be added to `emacs-lisp-mode-hook'.
+Interactively, just invoke `nameless-mode' directly."
+  (add-hook 'find-file-hook #'nameless-mode nil 'local))
+
 (provide 'nameless)
 ;;; nameless.el ends here