本教程將通過六個獨立的小應用帶你了解到Dash的一個基本方法:布局。
Dash包括兩個部分,一個是它的"layout",用來決定這個可視化面板看起來像什么;另一個部分是設置交互內容的,將在下一章講解。
注:這份文件中的代碼需要通過python文件運行(前提是你安裝了dash庫)。而如果你使用的是Jupyter,你必須安裝JupyterDash才能運行這些代碼,安裝方法見前面的文章。
你的第一個Dash
好,Dash學習正式開始!!復制下面的代碼並運行:
import dash
from dash import dcc
from dash import html
import plotly.express as px
import pandas as pd
#定義一個dash
app = dash.Dash(__name__)
#創建一個數據
df = pd.DataFrame({
"Fruit":['Apples','Oranges','Bananas','Apples','Oranges','Bananas']
"Amount":[4,1,2,2,4,5]
"City":['SF','SF','SF','Montreal','Montreal','Motreal']
})
#用plotly畫一個條形圖,x軸是蔬菜種類,y軸是數量,條形圖按城市分類
fig = px.bar(df , x='Fruit' , y='Amount' , color='City' , barmode = 'group')
#定義dash的格局,html.H1代表1級標題,也就是大標題;里面的html.Div代表一個分割塊。
app.layout = html.Div(children = [
html.H1(children='hello Dash'),
html.Div(children='''
Dash: A web application framework for your data.
'''),
#將你的圖片畫到html上,並命名
dcc.Graph(
id = 'example-graph',
figure=fig
)
])
#運行main函數
if __name__ = '__main__':
app.run_server(debug=True)
運行上面的代碼,你會在終端的到一個本地的web地址,點擊進入此web網頁你就可以看到你畫的第一個Dash圖啦!(運行的時間可能會比較長)
下圖藍色部分就是web地址:
點擊web地址,你會得到如下的網頁:
注:
layout
是由html.Div
或者dcc.Graph
等元素組成的樹構成的。- 對每一個html標簽,
dash_html_components
函數有一個對其都有一個對應的元素。(這句話我也不懂,可能也是在下的英語太差的鍋吧)- 並不是所有的組件都是純HTML的。其中
dash_core_components
擁有更為高級的交互函數,這些是由JavaScript等語言寫出來的。- 每個組件都完全通過關鍵字屬性來描述。Dash是聲明性的:您將主要通過這些屬性描述您的應用程序。說人話就是你能通過構成這個網頁的代碼輕松地知道它在干什么。
- children變量很特別。按照慣例,它總是第一個屬性,這意味着可以忽略它:
html.H1(children='Hello Dash')
與html.H1(“Hello,Dash”)
是一樣的。它可以包含字符串、數字、單個組件或組件列表。- 應用程序中的字體看起來與此處顯示的略有不同。此應用程序使用自定義CSS樣式表和Dash Enterprise Design Kit來修改元素的默認樣式。您可以在CSS教程中了解有關自定義CSS的更多信息。
來做一點點改變吧
Dash具有熱重裝性的(hot-reloading),這個特征當你運行app.run_server(debug=True)
后會默認開啟。當你對你的代碼進行改變的時候,Dash會自動更新。
試試將你代碼里的標題改成hello world
,或者改變x或者y的值,你會發現Dash面板的圖像也會發生相應的改變。
如果你不喜歡熱重裝,你也可以選擇關掉它(關掉后代碼能運行的更快)。關掉的代碼是:
app.run_server(dev_tools_hot_reload=False)
HTML組件的更多信息
dash_html_components
包含每個html標記的組件類,以及所有html參數的關鍵字參數。
讓我們通過修改組件的內聯樣式來定制應用程序中的文本,創建一個名為app的文件。使用以下代碼:
import dash
from dash import dcc
from dash import html
import plotly.express as px
import pandas as pd
app = dash.Dash(__name__)
#定義背景顏色和文字顏色
colors = {
'background': '#111111',
'text': '#7FDBFF'
}
#定義數據
df = pd.DataFrame({
"Fruit": ["Apples", "Oranges", "Bananas", "Apples", "Oranges", "Bananas"],
"Amount": [4, 1, 2, 2, 4, 5],
"City": ["SF", "SF", "SF", "Montreal", "Montreal", "Montreal"]
})
#畫條形圖
fig = px.bar(df, x="Fruit", y="Amount", color="City", barmode="group")
#更新圖片的布局,這里是用的與plotly相關的函數
fig.update_layout(
plot_bgcolor=colors['background'],
paper_bgcolor=colors['background'],
font_color=colors['text']
)
#定義dash的布局
app.layout = html.Div(style={'backgroundColor': colors['background']}, children=[
html.H1(
children='Hello Dash',
style={
'textAlign': 'center', #文字的所處位置:居中
'color': colors['text'] #文字的顏色
}
),
html.Div(children='Dash: A web application framework for your data.', style={
'textAlign': 'center',
'color': colors['text']
}),
dcc.Graph(
id='example-graph-2',
figure=fig
)
])
if __name__ == '__main__':
app.run_server(debug=True)
你運行出來是這個樣子嗎↓
這里,dash_html_components
和HTML屬性之間有一些差別:
- HTML中的
style
屬性是一個分號分隔的字符串。在Dash中,你可以提供一本字典。style
字典中的鍵是camelCase型的。所以,不是text-align
,而是textAlign
。- HTML中的
class
屬性在Dash中變為了className
.- children變量很特別。按照慣例,它總是第一個屬性,這意味着可以忽略它:
html.H1(children='Hello Dash')
與html.H1(“Hello,Dash”)
是一樣的。它可以包含字符串、數字、單個組件或組件列表。
除此之外,所有可用的HTML屬性和標記都可以在Python上下文中使用。
可重用組件
通過用Python編寫標記,我們可以創建復雜的可重用組件,比如表,而無需切換上下文或語言。
下面是一個從數據幀生成表的快速示例。使用以下代碼:
import dash
from dash import dcc
from dash import html
import plotly.express as px
import pandas as pd
# 我們讀取Github上的一個公開數據集,來作為接下來實驗的原材料
df = pd.read_csv('https://gist.githubusercontent.com/chriddyp/c78bf172206ce24f77d6363a2d754b59/raw/c353e8ef842413cae56ae3920b8fd78468aa4cb2/usa-agricultural-exports-2011.csv')
# 定義一個函數來自動生成表格
# html.Table生成表頭,html.Tbody一行一行的添加表內的具體內容
def generate_table(dataframe, max_rows=10):
return html.Table([
html.Thead(
html.Tr([html.Th(col) for col in dataframe.columns])
),
html.Tbody([
html.Tr([
html.Td(dataframe.iloc[i][col]) for col in dataframe.columns
]) for i in range(min(len(dataframe), max_rows))
])
])
app = dash.Dash(__name__)
app.layout = html.Div([
html.H4(children='US Agriculture Exports (2011)'),
generate_table(df)
])
if __name__ == '__main__':
app.run_server(debug=True)
我的表格顯示出來是這個樣子:
雖然有點丑,但是成功了: )
更多可視化
dash_core_components
庫中有一個組件叫做Graph
。Graph
使用JavaScript中的plotly.js開源庫呈現交互式數據可視化。plotly.js支持超過35種圖表類型,並以矢量SVG和高性能WebGL呈現圖表。
Graph組件中的figure參數與plotly.py中使用的figure參數相同。Plotly的開源Python繪圖庫。你如果想了解更多,可以去plotly的官方文檔看看。
下面是一個從pandas數據幀創建散點圖的示例。使用以下代碼:
import dash
from dash import dcc
from dash import html
import plotly.express as px
import pandas as pd
app = dash.Dash(__name__)
df = pd.read_csv('https://gist.githubusercontent.com/chriddyp/5d1ea79569ed194d432e56108a04d188/raw/a9f9e8076b837d541398e999dcbac2b2826a81f8/gdp-life-exp-2007.csv')
fig = px.scatter(df, x="gdp per capita", y="life expectancy",
size="population", color="continent", hover_name="country",
log_x=True, size_max=60)
app.layout = html.Div([
dcc.Graph(
id='life-exp-vs-gdp',
figure=fig
)
])
if __name__ == '__main__':
app.run_server(debug=True)
我畫出來是這樣:
這幅圖是可交互的,當你將鼠標懸停在這些點上是,會看到這個點所表示的信息。單擊圖例項以切換軌跡,單擊並拖動以縮放,按住shift鍵,然后單擊並拖動以平移。
markdown
你還可以用Dash來寫markdown!在markdown里再套一層markdown了屬於是。運行下面的代碼:
import dash
from dash import dcc
from dash import html
import plotly.express as px
import pandas as pd
app = dash.Dash(__name__)
markdown_text = '''
### Dash and Markdown
Dash apps can be written in Markdown.
Dash uses the [CommonMark](http://commonmark.org/)
specification of Markdown.
Check out their [60 Second Markdown Tutorial](http://commonmark.org/help/)
if this is your first introduction to Markdown!
'''
app.layout = html.Div([
dcc.Markdown(children=markdown_text)
])
if __name__ == '__main__':
app.run_server(debug=True)
核心組件
dash_core_components包括一組更高級別的組件,如下拉列表、圖表、markdown塊等。
與所有Dash組件一樣,它們完全是以聲明方式描述的。每個可配置的選項都可以作為組件的關鍵字參數使用。
我們將在整個教程中看到其中的許多組件。您可以在Dash Core Components Gallery中查看所有可用組件。
以下是一些可用的組件。使用以下代碼:
import dash
from dash import dcc
from dash import html
import plotly.express as px
import pandas as pd
app = dash.Dash(__name__)
app.layout = html.Div([
html.Div(children=[
html.Label('Dropdown'),
dcc.Dropdown(
options=[
{'label': 'New York City', 'value': 'NYC'},
{'label': u'Montréal', 'value': 'MTL'},
{'label': 'San Francisco', 'value': 'SF'}
],
value='MTL'
),
html.Br(),
html.Label('Multi-Select Dropdown'),
dcc.Dropdown(
options=[
{'label': 'New York City', 'value': 'NYC'},
{'label': u'Montréal', 'value': 'MTL'},
{'label': 'San Francisco', 'value': 'SF'}
],
value=['MTL', 'SF'],
multi=True
),
html.Br(),
html.Label('Radio Items'),
dcc.RadioItems(
options=[
{'label': 'New York City', 'value': 'NYC'},
{'label': u'Montréal', 'value': 'MTL'},
{'label': 'San Francisco', 'value': 'SF'}
],
value='MTL'
),
], style={'padding': 10, 'flex': 1}),
html.Div(children=[
html.Label('Checkboxes'),
dcc.Checklist(
options=[
{'label': 'New York City', 'value': 'NYC'},
{'label': u'Montréal', 'value': 'MTL'},
{'label': 'San Francisco', 'value': 'SF'}
],
value=['MTL', 'SF']
),
html.Br(),
html.Label('Text Input'),
dcc.Input(value='MTL', type='text'),
html.Br(),
html.Label('Slider'),
dcc.Slider(
min=0,
max=9,
marks={i: 'Label {}'.format(i) if i == 1 else str(i) for i in range(1, 6)},
value=5,
),
], style={'padding': 10, 'flex': 1})
], style={'display': 'flex', 'flex-direction': 'row'})
if __name__ == '__main__':
app.run_server(debug=True)
你會得到以下一大坨:
其中,所有的組件都是傳給children這個變量的,以列表的形式存在。
組件名稱 | 功能 |
---|---|
html.Label() | 用來設置組件的名稱 |
dcc.Dropdown(option= ,value= ,multi=False) | 下拉條,option設置下拉條中的選項,value是設置默認值 |
html.Br() | 用來分割各個組件 |
dcc.RadioItems(options= ,value= ) | 用來設置圓形選項 |
dcc.Checklist(options= ,value= ) | 用來形成方形選項 |
dcc.Input(value= ,type= ) | 用來組成輸入框 |
dcc.Slider(min= ,max= ,marks={},value= ) | 用來組成滑動條 |
html.Div(children= ,style={}) | 用來形成html,children傳入組件信息(列表形式),style用來設置各個組件的排列樣式等 |
幫助
Dash的組件是聲明性的:這些組件的每個可配置方面都在實例化期間設置為關鍵字參數。
在Python控制台中調用任何組件的幫助,以了解有關組件及其可用參數的更多信息。
>>> help(dcc.Dropdown)
class Dropdown(dash.development.base_component.Component)
| A Dropdown component.
| Dropdown is an interactive dropdown element for selecting one or more
| items.
| The values and labels of the dropdown items are specified in the `options`
| property and the selected item(s) are specified with the `value` property.
|
| Use a dropdown when you have many options (more than 5) or when you are
| constrained for space. Otherwise, you can use RadioItems or a Checklist,
| which have the benefit of showing the users all of the items at once.
|
| Keyword arguments:
| - id (string; optional)
| - className (string; optional)
| - disabled (boolean; optional): If true, the option is disabled
| - multi (boolean; optional): If true, the user can select multiple values
| - options (list; optional)
| - placeholder (string; optional): The grey, default text shown when no option is selected
| - value (string | list; optional): The value of the input. If `multi` is false (the default)
| then value is just a string that corresponds to the values
| provided in the `options` property. If `multi` is true, then
| multiple values can be selected at once, and `value` is an
| array of items with values corresponding to those in the
| `options` prop.
當然,你也可以去看它的官方文檔。值得注意的是,因為很多圖形都是基於plotly的,所以你如果想畫出各種吊炸天的圖,我建議你也去瞅瞅plotly的官方文檔。
總結
Dash的layout決定了Dash看起來像什么。dash_html_components(dash v2.0中的dash.html)庫為所有html標記提供類,關鍵字參數描述html屬性,如樣式、類和id。dash_core_components庫生成更高級別的組件,如控件和圖形。反正你在工作時需要啥,回來看看代碼就知道了,沒有必要搞得那么清楚,只是個工具而已啦。
這里放兩個鏈接:
Dash Core Components Gallery
Dash HTML Components Gallery
Dash教程的下一部分將介紹如何使這些應用程序具有交互性。
如果你喜歡這篇文章,那你肯定喜歡這篇文章。有任何問題可以發在評論區,或者發到我的郵箱:jiang.gucheng@foxmail.com