[R-SIG-Mac] Re.: Applescript window selection question

J ö rg Beyer Beyerj at students.uni-marburg.de
Sat Sep 8 00:45:43 CEST 2007


I don't have enough time to provide a complete (or even clever) solution,
but I can offer some tips and hints, based on R.app 1.21-pre (devel 4746)
with R 2.5.1 on OS X 10.4.10.

To start, have a look at R.app's AppleScript dictionary, and study the
object hierarchies and properties, if you haven't already. No guarantees,
though, dictionaries are known to be among of the weaker parts of
AppleScriptable applications.

> This is really an Applescript question, but I thought I would ask here.
> What I really want is a reliable way to source() in R a buffer in Emacs.
> How do you specify a certain window in the R interface using Applescript?
> I am trying to use the R gui from Emacs.  The code at the end does this,
> some of the time.
> The problem is that "tell window 1" addresses the window with focus in R, so
> this only works when the console has focus.  If the Quartz window or the
> Help window (or any other) has focus the Applescript fails.  This also
> usually, but not always fails after an exception is thrown in the gui (R
> error)
> The window order in Applescript is the order from front to back.  However, I
> have been getting errors trying to get a window from it's name, e.g.
>     set nn to (get window whose name contains "Con")

Next tip: The following stub works, if you have to address a specific window

tell application "R"
  set nn to (get every window whose name contains "Con")
  return properties of item 1 of nn -- just to demonstrate what happens
end tell

Note the 'every window' part, and note that you get a list returned, so you
have to use 'item # of' when you use 'nn'. May be also useful if you have
code that has to loop through a bunch of Quartz windows.

> This throws an error.  Even
> set wn to (get name of window 1)
> set nn to (get window whose name contains wn)
> Does not work.
> Thanks.
> -John
> In Emacs: 
> (defun R-source-buffer ()
>   (interactive)
>   (save-excursion
>     (let ((rbuf (current-buffer)))
>       (save-buffer-to-load-file "/tmp/tmp.R")
>       (shell-command "~/Common/Languages/Applescript/App/R01.app&")
>       ;;(kill-buffer "*Async Shell Command*"))
>       (pop-to-buffer rbuf))))
> ;;
> ;;  File name needs to be the same in the Applescript application
> ;;
> (defun save-buffer-to-load-file (fname)
>     (let ((ts (buffer-substring-no-properties (point-min) (point-max))))
>       (write-region (point-min) (point-max) fname)))
> In Applescript:
> tell application "R"
>     activate
>     tell application "System Events"
>         tell process "R"
>             tell window 1
>                 keystroke "source('/tmp/tmp.R')"
>                 keystroke return
>             end tell
>         end tell
>     end tell
> end tell

Sourcing files in R via AS is best done if you follow this pattern:

tell application "R"
  set thisFile to "POSIX-style/path/to/your/file"
  cmd "source( file=\"" & thisFile & "\")"
end tell

This works even in cases when the console isn't the active window; you don't
send the 'cmd' to the console window, the application itself is your target.
And note that you have to escape some of the quotation marks when you
assemble the 'source'-cmd.
I'm not sure if you have to use all the system events stuff, and you can
possibly omit the 'activate' command, too. Depends on the needs of your
workflow, I'd say. 

I'd also suggest to make use of try-on error-end try statements

tell application "R"
    set thisFile to "POSIX-style/path/to/your/file"
    cmd "source( file=\"" & thisFile & "\")"
  on error
      -- do something to address an error
  end try
end tell

Hope this helps, happy scripting ;-)




Jörg Beyer 
e-mail:  Beyerj -at- students.uni-marburg.de
PHILIPPS-University Marburg
Dept. of Psychology

More information about the R-SIG-Mac mailing list