Search code examples
pythongraphchartsplotlydata-visualization

Reduce padding (top and bottom) in plotly express chart


I have the following chart, but I wanted to remove big space between the top and bottom of the graph and the first datapoints. (The image is just a part of the chart, it is much bigger because I'm showing the data for all the countries)

enter image description here

Here is the code:

    fig = px.scatter(
    df, 
        x = 'happiness_score', 
        y = 'country',
        color = 'highlight',
        height=2500,
        hover_data = ['country', 'year', 'happiness_score'],
        color_discrete_map={'none': 'white'}
    )

    fig.update_yaxes(
        tickvals = df.country.unique(),              # make a line for each country
        
    )            

    fig.update_xaxes(
        tickwidth = 1,
        range = (1, 8.2)
    )

    fig.update_traces(
        marker = {
            'size': 12,
            'opacity':0.5,
            'line':{'width':1, 'color': 'DarkSlateGrey'}
        }
        
    )

    fig.update_layout({
        'plot_bgcolor': 'rgba(0, 0, 0, 0)'       # make the background transparent
        # 'paper_bgcolor': 'rgba(0, 0, 0, 0)'
    })

Maybe is the height that is too big, but if I decrease it the labels and the datapoints overlap and make the chart terrible. If I need to reduce height, how can I add space between each tip of the y axis?

Btw, the whole code is here: https://github.com/GDevigili/happiness_data_vis/charts.py and the interface is on streamlit cloud https://share.streamlit.io/gdevigili/happiness_data_vis/main if it help on solving the problem.


Solution

    • define the range of the y-axis
    fig.update_yaxes(
        range=[-.5,len(df.country.unique())+.5],
        tickvals=df.country.unique(),  # make a line for each country
    )
    

    full code including sourcing

    import plotly.express as px
    import pandas as pd
    import kaggle.cli
    import sys, requests
    from pathlib import Path
    from zipfile import ZipFile
    import urllib
    
    # fmt: off
    # download some images to demonstrate
    url = "https://www.kaggle.com/unsdsn/world-happiness"
    sys.argv = [sys.argv[0]] + f"datasets download {urllib.parse.urlparse(url).path[1:]}".split(" ")
    kaggle.cli.main()
    
    zfile = ZipFile(f'{urllib.parse.urlparse(url).path.split("/")[-1]}.zip')
    dfs = {f.filename: pd.read_csv(zfile.open(f), on_bad_lines="skip", low_memory=False)for f in zfile.infolist()}
    
    df = pd.concat([v.assign(year=k.split(".")[0]) for k,v in dfs.items()])
    df = df.rename(columns={c:c.lower().replace(" ","_") for c in df.columns})
    df["highlight"] = np.where(df["year"].astype(int)<2018, 'none', df["year"])
    # fmt: on
    
    fig = px.scatter(
        df,
        x="happiness_score",
        y="country",
        color="highlight",
        height=2500,
        hover_data=["country", "year", "happiness_score"],
        color_discrete_map={"none": "white"},
    )
    
    fig.update_yaxes(
        range=[-.5,len(df.country.unique())+.5],
        tickvals=df.country.unique(),  # make a line for each country
    )
    
    fig.update_xaxes(tickwidth=1, range=(1, 8.2))
    
    fig.update_traces(
        marker={"size": 12, "opacity": 0.5, "line": {"width": 1, "color": "DarkSlateGrey"}}
    )
    
    fig.update_layout(
        {
            "plot_bgcolor": "rgba(0, 0, 0, 0)",  # make the background transparent
            # 'paper_bgcolor': 'rgba(0, 0, 0, 0)'
            "margin":{"l":0,"r":0,"t":0,"b":0}
        }
    )