jchoo commited on
Commit
3ea7a36
·
verified ·
1 Parent(s): 4fa6a98

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +825 -124
app.py CHANGED
@@ -1,147 +1,848 @@
1
- import io
2
- import random
3
- from typing import List, Tuple
4
-
5
- import aiohttp
 
 
 
 
 
 
 
 
 
 
 
6
  import panel as pn
7
- from PIL import Image
8
- from transformers import CLIPModel, CLIPProcessor
9
 
10
- pn.extension(design="bootstrap", sizing_mode="stretch_width")
 
 
 
 
11
 
12
- ICON_URLS = {
13
- "brand-github": "https://github.com/holoviz/panel",
14
- "brand-twitter": "https://twitter.com/Panel_Org",
15
- "brand-linkedin": "https://www.linkedin.com/company/panel-org",
16
- "message-circle": "https://discourse.holoviz.org/",
17
- "brand-discord": "https://discord.gg/AXRHnJU6sP",
18
- }
 
 
 
 
 
 
 
19
 
 
 
 
 
 
20
 
21
- async def random_url(_):
22
- pet = random.choice(["cat", "dog"])
23
- api_url = f"https://api.the{pet}api.com/v1/images/search"
24
- async with aiohttp.ClientSession() as session:
25
- async with session.get(api_url) as resp:
26
- return (await resp.json())[0]["url"]
27
 
 
 
28
 
29
- @pn.cache
30
- def load_processor_model(
31
- processor_name: str, model_name: str
32
- ) -> Tuple[CLIPProcessor, CLIPModel]:
33
- processor = CLIPProcessor.from_pretrained(processor_name)
34
- model = CLIPModel.from_pretrained(model_name)
35
- return processor, model
36
 
 
 
 
 
 
 
 
 
 
 
37
 
38
- async def open_image_url(image_url: str) -> Image:
39
- async with aiohttp.ClientSession() as session:
40
- async with session.get(image_url) as resp:
41
- return Image.open(io.BytesIO(await resp.read()))
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
42
 
 
 
43
 
44
- def get_similarity_scores(class_items: List[str], image: Image) -> List[float]:
45
- processor, model = load_processor_model(
46
- "openai/clip-vit-base-patch32", "openai/clip-vit-base-patch32"
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
47
  )
48
- inputs = processor(
49
- text=class_items,
50
- images=[image],
51
- return_tensors="pt", # pytorch tensors
 
 
 
 
52
  )
53
- outputs = model(**inputs)
54
- logits_per_image = outputs.logits_per_image
55
- class_likelihoods = logits_per_image.softmax(dim=1).detach().numpy()
56
- return class_likelihoods[0]
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
57
 
 
 
58
 
59
- async def process_inputs(class_names: List[str], image_url: str):
60
- """
61
- High level function that takes in the user inputs and returns the
62
- classification results as panel objects.
63
- """
64
- try:
65
- main.disabled = True
66
- if not image_url:
67
- yield "##### ⚠️ Provide an image URL"
68
- return
69
-
70
- yield "##### ⚙ Fetching image and running model..."
71
- try:
72
- pil_img = await open_image_url(image_url)
73
- img = pn.pane.Image(pil_img, height=400, align="center")
74
- except Exception as e:
75
- yield f"##### 😔 Something went wrong, please try a different URL!"
76
- return
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
77
 
78
- class_items = class_names.split(",")
79
- class_likelihoods = get_similarity_scores(class_items, pil_img)
80
 
81
- # build the results column
82
- results = pn.Column("##### 🎉 Here are the results!", img)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
83
 
84
- for class_item, class_likelihood in zip(class_items, class_likelihoods):
85
- row_label = pn.widgets.StaticText(
86
- name=class_item.strip(), value=f"{class_likelihood:.2%}", align="center"
87
- )
88
- row_bar = pn.indicators.Progress(
89
- value=int(class_likelihood * 100),
90
- sizing_mode="stretch_width",
91
- bar_color="secondary",
92
- margin=(0, 10),
93
- design=pn.theme.Material,
94
- )
95
- results.append(pn.Column(row_label, row_bar))
96
- yield results
97
- finally:
98
- main.disabled = False
99
-
100
-
101
- # create widgets
102
- randomize_url = pn.widgets.Button(name="Randomize URL", align="end")
103
-
104
- image_url = pn.widgets.TextInput(
105
- name="Image URL to classify",
106
- value=pn.bind(random_url, randomize_url),
107
- )
108
- class_names = pn.widgets.TextInput(
109
- name="Comma separated class names",
110
- placeholder="Enter possible class names, e.g. cat, dog",
111
- value="cat, dog, parrot",
112
- )
113
 
114
- input_widgets = pn.Column(
115
- "##### 😊 Click randomize or paste a URL to start classifying!",
116
- pn.Row(image_url, randomize_url),
117
- class_names,
118
- )
119
 
120
- # add interactivity
121
- interactive_result = pn.panel(
122
- pn.bind(process_inputs, image_url=image_url, class_names=class_names),
123
- height=600,
124
- )
125
 
126
- # add footer
127
- footer_row = pn.Row(pn.Spacer(), align="center")
128
- for icon, url in ICON_URLS.items():
129
- href_button = pn.widgets.Button(icon=icon, width=35, height=35)
130
- href_button.js_on_click(code=f"window.open('{url}')")
131
- footer_row.append(href_button)
132
- footer_row.append(pn.Spacer())
133
-
134
- # create dashboard
135
- main = pn.WidgetBox(
136
- input_widgets,
137
- interactive_result,
138
- footer_row,
139
  )
140
 
