MultipleColumnChart

This example, drawn from Datawrapper’s official documentation, demonstrates how to create small multiple column charts showing population growth in major cities from 1950 to 2035.

import pandas as pd
import datawrapper as dw

# Load population data from GitHub
df = pd.read_csv(
    "https://raw.githubusercontent.com/chekos/Datawrapper/main/tests/samples/multiple_column/population.csv",
    sep="\t"
)

chart = dw.MultipleColumnChart(
    # Chart title
    title="Population of the world's largest cities, 1950 to 2035",
    # Data source attribution
    source_name="Our World in Data",
    source_url="https://ourworldindata.org/urbanization",
    # Data from pandas DataFrame
    data=df,
    # Layout configuration - 4 columns on desktop, 2 on mobile
    grid_layout="fixedCount",
    grid_column=4,
    grid_column_mobile=2,
    grid_row_height=140,
    # Sort panels by end value (2035 population) in descending order
    sort=True,
    sort_by="end",
    sort_reverse=False,
    # Set custom column color with highlighted year for 2025
    base_color="#c9a291",
    color_category={
        "2025": "#c71e1d"
    },
    # Turn off the y grid lines
    y_grid=False,
    # Format y-axis with abbreviated numbers
    y_grid_format=dw.NumberFormat.ABBREVIATED_ONE_DECIMAL,
    y_grid_labels="inside",
    y_grid_label_align="left",
    # Custom panel titles with city and country information
    panels=[
        {"column": "Delhi", "title": "Delhi, <span style=\"color:gray; font-weight: normal;\">India</span>"},
        {"column": "Dhaka", "title": "Dhaka, <span style=\"color:gray; font-weight: normal;\"> Bangladesh </span>"},
        {"column": "Lagos", "title": "Lagos, <span style=\"color:gray; font-weight: normal;\">Nigeria</span>"},
        {"column": "Paris", "title": "Paris, <span style=\"color:gray; font-weight: normal;\">France</span>"},
        {"column": "Tokyo", "title": "Tokyo, <span style=\"color:gray; font-weight: normal;\">Japan</span>"},
        {"column": "Beijing", "title": "Beijing, <span style=\"color:gray; font-weight: normal;\">China</span>"},
        {"column": "Mumbai (Bombay)", "title": "Mumbai, <span style=\"color:gray; font-weight: normal;\">India</span>"},
        {"column": "New York-Newark", "title": "New York/Newark, <span style=\"color:gray; font-weight: normal;\">U.S.</span>"},
    ],
    # Add text annotations to label specific panels
    text_annotations=[
        # "Projection" label on Mumbai panel
        dw.MultipleColumnTextAnnotation(
            text="Projection",
            x="2018/04/30 15:23",
            y=36224085,
            dx=-21,
            dy=-8,
            plot="Mumbai (Bombay)",
            size=13,
            color="#858585",
            align=dw.TextAlign.TOP_RIGHT,
            width=37,
            connector_line=dw.ConnectorLine(
                enabled=True,
                type=dw.ConnectorLineType.STRAIGHT,
                stroke=dw.StrokeWidth.THIN,
                inherit_color=True,
                arrow_head=False,
            ),
            show_mobile=True,
            show_desktop=True,
        ),
        # "Paris 2035" label on Delhi panel
        dw.MultipleColumnTextAnnotation(
            text="Paris 2035",
            x="1947/07/03 01:00",
            y=16409201,
            dx=0,
            dy=0,
            plot="Delhi",
            size=13,
            color="#858585",
            align=dw.TextAlign.TOP_LEFT,
            width=37,
            show_mobile=True,
            show_desktop=True,
        ),
        # "2025 population: 34.7M" label on Delhi panel with HTML formatting
        dw.MultipleColumnTextAnnotation(
            text='<b style="color:#b73229">2025 population:</b>\n34.7M',
            x="2023/07/14 22:34",
            y=33128010,
            dx=-21,
            dy=-29,
            plot="Delhi",
            size=13,
            color="#494949",
            align=dw.TextAlign.TOP_RIGHT,
            outline=True,
            width=66,
            connector_line=dw.ConnectorLine(
                enabled=True,
                type=dw.ConnectorLineType.STRAIGHT,
                stroke=dw.StrokeWidth.THIN,
                inherit_color=False,
                arrow_head=False,
            ),
            show_mobile=True,
            show_desktop=True,
        ),
        # "Paris grew the most..." label on Paris panel
        dw.MultipleColumnTextAnnotation(
            text="Paris grew the most between 1851 to 1856 (by over 20%).",
            x="1947/10/03 18:05",
            y=43097373,
            dx=0,
            dy=0,
            plot="Paris",
            size=13,
            color="#494949",
            align=dw.TextAlign.TOP_LEFT,
            outline=True,
            width=66,
            show_mobile=True,
            show_desktop=True,
        ),
        # "Lagos is expected to double..." label on Lagos panel (hidden)
        dw.MultipleColumnTextAnnotation(
            text="Lagos is expected to double in size by 2035 compared to 2015.",
            x="1947/07/03 01:00",
            y=43096075,
            dx=0,
            dy=0,
            plot="Lagos",
            size=13,
            color="#494949",
            align=dw.TextAlign.TOP_LEFT,
            outline=True,
            width=72,
            show_mobile=False,
            show_desktop=False,
        ),
    ],
    # Add range annotation to highlight projection period
    range_annotations=[
        dw.MultipleColumnXRangeAnnotation(**{
            "x0": "2018/01/01",
            "x1": "2037/07/02",
            "y0": 0,
            "y1": 50000000,
            "color": "#888",
            "opacity": 18,
        }),
        dw.MultipleColumnYLineAnnotation(**{
            "y0": 11765087.7143,
            "color": "#888",
            "opacity": 76,
            "stroke_width": dw.StrokeWidth.MEDIUM,
            "stroke_type": dw.StrokeType.DOTTED,
        })
    ],
)

