11.charts.py 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388
  1. import subprocess
  2. import time
  3. import plotly.graph_objects as go
  4. from cutecharts.charts import Bar
  5. from cutecharts.charts import Line
  6. from cutecharts.charts import Pie
  7. from cutecharts.charts import Radar
  8. from percy import percySnapshot
  9. from selenium.webdriver import Chrome
  10. import pywebio
  11. import util
  12. from pywebio import start_server
  13. from pywebio.output import *
  14. def bkapp(doc):
  15. import yaml
  16. from bokeh.layouts import column
  17. from bokeh.models import ColumnDataSource, Slider
  18. from bokeh.plotting import figure
  19. from bokeh.sampledata.sea_surface_temperature import sea_surface_temperature
  20. from bokeh.themes import Theme
  21. df = sea_surface_temperature.copy()
  22. source = ColumnDataSource(data=df)
  23. plot = figure(x_axis_type='datetime', y_range=(0, 25),
  24. y_axis_label='Temperature (Celsius)',
  25. title="Sea Surface Temperature at 43.18, -70.43")
  26. plot.line('time', 'temperature', source=source)
  27. def callback(attr, old, new):
  28. if new == 0:
  29. data = df
  30. else:
  31. data = df.rolling('{0}D'.format(new)).mean()
  32. source.data = ColumnDataSource.from_df(data)
  33. slider = Slider(start=0, end=30, value=0, step=1, title="Smoothing by N Days")
  34. slider.on_change('value', callback)
  35. doc.add_root(column(slider, plot))
  36. doc.theme = Theme(json=yaml.load("""
  37. attrs:
  38. Figure:
  39. background_fill_color: "#DDDDDD"
  40. outline_line_color: white
  41. toolbar_location: above
  42. height: 500
  43. width: 800
  44. Grid:
  45. grid_line_dash: [6, 4]
  46. grid_line_color: white
  47. """, Loader=yaml.FullLoader))
  48. def basci_doc():
  49. from bokeh.io import show
  50. from bokeh.plotting import figure
  51. # prepare some data
  52. x = [0.1, 0.5, 1.0, 1.5, 2.0, 2.5, 3.0]
  53. y0 = [i ** 2 for i in x]
  54. y1 = [10 ** i for i in x]
  55. y2 = [10 ** (i ** 2) for i in x]
  56. # create a new plot
  57. p = figure(
  58. tools="pan,box_zoom,reset,save",
  59. y_axis_type="log", y_range=[0.001, 10 ** 11], title="log axis example",
  60. x_axis_label='sections', y_axis_label='particles'
  61. )
  62. # add some renderers
  63. p.line(x, x, legend_label="y=x")
  64. p.circle(x, x, legend_label="y=x", fill_color="white", size=8)
  65. p.line(x, y0, legend_label="y=x^2", line_width=3)
  66. p.line(x, y1, legend_label="y=10^x", line_color="red")
  67. p.circle(x, y1, legend_label="y=10^x", fill_color="red", line_color="red", size=6)
  68. p.line(x, y2, legend_label="y=10^x^2", line_color="orange", line_dash="4 4")
  69. # show the results
  70. show(p)
  71. def widgets():
  72. from bokeh.io import show
  73. from bokeh.models import Select, CheckboxButtonGroup, Button, CheckboxGroup, ColorPicker, Dropdown, \
  74. FileInput, MultiSelect, RadioButtonGroup, RadioGroup, Slider, RangeSlider, TextAreaInput, TextInput, Toggle, \
  75. Paragraph, PreText, Div
  76. put_text('Button')
  77. button = Button(label="Foo", button_type="success")
  78. show(button)
  79. put_text('CheckboxButtonGroup')
  80. checkbox_button_group = CheckboxButtonGroup(
  81. labels=["Option 1", "Option 2", "Option 3"], active=[0, 1])
  82. show(checkbox_button_group)
  83. put_text('CheckboxGroup')
  84. checkbox_group = CheckboxGroup(
  85. labels=["Option 1", "Option 2", "Option 3"], active=[0, 1])
  86. show(checkbox_group)
  87. put_text('ColorPicker')
  88. color_picker = ColorPicker(color="#ff4466", title="Choose color:", width=200)
  89. show(color_picker)
  90. put_text('Dropdown')
  91. menu = [("Item 1", "item_1"), ("Item 2", "item_2"), None, ("Item 3", "item_3")]
  92. dropdown = Dropdown(label="Dropdown button", button_type="warning", menu=menu)
  93. show(dropdown)
  94. put_text('FileInput')
  95. file_input = FileInput()
  96. show(file_input)
  97. put_text('MultiSelect')
  98. multi_select = MultiSelect(title="Option:", value=["foo", "quux"],
  99. options=[("foo", "Foo"), ("bar", "BAR"), ("baz", "bAz"), ("quux", "quux")])
  100. show(multi_select)
  101. put_text('RadioButtonGroup')
  102. radio_button_group = RadioButtonGroup(
  103. labels=["Option 1", "Option 2", "Option 3"], active=0)
  104. show(radio_button_group)
  105. put_text('RadioGroup')
  106. radio_group = RadioGroup(
  107. labels=["Option 1", "Option 2", "Option 3"], active=0)
  108. show(radio_group)
  109. put_text('Select')
  110. select = Select(title="Option:", value="foo", options=["foo", "bar", "baz", "quux"])
  111. show(select)
  112. put_text('Slider')
  113. slider = Slider(start=0, end=10, value=1, step=.1, title="Stuff")
  114. show(slider)
  115. put_text('RangeSlider')
  116. range_slider = RangeSlider(start=0, end=10, value=(1, 9), step=.1, title="Stuff")
  117. show(range_slider)
  118. put_text('TextAreaInput')
  119. text_input = TextAreaInput(value="default", rows=6, title="Label:")
  120. show(text_input)
  121. put_text('TextInput')
  122. text_input = TextInput(value="default", title="Label:")
  123. show(text_input)
  124. put_text('Toggle')
  125. toggle = Toggle(label="Foo", button_type="success")
  126. show(toggle)
  127. put_text('Div')
  128. div = Div(text="""Your <a href="https://en.wikipedia.org/wiki/HTML">HTML</a>-supported text is initialized with the <b>text</b> argument. The
  129. remaining div arguments are <b>width</b> and <b>height</b>. For this example, those values
  130. are <i>200</i> and <i>100</i> respectively.""",
  131. width=200, height=100)
  132. show(div)
  133. put_text('Paragraph')
  134. p = Paragraph(text="""Your text is initialized with the 'text' argument. The
  135. remaining Paragraph arguments are 'width' and 'height'. For this example, those values
  136. are 200 and 100 respectively.""",
  137. width=200, height=100)
  138. show(p)
  139. put_text('PreText')
  140. pre = PreText(text="""Your text is initialized with the 'text' argument.
  141. The remaining Paragraph arguments are 'width' and 'height'. For this example,
  142. those values are 500 and 100 respectively.""",
  143. width=500, height=100)
  144. show(pre)
  145. def pyecharts():
  146. from pyecharts.charts import Bar
  147. from pyecharts.faker import Faker
  148. from pyecharts import options as opts
  149. from pyecharts.charts import Polar
  150. from pyecharts.charts import HeatMap
  151. from pyecharts.charts import Tree
  152. from pyecharts.globals import CurrentConfig
  153. CurrentConfig.ONLINE_HOST = "https://cdn.jsdelivr.net/gh/pyecharts/pyecharts-assets@master/assets/"
  154. r1 = ['草莓', '芒果', '葡萄', '雪梨', '西瓜', '柠檬', '车厘子']
  155. r2 = [127, 33, 110, 29, 146, 121, 36]
  156. r3 = [25, 87, 114, 131, 130, 94, 146]
  157. c1 = (
  158. Bar({"width": "100%"})
  159. .add_xaxis(r1)
  160. .add_yaxis("商家A", r2)
  161. .add_yaxis("商家B", r3)
  162. .set_global_opts(title_opts=opts.TitleOpts(title="Bar-基本示例", subtitle="我是副标题"))
  163. )
  164. c2 = (
  165. Polar({"width": "100%"})
  166. .add_schema(
  167. radiusaxis_opts=opts.RadiusAxisOpts(data=Faker.week, type_="category"),
  168. angleaxis_opts=opts.AngleAxisOpts(is_clockwise=True, max_=10),
  169. )
  170. .add("A", [1, 2, 3, 4, 3, 5, 1], type_="bar")
  171. .set_global_opts(title_opts=opts.TitleOpts(title="Polar-RadiusAxis"))
  172. .set_series_opts(label_opts=opts.LabelOpts(is_show=True))
  173. )
  174. data = [
  175. {
  176. "children": [
  177. {"name": "B"},
  178. {
  179. "children": [{"children": [{"name": "I"}], "name": "E"}, {"name": "F"}],
  180. "name": "C",
  181. },
  182. {
  183. "children": [
  184. {"children": [{"name": "J"}, {"name": "K"}], "name": "G"},
  185. {"name": "H"},
  186. ],
  187. "name": "D",
  188. },
  189. ],
  190. "name": "A",
  191. }
  192. ]
  193. c3 = (
  194. Tree({"width": "100%"})
  195. .add("", data)
  196. .set_global_opts(title_opts=opts.TitleOpts(title="Tree-基本示例"))
  197. )
  198. value = [[i, j, int(i * j * 3.14 * 314 % 50)] for i in range(24) for j in range(7)]
  199. c4 = (
  200. HeatMap({"width": "100%"})
  201. .add_xaxis(Faker.clock)
  202. .add_yaxis(
  203. "series0",
  204. Faker.week,
  205. value,
  206. label_opts=opts.LabelOpts(is_show=True, position="inside"),
  207. )
  208. .set_global_opts(
  209. title_opts=opts.TitleOpts(title="HeatMap-Label 显示"),
  210. visualmap_opts=opts.VisualMapOpts(),
  211. )
  212. )
  213. put_grid([
  214. [put_html(c1.render_notebook()), put_html(c2.render_notebook())],
  215. [put_html(c3.render_notebook()), put_html(c4.render_notebook())]
  216. ], cell_width='1fr', cell_height='1fr')
  217. def cutecharts():
  218. def radar_base():
  219. chart = Radar("Radar-基本示例", width="100%")
  220. chart.set_options(labels=["草莓", "芒果", "葡萄", "雪梨", "西瓜", "柠檬", "车厘子"])
  221. chart.add_series("series-A", [25, 87, 114, 131, 130, 94, 146])
  222. chart.add_series("series-B", [25, 87, 114, 131, 130, 94, 146])
  223. return put_html(chart.render_notebook())
  224. def pie_base():
  225. chart = Pie("Pie-基本示例", width="100%")
  226. chart.set_options(labels=["小米", "三星", "华为", "苹果", "魅族", "VIVO", "OPPO"])
  227. chart.add_series([25, 87, 114, 131, 130, 94, 146])
  228. return put_html(chart.render_notebook())
  229. def line_base():
  230. chart = Line("Line-基本示例", width="100%")
  231. chart.set_options(labels=["衬衫", "毛衣", "领带", "裤子", "风衣", "高跟鞋", "袜子"], x_label="I'm xlabel", y_label="I'm ylabel")
  232. chart.add_series("series-A", [25, 87, 114, 131, 130, 94, 146])
  233. chart.add_series("series-B", [127, 33, 110, 29, 146, 121, 36])
  234. return put_html(chart.render_notebook())
  235. def bar_base():
  236. chart = Bar("Bar-基本示例", width="100%")
  237. chart.set_options(labels=["可乐", "雪碧", "橙汁", "绿茶", "奶茶", "百威", "青岛"], x_label="I'm xlabel", y_label="I'm ylabel")
  238. chart.add_series("series-A", [127, 33, 110, 29, 146, 121, 36])
  239. return put_html(chart.render_notebook())
  240. put_grid([[bar_base(), line_base()], [pie_base(), radar_base()]], cell_width='1fr', cell_height='1fr')
  241. def plotly():
  242. x = list(range(10))
  243. fig = go.Figure(data=go.Scatter(x=x, y=[i ** 2 for i in x]))
  244. html1 = fig.to_html(include_plotlyjs="require", full_html=False)
  245. fig = go.Figure(data=[go.Scatter(
  246. x=[1, 2, 3, 4], y=[10, 11, 12, 13],
  247. mode='markers',
  248. marker=dict(
  249. color=['rgb(93, 164, 214)', 'rgb(255, 144, 14)',
  250. 'rgb(44, 160, 101)', 'rgb(255, 65, 54)'],
  251. opacity=[1, 0.8, 0.6, 0.4],
  252. size=[40, 60, 80, 100],
  253. )
  254. )])
  255. html2 = fig.to_html(include_plotlyjs="require", full_html=False)
  256. fig = go.Figure(go.Sankey(
  257. arrangement="snap",
  258. node={
  259. "label": ["A", "B", "C", "D", "E", "F"],
  260. "x": [0.2, 0.1, 0.5, 0.7, 0.3, 0.5],
  261. "y": [0.7, 0.5, 0.2, 0.4, 0.2, 0.3],
  262. 'pad': 10}, # 10 Pixels
  263. link={
  264. "source": [0, 0, 1, 2, 5, 4, 3, 5],
  265. "target": [5, 3, 4, 3, 0, 2, 2, 3],
  266. "value": [1, 2, 1, 1, 1, 1, 1, 2]}))
  267. html3 = fig.to_html(include_plotlyjs="require", full_html=False)
  268. fig = go.Figure(go.Sunburst(
  269. labels=["Eve", "Cain", "Seth", "Enos", "Noam", "Abel", "Awan", "Enoch", "Azura"],
  270. parents=["", "Eve", "Eve", "Seth", "Seth", "Eve", "Eve", "Awan", "Eve"],
  271. values=[10, 14, 12, 10, 2, 6, 6, 4, 4],
  272. ))
  273. # Update layout for tight margin
  274. # See https://plotly.com/python/creating-and-updating-figures/
  275. fig.update_layout(margin=dict(t=0, l=0, r=0, b=0))
  276. html4 = fig.to_html(include_plotlyjs="require", full_html=False)
  277. put_grid([
  278. [put_html(html1), put_html(html2)],
  279. [put_html(html3), put_html(html4)]
  280. ], cell_width='1fr', cell_height='1fr')
  281. def target():
  282. from bokeh.io import output_notebook
  283. from bokeh.io import show
  284. output_notebook(verbose=True, notebook_type='pywebio')
  285. put_markdown('# Bokeh')
  286. put_markdown('## Basic doc')
  287. basci_doc()
  288. put_markdown('## App')
  289. show(bkapp)
  290. put_markdown('## App again')
  291. show(bkapp)
  292. put_markdown('## Widgets')
  293. widgets()
  294. put_markdown('# pyecharts')
  295. pyecharts()
  296. put_markdown('# cutecharts')
  297. cutecharts()
  298. put_markdown('# plotly')
  299. plotly()
  300. def test(server_proc: subprocess.Popen, browser: Chrome):
  301. time.sleep(8)
  302. percySnapshot(browser, name='bokeh')
  303. def start_test_server():
  304. pywebio.enable_debug()
  305. start_server(target, port=8080, auto_open_webbrowser=False, cdn=False)
  306. if __name__ == '__main__':
  307. util.run_test(start_test_server, test)