2014-04-17 Daniel Colascione <dancol@dancol.org>
[bpt/emacs.git] / lisp / term / xterm.el
index eac4014..33eb61d 100644 (file)
@@ -43,10 +43,35 @@ The relevant features are:
   :type '(choice (const :tag "No" nil)
                  (const :tag "Check" check)
                  ;; NOTE: If you add entries here, make sure to update
-                 ;; `tocheck-capabilities' in `terminal-init-xterm' as well.
+                 ;; `terminal-init-xterm' as well.
                  (set (const :tag "modifyOtherKeys support" modifyOtherKeys)
                       (const :tag "report background" reportBackground))))
 
+(defconst xterm-paste-ending-sequence "\e[201~"
+  "Characters send by the terminal to end a bracketed paste.")
+
+(defun xterm-paste ()
+  "Handle the start of a terminal paste operation."
+  (interactive)
+  (let* ((end-marker-length (length xterm-paste-ending-sequence))
+         (pasted-text (with-temp-buffer
+                        (set-buffer-multibyte nil)
+                        (while (not (search-backward
+                                     xterm-paste-ending-sequence
+                                     (- (point) end-marker-length) t))
+                          (let ((event (read-event)))
+                            (when (eql event ?\r)
+                              (setf event ?\n))
+                            (insert event)))
+                        (let ((last-coding-system-used))
+                          (decode-coding-region
+                           (point-min) (point)
+                           (keyboard-coding-system) t))))
+         (interprogram-paste-function (lambda () pasted-text)))
+    (yank)))
+
+(define-key global-map [xterm-paste] #'xterm-paste)
+
 (defvar xterm-function-map
   (let ((map (make-sparse-keymap)))
 
@@ -394,6 +419,11 @@ The relevant features are:
     (define-key map "\e[12~" [f2])
     (define-key map "\e[13~" [f3])
     (define-key map "\e[14~" [f4])
+
+    ;; Recognize the start of a bracketed paste sequence.  The handler
+    ;; internally recognizes the end.
+    (define-key map "\e[200~" [xterm-paste])
+    
     map)
   "Function key map overrides for xterm.")
 
@@ -463,9 +493,6 @@ The relevant features are:
     map)
   "Keymap of possible alternative meanings for some keys.")
 
-;; List of terminals for which modify-other-keys has been turned on.
-(defvar xterm-modify-other-keys-terminal-list nil)
-
 (defun xterm--report-background-handler ()
   (let ((str "")
         chr)
@@ -595,21 +622,23 @@ We run the first FUNCTION whose STRING matches the input events."
     (when (memq 'modifyOtherKeys xterm-extra-capabilities)
       (terminal-init-xterm-modify-other-keys)))
 
+  ;; Unconditionally enable bracketed paste mode: terminals that don't
+  ;; support it just ignore the sequence.
+  (terminal-init-xterm-bracketed-paste-mode)
+
   (run-hooks 'terminal-init-xterm-hook))
 
 (defun terminal-init-xterm-modify-other-keys ()
   "Terminal initialization for xterm's modifyOtherKeys support."
-  ;; Make sure that the modifyOtherKeys state is restored when
-  ;; suspending, resuming and exiting.
-  (add-hook 'suspend-hook 'xterm-turn-off-modify-other-keys)
-  (add-hook 'suspend-resume-hook 'xterm-turn-on-modify-other-keys)
-  (add-hook 'kill-emacs-hook 'xterm-remove-modify-other-keys)
-  (add-hook 'delete-terminal-functions 'xterm-remove-modify-other-keys)
-  ;; Add the selected frame to the list of frames that
-  ;; need to deal with modify-other-keys.
-  (push (frame-terminal)
-      xterm-modify-other-keys-terminal-list)
-  (xterm-turn-on-modify-other-keys))
+  (send-string-to-terminal "\e[>4;1m")
+  (push "\e[>4m" (terminal-parameter nil 'tty-mode-reset-strings))
+  (push "\e[>4;1m" (terminal-parameter nil 'tty-mode-set-strings)))
+
+(defun terminal-init-xterm-bracketed-paste-mode ()
+  "Terminal initialization for bracketed paste mode."
+  (send-string-to-terminal "\e[?2004h")
+  (push "\e[?2004l" (terminal-parameter nil 'tty-mode-reset-strings))
+  (push "\e[?2004h" (terminal-parameter nil 'tty-mode-set-strings)))
 
 ;; Set up colors, for those versions of xterm that support it.
 (defvar xterm-standard-colors
@@ -727,29 +756,6 @@ versions of xterm."
     ;; right colors, so clear them.
     (clear-face-cache)))
 
-(defun xterm-turn-on-modify-other-keys ()
-  "Turn the modifyOtherKeys feature of xterm back on."
-  (let ((terminal (frame-terminal)))
-    (when (and (terminal-live-p terminal)
-              (memq terminal xterm-modify-other-keys-terminal-list))
-      (send-string-to-terminal "\e[>4;1m" terminal))))
-
-(defun xterm-turn-off-modify-other-keys (&optional frame)
-  "Temporarily turn off the modifyOtherKeys feature of xterm."
-  (let ((terminal (when frame (frame-terminal frame))))
-    (when (and (terminal-live-p terminal)
-               (memq terminal xterm-modify-other-keys-terminal-list))
-      (send-string-to-terminal "\e[>4m" terminal))))
-
-(defun xterm-remove-modify-other-keys (&optional terminal)
-  "Turn off the modifyOtherKeys feature of xterm for good."
-  (setq terminal (or terminal (frame-terminal)))
-  (when (and (terminal-live-p terminal)
-            (memq terminal xterm-modify-other-keys-terminal-list))
-    (setq xterm-modify-other-keys-terminal-list
-         (delq terminal xterm-modify-other-keys-terminal-list))
-    (send-string-to-terminal "\e[>4m" terminal)))
-
 (defun xterm-maybe-set-dark-background-mode (redc greenc bluec)
   ;; Use the heuristic in `frame-set-background-mode' to decide if a
   ;; frame is dark.