-- React prologue and Build a note app #post title
-
Download code: https://github.com/buckyroberts/React-Boilerplate, My editon with notes: https://github.com/xy7313/React-Boilerplate. Final note app click here, code here
-
Include JSX
//after download, also can ref online file,
<script src="../../js/react.min.js"></script>
<script src="../../js/react-dom.min.js"></script>
<script src="../../js/browser.min.js"></script>
The last line transpile jsx file to plain js file so that browser can understand jsx. There are also some online tools can do the same work for developer.
- an example:
<!DOCTYPE html> <html> <head> <script data-require="react@*" data-semver="15.5.0" src="https://cdnjs.cloudflare.com/ajax/libs/react/15.5.0/react.min.js"></script> <script data-require="react@*" data-semver="15.5.0" src="https://cdnjs.cloudflare.com/ajax/libs/react/15.5.0/react-dom.min.js"></script> <script data-require="react@*" data-semver="15.5.0" src=" https://cdnjs.cloudflare.com/ajax/libs/babel-core/5.8.24/browser.min.js"></script> <link rel="stylesheet" href="style.css" /> </head> <body> <div id="container"></div> <script type="text/babel"> ReactDOM.render( <h2>Welcome to React!</h2>, document.getElementById('container') ); </script> <script src="script.js"></script> </body> </html>
- Include bable: we add a h2 tag into the html element whoes id is 'container'
<script type="text/babel">
ReactDOM.render(
<h2>Welcome to React!</h2>,
document.getElementById('container')
);
</script>
-
Components parts of your website, entire application is made up of components.
-
Super component:
<script type="text/babel">
var BuckysComponent = React.createClass({
//object
//return html
render: function() {
return (<h2>This is a simple component</h2>);
}
});
ReactDOM.render(<BuckysComponent />, document.getElementById('container'));
</script>
- Mutiple components
- One component can only return one parent element(div). The render
ReactDOM.render(..,..)
can only render only one one parent tag - when we want to return more than one html tags.
<script type="text/babel">
var BuckysComponent = React.createClass({
//object
//return html
render: function() {
return (
<div>
<h2>This is a simple component</h2>
<p>para</p>
</div>
);
}
});
ReactDOM.render(<div>
<BuckysComponent />
<BuckysComponent />
</div>, document.getElementById('container'));
</script>
- Properties:
-
make template for one component and customize in different ways. Using curly brace{}
-
Property is essentially an HTML attribute that we can pass in to customize our components in different kinds of ways.
<body> <div id="container"></div> <script type="text/babel"> var Movie = React.createClass({ render:function(){ return( <div> <h1>{this.props.title}</h1> <h2>{this.props.genre}</h2> </div> ); } }); ReactDOM.render( <div> <Movie title="Avatar" genre="action"/> <Movie title="The NoteBook" genre="romance"/> <Movie title="Cube" genre="thriller"/> </div>,document.getElementById('container') ); </script> </body> //output: Avatar, action, The NoteBook, romance, Cube, thriller
- Event handling
-
Example: Built a sticky note app, where users can add new notes, delete or edit notes and write any notes.
-
can not use class as prop's name, because class is one of the reserve words in js
-
children property(built-in prop), between the opening tag and closing tag, like:
<Comment>hey-sample txt</Comment>
<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <meta name="viewport" content="width=device-width, initial-scale=1"> <title>React-stickyNote</title> <script src="../../js/react.min.js"></script> <script src="../../js/react-dom.min.js"></script> <script src="../../js/browser.min.js"></script> <link rel = "stylesheet" type="text/css" href = "../../css/main.css"> </head> <body> <div id="container"></div> <script type="text/babel"> var Comment = React.createClass({ edit: function(){ alert("edit"); }, remove: function(){ alert("remove"); }, render: function(){ return( //can not use class, because class is reserve word in js //children property, between the opening tag and closing tag <div className = "commentContainer"> <div className = "commentText"> {this.props.children} </div> <button onClick={this.edit} className = "button-primary">Edit</button> <button onClick={this.remove} className = "button-danger" >Remove</button> </div> ); } }); ReactDOM.render( <div className = "board"> <Comment>hey-sample txt</Comment> <Comment>beans</Comment> <Comment>TUNA txt</Comment> </div>,document.getElementById('container') ); </script> </body> </html>
- State
-
Customize the components using properties and states. Whenever something is gonna stay the same uses properties, whenever changes uses states.
-
You don't need to explicitly say whenever your state changes to redraw a certain part of your webpage, it automatically watches for your states. Whenever their state changes, the part of web page gets redrawn automatically to fit that.
<body> <div id="container"></div> <script type="text/babel"> var CheckBox = React.createClass({ getInitialState: function(){ return {checked:true} }, handleChecked: function(){ this.setState({checked:!this.state.checked}) }, render: function(){ var msg; if(this.state.checked){ msg='checked' }else{ msg='unchecked' } return( <div className = "commentContainer"> <input type = "checkbox" defaultChecked={this.state.checked} onChange = {this.handleChecked}/> <h3>checkBox is {msg}</h3> </div> ); } }); ReactDOM.render( <CheckBox />,document.getElementById('container') ); </script> </body>
- Add state to component(contd on the sticky note app)
-
Requirements: This note switches bewteen two modes/states: editing, normal. That is, whenever we click edit, the text area can be changed to a form for editing. After complish editing, the form turns to text area.
<body> <div id="container"></div> <script type="text/babel"> var Comment = React.createClass({ getInitialState: function(){ return {editing: false} }, edit: function(){ this.setState({editing:true}); }, save: function(){ this.setState({editing:false}); }, remove: function(){ alert("remove"); }, renderForm: function(){ return( <div className = "commentContainer"> <textarea defaultValue = {this.props.children}></textarea> <button onClick={this.save} className = "button-success" >Save</button> </div> ); }, renderNormal: function(){ return( <div className = "commentContainer"> <div className = "commentText"> {this.props.children} </div> <button onClick={this.edit} className = "button-primary">Edit</button> <button onClick={this.remove} className = "button-danger" >Remove</button> </div> ); }, render: function(){ if(this.state.editing){ return this.renderForm(); }else{ return this.renderNormal(); } } }); ReactDOM.render( <div className = "board"> <Comment>hey-sample txt</Comment> <Comment>beans</Comment> <Comment>TUNA txt</Comment> </div>,document.getElementById('container') ); </script> </body>
- refs (contd on the sticky note app)
- Requirements: Save whatever the textarer looks like now.
- First, get the text just typed
- Second, show it
- eg:
var val = this.refs.newText.value;
+<textarea ref = "newText" defaultValue = {this.props.children}></textarea>
- rearrange multiple independent components -- set up a 'parent' container (contd on the sticky note app)
- In the note example, we define a borad, which is like a magener of all note components
- unique identifier, key is the way to uniquely identify each child by giving an ID
//add Board in script babel, change ReactDom.render
var Board = React.createClass({
getInitialState: function(){
return {
comments:[
'I like bacon',
'want some ice cream',
'done here'
]
};
},
render: function(){
return (
<div className = "board">
{
//anonymous function, a.k.a a function with no name, key-unique identifier
this.state.comments.map(function(text,i){
return (<Comment key = {i}>{text}</Comment>);
})
}
</div>
);
}
});
ReactDOM.render(<Board/> ,document.getElementById('container')
);
- Updating state and remove notes(contd on the sticky note app)
- clean up the render function
- array.splice(index,num); remove num elements from index of array
//all in var Board
removeComment: function(i){
console.log("remove:"+i);
var arr = this.state.comments;
arr.splice(i,1);
this.setState({comments:arr});
},
updateComment: function(newText,i){
console.log("new text:"+newText);
var arr = this.state.comments;
arr[i] = newText;
this.setState({comments:arr});
},
eachComment: function(text,i){
// unique identifier, i: increment for the array
return (<Comment key = {i} index = {i}>
{text}
</Comment>);
},
render: function(){
return (
<div className = "board">
{this.state.comments.map(this.eachComment)}
</div>
);
}
- Passing functions as props (contd on the sticky note app)
- how to call functions from entirely different components? using props
- Add new component (contd on the sticky note app)
- Js can not figure out the scope, so we need to call band :
<button className = "button-info create" onClick = {this.addComment.bind(null,'Type here')}>New A Comment</button>
.
Notice that: Don't .bind in the render() function - that creates a new function every time render is called (which will be often.) .bind in the component constructor. We will create too many comment components and get an error.
网友评论