import * as React from "react"; import { css, cx } from "emotion"; import { StepperProps, StepperState } from "./typings/Stepper"; import Button from "./Button"; import { activeDotStyle, contentWrapper, dotStyle, footerStyle, headingStyle, headSection, headStyle, stepperLineStyle } from "./styles/Stepper.styles"; import { colors } from "pebble-shared"; function noop() {} class Stepper extends React.PureComponent { static defaultProps: Partial = { allowSkip: true, cancelLabel: "Cancel", nextLabel: "Next", prevLabel: "Prev", doneLabel: "Done", onBeforeNext: () => true, onBeforePrev: () => true, onChange: () => {}, onCancel: () => {}, onDone: () => {}, renderFooterElement: ({ leftButtonData, rightButtonData }, props) => { return (
); } }; state: StepperState = { active: this.props.initialSelectedIndex || 0 }; private goToNextPage = async () => { const { onBeforeNext, data } = this.props; const allow = await onBeforeNext(this.state.active); if (allow) this.goToPage(Math.min(data.length - 1, this.state.active + 1)); }; private goToPrevPage = async () => { const allow = await this.props.onBeforePrev(this.state.active); if (allow) this.goToPage(Math.max(0, this.state.active - 1)); }; private goToPage = (index: number): void => { const prev = this.state.active; this.setState( { active: index }, () => this.props.onChange({ prev, current: this.state.active }) ); }; private getHeadings = (): string[] => { const { headingExtractor, data } = this.props; return data.map(datum => headingExtractor({ item: datum })); }; private getLeftButtonData = () => { const { cancelLabel, prevLabel, onCancel } = this.props; return this.state.active === 0 ? { label: cancelLabel, action: onCancel } : { label: prevLabel, action: this.goToPrevPage }; }; private getRightButtonData = () => { const { nextLabel, onDone, data, doneLabel } = this.props; return this.state.active === data.length - 1 ? { label: doneLabel, action: onDone } : { label: nextLabel, action: this.goToNextPage }; }; render() { const { data, renderContentElement, keyExtractor, renderFooterElement, className, allowSkip } = this.props; const { active } = this.state; const args = { goToNext: this.goToNextPage, goToPage: this.goToPage, goToPrev: this.goToPrevPage, leftButtonData: this.getLeftButtonData(), rightButtonData: this.getRightButtonData() }; return (
{this.getHeadings().map((heading, i) => { const dotClass = cx(dotStyle, { [activeDotStyle]: i <= active }); const headingColor = i === active ? colors.violet.base : allowSkip ? colors.gray.base : undefined; return (
this.goToPage(i) : noop} >
{heading}
); })}
{data.map((datum, i) => (
{renderContentElement({ item: datum, isSelected: i === this.state.active, ...args })}
))} {renderFooterElement( { activeIndex: this.state.active, ...args }, this.props )}
); } } export default Stepper;