from dash import Dash, dcc # https://dash.plotly.com/
import dash_ag_grid as dag
import plotly.express as px # https://plotly.com/python/
import pandas as pd
# Download of complete CSV sheet from Google Drive: https://drive.google.com/file/d/1ZdH5C3kWaiRR3fOotvdW8l351YrKQJgG/view?usp=sharing
# This data app only uses 200 rows of the data becuase py.cafe limits data file size
df = pd.read_csv("Open_Parking_and_Camera_Violations.csv")
grid = dag.AgGrid(
rowData=df.to_dict("records"),
columnDefs=[{"field": i, 'filter': True, 'sortable': True} for i in df.columns],
dashGridOptions={"pagination": True},
# columnSize="sizeToFit"
)
# Make sure "Payment Amount" is numeric
df["Payment Amount"] = pd.to_numeric(df["Payment Amount"], errors="coerce")
# Group by state and sum "Amount Due"
state_totals = df.groupby("State")["Payment Amount"].sum().reset_index()
# Split top N and others
top_n = 5
top_states = state_totals.sort_values("Payment Amount", ascending=False).reset_index(drop=True)
top = top_states.iloc[:top_n]
others = top_states.iloc[top_n:]
# Add "Others" row
others_total = others["Payment Amount"].sum()
others_row = pd.DataFrame([{"State": "Others", "Payment Amount": others_total}])
top = pd.concat([top, others_row], ignore_index=True)
# Extract list of states, with "Others" at the end
states_order = [s for s in top["State"] if s != "Others"] + ["Others"]
# Create pie chart
fig = px.pie(
top,
names="State",
values="Payment Amount",
title="Total Payment Amount by State (Top 5 + Others)",
hole=0.3, # optional: makes it a donut chart
category_orders={"State": states_order} # <-- force legend order here
)
fig.update_layout(
title="Total Payment Amount by State",
legend=dict(
orientation="h", # horizontal layout
yanchor="bottom",
y=-0.1,
xanchor="center",
x=0.5,
font=dict(size=12)
),
height=850, # increase figure height
width=600 # optional: wider chart
)
app = Dash()
app.layout = [
grid, dcc.Graph(figure=fig)]