React JS + React Native
React Fundamentals
- JSX
- Hello World
- Virtual DOM
JSX
- Not a template language (ie. handlebars, spacebars etc..)
- Alternate JS syntax
- Does a lot of string conversion
<div id="greeting-container" className="container">
<Greeting name="World"/>
</div>
Becomes:
React.createElement("div",
{
id: "greeting-container",
className: "container"
},
React.createElement(Greeting, {name: "World"})
)Hello World
<body>
<div id="content"></div>
<script type="text/jsx">
var CounterBox = React.createClass({
render: function () {
return (
<h1>Hello World</h1>
)
}
});
React.render(
<CounterBox />,
document.getElementById('content')
);
</script>
</body>-Local example-
Virtual DOM
All React elements are in-memory virtual representations of DOM elements. React uses this.state to register changes on certain elements. It then runs a diff between Virtual DOM elements, then pushes the changes to the DOM.
React Syntax
- React.createClass
- getInitialState
- componentDidMount
- componentWillUnmount
- setState
- React.renderComponent
- props
React.createClass
var TimerExample = React.createClass({
// Custom functions as well as basic components here
})Used to create a custom component (similar to an Angular directive) that is used to render elements, as well as contain logic, to the page.
getInitialState
var TimerExample = React.createClass({
getInitialState: function(){
return { elapsed: 0 };
}
})Called before the render function. The object that is returned is assigned to this.state.
componentDidMount
var TimerExample = React.createClass({
// Previous functions
componentDidMount: function(){
this.timer = setInterval(this.tick, 50);
}
})Called after the component has been rendered to the page.
componentWillunmount
var TimerExample = React.createClass({
componentWillUnmount: function(){
clearInterval(this.timer);
}
})
Called before the destroy functions get run on the component.
setState
this.setState({elapsed: new Date() - this.props.start});Used to keep track of variables/objects that are closely coupled with React display elements. Each call forces a component refresh.
render
var TimerExample = React.createClass({
// Previous functions
render: function() {
// Although we return an entire <p> element, react will smartly update
// only the changed parts, which contain the seconds variable.
return <p>This example was started <b>{seconds} seconds</b> ago.</p>;
}
})Called to render the component to the page.
React.renderComponent
React.renderComponent(
<TimerExample start={Date.now()} />,
document.body
);Used to initiate the rendering sequence for an element, as well as specifying where the element is getting injected.
props
<TimerExample start={Date.now()} count='1000'/>Variables passed to the React component are set on the props object that each React component has.
React's opinion of CSS
- “Begone, foul dwimmerlaik, lord of carrion! Leave the dead in peace!" - JRR
- Translation: Facebook strongly dislikes CSS
- https://facebook.github.io/react-native/docs/style.html#content
CSS (React Native)
- Declared as JS variables
- Set as inline by default
var styles = StyleSheet.create({
container: {
width: 38,
height: 38,
},
title: {
borderWidth: 2,
borderColor: '#00ff00',
},
description: {
fontSize: 18,
margin: 5,
color: '#656565'
}
});Ways of Applying CSS
- Regular inline
- Combining elements as an array
- Adding styles conditionally
<View style={styles.background} />
<View style={[styles.base, styles.background]} />
<View style={[styles.base, this.state.active && styles.active]} />Inheriting Styles
- Uses JS variables to pass styles to child elements
var List = React.createClass({
propTypes: {
style: View.propTypes.style,
elementStyle: View.propTypes.style,
},
render: function() {
return (
<View style={this.props.style}>
{elements.map((element) =>
<View style={[styles.element, this.props.elementStyle]} />
)}
</View>
);
}
});
// ... Render ...
<List style={styles.list} elementStyle={styles.listElement} />Flexbox
- http://codepen.io/dcurletti/pen/MweyGr
- https://css-tricks.com/snippets/css/a-guide-to-flexbox/
- We should consider using this for the new agent insights modules
Data Binding
- Two-way data binding is available in React (ReactLink), but discouraged
- Adding listeners and REACTing to the changed state are the preferred methods to dealing with REACTive data (jQuery style)
ReactLink (2-way Binding)
var WithLink = React.createClass({
mixins: [React.addons.LinkedStateMixin],
getInitialState: function() {
return {message: 'Hello!'};
},
render: function() {
return <input type="text" valueLink={this.linkState('message')} />;
}
});
LinkedStateMixin adds a method to your React component called linkState(), that in turn returns a ReactLink object which contains the current value of the React state and a callback to change it.
Non-Data Binding Method
var NoLink = React.createClass({
getInitialState: function() {
return {message: 'Hello!'};
},
handleChange: function(event) {
this.setState({message: event.target.value});
},
render: function() {
var message = this.state.message;
return <input type="text" value={message} onChange={this.handleChange} />;
}
});React Native
Developing for iOS
- Allows you to develop apps as if they were for the web
- When making changes to the view, you can simply refresh the UI, doesn't require re-compiling
- You can debug in Chrome
Gesture Handling
- TouchableHighlight
- Touchable
Testing
- "We don't have great test coverage yet, however, so most changes will still require significant manual verification..." - Official React Docs
Tests
- Jest tests, run through Node (Unit Tests)
- Integration tests are run through XCode
- Snapshot Testing- Tests that render the tested page and compare them to pre-rendered snapshots of how it should look.
Cons
- Testing framework not fully featured
- Re-write our entire front-end
- Not a framework- therefore requires Backbone or Flux for production
- If you want a custom Native UI element (directive), you have to write it in Object C
- React is not yet ready for Android (FB is hoping to release by EOY)
- Web/Native Hybrid
Pros
- Fast (Virtual DOM)
- ES 6
- Doesn't require learning Objective C or Swift
- (Relatively) future proof with FB backing
- Moving away from the DOM (like everyone else)
- Web/Native Hybrid
Unanswered Questions
- Load order of JS files
- Future android/iOS interoperability
- Future android/iOS syntax
My Opinion of React Native + RealScout
- If a team is available to work on it, YES ASAP
- If React might make its way to our web app, YES
- If we want to ship a new app ASAP, NO
- If we are looking for simple, cross native compatibility, NO
React Native
By Davide Curletti
React Native
- 1,096