11.charts.py 12 KB

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