- ずっとほっといてたReactをやっと触ってみた
Reactとは
- JavaScriptライブラリ
- JavaScript内にHTMLタグ(のようなもの)を書ける
- テンプレートエンジンのような感じ
- MVCのV部分のみ
-
公式チュートリアルが充実してるのでこれを試す
- web初心者には厳しい内容です
ソースコード
- githubにこの内容のソースコードをおいています
開発環境
- 手っ取り早くサーバはnodeで。
- 以前投稿した手順を参考に。
React開始
Reactインストール
- npmより
- まずReact本体とreact-domを。これはセットで使う
- bootstrap使うなら
react-bootstrap
も一緒にinstall
npm install --save react react-dom react-bootstrap
- 次にbrowserifyにreactを認識させるため、
reactify
を入れる
npm install --save-dev reactify
gulp調整
- browserifyにreactを認識させる
-
transform
にreactify
を追加
gulpfile.js
gulp.task('js', function() {
browserify({
entries: ["./clientsrc/js/main.js"], // ビルド対象のファイル
debug: true, // sourcemapを出力、chromeでのdebug可能にする
transform: ['cssify', 'reactify']
})
.bundle()
.on('error', console.error.bind(console)) // js compileエラーでもwatchを止めない
.pipe(source("app.js")) // ビルド後のファイル名
.pipe(buffer())
.pipe(sourcemaps.init({loadMaps: true}))
.pipe(uglify())
.pipe(sourcemaps.write("./"))
.pipe(gulp.dest("./public/js/")); // 生成先の指定
});
React Tutorial
Hello World
- お試しなのでmain.jsで記述
- ReactとReactDomをrequireする
var React = require('react');
var ReactDom = require('react-dom');
- Reactのオブジェクト(コンポーネントという)は
React.createClass
を使って以下のように作成する 注意点としてcss class名の指定はhtmlと違い
className="xxx"
の形式作ったコンポーネントをDOMに吐き出すには
ReactDom.render
を使う中はコンポーネント名と吐き出し先DOM
- Reactに指定するtagはネスト可能
ただしルートレベルは1つのタグのみ
OKの例
<div>
<div>
</div>
</div>
- NGの例
<div>
</div>
<div>
</div>
- サンプルコード
function example3() {
var CommentBox = React.createClass({
render: function() {
return (
<div className="commentBox">
Hello, world! I am a CommentBox.
</div>
);
}
});
ReactDom.render(
<CommentBox />,
$('#example3').get(0)
);
}
JSXでの記述
- html tagでなくJSXでの記述も可能
function example4() {
var CommentBox = React.createClass({
displayName: 'CommentBox',
render: function() {
return (
React.createElement('div', {className: "commentBox"},
"This Object Created by JSX"
)
)
}
});
ReactDom.render(
React.createElement(CommentBox, null),
$('#example4').get(0)
);
}
コンポーネントのネスト
- コンポーネントはtag文字内で子オブジェクト名を指定することでネストできる
- 子オブジェクトをソース上先に定義する必要がある
function example5() {
// 子コンポーネント1
var CommentList = React.createClass({
render: function() {
return (
<div className="commentList">
Hello, I am a Comment List.
</div>
);
}
});
// 子コンポーネント2
var CommentForm = React.createClass({
render: function() {
return (
<div className="commentForm">
I am a CommentForm
</div>
);
}
});
// 親コンポーネント
var CommentBox = React.createClass({
render: function() {
return (
<div className="commentBox">
<h1>Example5</h1>
<CommentList />
<CommentForm />
</div>
)
}
});
ReactDom.render(
React.createElement(CommentBox, null),
$('#example5').get(0)
);
}
コンポーネントへパラメータ渡し
- パラメータは親コンポーネントで指定した子コンポーネントのattrで渡せる
- パラメータ受け取りは
param.props.xxx
- 親コンポーネントで指定した子コンポーネントの中身htmlは
param.props.children
で取得可能
function example6() {
var Comment = React.createClass({
// get parameter by this.props from parent
// this.props.[attributes name] - アトリビュートにセットされたパラメータ
// this.props.children - タグの子要素
render: function() {
return (
<div className="comment">
<h2 className="commentAuthor">
{this.props.author}
</h2>
{this.props.children}
</div>
);
}
});
var CommentList = React.createClass({
render: function() {
return (
<div className="commentList">
<Comment author="Akihiko Takayama">This is one comment</Comment>
<Comment author="Akemi Takayama">This is another comment</Comment>
</div>
);
}
});
// 子コンポーネント2
var CommentForm = React.createClass({
render: function() {
return (
<div className="commentForm">
I am a CommentForm
</div>
);
}
});
// 親コンポーネント
var CommentBox = React.createClass({
render: function() {
return (
<div className="commentBox">
<h1>Example6</h1>
<CommentList />
<CommentForm />
</div>
)
}
});
ReactDom.render(
React.createElement(CommentBox, null),
$('#example6').get(0)
);
}
コンポーネントへ動的パラメータ渡し
- 親コンポーネントに外部からのデータオブジェクトを渡す
- コンポーネント内で受け取ったデータを使って動的にhtmlを構成
function example7() {
var Comment = React.createClass({
render: function() {
return (
<div className="comment">
<h2 className="commentAuthor">
{this.props.author}
</h2>
{this.props.children}
</div>
);
}
});
var CommentList = React.createClass({
render: function() {
// 受け取ったデータ分、Commentオブジェクトを作成
var commentNodes = this.props.data.map(function(comment) {
return (
<Comment author={comment.author} key={comment.id}>
{comment.text}
</Comment>
);
});
return (
<div className="commentList">
{commentNodes}
</div>
);
}
});
// 子コンポーネント2
var CommentForm = React.createClass({
render: function() {
return (
<div className="commentForm">
I am a CommentForm
</div>
);
}
});
// 親コンポーネント
var CommentBox = React.createClass({
render: function() {
return (
<div className="commentBox">
<h1>Example7</h1>
<CommentList data={this.props.data} />
<CommentForm />
</div>
)
}
});
var data = [
{id: 1, author: "Akihiko Takayama", text: "Akiiko's Comment"},
{id: 2, author: "Akemi Takayama", text: "Akemi's Comment"}
];
ReactDom.render(
React.createElement(CommentBox, {data: data}),
$('#example7').get(0)
);
}
コンポーネントへajax渡し
- 正直ここまでreactにやらせると制御きつい気がするので割愛
- 続きは公式をみてください
触ってみた所感
- フロントエンド側のテンプレートエンジンと割り切ると気楽につかえて◯
- angularのように縛り一杯でないあたりとか
- jQueryでガチガチ書く人はとっつきやすいはず
- 今まで
jquery multiline
とかでやってたのの代わりにできそう - テンプレートいっぱい作ってexportsしといて使うスタイルまで昇華できれば
- どこまでコンポーネント化するか、設計方針ちゃんと決めとく必要ありそう