# Create the chart in Datawrapper
chart.create()

Reference

MultipleColumnChart

Parameter

Default

Description

Type

aria_description

“”

The alternative text for screen readers

str

auto_dark_mode

False

Whether the chart should automatically flip to dark mode when the user’s system is in dark mode

bool

bar_padding

30

The padding between bars as a percentage of the bar width

int

base_color

0

The base color for the chart (palette index or hex string)

str or int

byline

“”

The byline that appears below the chart

str

chart_id

None

The chart ID after creation (populated by create() method)

str or None

chart_type

“multiple-columns”

The type of datawrapper chart to create

Literal[multiple-columns]

color_category

PydanticUndefined

A mapping of layer names to colors

dict[str, str]

custom

PydanticUndefined

A dictionary of custom tags to attach to the chart

dict[str, Any]

custom_range_x

None

Custom range for X-axis as [min, max]. Overrides automatic range calculation.

list[Any] or tuple[Any, Any] or None

custom_range_y

None

Custom range for Y-axis as [min, max]. Overrides automatic range calculation.

list[Any] or tuple[Any, Any] or None

custom_ticks_x

None

Custom tick mark positions for X-axis. List of values where ticks should appear.

list[Any] or None

custom_ticks_y

None

Custom tick mark positions for Y-axis. List of values where ticks should appear.

list[Any] or None

dark_mode_invert

True

Whether to invert colors in dark mode

bool

data

PydanticUndefined

The data to use for the chart

DataFrame or list[dict]

download_image

False

Whether to allow PNG download

bool

download_pdf

False

Whether to allow PDF download

bool

download_svg

False

Whether to allow SVG download

bool

embed

False

Whether to allow embedding

bool

force_attribution

False

Whether to attribute the chart to datawrapper

bool

forkable

True

Whether to allow other users to fork this visualization

bool

get_the_data

False

Whether to allow data downloads

bool

grid_column

2

How the panels are laid out on desktop

int

grid_column_mobile

2

How the panels are laid out on mobile

int

grid_column_width

200

Minimum width for auto layout

int

grid_layout

“fixedCount”

Fixed vs auto layout

Literal[fixedCount, minimumWidth]

grid_row_height

140

Height of rows

int

hide_title

False

Whether or not to hide the title

bool

intro

“”

The intro text that appears above the chart

str

label_colors

False

Whether or not to column labels the same as the column

bool

label_margin

0

The amount of margin to leave for the right hand side for labels. Zero is automatically calculated.

int

language

“en-US”

The locale of the chart, which defines decimal and thousand separators as well as translations of month and weekday names.

str

logo

False

Whether to show a logo

bool

logo_id

“”

The id of the logo to show

str

negative_color

None

The negative color to use, if you want one

str or None

notes

“”

The footnotes that appear below the chart

str

panels

PydanticUndefined

Panel configurations for the chart

list[dict[str, Any]]

plot_height_fixed

300

The fixed height of the plot

int

plot_height_mode

“fixed”

How to set the plot height

PlotHeightMode (FIXED, RATIO) or str

plot_height_ratio

0.5

The ratio of the plot height

float

range_annotations

PydanticUndefined

A list of range annotations to display on the chart

Sequence[UnionType[RangeAnnotation, dict[Any, Any]]]

share_buttons

False

Whether to show social media share buttons

bool

share_url

“”

What URL to share

str

show_color_key

False

Whether or not to show the color key above the chart

bool

show_tooltips

True

Whether or not to show tooltips on hover

bool

show_value_labels

“off”

Whether or not to show value labels

ValueLabelDisplay (HOVER, ALWAYS, OFF) or str

