1#-----------------------------------------------------------------------------
2# Copyright (c) 2012 - 2021, Anaconda, Inc., and Bokeh Contributors.
3# All rights reserved.
4#
5# The full license is in the file LICENSE.txt, distributed with this software.
6#-----------------------------------------------------------------------------
7
8#-----------------------------------------------------------------------------
9# Boilerplate
10#-----------------------------------------------------------------------------
11import logging # isort:skip
12log = logging.getLogger(__name__)
13
14#-----------------------------------------------------------------------------
15# Imports
16#-----------------------------------------------------------------------------
17
18# Bokeh imports
19from ..core.enums import HorizontalLocation, MarkerType, VerticalLocation
20from ..core.properties import (
21    Any,
22    Auto,
23    Either,
24    Enum,
25    Instance,
26    Int,
27    List,
28    Null,
29    Nullable,
30    Seq,
31    String,
32    Tuple,
33)
34from ..models import ColumnDataSource, GraphRenderer, Plot, Title, Tool, glyphs
35from ..models.tools import Drag, InspectTool, Scroll, Tap
36from ..transform import linear_cmap
37from ..util.options import Options
38from ._decorators import glyph_method, marker_method
39from ._graph import get_graph_kwargs
40from ._plot import get_range, get_scale, process_axis_and_grid
41from ._stack import double_stack, single_stack
42from ._tools import process_active_tools, process_tools_arg
43
44#-----------------------------------------------------------------------------
45# Globals and constants
46#-----------------------------------------------------------------------------
47
48DEFAULT_TOOLS = "pan,wheel_zoom,box_zoom,save,reset,help"
49
50__all__ = (
51    'Figure',
52    'figure',
53    'markers',
54)
55
56#-----------------------------------------------------------------------------
57# General API
58#-----------------------------------------------------------------------------
59
60class Figure(Plot):
61    ''' Create a new Figure for plotting.
62
63    A subclass of :class:`~bokeh.models.plots.Plot` that simplifies plot
64    creation with default axes, grids, tools, etc.
65
66    Figure objects have many glyph methods that can be used to draw
67    vectorized graphical glyphs:
68
69    .. hlist::
70        :columns: 3
71
72        * :func:`~bokeh.plotting.Figure.annular_wedge`
73        * :func:`~bokeh.plotting.Figure.annulus`
74        * :func:`~bokeh.plotting.Figure.arc`
75        * :func:`~bokeh.plotting.Figure.asterisk`
76        * :func:`~bokeh.plotting.Figure.bezier`
77        * :func:`~bokeh.plotting.Figure.circle`
78        * :func:`~bokeh.plotting.Figure.circle_cross`
79        * :func:`~bokeh.plotting.Figure.circle_dot`
80        * :func:`~bokeh.plotting.Figure.circle_x`
81        * :func:`~bokeh.plotting.Figure.circle_y`
82        * :func:`~bokeh.plotting.Figure.cross`
83        * :func:`~bokeh.plotting.Figure.dash`
84        * :func:`~bokeh.plotting.Figure.diamond`
85        * :func:`~bokeh.plotting.Figure.diamond_cross`
86        * :func:`~bokeh.plotting.Figure.diamond_dot`
87        * :func:`~bokeh.plotting.Figure.dot`
88        * :func:`~bokeh.plotting.Figure.ellipse`
89        * :func:`~bokeh.plotting.Figure.harea`
90        * :func:`~bokeh.plotting.Figure.hbar`
91        * :func:`~bokeh.plotting.Figure.hex`
92        * :func:`~bokeh.plotting.Figure.hex_tile`
93        * :func:`~bokeh.plotting.Figure.image`
94        * :func:`~bokeh.plotting.Figure.image_rgba`
95        * :func:`~bokeh.plotting.Figure.image_url`
96        * :func:`~bokeh.plotting.Figure.inverted_triangle`
97        * :func:`~bokeh.plotting.Figure.line`
98        * :func:`~bokeh.plotting.Figure.multi_line`
99        * :func:`~bokeh.plotting.Figure.multi_polygons`
100        * :func:`~bokeh.plotting.Figure.oval`
101        * :func:`~bokeh.plotting.Figure.patch`
102        * :func:`~bokeh.plotting.Figure.patches`
103        * :func:`~bokeh.plotting.Figure.plus`
104        * :func:`~bokeh.plotting.Figure.quad`
105        * :func:`~bokeh.plotting.Figure.quadratic`
106        * :func:`~bokeh.plotting.Figure.ray`
107        * :func:`~bokeh.plotting.Figure.rect`
108        * :func:`~bokeh.plotting.Figure.segment`
109        * :func:`~bokeh.plotting.Figure.square`
110        * :func:`~bokeh.plotting.Figure.square_cross`
111        * :func:`~bokeh.plotting.Figure.square_dot`
112        * :func:`~bokeh.plotting.Figure.square_pin`
113        * :func:`~bokeh.plotting.Figure.square_x`
114        * :func:`~bokeh.plotting.Figure.star`
115        * :func:`~bokeh.plotting.Figure.star_dot`
116        * :func:`~bokeh.plotting.Figure.step`
117        * :func:`~bokeh.plotting.Figure.text`
118        * :func:`~bokeh.plotting.Figure.triangle`
119        * :func:`~bokeh.plotting.Figure.triangle_dot`
120        * :func:`~bokeh.plotting.Figure.triangle_pin`
121        * :func:`~bokeh.plotting.Figure.varea`
122        * :func:`~bokeh.plotting.Figure.vbar`
123        * :func:`~bokeh.plotting.Figure.wedge`
124        * :func:`~bokeh.plotting.Figure.x`
125        * :func:`~bokeh.plotting.Figure.y`
126
127    There is a scatter function that can be parameterized by marker type:
128
129    * :func:`~bokeh.plotting.Figure.scatter`
130
131    There are also specialized methods for stacking bars:
132
133    * bars: :func:`~bokeh.plotting.Figure.hbar_stack`, :func:`~bokeh.plotting.Figure.vbar_stack`
134    * lines: :func:`~bokeh.plotting.Figure.hline_stack`, :func:`~bokeh.plotting.Figure.vline_stack`
135    * areas: :func:`~bokeh.plotting.Figure.harea_stack`, :func:`~bokeh.plotting.Figure.varea_stack`
136
137    As well as one specialized method for making simple hexbin plots:
138
139    * :func:`~bokeh.plotting.Figure.hexbin`
140
141    In addition to all the ``Figure`` property attributes, the following
142    options are also accepted:
143
144    .. bokeh-options:: FigureOptions
145        :module: bokeh.plotting.figure
146
147    '''
148
149    __subtype__ = "Figure"
150    __view_model__ = "Plot"
151
152    def __init__(self, *arg, **kw):
153
154        if 'plot_width' in kw and 'width' in kw:
155            raise ValueError("Figure called with both 'plot_width' and 'width' supplied, supply only one")
156        if 'plot_height' in kw and 'height' in kw:
157            raise ValueError("Figure called with both 'plot_height' and 'height' supplied, supply only one")
158
159        opts = FigureOptions(kw)
160
161        title = kw.get("title", None)
162        if isinstance(title, str):
163            kw['title'] = Title(text=title)
164
165        super().__init__(*arg, **kw)
166
167        self.x_range = get_range(opts.x_range)
168        self.y_range = get_range(opts.y_range)
169
170        self.x_scale = get_scale(self.x_range, opts.x_axis_type)
171        self.y_scale = get_scale(self.y_range, opts.y_axis_type)
172
173        process_axis_and_grid(self, opts.x_axis_type, opts.x_axis_location, opts.x_minor_ticks, opts.x_axis_label, self.x_range, 0)
174        process_axis_and_grid(self, opts.y_axis_type, opts.y_axis_location, opts.y_minor_ticks, opts.y_axis_label, self.y_range, 1)
175
176        tool_objs, tool_map = process_tools_arg(self, opts.tools, opts.tooltips)
177        self.add_tools(*tool_objs)
178        process_active_tools(self.toolbar, tool_map, opts.active_drag, opts.active_inspect, opts.active_scroll, opts.active_tap)
179
180    @glyph_method(glyphs.AnnularWedge)
181    def annular_wedge(self, **kwargs):
182        pass
183
184    @glyph_method(glyphs.Annulus)
185    def annulus(self, **kwargs):
186        """
187Examples:
188
189    .. bokeh-plot::
190        :source-position: above
191
192        from bokeh.plotting import figure, output_file, show
193
194        plot = figure(plot_width=300, plot_height=300)
195        plot.annulus(x=[1, 2, 3], y=[1, 2, 3], color="#7FC97F",
196                     inner_radius=0.2, outer_radius=0.5)
197
198        show(plot)
199
200"""
201
202    @glyph_method(glyphs.Arc)
203    def arc(self, **kwargs):
204        pass
205
206    @marker_method()
207    def asterisk(self, **kwargs):
208        """
209Examples:
210
211    .. bokeh-plot::
212        :source-position: above
213
214        from bokeh.plotting import figure, output_file, show
215
216        plot = figure(plot_width=300, plot_height=300)
217        plot.asterisk(x=[1,2,3], y=[1,2,3], size=20, color="#F0027F")
218
219        show(plot)
220
221"""
222
223    @glyph_method(glyphs.Bezier)
224    def bezier(self, **kwargs):
225        pass
226
227    @glyph_method(glyphs.Circle)
228    def circle(self, **kwargs):
229        """
230.. note::
231    Only one of ``size`` or ``radius`` should be provided. Note that ``radius``
232    defaults to data units.
233
234Examples:
235
236    .. bokeh-plot::
237        :source-position: above
238
239        from bokeh.plotting import figure, output_file, show
240
241        plot = figure(plot_width=300, plot_height=300)
242        plot.circle(x=[1, 2, 3], y=[1, 2, 3], size=20)
243
244        show(plot)
245
246"""
247
248    @marker_method()
249    def circle_cross(self, **kwargs):
250        """
251Examples:
252
253    .. bokeh-plot::
254        :source-position: above
255
256        from bokeh.plotting import figure, output_file, show
257
258        plot = figure(plot_width=300, plot_height=300)
259        plot.circle_cross(x=[1,2,3], y=[4,5,6], size=20,
260                          color="#FB8072", fill_alpha=0.2, line_width=2)
261
262        show(plot)
263
264"""
265
266    @marker_method()
267    def circle_dot(self, **kwargs):
268        """
269Examples:
270
271    .. bokeh-plot::
272        :source-position: above
273
274        from bokeh.plotting import figure, output_file, show
275
276        plot = figure(plot_width=300, plot_height=300)
277        plot.circle_dot(x=[1,2,3], y=[4,5,6], size=20,
278                        color="#FB8072", fill_color=None)
279
280        show(plot)
281
282"""
283
284    @marker_method()
285    def circle_x(self, **kwargs):
286        """
287Examples:
288
289    .. bokeh-plot::
290        :source-position: above
291
292        from bokeh.plotting import figure, output_file, show
293
294        plot = figure(plot_width=300, plot_height=300)
295        plot.circle_x(x=[1, 2, 3], y=[1, 2, 3], size=20,
296                      color="#DD1C77", fill_alpha=0.2)
297
298        show(plot)
299
300"""
301
302    @marker_method()
303    def circle_y(self, **kwargs):
304        """
305Examples:
306
307    .. bokeh-plot::
308        :source-position: above
309
310        from bokeh.plotting import figure, output_file, show
311
312        plot = figure(plot_width=300, plot_height=300)
313        plot.circle_y(x=[1, 2, 3], y=[1, 2, 3], size=20,
314                      color="#DD1C77", fill_alpha=0.2)
315
316        show(plot)
317
318"""
319
320    @marker_method()
321    def cross(self, **kwargs):
322        """
323Examples:
324
325    .. bokeh-plot::
326        :source-position: above
327
328        from bokeh.plotting import figure, output_file, show
329
330        plot = figure(plot_width=300, plot_height=300)
331        plot.cross(x=[1, 2, 3], y=[1, 2, 3], size=20,
332                   color="#E6550D", line_width=2)
333
334        show(plot)
335
336"""
337
338    @marker_method()
339    def dash(self, **kwargs):
340        """
341Examples:
342
343    .. bokeh-plot::
344        :source-position: above
345
346        from bokeh.plotting import figure, output_file, show
347
348        plot = figure(plot_width=300, plot_height=300)
349        plot.dash(x=[1, 2, 3], y=[1, 2, 3], size=[10,20,25],
350                  color="#99D594", line_width=2)
351
352        show(plot)
353
354"""
355
356    @marker_method()
357    def diamond(self, **kwargs):
358        """
359Examples:
360
361    .. bokeh-plot::
362        :source-position: above
363
364        from bokeh.plotting import figure, output_file, show
365
366        plot = figure(plot_width=300, plot_height=300)
367        plot.diamond(x=[1, 2, 3], y=[1, 2, 3], size=20,
368                     color="#1C9099", line_width=2)
369
370        show(plot)
371
372"""
373
374    @marker_method()
375    def diamond_cross(self, **kwargs):
376        """
377Examples:
378
379    .. bokeh-plot::
380        :source-position: above
381
382        from bokeh.plotting import figure, output_file, show
383
384        plot = figure(plot_width=300, plot_height=300)
385        plot.diamond_cross(x=[1, 2, 3], y=[1, 2, 3], size=20,
386                           color="#386CB0", fill_color=None, line_width=2)
387
388        show(plot)
389
390"""
391
392    @marker_method()
393    def diamond_dot(self, **kwargs):
394        """
395Examples:
396
397    .. bokeh-plot::
398        :source-position: above
399
400        from bokeh.plotting import figure, output_file, show
401
402        plot = figure(plot_width=300, plot_height=300)
403        plot.diamond_dot(x=[1, 2, 3], y=[1, 2, 3], size=20,
404                         color="#386CB0", fill_color=None)
405
406        show(plot)
407
408"""
409
410    @marker_method()
411    def dot(self, **kwargs):
412        """
413Examples:
414
415    .. bokeh-plot::
416        :source-position: above
417
418        from bokeh.plotting import figure, output_file, show
419
420        plot = figure(plot_width=300, plot_height=300)
421        plot.dot(x=[1, 2, 3], y=[1, 2, 3], size=20, color="#386CB0")
422
423        show(plot)
424
425"""
426
427    @glyph_method(glyphs.HArea)
428    def harea(self, **kwargs):
429        """
430Examples:
431
432    .. bokeh-plot::
433        :source-position: above
434
435        from bokeh.plotting import figure, output_file, show
436
437        plot = figure(plot_width=300, plot_height=300)
438        plot.harea(x1=[0, 0, 0], x2=[1, 4, 2], y=[1, 2, 3],
439                   fill_color="#99D594")
440
441        show(plot)
442
443"""
444
445    @glyph_method(glyphs.HBar)
446    def hbar(self, **kwargs):
447        """
448Examples:
449
450    .. bokeh-plot::
451        :source-position: above
452
453        from bokeh.plotting import figure, output_file, show
454
455        plot = figure(plot_width=300, plot_height=300)
456        plot.hbar(y=[1, 2, 3], height=0.5, left=0, right=[1,2,3], color="#CAB2D6")
457
458        show(plot)
459
460"""
461
462    @glyph_method(glyphs.Ellipse)
463    def ellipse(self, **kwargs):
464        """
465Examples:
466
467    .. bokeh-plot::
468        :source-position: above
469
470        from bokeh.plotting import figure, output_file, show
471
472        plot = figure(plot_width=300, plot_height=300)
473        plot.ellipse(x=[1, 2, 3], y=[1, 2, 3], width=30, height=20,
474                     color="#386CB0", fill_color=None, line_width=2)
475
476        show(plot)
477
478"""
479
480    @marker_method()
481    def hex(self, **kwargs):
482        """
483Examples:
484
485    .. bokeh-plot::
486        :source-position: above
487
488        from bokeh.plotting import figure, output_file, show
489
490        plot = figure(plot_width=300, plot_height=300)
491        plot.hex(x=[1, 2, 3], y=[1, 2, 3], size=[10,20,30], color="#74ADD1")
492
493        show(plot)
494
495"""
496
497    @marker_method()
498    def hex_dot(self, **kwargs):
499        """
500Examples:
501
502    .. bokeh-plot::
503        :source-position: above
504
505        from bokeh.plotting import figure, output_file, show
506
507        plot = figure(plot_width=300, plot_height=300)
508        plot.hex_dot(x=[1, 2, 3], y=[1, 2, 3], size=[10,20,30],
509                     color="#74ADD1", fill_color=None)
510
511        show(plot)
512
513"""
514
515    @glyph_method(glyphs.HexTile)
516    def hex_tile(self, **kwargs):
517        """
518Examples:
519
520    .. bokeh-plot::
521        :source-position: above
522
523        from bokeh.plotting import figure, output_file, show
524
525        plot = figure(plot_width=300, plot_height=300, match_aspect=True)
526        plot.hex_tile(r=[0, 0, 1], q=[1, 2, 2], fill_color="#74ADD1")
527
528        show(plot)
529
530"""
531
532    @glyph_method(glyphs.Image)
533    def image(self, **kwargs):
534        """
535.. note::
536    If both ``palette`` and ``color_mapper`` are passed, a ``ValueError``
537    exception will be raised. If neither is passed, then the ``Greys9``
538    palette will be used as a default.
539
540"""
541
542    @glyph_method(glyphs.ImageRGBA)
543    def image_rgba(self, **kwargs):
544        """
545.. note::
546    The ``image_rgba`` method accepts images as a two-dimensional array of RGBA
547    values (encoded as 32-bit integers).
548
549"""
550
551    @glyph_method(glyphs.ImageURL)
552    def image_url(self, **kwargs):
553        pass
554
555    @marker_method()
556    def inverted_triangle(self, **kwargs):
557        """
558Examples:
559
560    .. bokeh-plot::
561        :source-position: above
562
563        from bokeh.plotting import figure, output_file, show
564
565        plot = figure(plot_width=300, plot_height=300)
566        plot.inverted_triangle(x=[1, 2, 3], y=[1, 2, 3], size=20, color="#DE2D26")
567
568        show(plot)
569
570"""
571
572    @glyph_method(glyphs.Line)
573    def line(self, **kwargs):
574        """
575Examples:
576
577    .. bokeh-plot::
578        :source-position: above
579
580        from bokeh.plotting import figure, output_file, show
581
582        p = figure(title="line", plot_width=300, plot_height=300)
583        p.line(x=[1, 2, 3, 4, 5], y=[6, 7, 2, 4, 5])
584
585        show(p)
586
587"""
588
589    @glyph_method(glyphs.MultiLine)
590    def multi_line(self, **kwargs):
591        """
592.. note::
593    For this glyph, the data is not simply an array of scalars, it is an
594    "array of arrays".
595
596Examples:
597
598    .. bokeh-plot::
599        :source-position: above
600
601        from bokeh.plotting import figure, output_file, show
602
603        p = figure(plot_width=300, plot_height=300)
604        p.multi_line(xs=[[1, 2, 3], [2, 3, 4]], ys=[[6, 7, 2], [4, 5, 7]],
605                    color=['red','green'])
606
607        show(p)
608
609"""
610
611    @glyph_method(glyphs.MultiPolygons)
612    def multi_polygons(self, **kwargs):
613        """
614.. note::
615    For this glyph, the data is not simply an array of scalars, it is a
616    nested array.
617
618Examples:
619
620    .. bokeh-plot::
621        :source-position: above
622
623        from bokeh.plotting import figure, output_file, show
624
625        p = figure(plot_width=300, plot_height=300)
626        p.multi_polygons(xs=[[[[1, 1, 2, 2]]], [[[1, 1, 3], [1.5, 1.5, 2]]]],
627                        ys=[[[[4, 3, 3, 4]]], [[[1, 3, 1], [1.5, 2, 1.5]]]],
628                        color=['red', 'green'])
629        show(p)
630
631"""
632
633    @glyph_method(glyphs.Oval)
634    def oval(self, **kwargs):
635        """
636Examples:
637
638    .. bokeh-plot::
639        :source-position: above
640
641        from bokeh.plotting import figure, output_file, show
642
643        plot = figure(plot_width=300, plot_height=300)
644        plot.oval(x=[1, 2, 3], y=[1, 2, 3], width=0.2, height=0.4,
645                  angle=-0.7, color="#1D91C0")
646
647        show(plot)
648
649"""
650
651    @glyph_method(glyphs.Patch)
652    def patch(self, **kwargs):
653        """
654Examples:
655
656    .. bokeh-plot::
657        :source-position: above
658
659        from bokeh.plotting import figure, output_file, show
660
661        p = figure(plot_width=300, plot_height=300)
662        p.patch(x=[1, 2, 3, 2], y=[6, 7, 2, 2], color="#99d8c9")
663
664        show(p)
665
666"""
667
668    @glyph_method(glyphs.Patches)
669    def patches(self, **kwargs):
670        """
671.. note::
672    For this glyph, the data is not simply an array of scalars, it is an
673    "array of arrays".
674
675Examples:
676
677    .. bokeh-plot::
678        :source-position: above
679
680        from bokeh.plotting import figure, output_file, show
681
682        p = figure(plot_width=300, plot_height=300)
683        p.patches(xs=[[1,2,3],[4,5,6,5]], ys=[[1,2,1],[4,5,5,4]],
684                  color=["#43a2ca", "#a8ddb5"])
685
686        show(p)
687
688"""
689
690    @marker_method()
691    def plus(self, **kwargs):
692        """
693Examples:
694
695    .. bokeh-plot::
696        :source-position: above
697
698        from bokeh.plotting import figure, output_file, show
699
700        plot = figure(plot_width=300, plot_height=300)
701        plot.plus(x=[1, 2, 3], y=[1, 2, 3], size=20, color="#DE2D26")
702
703        show(plot)
704
705"""
706
707    @glyph_method(glyphs.Quad)
708    def quad(self, **kwargs):
709        """
710Examples:
711
712    .. bokeh-plot::
713        :source-position: above
714
715        from bokeh.plotting import figure, output_file, show
716
717        plot = figure(plot_width=300, plot_height=300)
718        plot.quad(top=[2, 3, 4], bottom=[1, 2, 3], left=[1, 2, 3],
719                  right=[1.2, 2.5, 3.7], color="#B3DE69")
720
721        show(plot)
722
723"""
724
725    @glyph_method(glyphs.Quadratic)
726    def quadratic(self, **kwargs):
727        pass
728
729    @glyph_method(glyphs.Ray)
730    def ray(self, **kwargs):
731        """
732Examples:
733
734    .. bokeh-plot::
735        :source-position: above
736
737        from bokeh.plotting import figure, output_file, show
738
739        plot = figure(plot_width=300, plot_height=300)
740        plot.ray(x=[1, 2, 3], y=[1, 2, 3], length=45, angle=-0.7, color="#FB8072",
741                line_width=2)
742
743        show(plot)
744
745"""
746
747    @glyph_method(glyphs.Rect)
748    def rect(self, **kwargs):
749        """
750Examples:
751
752    .. bokeh-plot::
753        :source-position: above
754
755        from bokeh.plotting import figure, output_file, show
756
757        plot = figure(plot_width=300, plot_height=300)
758        plot.rect(x=[1, 2, 3], y=[1, 2, 3], width=10, height=20, color="#CAB2D6",
759                  width_units="screen", height_units="screen")
760
761        show(plot)
762
763"""
764
765    @glyph_method(glyphs.Step)
766    def step(self, **kwargs):
767        """
768Examples:
769
770    .. bokeh-plot::
771        :source-position: above
772
773        from bokeh.plotting import figure, output_file, show
774
775        plot = figure(plot_width=300, plot_height=300)
776        plot.step(x=[1, 2, 3, 4, 5], y=[1, 2, 3, 2, 5], color="#FB8072")
777
778        show(plot)
779
780"""
781
782    @glyph_method(glyphs.Segment)
783    def segment(self, **kwargs):
784        """
785Examples:
786
787    .. bokeh-plot::
788        :source-position: above
789
790        from bokeh.plotting import figure, output_file, show
791
792        plot = figure(plot_width=300, plot_height=300)
793        plot.segment(x0=[1, 2, 3], y0=[1, 2, 3],
794                     x1=[1, 2, 3], y1=[1.2, 2.5, 3.7],
795                     color="#F4A582", line_width=3)
796
797        show(plot)
798
799"""
800
801    @marker_method()
802    def square(self, **kwargs):
803        """
804Examples:
805
806    .. bokeh-plot::
807        :source-position: above
808
809        from bokeh.plotting import figure, output_file, show
810
811        plot = figure(plot_width=300, plot_height=300)
812        plot.square(x=[1, 2, 3], y=[1, 2, 3], size=[10,20,30], color="#74ADD1")
813
814        show(plot)
815
816"""
817
818    @marker_method()
819    def square_cross(self, **kwargs):
820        """
821Examples:
822
823    .. bokeh-plot::
824        :source-position: above
825
826        from bokeh.plotting import figure, output_file, show
827
828        plot = figure(plot_width=300, plot_height=300)
829        plot.square_cross(x=[1, 2, 3], y=[1, 2, 3], size=[10,20,25],
830                          color="#7FC97F",fill_color=None, line_width=2)
831
832        show(plot)
833
834"""
835
836    @marker_method()
837    def square_dot(self, **kwargs):
838        """
839Examples:
840
841    .. bokeh-plot::
842        :source-position: above
843
844        from bokeh.plotting import figure, output_file, show
845
846        plot = figure(plot_width=300, plot_height=300)
847        plot.square_dot(x=[1, 2, 3], y=[1, 2, 3], size=[10,20,25],
848                        color="#7FC97F", fill_color=None)
849
850        show(plot)
851
852"""
853
854    @marker_method()
855    def square_pin(self, **kwargs):
856        """
857Examples:
858
859    .. bokeh-plot::
860        :source-position: above
861
862        from bokeh.plotting import figure, output_file, show
863
864        plot = figure(plot_width=300, plot_height=300)
865        plot.square_pin(x=[1, 2, 3], y=[1, 2, 3], size=[10,20,25],
866                        color="#7FC97F",fill_color=None, line_width=2)
867
868        show(plot)
869
870"""
871
872    @marker_method()
873    def square_x(self, **kwargs):
874        """
875Examples:
876
877    .. bokeh-plot::
878        :source-position: above
879
880        from bokeh.plotting import figure, output_file, show
881
882        plot = figure(plot_width=300, plot_height=300)
883        plot.square_x(x=[1, 2, 3], y=[1, 2, 3], size=[10,20,25],
884                      color="#FDAE6B",fill_color=None, line_width=2)
885
886        show(plot)
887
888"""
889
890    @marker_method()
891    def star(self, **kwargs):
892        """
893Examples:
894
895    .. bokeh-plot::
896        :source-position: above
897
898        from bokeh.plotting import figure, output_file, show
899
900        plot = figure(plot_width=300, plot_height=300)
901        plot.star(x=[1, 2, 3], y=[1, 2, 3], size=20,
902                  color="#1C9099", line_width=2)
903
904        show(plot)
905
906"""
907
908    @marker_method()
909    def star_dot(self, **kwargs):
910        """
911Examples:
912
913    .. bokeh-plot::
914        :source-position: above
915
916        from bokeh.plotting import figure, output_file, show
917
918        plot = figure(plot_width=300, plot_height=300)
919        plot.star_dot(x=[1, 2, 3], y=[1, 2, 3], size=20,
920                      color="#386CB0", fill_color=None, line_width=2)
921
922        show(plot)
923
924"""
925
926    @glyph_method(glyphs.Text)
927    def text(self, **kwargs):
928        """
929.. note::
930    The location and angle of the text relative to the ``x``, ``y`` coordinates
931    is indicated by the alignment and baseline text properties.
932
933"""
934
935    @marker_method()
936    def triangle(self, **kwargs):
937        """
938Examples:
939
940    .. bokeh-plot::
941        :source-position: above
942
943        from bokeh.plotting import figure, output_file, show
944
945        plot = figure(plot_width=300, plot_height=300)
946        plot.triangle(x=[1, 2, 3], y=[1, 2, 3], size=[10,20,25],
947                      color="#99D594", line_width=2)
948
949        show(plot)
950
951"""
952
953    @marker_method()
954    def triangle_dot(self, **kwargs):
955        """
956Examples:
957
958    .. bokeh-plot::
959        :source-position: above
960
961        from bokeh.plotting import figure, output_file, show
962
963        plot = figure(plot_width=300, plot_height=300)
964        plot.triangle_dot(x=[1, 2, 3], y=[1, 2, 3], size=[10,20,25],
965                          color="#99D594", fill_color=None)
966
967        show(plot)
968
969"""
970
971    @marker_method()
972    def triangle_pin(self, **kwargs):
973        """
974Examples:
975
976    .. bokeh-plot::
977        :source-position: above
978
979        from bokeh.plotting import figure, output_file, show
980
981        plot = figure(plot_width=300, plot_height=300)
982        plot.triangle_pin(x=[1, 2, 3], y=[1, 2, 3], size=[10,20,25],
983                      color="#99D594", line_width=2)
984
985        show(plot)
986
987"""
988
989    @glyph_method(glyphs.VArea)
990    def varea(self, **kwargs):
991        """
992Examples:
993
994    .. bokeh-plot::
995        :source-position: above
996
997        from bokeh.plotting import figure, output_file, show
998
999        plot = figure(plot_width=300, plot_height=300)
1000        plot.varea(x=[1, 2, 3], y1=[0, 0, 0], y2=[1, 4, 2],
1001                   fill_color="#99D594")
1002
1003        show(plot)
1004
1005"""
1006
1007    @glyph_method(glyphs.VBar)
1008    def vbar(self, **kwargs):
1009        """
1010Examples:
1011
1012    .. bokeh-plot::
1013        :source-position: above
1014
1015        from bokeh.plotting import figure, output_file, show
1016
1017        plot = figure(plot_width=300, plot_height=300)
1018        plot.vbar(x=[1, 2, 3], width=0.5, bottom=0, top=[1,2,3], color="#CAB2D6")
1019
1020        show(plot)
1021
1022"""
1023
1024    @glyph_method(glyphs.Wedge)
1025    def wedge(self, **kwargs):
1026        """
1027Examples:
1028
1029    .. bokeh-plot::
1030        :source-position: above
1031
1032        from bokeh.plotting import figure, output_file, show
1033
1034        plot = figure(plot_width=300, plot_height=300)
1035        plot.wedge(x=[1, 2, 3], y=[1, 2, 3], radius=15, start_angle=0.6,
1036                   end_angle=4.1, radius_units="screen", color="#2b8cbe")
1037
1038        show(plot)
1039
1040"""
1041
1042    @marker_method()
1043    def x(self, **kwargs):
1044        """
1045Examples:
1046
1047    .. bokeh-plot::
1048        :source-position: above
1049
1050        from bokeh.plotting import figure, output_file, show
1051
1052        plot = figure(plot_width=300, plot_height=300)
1053        plot.x(x=[1, 2, 3], y=[1, 2, 3], size=[10, 20, 25], color="#fa9fb5")
1054
1055        show(plot)
1056
1057"""
1058
1059    @marker_method()
1060    def y(self, **kwargs):
1061        """
1062Examples:
1063
1064    .. bokeh-plot::
1065        :source-position: above
1066
1067        from bokeh.plotting import figure, output_file, show
1068
1069        plot = figure(plot_width=300, plot_height=300)
1070        plot.y(x=[1, 2, 3], y=[1, 2, 3], size=20, color="#DE2D26")
1071
1072        show(plot)
1073
1074"""
1075
1076    # -------------------------------------------------------------------------
1077
1078    @glyph_method(glyphs.Scatter)
1079    def _scatter(self, **kwargs):
1080        pass
1081
1082    def scatter(self, *args, **kwargs):
1083        ''' Creates a scatter plot of the given x and y items.
1084
1085        Args:
1086            x (str or seq[float]) : values or field names of center x coordinates
1087
1088            y (str or seq[float]) : values or field names of center y coordinates
1089
1090            size (str or list[float]) : values or field names of sizes in screen units
1091
1092            marker (str, or list[str]): values or field names of marker types
1093
1094            color (color value, optional): shorthand to set both fill and line color
1095
1096            source (:class:`~bokeh.models.sources.ColumnDataSource`) : a user-supplied data source.
1097                An attempt will be made to convert the object to :class:`~bokeh.models.sources.ColumnDataSource`
1098                if needed. If none is supplied, one is created for the user automatically.
1099
1100            **kwargs: :ref:`userguide_styling_line_properties` and :ref:`userguide_styling_fill_properties`
1101
1102        Examples:
1103
1104            >>> p.scatter([1,2,3],[4,5,6], marker="square", fill_color="red")
1105            >>> p.scatter("data1", "data2", marker="mtype", source=data_source, ...)
1106
1107        .. note::
1108            When passing ``marker="circle"`` it is also possible to supply a
1109            ``radius`` value in data-space units. When configuring marker type
1110            from a data source column, *all* markers including circles may only
1111            be configured with ``size`` in screen units.
1112
1113        '''
1114        marker_type = kwargs.pop("marker", "circle")
1115
1116        if isinstance(marker_type, str) and marker_type in _MARKER_SHORTCUTS:
1117            marker_type = _MARKER_SHORTCUTS[marker_type]
1118
1119        # The original scatter implementation allowed circle scatters to set a
1120        # radius. We will leave this here for compatibility but note that it
1121        # only works when the marker type is "circle" (and not referencing a
1122        # data source column). Consider deprecating in the future.
1123        if marker_type == "circle" and "radius" in kwargs:
1124            return self.circle(*args, **kwargs)
1125        else:
1126            return self._scatter(*args, marker=marker_type, **kwargs)
1127
1128    def hexbin(self, x, y, size, orientation="pointytop", palette="Viridis256", line_color=None, fill_color=None, aspect_scale=1, **kwargs):
1129        ''' Perform a simple equal-weight hexagonal binning.
1130
1131        A :class:`~bokeh.models.glyphs.HexTile` glyph will be added to display
1132        the binning. The :class:`~bokeh.models.sources.ColumnDataSource` for
1133        the glyph will have columns ``q``, ``r``, and ``count``, where ``q``
1134        and ``r`` are `axial coordinates`_ for a tile, and ``count`` is the
1135        associated bin count.
1136
1137        It is often useful to set ``match_aspect=True`` on the associated plot,
1138        so that hexagonal tiles are all regular (i.e. not "stretched") in
1139        screen space.
1140
1141        For more sophisticated use-cases, e.g. weighted binning or individually
1142        scaling hex tiles, use :func:`hex_tile` directly, or consider a higher
1143        level library such as HoloViews.
1144
1145        Args:
1146            x (array[float]) :
1147                A NumPy array of x-coordinates to bin into hexagonal tiles.
1148
1149            y (array[float]) :
1150                A NumPy array of y-coordinates to bin into hexagonal tiles
1151
1152            size (float) :
1153                The size of the hexagonal tiling to use. The size is defined as
1154                distance from the center of a hexagon to a corner.
1155
1156                In case the aspect scaling is not 1-1, then specifically `size`
1157                is the distance from the center to the "top" corner with the
1158                `"pointytop"` orientation, and the distance from the center to
1159                a "side" corner with the "flattop" orientation.
1160
1161            orientation ("pointytop" or "flattop", optional) :
1162                Whether the hexagonal tiles should be oriented with a pointed
1163                corner on top, or a flat side on top. (default: "pointytop")
1164
1165            palette (str or seq[color], optional) :
1166                A palette (or palette name) to use to colormap the bins according
1167                to count. (default: 'Viridis256')
1168
1169                If ``fill_color`` is supplied, it overrides this value.
1170
1171            line_color (color, optional) :
1172                The outline color for hex tiles, or None (default: None)
1173
1174            fill_color (color, optional) :
1175                An optional fill color for hex tiles, or None. If None, then
1176                the ``palette`` will be used to color map the tiles by
1177                count. (default: None)
1178
1179            aspect_scale (float) :
1180                Match a plot's aspect ratio scaling.
1181
1182                When working with a plot with ``aspect_scale != 1``, this
1183                parameter can be set to match the plot, in order to draw
1184                regular hexagons (instead of "stretched" ones).
1185
1186                This is roughly equivalent to binning in "screen space", and
1187                it may be better to use axis-aligned rectangular bins when
1188                plot aspect scales are not one.
1189
1190        Any additional keyword arguments are passed to :func:`hex_tile`.
1191
1192        Returns
1193            (Glyphrender, DataFrame)
1194                A tuple with the ``HexTile`` renderer generated to display the
1195                binning, and a Pandas ``DataFrame`` with columns ``q``, ``r``,
1196                and ``count``, where ``q`` and ``r`` are `axial coordinates`_
1197                for a tile, and ``count`` is the associated bin count.
1198
1199        Example:
1200
1201            .. bokeh-plot::
1202                :source-position: above
1203
1204                import numpy as np
1205                from bokeh.models import HoverTool
1206                from bokeh.plotting import figure, show
1207
1208                x = 2 + 2*np.random.standard_normal(500)
1209                y = 2 + 2*np.random.standard_normal(500)
1210
1211                p = figure(match_aspect=True, tools="wheel_zoom,reset")
1212                p.background_fill_color = '#440154'
1213                p.grid.visible = False
1214
1215                p.hexbin(x, y, size=0.5, hover_color="pink", hover_alpha=0.8)
1216
1217                hover = HoverTool(tooltips=[("count", "@c"), ("(q,r)", "(@q, @r)")])
1218                p.add_tools(hover)
1219
1220                show(p)
1221
1222        .. _axial coordinates: https://www.redblobgames.com/grids/hexagons/#coordinates-axial
1223
1224        '''
1225        from ..util.hex import hexbin
1226
1227        bins = hexbin(x, y, size, orientation, aspect_scale=aspect_scale)
1228
1229        if fill_color is None:
1230            fill_color = linear_cmap('c', palette, 0, max(bins.counts))
1231
1232        source = ColumnDataSource(data=dict(q=bins.q, r=bins.r, c=bins.counts))
1233
1234        r = self.hex_tile(q="q", r="r", size=size, orientation=orientation, aspect_scale=aspect_scale,
1235                          source=source, line_color=line_color, fill_color=fill_color, **kwargs)
1236
1237        return (r, bins)
1238
1239    def harea_stack(self, stackers, **kw):
1240        ''' Generate multiple ``HArea`` renderers for levels stacked left
1241        to right.
1242
1243        Args:
1244            stackers (seq[str]) : a list of data source field names to stack
1245                successively for ``x1`` and ``x2`` harea coordinates.
1246
1247                Additionally, the ``name`` of the renderer will be set to
1248                the value of each successive stacker (this is useful with the
1249                special hover variable ``$name``)
1250
1251        Any additional keyword arguments are passed to each call to ``harea``.
1252        If a keyword value is a list or tuple, then each call will get one
1253        value from the sequence.
1254
1255        Returns:
1256            list[GlyphRenderer]
1257
1258        Examples:
1259
1260            Assuming a ``ColumnDataSource`` named ``source`` with columns
1261            *2016* and *2017*, then the following call to ``harea_stack`` will
1262            will create two ``HArea`` renderers that stack:
1263
1264            .. code-block:: python
1265
1266                p.harea_stack(['2016', '2017'], y='y', color=['blue', 'red'], source=source)
1267
1268            This is equivalent to the following two separate calls:
1269
1270            .. code-block:: python
1271
1272                p.harea(x1=stack(),       x2=stack('2016'),         y='y', color='blue', source=source, name='2016')
1273                p.harea(x1=stack('2016'), x2=stack('2016', '2017'), y='y', color='red',  source=source, name='2017')
1274
1275        '''
1276        result = []
1277        for kw in double_stack(stackers, "x1", "x2", **kw):
1278            result.append(self.harea(**kw))
1279        return result
1280
1281    def hbar_stack(self, stackers, **kw):
1282        ''' Generate multiple ``HBar`` renderers for levels stacked left to right.
1283
1284        Args:
1285            stackers (seq[str]) : a list of data source field names to stack
1286                successively for ``left`` and ``right`` bar coordinates.
1287
1288                Additionally, the ``name`` of the renderer will be set to
1289                the value of each successive stacker (this is useful with the
1290                special hover variable ``$name``)
1291
1292        Any additional keyword arguments are passed to each call to ``hbar``.
1293        If a keyword value is a list or tuple, then each call will get one
1294        value from the sequence.
1295
1296        Returns:
1297            list[GlyphRenderer]
1298
1299        Examples:
1300
1301            Assuming a ``ColumnDataSource`` named ``source`` with columns
1302            *2016* and *2017*, then the following call to ``hbar_stack`` will
1303            will create two ``HBar`` renderers that stack:
1304
1305            .. code-block:: python
1306
1307                p.hbar_stack(['2016', '2017'], y=10, width=0.9, color=['blue', 'red'], source=source)
1308
1309            This is equivalent to the following two separate calls:
1310
1311            .. code-block:: python
1312
1313                p.hbar(bottom=stack(),       top=stack('2016'),         y=10, width=0.9, color='blue', source=source, name='2016')
1314                p.hbar(bottom=stack('2016'), top=stack('2016', '2017'), y=10, width=0.9, color='red',  source=source, name='2017')
1315
1316        '''
1317        result = []
1318        for kw in double_stack(stackers, "left", "right", **kw):
1319            result.append(self.hbar(**kw))
1320        return result
1321
1322    def _line_stack(self, x, y, **kw):
1323        ''' Generate multiple ``Line`` renderers for lines stacked vertically
1324        or horizontally.
1325
1326        Args:
1327            x (seq[str]) :
1328
1329            y (seq[str]) :
1330
1331        Additionally, the ``name`` of the renderer will be set to
1332        the value of each successive stacker (this is useful with the
1333        special hover variable ``$name``)
1334
1335        Any additional keyword arguments are passed to each call to ``hbar``.
1336        If a keyword value is a list or tuple, then each call will get one
1337        value from the sequence.
1338
1339        Returns:
1340            list[GlyphRenderer]
1341
1342        Examples:
1343
1344            Assuming a ``ColumnDataSource`` named ``source`` with columns
1345            *2016* and *2017*, then the following call to ``line_stack`` with
1346            stackers for the y-coordinates will will create two ``Line``
1347            renderers that stack:
1348
1349            .. code-block:: python
1350
1351                p.line_stack(['2016', '2017'], x='x', color=['blue', 'red'], source=source)
1352
1353            This is equivalent to the following two separate calls:
1354
1355            .. code-block:: python
1356
1357                p.line(y=stack('2016'),         x='x', color='blue', source=source, name='2016')
1358                p.line(y=stack('2016', '2017'), x='x', color='red',  source=source, name='2017')
1359
1360        '''
1361        if all(isinstance(val, (list, tuple)) for val in (x,y)):
1362            raise ValueError("Only one of x or y may be a list of stackers")
1363
1364        result = []
1365
1366        if isinstance(y, (list, tuple)):
1367            kw['x'] = x
1368            for kw in single_stack(y, "y", **kw):
1369                result.append(self.line(**kw))
1370            return result
1371
1372        if isinstance(x, (list, tuple)):
1373            kw['y'] = y
1374            for kw in single_stack(x, "x", **kw):
1375                result.append(self.line(**kw))
1376            return result
1377
1378        return [self.line(x, y, **kw)]
1379
1380    def hline_stack(self, stackers, **kw):
1381        ''' Generate multiple ``Line`` renderers for lines stacked horizontally.
1382
1383        Args:
1384            stackers (seq[str]) : a list of data source field names to stack
1385                successively for ``x`` line coordinates.
1386
1387        Additionally, the ``name`` of the renderer will be set to
1388        the value of each successive stacker (this is useful with the
1389        special hover variable ``$name``)
1390
1391        Any additional keyword arguments are passed to each call to ``line``.
1392        If a keyword value is a list or tuple, then each call will get one
1393        value from the sequence.
1394
1395        Returns:
1396            list[GlyphRenderer]
1397
1398        Examples:
1399
1400            Assuming a ``ColumnDataSource`` named ``source`` with columns
1401            *2016* and *2017*, then the following call to ``hline_stack`` with
1402            stackers for the x-coordinates will will create two ``Line``
1403            renderers that stack:
1404
1405            .. code-block:: python
1406
1407                p.hline_stack(['2016', '2017'], y='y', color=['blue', 'red'], source=source)
1408
1409            This is equivalent to the following two separate calls:
1410
1411            .. code-block:: python
1412
1413                p.line(x=stack('2016'),         y='y', color='blue', source=source, name='2016')
1414                p.line(x=stack('2016', '2017'), y='y', color='red',  source=source, name='2017')
1415
1416        '''
1417        return self._line_stack(x=stackers, **kw)
1418
1419    def varea_stack(self, stackers, **kw):
1420        ''' Generate multiple ``VArea`` renderers for levels stacked bottom
1421        to top.
1422
1423        Args:
1424            stackers (seq[str]) : a list of data source field names to stack
1425                successively for ``y1`` and ``y1`` varea coordinates.
1426
1427                Additionally, the ``name`` of the renderer will be set to
1428                the value of each successive stacker (this is useful with the
1429                special hover variable ``$name``)
1430
1431        Any additional keyword arguments are passed to each call to ``varea``.
1432        If a keyword value is a list or tuple, then each call will get one
1433        value from the sequence.
1434
1435        Returns:
1436            list[GlyphRenderer]
1437
1438        Examples:
1439
1440            Assuming a ``ColumnDataSource`` named ``source`` with columns
1441            *2016* and *2017*, then the following call to ``varea_stack`` will
1442            will create two ``VArea`` renderers that stack:
1443
1444            .. code-block:: python
1445
1446                p.varea_stack(['2016', '2017'], x='x', color=['blue', 'red'], source=source)
1447
1448            This is equivalent to the following two separate calls:
1449
1450            .. code-block:: python
1451
1452                p.varea(y1=stack(),       y2=stack('2016'),         x='x', color='blue', source=source, name='2016')
1453                p.varea(y1=stack('2016'), y2=stack('2016', '2017'), x='x', color='red',  source=source, name='2017')
1454
1455        '''
1456        result = []
1457        for kw in double_stack(stackers, "y1", "y2", **kw):
1458            result.append(self.varea(**kw))
1459        return result
1460
1461    def vbar_stack(self, stackers, **kw):
1462        ''' Generate multiple ``VBar`` renderers for levels stacked bottom
1463        to top.
1464
1465        Args:
1466            stackers (seq[str]) : a list of data source field names to stack
1467                successively for ``left`` and ``right`` bar coordinates.
1468
1469                Additionally, the ``name`` of the renderer will be set to
1470                the value of each successive stacker (this is useful with the
1471                special hover variable ``$name``)
1472
1473        Any additional keyword arguments are passed to each call to ``vbar``.
1474        If a keyword value is a list or tuple, then each call will get one
1475        value from the sequence.
1476
1477        Returns:
1478            list[GlyphRenderer]
1479
1480        Examples:
1481
1482            Assuming a ``ColumnDataSource`` named ``source`` with columns
1483            *2016* and *2017*, then the following call to ``vbar_stack`` will
1484            will create two ``VBar`` renderers that stack:
1485
1486            .. code-block:: python
1487
1488                p.vbar_stack(['2016', '2017'], x=10, width=0.9, color=['blue', 'red'], source=source)
1489
1490            This is equivalent to the following two separate calls:
1491
1492            .. code-block:: python
1493
1494                p.vbar(bottom=stack(),       top=stack('2016'),         x=10, width=0.9, color='blue', source=source, name='2016')
1495                p.vbar(bottom=stack('2016'), top=stack('2016', '2017'), x=10, width=0.9, color='red',  source=source, name='2017')
1496
1497        '''
1498        result = []
1499        for kw in double_stack(stackers, "bottom", "top", **kw):
1500            result.append(self.vbar(**kw))
1501        return result
1502
1503    def vline_stack(self, stackers, **kw):
1504        ''' Generate multiple ``Line`` renderers for lines stacked vertically.
1505
1506        Args:
1507            stackers (seq[str]) : a list of data source field names to stack
1508                successively for ``y`` line coordinates.
1509
1510        Additionally, the ``name`` of the renderer will be set to
1511        the value of each successive stacker (this is useful with the
1512        special hover variable ``$name``)
1513
1514        Any additional keyword arguments are passed to each call to ``line``.
1515        If a keyword value is a list or tuple, then each call will get one
1516        value from the sequence.
1517
1518        Returns:
1519            list[GlyphRenderer]
1520
1521        Examples:
1522
1523            Assuming a ``ColumnDataSource`` named ``source`` with columns
1524            *2016* and *2017*, then the following call to ``vline_stack`` with
1525            stackers for the y-coordinates will will create two ``Line``
1526            renderers that stack:
1527
1528            .. code-block:: python
1529
1530                p.vline_stack(['2016', '2017'], x='x', color=['blue', 'red'], source=source)
1531
1532            This is equivalent to the following two separate calls:
1533
1534            .. code-block:: python
1535
1536                p.line(y=stack('2016'),         x='x', color='blue', source=source, name='2016')
1537                p.line(y=stack('2016', '2017'), x='x', color='red',  source=source, name='2017')
1538
1539        '''
1540        return self._line_stack(y=stackers, **kw)
1541
1542    def graph(self, node_source, edge_source, layout_provider, **kwargs):
1543        ''' Creates a network graph using the given node, edge and layout provider.
1544
1545        Args:
1546            node_source (:class:`~bokeh.models.sources.ColumnDataSource`) : a user-supplied data source
1547                for the graph nodes. An attempt will be made to convert the object to
1548                :class:`~bokeh.models.sources.ColumnDataSource` if needed. If none is supplied, one is created
1549                for the user automatically.
1550
1551            edge_source (:class:`~bokeh.models.sources.ColumnDataSource`) : a user-supplied data source
1552                for the graph edges. An attempt will be made to convert the object to
1553                :class:`~bokeh.models.sources.ColumnDataSource` if needed. If none is supplied, one is created
1554                for the user automatically.
1555
1556            layout_provider (:class:`~bokeh.models.graphs.LayoutProvider`) : a ``LayoutProvider`` instance to
1557                provide the graph coordinates in Cartesian space.
1558
1559            **kwargs: :ref:`userguide_styling_line_properties` and :ref:`userguide_styling_fill_properties`
1560
1561        '''
1562        kw = get_graph_kwargs(node_source, edge_source, **kwargs)
1563        graph_renderer = GraphRenderer(layout_provider=layout_provider, **kw)
1564        self.renderers.append(graph_renderer)
1565        return graph_renderer
1566
1567def figure(**kwargs):
1568    return Figure(**kwargs)
1569figure.__doc__ = Figure.__doc__
1570
1571_MARKER_SHORTCUTS = {
1572    "*"  : "asterisk",
1573    "+"  : "cross",
1574    "o"  : "circle",
1575    "o+" : "circle_cross",
1576    "o." : "circle_dot",
1577    "ox" : "circle_x",
1578    "oy" : "circle_y",
1579    "-"  : "dash",
1580    "."  : "dot",
1581    "v"  : "inverted_triangle",
1582    "^"  : "triangle",
1583    "^." : "triangle_dot",
1584}
1585
1586def markers():
1587    ''' Prints a list of valid marker types for scatter()
1588
1589    Returns:
1590        None
1591    '''
1592    print("Available markers: \n\n - " + "\n - ".join(list(MarkerType)))
1593    print()
1594    print("Shortcuts: \n\n" + "\n".join(" %r: %s" % item for item in _MARKER_SHORTCUTS.items()))
1595
1596#-----------------------------------------------------------------------------
1597# Dev API
1598#-----------------------------------------------------------------------------
1599
1600# This class itself is intentionally undocumented (it is used to generate
1601# documentation elsewhere)
1602class FigureOptions(Options):
1603
1604    tools = Either(String, Seq(Either(String, Instance(Tool))), default=DEFAULT_TOOLS, help="""
1605    Tools the plot should start with.
1606    """)
1607
1608    x_range = Any(help="""
1609    Customize the x-range of the plot.
1610    """)
1611
1612    y_range = Any(help="""
1613    Customize the y-range of the plot.
1614    """)
1615
1616    x_minor_ticks = Either(Auto, Int, default="auto", help="""
1617    Number of minor ticks between adjacent x-axis major ticks.
1618    """)
1619
1620    y_minor_ticks = Either(Auto, Int, default="auto", help="""
1621    Number of minor ticks between adjacent y-axis major ticks.
1622    """)
1623
1624    x_axis_location = Nullable(Enum(VerticalLocation), default="below", help="""
1625    Where the x-axis should be located.
1626    """)
1627
1628    y_axis_location = Nullable(Enum(HorizontalLocation), default="left", help="""
1629    Where the y-axis should be located.
1630    """)
1631
1632    x_axis_label = Nullable(String, default="", help="""
1633    A label for the x-axis.
1634    """)
1635
1636    y_axis_label = Nullable(String, default="", help="""
1637    A label for the y-axis.
1638    """)
1639
1640    active_drag = Either(Auto, String, Instance(Drag), default="auto", help="""
1641    Which drag tool should initially be active.
1642    """)
1643
1644    active_inspect = Either(Auto, String, Instance(InspectTool), Seq(Instance(InspectTool)), default="auto", help="""
1645    Which drag tool should initially be active.
1646    """)
1647
1648    active_scroll = Either(Auto, String, Instance(Scroll), default="auto", help="""
1649    Which scroll tool should initially be active.
1650    """)
1651
1652    active_tap = Either(Auto, String, Instance(Tap), default="auto", help="""
1653    Which tap tool should initially be active.
1654    """)
1655
1656    x_axis_type = Either(Null, Auto, Enum("linear", "log", "datetime", "mercator"), default="auto", help="""
1657    The type of the x-axis.
1658    """)
1659
1660    y_axis_type = Either(Null, Auto, Enum("linear", "log", "datetime", "mercator"), default="auto", help="""
1661    The type of the y-axis.
1662    """)
1663
1664    tooltips = Either(Null, String, List(Tuple(String, String)), help="""
1665    An optional argument to configure tooltips for the Figure. This argument
1666    accepts the same values as the ``HoverTool.tooltips`` property. If a hover
1667    tool is specified in the ``tools`` argument, this value will override that
1668    hover tools ``tooltips`` value. If no hover tool is specified in the
1669    ``tools`` argument, then passing tooltips here will cause one to be created
1670    and added.
1671    """)
1672
1673#-----------------------------------------------------------------------------
1674# Private API
1675#-----------------------------------------------------------------------------
1676
1677_color_fields = {"color", "fill_color", "line_color"}
1678_alpha_fields = {"alpha", "fill_alpha", "line_alpha"}
1679
1680#-----------------------------------------------------------------------------
1681# Code
1682#-----------------------------------------------------------------------------
1683