The 2024 Plotnine Contest will close in 5 days on 26th July 2024, this is after a two week extension.
We have many submissions already but we could have move in these two categories.
1. Visualisation of Distributions
Most of the time, the main plot of statistical graphics is to get a sense of how the data is distributed. I would love to see more submissions of this type. This resource from the University of Iowa is a good introduction to the kinds of ways you can visualise distributions. I think there is plenty of room for otherwise simple visualisations of data distributions made more compelling by the choice of dataset, colors, annotations and overall polish.
2. Visualisation Art
Plotnine implements The Grammar of Graphics, which moulds Drawing and Painting Art into a system suitable for statistical graphics. Constrained within, the Art says “I want to break free” and a contest is the party at which to break free. We got all week.
A contest is a good trigger to spark you into action towards that which you have long procastinated or genuinely stayed away from for fear catching an unhealthy addiction.
A contest can trigger you into action on tasks you’ve long procrastinated or avoided due to concerns about developing an unhealthy addiction. This one may have got me. Inspired by a Yan Holtz piece, Michael Chow has deeped into generative art for this contest. In turn, I have given it a go.
From Yan and through Michael, I get an abstract form and first I unpaint it to reveal its spiky nature.
The Spiky World
Code
from plotnine import ( aes, coord_cartesian, element_rect, geom_area, ggplot, scale_color_manual, theme_void, theme,)import pandas as pdimport numpy as npnum_groups =30def get_colors(cmap_name, start=0, stop=1, n=10):"""Return colors from a colormap"""from mizani.palettes import get_colormap x = np.linspace(start, stop, n)return get_colormap(cmap_name).continuous_palette(x)def combine(colors: list[str]):from mizani.palettes import gradient_n_pal x = np.linspace(0, 1, num_groups)return gradient_n_pal(colors)(x)def make_data(seed=123): names = [f"G{i}"for i inrange(num_groups)] population = [0] *100+list(range(1, num_groups+1)) rs = np.random.RandomState(seed) frames = []for i inrange(30): arr = rs.choice(population, num_groups) _data = pd.DataFrame({"x": i,"y": arr / np.sum(arr),"g": rs.choice(names, num_groups, replace=False), }) frames.append(_data)return pd.concat(frames).sort_values(["x", "g"])def blink(colors: list[str] |list[list[str]], seed=123): data = make_data(seed) p = ( ggplot(data, aes(x="x", y="y", fill="g", color="g"))+ geom_area(show_legend=False)+ coord_cartesian(expand=False)+ scale_color_manual(values=combine(colors), aesthetics=["fill", "color"])+ theme_void() )return p( ggplot(make_data(), aes(x="x", y="y", group="g"))+ geom_area(fill="white", color="black", show_legend=False)+ coord_cartesian(expand=False)+ theme_void()+ theme(plot_background=element_rect(fill="white")))
Then with each blink of the eye, The Spiky World reveals one of her infinite faces.