Skip to content

Component

Joel Besada edited this page Feb 28, 2018 · 3 revisions

Component is a wrapper component for taking data from the global state and providing it as props to the child component(s). The Tide Component keeps tracks of changes in the listened to state, and re-renders the child whenever necessary. This way the child component can be kept as a pure react component, only rendering from the props it receives.

import {Component as TideComponent} from 'tide'

class App extends React.Component {
    render() {
      return (
        <div className='app'>
          <TideComponent todos={['todos']}>
            {props => <TodoList {...props} />}
          </TideComponent>
        </div>
      )
    }
}

The todos property given to the Tide Component above is an array specifying a path in the global state, which will be used with the Immutable getIn method to retrieve the data. The child TodoList component will receive the data in this.props.todos.

Instead defining key paths with ['nested', 'path'], you can also use dot notation: 'nested.path'. Alternatively, you can pass a function that creates the key path:

<TideComponent todoItem={(state, options) => ['todos', state.get('activeTodoItem')]}>
  {props => <TodoItem {...props} />}
</TideComponent>

The function is called with two arguments:

  • state: The global Tide state.
  • options: An options object defined by setting a tideOptions prop on TideComponent. This will be available to all children in the subtree of the component.

Wrapped Classes

As an alternative to using Component to send down props to a rendered child component, you can also define the child component class to automatically be wrapped within a Component with the given key paths. This is done using the Tide.wrap method:

import {wrap} from 'tide'

const ChildComponent = React.createClass(...)

export default wrap(ChildComponent, {data: 'path.to.data'})

This can then be rendered simply as:

render() {
  return (
    <div className='parent-component'>
      <ChildComponent otherProp={true}/>
    </div>
  )
}

Which is equivalent to the following (not using Tide.wrap):

import {Component as TideComponent} from 'tide'

render() {
  return (
    <div className='parent-component'>
      <TideComponent data='path.to.data'>
        {props => <ChildComponent {...props} otherProp={true}/>}
      </TideComponent>
    </div>
  )
}

Additional Child Properties

The Tide Component wrapper will send down one extra property to the child - this.props.tide - which includes a number of nested properties.

tide.actions

All of the registered actions on the tide instance. Your TodoActions added with tide.addActions('todo', TodoActions) will be available in this.props.tide.actions.todo.

tide.keyPaths

All of the used key paths to define the properties used from the global state. These are useful when nesting even further into the state object in the children of this component, such as when rendering items from a list:

class TodoList extends React.Component {
  renderTodos() {
    const {todos, tide} = this.props
    // Todos given from <Tide todos={['todos']}/>
    return todos.map((item, index) => (
      <Tide
        key={item.get('id')}
        todo={tide.keyPaths.todos.contact([index])}
      >
        {props => <TodoItem {...props} />}
      </Tide>
    ))
  }
}

This gives each todo item in the list its own cursor, and when that particular todo in the list updates the item will re-render, without triggering re-renders in all of the other untouched items in the list.

Component Properties

impure

A boolean indicating whether the component is impure or not. A pure component (where impure is not set) will only re-render whenever any of the global state that it listens to changes, regardless of any external changes to the children or re-renders further up the tree. To change the component to always re-render, set impure to true:

<Tide impure foo={['bar']}>
  {props => <Child {...props} />}
</Tide>

However, before doing this you should first consider if all of the data that the component renders from could live in the global state instead.

Clone this wiki locally