modelflowib 2.73__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
modelwidget.py ADDED
@@ -0,0 +1,718 @@
1
+ # -*- coding: utf-8 -*-
2
+ """
3
+ Created on Mon Aug 9 14:46:11 2021
4
+
5
+ To define Jupyter widgets show variables.
6
+ @author: Ib
7
+ """
8
+
9
+ import pandas as pd
10
+ import ipywidgets as widgets
11
+
12
+ # try:
13
+ # from ipysheet import sheet, cell, current
14
+ # from ipysheet.pandas_loader import from_dataframe, to_dataframe
15
+ # except:
16
+ # ...
17
+ # print('No ipysheet ')
18
+ from IPython.display import display, clear_output,Latex, Markdown
19
+ from dataclasses import dataclass,field
20
+ import matplotlib.pylab as plt
21
+
22
+ try:
23
+ from ipydatagrid import DataGrid
24
+ except Exception as e:
25
+ ...
26
+ # print( 'no update sheets',e)
27
+
28
+ from modelclass import insertModelVar
29
+ from modelclass import model
30
+ from modeljupyter import jupviz
31
+
32
+
33
+ @dataclass
34
+ class basewidget:
35
+ ''' basis for widget updating in jupyter'''
36
+
37
+
38
+ datachildren : list = field(default_factory=list) # list of children widgets
39
+
40
+ def update_df(self,df,current_per):
41
+ ''' will update container widgets'''
42
+ for w in self.datachildren:
43
+ w.update_df(df,current_per)
44
+
45
+
46
+ @dataclass
47
+ class tabwidget:
48
+ '''A widget to create tab or acordium contaners'''
49
+
50
+ tabdefdict : dict # = field(default_factory = lambda: ({}))
51
+ tab : bool = True
52
+ selected_index :any = None
53
+
54
+ def __post_init__(self):
55
+
56
+ thiswidget = widgets.Tab if self.tab else widgets.Accordion
57
+ self.datachildren = [tabcontent
58
+ for tabcontent in self.tabdefdict.values()]
59
+ self.datawidget = thiswidget([child.datawidget for child in self.datachildren],
60
+ selected_index = self.selected_index,
61
+ layout={'height': 'max-content'})
62
+
63
+ for i,key in enumerate(self.tabdefdict.keys()):
64
+ self.datawidget.set_title(i,key)
65
+
66
+
67
+ def update_df(self,df,current_per):
68
+ ''' will update container widgets'''
69
+ for w in self.datachildren:
70
+ w.update_df(df,current_per)
71
+
72
+
73
+ def reset(self,g):
74
+ ''' will reset container widgets'''
75
+ for w in self.datachildren:
76
+ w.reset(g)
77
+
78
+
79
+ @dataclass
80
+ class sheetwidget:
81
+ ''' Class defining a widget with a data grid (using ipydatagrid) '''
82
+ df_var: pd.DataFrame = field(default_factory=pd.DataFrame)
83
+ trans: any = lambda x: x # Translation of variable names
84
+ transpose: bool = False # If the dataframe should be transposed
85
+ heading: str = ""
86
+
87
+ def __post_init__(self):
88
+ newnamedf = self.df_var.copy().rename(columns=self.trans)
89
+ self.org_df_var = newnamedf.T if self.transpose else newnamedf
90
+
91
+ column_widths = {col: max(len(col), 10) * 9 for col in self.org_df_var.columns} # Adjust column width dynamically
92
+ self.data_grid = DataGrid(pd.DataFrame(self.org_df_var),
93
+ column_widths=column_widths, enable_filters=False,enable_sort=False,
94
+ editable=True, index_name = 'year')
95
+ self.org_values = self.org_df_var.copy()
96
+
97
+ self.datawidget = widgets.VBox([widgets.Label(value=self.heading), self.data_grid]) if len(self.heading) else self.data_grid
98
+
99
+ def update_df(self, df, current_per=None):
100
+ updated_df = pd.DataFrame(self.data_grid.data)
101
+ if self.transpose:
102
+ updated_df = updated_df.T
103
+
104
+ updated_df.columns = self.df_var.columns
105
+ updated_df.index = self.df_var.index
106
+ df.loc[updated_df.index, updated_df.columns] = df.loc[updated_df.index, updated_df.columns] + updated_df
107
+ return df
108
+
109
+ def reset(self, g):
110
+ self.data_grid.data = pd.DataFrame(self.org_values)
111
+
112
+
113
+ @dataclass
114
+ class slidewidget:
115
+ ''' class defefining a widget with lines of slides '''
116
+ slidedef : dict # definition
117
+ altname : str = 'Alternative'
118
+ basename : str = 'Baseline'
119
+ expname : str = "Carbon tax rate, US$ per tonn "
120
+ def __post_init__(self):
121
+ ...
122
+ # plt.ioff()
123
+ wexp = widgets.Label(value = self.expname,layout={'width':'54%'})
124
+ walt = widgets.Label(value = self.altname,layout={'width':'8%', 'border':"hide"})
125
+ wbas = widgets.Label(value = self.basename,layout={'width':'10%', 'border':"hide"})
126
+ whead = widgets.HBox([wexp,walt,wbas])
127
+ #
128
+ self.wset = [widgets.FloatSlider(description=des,
129
+ min=cont['min'],
130
+ max=cont['max'],
131
+ value=cont['value'],
132
+ step=cont.get('step',0.01),
133
+ layout={'width':'60%'},style={'description_width':'40%'},
134
+ readout_format = f":>,.{cont.get('dec',2)}f",
135
+ continuous_update=False
136
+ )
137
+ for des,cont in self.slidedef.items()]
138
+
139
+
140
+ for w in self.wset:
141
+ w.observe(self.set_slide_value,names='value',type='change')
142
+
143
+ waltval= [widgets.Label(
144
+ value=f"{cont['value']:>,.{cont.get('dec',2)}f}",
145
+ layout=widgets.Layout(display="flex", justify_content="center", width="10%", border="hide"))
146
+ for des,cont in self.slidedef.items()
147
+
148
+ ]
149
+ self.wslide = [widgets.HBox([s,v]) for s,v in zip(self.wset,waltval)]
150
+ self.slidewidget = widgets.VBox([whead] + self.wslide)
151
+ self.datawidget = widgets.VBox([whead] + self.wslide)
152
+
153
+ # define the result object
154
+ self.current_values = {des:
155
+ {key : v.split() if key=='var' else v for key,v in cont.items() if key in {'value','var','op'}}
156
+ for des,cont in self.slidedef.items()}
157
+
158
+ def reset(self,g):
159
+ for i,(des,cont) in enumerate(self.slidedef.items()):
160
+ self.wset[i].value = cont['value']
161
+
162
+
163
+
164
+ def update_df(self,df,current_per):
165
+ ''' updates a dataframe with the values from the widget'''
166
+ for i,(des,cont) in enumerate(self.current_values.items()):
167
+ op = cont.get('op','=')
168
+ value = cont['value']
169
+ for var in cont['var']:
170
+ if op == '+':
171
+ df.loc[current_per,var] = df.loc[current_per,var] + value
172
+ elif op == '+impulse':
173
+ df.loc[current_per[0],var] = df.loc[current_per[0],var] + value
174
+ elif op == '=start-':
175
+ startindex = df.index.get_loc(current_per[0])
176
+ varloc = df.columns.get_loc(var)
177
+ df.iloc[:startindex,varloc] = value
178
+ elif op == '=':
179
+ df.loc[current_per,var] = value
180
+ elif op == '=impulse':
181
+ df.loc[current_per[0],var] = value
182
+ elif op == '%':
183
+ df.loc[current_per,var] = df.loc[current_per,var] * (1-value/100)
184
+ else:
185
+ print(f'Wrong operator in {cont}.\nNot updated')
186
+ assert 1==3,'wRONG OPERATOR'
187
+
188
+
189
+ def set_slide_value(self,g):
190
+ ''' updates the new values to the self.current_vlues
191
+ will be used in update_df
192
+ '''
193
+ line_des = g['owner'].description
194
+ if 0:
195
+ print()
196
+ for k,v in g.items():
197
+ print(f'{k}:{v}')
198
+
199
+ self.current_values[line_des]['value'] = g['new']
200
+
201
+ @dataclass
202
+ class sumslidewidget:
203
+ ''' class defefining a widget with lines of slides '''
204
+ slidedef : dict # definition
205
+ maxsum : any = None
206
+ altname : str = 'Alternative'
207
+ basename : str = 'Baseline'
208
+ expname : str = "Carbon tax rate, US$ per tonn "
209
+ def __post_init__(self):
210
+ ...
211
+
212
+ self.first = list(self.slidedef.keys())[:-1]
213
+ self.lastdes = list(self.slidedef.keys())[-1]
214
+
215
+ wexp = widgets.Label(value = self.expname,layout={'width':'54%'})
216
+ walt = widgets.Label(value = self.altname,layout={'width':'8%', 'border':"hide"})
217
+ wbas = widgets.Label(value = self.basename,layout={'width':'10%', 'border':"hide"})
218
+ whead = widgets.HBox([wexp,walt,wbas])
219
+ #
220
+ self.wset = [widgets.FloatSlider(description=des,
221
+ min=cont['min'],
222
+ max=cont['max'],
223
+ value=cont['value'],
224
+ step=cont.get('step',0.01),
225
+ layout={'width':'60%'},style={'description_width':'40%'},
226
+ readout_format = f":>,.{cont.get('dec',2)}f",
227
+ continuous_update=False,
228
+ disabled= False
229
+ )
230
+ for des,cont in self.slidedef.items()]
231
+
232
+
233
+
234
+ for w in self.wset:
235
+ w.observe(self.set_slide_value,names='value',type='change')
236
+
237
+ waltval= [widgets.Label(
238
+ value=f"{cont['value']:>,.{cont.get('dec',2)}f}",
239
+ layout=widgets.Layout(display="flex", justify_content="center", width="10%", border="hide"))
240
+ for des,cont in self.slidedef.items()
241
+
242
+ ]
243
+ self.wslide = [widgets.HBox([s,v]) for s,v in zip(self.wset,waltval)]
244
+ self.slidewidget = widgets.VBox([whead] + self.wslide)
245
+ self.datawidget = widgets.VBox([whead] + self.wslide)
246
+
247
+ # define the result object
248
+ self.current_values = {des:
249
+ {key : v.split() if key=='var' else v for key,v in cont.items() if key in {'value','var','op','min','max'}}
250
+ for des,cont in self.slidedef.items()}
251
+
252
+ def reset(self,g):
253
+ for i,(des,cont) in enumerate(self.slidedef.items()):
254
+ self.wset[i].value = cont['value']
255
+
256
+
257
+
258
+ def update_df(self,df,current_per):
259
+ ''' updates a dataframe with the values from the widget'''
260
+ for i,(des,cont) in enumerate(self.current_values.items()):
261
+ op = cont.get('op','=')
262
+ value = cont['value']
263
+ for var in cont['var']:
264
+ if op == '+':
265
+ df.loc[current_per,var] = df.loc[current_per,var] + value
266
+ elif op == '+impulse':
267
+ df.loc[current_per[0],var] = df.loc[current_per[0],var] + value
268
+ elif op == '=start-':
269
+ startindex = df.index.get_loc(current_per[0])
270
+ varloc = df.columns.get_loc(var)
271
+ df.iloc[:startindex,varloc] = value
272
+ elif op == '=':
273
+ df.loc[current_per,var] = value
274
+ elif op == '=impulse':
275
+ df.loc[current_per[0],var] = value
276
+ else:
277
+ print(f'Wrong operator in {cont}.\nNot updated')
278
+ assert 1==3,'wRONG OPERATOR'
279
+
280
+
281
+ def set_slide_value(self,g):
282
+ ''' updates the new values to the self.current_vlues
283
+ will be used in update_df
284
+ '''
285
+ line_des = g['owner'].description
286
+ line_index = list(self.current_values.keys()).index(line_des)
287
+ if 0:
288
+ print()
289
+ for k,v in g.items():
290
+ print(f'{k}:{v}')
291
+
292
+ self.current_values[line_des]['value'] = g['new']
293
+ # print(self.current_values)
294
+ if type(self.maxsum) == float:
295
+ allvalues = [v['value'] for v in self.current_values.values()]
296
+ thissum = sum(allvalues)
297
+ if thissum > self.maxsum:
298
+ # print(f'{allvalues=}')
299
+ # print(f"{self.current_values[self.lastdes]['min']=}")
300
+ newlast = self.maxsum-sum(allvalues[:-1])
301
+ newlast = max(newlast,self.current_values[self.lastdes]['min'])
302
+ # print(f'{newlast=}')
303
+ self.current_values[self.lastdes]['value']= newlast
304
+
305
+ newsum= sum([v['value'] for v in self.current_values.values()])
306
+ # print(f'{newsum=}')
307
+ # print(f'{line_index=}')
308
+ if newsum > self.maxsum:
309
+ self.current_values[line_des]['value']=self.wset[line_index].value-newsum +self.maxsum
310
+ self.wset[line_index].value = self.current_values[line_des]['value']
311
+
312
+ self.wset[-1].value = newlast
313
+
314
+
315
+
316
+ @dataclass
317
+ class updatewidget:
318
+ ''' class to input and run a model'''
319
+
320
+ mmodel : any # a model
321
+ a_datawidget : any # a tab to update from
322
+ basename : str ='Business as usual'
323
+ keeppat : str = '*'
324
+ varpat : str ='*'
325
+ showvarpat : bool = True
326
+ exodif : pd.DataFrame = field(default_factory=pd.DataFrame) # definition
327
+ lwrun : bool = True
328
+ lwupdate : bool = False
329
+ lwreset : bool = True
330
+ lwsetbas : bool = True
331
+ lwshow :bool = True
332
+ outputwidget : str = 'jupviz'
333
+ prefix_dict : dict = field(default_factory=dict)
334
+ display_first :any = None
335
+ vline : list = field(default_factory=list)
336
+ relativ_start : int = 0
337
+ short :bool = False
338
+ legend :bool = False
339
+
340
+ def __post_init__(self):
341
+ self.baseline = self.mmodel.basedf.copy()
342
+ wrun = widgets.Button(description="Run scenario")
343
+ wrun.on_click(self.run)
344
+
345
+ wupdate = widgets.Button(description="Update the dataset ")
346
+ wupdate.on_click(self.update)
347
+
348
+ wreset = widgets.Button(description="Reset to start")
349
+ wreset.on_click(self.reset)
350
+
351
+ wshow = widgets.Button(description="Show results")
352
+ wshow.on_click(self.show)
353
+
354
+ wsetbas = widgets.Button(description="Use as baseline")
355
+ wsetbas.on_click(self.setbasis)
356
+ self.experiment = 0
357
+
358
+ lbut = []
359
+
360
+ if self.lwrun: lbut.append(wrun)
361
+ if self.lwshow: lbut.append(wshow)
362
+ if self.lwupdate: lbut.append(wupdate)
363
+ if self.lwreset: lbut.append(wreset)
364
+ if self.lwsetbas : lbut.append(wsetbas)
365
+
366
+ wbut = widgets.HBox(lbut)
367
+
368
+
369
+ self.wname = widgets.Text(value=self.basename,placeholder='Type something',description='Scenario name:',
370
+ layout={'width':'30%'},style={'description_width':'50%'})
371
+ self.wpat = widgets.Text(value= self.varpat,placeholder='Type something',description='Display variables:',
372
+ layout={'width':'65%'},style={'description_width':'30%'})
373
+
374
+ self.wpat.layout.visibility = 'visible' if self.showvarpat else 'hidden'
375
+
376
+
377
+ winputstring = widgets.HBox([self.wname,self.wpat])
378
+
379
+ self.wtotal = widgets.VBox([self.a_datawidget.datawidget,winputstring,wbut])
380
+
381
+ self.mmodel.keep_solutions = {}
382
+ self.mmodel.keep_solutions = {self.wname.value : self.baseline}
383
+ self.mmodel.keep_exodif = {}
384
+
385
+ self.experiment += 1
386
+ self.wname.value = f'Experiment {self.experiment}'
387
+
388
+
389
+ def update(self,g):
390
+ self.thisexperiment = self.baseline.copy()
391
+ self.a_datawidget.update_df(self.thisexperiment,self.mmodel.current_per)
392
+ self.exodif = self.mmodel.exodif(self.baseline,self.thisexperiment)
393
+
394
+
395
+ def show(self,g=None):
396
+ if self.outputwidget == 'jupviz':
397
+ clear_output()
398
+ display(self.wtotal)
399
+
400
+ displaydict = {k :v.loc[self.mmodel.current_per,self.wpat.value.split()]
401
+ for k,v in self.mmodel.keep_solutions.items()}
402
+ jupviz(displaydict,legend=0)()
403
+
404
+ elif self.outputwidget == 'keep_viz':
405
+
406
+ selectfrom = [v for v in self.mmodel.vlist(self.wpat.value) if v in
407
+ set(list(self.mmodel.keep_solutions.values())[0].columns)]
408
+ clear_output()
409
+ display(self.wtotal)
410
+ plt.close('all')
411
+ _ = self.mmodel.keep_viz(pat=selectfrom[0],selectfrom=selectfrom,vline=self.vline)
412
+
413
+ elif self.outputwidget == 'keep_viz_prefix':
414
+
415
+ selectfrom = [v for v in self.mmodel.vlist(self.wpat.value) if v in
416
+ set(list(self.mmodel.keep_solutions.values())[0].columns)]
417
+ clear_output()
418
+ if self.display_first:
419
+ display(self.display_first)
420
+ display(self.wtotal)
421
+ plt.close('all')
422
+ with self.mmodel.set_smpl_relative(self.relativ_start,0):
423
+ _ = self.mmodel.keep_viz_prefix(pat=selectfrom[0],
424
+ selectfrom=selectfrom,prefix_dict=self.prefix_dict,vline=self.vline,short=self.short,legend=self.legend)
425
+
426
+
427
+ def run(self,g):
428
+ clear_output(True)
429
+ display(self.wtotal)
430
+ self.update(g)
431
+ self.mmodel(self.thisexperiment,progressbar=1,keep = self.wname.value,
432
+ keep_variables = self.keeppat)
433
+ self.mmodel.keep_exodif[self.wname.value] = self.exodif
434
+ self.mmodel.inputwidget_alternativerun = True
435
+ self.current_experiment = self.wname.value
436
+ self.experiment += 1
437
+ self.wname.value = f'Experiment {self.experiment}'
438
+ self.show(g)
439
+
440
+ def setbasis(self,g):
441
+ clear_output(True)
442
+ display(self.wtotal)
443
+ self.mmodel.keep_solutions={self.current_experiment:self.mmodel.keep_solutions[self.current_experiment]}
444
+
445
+ self.mmodel.keep_exodif[self.current_experiment] = self.exodif
446
+ self.mmodel.inputwidget_alternativerun = True
447
+
448
+
449
+
450
+
451
+ def reset(self,g):
452
+ self.a_datawidget.reset(g)
453
+
454
+ def fig_to_image(figs,format='svg'):
455
+ from io import StringIO
456
+ f = StringIO()
457
+ figs.savefig(f,format=format)
458
+ f.seek(0)
459
+ image= f.read()
460
+ if format == 'svg':
461
+ # Make the SVG responsive: matplotlib emits the figure's native size
462
+ # (e.g. width="1440pt" for a wide ncol>1 figure), which overflows the
463
+ # notebook output area so only the left column shows. Drop the fixed
464
+ # pt width/height and let the viewBox drive the aspect ratio so the
465
+ # full figure scales to the container width.
466
+ import re
467
+ def _responsive(m):
468
+ tag = re.sub(r'\s(?:width|height)="[^"]*pt"', '', m.group(0))
469
+ if 'style=' not in tag:
470
+ tag = tag[:-1] + ' style="width:100%;height:auto;">'
471
+ return tag
472
+ image = re.sub(r'<svg\b[^>]*>', _responsive, image, count=1)
473
+ return image
474
+
475
+ @dataclass
476
+ class htmlwidget_df:
477
+ ''' class displays a dataframe in a html widget '''
478
+
479
+ mmodel : any # a model
480
+ df_var : pd.DataFrame = field(default_factory=pd.DataFrame) # definition
481
+ trans : any = lambda x : x # renaming of variables
482
+ transpose : bool = False # orientation of dataframe
483
+ expname : str = ""
484
+ percent : bool = False
485
+ style : any = ''
486
+
487
+
488
+ def __post_init__(self):
489
+ ...
490
+
491
+ self.wexp = widgets.Label(value = self.expname,layout={'width':'54%'})
492
+
493
+
494
+ newnamedf = self.df_var.copy().rename(columns=self.trans)
495
+ self.org_df_var = newnamedf.T if self.transpose else newnamedf
496
+ if 0:
497
+ image = self.mmodel.ibsstyle(self.org_df_var,percent = self.percent).to_html()
498
+ else:
499
+ style_html = """
500
+ <style>
501
+ table, th, td {
502
+ border: none;
503
+ border-collapse: collapse;
504
+ padding: 10px; # Adjust padding as needed
505
+ text-align: left;
506
+ }
507
+ </style>
508
+ """
509
+ if self.style:
510
+ image_html = self.style(self.df_var).to_html()
511
+ else:
512
+ image_html = self.mmodel.ibsstyle(self.org_df_var, percent=self.percent).to_html()
513
+ image = f"{style_html}{image_html}"
514
+
515
+ self.whtml = widgets.HTML(image)
516
+ self.datawidget=widgets.VBox([self.wexp,self.whtml]) if len(self.expname) else self.whtml
517
+
518
+
519
+
520
+ @property
521
+ def show(self):
522
+ display(self.datawidget)
523
+
524
+
525
+ @dataclass
526
+ class htmlwidget_fig:
527
+ ''' class displays a dataframe in a html widget '''
528
+
529
+ figs : any # a model
530
+ expname : str = ""
531
+ format : str = "svg"
532
+
533
+
534
+ def __post_init__(self):
535
+ ...
536
+ # print(f'Create {self.expname}')
537
+
538
+ self.wexp = widgets.Label(value = self.expname,layout={'width':'54%'})
539
+
540
+ image = fig_to_image(self.figs,format=self.format)
541
+ self.whtml = widgets.HTML(image)
542
+ self.datawidget=widgets.VBox([self.wexp,self.whtml]) if len(self.expname) else self.whtml
543
+
544
+ @dataclass
545
+ class htmlwidget_style:
546
+ ''' Class that displays text in an HTML widget. '''
547
+
548
+ styler: any = ''
549
+
550
+ def __post_init__(self):
551
+ # Initialize the label widget with the provided text
552
+ style_html = """
553
+ <style>
554
+ table, th, td {
555
+ border: none;
556
+ border-collapse: collapse;
557
+ padding: 10px; # Adjust padding as needed
558
+ line-height: normal; # Ensures normal line spacing
559
+
560
+ text-align: left;
561
+ }
562
+ </style>
563
+ """
564
+ self.datawidget = widgets.HTML(f'{style_html}{self.styler.to_html()}' )
565
+
566
+ def display(self):
567
+ # Function to display the widget
568
+ display(self.datawidget)
569
+
570
+
571
+ @dataclass
572
+ class htmlwidget_label:
573
+ ''' class displays a dataframe in a html widget '''
574
+
575
+ expname : str = ""
576
+ format : str = "svg"
577
+
578
+
579
+ def __post_init__(self):
580
+ ...
581
+
582
+ self.wexp = widgets.Label(value = self.expname,layout={'width':'54%'})
583
+
584
+
585
+ self.datawidget=self.wexp
586
+
587
+ @dataclass
588
+ class htmlwidget_text:
589
+ ''' Class that displays text in an HTML widget. '''
590
+
591
+ text: str = ""
592
+ format: str = "svg" # This property is included but not used in this example
593
+
594
+ def __post_init__(self):
595
+ # Initialize the label widget with the provided text
596
+ self.datawidget = widgets.HTML(
597
+ value=f"<p style='font-family:sans-serif;'>{self.text}</p>",
598
+ layout={'width': '90%'}
599
+ )
600
+
601
+ def display(self):
602
+ # Function to display the widget
603
+ display(self.data_widget)
604
+
605
+
606
+ @dataclass
607
+ class visshow:
608
+ mmodel : any # a model
609
+ varpat : str ='*'
610
+ showvarpat : bool = True
611
+ show_on : bool = True # Display when called
612
+
613
+ def __post_init__(self):
614
+ ...
615
+ # from IPython import get_ipython
616
+ # get_ipython().magic('matplotlib notebook')
617
+ # print(plt.get_backend())
618
+ # print('hej haj')
619
+ # plt.close('all')
620
+
621
+ # print(f'{self.show_on=}')
622
+ # plt.ioff()
623
+ this_vis = self.mmodel[self.varpat]
624
+ self.out_dict = {}
625
+ self.out_dict['Baseline'] ={'df':this_vis.base}
626
+ self.out_dict['Alternative'] ={'df':this_vis}
627
+ self.out_dict['Difference'] ={'df':this_vis.dif}
628
+ self.out_dict['Diff. pct. level'] ={'df':this_vis.difpctlevel,'percent':True}
629
+ self.out_dict['Base growth'] ={'df':this_vis.base.pct,'percent':True}
630
+ self.out_dict['Alt. growth'] ={'df':this_vis.pct,'percent':True}
631
+ self.out_dict['Diff. in growth'] ={'df':this_vis.difpct,'percent':True}
632
+
633
+ out = widgets.Output()
634
+ self.out_to_data = {key:
635
+ htmlwidget_df(self.mmodel,value['df'].df.T,expname=key,
636
+
637
+ percent=value.get('percent',False))
638
+ for key,value in self.out_dict.items()}
639
+
640
+ with out: # to suppress the display of matplotlib creation
641
+ self.out_to_figs ={key:
642
+ htmlwidget_fig(value['df'].rename().plot(top=1.0,title=''),expname='')
643
+ for key,value in self.out_dict.items() }
644
+
645
+
646
+ tabnew = {key: tabwidget({'Charts':self.out_to_figs[key],'Data':self.out_to_data[key]},selected_index=0) for key in self.out_to_figs.keys()}
647
+ # print('tabnew created')
648
+ exodif = self.mmodel.exodif()
649
+ exonames = exodif.columns
650
+ exoindex = exodif.index
651
+
652
+
653
+ if 1:
654
+
655
+ if len(exonames):
656
+ exoindexstart = max(self.mmodel.lastdf.index.get_loc(exodif.index[0]),self.mmodel.lastdf.index.get_loc(self.mmodel.current_per[0]))
657
+ exoindexend = min(self.mmodel.lastdf.index.get_loc(exodif.index[-1]),self.mmodel.lastdf.index.get_loc(self.mmodel.current_per[-1]))
658
+ exoindexnew = self.mmodel.lastdf.index[exoindexstart:exoindexend]
659
+ rows,cols =exodif.loc[exoindexnew,:].shape
660
+ exosize = rows*cols
661
+
662
+ if exosize < 2000 :
663
+ exobase = self.mmodel.basedf.loc[exoindexnew,exonames]
664
+ exolast = self.mmodel.lastdf.loc[exoindexnew,exonames]
665
+
666
+ out_exodif = htmlwidget_df(self.mmodel,exodif.loc[exoindexnew,:].T)
667
+ out_exobase = htmlwidget_df(self.mmodel,exobase.T)
668
+ out_exolast = htmlwidget_df(self.mmodel,exolast.T)
669
+ else:
670
+ out_exodif = htmlwidget_label(expname = 'To many to display ')
671
+ out_exobase = htmlwidget_label(expname = 'To many to display ')
672
+ out_exolast = htmlwidget_label(expname = 'To many to display ')
673
+ else:
674
+ out_exodif = htmlwidget_label(expname = 'No difference in exogenous')
675
+ out_exobase = htmlwidget_label(expname = 'No difference in exogenous')
676
+ out_exolast = htmlwidget_label(expname = 'No difference in exogenous')
677
+
678
+
679
+ out_tab_info = tabwidget({'Delta exogenous':out_exodif,
680
+ 'Baseline exogenous':out_exobase,
681
+ 'Alt. exogenous':out_exolast},selected_index=0)
682
+
683
+ tabnew['Exo info'] = out_tab_info
684
+ # print('exo inf created')
685
+
686
+ this = tabwidget(tabnew,selected_index=0)
687
+ # print('this created ')
688
+
689
+
690
+ self.datawidget = this.datawidget
691
+ if self.show_on:
692
+ ...
693
+ display(self.datawidget)
694
+
695
+ try:
696
+ get_ipython().magic('matplotlib inline')
697
+ except:
698
+ ...
699
+
700
+
701
+ def __repr__(self):
702
+ return ''
703
+
704
+ def _html_repr_(self):
705
+ return self.datawidget
706
+
707
+ @property
708
+ def show(self):
709
+ display(self.datawidget)
710
+
711
+
712
+ if __name__ == '__main__':
713
+ # if 'masia' not in locals():
714
+ # print('loading model')
715
+ # masia,baseline = model.modelload('C:/wb Dawn/UNESCAP-/Asia/Asia.pcim',run=0,silent=1)
716
+ # test = slidewidget(masia,{})
717
+ ...
718
+