<p><div><div><div><div data-width="100" data-show-faces="false" data-send="true" data-layout="button_count" data-height="21" data-href="http://www.r-bloggers.com/dumbbells-get-a-little-gg-smarter/"></div></div><div><a data-url="http://www.r-bloggers.com/dumbbells-get-a-little-gg-smarter/" data-counturl="http://www.r-bloggers.com/dumbbells-get-a-little-gg-smarter/" data-count="horizontal" data-text="Dumbbells get a little gg-smarter?" class="twitter-share-button" data-via="rbloggers" href="https://twitter.com/share"></a></div><div></div></div><div></div></div>
<div>
(This article was first published on <strong><a href="http://data-steve.github.io/making-ggdumbbell-smarter/"> data_steve</a></strong>, and kindly contributed to <a rel="nofollow" href="http://www.r-bloggers.com/">R-bloggers)</a> </div>
<p><img alt="" src="http://i0.wp.com/data-steve.github.io/images/dumbbell.png?w=456" data-recalc-dims="1"></p>
<p>Bob Rubis <a target="_blank" href="https://twitter.com/@hrbrmstr">@hrbrmstr</a> recently has blogged several interesting posts [ <a target="_blank" href="https://rud.is/b/2016/04/12/beating-lollipops-into-dumbbells/">1</a>, <a target="_blank" href="https://rud.is/b/2016/04/17/ggplot2-exercising-with-ggalt-dumbbells/">2</a>] about making dumbbell plots with ggplot2 via his package <a target="_blank" href="https://cran.r-project.org/web/packages/ggalt/index.html">ggalt</a>. <a target="_blank" href="https://twitter.com/@Tylerrinker">@Tylerrinker</a> did some <a target="_blank" href="http://www.talkstats.com/showthread.php/29320-R-Graphics-Beautiful-graphics-thread?p=170173&viewfull=1#post170173">really nice work reproducing a Pew dumbbell plot back in early 2015</a>, which I found really helpful.</p>
<p>Seeing @hrbrmstr’s posts reminded me of a project I did about 8 months ago. I was mocking up a way to compare two entities on a set of factors. The mock-up ended up as what I now know is called a dumbbell plot. Seeing these several posts, I realized that they all had something in common which my mock-up didn’t share. Unlike the earlier examples of a dumbbell plot, in the context I was working, entities being compared could switch their relative rank on the x-axis.</p>
<p>Also, in addition to rank order changing, I wanted to highlight that some gaps, independent of their lengths, were more substantive/important than others. Both were fun challenges to incorporate into the dumbbell and something I hadn’t seen encoded in the other dumbbell plots.</p>
<p>To make things concrete, let’s use a working example. Say, there’s a coach who wants to know how her athlete Jessica compares along judges scores to her strongest competitor Francine on 5 track-n-field events. Because she’s savvy, the coach decides to graph these difference on one dumbbell graph. The coach really wants to make clear to Jessica which events Jessica’s stronger and weaker than her competitor Francine.</p>
<div>
<pre><code>pacman::p_load(dplyr, tidyr, ggplot2)
dat &lt;-data.frame(&quot;Jessica&quot; = c(8.6, 9.3, 9.34, 9.1, 9),
                 &quot;Francine&quot; = c(9.4, 8.88, 9.2, 9.24, 9.34),
                 &quot;Events&quot; = factor(1:5,labels=c(&quot;sprint&quot;, &quot;hurdles&quot;,&quot;javelin&quot;, &quot;discus&quot;, &quot;hi-jump&quot;)))
