# React for Beginners * Video course: ## Video 1: Tooling * create-react-app * use Webpack * Sublime editor * React dev tools ## Video 2: Thinking and Understanding React Components * * React applications are split into components which share information over different ways like state and properties. ## Video 3: Our First React Component * Write first component ```javascript // MyComponent.js import React from 'react' class MyClass extends React.Component { render ( return(
) ) } export default MyClass ``` * Render it on the HTML ```javascript // index.js import React from 'react' import { render } from 'react-dom' import MyComponent from './MyComponent' render(, document.getElementById('main')) ``` * `$r` allows access to the react object from the console. ## Video 4: Write HTML with JSX * You can write HTML code directly in return functions within parentheses. * Wes blog post about how to use Emmet in babel * need to replace `class` tags with `className`, because class is sth different in JS * Can only return one parent element (need to wrap the children) * HTML comments have to be inside `{/**/}` in JSX **and** inside parent element. ## Video 5: CSS * Can be in HTML head * Can also be included with ```javascript import './style.css' ``` * Processed by Webpack ## Video 6: Create Application Layout with Components * decide how to organize the app with sub-components ## Video 7: Passing Dynamic Data with props * add attributes to components ```javascript ``` * access variables via props ```javascript class MyComponent extends React.Component { render( return(

{this.props.myProp}

{this.props.myObj}

{this.props.onClick}

) ) } ``` ## Video 8: Stateless Functional Components * If component has just a return function, you can use a stateless functional component * replace `class MyClass ...` with ```javascript const MyFunction = (props) => { return(

{props.myProp}<\/p>

{props.myObj}<\/p>

{props.onClick}<\/p> ) } ``` ## Video 9: Routing with React Router * Don't render component directly, but router ```javascript // index.js import { BrowserRouter, Match, Miss } from 'react-router' const Root = () => { return ( <\/BrowserRouter> ) } render(, document.getElementById('main')) ``` * (Video 18): the `:myarg` will be available as `this.props.params.myarg` ## Video 10: Helper and Utility Functions * Organize helper functions in separate files. ## Video 11: Working with React Events * Works as regular JS events, but adds cross-browser compatibility * Think about what event to handle * Think about, at what level the event should be handeled and pass the function down to the component via props. * Reference form elements as follows: ```javascript { this.whateverName = input }} ``` * now you can access it through `this`. * You have to bind `this` in functions other than render * See this example with event handling: ```javascript class MyClass extends React.Component { constructor () { super() this.myFunction = this.myFunction.bind('this') } myFunction (event) { this.nowAvailable('!!!') event.preventDefault() } render () { return (

test<\/p>

{this.myFunction(e)}}>test<\/p> or

