So I'm starting to learn a bit of lisp/elisp to optimize my emacs environment, and I've started making a simple emacs library, the major roadblock is being able to tell if a parenthesis entered has a match or not. I've been looking through the emacs source (paren.el.gz) and realized I can use the function show-paren-function to determine if it is a match or not.
Here's what I've got so far:
(defun it-is-a-paren()
(interactive)
(insert ")")
(if (show-paren-function)
(message "%s" "it is a match")
(message "%s" "it is not")))
So this is pretty basic, and "it is a match" works as it should, but when it is supposed to throw "it is not", it doesn't, instead it gives me "Wrong type argument: integer-or-marker-p, t".
Is anyone familiar enough to advise use of a different function, or maybe I should be writing my own altogether instead of using show-paren-function. Or is there a way around this error (sort of like exception handling)?
The "exception handling"-like construct you're looking for is condition-case.
(defun its-a-paren()
(interactive)
(insert ")")
(condition-case ex
(if (show-paren-function)
(message "its a match")
(message "its not"))
(error (message "its not"))))
Edit: Looking into show-paren-function's code, it seems to me that this error is a bug as it comes from the expression (goto-char pos) where pos is t.
Anyways, show-paren-function uses scan-sexps to look for the matching paren. Adapting from the way it's done in show-paren-function, a simplified function for your case would be:
(defun its-a-paren()
(interactive)
(insert ")")
(condition-case ()
(progn
(scan-sexps (point) -1)
(message "It's a match"))
(error (message "It's not a match"))))
Using show-paren-function for this purpose is overkill (like giving your car to a garage a checking if the oil-level has changed, to determine if the car needed more oil) and doesn't work right, as you've noticed.
I'd recommend you try
(condition-case nil
(progn (forward-sexp -1)
(message "Moved to the matching opener"))
(scan-error (message "No matching opener")))
Related
I currently have the following function:
(defun goto-python-class (classname)
(interactive "sClass name: ")
(search-forward (concat "class " classname)))
I am trying to find a search function that will search both forward or backward. Basically, search the entire buffer. There doesn't seem to be any. Is there any other way of doing so, without having to figure out if search succeeded or not, and attempt the backward search?
It is normally done like this:
(defun goto-python-class (classname)
(interactive "sClass name: ")
(goto-char (point-min))
(unless (re-search-forward
(concat "class " classname)
nil t)
(message "Class %S not found" classname)))
How can one have dired-do-search use the more visible isearch-face, or at least highlight the entire token found?
A blinking cursor would be an alternative, if it weren't so distracting while editing.
Restatement
If I run isearch-forward on the string "hello", that string is highlighted during the search, as you see in the image below.
If I am instead in dired(-x) mode, mark the file, as shown in the next figure,
then run dired-do-search on the string "hello", the string is found, but it is not highlighted, as you see below.
How can I make dired-do-search use the same face as isearch-forward? In this example it is easy to spot the cursor, but on a larger display with heavy use of font-lock, and after opting for a milder, non-obtrusive face for the cursor, it is rather difficult to spot the location of the search string.
Update
Is the answer below the briefest way to solve this problem?
Perhaps you're looking for dired-do-isearch or dired-do-isearch-regexp
If you want the same feel of dired-do-search, it looks like you could also make a defun that invokes tags-loop-continue with custom tags-loop-operate and tags-loop-scan operations.
Here's what I came up with:
(defvar dired-do-search-overlay nil)
(defvar dired-do-search-region nil)
(defun dired-do-search (regexp)
"Search through all marked files for a match for REGEXP.
Stops when a match is found.
To continue searching for next match, use command \\[tags-loop-continue]."
(interactive "sSearch marked files (regexp): ")
(setq
tags-loop-operate `(progn
(if dired-do-search-overlay
(delete-overlay dired-do-search-overlay))
(setq dired-do-search-overlay
(make-overlay (car dired-do-search-region)
(cadr dired-do-search-region)))
(overlay-put dired-do-search-overlay
'face isearch-face)
(overlay-put dired-do-search-overlay
'priority 1001)
nil)
tags-loop-scan `(progn
(if (re-search-forward ',regexp nil t)
(setq dired-do-search-region
(list (match-beginning 0)
(match-end 0)))
(if dired-do-search-overlay
(delete-overlay dired-do-search-overlay))
nil)))
(tags-loop-continue
(or '(dired-get-marked-files nil nil 'dired-nondirectory-p) t)))
I'd like to have a function that asks for a number n and executes the default compile command n-times afterwards. That is to say unlike C-c C-c (i.e. TeX-command-master) I don't want to be asked which command to run, it should select the default compile command based on the AUCTeX settings. Naturally if any error occurs the execution should stop.
I know about TeX-texify, however, this doesn't statisfy my needs because sometimes I just want emacs to run pdflatex five times indepent of what the AUCTeX parser thinks is adequate.
Any help is much appreciated!
Edit: I have looked into this a little further and using code from the above reference I have started writing a function that does this. However, it has one major flaw. Let me first give you the code:
(defcustom TeX-MultiTeX-Command "LaTeX" "Default MultiTeX command" :type 'string :group 'TeX-command)
(defun TeX-MultiTeX (n)
"Run TeX-command n-times"
(interactive "nRun TeX/LaTeX how many times: ")
(while (> n 0)
(TeX-command TeX-MultiTeX-Command 'TeX-master-file)
(setq n (- n 1))))
As you can see, I have implemented a config variable for selecting the correct compilation command. Now let me present the problem:
The compilation of the LaTeX document takes some time, however, my function instantly calls the second (and following) executions of the compile command. Maybe someone can provide help in finding a solution that checks whether compilation has finished successfully prior to executing (TeX-command TeX-MultiTeX-Command 'TeX-master-file), then executes said function or prints some error message if compilation finished with an error.
With the help of the code of the TeX-texify function I have developed a function that does what I want, the code is given below.
I'd like to thank user4815162342; although this solution is not based on his suggestion, I think his solution might be of use for a different problem. Also I'd like to thank TN, the author of TeX-texify, I shamelessly took and adapted his code for my problem. ;)
(defcustom TeX-MultiTeX-Command "LaTeX"
"Default MultiTeX command"
:type 'string :group 'TeX-command)
(defun TeX-MultiTeX-sentinel (&optional proc sentinel)
"Non-interactive! Call the standard-sentinel of the current LaTeX-process.
If there is still something left do do start the next latex-command."
(set-buffer (process-buffer proc))
(funcall TeX-MultiTeX-sentinel proc sentinel)
(let ((case-fold-search nil))
(when (string-match "\\(finished\\|exited\\)" sentinel)
(set-buffer TeX-command-buffer)
(unless (plist-get TeX-error-report-switches (intern (TeX-master-file)))
(TeX-MultiTeX TeX-MultiTeX-num-left)))))
(defun TeX-MultiTeX (n)
"Run TeX-command n-times"
(interactive "nRun TeX/LaTeX how many times: ")
(when (or (called-interactively-p 'any)
(null (boundp 'TeX-MultiTeX-num-left)))
(setq TeX-MultiTeX-num-left n))
(if (>= TeX-MultiTeX-num-left 1)
(progn
(TeX-command TeX-MultiTeX-Command 'TeX-master-file)
(setq TeX-MultiTeX-num-left (- TeX-MultiTeX-num-left 1))
(setq proc (get-buffer-process (current-buffer)))
(setq TeX-MultiTeX-sentinel (process-sentinel proc))
(set-process-sentinel proc 'TeX-MultiTeX-sentinel))))
It seems that you need a synchronous way to run TeX-command. I haven't word with TeX-command, but if it uses the compilation API, it can be made to wait for the compilation to finish, although it's not exactly obvious how to do that. Here is an example that uses compilation-finish-functions to achieve the desired effect:
(require 'cl) ; for lexical-let
(defun compile-and-wait (compilefun)
(interactive)
(lexical-let ((done nil) finish-callback)
(setq finish-callback
;; when the compilation is done, remove the callback from
;; compilation-finish-functions and interrupt the wait
(lambda (buf msg)
(setq compilation-finish-functions
(delq finish-callback compilation-finish-functions))
(setq done t)))
(push finish-callback compilation-finish-functions)
(funcall compilefun)
(while (not done)
(sleep-for .1))))
EDIT
AUC TeX is not using compilation mode to spawn TeX, so the above cannot work. Since it's still useful for other compilation buffers, I'm leaving it in the answer. Another way to implement TeX-MultiTeX is by binding TeX-process-asynchronous to nil, which should ensure that AUC TeX waits for the command to finish.
I am learning how to program in emacs lisp. I thought I would write a simple function that prints a function definition to the messages buffer. This works fine:
(let (
(fDefAsString (symbol-function 'scroll-down))
)
(message "%s" fDefAsString)
(switch-to-buffer-other-frame "*Messages*"))
but I wanted this to be a function that could take an argument, the argument being the name of the function whose definition I want to see. So I tried this:
(defun message-function-definition (nameOfFunction)
(let (
(fDefAsString (symbol-function 'nameOfFunction))
)
(message "%s" fDefAsString)
(switch-to-buffer-other-frame "*Messages*")))
and then I wrote this:
(message-function-definition 'scroll-down)
Then I ran "eval-buffer".
I keep getting this error:
Debugger entered--Lisp error: (void-function nameOfFunction)
symbol-function(nameOfFunction)
(let ((fDefAsString ...)) (message "%s" fDefAsString) (switch-to-buffer-other-frame "Messages"))
message-function-definition(scroll-down)
eval((message-function-definition (quote scroll-down)))
eval-last-sexp-1(nil)
eval-last-sexp(nil)
call-interactively(eval-last-sexp nil nil)
recursive-edit()
byte-code("\306 #\307=\203!
I've tried quoting, unquoting, and I've tried to use "nameOfFunction" but I can not get this to work. What am I doing wrong?
Did you try unquoting? This works for me:
(defun message-function-definition (nameOfFunction)
(let ((fDefAsString (symbol-function nameOfFunction)))
(message "%s" fDefAsString)
(switch-to-buffer-other-frame "*Messages*")))
Some hints:
Your code is not indented correctly. If you select the region and re-indent with tab, it'll be easier to read.
You should spend a couple of hours working through the "Emacs Lisp Intro",
you will have a much better idea of how things work in Emacs-lisp, rather
than figuring it all by asking one question at a time on StackOverflow.
symbol-function is not designed to show a human readable definition of
the function. In most cases you won't really see anything useful.
Try this:
(find-function-other-window 'scroll-down)
I was trying to answer another SO question when I hit upon some very odd behavior. Here's my little test case:
(make-variable-buffer-local
(defvar my-override-mode-on-save nil
"Can be set to automatically ignore read-only mode of a file when saving."))
(defadvice file-writable-p (around my-overide-file-writeable-p act)
"override file-writable-p if `my-override-mode-on-save' is set."
(or
my-override-mode-on-save
ad-do-it))
(defun my-override-toggle-read-only ()
"Toggle buffer's read-only status, keeping `my-override-mode-on-save' in sync."
(interactive)
(setq my-override-mode-on-save (not my-override-mode-on-save))
(toggle-read-only))
(defun tester-fn ()
(interactive)
(let ((xxx (file-writable-p "/tmp/foofoo"))
(yyy (file-writable-p "/tmp/fooxxfoo")))
(message (concat "XXX: " (if xxx "yes" "no") " - YYY: " (if yyy "yes" "no")))))
where:
/tmp/foofoo is a read-only file that I've visited and run my-override-toggle-read-only in.
/tmp/fooxxfoo does not exist.
/tmp is writable by the user I'm logged in as.
If I run tester-fn in a buffer where my-override-mode-on-save is set to t then I get an unexpected result: XXX: no - YYY: no. If I run tester-fn while in some other buffer (e.g. scratch) I get the expected response in the minibuffer: XXX: no - YYY: yes. Tracing the advice through the debugger shows it to be doing exactly what I think it should be doing, executing the parts I expect it to, skipping the parts I expect it to, returning the value I expect it to. However, tracing tester-fn through the debugger shows very different values being returned (nil & t if the variable evaluates as nil, nil & nil if the variable evaluates as non-nil). The nil & nil return is really what I find bizarre.
I have no clue what's happening here. Anyone know why I'm not getting the results I expect?
Your code looks good, except the one missing key. You need to set the return value appropriately:
(defadvice file-writable-p (around my-overide-file-writeable-p act)
"override file-writable-p if `my-override-mode-on-save' is set."
(setq ad-return-value
(or
my-override-mode-on-save
ad-do-it)))
This is documented in the advice manual.