</code></pre>
</div>
<p>To make the information apparent, I encode relative rank and gap size in the graph using color and alpha levels, which are the main additions to previous dumbbell plots. The relative order (win/loss) within each sporting event is encoded by the colors green/red. The intensity with which the entity of interest (Jessica in our example) wins or loses is captured with the alpha level intensifying for greater gaps and lessening for smaller ones.</p>
<p>This use of alpha level is especially useful in cases were the statistic being compared may have some dispersion around it, such that faint alphas suggest the difference isn’t meaningful. And I like alpha here. I had tried varying the line width to encode intensity at first; though it did attract my eyes’ attention more to the more intense differences, I didn’t like how it ruined the symmetry in the visual aesthetic.</p>
<p>So here’s my version of a dumbbell function to create the graph above.</p>
<div>
<pre><code>ggdumbbell &lt;- function(d ,colors=c(&quot;green4&quot;,&quot;red3&quot;,&quot;brown&quot;) ,sz=17){
    nms &lt;- names(d);names(d) &lt;- c(&quot;xvar&quot;,&quot;yvar&quot;, &quot;fvar&quot;)
    df &lt;- d %>% dplyr::mutate(
                   abs_diff = abs(xvar-yvar),
                   pos_neg = sign(xvar-yvar),
                   midpoint = abs_diff/2,
                   clr = ifelse(pos_neg>0, colors[1], colors[2]) ) %>%
                 rowwise() %>%
                 mutate(xmin = min(xvar,yvar), xmax = max(xvar,yvar)) %>% ungroup

    df_tall &lt;- df %>%
        tidyr::gather(keys, values, -c(fvar, xmin, xmax, midpoint, pos_neg, abs_diff, clr)) %>%
        mutate(keys=ifelse(keys==&quot;xvar&quot;, nms[1], nms[2]))

    l &lt;-  as.character(df[[&quot;fvar&quot;]][as.integer(df[[&quot;fvar&quot;]])==max(as.integer(df[[&quot;fvar&quot;]]))])
    ll &lt;- if(d[1,1]&lt;d[1,2]) nms[1:2] else nms[2:1]

    ggplot(df_tall, aes(y=fvar, x=values) ) +
        geom_segment(data=df, aes(x=xmin, xend=xmax, y=fvar, yend=fvar, alpha=abs_diff)
                            , color=df$clr, size=3) +
        geom_point(color = colors[3], size=5.5)  +
        geom_point(shape=21, color = colors[3], size=4.8, aes(fill=keys))  +
        scale_fill_manual(values = c(&quot;white&quot;, colors[3]), guide=FALSE) + 
        theme_bw()  + theme(text=element_text(size=sz),legend.position=&quot;none&quot;, panel.grid = element_blank() )  +
        annotate(&quot;text&quot;
           , x = c(df[df$&quot;fvar&quot;==l,]$xmin,df[df$&quot;fvar&quot;==l,]$xmax)
           , y= c(df[df$&quot;fvar&quot;==l,]$fvar,df[df$&quot;fvar&quot;==l,]$fvar)
           , label=ll , color = colors[3], size=4.8 , vjust = 2.5) +
        labs(list(x=&quot;Values&quot;,y=nms[3])) +
        annotate(&quot;text&quot;, x=8.75, y=5
                 , label=&quot;Green/Red signifiesnhigher/lower performance.nn Color intensity signifiesnmagnitude of difference.&quot;
                 , color=colors[3], size=7, vjust = .75) 
}

