commit 106c3a6c9d75780d01d193d659bf61e19c47418d
parent 51d48398423195e74ac5178397ac3241eb2b26dd
Author: Iqbal Ansari <iqbalansari02@yahoo.com>
Date: Sun, 6 Mar 2016 11:23:56 +0530
Merge branch 'develop'
Diffstat:
3 files changed, 132 insertions(+), 47 deletions(-)
diff --git a/emojify.el b/emojify.el
@@ -365,9 +365,19 @@ These can have one of the following values
:set (lambda (_ value) (emojify-set-emoji-styles value))
:group 'emojify)
-;; Obsolete vars
-(define-obsolete-variable-alias 'emojify-emoji-style 'emojify-emoji-styles "0.2")
-(define-obsolete-function-alias 'emojify-set-emoji-style 'emojify-set-emoji-styles "0.2")
+(defcustom emojify-program-contexts
+ '(comments string code)
+ "Contexts where emojis can be displayed in programming modes.
+
+Possible values are
+`comments' - Display emojis in comments
+`string' - Display emojis in strings
+`code' - Display emojis in code (this is applicable only for unicode emojis)"
+ :type '(set :tag "Contexts where emojis should be displayed in programming modes"
+ (const :tag "Display emojis in comments" comments)
+ (const :tag "Display emojis in string" string)
+ (const :tag "Display emojis in code" code))
+ :group 'emojify)
(defcustom emojify-prog-contexts
'both
@@ -383,6 +393,12 @@ Possible values are
(const :tag "Only in string" string)
(const :tag "Both in comments and string" both)
(const :tag "Do not display emojis in programming modes" none))
+ :set (lambda (_ value)
+ (setq emojify-program-contexts (pcase value
+ (`comments '(comments))
+ (`string '(string))
+ (`both '(comments string code))
+ (`none '()))))
:group 'emojify)
(defcustom emojify-inhibit-functions
@@ -417,20 +433,25 @@ The arguments IGNORED are, well ignored"
(and (eq major-mode 'org-mode)
(org-at-item-p)))
-(defun emojify-valid-prog-context-p (beg end)
- "Determine if the text between BEG and END should be used to display emojis.
-
-This returns non-nil if the region is valid according to `emojify-prog-contexts'"
- (when (and emojify-prog-contexts
- (memq emojify-prog-contexts '(string comments both)))
- (let ((syntax-beg (syntax-ppss beg))
- (syntax-end (syntax-ppss end))
- (pos (pcase emojify-prog-contexts
- (`string 3)
- (`comments 4)
- (`both 8))))
- (and (nth pos syntax-beg)
- (nth pos syntax-end)))))
+(defun emojify-valid-program-context-p (emoji beg end)
+ "Determine if emoji should be displayed for text between BEG and END.
+
+This returns non-nil if the region is valid according to `emojify-program-contexts'"
+ (when emojify-program-contexts
+ (let* ((syntax-beg (syntax-ppss beg))
+ (syntax-end (syntax-ppss end))
+ (context (cond ((and (nth 3 syntax-beg)
+ (nth 3 syntax-end)) 'string)
+ ((and (nth 4 syntax-beg)
+ (nth 4 syntax-end)) 'comments)
+ (t 'code))))
+ (and (memql context emojify-program-contexts)
+ (if (equal context 'code)
+ ;; If context if code display only unicode emojis
+ (and (string= (ht-get emoji "style") "unicode")
+ (memql 'unicode emojify-emoji-styles))
+ ;; No need to check for non-code context
+ t)))))
(defun emojify-inside-org-src-p (point)
"Return non-nil if POINT is inside `org-mode' src block.
@@ -463,7 +484,7 @@ the visible area."
(nth 8 syntax-end)))))))))
(defun emojify-valid-ascii-emoji-context-p (beg end)
- "Determine if the okay to display for text between BEG and END."
+ "Determine if the okay to display ascii emoji between BEG and END."
;; The text is at the start of the buffer
(and (or (not (char-before beg))
;; 32 space since ? (? followed by a space) is not readable
@@ -499,6 +520,14 @@ the visible area."
+;; Obsolete vars
+
+(define-obsolete-variable-alias 'emojify-emoji-style 'emojify-emoji-styles "0.2")
+(define-obsolete-function-alias 'emojify-set-emoji-style 'emojify-set-emoji-styles "0.2")
+(define-obsolete-variable-alias 'emojify-prog-contexts 'emojify-program-contexts "0.3")
+
+
+
;; Customizations to control the behaviour when point enters emojified text
(defcustom emojify-point-entered-behaviour 'echo
@@ -660,14 +689,30 @@ This returns nil if the emojis between BEG and END do not fall in region."
(emojify--inside-rectangle-selection-p beg end)))
(face-background 'region)))
-(defun emojify--overlay-face-background (beg)
+(defun emojify--overlay-face-background (face)
+ "Get background for given overlay FACE.
+
+This similar to `face-background' except it handles different values possible
+for overlay face including anonymous faces and list of faces. Unlike
+`face-background' it always looks up inherited faces if background is not
+directly defined on the face."
+ (if (memq (type-of face) '(string symbol))
+ (and (facep face)
+ (face-background face nil 'default))
+ (and (consp face)
+ ;; Handle anonymous faces
+ (or (or (plist-get face :background)
+ (emojify--face-background (car (plist-get face :inherit))))
+ ;; Possibly a list of faces
+ (emojify--overlay-face-background (car face))))))
+
+(defun emojify--overlay-background (beg)
"Get the overlay face for point BEG."
- (let* ((overlays-with-face (seq-filter (lambda (overlay)
- (and (overlay-get overlay 'face)
- (face-background (overlay-get overlay 'face) nil 'default)))
- (emojify-overlays-at beg t))))
- (when overlays-with-face
- (face-background (overlay-get (car (last overlays-with-face)) 'face) nil 'default))))
+ (let* ((overlay-backgrounds (delq nil (seq-map (lambda (overlay)
+ (and (overlay-get overlay 'face)
+ (emojify--overlay-face-background (overlay-get overlay 'face))))
+ (emojify-overlays-at beg t)))))
+ (car (last overlay-backgrounds))))
(defun emojify--face-background-at-point (beg)
"Get the background color for emoji at BEG."
@@ -680,13 +725,13 @@ This returns nil if the emojis between BEG and END do not fall in region."
(defun emojify--get-image-background (beg end)
"Get the color to be used as background for emoji between BEG and END.
-Ideally `emojify--overlay-face-background' should have been enough to handle
+Ideally `emojify--overlay-background' should have been enough to handle
selection, but for some reason it does not work well."
(or (emojify--region-background-face-maybe beg end)
;; TODO: `emojify--face-background-at-point' might already be
- ;; handling overlay faces as such `emojify--overlay-face-background'
+ ;; handling overlay faces as such `emojify--overlay-background'
;; might be redundant, need to verify this though
- (emojify--overlay-face-background beg)
+ (emojify--overlay-background beg)
(emojify--face-background-at-point beg)
(face-background 'default)))
@@ -756,21 +801,22 @@ TODO: Skip emojifying if region is already emojified."
(goto-char beg)
(while (and (> end (point))
(search-forward-regexp regexp end t))
- (let ((match-beginning (match-beginning 0))
- (match-end (match-end 0))
- (match (match-string-no-properties 0))
- (buffer (current-buffer)))
+ (let* ((match-beginning (match-beginning 0))
+ (match-end (match-end 0))
+ (match (match-string-no-properties 0))
+ (buffer (current-buffer))
+ (emoji (ht-get emojify-emojis match)))
- (when (and (memql (intern (ht-get (ht-get emojify-emojis match) "style"))
+ (when (and (memql (intern (ht-get emoji "style"))
emojify-emoji-styles)
;; Display unconditionally in non-prog mode
(or (not (derived-mode-p 'prog-mode 'tuareg--prog-mode))
- ;; In prog mode enable respecting `emojify-prog-contexts'
- (emojify-valid-prog-context-p match-beginning match-end))
+ ;; In prog mode enable respecting `emojify-program-contexts'
+ (emojify-valid-program-context-p emoji match-beginning match-end))
;; Display ascii emojis conservatively, since they have potential
;; to be annoying consider d: in head:
- (or (not (string= (ht-get (ht-get emojify-emojis match) "style") "ascii"))
+ (or (not (string= (ht-get emoji "style") "ascii"))
(emojify-valid-ascii-emoji-context-p match-beginning match-end))
(not (emojify-inside-org-src-p match-beginning))
diff --git a/test/emojify-test.el b/test/emojify-test.el
@@ -40,7 +40,27 @@
(should (equal (get-text-property (point) 'emojify-buffer) (current-buffer)))
(should (equal (get-text-property (point-min) 'emojify-beginning) (point-min-marker)))
(should (equal (get-text-property (point) 'emojify-end) (point-max-marker)))
- (should (equal (get-text-property (point) 'emojify-text) "😉"))))
+ (should (equal (get-text-property (point) 'emojify-text) "😉")))
+
+ (emojify-tests-with-emojified-static-buffer "😉"
+ ;; Emojis should be displayed by default in programming mode
+ (emacs-lisp-mode)
+ (emojify-tests-should-be-emojified (point-min))
+ (should (equal (get-text-property (point) 'emojify-buffer) (current-buffer)))
+ (should (equal (get-text-property (point-min) 'emojify-beginning) (point-min-marker)))
+ (should (equal (get-text-property (point) 'emojify-end) (point-max-marker)))
+ (should (equal (get-text-property (point) 'emojify-text) "😉"))
+
+ ;; Emojis should be displayed by default in non-programming mode
+ (fundamental-mode)
+ (emojify-redisplay-emojis-in-region)
+ (emojify-tests-should-be-emojified (point-min))
+
+ ;; Emojis should not be displayed if code is not an element in emojify-program-contexts
+ (setq emojify-program-contexts '())
+ (emacs-lisp-mode)
+ (emojify-redisplay-emojis-in-region)
+ (emojify-tests-should-not-be-emojified (point-min))))
(ert-deftest emojify-tests-mixed-emoji-test ()
:tags '(core mixed)
@@ -141,41 +161,60 @@
(emojify-tests-should-not-be-emojified unicode-emoji-pos)
(emojify-tests-should-not-be-emojified github-emoji-pos))))
-(ert-deftest emojify-tests-prog-contexts ()
+(ert-deftest emojify-tests-program-contexts ()
:tags '(core prog contextual)
- (emojify-tests-with-emojified-static-buffer ";; :) :smile:\n\":smile:\"\n8)"
+ (emojify-tests-with-emojified-static-buffer ";; :) :smile:\n\":smile:\"\n8) 💜 :smile:"
(let* ((comment-ascii-emoji-pos (+ 3 (point-min)))
(comment-github-emoji-pos (+ comment-ascii-emoji-pos (length ":) ")))
(string-github-emoji-pos (1+ (line-beginning-position 2)))
- (prog-ascii-emoji-pos (1+ (line-beginning-position 3))))
+ (prog-ascii-emoji-pos (line-beginning-position 3))
+ (prog-unicode-emoji-pos (+ 3 prog-ascii-emoji-pos))
+ (prog-github-emoji-pos (+ 2 prog-unicode-emoji-pos)))
(emacs-lisp-mode)
- (setq emojify-prog-contexts 'both)
+ (setq emojify-program-contexts '(comments string code))
(emojify-redisplay-emojis-in-region)
(emojify-tests-should-be-emojified comment-ascii-emoji-pos)
(emojify-tests-should-be-emojified comment-github-emoji-pos)
(emojify-tests-should-be-emojified string-github-emoji-pos)
(emojify-tests-should-not-be-emojified prog-ascii-emoji-pos)
+ (emojify-tests-should-be-emojified prog-unicode-emoji-pos)
+ (emojify-tests-should-not-be-emojified prog-github-emoji-pos)
- (setq emojify-prog-contexts 'comments)
+ (setq emojify-program-contexts '(comments))
(emojify-redisplay-emojis-in-region)
(emojify-tests-should-be-emojified comment-ascii-emoji-pos)
(emojify-tests-should-be-emojified comment-github-emoji-pos)
(emojify-tests-should-not-be-emojified string-github-emoji-pos)
(emojify-tests-should-not-be-emojified prog-ascii-emoji-pos)
+ (emojify-tests-should-not-be-emojified prog-unicode-emoji-pos)
+ (emojify-tests-should-not-be-emojified prog-github-emoji-pos)
- (setq emojify-prog-contexts 'string)
+ (setq emojify-program-contexts '(string))
(emojify-redisplay-emojis-in-region)
(emojify-tests-should-not-be-emojified comment-ascii-emoji-pos)
(emojify-tests-should-not-be-emojified comment-github-emoji-pos)
(emojify-tests-should-be-emojified string-github-emoji-pos)
(emojify-tests-should-not-be-emojified prog-ascii-emoji-pos)
+ (emojify-tests-should-not-be-emojified prog-unicode-emoji-pos)
+ (emojify-tests-should-not-be-emojified prog-github-emoji-pos)
+
+ (setq emojify-program-contexts '(code))
+ (emojify-redisplay-emojis-in-region)
+ (emojify-tests-should-not-be-emojified comment-ascii-emoji-pos)
+ (emojify-tests-should-not-be-emojified comment-github-emoji-pos)
+ (emojify-tests-should-not-be-emojified string-github-emoji-pos)
+ (emojify-tests-should-not-be-emojified prog-ascii-emoji-pos)
+ (emojify-tests-should-be-emojified prog-unicode-emoji-pos)
+ (emojify-tests-should-not-be-emojified prog-github-emoji-pos)
- (setq emojify-prog-contexts 'none)
+ (setq emojify-program-contexts '())
(emojify-redisplay-emojis-in-region)
(emojify-tests-should-not-be-emojified comment-ascii-emoji-pos)
(emojify-tests-should-not-be-emojified comment-github-emoji-pos)
(emojify-tests-should-not-be-emojified string-github-emoji-pos)
- (emojify-tests-should-not-be-emojified prog-ascii-emoji-pos))))
+ (emojify-tests-should-not-be-emojified prog-ascii-emoji-pos)
+ (emojify-tests-should-not-be-emojified prog-unicode-emoji-pos)
+ (emojify-tests-should-not-be-emojified prog-github-emoji-pos))))
(ert-deftest emojify-tests-ascii-emoji-contexts ()
:tags '(core text contextual)
diff --git a/test/test-helper.el b/test/test-helper.el
@@ -37,7 +37,7 @@ Helps isolate tests from each other's customizations."
(emojify-saved-inhibit-major-modes emojify-inhibit-major-modes)
(emojify-saved-inhibit-in-buffer-functions emojify-inhibit-in-buffer-functions)
(emojify-saved-emoji-style emojify-emoji-styles)
- (emojify-saved-prog-contexts emojify-prog-contexts)
+ (emojify-saved-program-contexts emojify-program-contexts)
(emojify-saved-inhibit-functions emojify-inhibit-functions)
(emojify-saved-point-entered-behaviour emojify-point-entered-behaviour)
(emojify-saved-show-help emojify-show-help)
@@ -53,7 +53,7 @@ Helps isolate tests from each other's customizations."
emojify-display-style emojify-saved-display-style
emojify-inhibit-major-modes emojify-saved-inhibit-major-modes
emojify-inhibit-in-buffer-functions emojify-saved-inhibit-in-buffer-functions
- emojify-prog-contexts emojify-saved-prog-contexts
+ emojify-program-contexts emojify-saved-program-contexts
emojify-inhibit-functions emojify-saved-inhibit-functions
emojify-point-entered-behaviour emojify-saved-point-entered-behaviour
emojify-show-help emojify-saved-show-help