O código a seguir tem como objetivo mostrar um passo a passo para construir um mapa do Brasil que mostre a receita anual de uma determinada empresa por estado.
Foram usados os pacotes:
ggplot2 para construir os gráficos.
geobr para obter o shapefile do mapa do
Brasil.
dplyr para a manipulação dos dados.
stringr para a manipulação de textos.
readxl para extrair os dados do excel.
library(ggplot2)
library(geobr)
library(dplyr)
library(stringr)
library(readxl)
A função read_country é usada para fazer download dos
dados espaciais do Brasil.
brasil <- read_country(year = 2020)
glimpse(brasil)
## Rows: 27
## Columns: 6
## $ code_state <dbl> 11, 12, 13, 14, 15, 16, 17, 21, 22, 23, 24, 25, 26, 27, 2…
## $ abbrev_state <chr> "RO", "AC", "AM", "RR", "PA", "AP", "TO", "MA", "PI", "CE…
## $ name_state <chr> "Rondônia", "Acre", "Amazônas", "Roraima", "Pará", "Amapá…
## $ code_region <dbl> 1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 3, 3, 3, …
## $ name_region <chr> "Norte", "Norte", "Norte", "Norte", "Norte", "Norte", "No…
## $ geom <MULTIPOLYGON [°]> MULTIPOLYGON (((-65.3815 -1..., MULTIPOLYGON…
A função geom_sf do ggplot2 usa as coordenadas que estão
em dados_brasil$geom no formato “sfc_MULTIPOLYGON” para
fazer as fronteiras dos estados.
ggplot() +
geom_sf(data=brasil)+
theme_minimal()
Para adicionar legenda dos estados: adicionar a função
geom_sf_label informando a coluna que contém as abreviatura
dos estados.
ggplot() +
geom_sf(data=brasil)+
geom_sf_label(data=brasil,aes(label = abbrev_state),size = 2) +
xlab("") + ylab("") +
theme_minimal()
A leitura dos dados vai depender de como está o banco de dados com as
informações. Como os dados que recebi estavam no excel, na 4ª planilha,
usei a função read_excel do pacote readxl.
dados <- read_excel("C:\\Users\\prisc\\Downloads\\DADOS_MAPA.xlsx",
sheet = 4, # Ler a 4º planilha
skip = 1) # Pular uma linha
dados[,c(1,5)]
## # A tibble: 46 × 2
## Estado Anual
## <chr> <dbl>
## 1 AM 118629
## 2 BA 15081.
## 3 BA 12600
## 4 DF 138289.
## 5 ES 1295.
## 6 ES 32695.
## 7 ES 110416
## 8 GO 28846.
## 9 GO 7200
## 10 GO 184000
## # … with 36 more rows
## # ℹ Use `print(n = ...)` to see more rows
Selecionei apenas as colunas “Estado” e “Anual” com a função
select.
Usei filtro pra remover os NA’s da coluna Anual.
Para fazer a soma total por estado usei o group_by
seguido do summarise.
dados <- dados %>% select(Estado, Anual) %>%
filter(!is.na(Anual)) %>%
group_by(Estado) %>% summarise(SomaAnual = sum(Anual))
dados
## # A tibble: 16 × 2
## Estado SomaAnual
## <chr> <dbl>
## 1 AM 118629
## 2 BA 27681.
## 3 DF 138289.
## 4 ES 144407.
## 5 GO 220046.
## 6 MA 2544
## 7 MG 443242.
## 8 MT 185238.
## 9 PE 57025.
## 10 PR 24197.
## 11 RJ 22271.
## 12 RO 2600
## 13 RS 120251.
## 14 SC 49691.
## 15 SP 214361.
## 16 TO 92000
Por fim, os dados estão no formato necessário, sendo uma coluna com a sigla do Estado e a outra com o valor total.
A função left_join vai unir as duas tabelas pela
abreviatura do estado.
Note que na tabela “brasil” as siglas dos estados estão na coluna “abbrev_state”.
dados_brasil <- brasil %>% left_join(dados, by = c("abbrev_state"="Estado"))
Como eu quero preencher os estados de acordo com a soma total daquele
estado, informo para o parametro fill dentro de
aes() qual é a coluna que contém essa informação, no caso é
a SomaAnual.
Ajustei a cor no scale_fill_gradient para ir do branco
ao verde.
A função options(scipen = 999) é para os valores não
sairem na notação científica.
options(scipen = 999)
ggplot() +
geom_sf(data=dados_brasil, aes(fill=SomaAnual),color = NA)+
scale_fill_gradient(low = "white", high = "#008000",
name="Total (Reais)") +
labs(title="Receita anual 2022", size=8) +
theme_minimal()
Para adicionar as legendas em cima do gráfico é necessario outra manipulação nos dados. Para é preciso criar uma nova coluna na tabela “dados_brasil” com a legenda que será inserida.
Primeiro achei uma função para formatar os valores em reais e
adicionei um \n para pular uma linha na hora de concatenar
com a sigla do estado.
format_real <- function(values) {
values %>%
as.numeric() %>%
format(nsmall = 0, decimal.mark = ",", big.mark = ".") %>%
str_trim() %>%
str_c("\nR$ ", .)
}
Como não haviam dados para todos os estados, alguns estavam com NA no
valor da SomaAnual, por isso usei a função ifelse para
formatar só no caso que tenham valores. Na legenda, concatenei a
abreviatura do estado com o valor em Reais formatado. Por fim, chamei a
função replace para substituir os NA’s por zero.
dados_brasil <- dados_brasil %>%
mutate(Real = ifelse(!is.na(SomaAnual),format_real(SomaAnual), "")) %>%
mutate(Legenda = paste0(abbrev_state, Real)) %>%
replace(is.na(.),0)
Para adicionar a legenda sem as bordas, usei a função
geom_sf_text, informando que o texto está na coluna
“Legenda”.
Adicionei para color = "grey" para as cores das
fronteiras ficarem cinza.
ggplot() +
geom_sf(data=dados_brasil, aes(fill=SomaAnual), color= "grey")+
geom_sf_text(data=dados_brasil,aes(label = Legenda),size = 2) +
scale_fill_gradient(low = "white", high = "#008000",
name="Total (Reais)") +
labs(title="Receita anual 2022")+
theme_minimal()
Como no Mapa o valor de Goias ficou em cima do valor do distrito federal, optei por fazer um ajuste manual na legenda de Goias, adicionando mais uma quebra de linha.
dados_brasil$Legenda[dados_brasil$abbrev_state == 'GO']
## [1] "GO\nR$ 220.046,20"
dados_brasil$Legenda[dados_brasil$abbrev_state == 'GO'] <- "GO\n\nR$ 220.046,20"
Adicionei alguns ajustes no Tema e removi a legenda, uma vez que já tem o texto com o valor em Reais em cima dos estados.
ggplot() +
geom_sf(data=dados_brasil, aes(fill=SomaAnual), color= "grey")+
geom_sf_text(data=dados_brasil,aes(label = Legenda),size = 3.5) +
scale_fill_gradient(low = "white", high = "#008000",
name="Total (Reais)") +
labs(title="Receita anual 2022")+
theme_minimal() +
theme(
axis.title.x = element_blank(),
axis.title.y = element_blank(),
legend.position="none",
plot.title=element_text(size=20, face="bold", hjust=0.5)
)