nicholasehamilton / ggtern

Extension to ggplot2 for plotting ternary diagrams
www.ggtern.com
55 stars 14 forks source link

Automatic zooming with tern_limits()? #24

Open Deleetdk opened 8 years ago

Deleetdk commented 8 years ago

Often one has data that is only found in a small region of the total space. When this happens, often one wants to zoom into that particular region. This can be done with tern_limits(). However, it is currently only possible to specify the limits manually. Would it be possible to add an automatic zoom argument for tern_limits()?

By automatic, I mean so that it automatically zooms into the smallest possible triangle that contains all points. Probably, one would want to round to the nearest 5/10/20 on the axes though.

To find the limits, find the max values of the three variables. Then round these to the nearest desired number. This is easy to do with plyr's round_any(). Then set the smallest number to the second smallest number. Then use these numbers.

I note that the order of tern_limits() does not match the order of arguments in the ggtern(aes(...)) call. E.g. The first given to ggtern() is the second to tern_limits(). So one has to rearrange them. You may want to rearrange these for consistency, but it may break prior plots.

Here's an example. I use genomic admixture values from Bryc et al (2015)'s paper based on 23andme data. The data is here.

# libs --------------------------------------------------------------------
library(pacman)
p_load(plyr, psych, ggplot2, ggtern)

# data --------------------------------------------------------------------
d_23andme = read.csv("BryceAdmixNAEP.tsv", sep="\t", row.names=1)

# Ternary admix plots -----------------------------------------------------
#ternary admix plots like those in the admix paper

#normal plot
ggtern(d_23andme, aes(BlackAfricanAncestry, BlackAmericanAncestry, BlackEuropeanAncestry)) + geom_point()

#manually set limits
ggtern(d_23andme, aes(BlackAfricanAncestry, BlackAmericanAncestry, BlackEuropeanAncestry)) + geom_point() + tern_limits(.4, 1, .4)

#find max values
max_vals = describe(d_23andme[1:3])$max %>% #get max values
  `*`(100) %>% #to percent
  round_any(20, f = ceiling) #round to desired level

#set the lowest to the second lowest
max_vals[order(max_vals)[1]] = sort(max_vals)[2]

#back to fractions
max_vals = max_vals/100

#plot with automatic zoom
ggtern(d_23andme, aes(BlackAfricanAncestry, BlackAmericanAncestry, BlackEuropeanAncestry)) + geom_point() + tern_limits(max_vals[2], max_vals[1], max_vals[3])

aa_admix2 aa_admix