test<\/p> Needs constructor hack ) } } ``` ## Video 12: * [React Router Documentation](https://github.com/ReactTraining/react-router/tree/master/docs) * Use context types: ```javascript // MyComponent.js MyComponent.contextTypes = { router: React.PropTypes.object } ``` * This gives access to these functions: - `blockTransitions` - `createHref` - `replaceWith` - `transitionTo` * Usage: ```javascript this.context.router.transitionTo('...') ``` ## Video 13: Understanding State * Whenever you want to change anything on your page, you change the state data instead. * Put the state on the main parent component * Initialize with ```javascript class App extends React.Component { constructor () { super() this.state = { child1state = {}, child2state = {}, } } render ( return ( ... ) ) } ``` * When changing the state, you must avoid race conditions. Follow this scheme: - make a copy of the state - update the copy - set the state with copy ```javascript class App extends React.Component { constructor () { super() this.addChild1StateElement = this.addChild1StateElement.bind(this) } addChild1StateElement (elem) { const child1state = { ...this.state.child1state } child1state['new-item'] = elem this.setState({ child1state }) } render ( ) } ``` * Create state manipulating functions on the main component and pass it to the children through props. ## Video 14: Loading Data Into State On Click * Can be used to load an initial object to the state. ## Video 15: Displaying State with JSX * Dynamically generate HTML tags based on state data * React recognizes state changes and re-renders the data * Example for ```javascript ... render () { return (

    {Object.keys(this.state.child1state).map(key => )} <\/ul> ) } ... ``` * each element in a loop needs a `key` attribute, so React can keep track! * if you pass down `key` itself, use a different name, e.g. `index`! * use data massaging to extract variables for easier access ```javascript const { details } = this.props ``` ## Video 16: Updating Order State * emphasizing **if you pass down `key` itself, use a different name, e.g. `index`!** ## Video 17: Displaying Order State * Use `Object.keys(...).reduce((prevValue, key)=>{...}, initValue)` to make a scalar of an object. * Don't forget to check is elements are valid (can change in real-time). ## Video 18: Persisting State with Firebase * Uses 're-base' to sync state with firebase web app * [React component lifecycle explained](https://facebook.github.io/react/docs/state-and-lifecycle.html) * use `componentWillMount()` to sync the state before the component loads. * this way, the component will render only once. * How to use react-router parameters * use `componentWillUnmount()` to stop syncing with the database. ## Video 19: Persisting Order with localstorage * Uses cookies to store data locally * use `componentWillUpdate(nextProps, nextState)` in this case, because it is called every time state or props is updated. ```javascript ... componentWillMount () { const localStorageRef = localStorage.getItem('mykey') if (localStorage) { this.setState({ order: JSON.parse(localStorageRef) }) } } componentWillUpdate () { localStorage.setItem('mykey', JSON.stringify(nextState.mykey)) } ... ``` * use `shouldComponentUpdate()` to check data before it is rendered. Returns true if component should be re-rendered or false if not. ## Video 20: Bi-directional Data Flow and Live State Editing * When you write forms, * You can used computed properties ```javascript ... handleChange (event, key) { const prev = this.props.prevs[key] const next = { ...prev, [event.target.name]: event.target.value } this.setState(next) } render () { return ( this.handleChange(event, key)} \/> ) } ... ``` ## Video 21: Removing Items From State * CRUD - Create Read Update Delete * `child1state[key] = null` is required by Firebase. Otherwise, `delete child1state[key]` is also possible ```javascript ... deleteElement (key) { const child1state = { ...this.statte.child1state } child1state[key] = null this.setState({ child1state }) } ... ``` * You can store JSX in a variable. ## Video 22: Animating React Components * use npm package concurrently to concurrently start npm scripts * use CSSTransitionGroup from 'react-addons-css-transition-group' * adds and removes again classes to animated items * class items can be styled with CSS * replace parent element of animation - e.g. `
      ` becomes `` ```stylus .mytrans background blue max-height 0px transition all 0.5s transform translateX(-120%) ... &.order-enter-active background yellow max-height auto transform translateX(0) ``` * The time in transitionEnterTimeout should match the `transition all <>s` * There are three actions: - enter - leave - appear ## Video 23: Component Validation with PropTypes * When sharing components with other people, use PropTypes to declared what needs to be passed to them. ```jsx const Header = function() {...} Header.propTypes = { tagline: React.PropTypes.string.isRequired } ``` ## Video 24: Authentication ## Video 25: Building React for Production * If you start with create-react-app, you can use `npm build` * creates optimized js and css files in the `build` folder. * when you deploy, you need to catch the URL routing and let react-router handle URLs. * otherwise, on reloads serving index.html will fail. ## Video 28: Deploying to Apache Server * Depending whether you run from the root or a subdirectory, you need to specify `` or not. * You also neet to specify this in package.json under "homepage" * Put the files on the server * in .htaccess define ``` RewriteBase / RewriteRule ^index\.html$ - [L] RewriteCond %{REQUEST_FILENAME} !-f RewriteCond %{REQUEST_FILENAME} !-d RewriteRule . /index.html [L] ```