I have collated some data on world happiness index reports from 2015 to 2019, which you can access here and download the dataset. I want to make an animation slider of happiness vs some other factor (like economy, health, etc) over the years. Below is my code:
import pandas as pd
from plotly.offline import download_plotlyjs, init_notebook_mode, iplot
from plotly.graph_objs import *
init_notebook_mode()
from chart_studio.grid_objs import Grid, Column
from plotly.tools import FigureFactory as FF
dataset = pd.read_csv('Full dataset.csv')
dataset.drop(['Family', 'Standard Error'], axis=1, inplace=True)
years_from_col = set(dataset['year'])
years_ints = sorted(list(years_from_col))
years = [str(year) for year in years_ints]
# make list of continents
continents = []
for continent in dataset['Continent']:
if continent not in continents:
continents.append(continent)
df = pd.DataFrame()
# make grid
for year in years:
for continent in continents:
dataset_by_year = dataset[dataset['year'] == int(year)]
dataset_by_year_and_cont = dataset_by_year[dataset_by_year['Continent'] == continent]
for col_name in dataset_by_year_and_cont:
# each column name is unique
temp = '{year}+{continent}+{header}_grid'.format(
year=year, continent=continent, header=col_name
)
#if dataset_by_year_and_cont[col_name].size != 0:
df = df.append({'value': list(dataset_by_year_and_cont[col_name]), 'key': temp}, ignore_index=True)
figure = {
'data': [],
'layout': {},
'frames': []
}
figure['layout']['xaxis'] = {'title': 'Economy (GDP per Capita)', 'type': 'log', 'autorange': True}
figure['layout']['yaxis'] = {'title': 'Happiness Score', 'autorange': True}
figure['layout']['hovermode'] = 'closest'
figure['layout']['showlegend'] = True
figure['layout']['sliders'] = {
'args': [
'slider.value', {
'duration': 400,
'ease': 'cubic-in-out'
}
],
'initialValue': '2015',
'plotlycommand': 'animate',
'values': years,
'visible': True
}
figure['layout']['updatemenus'] = [
{
'buttons': [
{
'args': [None, {'frame': {'duration': 500, 'redraw': False},
'fromcurrent': True, 'transition': {'duration': 300, 'easing': 'quadratic-in-out'}}],
'label': 'Play',
'method': 'animate'
},
{
'args': [[None], {'frame': {'duration': 0, 'redraw': False}, 'mode': 'immediate',
'transition': {'duration': 0}}],
'label': 'Pause',
'method': 'animate'
}
],
'direction': 'left',
'pad': {'r': 10, 't': 87},
'showactive': False,
'type': 'buttons',
'x': 0.1,
'xanchor': 'right',
'y': 0,
'yanchor': 'top'
}
]
sliders_dict = {
'active': 0,
'yanchor': 'top',
'xanchor': 'left',
'currentvalue': {
'font': {'size': 20},
'prefix': 'Year:',
'visible': True,
'xanchor': 'right'
},
'transition': {'duration': 300, 'easing': 'cubic-in-out'},
'pad': {'b': 10, 't': 50},
'len': 0.9,
'x': 0.1,
'y': 0,
'steps': []
}
custom_colors = {
'Asia': 'rgb(171, 99, 250)',
'Europe': 'rgb(230, 99, 250)',
'Africa': 'rgb(99, 110, 250)',
'North America': 'rgb(25, 211, 243)',
'South America': 'rgb(25, 163, 243)',
'Oceania': 'rgb(50, 170, 255)'
}
col_name_template = '{year}+{continent}+{header}_grid'
year = 2015
for continent in continents:
data_dict = {
'x': df.loc[df['key']==col_name_template.format(
year=year, continent=continent, header='Economy (GDP per Capita)'
), 'value'].values[0],
'y': df.loc[df['key']==col_name_template.format(
year=year, continent=continent, header='Happiness Score'
), 'value'].values[0],
'mode': 'markers',
'text': df.loc[df['key']==col_name_template.format(
year=year, continent=continent, header='Country'
), 'value'].values[0],
'marker': {
'sizemode': 'area',
'sizeref': 200000,
'size': df.loc[df['key']==col_name_template.format(
year=year, continent=continent, header='Generosity'
), 'value'].values[0],
'color': custom_colors[continent]
},
'name': continent
}
figure['data'].append(data_dict)
for year in years:
frame = {'data': [], 'name': str(year)}
for continent in continents:
data_dict = {
'x': df.loc[df['key']==col_name_template.format(
year=year, continent=continent, header='Economy (GDP per Capita)'
), 'value'].values[0],
'y': df.loc[df['key']==col_name_template.format(
year=year, continent=continent, header='Happiness Score'
), 'value'].values[0],
'mode': 'markers',
'text': df.loc[df['key']==col_name_template.format(
year=year, continent=continent, header='Country'
), 'value'].values[0],
'marker': {
'sizemode': 'area',
'sizeref': 200000,
'size': df.loc[df['key']==col_name_template.format(
year=year, continent=continent, header='Generosity'
), 'value'].values[0],
'color': custom_colors[continent]
},
'name': continent
}
frame['data'].append(data_dict)
figure['frames'].append(frame)
slider_step = {'args': [
[year],
{'frame': {'duration': 300, 'redraw': False},
'mode': 'immediate',
'transition': {'duration': 300}}
],
'label': year,
'method': 'animate'}
sliders_dict['steps'].append(slider_step)
figure['layout']['sliders'] = [sliders_dict]
iplot(figure, config={'scrollzoom': True})
It produces animation of a blank viz, like so:
What went wrong? And how do I fix it?
import pandas as pd
import plotly.graph_objs as go
from plotly.offline import init_notebook_mode, iplot
init_notebook_mode()
dataset = pd.read_csv('https://raw.githubusercontent.com/PrashantSaikia/Happiness-Index/master/Full%20dataset.csv')
years = list(dataset['year'].sort_values().unique())
continents = list(dataset['Continent'].sort_values().unique())
layout = {
'xaxis': {
'title': 'Economy (GDP per Capita)',
'type': 'log',
'autorange': True
},
'yaxis': {
'title': 'Happiness Score',
'autorange': True
},
'hovermode': 'closest',
'showlegend': True,
'updatemenus': [{
'buttons': [
{
'args': [None, {'frame': {'duration': 600, 'redraw': True}, 'fromcurrent': True, 'transition': {'duration': 0}}],
'label': 'Play',
'method': 'animate'
},
{
'args': [[None], {'frame': {'duration': 0, 'redraw': False}, 'mode': 'immediate', 'transition': {'duration': 0}}],
'label': 'Pause',
'method': 'animate'
}
],
'direction': 'left',
'pad': {'r': 10, 't': 87},
'showactive': False,
'type': 'buttons',
'x': 0.1,
'xanchor': 'right',
'y': 0,
'yanchor': 'top'
}],
'sliders': [{
'active': 0,
'yanchor': 'top',
'xanchor': 'left',
'currentvalue': {
'font': {'size': 20},
'prefix': 'Year:',
'visible': True,
'xanchor': 'right'},
'transition': {'duration': 300, 'easing': 'cubic-in-out'},
'pad': {'b': 10, 't': 50},
'len': 0.9,
'x': 0.1,
'y': 0,
'steps': []
}]
}
custom_colors = {
'Asia': 'rgb(171, 99, 250)',
'Europe': 'rgb(230, 99, 250)',
'Africa': 'rgb(99, 110, 250)',
'North America': 'rgb(25, 211, 243)',
'South America': 'rgb(25, 163, 243)',
'Oceania': 'rgb(50, 170, 255)'
}
data = []
year = years[0]
for continent in continents:
df = dataset[(dataset['Continent'] == continent) & (dataset['year'] == year)]
data.append(go.Scatter(x=df['Economy (GDP per Capita)'],
y=df['Happiness Score'],
text=df['Country'],
mode='markers',
marker={
'size': 100 * df['Generosity'],
'color': custom_colors[continent]
},
name=continent))
frames = []
for year in years[1:]:
frame = {'data': [], 'name': str(year)}
for continent in continents:
df = dataset[(dataset['Continent'] == continent) & (dataset['year'] == year)]
frame['data'].append(go.Scatter(x=df['Economy (GDP per Capita)'],
y=df['Happiness Score'],
text=df['Country'],
mode='markers',
marker={
'size': 100 * df['Generosity'],
'color': custom_colors[continent]
},
name=continent))
frames.append(go.Frame(data=frame['data'], name=frame['name']))
slider_step = {
'args': [
[str(year)],
{'frame': {'duration': 600, 'redraw': True},
'mode': 'immediate',
'transition': {'duration': 200}}
],
'label': str(year),
'method': 'animate'
}
layout['sliders'][0]['steps'].append(slider_step)
figure = go.Figure(data=data, layout=layout, frames=frames)
iplot(figure)
Related
I'm trying to create combination of dictionary based on some condition
below is the main dictionary:
payload = {
"type": ["sedan","suv"],
"name": ["car1","car2"],
"color": ["black","white","green"],
"version": ["mid","top"],
"model": ["2","5","13"],
}
below are the conditions:
color = {
"car1": ["black","green"],
"car2":["white"]
}
model = {
"mid":["5"],
"top":["13","5"]
}
For payload["name"] = "car1" the colors can be only be "black" or "green" even if the payload["color"] has more than these color.
for payload["name"] = "car2", it can have only be "white" color.
Same goes for model also, for mid version it can only have model as "5" and for top version it can have only "13" and "5".
below is the expected output:
[
{'type': 'sedan', 'name': 'car1', 'color': 'black', 'version': 'mid', 'model': '5'},
{'type': 'sedan', 'name': 'car1', 'color': 'black', 'version': 'top', 'model': '5'},
{'type': 'sedan', 'name': 'car1', 'color': 'black', 'version': 'top', 'model': '13'},
{'type': 'sedan', 'name': 'car1', 'color': 'green', 'version': 'mid', 'model': '5'},
{'type': 'sedan', 'name': 'car1', 'color': 'green', 'version': 'top', 'model': '5'},
{'type': 'sedan', 'name': 'car1', 'color': 'green', 'version': 'top', 'model': '13'},
{'type': 'suv', 'name': 'car1', 'color': 'black', 'version': 'top', 'model': '5'},
{'type': 'suv', 'name': 'car1', 'color': 'black', 'version': 'top', 'model': '13'},
{'type': 'suv', 'name': 'car1', 'color': 'black', 'version': 'mid', 'model': '5'},
{'type': 'suv', 'name': 'car1', 'color': 'green', 'version': 'top', 'model': '5'},
{'type': 'suv', 'name': 'car1', 'color': 'green', 'version': 'top', 'model': '13'},
{'type': 'suv', 'name': 'car1', 'color': 'green', 'version': 'mid', 'model': '5'},
{'type': 'sedan', 'name': 'car2', 'color': 'white', 'version': 'mid', 'model': '5'},
{'type': 'sedan', 'name': 'car2', 'color': 'white', 'version': 'top', 'model': '5'},
{'type': 'sedan', 'name': 'car2', 'color': 'white', 'version': 'top', 'model': '13'},
{'type': 'suv', 'name': 'car2', 'color': 'white', 'version': 'mid', 'model': '5'},
{'type': 'suv', 'name': 'car2', 'color': 'white', 'version': 'top', 'model': '5'},
{'type': 'suv', 'name': 'car2', 'color': 'white', 'version': 'top', 'model': '13'}
]
Below is my code..it brings out all the combinations, how can i add the condition check to this. Can someone help?
import itertools
payload = {
"type": ["sedan","suv"],
"name": ["car1","car2"],
"color": ["black","white","green"],
"version": ["mid","top"],
"model": ["2","5","13"],
}
color = {
"car1": ["black","green"],
"car2":["white"]
}
model = {
"mid":["5"],
"top":["13","5"]
}
output = [dict(zip(payload.keys(), a)) for a in itertools.product(*payload.values())]
print(output)
You can try to create a dataframe with the outputs and the filter it for each condition like below
import itertools
import pandas as pd
payload = {
"type": ["sedan","suv"],
"name": ["car1","car2"],
"color": ["black","white","green"],
"version": ["mid","top"],
"model": ["2","5","13"],
}
color = {
"car1": ["black","green"],
"car2":["white"]
}
model = {
"mid":["5"],
"top":["13","5"]
}
output = [dict(zip(payload.keys(), a)) for a in itertools.product(*payload.values())]
print(output)
df = pd.DataFrame(output)
# filter for car1 color
df = df.loc[~((df.name == 'car1') & ~(df.color.isin(color['car1']))),:]
# filter for car2 color
df = df.loc[~((df.name == 'car2') & ~(df.color.isin(color['car2']))),:]
#filter for mid model
df = df.loc[~((df.version == 'mid') & ~(df.model.isin(model['mid']))),:]
#filter for topmodel
df = df.loc[~((df.version == 'top') & ~(df.model.isin(model['top']))),:]
df
I have array and dictionary that I want to combine my_array and my_brand_dictand create new mydict dictionary fill that the non-existing date values with 0's.
my_array = ['20201', '20203', '20204', '20205', '20206', '20207', '20208', '20209', '202010', '202011', '202012', '202013', '202014']
my_brand_dict = [{'key': {'Brand': 'Tesla', 'Date': '20203'}, 'Total': 56}, {'key': {'Brand': 'Tesla', 'Date': '20207'}, 'Total': 88},
{'key': {'Brand': 'Toyota', 'Date': '202014'}, 'Total': 79}, {'key': {'Brand': 'Toyota', 'Date': '20201'}, 'Total': 49}]
mydict = {
'name' : "Brand, Dates and sales",
'labels': my_array,
'datasets': []
}
Here is my try to fill mydict with values
temp_dict = dict()
for i in my_brand_dict:
temp_dict = {
'label': i['key']['Brand'],
'data': [],
}
mydict['datasets'].append(temp_dict)
temp_dict['data'].extend([t['Total'] for t in my_brand_dict if t['key']['Brand'] == temp_dict['label']])
print(mydict)
Which prints :
{'name': 'Brand, Dates and sales', 'labels': ['20201', '20203', '20204', '20205', '20206', '20207', '20208', '20209', '202010', '202011', '202012', '202013', '202014'], 'datasets': [{'label': 'Tesla', 'data': [56, 88]}, {'label': 'Tesla', 'data': [56, 88]}, {'label': 'Toyota', 'data': [79, 49]}, {'label': 'Toyota', 'data': [79, 49]}]}
But I need the output as below for those values added by order and non-exist values to corresponding dates filled with 0s
{'name': 'Brand, Dates and sales', 'labels': ['20201', '20203', '20204', '20205', '20206', '20207', '20208', '20209', '202010', '202011', '202012', '202013', '202014'],
'datasets': [{'label': 'Tesla', 'data': [0,56,0,0,0,88,0,0,0,0,0,0,0]}, {'label': 'Toyota', 'data': [49,0,0,0,0,0,0,0,0,0,0,0,79]}]}
Try:
tmp = {}
for d in my_brand_dict:
tmp.setdefault(d["key"]["Brand"], {})[d["key"]["Date"]] = d["Total"]
mydict = {
"name": "Brand, Dates and sales",
"labels": my_array,
"datasets": [
{"Label": k, "data": [v.get(vv, 0) for vv in my_array]}
for k, v in tmp.items()
],
}
print(mydict)
Prints:
{
"name": "Brand, Dates and sales",
"labels": [
"20201",
"20203",
"20204",
"20205",
"20206",
"20207",
"20208",
"20209",
"202010",
"202011",
"202012",
"202013",
"202014",
],
"datasets": [
{"Label": "Tesla", "data": [0, 56, 0, 0, 0, 88, 0, 0, 0, 0, 0, 0, 0]},
{"Label": "Toyota", "data": [49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 79]},
],
}
I just changed your approach to the problem and it cost an extra O(n) time complexity.
temp_dict = {}
for i in my_brand_dict:
date = i['key']['Date']
date_ind = my_array.index(date)
brand = i['key']['Brand']
if brand not in temp_dict:
temp_dict[brand] = [0]*len(my_array)
temp_dict[brand][date_ind] = i['Total']
else:
temp_dict[brand][date_ind] = i['Total']
I created a new dictionary for each Brand because we would like to create an array for each Brand. The length of that array is known so in the beginning I can create it with zeros. Also, we can find indexes for matching dates and change the values on array. After these steps I just put the info on the mydict:
for dates,brand in temp_dict.items():
mydict['datasets'].append({'label':brand,'data':dates})
Thus the entire code will be:
my_array = ['20201', '20203', '20204', '20205', '20206', '20207', '20208', '20209', '202010', '202011', '202012', '202013', '202014']
my_brand_dict = [{'key': {'Brand': 'Tesla', 'Date': '20203'}, 'Total': 56}, {'key': {'Brand': 'Tesla', 'Date': '20207'}, 'Total': 88},
{'key': {'Brand': 'Toyota', 'Date': '202014'}, 'Total': 79}, {'key': {'Brand': 'Toyota', 'Date': '20201'}, 'Total': 49}]
mydict = {
'name' : "Brand, Dates and sales",
'labels': my_array,
'datasets': []
}
temp_dict = {}
for i in my_brand_dict:
date = i['key']['Date']
date_ind = my_array.index(date)
brand = i['key']['Brand']
if brand not in temp_dict:
temp_dict[brand] = [0]*len(my_array)
temp_dict[brand][date_ind] = i['Total']
else:
temp_dict[brand][date_ind] = i['Total']
for dates,brand in temp_dict.items():
mydict['datasets'].append({'label':brand,'data':dates})
print(mydict)
I have a json array on python which I want to filter based on the value of : my_json_array['models']['variants']['condition']['type']
my json array looks like the following :
my_json_array = [
{'id': 1,
'models': [
{'color': {'code': '#626262', 'name': 'Gray'},
'variants': [{'id': 1,
'condition': [{'id': 1,
'type': 'type1',
'value': 14900},
{'id': 2,
'type': 'type2',
'value': 14000}]]
]
}]
I'm looking for a method to remove condition items with type = type2. The output should look like this :
my_json_array = [{
'id': 1,
'models': [
{'color': {'code': '#626262', 'name': 'Gray'},
'variants': [{'id': 1,
'condition': [{'id': 1,
'type': 'type1',
'value': 14900}]]
]
}]
Do you mean this?
my_json_array = [
{
'id': 1,
'models': [
{
'color': {'code': '#626262', 'name': 'Gray'},
'variants': [
{
'id': 1,
'condition': [
{
'id': 1,
'type': 'type1',
'value': 14900
},
{
'id': 2,
'type': 'type2',
'value': 14000
}
]
}
]
}
]
}
]
for mydict in my_json_array:
for model in mydict['models']:
for variant in model['variants']:
for condition in variant['condition']:
if condition['type']=="type2":
variant['condition'].remove(condition)
print(my_json_array) # [{'id': 1, 'models': [{'color': {'code': '#626262', 'name': 'Gray'}, 'variants': [{'id': 1, 'condition': [{'id': 1, 'type': 'type1', 'value': 14900}]}]}]}]
How do I increase the opacity or alpha of the 'filled' area of my plot? I tried:
import pandas as pd
import plotly.offline as py
import plotly.graph_objs as go
import cufflinks as cf
from plotly import tools
plotly.offline.init_notebook_mode()
cf.go_offline()
df = pd.DataFrame(np.random.rand(10, 4), columns=['a', 'b', 'c', 'd'])
df.iplot(kind='area', fill=True, filename='cuflinks/stacked-area', opacity=.1)
but it doesn't seem to work.
There doesn't seem to be an easy built-in way of achieving this. However, a work-around is to first get the figure object of the plot, modify it to change the opacity, and then plot it.
You can get the figure object using the asFigure attribute like this:
figure = df.iplot(asFigure=True, kind='area', fill=True, filename='cuflinks/stacked-area')
The figure object in this case looks like:
Figure({
'data': [{'fill': 'tonexty',
'fillcolor': 'rgba(255, 153, 51, 0.3)',
'line': {'color': 'rgba(255, 153, 51, 1.0)', 'dash': 'solid', 'shape': 'linear', 'width': 1.3},
'mode': 'lines',
'name': 'a',
'text': '',
'type': 'scatter',
'uid': '4dcc1a3e-fba3-4a32-bb2a-40925b4fae5b',
'x': array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9], dtype=int64),
'y': array([0.91229144, 0.63049138, 0.22855077, 0.13470399, 0.9114691 , 0.39640368,
0.46534334, 0.20508211, 0.00203548, 0.41343938])},
{'fill': 'tonexty',
'fillcolor': 'rgba(55, 128, 191, 0.3)',
'line': {'color': 'rgba(55, 128, 191, 1.0)', 'dash': 'solid', 'shape': 'linear', 'width': 1.3},
'mode': 'lines',
'name': 'b',
'text': '',
'type': 'scatter',
'uid': '1015b30d-7c09-456c-875c-8a211a6ebdeb',
'x': array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9], dtype=int64),
'y': array([1.81115175, 1.57534372, 0.41288126, 0.38068805, 1.72268856, 0.87778503,
1.32714727, 0.848242 , 0.51605283, 0.58190402])},
{'fill': 'tonexty',
'fillcolor': 'rgba(50, 171, 96, 0.3)',
'line': {'color': 'rgba(50, 171, 96, 1.0)', 'dash': 'solid', 'shape': 'linear', 'width': 1.3},
'mode': 'lines',
'name': 'c',
'text': '',
'type': 'scatter',
'uid': '7d1852ac-b8e7-44e6-ae69-54229d7e2c83',
'x': array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9], dtype=int64),
'y': array([2.79222081, 1.58812634, 1.1439478 , 1.30453731, 2.50881795, 1.67681961,
1.85609861, 1.36657712, 0.89024486, 0.82749039])},
{'fill': 'tonexty',
'fillcolor': 'rgba(128, 0, 128, 0.3)',
'line': {'color': 'rgba(128, 0, 128, 1.0)', 'dash': 'solid', 'shape': 'linear', 'width': 1.3},
'mode': 'lines',
'name': 'd',
'text': '',
'type': 'scatter',
'uid': '89b85012-fc95-487c-b7ba-9cb6c249b768',
'x': array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9], dtype=int64),
'y': array([3.54740551, 1.79856232, 2.1326556 , 2.10560567, 2.64867039, 2.55519564,
2.73888819, 2.23274393, 1.16987343, 1.42794202])}],
'layout': {'legend': {'bgcolor': '#F5F6F9', 'font': {'color': '#4D5663'}},
'paper_bgcolor': '#F5F6F9',
'plot_bgcolor': '#F5F6F9',
'title': {'font': {'color': '#4D5663'}},
'xaxis': {'gridcolor': '#E1E5ED',
'showgrid': True,
'tickfont': {'color': '#4D5663'},
'title': {'font': {'color': '#4D5663'}, 'text': ''},
'zerolinecolor': '#E1E5ED'},
'yaxis': {'gridcolor': '#E1E5ED',
'showgrid': True,
'tickfont': {'color': '#4D5663'},
'title': {'font': {'color': '#4D5663'}, 'text': ''},
'zerolinecolor': '#E1E5ED'}}
})
You'll note that each trace in the data has a fillcolor attribute: 'fillcolor': 'rgba(255, 153, 51, 0.3)'. The last number is the alpha value, which you want to modify. I've made a hacky little function to update the fillcolor attribute of all traces in a figure object:
def update_opacity(figure,opacity):
for trace in range(len(figure['data'])):
# print(figure['data'][trace]['fillcolor'],'-> ',end='')
rgba_split = figure['data'][trace]['fillcolor'].split(',')
figure['data'][trace]['fillcolor'] = ','.join(rgba_split[:-1] + [' {})'.format(opacity)])
# print(figure['data'][trace]['fillcolor'])
return figure
For full opacity, you can do:
figure = update_opacity(figure,1)
Then, simply plot the result with
py.iplot(figure)
Output:
I am attempting to adapt the Python Plotly example on 'Adding Sliders to Animations in Python' to a barchart but am getting a 'Figure field is invalid' message.
I am trying to adapt the input data to reflect that of a bar chart rather than a scatter chart (used in the example). I have created a grid:
Which I am using with the following code:
years = ['2007','2008','2009']
items = ['Name_1','Name_2']
col_name_template = '{column}'
for year in years:
frame = {'data': [], 'name': str(year)}
x_list = []
y_list = []
for item in items:
x_list.append(grid.get_column_reference(col_name_template.format(column='name')))
y_list.append(grid.get_column_reference(col_name_template.format(column=year)))
frame['data'].append(go.Bar(
x=x_list,
y=y_list
))
figure['frames'].append(frame)
slider_step = {'args': [
[year],
{'frame': {'duration': 300, 'redraw': False},
'mode': 'immediate',
'transition': {'duration': 300}}
],
'label': year,
'method': 'animate'}
sliders_dict['steps'].append(slider_step)
figure['layout']['sliders'] = [sliders_dict]
py.icreate_animations(figure, 'barchart example')
When trying to plot I get the following error:
Figure field is invalid. Reason: Raw data arrays are not allowed at this endpoint. Use grid references instead. Raw data found at the following paths in the figure...
How do I use only grid references but also ensure that a bar chart is plotted rather than a scatter chart?
I used the offline method of plotting plotly.offline.iplot which doesn't require grid references. The only downside of animations with bar charts is that transitions aren't currently supported.
Code below (including buttons and slider):
from plotly.offline import init_notebook_mode, iplot
from IPython.display import display, HTML
init_notebook_mode(connected = True)
years = ['2010', '2011', '2012']
items = ['A', 'B', 'C', 'D']
count = [
[1, 2, 3, 4],
[2, 3, 4, 1],
[3, 4, 1, 2]
]
figure = {
'data': [{
'type': 'bar',
'x': items,
'y': count[0]
}],
'layout': {
'xaxis': {
'title': 'X',
'gridcolor': '#FFFFFF',
'linecolor': '#000',
'linewidth': 1,
'zeroline': False,
'autorange': False
},
'yaxis': {
'title': 'Y',
'gridcolor': '#FFFFFF',
'linecolor': '#000',
'linewidth': 1,
'range': [0, 5],
'autorange': False
},
'title': 'Example Title',
'hovermode': 'closest',
'updatemenus': [{
'type': 'buttons',
'buttons': [{
'label': 'Play',
'method': 'animate',
'args': [None, {
'frame': {
'duration': 500,
'redraw': True
},
'fromcurrent': True,
'transition': {
'duration': 300,
'easing': 'quadratic-in-out'
}
}]
},
{
'label': 'End',
'method': 'animate',
'args': [None, {
'frame': {
'duration': 0,
'redraw': True
},
'fromcurrent': True,
'mode': 'immediate',
'transition': {
'duration': 0
}
}]
}
],
'direction': 'left',
'pad': {
'r': 10,
't': 87
},
'showactive': False,
'type': 'buttons',
'x': 0.1,
'xanchor': 'right',
'y': 0,
'yanchor': 'top'
}]
},
'frames': []
}
sliders_dict = {
'active': 0,
'yanchor': 'top',
'xanchor': 'left',
'currentvalue': {
'font': {
'size': 20
},
'prefix': 'Year:',
'visible': True,
'xanchor': 'right'
},
'transition': {
'duration': 300,
'easing': 'cubic-in-out'
},
'pad': {
'b': 10,
't': 50
},
'len': 0.9,
'x': 0.1,
'y': 0,
'steps': []
}
for index, year in enumerate(years):
frame = {
'data': [{
'type': 'bar',
'x': items,
'y': count[index]
}],
'name': str(year)
}
figure['frames'].append(frame)
slider_step = {
'args': [
[year],
{
'frame': {
'duration': 300,
'redraw': True
},
'mode': 'immediate',
'transition': {
'duration': 300
}
}
],
'label': year,
'method': 'animate'
}
sliders_dict['steps'].append(slider_step)
figure['layout']['sliders'] = [sliders_dict]
iplot(figure)