141
- title = "Panel Demo - Image Classification"
142
- pn.template.BootstrapTemplate(
143
- title=title,
144
- main=main,
145
- main_max_width="min(50%, 698px)",
146
- header_background="#F08080",
147
- ).servable(title=title)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import os
2
+ import re
3
+ import csv
4
+ import json
5
+ import math
6
+ import openai
7
+ import numpy as np
8
+ import pandas as pd
9
+ import seaborn as sns
10
+ import matplotlib.pyplot as plt
11
+ from tqdm import tqdm
12
+ from scipy import stats
13
+ from datetime import datetime
14
+ from collections import defaultdict, Counter
15
+ from matplotlib.ticker import FuncFormatter
16
+ from matplotlib.colors import ListedColormap
17
  import panel as pn
18
+ import altair as alt
 
19
 
20
+ def choices_to_df(choices, hue):
21
+ df = pd.DataFrame(choices, columns=['choices'])
22
+ df['hue'] = hue
23
+ df['hue'] = df['hue'].astype(str)
24
+ return df
25
 
26
+ binrange = (0, 100)
27
+ moves = []
28
+ with open('dictator.csv', 'r') as f:
29
+ reader = csv.reader(f)
30
+ header = next(reader)
31
+ col2idx = {col: idx for idx, col in enumerate(header)}
32
+ for row in reader:
33
+ record = {col: row[idx] for col, idx in col2idx.items()}
34
+
35
+ if record['Role'] != 'first': continue
36
+ if int(record['Round']) > 1: continue
37
+ if int(record['Total']) != 100: continue
38
+ if record['move'] == 'None': continue
39
+ if record['gameType'] != 'dictator': continue
40
 
41
+ move = float(record['move'])
42
+ if move < binrange[0] or \
43
+ move > binrange[1]: continue
44
+
45
+ moves.append(move)
46
 
47
+ df_dictator_human = choices_to_df(moves, 'Human')
 
 
 
 
 
48
 
49
+ choices = [50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0]
50
+ df_dictator_gpt4 = choices_to_df(choices, hue=str('ChatGPT-4'))
51
 
52
+ choices = [25, 35, 70, 30, 20, 25, 40, 80, 30, 30, 40, 30, 30, 30, 30, 30, 40, 40, 30, 30, 40, 30, 60, 20, 40, 25, 30, 30, 30]
53
+ df_dictator_turbo = choices_to_df(choices, hue=str('ChatGPT-3'))
 
 
 
 
 
54
 
55
+ def extract_choices(recrods):
56
+ choices = [extract_amout(
57
+ messages[-1]['content'],
58
+ prefix='$',
59
+ print_except=True,
60
+ type=float) for messages in records['messages']
61
+ ]
62
+ choices = [x for x in choices if x is not None]
63
+ # print(choices)
64
+ return choices
65
 
66
+ def extract_amout(
67
+ message,
68
+ prefix='',
69
+ print_except=True,
70
+ type=float,
71
+ brackets='[]'
72
+ ):
73
+ try:
74
+ matches = extract_brackets(message, brackets=brackets)
75
+ matches = [s[len(prefix):] \
76
+ if s.startswith(prefix) \
77
+ else s for s in matches]
78
+ invalid = False
79
+ if len(matches) == 0:
80
+ invalid = True
81
+ for i in range(len(matches)):
82
+ if matches[i] != matches[0]:
83
+ invalid = True
84
+ if invalid:
85
+ raise ValueError('Invalid answer: %s' % message)
86
+ return type(matches[0])
87
+ except Exception as e:
88
+ if print_except: print(e)
89
+ return None
90
 
91
+ records = json.load(open('dictator_wo_ex_2023_03_13-11_24_07_PM.json', 'r'))
92
+ choices = extract_choices(records)
93
 
94
+ # Plot 1 - Dictator (altruism)
95
+ def plot_facet(
96
+ df_list,
97
+ x='choices',
98
+ hue='hue',
99
+ palette=None,
100
+ binrange=None,
101
+ bins=10,
102
+ # binwidth=10,
103
+ stat='count',
104
+ x_label='',
105
+ sharex=True,
106
+ sharey=False,
107
+ subplot=sns.histplot,
108
+ xticks_locs=None,
109
+ # kde=False,
110
+ **kwargs
111
+ ):
112
+ data = pd.concat(df_list)
113
+ if binrange is None:
114
+ binrange = (data[x].min(), data[x].max())
115
+ g = sns.FacetGrid(
116
+ data, row=hue, hue=hue,
117
+ palette=palette,
118
+ aspect=2, height=2,
119
+ sharex=sharex, sharey=sharey,
120
+ despine=True,
121
  )
122
+ g.map_dataframe(
123
+ subplot,
124
+ x=x,
125
+ # kde=kde,
126
+ binrange=binrange,
127
+ bins=bins,
128
+ stat=stat,
129
+ **kwargs
130
  )
