2010-12-26 4 views
7

Sto appena iniziando ad imparare emacs (woohoo!) E sono stato molto contento nel mio .emacs. Sfortunatamente, non conosco ancora Lisp, quindi sto avendo problemi con le basi.Come si associa un tasto a "la funzione rappresentata dalla seguente sequenza di tasti"?

ho già rimappata alcuni tasti fino a che non risolvere il mio memoria muscolare:

(global-set-key (kbd "<f9>") 'recompile) 

va bene. Ma come posso dire una chiave per 'simulare la pressione di più tasti'? Ad esempio, non lo so, creare <f1> come lo C-u 2 C-x } (ampliare il buffer di due caratteri).

Un modo è quello di guardare in alto che C-x } chiama shrink-window-horizontally, e fare una sorta di cose lambda. Questo è ovviamente il modo pulito ed elegante (come si fa?). Ma sicuramente c'è un modo per definire <f1> per inviare le sequenze di tasti C-u 2 C-x }?

risposta

8

Per quanto a lungo termine, mi sento di raccomandare l'approccio mostrato da seh, come quella sarà naturalmente più robusta nella maggior parte delle situazioni. Richiede un po 'più di lavoro e know-how, ovviamente, ma ne vale la pena :)

L'approccio di angus è come una versione ridotta della funzione macro della tastiera che dà a Emacs il suo nome (e un po' più semplice da usare di macro per l'esempio in questione). Dovresti comunque essere a conoscenza dei macro, tuttavia possono essere estremamente utili e, per qualcosa di più complicato, diventa molto più facile registrarne uno dinamicamente che scrivere manualmente tutte le singole chiavi.

Ecco il riassunto io ho scritto dei bit più importanti:

;;;; * Keyboard macros 
;; C-x (   or F3 Begin recording. 
;;      F3 Insert counter (if recording has already commenced). 
;; C-u <n> C-x ( or F3 Begin recording with an initial counter value <n>. 
;; C-x)   or F4 End recording. 
;; C-u <n> C-x) or F4 End recording, then execute the macro <n>-1 times. 
;; C-x e   or F4 Execute the last recorded keyboard macro. 
;;  e   or F4 Additional e or F4 presses repeat the macro. 
;; C-u <n> C-x e or F4 Execute the last recorded keyboard macro <n> times. 
;; C-x C-k r    Apply the last macro to each line of the region. 
;; C-x C-k e    Edit a keyboard macro (RET for most recent). 
;; C-x C-k b    Set a key-binding. 
;; 
;; If you find yourself using lots of macros, you can even name them 
;; for later use, and save them to your init file. 
;; M-x name-last-kbd-macro RET (name) RET 
;; M-x insert-kbd-macro RET (name) RET 
;; 
;; For more documentation: 
;; C-h k C-x (
;; M-: (info "(emacs) Keyboard Macros") RET 

Se giochiamo con l'esempio della domanda, vedrete come alcune di queste cose insieme legame ...

Per cominciare, è possibile definire le macro con F3CuCx}F4

Si potrebbe quindi associare temporaneamente al F1 con CxCkbF1 (in realtà non è vero se F1 è attualmente una chiave di prefisso per una keymap esistente, poiché digitandola in modo interattivo verrà semplicemente richiesto il resto. È possibile aggirare questo codice con (global-set-key (kbd "<f1>") ...), ma suggerirei di attenersi allo reserved bindings).

Se quindi si utilizza describe-key (C-hk) per esaminare ciò che è legato a quel tasto, Emacs vi mostrerà una (lambda) un'espressione che si potrebbe copiare il file init, se lo desiderasse.

alternativa, è possibile assegnare un nome alla macro e chiedere Emacs per inserire il codice nel buffer corrente:

Mxname-last-kbd-macroRET (nome) RET
Mxinsert-kbd-macroRETRET

Questo codice sembrerà diverso dall'espressione lambda mostrata da describe-key, ma se valuti la macro inserita, vedrai l'equivalenza. Puoi anche mostrare che l'espressione (kbd "...") valuta anche lo stesso valore, e quindi questi sono solo modi alternativi di fare la stessa cosa.

(È possibile utilizzare il buffer * scratch * valutare il codice punto spostando dopo la fine dell'espressione, e immettendo CxCe per visualizzare il valore nel minibuffer, o Cj inserire il valore nel buffer).

Si noti che il codice "inserito" utilizza fset per assegnare la macro a un simbolo. È possibile associare la macro a una chiave eseguendo lo (fset) e assegnando tale simbolo a una chiave con (global-set-key) oppure ignorando lo (fset) e assegnando semplicemente direttamente il valore della macro. Questo, ovviamente, è direttamente equivalente alla risposta di Angus.

Edit: Ho appena notato che c'è una funzione kmacro-name-last-macro vincolato al CxCkn che è quasi identico nella forma a name-last-kbd-macro, ma che genera la forma espressione lambda visto quando si utilizza kmacro-bind-to-key (CxCkb) e describe-key.

+0

Mille grazie! +1 per avermi mostrato il modo generale di fare questo genere di cose. – katrielalex

17

Certo che c'è, ed è il modo più ovvio:

(global-set-key (kbd "<f1>") (kbd "C-u 2 C-x }")) 
+3

Grazie mille. Questo non è affatto ovvio come pensi. :) State cercando questo da molto tempo. – spk

8

userò shrink-window-horizontally come la funzione di esempio, ma si può generalizzare l'idea di eventuali attacchi che desideri da definire.

Se si desidera utilizzare due come la quantità predefinita per ridurre la finestra, piuttosto che uno, provare quanto segue:

(global-set-key [f9] 
    (lambda (&optional n) 
    (interactive "P") 
    (shrink-window-horizontally (or n 2)))) 

che lega il chiave F9 per una funzione interattiva che accetta un argomento prefix. Se si preme F9 , you'll pass no argument, che evoca il valore predefinito di 2, come il parametro n riceverà nil come argomento. Tuttavia, se si preme, ad esempio, C-u 10 F9, si passa dieci come argomento per n. Ciò ti consente di utilizzare la tua rilegatura in modo più flessibile.

+0

Vorrei poter accettare più di una risposta ... +1. – katrielalex