diff options
| author | Andrej Mihajlov <and@mullvad.net> | 2018-07-18 12:56:12 +0200 |
|---|---|---|
| committer | Andrej Mihajlov <and@mullvad.net> | 2018-07-18 20:06:22 +0200 |
| commit | e6dc383704b1c7a6aff8abfad2bd5e2d948138cc (patch) | |
| tree | 0c2ffe951c376e0a0425119f99709945a92520f6 /app/components/Cell.js | |
| parent | 9f0ed3cc4878edac9aa8ae67fae366cb1d0bf588 (diff) | |
| download | mullvadvpn-e6dc383704b1c7a6aff8abfad2bd5e2d948138cc.tar.xz mullvadvpn-e6dc383704b1c7a6aff8abfad2bd5e2d948138cc.zip | |
- Reintegrate components/styled into components
- Drop styled/Button, use RX.Button instead and reset cursor when needed
- Scope AppButton and Cell to avoid class clash for Label and SubText
- Add missing cursor: default
Diffstat (limited to 'app/components/Cell.js')
| -rw-r--r-- | app/components/Cell.js | 120 |
1 files changed, 120 insertions, 0 deletions
diff --git a/app/components/Cell.js b/app/components/Cell.js new file mode 100644 index 0000000000..9f0efaab2c --- /dev/null +++ b/app/components/Cell.js @@ -0,0 +1,120 @@ +// @flow + +import * as React from 'react'; +import { Button, Text, Component, Types } from 'reactxp'; +import { colors } from '../config'; + +import { createViewStyles, createTextStyles } from '../lib/styles'; + +const styles = { + ...createViewStyles({ + cell: { + backgroundColor: colors.blue, + paddingTop: 14, + paddingBottom: 14, + paddingLeft: 16, + paddingRight: 16, + marginBottom: 1, + flex: 1, + flexDirection: 'row', + alignItems: 'center', + alignContent: 'center', + }, + cellHover: { + backgroundColor: colors.blue80, + }, + icon: { + color: colors.white60, + marginLeft: 8, + }, + }), + ...createTextStyles({ + label: { + color: colors.white, + alignSelf: 'center', + fontFamily: 'DINPro', + fontSize: 20, + fontWeight: '900', + lineHeight: 26, + flex: 1, + marginLeft: 8, + }, + subtext: { + color: colors.white60, + fontFamily: 'Open Sans', + fontSize: 13, + fontWeight: '800', + flex: 0, + textAlign: 'right', + }, + }), +}; + +export class SubText extends Text {} +export class Label extends Text {} + +type CellButtonProps = { + children?: React.Node, + disabled?: boolean, + cellHoverStyle?: Types.ViewStyle, + style?: Types.ViewStyle, +}; + +type State = { hovered: boolean }; + +export class CellButton extends Component<CellButtonProps, State> { + state = { hovered: false }; + + textStyle = (cellHoverStyle?: Types.ViewStyle) => (this.state.hovered ? cellHoverStyle : null); + iconStyle = (cellHoverStyle?: Types.ViewStyle) => (this.state.hovered ? cellHoverStyle : null); + subtextStyle = (cellHoverStyle?: Types.ViewStyle) => (this.state.hovered ? cellHoverStyle : null); + backgroundStyle = (cellHoverStyle?: Types.ViewStyle) => + this.state.hovered ? cellHoverStyle || styles.cellHover : null; + + onHoverStart = () => (!this.props.disabled ? this.setState({ hovered: true }) : null); + onHoverEnd = () => (!this.props.disabled ? this.setState({ hovered: false }) : null); + + render() { + const { children, style, cellHoverStyle, ...otherProps } = this.props; + return ( + <Button + style={[styles.cell, style, this.backgroundStyle(cellHoverStyle)]} + onHoverStart={this.onHoverStart} + onHoverEnd={this.onHoverEnd} + {...otherProps}> + {React.Children.map(children, (node) => { + if (React.isValidElement(node)) { + let updatedProps = {}; + + if (node.type.name === 'Label') { + updatedProps = { + style: [styles.label, node.props.style, this.textStyle(node.props.cellHoverStyle)], + }; + } + + if (node.type.name === 'Img') { + updatedProps = { + tintColor: 'currentColor', + style: [styles.icon, node.props.style, this.iconStyle(node.props.cellHoverStyle)], + }; + } + + if (node.type.name === 'SubText') { + updatedProps = { + style: [ + styles.subtext, + node.props.style, + this.subtextStyle(node.props.cellHoverStyle), + ], + }; + } + + return React.cloneElement(node, updatedProps); + } else if (node) { + return <Label style={[styles.label, this.textStyle()]}>{children}</Label>; + } + })} + </Button> + ); + } +} |
