Created
December 10, 2015 12:08
-
-
Save micahnz/bcd25a70229355460171 to your computer and use it in GitHub Desktop.
example using reselect
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/// <reference path="../../typings/tsd.d.ts" /> | |
import * as React from 'react'; | |
import {Component, PropTypes} from 'react'; | |
import {connect} from 'react-redux'; | |
import {bindActionCreators} from 'redux'; | |
import {createSelector} from 'reselect'; | |
import * as ReactPureRenderMixin from 'react-addons-pure-render-mixin'; | |
import * as Immutable from 'immutable'; | |
// | |
import * as _ from 'lodash'; | |
// actions | |
import {push} from '../actions/router'; | |
import {toggleFlowManagerView} from '../actions/ui'; | |
// material-ui components | |
import {AppBar, IconButton, LeftNav, ToolbarGroup} from 'material-ui'; | |
// material icons | |
let ActionViewList = require('react-material-icons/icons/action/view-list'); | |
let ActionViewModule = require('react-material-icons/icons/action/view-module'); | |
let NavigationMenuIcon = require('react-material-icons/icons/navigation/menu'); | |
// | |
export class Viewport extends Component<any, any> { | |
static mixins = [ReactPureRenderMixin]; | |
refs: { | |
leftNav:any | |
}; | |
onLeftNavChange() { | |
let {push} = this.props.actions; | |
push('/'); | |
} | |
onToggleViewClick() { | |
let {toggleFlowManagerView} = this.props.actions; | |
toggleFlowManagerView(); | |
} | |
onMenuButtonClick() { | |
this.refs.leftNav.toggle(); | |
} | |
getStyles() { | |
return { | |
root: { | |
}, | |
appBar: { | |
root: { | |
transition: "top 300ms", | |
position: "fixed", | |
zIndex: 10, | |
top: "0px", | |
left: "0px", | |
width: "100%" | |
}, | |
fullView: { | |
transition: "opacity 300ms", | |
textAlign: "center", | |
opacity: 1, | |
top: "0px" | |
}, | |
compactView: { | |
root: { | |
position: "absolute", | |
zIndex: 10, | |
top: "8px", | |
left: "8px" | |
}, | |
logo: { | |
display: "inline-block", | |
position: "relative", | |
height: "24px", | |
top: "4px" | |
} | |
} | |
}, | |
childCt: { | |
transition: "padding-top 300ms", | |
paddingTop: "64px" | |
}, | |
leftNav: { | |
zIndex: 100 | |
} | |
} | |
} | |
renderAppBar() { | |
let {appBarViewMode, flowManagerViewMode} = this.props; | |
let logo = "/themes/default/images/logo-light.png"; | |
let styles = this.getStyles(); | |
// | |
let onMenuButtonClick = this.onMenuButtonClick.bind(this); | |
let onToggleViewClick = this.onToggleViewClick.bind(this); | |
// animate to compact view | |
if (appBarViewMode === 'compact') { | |
logo = "/themes/default/images/logo-dark.png"; | |
// reduce appbar width for compact mode | |
styles.appBar.root.width = "166px"; | |
// fadeout and hide the full appbar | |
styles.appBar.fullView.transition = "opacity 300ms, top 0ms 300ms"; | |
styles.appBar.fullView.top = "-64px"; | |
styles.appBar.fullView.opacity = 0; | |
} | |
else if (appBarViewMode === 'hidden') { | |
styles.appBar.root.top = "-64px"; | |
} | |
let btnColor = (appBarViewMode === 'compact') | |
? "black" | |
: "white"; | |
// | |
let iconElementLeft = ( | |
<IconButton onClick={onMenuButtonClick}> | |
<NavigationMenuIcon color={btnColor} /> | |
</IconButton> | |
); | |
let viewModeIcon = (flowManagerViewMode === 'list') | |
? <ActionViewModule color={btnColor}/> | |
: <ActionViewList color={btnColor} />; | |
let iconElementRight = ( | |
<IconButton onClick={onToggleViewClick}> | |
{viewModeIcon} | |
</IconButton> | |
); | |
return ( | |
<div style={styles.appBar.root}> | |
<AppBar ref="appBar" style={styles.appBar.fullView} iconElementRight={iconElementRight}/>, | |
<div style={styles.appBar.compactView.root}> | |
{iconElementLeft} | |
<img style={styles.appBar.compactView.logo} src={logo} /> | |
</div> | |
</div> | |
); | |
} | |
render() { | |
let {appBarViewMode, leftNavMenuItems} = this.props; | |
let styles = this.getStyles(); | |
leftNavMenuItems = leftNavMenuItems.toJS(); | |
if (appBarViewMode !== "full") { | |
styles.childCt.paddingTop = "0px"; | |
} | |
// | |
let onLeftNavChange = this.onLeftNavChange.bind(this); | |
console.log('render viewport'); | |
return ( | |
<div style={styles.root}> | |
<LeftNav style={styles.leftNav} ref="leftNav" docked={false} menuItems={leftNavMenuItems} | |
onChange={onLeftNavChange} /> | |
{this.renderAppBar()} | |
<div style={styles.childCt}> | |
{this.props.children} | |
</div> | |
</div> | |
); | |
} | |
} | |
// map state to props using a selector | |
export const selector = createSelector( | |
[ | |
state => state.getIn(['ui', 'appBar', 'viewMode']), | |
state => state.getIn(['ui', 'flowManager', 'viewMode']), | |
state => state.getIn(['ui', 'leftNav', 'menuItems']) | |
], | |
(appBarViewMode, flowManagerViewMode, leftNavMenuItems) => { | |
return { | |
appBarViewMode, | |
flowManagerViewMode, | |
leftNavMenuItems | |
} | |
} | |
); | |
// map and bind dispatchable actions to props | |
export const actions = (dispatch, props) => { | |
return { | |
actions: bindActionCreators( | |
{ | |
push, | |
toggleFlowManagerView | |
}, | |
dispatch | |
) | |
}; | |
}; | |
// connect component to redux store | |
export default connect(selector, actions)(Viewport); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment