I am trying to make subplots (2x2) but in doing so one plot is overlapping over all others.
Code:
import random
import pandas as pd
import numpy as np
import plotly_express as px
from plotly.subplots import make_subplots
import plotly
import plotly.graph_objects as go
import dash
import dash_core_components as dcc
import dash_html_components as html
import dash_bootstrap_components as dbc
from dash.dependencies import Input, Output, State
df_copy = pd.read_csv("data.csv")
card_graph2 = dbc.Card([dbc.CardBody(dcc.Graph(id="id-graph2", figure={})),])
card_graph1 = dbc.Card(
[
dbc.CardBody(
[
dcc.Dropdown(
id="demo-dropdown",
options=[
{"label": str(item), "value": str(item)}
for item in sorted(df_copy["country_txt"].unique())
],
placeholder="Select a country...",
value="United States",
optionHeight=25,
searchable=True,
search_value="",
clearable=True,
),
dcc.Graph(id="id-graph1", figure={}),
],
),
]
)
card3 = dbc.Card(
[
dbc.CardBody(
[
dcc.Graph(id="cities", figure={}),
# dcc.Graph(id="donut", figure={}),
# dcc.Graph(id="casualities", figure={}),
# dcc.Graph(id="terror-group", figure={}),
]
)
]
)
app = dash.Dash(__name__)
app.layout = html.Div(
[
dbc.Row(
[
dbc.Col(
[
dbc.CardHeader(
[html.H1("Terrorism Around the Globe"), html.P("")]
)
],
style={
"text-align": "left",
"font-size": "100%",
"color": "black",
"font-weight": "bold",
"padding-top": "1px",
"padding-right": "1px",
"padding-bottom": " 1px",
"padding-left": "1px",
"margin-left": "2%",
},
),
# dbc.Col(
# html.Img(
# src=app.get_asset_url("terrorism_logo.jpg"),
# style={
# "height": "60px",
# "width": "auto",
# "margin": "0px",
# "padding-top": "0px",
# "padding-bottom": "0px",
# "display": "inline",
# "float": "right",
# },
# )
# ),
],
className="one-third column",
),
dbc.Row(
[
dbc.Col(
card_graph1,
style={
"width": "47%",
"display": "inline-block",
"margin-left": "2%",
"padding-top": "0px",
},
),
dbc.Col(
card_graph2,
style={
"width": "47%",
"display": "inline-block",
"margin-right": "2%",
"margin-left": "2%",
},
),
],
justify="around",
),
dbc.Row(dbc.Col(card3, style={"margin-left": "2%", "margin-right": "2%"})),
],
style={"background-color": "#f9f9f9"},
)
@app.callback(Output("id-graph1", "figure"), [Input("demo-dropdown", "value")])
def update_output(value):
df_sub = df_copy.loc[df_copy["country_txt"] == value]
random.seed(1)
# print(df_sub.head())
# create graph
location = [
(
go.Scattermapbox(
lon=df_sub["longitude"],
lat=df_sub["latitude"],
mode="markers",
marker=dict(size=10, allowoverlap=False, opacity=0.7, color="crimson"),
hovertemplate=["casualities:%{casualities_median}", "city:%{city}"],
hovertext=["casualities_median"],
)
)
]
# return graph
return {
"data": location,
"layout": go.Layout(
uirevision="foo",
hovermode="closest",
hoverdistance=2,
mapbox=dict(
accesstoken=mapbox_access_token,
style="light",
center=dict(
lat=random.choice(df_sub["latitude"].tolist()),
lon=random.choice(df_sub["longitude"].tolist()),
),
zoom=4,
),
),
}
@app.callback(Output("id-graph2", "figure"), [Input("demo-dropdown", "value")])
def update_graph(drop_value):
dff = df_copy.loc[df_copy["country_txt"] == drop_value]
fig = px.bar(
dff["weapon_type"].value_counts()[:10], title=f"Weapons used in {drop_value}"
)
return fig
@app.callback(Output("cities", "figure"), [Input("demo-dropdown", "value")])
def subplot_graph(drop_value):
dff_sub = df_copy.loc[df_copy["country_txt"] == drop_value]
fig = make_subplots(
rows=2,
cols=2,
specs=[
[{"type": "bar"}, {"type": "pie"}],
[{"type": "scatter"}, {"type": "bar"}],
],
)
# Figure1
fig.add_trace(
go.Bar(y=dff_sub["city"].value_counts()[:10]), row=1, col=1,
)
# Figure2
fig.add_trace(
go.Pie(
labels=dff_sub["success"].value_counts().index,
values=dff_sub["success"].value_counts(),
hole=0.4,
)
)
# Figure3
fig.add_trace(
go.Scatter(x=dff_sub["year"], y=dff_sub["casualities"], mode="lines",),
row=2,
col=1,
)
# Figure4
fig.add_trace(
go.Bar(x=dff_sub["group"].value_counts()[:10]), row=2, col=2,
)
# fig.layout.yaxis(domain=[0, 0.25], row=1, col=1)
# fig.layout.yaxis(domain=[0.26, 0.5], row=1, col=2)
# fig.layout.yaxis(domain=[0.51, 0.75], row=2, col=1)
# fig.layout.yaxis(domain=[0.76, 1], row=2, col=2)
fig.update_layout(
height=800, width=1200, showlegend=False,
)
return fig
if __name__ == "__main__":
app.run_server(debug=False)
Screenshot of Plots:
As you can see pie chart
is overlapping and ideally it should be at (row = 1 , col =2) .
In code section , subplot function
is the part where changes needs to done for this.
Any help will be highly appreciated.