class: middle, inverse .leftcol30[ <center> <img src="https://eda.seas.gwu.edu/images/logo.png" width=250> </center> ] .rightcol70[ # Week 10: .fancy[Polishing Charts] ###
EMSE 4572 / 6572: Exploratory Data Analysis ###
John Paul Helveston ###
October 30, 2024 ] --- class: inverse # .center[.fancy[.blue[Tip of the week]]] ### .center[Ever wondered what colors look like _before_ you plot them?] -- Use `scales::show_col()` to preview them .leftcol60[.code60[ Example: ``` r colors <- c('lightblue', 'sienna', 'forestgreen', '#eae9ea') scales::show_col(colors) ``` ]] -- .rightcol40[ <img src="figs/unnamed-chunk-2-1.png" width="360" style="display: block; margin: auto;" /> ] --- ## Today's data ``` r wildlife_impacts <- read_csv(here::here('data', 'wildlife_impacts.csv')) federal_spending <- read_csv(here::here('data', 'federal_spending_long.csv')) milk_production <- read_csv(here::here('data', 'milk_production.csv')) lotr_words <- read_csv(here::here('data', 'lotr_words.csv')) msleep <- read_csv(here::here('data', 'msleep.csv')) ``` ## New (?) package: ``` r install.packages('hrbrthemes') ``` --- class: inverse, middle # Week 10: .fancy[Polishing Charts] ### 1. Scales ### 2. Annotations ### BREAK ### 3. Colors ### 4. Fonts ### 5. qmd tricks --- class: inverse, middle # Week 10: .fancy[Polishing Charts] ### 1. .orange[Scales] ### 2. Annotations ### BREAK ### 3. Colors ### 4. Fonts ### 5. qmd tricks <!-- Much of the content on adjusting the y axis came from Andrew Heiss's course slides: https://datavizf17.classes.andrewheiss.com/class/06-class/ --> --- ## When is it okay to to truncate an axis? .leftcol[ - **When small movements matter** ] -- .rightcol[ <img src="figs/us_gdp-1.png" width="360" style="display: block; margin: auto;" /> <img src="figs/us_gdp_trimmed-1.png" width="360" style="display: block; margin: auto;" /> ] --- ## When is it okay to to truncate an axis? .leftcol[ - When small movements matter - **When zero values are impossible** ] -- .rightcol[ <img src="figs/us_mpg0-1.png" width="360" style="display: block; margin: auto;" /> <img src="figs/us_mpg-1.png" width="360" style="display: block; margin: auto;" /> ] --- ## When is it okay to to truncate an axis? .leftcol[ - When small movements matter - When zero values are impossible - **When it's normal / a convention** ] -- .rightcol[ <center> <img src="images/linkedin_stocks.png"> </center> ] --- ## When is it okay to to truncate an axis? .leftcol[ - When small movements matter - When zero values are impossible - When it's normal / a convention - **.red[Never on a bar chart]** ] .rightcol[ <center> <img src="images/fox_news_bars.jpeg"> </center> ] --- class: inverse, middle, center # You are most sensitive to changes<br>in angles close to 45 degrees --- class: center ## You are most sensitive to changes<br>in angles close to 45 degrees .cols3[ .center[Good scaling] <img src="figs/unnamed-chunk-9-1.png" width="432" style="display: block; margin: auto;" /> ] .cols3[ .center[Y scale too large] <img src="figs/unnamed-chunk-10-1.png" width="432" style="display: block; margin: auto;" /> ] .cols3[ .center[X scale too large] <img src="figs/unnamed-chunk-11-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## You are most sensitive to changes<br>in angles close to 45 degrees .leftcol30[ Bad <img src="figs/unnamed-chunk-12-1.png" width="288" /> ] .rightcol70[ Better <img src="figs/unnamed-chunk-13-1.png" width="756" /> Set image dimensions in R chunk header: ````markdown ```{r} #| fig.width: 5 #| fig.height: 3.1 plot ``` ```` ] --- class: inverse background-color: #000000 ### .center[Consider setting dimensions to "Golden Ratio" (1 : 1.618)] <br> .leftcol[ <center> <img src="images/golden_ratio.jpg"> </center> ] -- .rightcol[.center[ Approx. to golden ratio: width | height -------|--------- 5 | 3.1 or 3 6 | 3.7 or 4 7 | 4.3 <br> [Also check out Donald Duck in Mathemagic Land](https://youtu.be/U_ZHsk0-eF0?t=512) ]] --- ## Adjust axes with `scale_*` functions .leftcol35[ Continous variables ``` r scale_x_continuous() scale_y_continuous() ``` Discrete variables ``` r scale_x_discrete() scale_y_discrete() ``` Others ``` r scale_x_log10() scale_y_log10() scale_x_date() ``` ] -- .rightcol65[ Common arguments for **continuous** variables ``` r scale_y_continuous( # Set the lower & upper boundaries limits = c(lower, upper), # Explicitly set the break points breaks = c(break1, break2, etc.) # Adjust the axis so bars start at 0 expand = expand_scale(mult = c(0, 0.05)) ) ``` ] --- ## Adjusting **continuous** scales .leftcol55[.code70[ ``` r milk_bars <- milk_production %>% filter(year == 2017) %>% arrange(desc(milk_produced)) %>% slice(1:10) %>% mutate( milk_produced = milk_produced / 10^9, state = fct_reorder(state, milk_produced)) %>% ggplot() + geom_col(aes(x = milk_produced, y = state)) + theme_minimal_vgrid(font_size = 18) + labs(x = 'Milk produced (billions of lbs)', y = 'State') milk_bars ``` ]] .rightcol45[ <img src="figs/unnamed-chunk-18-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## Adjusting **continuous** scales .leftcol55[.code70[ ``` r milk_bars + * scale_x_continuous( * breaks = c(0, 15, 30, 45), * limits = c(0 , 45), * expand = expand_scale(mult = c(0, 0.05))) ``` ]] .rightcol45[ <img src="figs/unnamed-chunk-19-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## Adjusting **discrete** scales .leftcol55[.code70[ ``` r milk_bars + * scale_y_discrete( * breaks = c('California', 'Wisconsin', 'Idaho')) ``` ]] .rightcol45[ <img src="figs/unnamed-chunk-20-1.png" width="432" style="display: block; margin: auto;" /> ] --- .leftcol[.code70[ ## Adjusting **log** scales Regular scaling ``` r plot <- ggplot(msleep) + geom_point(aes(x = brainwt, y = bodywt)) + theme_half_open(font_size = 20) + labs(x = 'Brain weight (kg)', y = 'Body weight (kg)') plot ``` ]] .rightcol[ <img src="figs/unnamed-chunk-21-1.png" width="360" style="display: block; margin: auto;" /> ] --- .leftcol[.code70[ ## Adjusting **log** scales Log scaling ``` r plot + * scale_x_log10() + * scale_y_log10() + labs(x = 'Log brain weight (kg)', y = 'Log body weight (kg)') ``` ] Log-log relationship: `$$y = x^n$$` `$$\log(y) = n\log(x)$$` ] .rightcol[ <img src="figs/unnamed-chunk-22-1.png" width="360" style="display: block; margin: auto;" /> <img src="figs/unnamed-chunk-23-1.png" width="360" style="display: block; margin: auto;" /> ] --- .leftcol[.code70[ ## Example from Mini Project 2 Regular scaling ``` r plot <- transit_cost %>% filter(!is.na(length)) %>% filter(length < 2500) %>% mutate(cost = as.numeric(real_cost)) %>% * ggplot(aes(x = length, y = cost)) + geom_point() + geom_smooth(method = 'lm', se = FALSE) + theme_half_open(font_size = 20) + labs(x = "Length of Proposed Line", y = "Real Cost in Millions USD") plot ``` ]] .rightcol[ <img src="figs/unnamed-chunk-24-1.png" width="360" style="display: block; margin: auto;" /> ] --- .leftcol[ ## Example from Mini Project 2 Log scaling .code70[ ``` r plot + * scale_x_log10() + * scale_y_log10() + labs(x = 'Log length of proposed line', y = 'Log cost') ``` ] Log-log relationship: `$$y = x^n$$` `$$\log(y) = n\log(x)$$` ] .rightcol[ <img src="figs/unnamed-chunk-25-1.png" width="360" style="display: block; margin: auto;" /> <img src="figs/unnamed-chunk-26-1.png" width="360" style="display: block; margin: auto;" /> ] --- class: inverse, center, middle # Date scales can be confusing --- class: center # What's wrong with this chart? <center> <img src="images/utility_bill_1.png" width=700> </center> --- class: center # What's wrong with this chart? <center> <img src="images/utility_bill_3.png" width=700> </center> --- class: center # What's wrong with this chart? <center> <img src="images/utility_bill_4.png" width=700> </center> --- class: center # What's wrong with this chart? <center> <img src="images/utility_bill_5.png" width=700> </center> --- .leftcol[.code70[ ## Adjusting **date** scales Summarise the data ``` r *library(lubridate) plot <- wildlife_impacts %>% filter(incident_year == 2016) %>% count(operator, incident_date) %>% * mutate(incident_date = ymd(incident_date)) %>% ggplot() + geom_col( aes(x = incident_date, y = n, color = operator)) + facet_wrap(~operator, ncol = 1) + theme_minimal_grid(font_size = 16) + panel_border() + theme(legend.position = 'none') + labs(x = 'Incident date (2016)', y = 'Number of incidents') plot ``` ]] .rightcol[ <br> <img src="figs/unnamed-chunk-27-1.png" width="504" style="display: block; margin: auto;" /> ] --- .leftcol[.code70[ ## Adjusting **date** scales ``` r plot + * scale_x_date( * date_breaks = '1 month', * date_labels = '%b') ``` ]] .rightcol[ <br> <img src="figs/unnamed-chunk-28-1.png" width="504" style="display: block; margin: auto;" /> ] --- ## Adjusting **date** scales ``` r scale_x_date( date_breaks = '1 month', date_labels = '%b') ``` .leftcol[ ``` r date_breaks = '1 month' ``` - '1 day' - '10 days' - '1 month' - '3 months' - '1 year' - '3 years' ] .rightcol[ ``` r date_labels = '%b' ``` Example date: March 04, 2020 - `%Y` = 2020 - `%y` = 20 - `%B` = March - `%b` = Mar - `%D` = 03/04/2020 - `%d` = 03 ] --- class: inverse, center, middle ## Use **scales** library to modify scale **text** --- ## `scales` converts numbers to formatted characters ``` r scales::comma(200000) ``` ``` #> [1] "200,000" ``` ``` r scales::dollar(200000) ``` ``` #> [1] "$200,000" ``` ``` r scales::percent(0.5) ``` ``` #> [1] "50%" ``` --- ## Use **scales** library to modify scale text .leftcol[.code70[ ``` r federal_spending %>% filter(year == 2017) %>% mutate( department = fct_reorder( department, rd_budget)) %>% ggplot() + geom_col(aes(x = rd_budget, y = department)) + scale_x_continuous( expand = expand_scale(mult = c(0, 0.05))) + theme_minimal_vgrid(font_size = 16) + labs(x = 'Department', y = 'R&D spending ($ Millions)') ``` ]] .rightcol[ <img src="figs/unnamed-chunk-33-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## Use **scales** library to modify scale text .leftcol[.code70[ ``` r federal_spending %>% filter(year == 2017) %>% mutate( department = fct_reorder( department, rd_budget)) %>% ggplot() + geom_col(aes(x = rd_budget, y = department)) + scale_x_continuous( * labels = scales::comma, expand = expand_scale(mult = c(0, 0.05))) + theme_minimal_vgrid(font_size = 16) + labs(x = 'Department', y = 'R&D spending ($ Millions)') ``` ]] .rightcol[ <img src="figs/unnamed-chunk-34-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## Use **scales** library to modify scale text .leftcol[.code70[ ``` r federal_spending %>% filter(year == 2017) %>% mutate( department = fct_reorder( department, rd_budget)) %>% ggplot() + geom_col(aes(x = rd_budget, y = department)) + scale_x_continuous( * labels = scales::dollar, expand = expand_scale(mult = c(0, 0.05))) + theme_minimal_vgrid(font_size = 16) + labs(x = 'Department', y = 'R&D spending ($ Millions)') ``` ]] .rightcol[ <img src="figs/unnamed-chunk-35-1.png" width="432" style="display: block; margin: auto;" /> ] --- class: middle, center # Check out this guide to scales: https://ggplot2tor.com/scales --- class: inverse
−
+
15
:
00
## Your turn .leftcol40[ Adjust the scales in the code chunk provided to match the chart on the slides. ] .rightcol60[ <img src="figs/wildlife_costs-1.png" width="504" style="display: block; margin: auto;" /> ] --- class: inverse, middle # Week 10: .fancy[Polishing Charts] ### 1. Scales ### 2. .orange[Annotations] ### BREAK ### 3. Colors ### 4. Fonts ### 5. qmd tricks <!-- Most of this content came from this presentation: https://designing-ggplots.netlify.com/#1 --> --- class: center, middle, inverse # Text is usually the single most important component on your chart --- class: middle <center> <img src="images/eye_tracking.gif" width=900> </center> .font80[Michelle Borkin, et al. (2015) [Beyond Memorability: Visualization Recognition and Recall](https://ieeexplore.ieee.org/document/7192646)] --- class: center .leftcol60[ <center> <img src="images/titles_matter.jpg" width=100%> </center> ] .rightcol40[ ## Titles matter <br><br><br><br><br><br><br><br><br><br><br> Source: https://www.reddit.com/r/dataisugly/comments/odk65x/this_was_not_the_right_headline_to_go_along_with ] --- .leftcol60[ <center> <img src="images/protein.png" width=100%> </center> ] .rightcol40[ ## Good annotations should tell a story <br><br><br><br><br><br><br><br><br><br> Source: https://ourworldindata.org/less-meat-or-sustainable-meat ] --- ``` r labs( x = 'Year', y = 'Cost of incident repairs ($ millions)', title = 'Repair costs of aircraft impacts with wildlife', subtitle = 'Top 4 airlines', caption = 'Source: https://wildlife.faa.gov/home') ``` <img src="figs/unnamed-chunk-39-1.png" width="504" style="display: block; margin: auto;" /> --- Use mapped variables in `aes()` in `labs()` .leftcol60[.code70[ ``` r milk_production %>% filter(year %in% c(1970, 2017)) %>% group_by(year, region) %>% summarise(milk_produced = sum(milk_produced) / 10^9) %>% ungroup() %>% mutate( region = fct_reorder2(region, year, desc(milk_produced))) %>% ggplot() + geom_col( * aes(x = milk_produced, * y = region, fill = as.factor(year)), position = "dodge") + scale_x_continuous(expand = expansion(mult = c(0, 0.05))) + theme_minimal_vgrid() + labs( * x = 'Milk produced (billions lbs)', * y = 'Region', title = 'Milk production by region', subtitle = '1970 & 2017') ``` ]] .rightcol40[ <img src="figs/unnamed-chunk-40-1.png" width="504" style="display: block; margin: auto;" /> ] --- Use mapped variables in `aes()` in `labs()` .leftcol60[.code70[ ``` r milk_production %>% filter(year %in% c(1970, 2017)) %>% group_by(year, region) %>% summarise(milk_produced = sum(milk_produced) / 10^9) %>% ungroup() %>% mutate( region = fct_reorder2(region, year, desc(milk_produced))) %>% ggplot() + geom_col( aes(x = milk_produced, y = region, * fill = as.factor(year)), position = "dodge") + scale_x_continuous(expand = expansion(mult = c(0, 0.05))) + theme_minimal_vgrid() + labs( x = 'Milk produced (billions lbs)', y = 'Region', title = 'Milk production by region', subtitle = '1970 & 2017', * fill = "Year") ``` ]] .rightcol40[ <img src="figs/unnamed-chunk-41-1.png" width="504" style="display: block; margin: auto;" /> ] --- class: center, middle, inverse # Legends suck --- class: center # Legends suck .leftcol[ ### Legends require look-up task <img src="figs/milk_region_line-1.png" width="540" style="display: block; margin: auto;" /> ] -- .rightcol[ ### Direct labeling is much better <img src="figs/milk_region_line_label-1.png" width="504" style="display: block; margin: auto;" /> ] --- class: center # Legends suck .leftcol[ ### Legends require look-up task <img src="figs/fed_spending_legend-1.png" width="504" style="display: block; margin: auto;" /> ] -- .rightcol[ ### Direct labeling is much better <img src="figs/fed_spending_annotate-1.png" width="504" style="display: block; margin: auto;" /> ] --- ## Use `annotate()` to add text to chart .leftcol60[.code70[ ``` r dod_spending <- ggplot(federal_spending_summary) + geom_area(aes(x = year, y = rd_budget, fill = department)) + * annotate(geom = 'text', x = 1995, y = 85, * label = 'Other', size = 6, color = 'black') + * annotate(geom = 'text', x = 1995, y = 25, * label = 'DOD', size = 6, color = 'white') + scale_y_continuous( expand = expand_scale(mult = c(0, 0.05))) + scale_fill_manual(values = c('grey', 'sienna')) + theme_minimal_hgrid() + * theme(legend.position = 'none') + labs(x = NULL, y = 'R&D Budget ($ Billions)', title = 'Federal R&D spending, 1976 - 2017', subtitle = 'Source: AAAS Historical Trends') dod_spending ``` ]] .rightcol40[ <br> <img src="figs/unnamed-chunk-43-1.png" width="504" style="display: block; margin: auto;" /> ] --- ## Use `geom_text()` to add text to chart .leftcol60[.code70[ ``` r dod_spending <- ggplot(federal_spending_summary) + geom_area(aes(x = year, y = rd_budget, fill = department)) + * geom_text( * data = data.frame(x = 1995, y = 85, label = 'Other'), * aes(x = x, y = y, label = label), * size = 6, color = 'black') + * geom_text( * data = data.frame(x = 1995, y = 25, label = 'DOD'), * aes(x = x, y = y, label = label), * size = 6, color = 'white') + scale_y_continuous( expand = expand_scale(mult = c(0, 0.05))) + scale_fill_manual(values = c('grey', 'sienna')) + theme_minimal_hgrid() + theme(legend.position = 'none') + labs(x = NULL, y = 'R&D Budget ($ Billions)', title = 'Federal R&D spending, 1976 - 2017', subtitle = 'Source: AAAS Historical Trends') dod_spending ``` ]] .rightcol40[ <br> <img src="figs/unnamed-chunk-44-1.png" width="504" style="display: block; margin: auto;" /> ] --- ### Use `geom_label()` to add text to chart **with a background** .leftcol60[.code70[ ``` r dod_spending <- ggplot(federal_spending_summary) + geom_area(aes(x = year, y = rd_budget, fill = department)) + * geom_label( data = data.frame(x = 1995, y = 85, label = 'Other'), aes(x = x, y = y, label = label), size = 6) + * geom_label( data = data.frame(x = 1995, y = 25, label = 'DOD'), aes(x = x, y = y, label = label), * size = 6, fill = "black", color = "white") + scale_y_continuous( expand = expand_scale(mult = c(0, 0.05))) + scale_fill_manual(values = c('grey', 'sienna')) + theme_minimal_hgrid() + theme(legend.position = 'none') + labs(x = NULL, y = 'R&D Budget ($ Billions)', title = 'Federal R&D spending, 1976 - 2017', subtitle = 'Source: AAAS Historical Trends') dod_spending ``` ]] .rightcol40[ <br> <img src="figs/unnamed-chunk-45-1.png" width="504" style="display: block; margin: auto;" /> ] --- ### Use `geom_curve()` + `geom_label()` to direct attention .leftcol60[.code70[ ``` r label <- "The Dept. of Defense R&D Budget has made up nearly half of all federal R&D spending" dod_spending + * geom_curve( * data = data.frame( * x = 1981, xend = 1987, y = 160, yend = 25), * mapping = aes(x = x, xend = xend, y = y, yend = yend), * color = 'grey75', size = 0.5, curvature = 0.1, * arrow = arrow(length = unit(0.01, "npc"), * type = "closed")) + geom_label( data = data.frame(x = 1977, y = 160, label = label), mapping = aes(x = x, y = y, label = label), hjust = 0, lineheight = 0.8) ``` ]] .rightcol40[ <img src="figs/unnamed-chunk-46-1.png" width="504" style="display: block; margin: auto;" /> ] --- ## Use `annotate()` to direct attention Use `geom = "rect"` for box, `geom = "text"` for label .leftcol60[.code70[ ``` r ggplot(mpg, aes(x = displ, y = hwy)) + geom_point( aes(fill = as.factor(cyl)), color = 'white', alpha = 0.8, size = 3.5, shape = 21) + * annotate(geom = "rect", xmin = 5, xmax = 7.5, ymin = 21, ymax = 28, fill = "grey55", alpha = 0.2) + * annotate(geom = "text", x = 5, y = 29, label = "Hybrid vehicles", hjust = 0, size = 5) + theme_half_open(font_size = 15) + labs(x = "Engine displacement", y = "Fuel efficiency (mpg)", fill = '# cylinders', title = "Vehicle fuel efficiency vs. engine displacement", caption = "Source: U.S. EPA.") ``` ]] .rightcol40[ <img src="figs/unnamed-chunk-47-1.png" width="504" style="display: block; margin: auto;" /> ] --- ## Find where to put annotations with [`ggannotate`](https://github.com/MattCowgill/ggannotate) .leftcol65[ Install: ``` r remotes::install_github("mattcowgill/ggannotate") ``` Use: ``` r library(ggannotate) plot <- ggplot(mpg) + geom_point(aes(x = displ, y = hwy, color = as.factor(cyl))) + theme_half_open() *ggannotate(plot) ``` ] --- class: inverse
−
+
20
:
00
## Your turn .leftcol[ Use the `lotr_summary` data frame to create the following chart. Hints: - For the `geom_label()`, use these points: - `x = 0.6` - `y = 2100` - For the `geom_curve()`, use these points: - `x = 1.2` - `xend = 1` - `y = 1300` - `yend = 200` ] .rightcol[ <img src="figs/lotr_bars-1.png" width="540" style="display: block; margin: auto;" /> ] --- class: inverse, center
−
+
05
:
00
# Intermission --- class: inverse, middle # Week 10: .fancy[Polishing Charts] ### 1. Scales ### 2. Annotations ### BREAK ### 3. .orange[Colors] ### 4. Fonts ### 5. qmd tricks <!-- Source of a lot of the slide content: https://resources.rstudio.com/rstudio-conf-2020/the-glamour-of-graphics-william-chase --> --- class: inverse, center, middle # Color is hard --- ## How do I know what colors look good together? -- ### .red[Use the color wheel] .rightcol45[ <center> <img src="images/color_wheel.png"> </center> .center[Image from [this color wheel tool](https://www.sessions.edu/color-calculator/)] ] --- ## How do I know what colors look good together? ### .red[Use the color wheel] .leftcol55[ ### 1. **Complementary**: High contrast ] .rightcol45[ <center> <img src="images/color_wheel_complementary.png"> </center> .center[Image from [this color wheel tool](https://www.sessions.edu/color-calculator/)] ] --- ## How do I know what colors look good together? ### .red[Use the color wheel] .leftcol55[ ### 1. Complementary: High contrast ### 2. **Analogous**: Calm, harmonious ] .rightcol45[ <center> <img src="images/color_wheel_analogous.png"> </center> .center[Image from [this color wheel tool](https://www.sessions.edu/color-calculator/)] ] --- ## How do I know what colors look good together? ### .red[Use the color wheel] .leftcol55[ ### 1. Complementary: High contrast ### 2. Analogous: Calm, harmonious ### 3. **Triadic**: Vibrant, contrast ] .rightcol45[ <center> <img src="images/color_wheel_triadic.png"> </center> .center[Image from [this color wheel tool](https://www.sessions.edu/color-calculator/)] ] --- class: center, middle # [Artists use color theory too!](https://twitter.com/emeldraws/status/1151835561415495681?s=19) --- class: center # Steal colors with the [eye dropper tool](https://chrome.google.com/webstore/detail/eye-dropper/hmdcmlfkchdmnmnmheododdhjedfccka?hl=en) .noborder[ <center> <img src="images/eye_dropper.png" width=242> </center> ] --- ## Using your own colors .leftcol60[.code70[ Map color to variable ``` r mpg_plot <- ggplot(mtcars, aes(x = mpg, y = hp)) + geom_point( * aes(color = as.factor(cyl)), alpha = 0.8, size = 3) + theme_half_open(font_size = 16) + labs(x = "Fuel efficiency (mpg)", y = "Power (hp)", color = '# cylinders', title = "Vehicle fuel efficiency vs. power", caption = "Source: 1974 Motor Trend U.S. magazine.") ``` ]] <br> .rightcol40[ <img src="figs/unnamed-chunk-54-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## Using your own colors .leftcol60[.code70[ Map color to variable ``` r mpg_plot <- ggplot(mtcars, aes(x = mpg, y = hp)) + geom_point( * aes(color = as.factor(cyl)), alpha = 0.8, size = 3) + theme_half_open(font_size = 16) + labs(x = "Fuel efficiency (mpg)", y = "Power (hp)", color = '# cylinders', title = "Vehicle fuel efficiency vs. power", caption = "Source: 1974 Motor Trend U.S. magazine.") ``` Manually change colors ``` r mpg_plot + * scale_color_manual(values = c( * '#a0522d', '#522da0', '#2da052')) ``` ]] <br> .rightcol40[ <img src="figs/unnamed-chunk-56-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## Consider color blind friendly colors .leftcol45[.code70[ Manually change colors ``` r mpg_plot_mycolors <- mpg_plot + theme_half_open(font_size = 10) + * scale_color_manual(values = c( * '#a0522d', '#522da0', '#2da052')) ``` Simulate color blindness with [colorblindr](https://github.com/clauswilke/colorblindr) ``` r # remotes::install_github("clauswilke/colorblindr") library(colorblindr) cvd_grid(mpg_plot_mycolors) ``` ]] .rightcol55[ <img src="figs/unnamed-chunk-58-1.png" width="576" style="display: block; margin: auto;" /> ] --- class:center .leftcol[ # Use palettes ### [Viridis](https://cran.r-project.org/web/packages/viridis/vignettes/intro-to-viridis.html) <center> <img src="images/viridis.png"> </center> ] .rightcol[ ### [ColorBrewer](https://www.datanovia.com/en/blog/the-a-z-of-rcolorbrewer-palette/) <center> <img src="images/colorbrewer.png" width=370> </center> ] --- .leftcol35[ ### 3 types of palettes ### 1. Sequential ### 2. Diverging ### 3. Categorical ] --- .leftcol35[ ### 3 types of palettes ### 1. **Sequential** ### 2. Diverging ### 3. Categorical ] .rightcol65[ <img src="images/palette_sequential.png" width=450> <img src="images/palette_sequential_example.png" width=450> Image from [betterfigures.org](https://betterfigures.org/2015/06/23/picking-a-colour-scale-for-scientific-graphics/) ] --- .leftcol35[ ### 3 types of palettes ### 1. Sequential ### 2. **Diverging** ### 3. Categorical ] .rightcol65[ <img src="images/palette_diverging.png" width=450> <img src="images/palette_diverging_example.png" width=450> Image from [betterfigures.org](https://betterfigures.org/2015/06/23/picking-a-colour-scale-for-scientific-graphics/) ] --- .leftcol35[ ### 3 types of palettes ### 1. Sequential ### 2. Diverging ### 3. **Categorical** ] .rightcol65[ <img src="images/palette_categorical.png" width=500> <img src="images/palette_categorical_example.png" width=500> Image from [betterfigures.org](https://betterfigures.org/2015/06/23/picking-a-colour-scale-for-scientific-graphics/) ] --- ## **ColorBrewer** palettes .leftcol60[.code70[ Map color to variable ``` r mpg_plot <- ggplot(mtcars, aes(x = mpg, y = hp)) + * geom_point(aes(color = as.factor(cyl)), alpha = 0.8, size = 3) + theme_half_open(font_size = 16) + labs(x = "Fuel efficiency (mpg)", y = "Power (hp)", color = '# cylinders', title = "Vehicle fuel efficiency vs. power", caption = "Source: 1974 Motor Trend U.S. magazine.") ``` Use "Dark2" palette ``` r mpg_plot + * scale_color_brewer(palette = 'Dark2') ``` ]] <br> .rightcol40[ <img src="figs/unnamed-chunk-60-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## **ColorBrewer** palettes .cols3[.code70[ ``` r mpg_plot + scale_color_brewer( * palette = 'Set1') ``` <img src="figs/unnamed-chunk-61-1.png" width="432" style="display: block; margin: auto;" /> ]] .cols3[.code70[ ``` r mpg_plot + scale_color_brewer( * palette = 'Set2') ``` <img src="figs/unnamed-chunk-62-1.png" width="432" style="display: block; margin: auto;" /> ]] .cols3[.code70[ ``` r mpg_plot + scale_color_brewer( * palette = 'Accent') ``` <img src="figs/unnamed-chunk-63-1.png" width="432" style="display: block; margin: auto;" /> ]] --- ## **viridis** palettes .leftcol60[.code70[ Map color to variable ``` r mpg_plot <- ggplot(mtcars, aes(x = mpg, y = hp)) + * geom_point(aes(color = as.factor(cyl)), alpha = 0.8, size = 3) + theme_half_open(font_size = 16) + labs(x = "Fuel efficiency (mpg)", y = "Power (hp)", color = '# cylinders', title = "Vehicle fuel efficiency vs. power", caption = "Source: 1974 Motor Trend U.S. magazine.") ``` Use viridis colors ``` r mpg_plot + * scale_color_viridis(discrete = TRUE) ``` ]] <br> .rightcol40[ <img src="figs/unnamed-chunk-65-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## **viridis** palettes .cols3[.code70[ ``` r mpg_plot + scale_color_viridis( discrete = TRUE, * option = 'viridis') ``` <img src="figs/unnamed-chunk-66-1.png" width="432" style="display: block; margin: auto;" /> ]] .cols3[.code70[ ``` r mpg_plot + scale_color_viridis( discrete = TRUE, * option = 'inferno') ``` <img src="figs/unnamed-chunk-67-1.png" width="432" style="display: block; margin: auto;" /> ]] .cols3[.code70[ ``` r mpg_plot + scale_color_viridis( discrete = TRUE, * option = 'plasma') ``` <img src="figs/unnamed-chunk-68-1.png" width="432" style="display: block; margin: auto;" /> ]] --- class: center Fun custom palettes .leftcol[ [Inauguration palette](https://github.com/ciannabp/inauguration) <center> <img src="images/inauguration.png" width=500> <br> <img src="images/inauguration_palette.png" width=500> </center> ] -- .rightcol[ [PNWColors](https://github.com/jakelawlor/PNWColors) <center> <img src="images/PNWColors.jpg" width=500> ] --- ## Consider using `color` + `fill` for points .leftcol60[.code70[ ``` r ggplot(mtcars, aes(x = mpg, y = hp)) + geom_point( * aes(fill = as.factor(cyl)), * color = 'white', shape = 21, size = 3.5, alpha = 0.8) + * scale_fill_brewer(palette = 'Dark2') + theme_half_open(font_size = 15) + labs( x = "Fuel efficiency (mpg)", y = "Power (hp)", fill = '# cylinders', title = "Vehicle fuel efficiency vs. power", caption = "Source: 1974 Motor Trend U.S. magazine.") ``` ]] .rightcol40[ <img src="figs/unnamed-chunk-69-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## .center[`grey` = "Other"] .leftcol[.code70[ ``` r dod_spending_plot <- federal_spending %>% mutate(department = fct_other( department, keep = 'DOD')) %>% group_by(department, year) %>% summarise(rd_budget = sum(rd_budget) / 10^3) %>% ungroup() %>% mutate(department = fct_relevel( department, c('Other', 'DOD'))) %>% ggplot() + geom_area(aes(x = year, y = rd_budget, fill = department)) + scale_y_continuous( expand = expand_scale(mult = c(0, 0.05))) + * scale_fill_manual( * values = c('grey', 'sienna')) + theme_minimal_hgrid() + labs(x = NULL, y = 'R&D Budget ($ Billions)', fill = 'Department', caption = 'Source: AAAS') dod_spending_plot ``` ]] .rightcol[ <img src="figs/unnamed-chunk-70-1.png" width="432" style="display: block; margin: auto;" /> ] --- # .center[`grey` = "Other"] .cols3[.code60[ ``` r dod_spending_plot + scale_fill_manual( * values = c('grey40', 'sienna')) ``` <img src="figs/unnamed-chunk-71-1.png" width="432" style="display: block; margin: auto;" /> ]] .cols3[.code60[ ``` r dod_spending_plot + scale_fill_manual( * values = c('grey60', 'sienna')) ``` <img src="figs/unnamed-chunk-72-1.png" width="432" style="display: block; margin: auto;" /> ]] .cols3[.code60[ ``` r dod_spending_plot + scale_fill_manual( * values = c('grey80', 'sienna')) ``` <img src="figs/unnamed-chunk-73-1.png" width="432" style="display: block; margin: auto;" /> ]] --- class: inverse
−
+
20
:
00
# Your turn .leftcol[ Make 3 different versions of this chart: 1. Change the colors to the `"RdYlBu"` ColorBrewer palette. 2. Change the colors to the `"inferno"` palette from the **viridis** library. 3. Change the colors to your custom triadic palette: - Use the ["eye dropper"](https://chrome.google.com/webstore/detail/eye-dropper/hmdcmlfkchdmnmnmheododdhjedfccka?hl=en) tool in Google Chrome to select a color from a website, then - Use your color and the [color wheel tool](https://www.sessions.edu/color-calculator/) to find a triadic color palette. ] .rightcol[ <img src="figs/unnamed-chunk-75-1.png" width="504" style="display: block; margin: auto;" /> ] --- class: inverse, middle # Week 10: .fancy[Polishing Charts] ### 1. Scales ### 2. Annotations ### BREAK ### 3. Colors ### 4. .orange[Fonts] ### 5. qmd tricks <!-- Source of the content on how to change fonts in ggplot2: https://www.andrewheiss.com/blog/2017/09/27/working-with-r-cairo-graphics-custom-fonts-and-ggplot/ Source of a lot of the slide content on choosing good fonts: https://resources.rstudio.com/rstudio-conf-2020/the-glamour-of-graphics-william-chase --> --- class: inverse, center, middle # Fonts matter .leftcol[ <center> <img src="images/fonts_matter_fast_taco.jpg" width=500> </center> "Fast Taco" ] .rightcol[ <center> <img src="images/fonts_matter_megaflicks.jpg" width=500> </center> "Mega Flicks" ] --- class: inverse, center, middle <center> <img src="images/fonts_matter.jpg" width=500> </center> --- class: center, middle ## Best resource on fonts: ## [practicaltypography.com](https://practicaltypography.com/) --- ## .center[Font families you should consider using] .leftcol30[.font120[ <p style="font-family: Roboto;">Roboto</p> <p style="font-family: Source Code Pro;">Source</p> <p style="font-family: Fira Sans;">Fira</p> <p style="font-family: Alegreya;">Alegreya</p> <p style="font-family: Lato;">Lato</p> ]] .rightcol70[ Download: - Individually from https://fonts.google.com/ - All of these with [this zip file](https://github.com/emse-eda-gwu/2022-Fall/raw/main/content/fonts.zip) ] --- ## Use fonts to create **hierarchy** .leftcol[ ``` # Hierarchy ## Hierarchy ### Hierarchy #### Hierarchy ``` ] .rightcol[ # Hierarchy ## Hierarchy ### Hierarchy #### Hierarchy ] --- .leftcol[ Title<br>This is some text that goes into detail and explains a lot more about the topic described in the title. Here's some random Latin words: Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. ] --- .leftcol[ # Size This is some text that goes into detail and explains a lot more about the topic described in the title. Here's some random Latin words: Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. ] --- .leftcol[ **Weight** This is some text that goes into detail and explains a lot more about the topic described in the title. Here's some random Latin words: Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. ] --- .leftcol[ .red[Color] This is some text that goes into detail and explains a lot more about the topic described in the title. Here's some random Latin words: Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. ] --- .leftcol[ Spacing <br> This is some text that goes into detail and explains a lot more about the topic described in the title. Here's some random Latin words: Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. ] --- .leftcol[ Typeface <p style="font-family: Alegreya;"> This is some text that goes into detail and explains a lot more about the topic described in the title. Here's some random Latin words: Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. </p> ] --- .leftcol[ <h2 style="font-family: Roboto Condensed; color: #a5442b;">Title</h2> <h3 style="font-family: Alegreya;">Subtitle</h3> <p style="font-family: Roboto;"> This is some text that goes into detail and explains a lot more about the topic described in the title. Here's some random Latin words: Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. </p> ] --- # .center[Use fonts with **same-height** numbers] <br> .leftcol35[.right[ ## "Oldstyle" (bad) <br> ## Lining (good) ]] .rightcol65[ <img src="images/font_oldstyle1.jpg" width=500> ] --- # .center[Use fonts with **same-width** numbers] <br> .leftcol40[.right[ ## "Proportional" (bad) <br> ## "Tabular" (good) ]] .rightcol60[ <img src="images/font_oldstyle2.jpg" width=500> ] --- class: inverse, center, middle # How to customize fonts in **ggplot** --- ## 1. Change the whole theme For "Base R" themes, use `base_family`: ``` r theme_minimal(base_family = "Roboto Condensed") ``` ``` r theme_bw(base_family = "Roboto Condensed") ``` <br> For "cowplot" themes, use `font_family`: ``` r theme_half_open(font_family = "Roboto Condensed") ``` ``` r theme_minimal_grid(font_family = "Roboto Condensed") ``` --- ## 1. Change the whole theme font Make the base plot .leftcol60[.code70[ ``` r mpg_plot <- ggplot(mtcars) + geom_point(aes(x = mpg, y = hp)) + * theme_minimal(base_size = 15) + labs( x = "Fuel efficiency (mpg)", y = "Power (hp)", title = "Vehicle fuel efficiency vs. power", subtitle = "Select makes and models", caption = "Source: 1974 Motor Trend U.S. magazine.") ``` ]] .rightcol40[ <img src="figs/unnamed-chunk-81-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## 1. Change the whole theme font Use `base_family` with base themes .leftcol60[.code70[ ``` r mpg_plot <- ggplot(mtcars) + geom_point(aes(x = mpg, y = hp)) + * theme_minimal( * base_family = 'Source Sans Pro', base_size = 15) + labs( x = "Fuel efficiency (mpg)", y = "Power (hp)", title = "Vehicle fuel efficiency vs. power", subtitle = "Select makes and models", caption = "Source: 1974 Motor Trend U.S. magazine.") ``` ]] .rightcol40[ <img src="figs/unnamed-chunk-82-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## 1. Change the whole theme font Use `font_family` with cowplot themes .leftcol60[.code70[ ``` r mpg_plot <- ggplot(mtcars) + geom_point(aes(x = mpg, y = hp)) + * theme_minimal_grid( * font_family = 'Source Sans Pro', font_size = 15) + labs( x = "Fuel efficiency (mpg)", y = "Power (hp)", title = "Vehicle fuel efficiency vs. power", subtitle = "Select makes and models", caption = "Source: 1974 Motor Trend U.S. magazine.") ``` ]] .rightcol40[ <img src="figs/unnamed-chunk-83-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## 2. Adjust theme elements with `element_text()` .leftcol60[.code70[ ``` r mpg_plot <- ggplot(mtcars) + geom_point(aes(x = mpg, y = hp)) + theme_minimal_grid( font_family = 'Source Sans Pro', font_size = 15) + theme( * plot.title = element_text( * family = "Roboto Condensed", * size = 20)) + labs( x = "Fuel efficiency (mpg)", y = "Power (hp)", title = "Vehicle fuel efficiency vs. power", subtitle = "Select makes and models", caption = "Source: 1974 Motor Trend U.S. magazine.") ``` ] See theme components [here](https://ggplot2.tidyverse.org/reference/theme.html) ] .rightcol40[ <img src="figs/unnamed-chunk-84-1.png" width="432" style="display: block; margin: auto;" /> ] --- ### 3. Adjust annotations: ### `geom_text()`, `geom_label()`, and `annotate()` .leftcol60[.code70[ ``` r label <- "Higher power engines, often come at the expense, of fuel economy." mpg_plot + geom_label( data = data.frame( x = 17, y = 270, label = label), aes(x = x, y = y, label = label), lineheight = .8, hjust = 0, * family = 'Roboto Condensed') ``` ]] .rightcol40[ <img src="figs/unnamed-chunk-85-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## The [hrbrthemes](https://github.com/hrbrmstr/hrbrthemes) package: ### Great themes + great fonts .leftcol60[ ``` r *library(hrbrthemes) mpg_plot <- ggplot(mtcars) + geom_point(aes(x = mpg, y = hp)) + labs( x = "Fuel efficiency (mpg)", y = "Power (hp)", title = "Vehicle fuel efficiency vs. power", subtitle = "Select makes and models", caption = "Source: 1974 Motor Trend U.S. magazine.") mpg_plot + * theme_ipsum() ``` ] .rightcol40[ <img src="figs/unnamed-chunk-86-1.png" width="432" style="display: block; margin: auto;" /> ] --- ## The [hrbrthemes](https://github.com/hrbrmstr/hrbrthemes) package: ### Great themes + great fonts .cols3[ ``` r mpg_plot + theme_ipsum() ``` <img src="figs/unnamed-chunk-88-1.png" width="432" style="display: block; margin: auto;" /> ] .cols3[ ``` r mpg_plot + theme_ipsum_rc() ``` <img src="figs/unnamed-chunk-89-1.png" width="432" style="display: block; margin: auto;" /> ] .cols3[ ``` r mpg_plot + theme_ft_rc() ``` <img src="figs/unnamed-chunk-90-1.png" width="432" style="display: block; margin: auto;" /> ] --- class: inverse
−
+
15
:
00
## Your turn .leftcol[.font80[ Modify the fonts and annotations in the dumbbell chart to match the chart shown here. The main font is `'Roboto Condensed'`. Once you've recreated the plot, try other fonts and themes, such as: - The `'Source Sans Pro'` font. - The `'Lato'` font. - The `theme_ipsum()` theme from the `hrbrthemes` library. Hint: Use `annotate()` to insert the year labels at the top: - 1970: `x = 9`, `y = 10.5` - 2017: `x = 40`, `y = 10.5` ]] .rightcol[ <img src="figs/milk_dumbbell-1.png" width="504" style="display: block; margin: auto;" /> ] --- class: inverse, middle # Week 10: .fancy[Polishing Charts] ### 1. Scales ### 2. Annotations ### BREAK ### 3. Colors ### 4. Fonts ### 5. .orange[qmd tricks] --- ## .center[Use themes to change global look] .leftcol[ ## Change theme in YAML header ``` --- title: Your title author: Author name toc: true format: html: theme: united --- ``` ] -- .rightcol[ ## List of themes https://quarto.org/docs/output-formats/html-themes.html ] --- ## Use Quarto extensions https://quarto.org/docs/extensions/ Some personal favoriates: - [lightbox](https://quarto-ext.github.io/lightbox/) - [elevator](https://m.canouil.dev/quarto-elevator/) - [webR](https://quarto-webr.thecoatlessprofessor.com/) --- # Set a global chart theme ``` r theme_set(theme_minimal_grid()) ``` --- # Check out [these Quarto tricks](https://www.productive-r-workflow.com/quarto-tricks), by Yan Holtz