import * as React from 'react' import * as cx from 'classnames' import { sum } from 'lodash' import { connect } from 'react-redux' import { Column } from '../flex' import { Row } from '../flex' import { StylableComponent } from '../theme' import { childrenChanged, forceArray } from '../../utils' import { panelInit, panelDestroy, panelResizeStart, panelResize, panelResizeStop, } from './actions' import { getPanelById } from './selectors' import { PanelComponentProps, PanelProps } from './interfaces' class Component extends StylableComponent { private container: HTMLDivElement public componentWillMount() { this.props.panelInit(this.props.id, this.props.defaultIntervals) } public componentWillUnmount() { // this.props.panelDestroy(this.props.id) } public render(): JSX.Element { return (
{this.childNodes()}
) } private childNodes(): JSX.Element[] { const children = (forceArray(this.props.children) as JSX.Element[]) .filter(Boolean) .map((child: JSX.Element, idx: number) =>
{child}
, ) .reduce( (acc: JSX.Element[], child: JSX.Element, idx: number) => [ ...acc, child, , ], [], ) // TODO: Ew. return children.slice(0, children.length - 1) } private intervals(): number[] { const { panel } = this.props if (!panel) return this.props.defaultIntervals return panel.intervals } private setContainerRef = (ref: HTMLDivElement) => { this.container = ref } private mkHandleStartResizing = (idx: number) => (e: React.MouseEvent) => { e.preventDefault() e.stopPropagation() this.props.panelResizeStart( this.props.id, idx, ) } private getPercentage(e: React.MouseEvent): number { const cursorPosition = this.layout(e.clientX, e.clientY) const rect = this.container.getBoundingClientRect() const size = this.layout(rect.width, rect.height) const intervals = this.intervals() const adjustedPos = cursorPosition - this.layout(rect.left, rect.top) return 100 * (adjustedPos / size) } private handleMouseMove = (e: React.MouseEvent) => { const { panel } = this.props if (!panel || !panel.dragging) return false const { idx } = panel const intervals = this.intervals() const beforeIntervals = intervals.slice(0, idx) const afterIntervals = intervals.slice(idx + 2, intervals.length) const relevantIntervals = intervals.slice(idx, idx + 2) const [a, b] = relevantIntervals const nextA = this.getPercentage(e) - sum(beforeIntervals) const nextB = 100 - (nextA + sum(afterIntervals) + sum(beforeIntervals)) const nextIntervals = [...beforeIntervals, nextA, nextB, ...afterIntervals] this.props.panelResize(this.props.id, nextIntervals) } private handleStopResizing = (e: React.SyntheticEvent) => { e.stopPropagation() const { panel } = this.props if (!panel || !panel.dragging) return false this.props.panelResizeStop(this.props.id) } private layout = (columns: any, rows: any): any => this.props.layout === 'columns' ? columns : rows } const separatorWidth = (width: number | undefined) => `${width !== undefined ? width : 3}px` const Separator = ({ layout, onMouseDown, width }: any) =>
const mapStateToProps = (state: any, ownProps: PanelProps) => ({ ...ownProps, panel: getPanelById(state, ownProps.id), }) const mapDispatchToProps = { panelInit, panelDestroy, panelResizeStart, panelResize, panelResizeStop, } export const Panel = connect(mapStateToProps, mapDispatchToProps)(Component)