help-gnu-emacs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: manipulating abbreviation mode hooks


From: Suvayu Ali
Subject: Re: manipulating abbreviation mode hooks
Date: Sun, 16 May 2010 05:29:50 -0700
User-agent: Mozilla/5.0 (X11; U; Linux x86_64; en-US; rv:1.9.1.9) Gecko/20100330 Fedora/3.0.4-1.fc11 Lightning/1.0b2pre Thunderbird/3.0.4

Just in case someone else was looking for a solution something similar,

On Sunday 09 May 2010 06:38 PM, Suvayu Ali wrote:
Hi everyone,

I'm not sure I'll be able to explain what I am trying to do but I'll
give it a shot nonetheless. I wrote some abbreviations for the c++ mode
(e.g. `for' expands to the entire for loop construct, if..else, ...).
However when ever I use any of those abbrevs within a comment, it still
expands to the loop.

 From the info node, "(elisp)Top:: > *Note Abbrevs:: > Abbrev Expansion"
I got the hint to use `abbrev-expand-functions' hook. To start out
simple, I tried to implement this for shell-script mode abbrev table,
and the text-mode abbrev table.

So in a scratch buffer I tried this,

(defun foo ()
(interactive)
(if (not (save-excursion
(and
(forward-line 0)
(eq (char-after) ?#))))
(print "src")
(let ((local-abbrev-table text-mode-abbrev-table))
(print "comments")
(funcall 'expand-abbrev))
))

This worked as expected, my text mode abbreviations were expanded on a
line starting with #, but didn't expand otherwise.

But when I put the following in my ~/.emacs, I get no such behaviour.

(defun my-shell-script-mode-abbrev-expand-function ()
(if (not (save-excursion
(forward-line 0)
(eq (char-after) ?#)))
(funcall 'expand-abbrev)
(let ((local-abbrev-table text-mode-abbrev-table))
(funcall 'expand-abbrev))))

(add-hook 'shell-script-mode-hook
'(lambda ()
(add-hook 'abbrev-expand-functions
'my-shell-script-mode-abbrev-expand-function
nil t)))


Once this is solved, my second question is how do I implement this for
c++-mode? I can't figure out how to match to `//' or a `/* ... */'
block. I'm a newbie in lisp, so a little guidance would be very
appreciated. :)


I solved it like this,

,----
| (defun expand-abbrev-in-context (expand)
| "Expands abbreviations according to the context. Determines whether within
| comments or source by looking at the face name. If within comments the
| `text-mode-abbrev-table' is used, the major mode abbrev-table is used otherwise.
|
| Expansion is done by the function passed as the argument. This is controlled by
| the \"abnormal\" hook `abbrev-expand-functions'."
|   (if (not (save-excursion
|            (string-match "comment"
|                          (symbol-name (if (< (point) (point-max))
|                                           (face-at-point)
|                                         (backward-char)
|                                         (face-at-point))))))
|       (funcall expand)
|     (let ((local-abbrev-table text-mode-abbrev-table))
|       (funcall expand))))
| (add-hook 'after-change-major-mode-hook
|         (lambda ()
|           (add-hook 'abbrev-expand-functions 'expand-abbrev-in-context nil 
t)))
`----

Hope this helps someone in the future.

--
Suvayu

Open source is the future. It sets us free.



reply via email to

[Prev in Thread] Current Thread [Next in Thread]