From rmh at temple.edu  Wed Sep  6 04:30:31 2006
From: rmh at temple.edu (Richard M. Heiberger)
Date: Tue,  5 Sep 2006 22:30:31 -0400 (EDT)
Subject: [Rd] Two submitted packages
Message-ID: <20060905223031.BHI71699@po-d.temple.edu>

Deepayan wrote:

> > xyplot(y ~ x | a,
> >        data=tmp, ylim=c(1.5,4.5),
> >        par.settings = list(clip = list(panel = "off")),
> >        layout=c(2,2))
> 
> I'm curious to know why this functionality is not enough.


## 1. Here is a more realistic example.

tmp <- data.frame(x=1:5, y=1:5, a=factor(c(1,1,1,1,1), levels=1:4))

## This gives what I want.
## It looks like the upViewport/downViewport sequence is the control I
## should be using.  If this is a stable sequence, it answers my needs.
xyplot(y ~ x,
       data=tmp, ylim=c(1.5,4.5),
       panel=function(...) {
          panel.xyplot(...)
            upViewport()
            downViewport(trellis.vpname("panel",
                                        row = 1, column = 1, clip.off = TRUE))
          panel.axis(side="right", outside=TRUE)
       },
       layout=c(2,2),
       main="right axis visible by control, points clipped by default")

## If I turned off clipping at the top, I would get the unwanted points
## plotted outside the figure region.
xyplot(y ~ x,
       data=tmp, ylim=c(1.5,4.5),
       par.settings = list(clip = list(panel = "off")),
       panel=function(...) {
          panel.xyplot(...)
          panel.axis(side="right", outside=TRUE)
       },
       layout=c(2,2),
       main="right axis visible by control, points not clipped")


## this is what happens if I don't do any control of clipping
xyplot(y ~ x,
       data=tmp, ylim=c(1.5,4.5),
       panel=function(...) {
          panel.xyplot(...)
          panel.axis(side="right", outside=TRUE)
       },
       layout=c(2,2),
       main="right axis invisible by clipping, points clipped by default")


## This doesn't work, but it illustrates the syntax I would like.
xyplot(y ~ x,
       data=tmp, ylim=c(1.5,4.5),
       panel=function(...) {
          panel.xyplot(...)
          panel.axis(side="right", outside=TRUE, clip="off")
       },
       layout=c(2,2),
       main="right axis visible by control, points clipped by default")




## 2
> Unfortunately, there is currently no easy way to find out which column
> and row the current panel occupies. I plan to make some changes before
> R 2.4.0 is released that should expose that information, so please try
> again in a few weeks.

The way I have been using is to back up the calling sequence and
use statements like
{
    ## This loop is needed because
    ##    console usage has i=2,
    ##    Rcmdr script window has i=5,
    ##    Rcmdr justDoIt has i=20
    for (i in seq(2, length=30)) {
      sf2 <- sys.frame(i)
      column.tmp <- try(get("column", pos=sf2), silent=TRUE)
      if (class(column.tmp) != "try-error") break
    }
    if (class(column.tmp) == "try-error")
      stop("panel.interaction2wt is too deeply nested in the system stack.")
    row <- get("row", pos=sf2)
    column <- get("column", pos=sf2)
    cols.per.page <- get("cols.per.page", pos=sf2)
    rows.per.page <- get("rows.per.page", pos=sf2)
  }

## A cleaner way would be preferable.  Will the above stay valid?  The
## need for a loop to find out how far up the calling sequence to go
## caught me by surprise.  I don't understand why generating commands
## the way Rcmdr does it should have an effect on the depth of the
## calling sequence.




[Rd] Two submitted packages
Richard M. Heiberger