#!/usr/bin/env python
# coding: utf-8
# ## Chapter1
# D3.js in Actionの1章の勉強ノートです。
#
# これまで、d3.v3.min.jsを以下のようにロードしていましたが、nvd3のinitialize_javascriptでこれが不要になりました。
#
# ただし、kernelはPython2を使用するため、sageは%load_extでロードします。
#
# ``` html
#
# ```
#
#
#
# In[1]:
get_ipython().run_line_magic('load_ext', 'sage')
from IPython.core.display import HTML
from string import Template
import json
import nvd3
nvd3.ipynb.initialize_javascript(use_remote=True)
# ## 要素の選択とデータバインド
# 要素の選択には、select, selectAll関数が用意されいます。要素の選択パターンはjQueryと同じです。
# - #<要素のID>: 要素のIDで選択
# - <タグ>: HTMLタグ名で選択
# - .<クラス>: 要素のclass名で選択
#
#
# ### リスト1.1をjupyterでためす
#
# In[2]:
get_ipython().run_cell_magic('html', '', '
\n\n
\n')
# javascriptのmagic関数をこんな形で使うことは考えたことがなかったので、とても重宝します。
#
# 通常はhtmlのscriptタグかブラウザのconsoleでしかjavascriptを操作できないのですが、
# jupyterノートブックでは、このように結果を確認しながら処理を進めることができます。
#
# 以下の例では、以下の処理をします。
# - divタグのid=someDivのstyleをborder="5px darkgray dashed"に変更
# - divタグのid=someDivのidをnewIDに変更
# - inputタグのid=someCheckboxの変数checkedをtrueにセット
#
# In[3]:
get_ipython().run_cell_magic('javascript', '', 'd3.select("#someDiv").style("border", "5px darkgray dashed");\nd3.select("#someDiv").attr("id", "newID");\nd3.select("#someCheckbox").property("checked", true);\n')
# Chromeの「表示」>「開発/管理」から「デベロッパーツール」を開くと上記の処理でどのようにHTMLが変化したか確認することができます。
#
# ![Developer-Tool](images/developer-tool.png)
#
# ### データバインディング
# 次に「データバインディング」を使ってみます。
#
# データバインディングは、選択された要素に配列で与えられた個々のデータを割り当てる機能です。
#
# 以下の例では、4個のdivにsomeDataの4つの文字列をバインドします。
# - html関数のfunction (d)で個々のデータが渡されます
#
# 次の行を実行すると、「データバインディングの例です」と表示し、%%javascriptを実行すると
#
# Test1
# Test2
# Test3
# Test4
#
# が追加されます。
# In[4]:
get_ipython().run_cell_magic('HTML', '', '\nデータバインディングの例です。\n
\n
\n
\n
\n
\n')
# In[5]:
get_ipython().run_cell_magic('javascript', '', 'var someData = ["Test1", "Test2", "Test3", "Test4"];\n\nd3.select("#ex2").selectAll("div")\n .data(someData)\n .append("div")\n .html(function (d) { return d;});\n')
# ### D3.js のHello Worldを試す
# D3アプリのHello Worldとして、円を動かす例が紹介されているので、これをjupyterで試してみます。
#
# 最初にHTMLを定義します。
#
# In[6]:
get_ipython().run_cell_magic('HTML', '', '\n \n
\n')
# SVGキャンパスに様々な図形を追加します。
# In[7]:
get_ipython().run_cell_magic('javascript', '', 'd3.select("#ex3").select("svg")\n .append("line")\n .attr("x1", 20).attr("y1", 20)\n .attr("x2",250).attr("y2",250)\n .style("stroke", "black").style("stroke-width","2px");\nd3.select("svg")\n .append("text")\n .attr("x",20).attr("y",20)\n .text("HELLO");\nd3.select("svg")\n .append("circle")\n .attr("r", 20).attr("cx",20).attr("cy",20)\n .style("fill","red");\nd3.select("svg")\n .append("circle")\n .attr("r", 50).attr("cx",250).attr("cy",250)\n .style("fill","lightblue");\nd3.select("svg")\n .append("text")\n .attr("x",250).attr("y",250)\n .text("WORLD");\n')
# SVGでは表示順序で上書きするので、HELLOの文字が赤い丸に潰されています。
#
# 次の例は、アニメーションです。
# これもtransitionとdurationを使ってとても簡単に実現しています。
#
# In[8]:
get_ipython().run_cell_magic('HTML', '', '\n \n
\n')
# In[9]:
get_ipython().run_cell_magic('javascript', '', 'd3.select("#ex4").select("svg")\n .append("circle")\n .attr("r", 20).attr("cx",20).attr("cy",20).style("fill","red");\nd3.select("#ex4").select("svg")\n .append("text")\n .attr("id", "a").attr("x",20).style("opacity", 0).attr("y",20)\n .text("HELLO WORLD");\nd3.select("#ex4").select("svg")\n .append("circle")\n .attr("r", 50).attr("cx",250).attr("cy",250).style("fill","lightblue");\nd3.select("#ex4").select("svg")\n .append("text")\n .attr("id", "b").attr("x",250).attr("y",250).style("opacity", 0).text("Uh, hi.");\n\nd3.select("#a").transition().delay(1000).style("opacity", 1);\nd3.select("#b").transition().delay(3000).style("opacity", .75);\n\nd3.select("#ex4").selectAll("circle").transition().duration(4000).attr("cy", 150);\n')
# In[ ]: