From mboxrd@z Thu Jan 1 00:00:00 1970 Path: news.gmane.org!not-for-mail From: Stefan Monnier Newsgroups: gmane.emacs.devel Subject: Re: Is there a plan to record kbd macro as elisp code? Date: Sat, 27 Oct 2007 21:14:23 -0400 Message-ID: References: <87y7doxmcw.fsf@jurta.org> NNTP-Posting-Host: lo.gmane.org Mime-Version: 1.0 Content-Type: text/plain; charset=us-ascii X-Trace: ger.gmane.org 1193534076 5343 80.91.229.12 (28 Oct 2007 01:14:36 GMT) X-Complaints-To: usenet@ger.gmane.org NNTP-Posting-Date: Sun, 28 Oct 2007 01:14:36 +0000 (UTC) Cc: yzhh , emacs-devel@gnu.org To: Juri Linkov Original-X-From: emacs-devel-bounces+ged-emacs-devel=m.gmane.org@gnu.org Sun Oct 28 02:14:37 2007 Return-path: Envelope-to: ged-emacs-devel@m.gmane.org Original-Received: from lists.gnu.org ([199.232.76.165]) by lo.gmane.org with esmtp (Exim 4.50) id 1Ilwjd-0004Ef-KR for ged-emacs-devel@m.gmane.org; Sun, 28 Oct 2007 02:14:37 +0100 Original-Received: from localhost ([127.0.0.1] helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.43) id 1IlwjU-0001FF-EC for ged-emacs-devel@m.gmane.org; Sat, 27 Oct 2007 21:14:28 -0400 Original-Received: from mailman by lists.gnu.org with tmda-scanned (Exim 4.43) id 1IlwjR-0001E7-HH for emacs-devel@gnu.org; Sat, 27 Oct 2007 21:14:25 -0400 Original-Received: from exim by lists.gnu.org with spam-scanned (Exim 4.43) id 1IlwjR-0001Dg-68 for emacs-devel@gnu.org; Sat, 27 Oct 2007 21:14:25 -0400 Original-Received: from [199.232.76.173] (helo=monty-python.gnu.org) by lists.gnu.org with esmtp (Exim 4.43) id 1IlwjQ-0001DZ-Tx for emacs-devel@gnu.org; Sat, 27 Oct 2007 21:14:24 -0400 Original-Received: from tomts25-srv.bellnexxia.net ([209.226.175.188]) by monty-python.gnu.org with esmtp (Exim 4.60) (envelope-from ) id 1IlwjR-0004gG-0d for emacs-devel@gnu.org; Sat, 27 Oct 2007 21:14:25 -0400 Original-Received: from pastel.home ([74.12.208.145]) by tomts25-srv.bellnexxia.net (InterMail vM.5.01.06.13 201-253-122-130-113-20050324) with ESMTP id <20071028011423.NNBL19497.tomts25-srv.bellnexxia.net@pastel.home> for ; Sat, 27 Oct 2007 21:14:23 -0400 Original-Received: by pastel.home (Postfix, from userid 20848) id 986E180F4; Sat, 27 Oct 2007 21:14:23 -0400 (EDT) In-Reply-To: <87y7doxmcw.fsf@jurta.org> (Juri Linkov's message of "Sun\, 28 Oct 2007 00\:45\:45 +0300") User-Agent: Gnus/5.11 (Gnus v5.11) Emacs/23.0.50 (gnu/linux) X-detected-kernel: by monty-python.gnu.org: Solaris 8 (1) X-BeenThere: emacs-devel@gnu.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: "Emacs development discussions." List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Original-Sender: emacs-devel-bounces+ged-emacs-devel=m.gmane.org@gnu.org Errors-To: emacs-devel-bounces+ged-emacs-devel=m.gmane.org@gnu.org Xref: news.gmane.org gmane.emacs.devel:81905 Archived-At: >>> Thank you for your appreciation. But my modification is in the C code of >>> emacs, because 'execute-command' and 'call-interactively' are in C code. >>> And I don't think my dirty code would be a valid patch for the emacs >>> developers. >> >> I think what was expected was to first record a keyboard macro and later to >> turn that into elisp code. > That's was exactly my first attempt when I tried to implement this feature. > However, this approach doesn't work because a macro highly depends on its > context, and will fail when repeating it in different buffers, modes, etc. I think this doesn't matter: the same holds for the keyboard macros themselves and yet they're quite usable. The limitation of the approach (that the macro needs to be converted to Elisp in the same context where it was recorded) doesn't seem to be too serious: at least not a show-stopper. OTOH I do expect that it can be very tricky to recover the structure from just the key sequence: e.g. after a keybinding that may or may not present a minibuffer prompt, figuring out whether the rest of the keys were sent to the minibuffer or to the next command can be impossible without guessing. >> Another approach is to use a pre-command-hook to record the value of >> `this-command' for each command run. > After failing with the first approach, I tried to do this, but this doesn't > work because `this-command' doesn't record the arguments of the last > command. So when I added a new variable `this-command-args' that records > the arguments of the command being executed, this approach produced > good results. > Also I added a new variable `last-kbd-macro-commands', and a new command > `insert-last-kbd-macro-commands' to convert the recorded commands with > their arguments to a Lisp function. A change in isearch was also required > to convert all isearch subcommands into one search function. > Since yzhh doesn't want to post his code, I will post mine. > I ask yzhh to comment on this code, compare with his own, > and suggest further improvements: This doesn't sound too bad. Another approach would be to advise `call-interactively'. This may require changes at the C level so as to make sure that calls to Fcall_interactively are never made directly but always go through the `call-interactively' symbol. With an exhaustive around advice on call-interactively, you should be able to get a fairly reliable trace. But even a reliable trace will encounter the problems mentioned by Kim, and in order to get /good/ Elisp code (rather than just /working/ Elisp code), a fair bit of post-processing will be needed with ad-hoc rewrites. Stefan