Saturday, June 27, 2009

Emacs To Maya for Python Scripts

I modified the original Emacs To Maya by slavomir.kaslev.

Feb. 13, 2011.
Sending a command through file is a spec, not cutting corners. Due to Maya command port limitation we need to make a command small enough to have it within one packet (I don't know if the limitation still exisits in Maya 2011, anyone knows it?).

Feb. 6, 2011.
When I posted this entry two years ago, I emailed Slavomir and he replied
I am very happy that you find etom.el usefull. Etom.el is free

software, so you can do whatever you want with it to suit your needs.
so you can feel free to use this patch. Still please keep in mind that this is GPL licenced.

Jan. 23, 2011.
If you get error regarding replace-in-string, it's probably due to missing function on your emacs. you can find a replace-in-string implementation in find-files.el module, made by Robert Fenk.

And on Windows Vista,
commandPort -eo -n ":2222";
doesn't work. Execute
commandPort -eo -n "";

Tnanks Hajime!

This is not an authorized version by the original author/maintainer, and I only tested on Linux (Fedora 11, Maya 8.5, GNU Emacs 22.3.1)
last modified: Jul. 27, 2012

;;; etom.el --- Emacs to Maya communication

;; Copyright (C) 2007 Slavomir Kaslev

;; Author: Slavomir Kaslev <>
;; Maintainer: Slavomir Kaslev <>
;; Created: 17 Jun 2007
;; Version: etom.el 0.02 dated 07/07/03 at 16:45:51
;; Keywords: emacs, maya, mel

;; Modified the original script by Slavomir Kaslev to send Python scripts
;; Modified By: Koichi Tamura <>
;; Date: 28 Jun 2009

;; This file is NOT part of Emacs.
;; This program is free software; you can redistribute it and/or
;; modify it under the terms of the GNU General Public License
;; as published by the Free Software Foundation; either version 2
;; of the License, or (at your option) any later version.
;; This program is distributed in the hope that it will be useful,
;; but WITHOUT ANY WARRANTY; without even the implied warranty of
;; GNU General Public License for more details.
;; You should have received a copy of the GNU General Public License
;; along with this program; if not, write to the Free Software
;; Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
;; MA 02110-1301, USA.

;; Commentary:

;; This package is used for communication between emacs and Maya. For
;; example you can use it together with Shuji Narazaki's mel-mode to
;; send pieces of mel code to Maya and get the results back in emacs.

;; To use this, insert in your ~/.emacs file:
;; (add-hook
;;  'mel-mode-hook
;;  (lambda ()
;;    (require 'etom)
;;    (setq etom-default-host "localhost")
;;    (setq etom-default-port 2222)
;;    (local-set-key (kbd "C-c C-r") 'etom-send-region)
;;    (local-set-key (kbd "C-c C-c") 'etom-send-buffer)
;;    (local-set-key (kbd "C-c C-l") 'etom-send-buffer)
;;    (local-set-key (kbd "C-c C-z") 'etom-show-buffer)))
;; For Python
;; Add the following script after the above one.
;; (add-hook
;;  'python-mode-hook
;;  (lambda ()
;;    (require 'etom)
;;    (setq etom-default-host "localhost")
;;    (setq etom-default-port 2222)
;;    (local-set-key (kbd "C-c C-r") 'etom-send-region-py)
;;    (local-set-key (kbd "C-c C-c") 'etom-send-buffer-py)
;;    (local-set-key (kbd "C-c C-l") 'etom-send-buffer-py)
;;    (local-set-key (kbd "C-c C-z") 'etom-show-buffer)))

;;; Code:

(require 'comint)

(defcustom etom-default-host "localhost"
"Default name of the host on which Maya is running."
:type 'string
:group 'etom)

(defcustom etom-default-port 2222
"Default port number to connect to Maya."
:type 'integer
:group 'etom)

(defcustom etom-always-show t
"Non-nil means display etom-buffer after sending a command."
:type 'boolean
:group 'etom)

(defcustom etom-prompt-regexp "^\0$"
"Regexp which matches the Maya's prompt."
:type 'regexp
:group 'etom)

(defvar etom-buffer nil
"Buffer used for communication with Maya.")

(defun etom-show-buffer ()
"Make sure `etom-buffer' is being displayed."
(if (not (etom-connected))
(display-buffer etom-buffer))

(defun etom-hide-buffer ()
"Delete all windows that display `etom-buffer'."
(delete-windows-on etom-buffer))

(defun etom-connect ()
"Connect to Maya."
(setq comint-prompt-regexp etom-prompt-regexp)
(setq etom-buffer (make-comint "Maya" (cons etom-default-host etom-default-port)))
(set-process-query-on-exit-flag (get-buffer-process etom-buffer) nil)
(if etom-always-show
(comint-simple-send (get-buffer-process etom-buffer)
                 "def etom_pyexec(fname):\\n"
                 "  f = open(fname)\\n"
                 "  try:\\n"
                 "    c ='\\\\r\\\\n', '\\\\n')\\n"
                 "    try:\\n"
                 "      return str(eval(c))\\n"
                 "    except:\\n"
                 "      exec c in globals(), globals()\\n"
                 "  finally:\\n"
                 "    f.close()"

(defun etom-disconnect ()
"Disconnect from Maya and kill etom-buffer."
(if etom-buffer
(kill-buffer etom-buffer)))

(defun etom-connected ()
"Return non-nil if there is connection to Maya."
(comint-check-proc etom-buffer))

(defun etom-prompt-line ()
(forward-line 0)
(looking-at comint-prompt-regexp)))

(defun etom-wait-for-prompt (last-prompt)
(let ((prompt-found nil))
(while (not prompt-found)
(accept-process-output (get-buffer-process (current-buffer)))
(goto-char (point-max))
(setq prompt-found (and (etom-prompt-line) (not (= (count-lines (point-min) (point-max)) last-prompt)))))))

(defun etom-send-current-line ()
"Send current line to Maya."
(let ((start (save-excursion (beginning-of-line) (point)))
(end (save-excursion (end-of-line) (point))))
(etom-send-region start end)))

(defun etom-send-current-line-py ()
"Send current line to Maya as Python."
(let ((start (save-excursion (beginning-of-line) (point)))
(end (save-excursion (end-of-line) (point))))
(etom-send-region-py start end)))

(defun etom-send-region (start end &optional aspython)
"Send region to Maya."
(interactive "r")
(if (not (etom-connected))
(if etom-always-show
(let (
(tempfile (make-temp-file "etom-"))
(formatstr (if aspython "python(\"etom_pyexec('%s')\")" "source \"%s\";")))
(write-region start end tempfile)
;; send source(tempfile)
(with-current-buffer etom-buffer
(let ((last-prompt (count-lines (point-min) (point-max))))
(goto-char (point-max))
(comint-simple-send (get-buffer-process (current-buffer))
                   (format formatstr
                           (replace-in-string tempfile "\\\\" "\\\\\\\\" )))
(etom-wait-for-prompt last-prompt)
(delete-file tempfile)))))

(defun etom-send-region-py (start end)
"Send region to Maya as Python."
(interactive "r")
(etom-send-region start end t))

(defun etom-send-region-2 (start end)
"Send region to Maya."
(interactive "r")
(if (not (etom-connected))
(if etom-always-show
(comint-simple-send (get-buffer-process etom-buffer)
             (buffer-substring start end)))

(defun etom-send-buffer ()
"Send whole buffer to Maya."
(etom-send-region (point-min) (point-max)))

(defun etom-send-buffer-py ()
"Send whole buffer to Maya as Python."
(etom-send-region-py (point-min) (point-max)))

(provide 'etom)

;;; etom.el ends here

No comments: