Task: Annotations

library(tidyverse)  
library(WDI)        
library(ggrepel)    
library(ggtext) 
indicators <- c("SP.POP.TOTL",     # Population
                "EN.ATM.CO2E.PC",  # CO2 emissions
                "NY.GDP.PCAP.KD")  # GDP per capita

wdi_gdp <- read_csv("data/wdi_gdp.csv")

Clean Data

wdi_clean <- wdi_gdp %>% 
  filter(region != "Aggregates") %>% 
  select(iso2c, iso3c, country, year, 
         population = SP.POP.TOTL,
         co2_emissions = EN.ATM.CO2E.PC, 
         gdp_per_capita = NY.GDP.PCAP.KD,
         region, income)

Clean and reshape data

gdp_capita_rankings <- wdi_clean %>% 
  filter(year %in% c(1995, 2015)) %>% 
  drop_na(gdp_per_capita) %>% 
  group_by(year) %>% 
  mutate(ranking = rank(gdp_per_capita)) %>% 
  ungroup() %>% 
  select(iso3c, country, year, region, income, ranking) %>% 
  pivot_wider(names_from = year, names_prefix = "rank_", values_from = ranking) %>% 
  mutate(rank_diff = rank_2015 - rank_1995) %>% 
  drop_na(rank_diff) %>% 
  mutate(big_change = ifelse(abs(rank_diff) >= 25, TRUE, FALSE)) %>% 
  mutate(better_big_change = case_when(
    rank_diff <= -25 ~ "Rank improved",
    rank_diff >= 25 ~ "Rank worsened",
    TRUE ~ "Rank changed a little"
  ))

head(wdi_clean)
## # A tibble: 6 × 9
##   iso2c iso3c country  year population co2_emissions gdp_per_capita region      
##   <chr> <chr> <chr>   <dbl>      <dbl>         <dbl>          <dbl> <chr>       
## 1 AD    AND   Andorra  2015      78011         NA            41768. Europe & Ce…
## 2 AD    AND   Andorra  2004      76244          7.36         47033. Europe & Ce…
## 3 AD    AND   Andorra  2001      67341          7.79         41421. Europe & Ce…
## 4 AD    AND   Andorra  2002      70049          7.59         42396. Europe & Ce…
## 5 AD    AND   Andorra  2014      79213          5.83         40790. Europe & Ce…
## 6 AD    AND   Andorra  1995      63850          6.66         32918. Europe & Ce…
## # … with 1 more variable: income <chr>
head(gdp_capita_rankings) 
## # A tibble: 6 × 9
##   iso3c country           region income rank_2015 rank_1995 rank_diff big_change
##   <chr> <chr>             <chr>  <chr>      <dbl>     <dbl>     <dbl> <lgl>     
## 1 AND   Andorra           Europ… High …       172       165         7 FALSE     
## 2 ARE   United Arab Emir… Middl… High …       171       180        -9 FALSE     
## 3 ATG   Antigua and Barb… Latin… High …       133       134        -1 FALSE     
## 4 ALB   Albania           Europ… Upper…        86        65        21 FALSE     
## 5 ARM   Armenia           Europ… Upper…        81        44        37 TRUE      
## 6 AGO   Angola            Sub-S… Lower…        76        69         7 FALSE     
## # … with 1 more variable: better_big_change <chr>

Life Expectancy Rankings Graph

update_geom_defaults("text", list(family = "serif"))
update_geom_defaults("label", list(family = "serif"))
update_geom_defaults("label_repel", list(family = "serif"))

ggplot(gdp_capita_rankings,
       aes(x = rank_1995, y = rank_2015)) +
  annotate(geom = "segment", x = 0, xend = 200, y = 0, yend = 200) +
  geom_point(aes(color = better_big_change)) +
  geom_label_repel(data = filter(gdp_capita_rankings, big_change == TRUE),
                   aes(label = country, fill = better_big_change),
                   color = "white") +
  annotate(geom = "text", x = 196, y = 6, label = "Outliers improving", 
           fontface = "italic", hjust = 1, color = "grey50") +
  annotate(geom = "text", x = 2, y = 196, label = "Outliers worsening", 
           fontface = "italic", hjust = 0, color = "grey50") +
  annotate(geom = "rect", xmin = 0, xmax = 25, ymin = 0, ymax = 25, 
           fill = "#2ECC40", alpha = 0.25) +
  annotate(geom = "rect", xmin = 175, xmax = 200, ymin = 175, ymax = 200, 
           fill = "#FF851B", alpha = 0.25) +
  annotate(geom = "text", x = 40, y = 12, label = "Lowest GDP per Capita", 
           hjust = 0, color = "#2ECC40") +
  annotate(geom = "text", x = 180, y = 148, label = "Highest\nGDP\nper Capita", 
           hjust = 0.5, vjust = 1, lineheight = 1, color = "#FF851B") +
  annotate(geom = "segment", x = 0, xend = 0, y = 0, yend = 0, color = "#2ECC40") +
  geom_curve(x = 40, xend = 20, y = 12, yend = 12, color = "#2ECC40", arrow = arrow()) +
  annotate(geom = "segment", x = 0, xend = 0, y = 0, yend = 0, color = "#FF851B") +
  geom_curve(x = 180, xend = 185, y = 150, yend = 180, color = "#FF851B", arrow = arrow()) +
  scale_color_manual(values = c("grey50", "#0074D9", "#FF4136")) +
  scale_fill_manual(values = c("#0074D9", "#FF4136")) +
  scale_x_continuous(expand = c(0, 0), breaks = seq(0, 200, 25)) +
  scale_y_continuous(expand = c(0, 0), breaks = seq(0, 200, 25)) +
  labs(x = "Rank in 1995", y = "Rank in 2015",
       title = "Changes in GDP per capita rankings between 1995 and 2015",
       subtitle = "Countries that <span style='color: #0074D9'>**improved**</span> or <span style='color: #FF4136'>**worsened**</span> more than 25 positions in the rankings highlighted",
       caption = "Source: The World Bank.\nCountries with populations of less than 200,000 included") +
  guides(color = "none", fill = "none") +
  theme_bw(base_family = "serif") +
  theme(plot.title = element_markdown(face = "bold", size = rel(1.4)),
        plot.subtitle = element_markdown(size = rel(1.1)),
        plot.margin = unit(c(0.5, 1, 0.5, 0.5), units = "lines"))