131
+ # g.add_legend(title='hue')
132
+ g.set_axis_labels(x_label, stat.title())
133
+ g.set_titles(row_template="{row_name}")
134
+ for ax in g.axes.flat:
135
+ ax.yaxis.set_major_formatter(
136
+ FuncFormatter(lambda y, pos: '{:.2f}'.format(y))
137
+ )
138
+
139
+ binwidth = (binrange[1] - binrange[0]) / bins
140
+ if xticks_locs is None:
141
+ locs = np.linspace(binrange[0], binrange[1], bins//2+1)
142
+ locs = [loc + binwidth for loc in locs]
143
+ else:
144
+ locs = xticks_locs
145
+ labels = [str(int(loc)) for loc in locs]
146
+ locs = [loc + 0.5*binwidth for loc in locs]
147
+ plt.xticks(locs, labels)
148
+
149
+ g.set(xlim=binrange)
150
+ return g
151
 
152
+ df = df_dictator_human
153
+ bin_ranges = [0, 10, 30, 50, 70]
154
 
155
+ # Calculate density as a percentage
156
+ density_percentage = df['choices'].value_counts(normalize=True)
157
+
158
+ # Create a DataFrame with the density percentages
159
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
160
+
161
+ # Create the bar chart using Altair
162
+ chart1 = alt.Chart(density_df).mark_bar().encode(
163
+ x=alt.X('choices:O', bin=alt.Bin(extent=[0, 70], step=10), axis=None),
164
+ y='density:Q',
165
+ color=alt.value('steelblue'),
166
+ tooltip=['density']
167
+ ).properties(
168
+ width=500,
169
+ title='Density of Choices'
170
+ ).interactive()
171
+
172
+ df = df_dictator_gpt4
173
+ bin_ranges = [0, 10, 30, 50, 70]
174
+
175
+ # Calculate density as a percentage
176
+ density_percentage = df['choices'].value_counts(normalize=True)
177
+
178
+ # Create a DataFrame with the density percentages
179
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
180
+
181
+ # Create the bar chart using Altair
182
+ chart2 = alt.Chart(density_df).mark_bar().encode(
183
+ x=alt.X('choices:O', bin=alt.Bin(extent=[0, 70], step=10), axis=None),
184
+ y='density:Q',
185
+ color=alt.value('orange'),
186
+ tooltip=['density']
187
+ ).properties(
188
+ width=500,
189
+ title='Density of Choices'
190
+ ).interactive()
191
+
192
+ df = df_dictator_turbo
193
+
194
+ bin_ranges = [0, 10, 30, 50, 70]
195
+
196
+ # Calculate density as a percentage
197
+ density_percentage = df['choices'].value_counts(normalize=True)
198
+
199
+ # Create a DataFrame with the density percentages
200
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
201
+
202
+ # Create the bar chart using Altair
203
+ chart3 = alt.Chart(density_df).mark_bar().encode(
204
+ x=alt.X('choices:O', bin=alt.Bin(extent=[0, 70], step=10)),
205
+ y='density:Q',
206
+ color=alt.value('green'),
207
+ tooltip=['density']
208
+ ).properties(
209
+ width=500,
210
+ title='Density of Choices'
211
+ ).interactive()
212
+
213
+ final = alt.vconcat(chart1, chart2, chart3).resolve_scale(x='shared')
214
+
215
+ #Plot 2 - - Ultimatum (Fairness)
216
+ df = pd.read_csv('ultimatum_strategy.csv')
217
+ df = df[df['gameType'] == 'ultimatum_strategy']
218
+ df = df[df['Role'] == 'player']
219
+ df = df[df['Round'] == 1]
220
+ df = df[df['Total'] == 100]
221
+ df = df[df['move'] != 'None']
222
+ df['propose'] = df['move'].apply(lambda x: eval(x)[0])
223
+ df['accept'] = df['move'].apply(lambda x: eval(x)[1])
224
+ df = df[(df['propose'] >= 0) & (df['propose'] <= 100)]
225
+ df = df[(df['accept'] >= 0) & (df['accept'] <= 100)]
226
+
227
+ df_ultimatum_1_human = choices_to_df(list(df['propose']), 'Human')
228
+ df_ultimatum_2_human = choices_to_df(list(df['accept']), 'Human')
229
+
230
+ choices = [50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0, 50.0]
231
+ df_ultimatum_1_gpt4 = choices_to_df(choices, hue=str('ChatGPT-4'))
232
+
233
+ choices = [40, 40, 40, 30, 70, 70, 50, 40, 40, 40, 40, 40, 40, 40, 40, 40, 40, 40, 30, 30, 35, 50, 40, 70, 40, 60, 60, 70, 40, 50]
234
+ df_ultimatum_1_turbo = choices_to_df(choices, hue=str('ChatGPT-3'))
235
+
236
+ choices = [50.0, 50.0, 50.0, 1.0, 1.0, 1.0, 50.0, 25.0, 50.0, 1.0, 1.0, 20.0, 50.0, 50.0, 50.0, 20.0, 50.0, 1.0, 1.0, 1.0, 50.0, 50.0, 50.0, 1.0, 1.0, 1.0, 20.0, 1.0] + [0, 1]
237
+ df_ultimatum_2_gpt4 = choices_to_df(choices, hue=str('ChatGPT-4'))
238
+
239
+ choices = [None, 50, 50, 50, 50, 30, None, None, 30, 33.33, 40, None, 50, 40, None, 1, 30, None, 10, 50, 30, 10, 30, None, 30, None, 10, 30, 30, 30]
240
+ df_ultimatum_2_turbo = choices_to_df(choices, hue=str('ChatGPT-3'))
241
+
242
+ choices = [50.0, 50.0, 10.0, 40.0, 20.0, 50.0, 1.0, 1.0, 50.0, 1.0, 50.0, 50.0, 20.0, 10.0, 50.0, 20.0, 1.0, 1.0, 50.0, 1.0, 20.0, 1.0, 50.0, 50.0, 20.0, 20.0, 50.0, 20.0, 1.0, 50.0]
243
+ df_ultimatum_2_gpt4_female = choices_to_df(choices, hue='ChatGPT-4 Female')
244
+
245
+ choices = [1.0, 1.0, 1.0, 20.0, 1.0, 1.0, 50.0, 1.0, 1.0, 50.0, 50.0, 50.0, 20.0, 20.0, 1.0, 50.0, 1.0, 1.0, 1.0, 50.0, 20.0, 1.0, 50.0, 20.0, 20.0, 10.0, 50.0, 1.0, 1.0, 1.0]
246
+ df_ultimatum_2_gpt4_male = choices_to_df(choices, hue='ChatGPT-4 Male')
247
+
248
+ choices = [40.0, 1.0, 1.0, 20.0, 1.0, 20.0, 50.0, 50.0, 1.0, 1.0, 1.0, 50.0, 1.0, 20.0, 50.0, 10.0, 50.0, 1.0, 1.0, 20.0, 1.0, 50.0, 20.0, 20.0, 20.0, 1.0, 1.0, 1.0, 1.0, 40.0]
249
+ df_ultimatum_2_gpt4_US = choices_to_df(choices, hue='ChatGPT-4 US')
250
+
251
+ choices = [1.0, 1.0, 20.0, 50.0, 1.0, 1.0, 1.0, 1.0, 20.0, 20.0, 50.0, 20.0, 20.0, 50.0, 20.0, 1.0, 40.0, 50.0, 1.0, 1.0, 1.0, 20.0, 1.0, 1.0, 50.0, 50.0, 1.0, 1.0, 1.0, 1.0]
252
+ df_ultimatum_2_gpt4_Poland = choices_to_df(choices, hue='ChatGPT-4 Poland')
253
+
254
+ choices = [50.0, 1.0, 20.0, 50.0, 50.0, 50.0, 50.0, 1.0, 1.0, 50.0, 1.0, 50.0, 1.0, 50.0, 1.0, 20.0, 1.0, 1.0, 20.0, 50.0, 0.0, 20.0, 1.0, 1.0, 1.0, 1.0, 20.0, 20.0, 50.0, 20.0]
255
+ df_ultimatum_2_gpt4_China = choices_to_df(choices, hue='ChatGPT-4 China')
256
+
257
+ choices = [1.0, 1.0, 1.0, 50.0, 1.0, 1.0, 50.0, 40.0, 1.0, 1.0, 1.0, 1.0, 20.0, 1.0, 1.0, 50.0, 1.0, 50.0, 1.0, 20.0, 1.0, 20.0, 1.0, 50.0, 1.0, 50.0, 20.0, 1.0, 1.0, 50.0]
258
+ df_ultimatum_2_gpt4_UK = choices_to_df(choices, hue='ChatGPT-4 UK')
259
+
260
+ choices = [50.0, 1.0, 20.0, 50.0, 50.0, 50.0, 50.0, 10.0, 1.0, 40.0, 50.0, 20.0, 1.0, 1.0, 1.0, 50.0, 50.0, 20.0, 20.0, 1.0, 1.0, 50.0, 20.0, 50.0, 50.0, 20.0, 1.0, 20.0, 50.0, 1]
261
+ df_ultimatum_2_gpt4_Columbia = choices_to_df(choices, hue='ChatGPT-4 Columbia')
262
+
263
+ choices = [50.0, 1.0, 50.0, 20.0, 20.0, 20.0, 50.0, 20.0, 20.0, 1.0, 1.0, 1.0, 1.0, 20.0, 1.0, 50.0, 1.0, 20.0, 20.0, 50.0, 1.0, 50.0, 1.0, 40.0, 1.0, 20.0, 1.0, 20.0, 1.0, 1.0]
264
+ df_ultimatum_2_gpt4_under = choices_to_df(choices, hue='ChatGPT-4 Undergrad')
265
+
266
+ choices = [1.0, 20.0, 1.0, 40.0, 50.0, 1.0, 1.0, 1.0, 25.0, 20.0, 50.0, 20.0, 50.0, 50.0, 1.0, 50.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 50.0, 20.0, 1.0, 1.0, 1.0, 50.0, 20.0, 20.0]
267
+ df_ultimatum_2_gpt4_grad = choices_to_df(choices, hue='ChatGPT-4 Graduate')
268
+
269
+ df = df_ultimatum_1_human
270
+ bin_ranges = [0, 10, 30, 50, 70]
271
+
272
+ # Calculate density as a percentage
273
+ density_percentage = df['choices'].value_counts(normalize=True)
274
+
275
+ # Create a DataFrame with the density percentages
276
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
277
+
278
+ # Create the bar chart using Altair
279
+ chart1 = alt.Chart(density_df).mark_bar().encode(
280
+ x=alt.X('choices:O', bin=alt.Bin(extent=[0, 70], step=10), axis=None),
281
+ y='density:Q',
282
+ color=alt.value('steelblue'),
283
+ tooltip=['density']
284
+ ).properties(
285
+ width=500,
286
+ title='Density of Choices'
287
+ ).interactive()
288
+
289
+ df = df_ultimatum_1_gpt4
290
+ bin_ranges = [0, 10, 30, 50, 70]
291
+
292
+ # Calculate density as a percentage
293
+ density_percentage = df['choices'].value_counts(normalize=True)
294
+
295
+ # Create a DataFrame with the density percentages
296
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
297
+
298
+ # Create the bar chart using Altair
299
+ chart2 = alt.Chart(density_df).mark_bar().encode(
300
+ x=alt.X('choices:O', bin=alt.Bin(extent=[0, 70], step=10), axis=None),
301
+ y='density:Q',
302
+ color=alt.value('orange'),
303
+ tooltip=['density']
304
+ ).properties(
305
+ width=500,
306
+ title='Density of Choices'
307
+ ).interactive()
308
+
309
+ df = df_ultimatum_1_turbo
310
+ bin_ranges = [0, 10, 30, 50, 70]
311
+
312
+ # Calculate density as a percentage
313
+ density_percentage = df['choices'].value_counts(normalize=True)
314
+
315
+ # Create a DataFrame with the density percentages
316
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
317
+
318
+ # Create the bar chart using Altair
319
+ chart3 = alt.Chart(density_df).mark_bar().encode(
320
+ x=alt.X('choices:O', bin=alt.Bin(extent=[0, 70], step=10)),
321
+ y='density:Q',
322
+ color=alt.value('green'),
323
+ tooltip=['density']
324
+ ).properties(
325
+ width=500,
326
+ title='Density of Choices'
327
+ ).interactive()
328
+
329
+ final2 = alt.vconcat(chart1, chart2, chart3).resolve_scale(x='shared')
330
+
331
+ #Plot 3 - - Ultimatum (Responder) (spite)
332
+ df = df_ultimatum_2_human
333
+ bin_ranges = [0, 10, 30, 50, 70]
334
+
335
+ # Calculate density as a percentage
336
+ density_percentage = df['choices'].value_counts(normalize=True)
337
+
338
+ # Create a DataFrame with the density percentages
339
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
340
+
341
+ # Create the bar chart using Altair
342
+ chart1 = alt.Chart(density_df).mark_bar().encode(
343
+ x=alt.X('choices:O', bin=alt.Bin(extent=[0, 70], step=10), axis=None),
344
+ y='density:Q',
345
+ color=alt.value('steelblue'),
346
+ tooltip=['density']
347
+ ).properties(
348
+ width=500,
349
+ title='Density of Choices'
350
+ ).interactive()
351
+
352
+ df = df_ultimatum_2_gpt4
353
+ bin_ranges = [0, 10, 30, 50, 70]
354
+
355
+ # Calculate density as a percentage
356
+ density_percentage = df['choices'].value_counts(normalize=True)
357
+
358
+ # Create a DataFrame with the density percentages
359
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
360
+
361
+ # Create the bar chart using Altair
362
+ chart2 = alt.Chart(density_df).mark_bar().encode(
363
+ x=alt.X('choices:O', bin=alt.Bin(extent=[0, 70], step=10), axis=None),
364
+ y='density:Q',
365
+ color=alt.value('orange'),
366
+ tooltip=['density']
367
+ ).properties(
368
+ width=500,
369
+ title='Density of Choices'
370
+ ).interactive()
371
+
372
+ df = df_ultimatum_2_turbo
373
+ bin_ranges = [0, 10, 30, 50, 70]
374
+
375
+ # Calculate density as a percentage
376
+ density_percentage = df['choices'].value_counts(normalize=True)
377
+
378
+ # Create a DataFrame with the density percentages
379
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
380
+
381
+ # Create the bar chart using Altair
382
+ chart3 = alt.Chart(density_df).mark_bar().encode(
383
+ x=alt.X('choices:O', bin=alt.Bin(extent=[0, 70], step=10), axis=None),
384
+ y='density:Q',
385
+ color=alt.value('green'),
386
+ tooltip=['density']
387
+ ).properties(
388
+ width=500,
389
+ title='Density of Choices'
390
+ ).interactive()
391
+
392
+ final3 = alt.vconcat(chart1, chart2, chart3).resolve_scale(x='shared')
393
+
394
+ #Plot 4 - - Trust (as Investor) (trust)
395
+ binrange = (0, 100)
396
+ moves_1 = []
397
+ moves_2 = defaultdict(list)
398
+ with open('trust_investment.csv', 'r') as f:
399
+ reader = csv.reader(f)
400
+ header = next(reader)
401
+ col2idx = {col: idx for idx, col in enumerate(header)}
402
+ for row in reader:
403
+ record = {col: row[idx] for col, idx in col2idx.items()}
404
+
405
+ # if record['Role'] != 'first': continue
406
+ if int(record['Round']) > 1: continue
407
+ # if int(record['Total']) != 100: continue
408
+ if record['move'] == 'None': continue
409
+ if record['gameType'] != 'trust_investment': continue
410
+
411
+ if record['Role'] == 'first':
412
+ move = float(record['move'])
413
+ if move < binrange[0] or \
414
+ move > binrange[1]: continue
415
+ moves_1.append(move)
416
+ elif record['Role'] == 'second':
417
+ inv, ret = eval(record['roundResult'])
418
+ if ret < 0 or \
419
+ ret > inv * 3: continue
420
+ moves_2[inv].append(ret)
421
+ else: continue
422
+
423
+ df_trust_1_human = choices_to_df(moves_1, 'Human')
424
+ df_trust_2_human = choices_to_df(moves_2[10], 'Human')
425
+ df_trust_3_human = choices_to_df(moves_2[50], 'Human')
426
+ df_trust_4_human = choices_to_df(moves_2[100], 'Human')
427
+
428
+ choices = [50.0, 50.0, 40.0, 30.0, 50.0, 50.0, 40.0, 50.0, 50.0, 50.0, 50.0, 50.0, 30.0, 30.0, 50.0, 50.0, 50.0, 40.0, 40.0, 50.0, 50.0, 50.0, 50.0, 40.0, 50.0, 50.0, 50.0, 50.0]
429
+ df_trust_1_gpt4 = choices_to_df(choices, hue=str('ChatGPT-4'))
430
+
431
+ choices = [50.0, 50.0, 30.0, 30.0, 30.0, 60.0, 50.0, 40.0, 20.0, 20.0, 50.0, 40.0, 30.0, 20.0, 30.0, 20.0, 30.0, 60.0, 50.0, 30.0, 50.0, 20.0, 20.0, 30.0, 50.0, 30.0, 30.0, 50.0, 40.0] + [30]
432
+ df_trust_1_turbo = choices_to_df(choices, hue=str('ChatGPT-3'))
433
+
434
+ choices = [20.0, 20.0, 20.0, 20.0, 15.0, 15.0, 15.0, 20.0, 20.0, 20.0, 20.0, 20.0, 20.0, 15.0, 20.0, 20.0, 20.0, 20.0, 20.0, 15.0, 15.0, 20.0, 15.0, 15.0, 15.0, 15.0, 15.0, 20.0, 20.0, 15.0]
435
+ df_trust_2_gpt4 = choices_to_df(choices, hue=str('ChatGPT-4'))
436
+
437
+ choices = [20.0, 20.0, 20.0, 20.0, 20.0, 20.0, 15.0, 25.0, 30.0, 30.0, 20.0, 25.0, 30.0, 20.0, 20.0, 18.0] + [20, 20, 20, 25, 25, 25, 30]
438
+ df_trust_2_turbo = choices_to_df(choices, hue=str('ChatGPT-3'))
439
+
440
+ choices = [100.0, 75.0, 75.0, 75.0, 75.0, 75.0, 100.0, 75.0, 100.0, 100.0, 100.0, 100.0, 100.0, 100.0, 75.0, 100.0, 75.0, 75.0, 75.0, 100.0, 100.0, 100.0, 75.0, 100.0, 100.0, 100.0, 100.0, 75.0, 100.0, 75.0]
441
+ df_trust_3_gpt4 = choices_to_df(choices, hue=str('ChatGPT-4'))
442
+
443
+ choices = [150.0, 100.0, 150.0, 150.0, 50.0, 150.0, 100.0, 150.0, 100.0, 100.0, 100.0, 150.0] + [100, 100, 100, 100, 100, 100, 100, 100]
444
+ df_trust_3_turbo = choices_to_df(choices, hue=str('ChatGPT-3'))
445
+
446
+ choices = [200.0, 200.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 200.0, 200.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0, 150.0]
447
+ df_trust_4_gpt4 = choices_to_df(choices, hue=str('ChatGPT-4'))
448
+
449
+ choices = [225.0, 225.0, 300.0, 300.0, 220.0, 300.0, 250.0] + [200, 200, 250, 200, 200]
450
+ df_trust_4_turbo = choices_to_df(choices, hue=str('ChatGPT-3'))
451
+
452
+ df = df_trust_1_human
453
+
454
+ bin_ranges = [0, 10, 30, 50, 70]
455
+
456
+ # Calculate density as a percentage
457
+ density_percentage = df['choices'].value_counts(normalize=True)
458
+
459
+ # Create a DataFrame with the density percentages
460
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
461
+
462
+ # Create the bar chart using Altair
463
+ chart1 = alt.Chart(density_df).mark_bar().encode(
464
+ x=alt.X('choices:O', bin=alt.Bin(extent=[0, 70], step=10), axis=None),
465
+ y='density:Q',
466
+ color=alt.value('steelblue'),
467
+ tooltip=['density']
468
+ ).properties(
469
+ width=500,
470
+ title='Density of Choices'
471
+ ).interactive()
472
+
473
+
474
+
475
+ df = df_trust_1_gpt4
476
+
477
+ bin_ranges = [0, 10, 30, 50, 70]
478
+
479
+ # Calculate density as a percentage
480
+ density_percentage = df['choices'].value_counts(normalize=True)
481
+
482
+ # Create a DataFrame with the density percentages
483
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
484
+
485
+ # Create the bar chart using Altair
486
+ chart2 = alt.Chart(density_df).mark_bar().encode(
487
+ x=alt.X('choices:O', bin=alt.Bin(extent=[0, 70], step=10), axis=None),
488
+ y='density:Q',
489
+ color=alt.value('orange'),
490
+ tooltip=['density']
491
+ ).properties(
492
+ width=500,
493
+ title='Density of Choices'
494
+ ).interactive()
495
+
496
+
497
+ df = df_trust_1_turbo
498
+
499
+ bin_ranges = [0, 10, 30, 50, 70]
500
+
501
+ # Calculate density as a percentage
502
+ density_percentage = df['choices'].value_counts(normalize=True)
503
+
504
+ # Create a DataFrame with the density percentages
505
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
506
+
507
+ # Create the bar chart using Altair
508
+ chart3 = alt.Chart(density_df).mark_bar().encode(
509
+ x=alt.X('choices:O', bin=alt.Bin(extent=[0, 70], step=10), axis=None),
510
+ y='density:Q',
511
+ color=alt.value('green'),
512
+ tooltip=['density']
513
+ ).properties(
514
+ width=500,
515
+ title='Density of Choices'
516
+ ).interactive()
517
 
 
 
518
 
519
+ final4 = alt.vconcat(chart1, chart2, chart3).resolve_scale(x='shared')
520
+
521
+ #Plot 5 - Trust (as Banker) (fairness, altruism, reciprocity)
522
+ df = df_trust_3_human
523
+
524
+ bin_ranges = [0, 25, 50, 75, 100, 125, 150]
525
+
526
+ custom_ticks = [2, 6, 10, 14, 18]
527
+
528
+ # Calculate density as a percentage
529
+ density_percentage = df['choices'].value_counts(normalize=True)
530
+
531
+ # Create a DataFrame with the density percentages
532
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
533
+
534
+ # Create the bar chart using Altair
535
+ chart1 = alt.Chart(density_df).mark_bar().encode(
536
+ x=alt.X('choices:O', bin=alt.Bin(step=10), axis=None),
537
+ y='density:Q',
538
+ color=alt.value('steelblue')
539
+ ).properties(
540
+ width=500,
541
+ title='Density of Choices'
542
+ ).interactive()
543
+
544
+
545
+
546
+ df = df_trust_3_gpt4
547
+
548
+ bin_ranges = [0, 25, 50, 75, 100, 125, 150]
549
+
550
+ # Calculate density as a percentage
551
+ density_percentage = df['choices'].value_counts(normalize=True)
552
+
553
+ # Create a DataFrame with the density percentages
554
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
555
+
556
+ # Create the bar chart using Altair
557
+ chart2 = alt.Chart(density_df).mark_bar().encode(
558
+ x=alt.X('choices:O', bin=alt.Bin(step=10), axis=None),
559
+ y='density:Q',
560
+ color=alt.value('orange')
561
+ ).properties(
562
+ width=500,
563
+ title='Density of Choices'
564
+ ).interactive()
565
+
566
+
567
+ df = df_trust_3_turbo
568
+
569
+ bin_ranges = [0, 25, 50, 75, 100, 125, 150]
570
+
571
+ # Calculate density as a percentage
572
+ density_percentage = df['choices'].value_counts(normalize=True)
573
+
574
+ # Create a DataFrame with the density percentages
575
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
576
+
577
+ # Create the bar chart using Altair
578
+ chart3 = alt.Chart(density_df).mark_bar().encode(
579
+ x=alt.X('choices:O', bin=alt.Bin(step=10)),
580
+ y='density:Q',
581
+ color=alt.value('green')
582
+ ).properties(
583
+ width=500,
584
+ title='Density of Choices'
585
+ ).interactive()
586
+
587
+ # chart1
588
+ final5 = alt.vconcat(chart1, chart2, chart3).resolve_scale(x='shared')
589
+
590
+ #Plot 6 - Public Goods (Free-Riding, altruism, cooperation)
591
+ df = pd.read_csv('public_goods_linear_water.csv')
592
+ df = df[df['Role'] == 'contributor']
593
+ df = df[df['Round'] <= 3]
594
+ df = df[df['Total'] == 20]
595
+ df = df[df['groupSize'] == 4]
596
+ df = df[df['move'] != None]
597
+ df = df[(df['move'] >= 0) & (df['move'] <= 20)]
598
+ df = df[df['gameType'] == 'public_goods_linear_water']
599
+
600
+ round_1 = df[df['Round'] == 1]['move']
601
+ round_2 = df[df['Round'] == 2]['move']
602
+ round_3 = df[df['Round'] == 3]['move']
603
+ print(len(round_1), len(round_2), len(round_3))
604
+ df_PG_human = pd.DataFrame({
605
+ 'choices': list(round_1)
606
+ })
607
+ df_PG_human['hue'] = 'Human'
608
+ # df_PG_human
609
+
610
+ file_names = [
611
+ 'PG_basic_turbo_2023_05_09-02_49_09_AM.json',
612
+ 'PG_basic_turbo_loss_2023_05_09-03_59_49_AM.json',
613
+ 'PG_basic_gpt4_2023_05_09-11_15_42_PM.json',
614
+ 'PG_basic_gpt4_loss_2023_05_09-10_44_38_PM.json',
615
+ ]
616
+
617
+ choices = []
618
+ for file_name in file_names:
619
+ with open(file_name, 'r') as f:
620
+ choices += json.load(f)['choices']
621
+ choices_baseline = choices
622
+
623
+ choices = [tuple(x)[0] for x in choices]
624
+ df_PG_turbo = choices_to_df(choices, hue=str('ChatGPT-3'))
625
+ # df_PG_turbo.head()
626
+ df_PG_gpt4 = choices_to_df(choices, hue=str('ChatGPT-4'))
627
+ # df_PG_gpt4.head()
628
+
629
+ df = df_PG_human
630
+
631
+ bin_ranges = [0, 25, 50, 75, 100, 125, 150]
632
+
633
+ custom_ticks = [2, 6, 10, 14, 18]
634
+
635
+ # Calculate density as a percentage
636
+ density_percentage = df['choices'].value_counts(normalize=True)
637
+
638
+ # Create a DataFrame with the density percentages
639
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
640
+
641
+ # Create the bar chart using Altair
642
+ chart1 = alt.Chart(density_df).mark_bar().encode(
643
+ x=alt.X('choices:O', bin=alt.Bin(step=2), axis=None),
644
+ y='density:Q',
645
+ color=alt.value('steelblue'),
646
+ tooltip=['density']
647
+ ).properties(
648
+ width=500,
649
+ title='Density of Choices'
650
+ ).interactive()
651
+
652
+
653
+
654
+ df = df_PG_gpt4
655
+
656
+ bin_ranges = [0, 25, 50, 75, 100, 125, 150]
657
+
658
+ # Calculate density as a percentage
659
+ density_percentage = df['choices'].value_counts(normalize=True)
660
+
661
+ # Create a DataFrame with the density percentages
662
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
663
+
664
+ # Create the bar chart using Altair
665
+ chart2 = alt.Chart(density_df).mark_bar().encode(
666
+ x=alt.X('choices:O', bin=alt.Bin(step=2), axis=None),
667
+ y='density:Q',
668
+ color=alt.value('orange'),
669
+ tooltip=['density']
670
+ ).properties(
671
+ width=500,
672
+ title='Density of Choices'
673
+ ).interactive()
674
+
675
+
676
+ df = df_PG_turbo
677
+
678
+ bin_ranges = [0, 25, 50, 75, 100, 125, 150]
679
+
680
+ # Calculate density as a percentage
681
+ density_percentage = df['choices'].value_counts(normalize=True)
682
+
683
+ # Create a DataFrame with the density percentages
684
+ density_df = pd.DataFrame({'choices': density_percentage.index, 'density': density_percentage.values})
685
+
686
+ # Create the bar chart using Altair
687
+ chart3 = alt.Chart(density_df).mark_bar().encode(
688
+ x=alt.X('choices:O', bin=alt.Bin(step=2)),
689
+ y='density:Q',
690
+ color=alt.value('green'),
691
+ tooltip=['density']
692
+ ).properties(
693
+ width=500,
694
+ title='Density of Choices'
695
+ ).interactive()
696
 
697
+ # chart1
698
+ final6 = alt.vconcat(chart1, chart2, chart3).resolve_scale(x='shared')
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
699
 
700
+ #Final_Final
701
+ final_final = (final | final2 | final3 ) & (final4 | final5 | final6)
 
 
 
702
 
703
+ #Dashboard
704
+ import panel as pn
705
+ import vega_datasets
 
 
706
 
707
+ # Enable Panel extensions
708
+ pn.extension(design='bootstrap')
709
+ pn.extension('vega')
710
+
711
+ template = pn.template.BootstrapTemplate(
712
+ title='SI649 Project2',
 
 
 
 
 
 
 
713
  )
714
 
715
+ # the main column will hold our key content
716
+ maincol = pn.Column()
717
+
718
+ options1 = ['ALL', 'Choose Your Own', 'Based On Category']
719
+ select0 = pn.widgets.Select(options=options1, name='Choose what to compare')
720
+ # maincol.append(select0)
721
+
722
+ # Charts
723
+ charts = []
724
+ charts.append(final)
725
+ charts.append(final2)
726
+ charts.append(final3)
727
+ charts.append(final4)
728
+ charts.append(final5)
729
+ charts.append(final6)
730
+
731
+ # Define options for dropdown
732
+ options = [f'Chart {i+1}' for i in range(len(charts))]
733
+
734
+ # Panel widgets
735
+ select1 = pn.widgets.Select(options=options, name='Select Chart 1')
736
+ select2 = pn.widgets.Select(options=options, name='Select Chart 2')
737
+
738
+ options = ['Altruism', 'Fairness', 'spite', 'trust', 'reciprocity', 'free-riding', 'cooperation']
739
+ select_widget = pn.widgets.Select(options=options, name='Select a category')
740
+
741
+
742
+ # Define function to update chart
743
+ def update_chart(value):
744
+ if value:
745
+ index = int(value.split()[-1]) - 1
746
+ return charts[index]
747
+ else:
748
+ return None
749
+
750
+ # Combine dropdown and chart
751
+ @pn.depends(select1.param.value, select2.param.value)
752
+ def update_plots(value1, value2):
753
+ selected_chart1 = update_chart(value1)
754
+ selected_chart2 = update_chart(value2)
755
+ if selected_chart1 and selected_chart2:
756
+ return pn.Row(selected_chart1, selected_chart2)
757
+ elif selected_chart1:
758
+ return selected_chart1
759
+ elif selected_chart2:
760
+ return selected_chart2
761
+ else:
762
+ return None
763
+
764
+ # Define functions for each category
765
+ def update_plots_altruism():
766
+ return pn.Row(final, final5)
767
+
768
+ def update_plots_fairness():
769
+ return pn.Row(final2, final5)
770
+
771
+ def update_plots_spite():
772
+ return final
773
+
774
+ def update_plots_trust():
775
+ return final4
776
+
777
+ def update_plots_reciprocity():
778
+ return final5
779
+
780
+ def update_plots_freeriding():
781
+ return final6
782
+
783
+ def update_plots_cooperation():
784
+ return final6
785
+
786
+ # Define a dictionary to map categories to update functions
787
+ update_functions = {
788
+ 'Altruism': update_plots_altruism,
789
+ 'Fairness': update_plots_fairness,
790
+ 'spite': update_plots_spite,
791
+ 'trust': update_plots_trust,
792
+ 'reciprocity': update_plots_reciprocity,
793
+ 'freeriding': update_plots_freeriding,
794
+ 'cooperation': update_plots_cooperation
795
+ }
796
+
797
+
798
+ # # Define function to update chart based on selected category
799
+ # def update_plots_category(event):
800
+ # selected_category = event.new
801
+ # maincol.clear() # Clear existing content in main column
802
+
803
+ # if selected_category in update_functions:
804
+ # update_function = update_functions[selected_category]
805
+ # maincol.append(update_function())
806
+ # else:
807
+ # maincol.append(pn.pane.Markdown(f"No update function found for category: {selected_category}"))
808
+
809
+ # Define function to update chart based on selected category
810
+ def update_plots_category(event):
811
+ selected_category = event.new
812
+ maincol.clear() # Clear existing content in main column
813
+
814
+ if selected_category in update_functions:
815
+ update_function = update_functions[selected_category]
816
+ maincol.append(update_function())
817
+ else:
818
+ maincol.append(pn.pane.Markdown(f"No update function found for category: {selected_category}"))
819
+
820
+ # Append select_widget again to allow changing the category selection
821
+ maincol.append(select_widget)
822
+
823
+
824
+ # Callback function to handle select widget events
825
+ def select_callback(event):
826
+ selected_value = event.new
827
+ maincol.clear() # Clear existing content in main column
828
+
829
+ if selected_value == 'Choose Your Own':
830
+ maincol.append(select1)
831
+ maincol.append(select2)
832
+ maincol.append(update_plots)
833
+
834
+ elif selected_value == 'Based On Category':
835
+ maincol.append(select_widget)
836
+ select_widget.param.watch(update_plots_category, 'value')
837
+
838
+ # # Bind the update_plots_category function to the select widget's 'value' parameter
839
+ # select.param.watch
840
+ # maincol.append(update_plots_category())
841
+
842
+ # Bind the callback function to the select widget's 'value' parameter
843
+ select0.param.watch(select_callback, 'value')
844
+
845
+ maincol.append(select0)
846
+
847
+ template.main.append(maincol)
848
+ template.servable()