Skip to main content
Data Visualization
CHAPTER 17 Beginner

Interactive Visualization with Plotly

Updated: May 18, 2026
5 min read

# CHAPTER 17

Interactive Visualization with Plotly

1. Chapter Introduction

Plotly creates web-ready interactive charts with hover tooltips, zoom, pan, and filter — without writing JavaScript. It's the bridge between Python analysis and web-embedded, executive-facing dashboards.

2. Plotly Express — One-Line Charts

python
12345678910111213141516171819202122
import plotly.express as px
import pandas as pd
import numpy as np

np.random.seed(42)
df = pd.DataFrame({
    'Month': pd.date_range('2024-01', periods=12, freq='MS'),
    'Revenue': np.random.normal(80000, 15000, 12).clip(50000, 120000),
    'Region': np.random.choice(['North', 'South', 'East', 'West'], 12)
})

# Line chart — interactive with hover
fig = px.line(df, x='Month', y='Revenue',
               title='Monthly Revenue 2024',
               markers=True,
               labels={'Revenue': 'Revenue ($)', 'Month': ''},
               template='plotly_white')
fig.update_traces(line_color='#1565C0', line_width=3)
fig.update_layout(hovermode='x unified')  # Aligned hover on x-axis
fig.show()  # Opens in browser
# fig.write_html('revenue.html')       # Save as interactive HTML
# fig.write_image('revenue.png')       # Save as static image (needs kaleido)

3. Rich Interactive Charts

python
12345678910111213141516171819202122232425262728
import plotly.express as px
import plotly.graph_objects as go
from plotly.subplots import make_subplots
import pandas as pd
import numpy as np

# Scatter with animation (evolution over time)
gapminder = px.data.gapminder()
fig = px.scatter(gapminder, x='gdpPercap', y='lifeExp',
                  size='pop', color='continent',
                  hover_name='country',
                  animation_frame='year',
                  animation_group='country',
                  log_x=True,
                  size_max=60,
                  title='GDP vs Life Expectancy Over Time',
                  template='plotly_white')
fig.update_layout(height=550)
fig.show()

# Choropleth map
fig2 = px.choropleth(gapminder[gapminder['year'] == 2007],
                      locations='iso_alpha',
                      color='gdpPercap',
                      hover_name='country',
                      color_continuous_scale=px.colors.sequential.Plasma,
                      title='Global GDP per Capita — 2007')
fig2.show()

4. Graph Objects — Full Control

python
12345678910111213141516171819202122232425262728293031
import plotly.graph_objects as go
from plotly.subplots import make_subplots
import numpy as np

np.random.seed(42)
months = ['Jan','Feb','Mar','Apr','May','Jun','Jul','Aug','Sep','Oct','Nov','Dec']
sales_2023 = np.random.randint(60000, 100000, 12)
sales_2024 = sales_2023 * np.random.uniform(1.05, 1.25, 12)

fig = make_subplots(rows=1, cols=2, subplot_titles=['Revenue Trend', 'Revenue Comparison'],
                     specs=[[{'type': 'scatter'}, {'type': 'bar'}]])

# Trace 1: Line
fig.add_trace(go.Scatter(x=months, y=sales_2023, mode='lines+markers',
                           name='2023', line=dict(color='#90CAF9', width=2)), row=1, col=1)
fig.add_trace(go.Scatter(x=months, y=sales_2024, mode='lines+markers',
                           name='2024', line=dict(color='#1565C0', width=3)), row=1, col=1)

# Trace 2: Grouped bar
fig.add_trace(go.Bar(x=months, y=sales_2023, name='2023',
                      marker_color='#90CAF9', showlegend=False), row=1, col=2)
fig.add_trace(go.Bar(x=months, y=sales_2024, name='2024',
                      marker_color='#1565C0', showlegend=False), row=1, col=2)

fig.update_layout(title_text='Interactive Business Dashboard — 2023 vs 2024',
                   title_font_size=16, template='plotly_white',
                   barmode='group', height=450, hovermode='x unified',
                   legend=dict(orientation='h', y=-0.15))

fig.update_yaxes(tickprefix='$', tickformat=',.0f')
fig.show()

5. Common Mistakes

  • fig.show() instead of fig.writehtml(): show() opens in browser (local dev). For production/sharing, always writehtml() for interactive or writeimage() for static.
  • Using Plotly without template='plotlywhite': Default dark template (plotlydark) looks great in notebooks but poor in reports. Specify template explicitly.

6. MCQs

Question 1

Plotly's main advantage over Matplotlib?

Question 2

px.scatter() creates?

Question 3

animationframe='year' in plotly?

Question 4

px.choropleth() creates?

Question 5

fig.writehtml('chart.html') saves?

Question 6

hovermode='x unified' shows?

Question 7

makesubplots() in Plotly is for?

Question 8

go.Scatter vs px.scatter?

Question 9

template='plotlywhite' applies?

Question 10

fig.writeimage() requires?

7. Interview Questions

  • Q: What is the difference between Plotly Express and Plotly Graph Objects?
  • Q: How do you export a Plotly chart as an interactive HTML file?

8. Summary

Plotly Express: one-line interactive charts from DataFrames. Plotly Graph Objects: full trace-level control for complex layouts. makesubplots for multi-panel interactive figures. Always use template='plotlywhite' for reports. writehtml() for interactive sharing, writeimage() (needs kaleido) for static export.

9. Next Chapter Recommendation

In Chapter 18: Dashboard Design Principles, we learn the UX and visual design principles behind professional KPI dashboards before coding them.

Finish this Chapter

Save your progress on your learning path and prepare for coding interview challenges.

Discussion

Join the discussion

Log in or create a free account to participate.

Sort: ·