Superimpose variables within a single pie chart

Hi everyone !

I'm trying to create a pie chart superimposing multiple variables using r-plotly.

For instance, I have values for the global population of a country, it's economically active population, and the economically active male/female.

I want to get all those data inside a single pie chart, with the full cercle as the golbal population, a part of this cercle representing the active population, which is divided itslef in 2 parts, male/female.

I unfortunnatly have no idea how to archieve it and I don't even know is it's possible. I didn't manage to do it using the function :

plot_ly(...)

Thank you for your help and happy new year !

I would strongly recommend not using a pie chart to visualize this kind of nested data. Please consider using something like a stacked bar chart or mosaic plot, sankey diagram, or a sunburst chart

If you must go with a pie chart, rather than trying to show all that information at once, it seems like a 'drill-down' approach might be useful. Here is an example of drilling down into sales data (this uses bar charts, but you could do something similar with pie charts):

In case it helps, here is the code:

library(shiny)
library(plotly)
library(dplyr)

sales <- readr::read_csv("https://raw.githubusercontent.com/cpsievert/plotly_book/linking/data/sales.csv")

ui <- fluidPage(
    plotlyOutput("category", height = 200),
    plotlyOutput("sub_category", height = 200),
    plotlyOutput("sales", height = 300),
    dataTableOutput("datatable")
)

# avoid repeating this code
axis_titles <- . %>%
    layout(
        xaxis = list(title = ""),
        yaxis = list(title = "Sales")
    )

server <- function(input, output, session) {
    
    # for maintaining the state of drill-down variables
    category <- reactiveVal()
    sub_category <- reactiveVal()
    order_date <- reactiveVal()
    
    # when clicking on a category, 
    observeEvent(event_data("plotly_click", source = "category"), {
        category(event_data("plotly_click", source = "category")$x)
        sub_category(NULL)
        order_date(NULL)
    })
    
    observeEvent(event_data("plotly_click", source = "sub_category"), {
        sub_category(event_data("plotly_click", source = "sub_category")$x)
        order_date(NULL)
    })
    
    observeEvent(event_data("plotly_click", source = "order_date"), {
        order_date(event_data("plotly_click", source = "order_date")$x)
    })
    
    output$category <- renderPlotly({
        sales %>%
            count(category, wt = sales) %>%
            plot_ly(x = ~category, y = ~n, source = "category") %>%
            axis_titles() %>% 
            layout(title = "Sales by category")
    })
    
    output$sub_category <- renderPlotly({
        if (is.null(category())) return(NULL)
        
        sales %>%
            filter(category %in% category()) %>%
            count(sub_category, wt = sales) %>%
            plot_ly(x = ~sub_category, y = ~n, source = "sub_category") %>%
            axis_titles() %>%
            layout(title = category())
    })
    
    output$sales <- renderPlotly({
        if (is.null(sub_category())) return(NULL)
        
        sales %>%
            filter(sub_category %in% sub_category()) %>%
            count(order_date, wt = sales) %>%
            plot_ly(x = ~order_date, y = ~n, source = "order_date") %>%
            add_lines() %>%
            axis_titles() %>%
            layout(title = paste(sub_category(), "sales over time"))
    })
    
    output$datatable <- renderDataTable({
        if (is.null(order_date())) return(NULL)
        
        sales %>%
            filter(
                sub_category %in% sub_category(),
                as.Date(order_date) %in% as.Date(order_date())
            )
    })
    
}

shinyApp(ui, server)
5 Likes

Thank you very much Sir ! Really usefull i'll use it whenever i can it's pretty fun !

This topic was automatically closed 21 days after the last reply. New replies are no longer allowed.

If you have a query related to it or one of the replies, start a new topic and refer back with a link.