sort

False

Whether to sort the panels

bool

sort_by

“end”

How to sort the panels

Literal[start, end, range, diff, change, title]

sort_reverse

False

Whether to sort the panels in reverse order

bool

source_name

“”

The source name that appears below the chart

str

source_url

“”

The source URL that appears below the chart

str

sync_multiple_tooltips

False

Whether to show tooltips synchronously across all panels

bool

text_annotations

PydanticUndefined

A list of text annotations to display on the chart

Sequence[UnionType[TextAnnotation, dict[Any, Any]]]

theme

“datawrapper”

The theme of the chart

str

title

“”

The headline that appears above the chart

str

tooltip_number_format

“”

The format for the y-axis values in tooltips. Use DateFormat for temporal data, NumberFormat for numeric data, or provide custom format strings.

DateFormat (AUTO, YEAR_FULL, YEAR_TWO_DIGIT, …) or NumberFormat (AUTO, THOUSANDS_WITH_OPTIONAL_DECIMALS, INTEGER, …) or str

transformations

PydanticUndefined

Transform or dict[str, Any]

value_labels_format

“”

How to format the value labels. Use DateFormat for temporal data, NumberFormat for numeric data, or provide custom format strings.

DateFormat (AUTO, YEAR_FULL, YEAR_TWO_DIGIT, …) or NumberFormat (AUTO, THOUSANDS_WITH_OPTIONAL_DECIMALS, INTEGER, …) or str

value_labels_placement

“outside”

Where to place the value labels

ValueLabelPlacement (INSIDE, OUTSIDE, BELOW) or str

x_grid

“off”

X-axis grid display setting. Controls vertical grid lines.

GridDisplay (OFF, ON, TICKS, …) or str or bool or None

x_grid_all

“off”

x_grid for panels

GridDisplay (OFF, ON, TICKS, …) or str

x_grid_format

None

Format string for X-axis grid labels. Supports date and number formats.

DateFormat (AUTO, YEAR_FULL, YEAR_TWO_DIGIT, …) or NumberFormat (AUTO, THOUSANDS_WITH_OPTIONAL_DECIMALS, INTEGER, …) or str or None

x_grid_label_all

False

Show label for all panels

bool

x_grid_labels

“on”

The labeling of the x axis

Literal[on, off]

y_grid

“on”

Y-axis grid display setting. Controls horizontal grid lines.

GridDisplay (OFF, ON, TICKS, …) or str or bool or None

y_grid_format

None

Format string for Y-axis grid labels. Supports number formats.

NumberFormat (AUTO, THOUSANDS_WITH_OPTIONAL_DECIMALS, INTEGER, …) or str or None

y_grid_label_align

“left”

Which side to put the y-axis labels on

GridLabelAlign (LEFT, RIGHT) or str

y_grid_labels

“outside”

The labeling of the y grid labels

GridLabelPosition (AUTO, INSIDE, OUTSIDE, …) or str

MultipleColumnTextAnnotation

Parameter

Default

Description

Type

align

“tl”

The alignment of the text

TextAlign (TOP_LEFT, TOP_CENTER, TOP_RIGHT, …) or str

bold

False

Whether or not to bold the text

bool

color

False

The color of the text

str or bool

connector_line

None

The connector line for the annotation (None = disabled, object = enabled)

ConnectorLine or dict[Any, Any] or None

dx

0

The x offset of the annotation relative to its position

int

dy

0

The y offset of the annotation relative to its position

int

id

None

The unique ID for this annotation (used as dict key, not included in serialized output)

str or None

italic

False

Whether or not to italicize the text

bool

mobile_fallback

False

Whether or not to show a mobile fallback

bool

outline

True

Whether or not to show a text outline

bool

plot

None

Which plot/panel this annotation applies to

str or None

show_desktop

True

Whether or not to show the annotation on desktop

bool

show_in_all_plots

False

Whether to show this annotation in all plots

bool

show_mobile

True

Whether or not to show the annotation on mobile

bool

size

14

The size of the text

int

text

Required

The text to display

str

underline

False

Whether or not to underline the text

bool

width

33.3

The width of the text as a percentage of the chart width

float

x

Required

The x position of the annotation

Any

y

Required

The y position of the annotation

Any

MultipleColumnRangeAnnotation

Parameter

Default

Description

Type

color

“#989898”

The color of the annotation

str

display

“range”

The display style of the annotation

Literal[line, range]

id

None

The unique ID for this annotation (used as dict key, not included in serialized output)

str or None

opacity

50

The opacity of the annotation

int

plot

None

Which plot/panel this annotation applies to

str or None

show_in_all_plots

True

Whether to show this annotation in all plots

bool

stroke_type

“solid”

The stroke type of the annotation, if the display style is a line

