Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Sign up for free
Menu
Search
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Pricing
Search
Sign in
Sign up for free
既存プロダクトのViewをReactに置き換える
Search
boiyama
December 15, 2016
Programming
2.3k
1
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
既存プロダクトのViewをReactに置き換える
【ヒカ☆ラボ】最新フロントエンドフレームワークを利用した開発事例!
https://atnd.org/events/83403
用の資料です
boiyama
December 15, 2016
More Decks by boiyama
See All by boiyama
Reproのビジネスサイドを支えるJS
boiyama
0
190
バックオフィスに行ったソフトウェアエンジニアの業務効率化事例
boiyama
1
290
2018年、IE6対応サイトを作る
boiyama
4
1k
ヤバいESLint/TSLintルール作っちゃったかもしれない
boiyama
0
1.5k
チームをCQRS
boiyama
1
1.7k
フロントエンドのサーバーレス SSR編
boiyama
0
730
Serverless for Front-end Server-Side Rendering
boiyama
1
150
Learning Elm in JS
boiyama
1
580
JSでElmを学ぶ
boiyama
0
120
Other Decks in Programming
See All in Programming
[ハンズオン]AIへの指示だけで「五目並べ」を作ってみよう
satoshi256kbyte
1
310
技術的負債の返済は、AI時代の複利で効く投資 — 経営としての意思決定とその遂行
curekoshimizu
1
2k
モデルのリファクタリングが難しいと思ったら、そもそも複雑だったのはビジネス仕様だった ? / is-the-business-domain-the-real-complexity
hatsu38
0
430
Workers Cache を知る
syumai
0
310
パズルゲームの作り方 / how to make puzzle games
kaityo256
PRO
2
250
TiDB Cloudのカスタムコントローラーによるオートスケール対応
takaidohigasi
0
140
AgentCore CLI で進化した AWS での AI エージェントの作り方 : 必要な機能を必要な時に
icoxfog417
PRO
4
400
wkhtmltopdfの次どうするか問題2026
willnet
2
1.8k
ハーネス設計入門 〜 基礎知識の整理から実務へのステップアップ 〜
kinopeee
19
19k
AI が書く Go コードの品質を劇的に向上させる Linter: “declscope”
mpyw
0
450
JPUG勉強会 OSSデータベースの内部構造を理解しよう(第2回)
oga5
0
280
巨大モノリシックアプリ モダン化大作戦
ktcryomm
1
1.2k
Featured
See All Featured
Information Architects: The Missing Link in Design Systems
soysaucechin
1
1.2k
Tips & Tricks on How to Get Your First Job In Tech
honzajavorek
1
780
Save Time (by Creating Custom Rails Generators)
garrettdimon
PRO
33
5k
Ruling the World: When Life Gets Gamed
codingconduct
0
380
Helping Users Find Their Own Way: Creating Modern Search Experiences
danielanewman
31
3.4k
AI Search: Where Are We & What Can We Do About It?
aleyda
0
8k
SEO for Brand Visibility & Recognition
aleyda
0
4.8k
GitHub's CSS Performance
jonrohan
1033
470k
[Rails World 2026] Durable orchestration on Rails: from continuation to workflow
palkan
1
400
Self-Hosted WebAssembly Runtime for Runtime-Neutral Checkpoint/Restore in Edge–Cloud Continuum
chikuwait
0
850
Game over? The fight for quality and originality in the time of robots
wayneb77
1
290
StorybookのUI Testing Handbookを読んだ
zakiyama
31
6.9k
Transcript
طଘϓϩμΫτͷViewΛ Reactʹஔ͖͑Δ Dec 15 2016 @boiyaa
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ϓϩϑΟʔϧ ▸ @boiyaa ▸ 33ࡀ ▸ ϑϧεέοϕΤϯδχΞ
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ͢͜ͱɾ͞ͳ͍͜ͱ ▸ ͢͜ͱ ▸ طଘϓϩμΫτʹReactΛಋೖ͢Δ͜ͱʹͨ͠എܠ ▸ ࣮αϯϓϧ ▸ https://github.com/boiyaa/todomvc-backbone-react
▸ ͞ͳ͍͜ͱ ▸ πʔϧͱ͔ES6ͱ͔ͷৄ͍͠༰
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ࣮ݱࡏ ▸ View͚ͩஔ͖͑ΔͷΊ͍ͯ·͢ʢٕज़తෛ࠴తͳཧ ༝Ͱʣ ▸ ͜ͷεϥΠυͰɺViewΛReactʹஔ͖͑Α͏ͱࢼߦࡨޡ ͍ͯͨ࣌͠ͷ͓Λ͠·͢
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ৽ٕज़Λݕ౼ͨ͠എܠ ▸ 4લʹ࡞ΒΕͨۀγεςϜ ▸ ϑϩϯτΤϯυFWʹBackbone.jsΛ࠾༻ ▸ ػೳͷܧ͗͠Λ܁Γฦ͍ͯͬͨ݁͠ՌɺDOMૢ࡞ͷॲཧ͕ᷓΕ͔͑ͬͨ Backbone ViewʹͳΔ
▸ ͏গ͠εϚʔτʹUIΛ࡞ΕΔํ๏ʹม͑ΔͨΊɺjQueryʹґଘ͠ͳ͍React ͱAngular2͕ީิʹ্͕Δ ▸ Ͱ͖Εطଘࢿ࢈׆༻͍ͨ͠ͱ͍͏͜ͱͰɺUI·ΘΓͷΈΛReactʹஔ͖ ͑ΔํࣜͱɺAngular2Ͱ1͔Β࡞Γ͢ํࣜͷ̎௨Γݕ౼͢Δ͜ͱʹͳͬͨ
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ࣌ͷݕূ༰ ▸ ̍൪ӈͷ߲͍͍ͬͨͳΜͩͱ͍͏ײ͡Ͱ͕͢ɺݱߦʹͦ͏͍͏ը໘͕͋Γɺ ສݸͷDOMͷඳըૢ࡞ʹ͕͔͔࣌ؒΔΑ͏ͩͱଞ߲͕ັྗతͰ࠾༻Ͱ ͖ͳ͍ͱ͍͏͜ͱͰ༻ҙ͞Ε߲ͨͰ͢ɻʢWhy?ʣ ▸ ݁ՌɺAngular2མબ͠ɺBackboneͷΈͷը໘ͱBackbone + Reactͷը໘Λ
͍͚͍ͯ͘ͱ͍͏͜ͱʹͳΓ·ͨ͠ ֶशίετ ੜ࢈ੑ อकੑ طଘࢿ࢈׆༻ ̍ສߦදૢ࡞ ύϑΥʔϚϯε Backbone ˕ ̋ ˚ ˕ ̋ Backbone + React ̋ ˕ ̋ ̋ ˚ Angular2 ˚ ˕ ̋ × ˚
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Reactʹ͍ͭͯ ▸ MV*Ͱ͍͏ViewͷΈఏڙ͢ΔϑϨʔϜϫʔΫ ▸ React͚ͩͳΒ֮͑Δ͜ͱগͳ͍Ͱ͢ ▸ React ComponentΫϥεΛܧঝ͠ɺHTML, CSS,
JSͷͻͱ͔ͨ·ΓΛఆٛͨ͠ίϯ ϙʔωϯτΛ࡞Δͷ͕جຊతͳ͍ํͰ͢ɻ ▸ ίϯϙʔωϯτɺJSXͱ͍͏จ๏ΛͬͯHTMLͷΑ͏ʹݺͼग़͠·͢ʢྫɿ <Example hoge=“fuga” />ʣ ▸ ίϯϙʔωϯτʹͨ͠propsɺίϯϙʔωϯτ͕࣋ͭstateʹೖΓɺͦΕ Βͷ͕ߋ৽͞ΕΔͱίϯϙʔωϯτ͕࠶ඳը͞Ε·͢ ▸ Πϕϯτॲཧλάଐੑʹઃఆ͠·͢ʢྫɿ<Example onClick={handleClick} />ʣ
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Backboneʹ͍ͭͯ ▸ RESTful APIͱͷ࿈ܞΛγϯϓϧʹநԽɻେ͖̏ͭ͘ͷػೳΛ࣋ͪ·͢ ▸ Model: APIͷ୯Ϧιʔεͱಉظ ▸ Collection:
Modelͷू߹ͰɺAPIͷෳϦιʔεͱಉظ ▸ View: ඥͮ͘ModelCollectionͷσʔλΛDOMʹө͠ɺDOMͷϢʔβೖྗ ΛModelCollectionʹө
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ReactԽ Part.1 : ΊͪΌΊͪΌബ͘ReactΛ͏ ▸ Ұ൪؆୯ͳ͍ํͰ͢ɻ ؆୯ʹಋೖͰ͖·͕͢ɺ͜ͷ͍ํͰReact͍͍ͨਓ͍ͳ͍ͱ ࢥ͏ͷͰɺࢀߟఔʹհ͠·͢ ▸
ࢀߟURL ▸ https://facebook.github.io/react/docs/installation.html#using-a-cdn ▸ https://facebook.github.io/react/docs/react-without-es6.html ▸ https://facebook.github.io/react/docs/react-without-jsx.html ▸ ຊདྷReactɺYarn,npmͷύοέʔδϚωʔδϟɺwebpack,Browserifyͷόϯυϥɺ BabelͷίϯύΠϥΛซͤͯ׆༻͢Δ͜ͱΛਪ͍ͯ͠·͕͢ɺࠓճͦΕΒͷπʔϧ ΛΘͣ͏ํ๏Ͱ͢
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Α͋͘ΔBackboneϓϩδΣΫτͷྫ ▸ htmlʹςϯϓϨʔτΛॻ͍ͯɺ <script type="text/template" id="item-template"> <div class="view"> <input
class="toggle" type="checkbox" <%= completed ? 'checked' : '' %>> <label><%- title %></label> <button class="destroy"></button> </div> <input class="edit" value="<%- title %>"> </script>
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Α͋͘ΔBackboneϓϩδΣΫτͷྫ ▸ BackboneViewͰɺUnderscoreͱjQueryͰඳը͠·͢Ͷ template: _.template($('#item-template').html()), render: function () {
this.$el.html(this.template(this.model.toJSON())); },
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ςϯϓϨʔτΛReactԽ͢Δ ▸ htmlʹCDNͷReactΛه͠ɺ <script src="https://unpkg.com/react@15/dist/react.js"></ script> <script src="https://unpkg.com/react-dom@15/dist/react- dom.js"></script>
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ςϯϓϨʔτΛReactԽ͢Δ ▸ htmlͷςϯϓϨʔτΛফͯ͠ɺReact ComponentΛ࡞Γ·͢ var Item = React.createClass({ render:
function() { return React.createElement('div', null, React.createElement('div', {className: 'view'}, React.createElement('input', { className: ‘toggle', type: ‘checkbox', checked: this.props.completed }, null), React.createElement('label', null, this.props.title), React.createElement('button', {className: 'destroy'}, null) ), React.createElement('input', { className: ‘edit', defaultValue: this.props.title }, null) ); } });
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ςϯϓϨʔτΛReactԽ͢Δ ▸ BackboneViewͷඳը͢Δͱ͜ΖΛॻ͖͑·͢ render: function () { ReactDOM.render( React.createElement(Item,
this.model.toJSON(), null), this.$el.get(0) ); },
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ <script type="text/template" id="item-template"> <div class="view"> <input class="toggle" type="checkbox" <%=
completed ? 'checked' : '' %>> <label><%- title %></label> <button class="destroy"></button> </div> <input class="edit" value="<%- title %>"> </script> var Item = React.createClass({ render: function() { return React.createElement('div', null, React.createElement('div', {className: 'view'}, React.createElement('input', { className: ‘toggle', type: ‘checkbox', checked: this.props.completed }, null), React.createElement('label', null, this.props.title), React.createElement('button', {className: 'destroy'}, null) ), React.createElement('input', { className: ‘edit', defaultValue: this.props.title }, null) ); } });
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ template: _.template($('#item-template').html()), render: function () { this.$el.html(this.template(this.model.toJSON())); }, render:
function () { ReactDOM.render( React.createElement(Item, this.model.toJSON(), null), this.$el.get(0) ); },
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Part.1 ·ͱΊ ▸ ͱͯݟͮΒͯ͘ݏͰ͢Ͷɻ ▸ ReactͬΆ͞ΛࣺͯΕɺಋೖࣗମ؆୯ʹͰ͖Δͱ͍͏ྫ Ͱͨ͠
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ReactԽ Part.2 : JSXͰBackbone TemplateΛஔ͖͑Δ ▸ ύοέʔδϚωʔδϟɺόϯυϥɺίϯύΠϥΛಋೖ͢Δ͜ͱʹͳΓ·͕͢ɺ ReactࣗମͰ֮ ͑Δ͜ͱগͳ͍͍ํͰ͢ɻ
πʔϧʹ׳Ε͍ͯͳ͚Εɺ࿅शʹͪΐ͏Ͳ͍͍͘Β͍ͷม ߋྔͰ͠ΐ͏ɻ ▸ ࢀߟURL ▸ https://nodejs.org/en/download/package-manager/ ▸ https://yarnpkg.com/en/docs/install#alternatives-tab ▸ https://facebook.github.io/react/docs/installation.html#installing-react ▸ https://webpack.js.org/guides/installation/ ▸ https://babeljs.io/docs/setup/#installation ▸ https://facebook.github.io/react/docs/introducing-jsx.html
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ඞཁͳͷΛΠϯετʔϧ͢Δ ▸ ύοέʔδϚωʔδϟYarnΛΠϯετʔϧ ▸ ύοέʔδϚωʔδϟͱ͍͑npmͰ͕͢ɺReactؔ࿈ͷυΩϡϝϯτͰyarnϕʔ εͰॻ͔Ε͍ͯΔ͜ͱ͕ଟ͍ͷͰࠓճͪ͜ΒΛ͍·͢ɻ ▸ ίϚϯυେମޓ͍ͯ͠ΔͷͰɺnpm͕͍͍ํదٓஔ͖͑ͯಡΜͰ͍ͩ͘͞ɻ ▸
npmίϚϯυରরදɿ https://yarnpkg.com/en/docs/migrating-from-npm ▸ YarnΛͬͯɺReactͱɺόϯυϥʹwebpackɺίϯύΠϥʹbabelΛΠϯετʔϧ yarn add react react-dom yarn add webpack babel-core babel-loader babel-preset-react --dev
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ςϯϓϨʔτΛReactԽ͢Δ ▸ React ComponentΛ࡞ͬͯΈ·͢ ▸ ҰݟHTMLʹݟ͑Δ͜ͷจ๏͕JSXͰ͢ɻ className, defaultValueগ͠HTMLͱ ҧ͏ଐੑ͕͋Γ·͢Ͷɻ
var Item = React.createClass({ render: function() { return ( <div> <div className="view"> <input className="toggle" type="checkbox" checked={this.props.checked} /> <label>{this.props.title}</label> <button className="destroy"></button> </div> <input className="edit" defaultValue={this.props.title} /> </div> ); } });
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ςϯϓϨʔτΛReactԽ͢Δ ▸ BackboneViewͷඳը͢Δͱ͜ΖΛॻ͖͑ͯΈ·͢ render: function () { ReactDOM.render( <Item
title={this.model.get('title')} checked={this.model.get('completed')} />, this.$el.get(0) ); },
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ <script type="text/template" id="item-template"> <div class="view"> <input class="toggle" type="checkbox" <%=
completed ? 'checked' : '' %>> <label><%- title %></label> <button class="destroy"></button> </div> <input class="edit" value="<%- title %>"> </script> var Item = React.createClass({ render: function() { return ( <div> <div className="view"> <input className="toggle" type="checkbox" checked={this.props.checked} /> <label>{this.props.title}</label> <button className="destroy"></button> </div> <input className="edit" defaultValue={this.props.title} /> </div> ); } });
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ template: _.template($('#item-template').html()), render: function () { this.$el.html(this.template(this.model.toJSON())); }, render:
function () { ReactDOM.render( <Item title={this.model.get('title')} checked={this.model.get('completed')} />, this.$el.get(0) ); },
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ςϯϓϨʔτΛReactԽ͢Δ ▸ ςϯϓϨʔτ෦ࣅͨΑ͏ʹهड़Ͱ͖ΔΑ͏ʹͳΓɺඳ ը෦͕ײతͳදݱʹͳΓ·ͨ͠Ͷ ▸ ͨͩ͠ɺ͔͜͜ΒϏϧυ͢Δ࡞ۀ͕ඞཁͰ͢
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ςϯϓϨʔτΛReactԽ͢Δ ▸ webpack.config.jsΛ࡞ΓɺϏϧυઃఆΛॻ͖·͢ module.exports = { entry: { 'components/Item.js':
'./js/components/Item.js', 'views/todo-view.js': './js/views/todo-view.js' }, output: { path: `${__dirname}/dist`, filename: '[name]' }, module: { loaders: [ { test: /\.js$/, loader: 'babel', query: { presets: ['react'] }
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ςϯϓϨʔτΛReactԽ͢Δ ▸ package.jsonʹϏϧυεΫϦϓτΛه͠·͢ "scripts": { "build": "webpack" },
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ςϯϓϨʔτΛReactԽ͢Δ ▸ Ϗϧυ͠·͠ΐ͏ ▸ ͜ΕͰdistʹϏϧυͨ͠jsϑΝΠϧ͕ੜ͞ΕΔͷͰɺ͜ΕΛhtmlʹಡΈ ࠐ·ͤ·͢ yarn run build
<script src="node_modules/react/dist/react.js"></script> <script src="node_modules/react-dom/dist/react-dom.js"></ script> <script src="dist/components/Item.js"></script> <script src="dist/views/todo-view.js"></script>
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ςϯϓϨʔτΛReactԽ͢Δ ▸ ϑΝΠϧ͕Ͱ͖ΔͨΊɺϖʔδؒͰͷςϯϓϨʔτͷڞ༗͕༰қʹ ▸ ͨͩɺςϯϓϨʔτϑΝΠϧΓग़͚ͩ͠Ͱ͋ΕɺUnderscore TemplateͰJSTίϯύΠϥΛ࣮͑ݱͰ͖·͢ɻ ▸ ͦΕ͚ͩͩͱ͍ͨͨ͠ϝϦοτʹͳΓ·ͤΜͶ ▸
JSXͷ͞Βʹ͍͍ͱ͜ΖɺJSXͰReact ComponentΛݺͼग़͢͜ͱ ͕Ͱ͖ΔͷͰɺΑΓݟ͘͢ίϯϙʔωϯτͷೖΕࢠΛදݱͰ͖Δͱ ͜ΖͰ͢
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Underscore Templateͷ߹ ▸ ཁૉʹࢠཁૉΛՃ͢ΔͳΒɺView͔ΒViewΛݺͼग़ͯ͠ɺ DOMʹૠೖ͢ΔॲཧΛॻ͘͜ͱʹͳΓ·͢ ▸ html <script type="text/template"
id="parent"> <div class="parent"></div> </script> <script type="text/template" id="child"> <div class="child"><%- text %></div> </script>
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Underscore Templateͷ߹ ▸ js var ChildView = Backbone.View.extend({ template:
_.template($('#child').html()), render: function () { this.$el.html(this.template(this.model.toJSON())); } }); var ParentView = Backbone.View.extend({ template: _.template($('#parent').html()), render: function () { this.$el.html(this.template()); var parent = this.$el.find('.parent'); this.collection.each(function (model) { var child = new ChildView({model: model}); parent.append(child.$el); }); } });
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Reactͷ߹ ▸ ίϯϙʔωϯτ͔ΒίϯϙʔωϯτΛݺͼग़ͤ·͢ var Parent = React.createClass({ render: function()
{ var children = []; this.props.collection.each(function (model) { children.push(<Child model={model}>); }); return <div className="parent">{children}</div>; } }); var Child = React.createClass({ render: function() { return <div className="child">{this.props.text}</div>; } });
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Reactͷ߹ ▸ ͳͷͰView1ͭʹͳΓ·͢ var ParentView = Backbone.View.extend({ render: function
() { ReactDOM.render( <Item collection={this.collection} />, this.$el.get(0) ); } });
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Part.2 ·ͱΊ ▸ ͜ͷΑ͏ʹγϯϓϧʹهड़Ͱ͖ɺؾܰʹڞ௨UI෦Λͯ͠͠·͑·͢ɻ Child͕ඳըͷΈͰ͍͍߹ɺ͜ͷख๏ͰऔΓೖΕΔͷ͋Γͩͱࢥ͍·͢ɻ ▸ ͔͠͠ͳ͕Βɺ Childʹੜ࣌Ϣʔβೖྗ࣌ͷΠϕϯτॲཧΛ࣋ͨͤͯɺͦΕڞ௨Խ͍ͨ͠ ͱ͍͏߹ɺ
React ComponentͰͦ͏͍ͬͨࣄॻ͚·͕͢ɺͷʹΑͬͯBackbone View ʹॻ͍ͯ͋ͬͨΓReact Componentʹॻ͍ͯ͋ͬͨΓ͢ΔͱɺՄಡੑอकੑ ΛԼ͛ͯ͠·͏ͷͰɺ ݁ہChildͷBackbone ViewΛ࡞ͬͯParentView͔Βݺͼग़͢͜ͱʹͳΓ·͢ɻ
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ReactԽ Part.3 : Backbone ViewΛReact Componentʹஔ͖͑Δ ▸ React ComponentͷػೳͰBackbone
ViewͰ͍ͬͯΔ͜ͱΛҠ২͠·͢ɻ ▸ มߋྔ݁ߏ͋ΓɺES2015+Λಋೖ͠JSͷॻ͖ํ͕݁ߏมΘΓ·͕͢ɺ Backboneʹͳ͍ViewͷՄಡੑɾอकੑ্ͷͨΊͷ༷ʑͳϝϦοτΛڗ डͰ͖·͢ɻ ▸ ࢀߟURL ▸ https://facebook.github.io/react/docs/components-and-props.html ▸ https://facebook.github.io/react/docs/handling-events.html
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Α͋͘ΔBackbone View var View = Backbone.View.extend({ tagName: 'li', //
ユーザ入力イベントとハンドラの紐付け events: { 'click .toggle': 'toggleCompleted' }, // モデル変更イベントとハンドラの紐付け initialize: function () { this.listenTo(this.model, 'change', this.render); }, render: function () { this.$el.html(this.template(this.model.toJSON())); }, toggleCompleted: function () { this.model.toggle(); } });
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ React ComponentԽ // 依存ライブラリの参照はHTMLではなくjsに書く import Item, {Component} from 'react';
// classが使える class Todo extends Component { // 描画後イベント componentDidMount() { // モデル変更イベントとハンドラの紐付け this.props.model.on('change', this.handleChangeModel); } handleChangeModel() { // 描画実行 this.forceUpdate(); } handleClickToggle() { this.props.model.toggle(); } 〜つづく〜
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ React ComponentԽ 〜つづき〜 render() { const title = this.props.model.get('title');
const completed = this.props.model.get('completed'); // ユーザ入力イベントとハンドラの紐付け return ( <li> <div className="view"> <input className="toggle" type="checkbox" checked={completed} onClick={this.handleClickToggle} /> <label>{title}</label> </div> </li> ); } }
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ React ComponentԽ ▸ BackboneɺϚʔΫΞοϓͱJSΛ͠·͕͢ɺReactɺ݁߹͠·͢ɻ HTMLίʔσΟϯά͔͠Ͱ͖ͳ͍ਓͱɺϓϩάϥϚͷۀͰ͍ͬͯΔνʔϜͩͱෆ͖ʁ ▸ খ͘͞࡞ΒΕͨίϯϙʔωϯτɺ ΠϕϯτͷྲྀΕ͕ಡΈ͘͢ɺίʔυ͕ࢄ͍ͯ͠ͳ͍ͷͰɺ ࠶ར༻࣌ʹؾʹ͔͚Δ෦ݮΓ·͢ɻ
▸ ·ͨ෦Ͱఆٛ͞ΕͨϝιουCSSΫϥεӅṭ͞Εɺ ֎͔Βࢀর͢Δ͜ͱ͕Ͱ͖ͳ͍ͷͰɺ໊લͷڝ߹ͰࠔΔ͜ͱ͕ͳ͘ͳΔɺ ϝϦοτ͕͋Γ·͢ɻ
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ React ComponentԽ ▸ htmlʹࢀরΛه͢Δࡍɺ webpackʹΑͬͯɺimportઌͷϑΝΠϧΛશͯΤϯτϦʔϑΝ Πϧʹ݁߹͞Ε͍ͯΔͷͰɺಡΈࠐΉͷ1ͭͰΑ͘ͳΓ·͢ <script src="dist/views/app-view.js"></script>
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Part.3 ·ͱΊ ▸ Backbone ViewͰΓʹ͍͘ίϯϙʔωϯτࢦΛ༰қ ʹͰ͖·ͨ͠ ▸ UIͷΈίϯϙʔωϯτͷೖΕࢠ͚ͩͰͳ͘ɺ ςϯϓϨʔτ͚ͩͷReactԽͷ՝ͱͳΔɺػೳͷ͋Δίϯ
ϙʔωϯτͷڞ༗ɺ Backbone View͝ͱReact Componentʹஔ͖͑Δ͜ͱͰ ࣮ݱͰ͖·ͨ͠
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ReactԽ Part.4 : ComponentΛׂͰׂ͠ɺ࠶ར༻ੑΛߴΊΔ ▸ Part3ͰɺϩδοΫͷ͋ΔComponent෦Ͱঢ়ଶૢ࡞Λߦ͍ͬͯΔ ͨΊɺ ෦༻ͷঢ়ଶϓϩύςΟstateΛ༻͍ͯ͠·͢ɻ ▸
͔͠͠ͳ͕ΒɺComponentεςʔτϨεʹ࡞ΒΕ͍ͯΔํ͕ɺ Մಡੑɾ࠶ར༻ੑɾςελϏϦςΟ্͕͠·͢
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Componentͷׂ ▸ ReactΛ༻͢ΔFWͷFlux UtilsReduxͰɺ ComponentΛ2ׂͭͰׂ͢Δ͜ͱΛਪ͍ͯ͠·͢ɻ ▸ 1ͭɺ͞ΕΔpropsʹԠͯ͡UIΛඳը͢ΔεςʔτϨείϯϙʔωϯτ ͏1ͭɺσʔλͱViewΛૢ࡞͢Δίϯϙʔωϯτ
લऀViews·ͨPresentational Componentsɺ ޙऀContainers·ͨContainer ComponentsͱݺΕ·͢ ▸ ࢀߟURL ▸ https://facebook.github.io/flux/docs/flux-utils.html#best-practices ▸ http://redux.js.org/docs/basics/UsageWithReact.html#presentational-and- container-components
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Part3ͷComponentΛViewͱContainerʹׂ͢Δ ▸ View ▸ propsΛඳը͢Δ͚ͩ ͳͷͰFunctional Componentʹ͠·͢ ▸ https://
facebook.github.io/ react/docs/ components-and- props.html#functional- and-class-components const Item = (props) => { // 状態は外から渡される const {title, checkedToggle} = props; const handleClickToggle = () => { // 外から渡されたハンドラにそのまま返す props.onClickToggle(); } return ( <li> <div className="view"> <input className="toggle" type="checkbox" checked={checkedToggle} onClick={handleClickToggle} /> <label>{title}</label> </div> </li> ); }
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Part3ͷComponentΛViewͱContainerʹׂ͢Δ ▸ Container class ItemContainer extends Component { componentDidMount()
{ this.props.model.on('change', this.handleChangeModel); } handleChangeModel() { this.forceUpdate(); } handleClickToggle() { this.state.model.toggle(); } render() { const title = this.props.model.get('title'); const completed = this.props.model.get('completed'); // Itemの状態はこちらで管理する return ( <Item title={title} checkedToggle={completed} onClickToggle={handleClickToggle} /> ); } }
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Part.4 ·ͱΊ ▸ σʔλͷΓͱΓͱɺUIͷදݱ͕ผΕͨ͜ͱͰɺ ͞ΒʹUIͷ࠶ར༻ੑ্͕ͨ͠ͱࢥ͍·͢ɻ ▸ ྫ͑ɺDate PickerͷΑ͏ͳϢʔβೖྗUIɺ ೖྗʹΑͬͯͲ͏ॲཧ͢Δ͔ɺ͏ॴͰܾΊ͍ͨͷͳͷ
Ͱɺ͜ͷϓϥΫςΟε͕༗ޮʹಇ͖·͢ɻ
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ReactԽ Part.5 : σʔλϑϩʔʹFluxΛऔΓೖΕΔ ▸ FluxFacebook͕ఏএ͢Δ୯ํσʔλϑϩʔΞʔΩςΫνϟ ▸ Model-ViewͰModel͕σʔλͱσʔλʹର͢ΔཁٻΛ͍࣋ͬͯ·͕͢ɺ FluxͰɺσʔλ(Store)ͱσʔλʹର͢Δཁٻ(Action)Λ͠·͢
▸ Reactɺ͜ͷΈͷதͰViewʹΘΕΔ͜ͱΛਪ͍ͯ͠·͢
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ BackboneʹFluxͷ֓೦ΛऔΓೖΕΔʹ ▸ ͷൣғΛ୲͍ͬͯΔCollectionModelΛׂ
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Part.5 ·ͱΊ ▸ ݱঢ়ViewModelʹϩδοΫ͕ࢄΒ͔͍ͬͯΔ͕ɺ ActionΛऔΓೖΕͨ͜ͱͰɺߋ৽ͱऔಘΛ͢Δ͜ͱ͕Ͱ͖ɺ ϩδοΫͷཧͱංେԽΛ͑ΒΕͦ͏Ͱͨ͠ ▸ ͔͠͠ɺDispatcherͱ͔ɺViewͱModelΛDispatcherͰඥ͚Δ ෦ͱ͔ɺಠ࣮ࣗ͢Δͱ͜Ζ͕৭ʑ͋ͬͯɺ݁ہBackbone
Ϣʔβʹͱֶͬͯशίετ͕͔͔ͬͯ͠·͏ײ͡Ͱ͢ ▸ ͰɺFLUXɺCQRS + Event Sourcingύλʔϯͱ͍ͬͨҰํ ͷσʔλϑϩʔτϨϯυͳͷͰੋඇ͓͓͖͍͑ͯͨ͞Ͱ͢Ͷɻ
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ࣮͜ͷࠒʹ ▸ ͳΜ͔ٕज़తෛ࠴ଟա͗ͯɺReactʹஔ͖͑ʹ͍͘ॴ͕ ͋Γ͗͢Δͱ͍͏ݱ࣮ʹ໘͍ͯ͠·ͨ͠ɻ ▸ ݁ہϓϩδΣΫτෛ࠴ฦࡁͱ৽ن։ൃʹ͠·ͨ͠ɻ
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ ReactԽ Part.6 : BackboneΊΔ ▸ ৽ن։ൃϓϩδΣΫτ͕࢝·ΓɺτϨϯυͷReduxͱɺ Facebook͕ϝϯςφϯε͢ΔFlux UtilsͰൺֱ͢Δ͜ͱʹͳΓ ·ͨ͠ɻ
▸ ͜ͷ2ͭͷେ͖ͳҧ͍ɺReduxʹ1ͭͷΦϒδΣΫτʹΞϓ ϦέʔγϣϯશମͷεςʔτΛ·ͱΊΔݪଇ͕͋Δɺͱ͍͏ͱ ͜ΖͰ͢ɻ ▸ ElmͷӨڹΛड͚ͨReduxɺؔܕϓϩάϥϛϯάͷ׆༻ʹ Αͬͯอकੑͷߴ͍ίʔυΛॻ͚ΔͷͰ͍͍ͱࢥ͍·ͨ͠ɻ
طଘϓϩμΫτͷViewΛReactʹஔ͖͑Δ Part.6 ·ͱΊ ▸ ͔ͳΓࡉ͔͍ίʔσΟϯάνΣοΫઃఆͰ͋Δeslint-config- airbnbΛซ༻͢Δͱ͍͍ͱࢥ͍·͢ɻ ▸ FacebookJS੩తܕνΣοΧʔͷFlowซͤͯಋೖ͠ɺ JSʹڧ͍ܕ͚ͱnullඇڐ༰Λ͚ͭΔͱΑΓ҆৺Ͱ͠ΐ͏ɻ
THAT'S IT. ͝ਗ਼ௌ͋Γ͕ͱ͏͍͟͝·ͨ͠