diff --git a/cufflinks/auth.py b/cufflinks/auth.py index daff0f8..0742aad 100644 --- a/cufflinks/auth.py +++ b/cufflinks/auth.py @@ -7,6 +7,7 @@ import json import warnings from .offline import go_offline +from functools import lru_cache package='cufflinks' @@ -176,7 +177,7 @@ def set_config_file(sharing=None,theme=None,colorscale=None,offline=None,offline save_json_dict(CONFIG_FILE, config) ensure_local_files() - +@lru_cache(maxsize=32) def get_config_file(*args): """ Return specified args from `~/.config`. as dict. @@ -260,4 +261,4 @@ def save_json_dict(filename, json_dict): with open(filename, "w") as f: f.write(json.dumps(json_dict, indent=4)) else: - raise TypeError("json_dict was not a dictionary. couldn't save.") \ No newline at end of file + raise TypeError("json_dict was not a dictionary. couldn't save.") diff --git a/cufflinks/plotlytools.py b/cufflinks/plotlytools.py index 4d8b162..e3a31c1 100644 --- a/cufflinks/plotlytools.py +++ b/cufflinks/plotlytools.py @@ -36,7 +36,7 @@ def dict_to_iplot(d): def _to_iplot(self,colors=None,colorscale=None,kind='scatter',mode='lines',interpolation='linear',symbol='dot',size='12',fill=False, width=3,dash='solid',sortbars=False,keys=False,bestfit=False,bestfit_colors=None,opacity=0.6, - mean=False,mean_colors=None,asDates=False,asTimestamp=False,text=None,**kwargs): + mean=False,mean_colors=None,asDates=False,asTimestamp=False,text=None,hovertext=None,textangle=None,**kwargs): """ Generates a plotly Data object @@ -206,7 +206,7 @@ def _iplot(self,kind='scatter',data=None,layout=None,filename='',sharing=None,ti bestfit_colors=None,mean=False,mean_colors=None,categories='',x='',y='',z='',text='',gridcolor=None, zerolinecolor=None,margin=None,labels=None,values=None,secondary_y='',secondary_y_title='',subplots=False,shape=None,error_x=None, error_y=None,error_type='data',locations=None,lon=None,lat=None,asFrame=False,asDates=False,asFigure=False, - asImage=False,dimensions=None,asPlot=False,asUrl=False,online=None,**kwargs): + asImage=False,dimensions=None,asPlot=False,asUrl=False,online=None,hovertemplate=None,hovertext=None,textangle=None,arrowlen=-50,**kwargs): """ Returns a plotly chart either as inline chart, image of Figure object @@ -666,9 +666,9 @@ def _iplot(self,kind='scatter',data=None,layout=None,filename='',sharing=None,ti """ # Valid Kwargs - valid_kwargs = ['color','opacity','column','columns','labels','text','world_readable','colorbar'] + valid_kwargs = ['color','opacity','column','columns','labels','text','world_readable','colorbar','hoverinfo','hovertext'] BUBBLE_KWARGS = ['abs_size'] - TRACE_KWARGS = ['hoverinfo','connectgaps'] + TRACE_KWARGS = ['hoverinfo','connectgaps','hovertext'] HEATMAP_SURFACE_KWARGS = ['center_scale','zmin','zmax'] PIE_KWARGS=['sort','pull','hole','textposition','textinfo','linecolor','linewidth','textcolor'] OHLC_KWARGS=['up_color','down_color','open','high','low','close','volume','name','decreasing','increasing'] @@ -770,7 +770,7 @@ def get_marker(marker={}): df=self.copy() df=df.set_index(categories) fig=df.figure(kind=kind,colors=colors,colorscale=colorscale,fill=fill,width=width,sortbars=sortbars,opacity=opacity, - asDates=asDates,mode=mode,symbol=symbol,size=size,text=text,barmode=barmode,orientation=orientation) + asDates=asDates,mode=mode,symbol=symbol,size=size,text=text,barmode=barmode,orientation=orientation,textangle=textangle,hovertext=hovertext) data=fig['data'] else: _keys=pd.unique(self[categories]) @@ -871,6 +871,8 @@ def get_marker(marker={}): orientation = 'h' if kind=='barh' else orientation for trace in data: trace.update(orientation=orientation) + trace.update(textangle=textangle) + trace.update(hovertext=hovertext) if orientation=='h': trace['x'],trace['y']=trace['y'],trace['x'] @@ -956,9 +958,11 @@ def get_marker(marker={}): x=self.index.values.tolist() y=self[y].values.tolist() if y else self.columns.values.tolist() z=self[z].values.tolist() if z else self.values.transpose() - scale=get_scales('rdbu') if not colorscale else get_scales(colorscale) - scale=[normalize(_) for _ in scale] - colorscale=[[float(_)/(len(scale)-1),scale[_]] for _ in range(len(scale))] + # scale=get_scales('rdbu') if not colorscale else get_scales(colorscale) + scale=get_scales('rdbu') if not colorscale else colorscale + # scale=[normalize(_) for _ in scale] + # colorscale=[[float(_)/(len(scale)-1),scale[_]] for _ in range(len(scale))] + center_scale = kwargs.get('center_scale',None) if is_list(z): @@ -1625,11 +1629,13 @@ def get_study(df,func,iplot_kwargs,iplot_study_kwargs,str=None,include=False,col study_kwargs=check_kwargs(iplot_kwargs,__TA_KWARGS,{},clean_origin=True) iplot_study_kwargs=kwargs_from_keyword(iplot_kwargs,{},'study') + # if not study == 'kalman': # Saran + # study_kwargs.update({'periods':periods}) study_kwargs.update({'periods':periods}) ta_func = eval('ta.{0}'.format(study)) - inset=study in ('sma','boll','ema','atr','ptps') + inset=study in ('sma','boll','ema','atr','ptps','ama', 'kalman') figure=get_study(self,ta_func,iplot_kwargs,iplot_study_kwargs,include=include, column=column,str=str,inset=inset) diff --git a/cufflinks/quant_figure.py b/cufflinks/quant_figure.py index f2a1940..c047c95 100644 --- a/cufflinks/quant_figure.py +++ b/cufflinks/quant_figure.py @@ -239,6 +239,7 @@ def figure(self,**kwargs): """ kwargs['asFigure']=True + kwargs['auto_open']=auto_open #Saran return self.iplot(**kwargs) def _panel_domains(self,n=2,min_panel_size=.15,spacing=0.08,top_margin=1,bottom_margin=0): @@ -713,8 +714,120 @@ def add_sma(self,periods=20,column=None,name='', 'display':utils.merge_dict({'legendgroup':False},kwargs)} self._add_study(study) + def add_line(self,column=None,name='', + str=None,**kwargs): + """ + #Saran: Add another security (line, not OHLC) to QuantFigure.studies + + Parameters: + periods : int or list(int) + Number of periods + column :string + Defines the data column name that contains the + data over which the study will be applied. + Default: 'close' + name : string + Name given to the study + str : string + Label factory for studies + The following wildcards can be used: + {name} : Name of the column + {study} : Name of the study + {period} : Period used + Examples: + 'study: {study} - period: {period}' + kwargs: + legendgroup : bool + If true, all legend items are grouped into a + single one + All formatting values available on iplot() + """ + if not column: + column=self._d['close'] + study={'kind':'line', + 'name':name, + 'params':{'column':column, + 'str':str}, + 'display':utils.merge_dict({'legendgroup':False},kwargs)} + self._add_study(study) + + def add_ama(self,periods=9,column=None,name='', + str=None,**kwargs): + """ + Saran: Add Adaptive Moving Average (AMA) study to QuantFigure.studies + + Parameters: + periods : int + Number of periods + fast_period : int + number of periods for the fastest EMA constant. + slow_period : int + number of periods for the slowest EMA constant. + column :string + Defines the data column name that contains the + data over which the study will be applied. + Default: 'close' + name : string + Name given to the study + str : string + Label factory for studies + The following wildcards can be used: + {name} : Name of the column + {study} : Name of the study + {period} : Period used + Examples: + 'study: {study} - period: {period}' + kwargs: + legendgroup : bool + If true, all legend items are grouped into a + single one + All formatting values available on iplot() + """ + if not column: + column=self._d['close'] + study={'kind':'ama', + 'name':name, + 'params':{'periods':periods,'column':column, + 'str':str}, + 'display':utils.merge_dict({'legendgroup':False},kwargs)} + self._add_study(study) + + def add_kalman(self,periods=1,column=None,name='', + str=None,**kwargs): + """ + Saran: Add a Kalman Filter study to QuantFigure.studies + + Parameters: + column :string + Defines the data column name that contains the + data over which the study will be applied. + Default: 'close' + name : string + Name given to the study + str : string + Label factory for studies + The following wildcards can be used: + {name} : Name of the column + {study} : Name of the study + Examples: + 'study: {study}' + kwargs: + legendgroup : bool + If true, all legend items are grouped into a + single one + All formatting values available on iplot() + """ + if not column: + column=self._d['close'] + study={'kind':'kalman', + 'name':name, + 'params':{'periods':periods,'column':column, + 'str':str}, + 'display':utils.merge_dict({'legendgroup':False},kwargs)} + self._add_study(study) + def add_rsi(self,periods=20,rsi_upper=70,rsi_lower=30,showbands=True,column=None, - name='',str=None,**kwargs): + name='',str='{name}({period})',**kwargs): """ Add Relative Strength Indicator (RSI) study to QuantFigure.studies @@ -763,7 +876,7 @@ def add_rsi(self,periods=20,rsi_upper=70,rsi_lower=30,showbands=True,column=None self._add_study(study) def add_bollinger_bands(self,periods=20,boll_std=2,fill=True,column=None,name='', - str='{name}({column},{period})',**kwargs): + str='{name}({period})',**kwargs): """ Add Bollinger Bands (BOLL) study to QuantFigure.studies @@ -1068,7 +1181,7 @@ def get_params(locals_list,params,display,append_study=True): fig['data'][0].update(marker=dict(color=bar_colors,line=dict(color=bar_colors)), opacity=0.8) - if kind in ('sma','ema','atr','adx','dmi','ptps'): + if kind in ('sma','ema','atr','adx','dmi','ptps','ama','kalman', f'{df}'): #Saran local_kwargs,params=get_params([],params,display) fig=df.ta_figure(study=kind,**params) @@ -1144,7 +1257,7 @@ def get_params(locals_list,params,display,append_study=True): def iplot(self,**kwargs): __QUANT_FIGURE_EXPORT = ['asFigure','asUrl','asImage','asPlot','display_image','validate', - 'sharing','online','filename','dimensions'] + 'sharing','online','filename','dimensions','auto_open'] # Saran added auto_open layout=copy.deepcopy(self.layout) data=copy.deepcopy(self.data) @@ -1154,6 +1267,7 @@ def iplot(self,**kwargs): data['resample']=kwargs.pop('resample',data.pop('resample',None)) asFigure=kwargs.pop('asFigure',False) + auto_open=kwargs.pop('auto_open',False) # Saran showstudies=kwargs.pop('showstudies',True) study_kwargs=utils.kwargs_from_keyword(kwargs,{},'study',True) datalegend=kwargs.pop('datalegend',data.pop('datalegend',data.pop('showlegend',True))) @@ -1237,7 +1351,7 @@ def iplot(self,**kwargs): if 'yaxis' in study_fig['layout']: study_fig['layout']['yaxis1']=study_fig['layout']['yaxis'].copy() del study_fig['layout']['yaxis'] - if v['kind'] in ('boll','sma','ema','ptps'): + if v['kind'] in ('boll','sma','ema','ptps','ama','kalman',f'{df}'): #Saran tools._move_axis(study_fig, yaxis='y2') # FIXME TKP pass if v['kind'] in ('rsi','volume','macd','atr','adx','cci','dmi'): @@ -1265,7 +1379,7 @@ def iplot(self,**kwargs): except: pass if asFigure: - return go.Figure(fig) + return go.Figure(fig) # , write_html={'auto_open': auto_open} else: return pt_iplot(fig, **export_kwargs) diff --git a/cufflinks/ta.py b/cufflinks/ta.py index b72fa23..f0b5462 100644 --- a/cufflinks/ta.py +++ b/cufflinks/ta.py @@ -4,7 +4,8 @@ # import talib from plotly.graph_objs import Figure from .utils import make_list - +import ta #Saran +from pykalman import KalmanFilter #Saran class StudyError(Exception): pass @@ -176,6 +177,27 @@ def _sma(df,periods,column,include,str,detail=False): return pd.concat([df,__df],axis=1) else: return __df + +def line(df,column=None,include=True,str='{name}({column})',detail=False): + def _line(df,column,include,str,detail=False): + study=f'{df}' + df,_df,column=validate(df,column) + + ## === talib ==== + # _df['SMA']=pd.Series(talib.MA(df[column].values,periods),index=df.index) + ## === /talib ==== + + ## === pure python ==== + _df[f'{df}']=df[column] + ## === /pure python ==== + + return rename(df,_df,study,column,include,str,detail) + column=make_list(column) + __df=pd.concat([_sma(df,column=x,include=False,str=str) for y in periods],axis=1) + if include: + return pd.concat([df,__df],axis=1) + else: + return __df def ema(df,periods=21,column=None,include=True,str='{name}({column},{period})',detail=False): def _ema(df,periods,column,include,str,detail=False): @@ -198,6 +220,83 @@ def _ema(df,periods,column,include,str,detail=False): return pd.concat([df,__df],axis=1) else: return __df + +# def ama(df,periods=9,fast_period=6,slow_period=12,column=None,include=True,str='{name}({column},{period})',detail=False): + +def ama(df,periods=9,column=None,include=True,str='{name}({column},{period})',detail=False): #fast_period=6,slow_period=12, + def _ama(df,periods,column,include,str,detail=False): + fast_period=6 + slow_period=12 + study=f"AMA({fast_period},{slow_period})" + df,_df,column=validate(df,column) + + ## === talib ==== + #_df['AMA']=pd.Series(talib.MA(df[column].values,periods),index=df.index) + #_df['AMA']=pd.Series(talib.KAMA(df[column].values,periods),index=df.index) + ## === /talib ==== + + ## === ta ==== + window = periods + + _df[f"AMA({fast_period},{slow_period})"]=ta.momentum.KAMAIndicator(df[column],window=window,pow1=6,pow2=12, fillna=False).kama() + #_df=pd.DataFrame({'AMA':ama,},index=df.index) + #_df= _df.reindex(df.index) + #ama.to_json(orient='real') + #_df=pd.DataFrame({'AMA':ama},index=df.index) + ## === /ta ==== + + # macd,signal,hist=talib.MACD(df[column].values,fast_period,slow_period,signal_period) + # _df=pd.DataFrame({'MACD':macd,'SIGNAL':signal},index=df.index) + + return rename(df,_df,study,periods,column,include,str,detail) + column=make_list(column) + periods=make_list(periods) + __df=pd.concat([_ama(df,column=x,periods=y,include=False,str=str) for y in periods for x in column],axis=1) + if include: + return pd.concat([df,__df],axis=1) + else: + return __df + +def kalman(df,periods=1,column=None,include=True,str='{name}({period})',detail=False): + def _kalman(df,periods,column,include,str,detail=False): + study="kalman" + df,_df,column=validate(df,column) + + transition_matrices=[1] + observation_matrices=[1] + # initial_state_mean=0 + initial_state_mean= df[column][0] + initial_state_covariance=1 + observation_covariance=1, + transition_covariance=.01 + + kf = KalmanFilter(transition_matrices=transition_matrices, + observation_matrices=observation_matrices, + initial_state_mean=initial_state_mean, + initial_state_covariance=initial_state_covariance, + observation_covariance=observation_covariance, + transition_covariance=transition_covariance) + + state_means, _ = kf.filter(df[column]) + # print(state_means) + + _df.index = df.index + _df["kalman"] = state_means + # _df["kalman"] = _df["kalman"][19:] + # print(_df) + + __df = rename(df,_df,study,periods,column,include,str,detail) + __df.name = 'KALMAN' + return __df + + column=make_list(column) + periods=make_list(periods) + + __df=pd.concat([_kalman(df,column=x,periods=y,include=False,str=str) for y in periods for x in column],axis=1) + if include: + return pd.concat([df,__df],axis=1) + else: + return __df def dmi(df,periods=14,high='high',low='low',close='close',include=True,str='{name}({period})',**kwargs): return adx(df,periods=periods,high=high,low=low,close=close,di=True,include=include,str=str,**kwargs) @@ -435,7 +534,7 @@ def _correl(df,periods=21,columns=None,include=True,str=None,detail=False,**corr else: return __df -def boll(df,periods=20,boll_std=2,column=None,include=True,str='{name}({column},{period})',detail=False,**boll_kwargs): +def boll(df,periods=20,boll_std=2,column=None,include=True,str='{name}({column},{period})',detail=True,**boll_kwargs): def _boll(df,periods,column): study='BOLL' df,_df,column=validate(df,column) diff --git a/cufflinks/tools.py b/cufflinks/tools.py index 0a15a02..d7be8a8 100644 --- a/cufflinks/tools.py +++ b/cufflinks/tools.py @@ -25,7 +25,7 @@ 'framecolor','coastlinewidth','landcolor','showcoastlines','framewidth','resolution','projection_type'] __ANN_KWARGS=['xref','yref','text','showarrow', - 'arrowhead','ax','ay','textangle','arrowsize', + 'arrowhead','ax','ay','anntextangle','arrowsize', 'arrowlen', 'arrowwidth','arrowcolor','fontcolor','fontsize','xanchor','yanchor','align'] __LAYOUT_AXIS=['autorange','autotick','backgroundcolor','categoryarray','categoryarraysrc','categoryorder', @@ -54,7 +54,6 @@ def getTheme(theme=None): """ Returns a theme definition. - To see the colors translated (hex) use cufflinks.getLayout(theme) instead. """ @@ -95,7 +94,6 @@ def getLayout(kind=None,theme=None,title='',xTitle='',yTitle='',zTitle='',barmod annotations=None,is3d=False,**kwargs): """ Generates a plotly Layout - Parameters: ----------- theme : string @@ -142,10 +140,8 @@ def getLayout(kind=None,theme=None,title='',xTitle='',yTitle='',zTitle='',barmod List of Plotly Annotations is3d : bool Indicates if the layout is for a 3D chart - Other Kwargs ============ - Shapes hline : int, list or dict Draws a horizontal line at the @@ -172,7 +168,6 @@ def getLayout(kind=None,theme=None,title='',xTitle='',yTitle='',zTitle='',barmod specifications of a given shape. See help(cufflinks.tools.get_shape) for more information - Axis Ranges xrange : [lower_bound,upper_bound] Sets the range for the x axis @@ -180,13 +175,11 @@ def getLayout(kind=None,theme=None,title='',xTitle='',yTitle='',zTitle='',barmod Sets the range for the y axis zrange : [lower_bound,upper_bound] Sets the range for the z axis - Explicit Layout Updates layout_update : dict The layout will be modified with all the explicit values stated in the dictionary - Range Selector rangeselector : dict Defines a rangeselector object @@ -195,7 +188,6 @@ def getLayout(kind=None,theme=None,title='',xTitle='',yTitle='',zTitle='',barmod {'steps':['1y','2 months','5 weeks','ytd','2mtd'], 'axis':'xaxis', 'bgcolor' : ('blue',.3), 'x': 0.2 , 'y' : 0.9} - Range Slider rangeslider : bool or dict Defines if a rangeslider is displayed @@ -205,13 +197,12 @@ def getLayout(kind=None,theme=None,title='',xTitle='',yTitle='',zTitle='',barmod Rangeslider object Example: {'bgcolor':('blue',.3),'autorange':True} - Annotations fontcolor : str Text color for annotations fontsize : int Text size for annotations - textangle : int + anntextangle : int Textt angle See https://plot.ly/python/reference/#layout-annotations for a complete list of valid parameters. @@ -247,9 +238,12 @@ def getLayout(kind=None,theme=None,title='',xTitle='',yTitle='',zTitle='',barmod layout.update(bargap=bargap) if title: try: - layout['title'].update({'text':title}) + layout.update(title=title) except: - layout.update({'title':title}) + try: + layout['title'].update({'text':title}) + except: + layout.update({'title':title}) if annotations: layout.update({'annotations':annotations}) @@ -463,10 +457,9 @@ def get_span(xspan): return layout -def get_annotations(df,annotations,kind='lines',theme=None,**kwargs): +def get_annotations(df,annotations,kind='lines',theme=None, annot_col=None,**kwargs): """ Generates an annotations object - Parameters: ----------- df : DataFrame @@ -523,7 +516,7 @@ def check_ann(annotation): arrowcolor=annotation.get('arrowcolor',kwargs.get('arrowcolor')), ax=annotation.get('ax',0), ay=annotation.get('ay',-100), - textangle=annotation.get('textangle',-90), + textangle=annotation.get('anntextangle',0), hovertext=annotation.get('hovertext',''), opacity=annotation.get('opacity',1), font = dict( @@ -539,6 +532,12 @@ def check_ann(annotation): d=ta._ohlc_dict(df) maxv=df[d['high']].loc[k] yref='y2' + elif kind=='scatter': + if k in df.index: + maxv=df[[annot_col]].loc[k].sum() + else: + maxv = 0 + yref='y' else: maxv=df.loc[k].sum() if k in df.index else 0 yref='y1' @@ -552,8 +551,8 @@ def check_ann(annotation): arrowhead=kwargs.get('arrowhead',7), arrowcolor = kwargs['arrowcolor'], ax=kwargs.get('ax',0), - ay=kwargs.get('ay',-100), - textangle=kwargs.get('textangle',-90), + ay=kwargs.get('arrowlen',-50), + textangle=kwargs.get('anntextangle',0), hovertext=kwargs.get('hovertext', ''), opacity=kwargs.get('opacity',1), font = dict( @@ -576,7 +575,6 @@ def check_ann(annotation): def strip_figures(figure): """ Strips a figure into multiple figures with a trace on each of them - Parameters: ----------- figure : Figure @@ -592,7 +590,6 @@ def get_base_layout(figs): """ Generates a layout with the union of all properties of multiple figures' layouts - Parameters: ----------- fig : list(Figures) @@ -609,7 +606,6 @@ def get_base_layout(figs): def figures(df,specs,asList=False): """ Generates multiple Plotly figures for a given DataFrame - Parameters: ----------- df : DataFrame @@ -635,7 +631,6 @@ def figures(df,specs,asList=False): def merge_figures(figures): """ Generates a single Figure from a list of figures - Parameters: ----------- figures : list(Figures) @@ -658,7 +653,6 @@ def subplots(figures,shape=None, """ Generates a subplot view for a set of figures This is a wrapper for plotly.subplots.make_subplots - Parameters: ----------- figures : [Figures] @@ -701,26 +695,19 @@ def subplots(figures,shape=None, Subplot specifications. ex1: specs=[[{}, {}], [{'colspan': 2}, None]] ex2: specs=[[{'rowspan': 2}, {}], [None, {}]] - - Indices of the outer list correspond to subplot grid rows starting from the bottom. The number of rows in 'specs' must be equal to 'rows'. - - Indices of the inner lists correspond to subplot grid columns starting from the left. The number of columns in 'specs' must be equal to 'cols'. - - Each item in the 'specs' list corresponds to one subplot in a subplot grid. (N.B. The subplot grid has exactly 'rows' times 'cols' cells.) - - Use None for blank a subplot cell (or to move pass a col/row span). - - Note that specs[0][0] has the specs of the 'start_cell' subplot. - - Each item in 'specs' is a dictionary. The available keys are: - * is_3d (boolean, default=False): flag for 3d scenes * colspan (int, default=1): number of subplot columns for this subplot to span. @@ -730,16 +717,12 @@ def subplots(figures,shape=None, * r (float, default=0.0): padding right of cell * t (float, default=0.0): padding right of cell * b (float, default=0.0): padding bottom of cell - - Use 'horizontal_spacing' and 'vertical_spacing' to adjust the spacing in between the subplots. - insets : list of dicts Inset specifications. - - Each item in 'insets' is a dictionary. The available keys are: - * cell (tuple, default=(1,1)): (row, col) index of the subplot cell to overlay inset axes onto. * is_3d (boolean, default=False): flag for 3d scenes @@ -812,7 +795,6 @@ def get_subplots(rows=1,cols=1, """ Generates a subplot view for a set of figures - Parameters: ----------- rows : int @@ -848,26 +830,19 @@ def get_subplots(rows=1,cols=1, Subplot specifications. ex1: specs=[[{}, {}], [{'colspan': 2}, None]] ex2: specs=[[{'rowspan': 2}, {}], [None, {}]] - - Indices of the outer list correspond to subplot grid rows starting from the bottom. The number of rows in 'specs' must be equal to 'rows'. - - Indices of the inner lists correspond to subplot grid columns starting from the left. The number of columns in 'specs' must be equal to 'cols'. - - Each item in the 'specs' list corresponds to one subplot in a subplot grid. (N.B. The subplot grid has exactly 'rows' times 'cols' cells.) - - Use None for blank a subplot cell (or to move pass a col/row span). - - Note that specs[0][0] has the specs of the 'start_cell' subplot. - - Each item in 'specs' is a dictionary. The available keys are: - * is_3d (boolean, default=False): flag for 3d scenes * colspan (int, default=1): number of subplot columns for this subplot to span. @@ -877,16 +852,12 @@ def get_subplots(rows=1,cols=1, * r (float, default=0.0): padding right of cell * t (float, default=0.0): padding right of cell * b (float, default=0.0): padding bottom of cell - - Use 'horizontal_spacing' and 'vertical_spacing' to adjust the spacing in between the subplots. - insets : list of dicts Inset specifications. - - Each item in 'insets' is a dictionary. The available keys are: - * cell (tuple, default=(1,1)): (row, col) index of the subplot cell to overlay inset axes onto. * is_3d (boolean, default=False): flag for 3d scenes @@ -1000,7 +971,6 @@ def scatter_matrix(df,theme=None,bins=10,color='grey',size=2): Displays a matrix with scatter plot for each pair of Series in the DataFrame. The diagonal shows a histogram for each of the Series - Parameters: ----------- df : DataFrame @@ -1130,7 +1100,6 @@ def _set_axis(self,traces,on=None,side='right',title=''): """ Sets the axis in which each trace should appear If the axis doesn't exist then a new axis is created - Parameters: ----------- traces : list(str) @@ -1265,7 +1234,6 @@ def get_shape(kind='line',x=None,y=None,x0=None,y0=None,x1=None,y1=None,span=0,c fillcolor=None,fill=False,opacity=1,xref='x',yref='y'): """ Returns a plotly shape - Parameters: ----------- kind : string @@ -1390,7 +1358,6 @@ def get_range_selector(steps=['1m','1y'],bgcolor='rgba(150, 200, 250, 0.4)',x=0, """ Returns a range selector Reference: https://plot.ly/python/reference/#layout-xaxis-rangeselector - Parameters: ----------- steps : string or list(string) @@ -1441,7 +1408,8 @@ def get_step(s): if term in ['y','year','yr']: steps='year' elif term in ['w','week','wk']: - steps='week' + steps='day' + cnt=cnt*7 elif term in ['m','month','mth','mnth','mo']: steps='month' elif term in ['hr','hour']: