| # import panel as pn | |
| # import pandas as pd | |
| # import altair as alt | |
| # # we want to use bootstrap/template, tell Panel to load up what we need | |
| # pn.extension(design='bootstrap') | |
| # # we want to use vega, tell Panel to load up what we need | |
| # pn.extension('vega') | |
| # # create a basic template using bootstrap | |
| # template = pn.template.BootstrapTemplate( | |
| # title='SI649 Altair Assignment', | |
| # ) | |
| # # the main column will hold our key content | |
| # maincol = pn.Column() | |
| # # add some markdown to the main column | |
| # maincol.append("# Polling Data Interactive Visualization") | |
| # # load up a dataframe and show it in the main column | |
| # df1=pd.read_csv("https://raw.githubusercontent.com/dallascard/SI649_public/main/altair_hw3/approval_polllist.csv") | |
| # df2=pd.read_csv("https://raw.githubusercontent.com/dallascard/SI649_public/main/altair_hw3/approval_topline.csv") | |
| # # fix the time stamps and reorganize the data to combine approve and disapprove into one column | |
| # df2['timestamp']=pd.to_datetime(df2['timestamp']) | |
| # df2=pd.melt(df2, id_vars=['president', 'subgroup', 'timestamp'], value_vars=['approve','disapprove']).rename(columns={'variable':'choice', 'value':'rate'}) | |
| # # Selection widgets | |
| # subgroup_select = pn.widgets.Select(name='Select', options=['Adults', 'Voters', 'All polls']) | |
| # date_slider = pn.widgets.DateRangeSlider(name='Date Range Slider', start=df2['timestamp'].min(), end=df2['timestamp'].max()) | |
| # moving_avg_slider = pn.widgets.IntSlider(name='Moving Average Window', start=1, end=100, step=1) | |
| # # Bind the widgets to the create_plot function | |
| # @pn.depends(subgroup_select.param.value, date_slider.param.value, moving_avg_slider.param.value) | |
| # def create_plot(subgroup, date_range, moving_av_window): | |
| # data = df2[(df2['subgroup'] == subgroup) & (df2['choice'] == "approve") & (df2['timestamp'].dt.date.between(date_range[0], date_range[1]))] | |
| # min_rate = df2['rate'].min() | |
| # max_rate = df2['rate'].max() | |
| # data = data.sort_values('timestamp') | |
| # data['moving_avg'] = data['rate'].rolling(window=moving_av_window, min_periods=1).mean() | |
| # # Line chart for moving average | |
| # line = alt.Chart(data).mark_line(interpolate='natural').encode( | |
| # x=alt.X('timestamp:T', axis=alt.Axis(title='', format='%b %d, %Y')), | |
| # y=alt.Y('moving_avg:Q', axis=alt.Axis(title='approve,mov_avg'), scale=alt.Scale(domain=[min_rate, max_rate])), | |
| # color=alt.value('red') | |
| # ) | |
| # # Scatter plot for individual data points | |
| # points = alt.Chart(data).mark_point().encode( | |
| # x=alt.X('timestamp:T'), | |
| # y=alt.Y('rate:Q', axis=alt.Axis(title='approve,mov_avg'), scale=alt.Scale(domain=[min_rate, max_rate])), | |
| # color=alt.value('gray'), | |
| # tooltip=['timestamp:T', 'rate:Q'] | |
| # ) | |
| # # Combine line chart and scatter plot | |
| # plot = alt.layer(points, line).resolve_scale(y='shared') | |
| # return plot | |
| # # app = pn.Column("# Polling Data Interactive Visualization", pn.panel(create_plot, reactive=True), subgroup_select, date_slider, moving_avg_slider) | |
| # maincol.append(pn.panel(create_plot, reactive=True)) | |
| # maincol.append(subgroup_select) | |
| # maincol.append(date_slider) | |
| # maincol.append(moving_avg_slider) | |
| # # add the main column to the template | |
| # template.main.append(maincol) | |
| # # Indicate that the template object is the "application" and serve it | |
| # template.servable(title="SI649 Altair Assignment") | |
| import panel as pn | |
| import pandas as pd | |
| import altair as alt | |
| # Ensure Panel and Altair extensions are loaded | |
| pn.extension('vega', design='bootstrap') | |
| # Load data | |
| df1 = pd.read_csv("https://raw.githubusercontent.com/dallascard/SI649_public/main/altair_hw3/approval_polllist.csv") | |
| df2 = pd.read_csv("https://raw.githubusercontent.com/dallascard/SI649_public/main/altair_hw3/approval_topline.csv") | |
| # Data preprocessing | |
| df2['timestamp'] = pd.to_datetime(df2['timestamp']) | |
| df2 = pd.melt(df2, id_vars=['president', 'subgroup', 'timestamp'], value_vars=['approve', 'disapprove']).rename(columns={'variable': 'choice', 'value': 'rate'}) | |
| # Widgets | |
| subgroup_select = pn.widgets.Select(name='Select Subgroup', options=['Adults', 'Voters', 'All polls']) | |
| date_slider = pn.widgets.DateRangeSlider(name='Date Range Slider', start=df2['timestamp'].min(), end=df2['timestamp'].max()) | |
| moving_avg_slider = pn.widgets.IntSlider(name='Moving Average Window', start=1, end=100, step=1) | |
| # Visualization function | |
| def create_plot(subgroup, date_range, moving_av_window): | |
| start_date, end_date = date_range[0], date_range[1] # Convert to date | |
| data = df2[(df2['subgroup'] == subgroup) & (df2['choice'] == "approve") & (pd.to_datetime(df2['timestamp']) >= pd.to_datetime(start_date)) & (pd.to_datetime(df2['timestamp']) <= pd.to_datetime(end_date))] | |
| min_rate = df2['rate'].min() | |
| max_rate = df2['rate'].max() | |
| data = data.sort_values('timestamp') | |
| data['moving_avg'] = data['rate'].rolling(window=moving_av_window, min_periods=1).mean() | |
| # Line chart for moving average | |
| line = alt.Chart(data).mark_line(interpolate='natural').encode( | |
| x=alt.X('timestamp:T', axis=alt.Axis(title='', format='%b %d, %Y')), | |
| y=alt.Y('moving_avg:Q', axis=alt.Axis(title='approve,mov_avg'), scale=alt.Scale(domain=[min_rate, max_rate])), | |
| color=alt.value('red') | |
| ) | |
| # Scatter plot for individual data points | |
| points = alt.Chart(data).mark_point().encode( | |
| x=alt.X('timestamp:T'), | |
| y=alt.Y('rate:Q', axis=alt.Axis(title='approve,mov_avg'), scale=alt.Scale(domain=[min_rate, max_rate])), | |
| color=alt.value('gray'), | |
| tooltip=['timestamp:T', 'rate:Q'] | |
| ) | |
| # Combine line chart and scatter plot | |
| plot = alt.layer(points, line).resolve_scale(y='shared') | |
| return plot | |
| # Main layout | |
| main_layout = pn.Column( | |
| "# Polling Data Interactive Visualization", | |
| pn.panel(create_plot, reactive=True), | |
| subgroup_select, | |
| date_slider, | |
| moving_avg_slider, | |
| ) | |
| # Create a basic template | |
| template = pn.template.BootstrapTemplate(title='SI649 Altair Assignment') | |
| template.main.append(main_layout) | |
| # Serve the application | |
| template.servable() | |