StrokeType (SOLID, DASHED, DOTTED) or str

stroke_width

2

The stroke width of the annotation, if the display style is a line

StrokeWidth (THIN, MEDIUM, THICK) or int

type

“x”

The axis of the annotation

Literal[x, y]

x0

None

The first x position (required for type=’x’ annotations)

Any or None

x1

None

The second x position (required for type=’x’ range annotations)

Any or None

y0

None

The first y position (required for type=’y’ annotations)

Any or None

y1

None

The second y position (required for type=’y’ range annotations)

Any or None

MultipleColumnXRangeAnnotation

Parameter

Default

Description

Type

color

“#989898”

The color of the annotation

str

display

“range”

The display style of the annotation

Literal[line, range]

id

None

The unique ID for this annotation (used as dict key, not included in serialized output)

str or None

opacity

50

The opacity of the annotation

int

plot

None

Which plot/panel this annotation applies to

str or None

show_in_all_plots

True

Whether to show this annotation in all plots

bool

stroke_type

“solid”

The stroke type of the annotation, if the display style is a line

StrokeType (SOLID, DASHED, DOTTED) or str

stroke_width

2

The stroke width of the annotation, if the display style is a line

StrokeWidth (THIN, MEDIUM, THICK) or int

type

“x”

The axis of the annotation

Literal[x, y]

x0

None

The first x position (required for type=’x’ annotations)

Any or None

x1

None

The second x position (required for type=’x’ range annotations)

Any or None

y0

None

The first y position (required for type=’y’ annotations)

Any or None

y1

None

The second y position (required for type=’y’ range annotations)

Any or None

MultipleColumnYRangeAnnotation

Parameter

Default

Description

Type

color

“#989898”

The color of the annotation

str

display

“range”

The display style of the annotation

Literal[line, range]

id

None

The unique ID for this annotation (used as dict key, not included in serialized output)

str or None

opacity

50

The opacity of the annotation

int

plot

None

Which plot/panel this annotation applies to

str or None

show_in_all_plots

True

Whether to show this annotation in all plots

bool

stroke_type

“solid”

The stroke type of the annotation, if the display style is a line

StrokeType (SOLID, DASHED, DOTTED) or str

stroke_width

2

The stroke width of the annotation, if the display style is a line

StrokeWidth (THIN, MEDIUM, THICK) or int

type

“x”

The axis of the annotation

Literal[x, y]

x0

None

The first x position (required for type=’x’ annotations)

Any or None

x1

None

The second x position (required for type=’x’ range annotations)

Any or None

y0

None

The first y position (required for type=’y’ annotations)

Any or None

y1

None

The second y position (required for type=’y’ range annotations)

Any or None

MultipleColumnXLineAnnotation

Parameter

Default

Description

Type

color

“#989898”

The color of the annotation

str

display

“range”

The display style of the annotation

Literal[line, range]

id

None

The unique ID for this annotation (used as dict key, not included in serialized output)

str or None

opacity

50

The opacity of the annotation

int

plot

None

Which plot/panel this annotation applies to

str or None

show_in_all_plots

True

Whether to show this annotation in all plots

bool

stroke_type

“solid”

The stroke type of the annotation, if the display style is a line

StrokeType (SOLID, DASHED, DOTTED) or str

stroke_width

2

The stroke width of the annotation, if the display style is a line

StrokeWidth (THIN, MEDIUM, THICK) or int

type

“x”

The axis of the annotation

Literal[x, y]

x0

None

The first x position (required for type=’x’ annotations)

Any or None

x1

None

The second x position (required for type=’x’ range annotations)

Any or None

y0

None

The first y position (required for type=’y’ annotations)

Any or None

y1

None

The second y position (required for type=’y’ range annotations)

Any or None

MultipleColumnYLineAnnotation

Parameter

Default

Description

Type

color

“#989898”

The color of the annotation

str

display

“range”

The display style of the annotation

Literal[line, range]

id

None

The unique ID for this annotation (used as dict key, not included in serialized output)

str or None

opacity

50

The opacity of the annotation

int

plot

None

Which plot/panel this annotation applies to

str or None

show_in_all_plots

True

Whether to show this annotation in all plots

bool

stroke_type

“solid”

The stroke type of the annotation, if the display style is a line

StrokeType (SOLID, DASHED, DOTTED) or str

stroke_width

2

The stroke width of the annotation, if the display style is a line

StrokeWidth (THIN, MEDIUM, THICK) or int

type

“x”

The axis of the annotation

Literal[x, y]

x0

None

The first x position (required for type=’x’ annotations)

Any or None

x1

None

The second x position (required for type=’x’ range annotations)

Any or None

y0

None

The first y position (required for type=’y’ annotations)

Any or None

y1

None

The second y position (required for type=’y’ range annotations)

Any or None