ggdumbbell(dat) +
  ggtitle(&quot;Francine's performance against Jessica&quot;)
</code></pre>
</div>
<p>I’ll not pretend to have it packaged up as nicely as @hrbrmstr has in ggalt. He’s managed to set up his data and/or his function such that he doesn’t appear to need to have a wide and tall set of dataframes.</p>
<p>For me, a rather frustrating point about <code>geom_segment()</code> is how its <code>aes</code> handles the color arguments. It took me 2 hours of googling and fiddling to figure out that if you want the segments to vary by color where you actually define the colors, you need to have the color arg assigned outside the aes.</p>
<div>
<pre><code>p &lt;- ggplot(data=something) 

p + geom_segment( aes(x=a, xend=b, y=A) , color=color_vec)   # you control colors

p + geom_segment( aes(x=a, xend=b, y=A, color=color_vec) )   # color does sth else
</code></pre>
</div>
<p>Check out Hadley’s use of the color arg inside of aes at his <a target="_blank" href="http://docs.ggplot2.org/current/geom_segment.html">ggplot documentation page</a> to find another way to use color to distinguish between curves and segments. It’s the first example.</p>
<p><a target="_blank" class="twitter-share-button" data-via="data_steve" data-size="large" data-hashtags="rstats,ggplot2,datascience,dataviz" data-dnt="true" href="https://twitter.com/share">Tweet</a></p>
<p><div><div><div><div data-width="55" data-show-faces="false" data-send="true" data-layout="box_count" data-height="62" data-href="http://www.r-bloggers.com/dumbbells-get-a-little-gg-smarter/"></div></div><div><a data-url="http://www.r-bloggers.com/dumbbells-get-a-little-gg-smarter/" data-counturl="http://www.r-bloggers.com/dumbbells-get-a-little-gg-smarter/" data-count="vertical" data-text="Dumbbells get a little gg-smarter?" class="twitter-share-button" data-via="rbloggers" href="https://twitter.com/share"></a></div><div></div></div><div></div></div>
<div>
<div>To <strong>leave a comment</strong> for the author, please follow the link and comment on their blog: <strong><a href="http://data-steve.github.io/making-ggdumbbell-smarter/"> data_steve</a></strong>.</div>
<hr>
<a rel="nofollow" href="http://www.r-bloggers.com/">R-bloggers.com</a> offers <strong><a rel="nofollow" href="http://feedburner.google.com/fb/a/mailverify?uri=RBloggers">daily e-mail updates</a></strong> about <a title="The R Project for Statistical Computing" rel="nofollow" href="http://www.r-project.org/">R</a> news and <a title="R tutorials" rel="nofollow" href="http://www.r-bloggers.com/?s=tutorial">tutorials</a> on topics such as: <a title="Data science" rel="nofollow" href="http://www.r-bloggers.com/?s=data%20science">Data science</a>, <a title="Big Data" rel="nofollow" href="http://www.r-bloggers.com/?s=Big%20Data">Big Data, <a title="R jobs" rel="nofollow" href="http://www.r-users.com/">R jobs</a>, visualization (<a title="ggplot and ggplot2 tutorials" rel="nofollow" href="http://www.r-bloggers.com/?s=ggplot2">ggplot2</a>, <a title="Boxplots using lattice and ggplot2 tutorials" rel="nofollow" href="http://www.r-bloggers.com/?s=boxplot">Boxplots</a>, <a title="Maps and gis" rel="nofollow" href="http://www.r-bloggers.com/?s=map">maps</a>, <a title="Animation in R" rel="nofollow" href="http://www.r-bloggers.com/?s=animation">animation</a>), programming (<a title="RStudio IDE for R" rel="nofollow" href="http://www.r-bloggers.com/?s=RStudio">RStudio</a>, <a title="Sweave and literate programming" rel="nofollow" href="http://www.r-bloggers.com/?s=sweave">Sweave</a>, <a title="LaTeX in R" rel="nofollow" href="http://www.r-bloggers.com/?s=LaTeX">LaTeX</a>, <a title="SQL and databases" rel="nofollow" href="http://www.r-bloggers.com/?s=SQL">SQL</a>, <a title="Eclipse IDE for R" rel="nofollow" href="http://www.r-bloggers.com/?s=eclipse">Eclipse</a>, <a title="git and github, Version Control System" rel="nofollow" href="http://www.r-bloggers.com/?s=git">git</a>, <a title="Large data in R using Hadoop" rel="nofollow" href="http://www.r-bloggers.com/?s=hadoop">hadoop</a>, <a title="Web Scraping of google, facebook, yahoo, twitter and more using R" rel="nofollow" href="http://www.r-bloggers.com/?s=Web+Scraping">Web Scraping</a>) statistics (<a title="Regressions and ANOVA analysis tutorials" rel="nofollow" href="http://www.r-bloggers.com/?s=regression">regression</a>, <a title="principal component analysis tutorial" rel="nofollow" href="http://www.r-bloggers.com/?s=PCA">PCA</a>, <a title="Time series" rel="nofollow" href="http://www.r-bloggers.com/?s=time+series">time series</a>, <a title="finance trading" rel="nofollow" href="http://www.r-bloggers.com/?s=trading">trading</a>) and more...
<img height="1" alt="" width="1" src="http://feeds.feedburner.com/~r/RBloggers/~4/8T9MFrr3FuA"></a></div>