Search code examples
rheatmaplevelplot

Calendar Heatmap: Colors not as specified


I'm using agstudy's modification of calendar heatmap (discussion and source GitHub)

In general, the code works very fine but I'm having trouble getting my color code to work. Example

In the example shown, the first 3 weeks should be colored red and the 4th blue. Altogether this sequence should repeat 6 times, i.e. there should be 6 weeks colored in blue (every 4th).

In order to achieve my color code I load a list of colors in hex code from a file and name it 'user':

col.sty <- switch(color,
'user'=data_2$colorMicro,
'r2b'=c("#0571B0", "#92C5DE", "#F7F7F7", "#F4A582", "#CA0020"), #red to blue                                                                               
'r2g'=c("#D61818", "#FFAE63", "#FFFFBD", "#B5E384")  , #red to green
'w2b'=c("#045A8D", "#2B8CBE", "#74A9CF", "#BDC9E1", "#F1EEF6"),   #white to blue
'b2w'=grey.colors(5) )## black to white
# assign("col.sty", get(color))
calendar.pal <- colorRampPalette((col.sty), space = "rgb")

The content of data_2 is:

colorMicro
#CC0000
#CC0000
#CC0000
#00CCFF
#CC0000
#CC0000
#CC0000
#00CCFF
#CC0000
#CC0000
#CC0000
#00CCFF
#CC0000
#CC0000
#CC0000
#00CCFF
#CC0000
#CC0000
#CC0000
#00CCFF
#CC0000
#CC0000
#CC0000
#00CCFF

These are 24 color values for the 24 weeks I want to represent in the heatmap. The variable ncolors is set to 24 and cuts is set to ncolors-1.

I've slightly changed my levelplot settings compared to the code from agstudy.

# major plot ------------------------------------------------------------------
 p <- levelplot(value~woty*dotw | yr, data=dat, border = "black",
            layout = c(1, nyr%%7),
            col.regions = calendar.pal(ncolors),
            aspect='iso',
            between = list(x=0, y=c(1,1)),
            strip=TRUE,
            main =varname, 
            panel = function(x,y,z,...) {
              panel.levelplot(x,y,z,...)
              ll <- list(...)
              at = pretty(dat$pvalue)
              ind.pch <- cut(dat$pvalue, at, include.lowest = TRUE, labels = FALSE)
              pch.symbols <- pch.symbol[ind.pch]
              subscripts <- ll$subscripts
              x <- x[subscripts]
              y <- y[subscripts]
              pch.symbols <-  pch.symbols[subscripts]
              a=ifelse(dat$pvalue==0,15,ifelse(dat$pvalue==1,16,ifelse(dat$pvalue==2,17,ifelse(dat$pvalue==3,18,ifelse(dat$pvalue==4,25,ifelse(dat$pvalue==5,10,ifelse(dat$pvalue==6,65,ifelse(dat$pvalue==7,66,ifelse(dat$pvalue==67,S,NA)))))))))
              b=ifelse(dat$pvalue==0,"blue1",ifelse(dat$pvalue==1,"darkorange4",ifelse(dat$pvalue==2,"red",ifelse(dat$pvalue==3,"seashell4",ifelse(dat$pvalue==4,"magenta",ifelse(dat$pvalue==5,"limegreen",ifelse(dat$pvalue>5,'yellow','black')))))))
              panel.xyplot(x, y,fill =col.symbol ,col.symbol =b,
                           pch = a, cex=cex.symbol,
                           ,  ...)
              calendar.division(...)  
            },
            scales= scales,
            cuts = ncolors-1,
            colorkey= list(at=seq(from=1, to=24, by=1), col = calendar.pal(ncolors), width = 0.6, height = 0.5),
            xlim =extendrange(dat$woty,f=0.01),
            xlab="",ylab="",
            ylim=extendrange(dat$dotw,f=0.1),
            subscripts=TRUE,
            par.settings = calendar.theme)
  p
}

I can't find out why the colors are shifted and don't match the intended color code. Does anyone have an idea what could be the reason?


Solution

  • Finally, I've found out how it works:

    In my first try I assigned the days of each week an individual number in ascending order from 1 to 24. I.e. the values of the days of week one were set to 1, the days of week two to 2 and so on. The list colorMicro contained 24 colors that were supposed to correspond to the individual weeks. The list contained colors multiple times.

    In my second try I assigned all days with the same color the same number. At the same time I put the corresponding colors in the list colorMicro. This way each color appears only once in the list and in the same order as the numbers appear in the calendar. The variable ncolors I set to a large number and now everything works as desired. Example

    The first way was easier for me in view of the data generation outside of R but for some reason it doesn't work. Knowing this fact, the second way is easy as well and leads to proper plotting behavior. Now it's possible to assign predefined colors to each day or week at free will, which is what I need. Maybe this is useful for others too.