pythonplotlyplotly-pythonsunburst-diagram

Plotly sunburst - define different colors for inner and outer circles


I am trying to do some data visualization for the famous Kaggle Titanic challenge. I would like to plot several pie charts, sunburst variant, putting in the inner circle some specific features (sex, ticket class, ...), and on the outer circle the feature survived/deceased.

Here is an example:

enter image description here

I would like to use different colors for the inner and outer circles. For example, blue/pink for male/female, and green/grey for survived/deceased. I can't do it, if I differentiate by sex I cant differentiate by survival and viceversa.

This is my code:

color_discrete_sequence = ['#8B25BE', '#2D9157', '#2D5F91', '#97909A']

fig = px.sunburst(
    total_raw_df,
    path=['sex', 'survived'],
    # names='sex',
    labels=[{'0': 'Deceased', '1': 'Survived'}],
    color=total_raw_df['sex'],
    color_discrete_sequence=color_discrete_sequence
)
fig.update_traces(
    textinfo="label+percent parent",
    insidetextorientation='horizontal'
)
fig.update_layout(
        font=dict(size=18)
    )
fig.show()

The dataset is the classic TItanic dataset, FYI these are the Dataframe columns:

Index(['pclass', 'survived', 'name', 'sex', 'age', 'sibsp', 'parch', 'ticket',
   'fare', 'cabin', 'embarked', 'boat', 'body', 'home.dest'],
  dtype='object')

Solution

  • Since we could not prepare the same data as the question, we diverted the seaborn data set to address the question. The color correspondence is confusing, but it can be achieved by updating the colors in a one-to-one relationship with the labels. You can check the labels by using fig.data to see the graph structure.

    import seaborn as sns
    df = sns.load_dataset('titanic')
    
    import plotly.express as px
    
    color_discrete_sequence = ['#8B25BE', '#2D9157', '#2D5F91', '#97909A']
    
    fig = px.sunburst(
        df,
        path=['sex', 'survived'],
        # names='sex',
        labels=[{'0': 'Deceased', '1': 'Survived'}],
        color=df['sex'],
        color_discrete_sequence=color_discrete_sequence
    )
    fig.update_traces(
        textinfo="label+percent parent",
        insidetextorientation='horizontal'
    )
    fig.update_layout(
            font=dict(size=18)
        )
    
    color_mapping = {'0': "#708090", '1': "#006400", 'female': "#c71585", 'male': "#0000cd"}
    fig.update_traces(marker_colors=[color_mapping[cat] for cat in fig.data[-1].labels])
    
    fig.show()
    

    enter image description here