import React from 'react';
import noop from 'lodash/noop';
import get from 'lodash/get';
import { CanvasStateProvider } from 'redhotmagma-graphics-editor/CanvasInterface/CanvasProvider';

import IconDelete from '@material-ui/icons/Delete';
import IconRotate from '@material-ui/icons/RotateRight';
import IconScale from '@material-ui/icons/UnfoldMore';

import Designer from './Designer';
import AddVisualElement from './Containers/AddVisualElement';
import withWidth, { isWidthUp } from '@material-ui/core/withWidth';

import { getConf } from 'App/configuration';
import PropTypes from 'prop-types';
import Typography from '@material-ui/core/Typography';
import { useSelector } from 'react-redux';
import { getSelectedDesignProductionMethod } from '../../Reducers/DesignArea/Selectors';
import StandardToolboxPortal from './MultilayerComponents/StandardToolboxPortal';
import InlineToolboxPortal from './MultilayerComponents/InlineToolboxPortal';

const StandardToolboxWithCanvasState = withWidth({ initialWidth: window.innerWidth > 730 ? 'sm' : 'xs' })(
    ({ width }) =>
        isWidthUp('sm', width) && ( // desktop only, for mobile it's rendered in the sidebar, see Screen.js
            <div className="noShrink" style={{ paddingTop: 8, pointerEvents: 'none', position: 'relative' }}>
                <AddVisualElement />
            </div>
        )
);

const renderStandardToolbox = ({ visualizationOverlayMode } = {}) => ({
    upload,
    components: { StandardToolbox },
}) => {
    const ContainerComponent = visualizationOverlayMode ? StandardToolboxPortal : React.Fragment;
    return (
        <ContainerComponent>
            <StandardToolbox {...{ upload }}>
                {({ canvas }) => (
                    <CanvasStateProvider canvas={canvas}>
                        <StandardToolboxWithCanvasState canvas={canvas} />
                    </CanvasStateProvider>
                )}
            </StandardToolbox>
        </ContainerComponent>
    );
};

const toolboxButtonStyle = {
    width: 40,
    height: 40,
    padding: 0,
    border: '1px solid rgba(0,0,0,0.23)',
    boxSizing: 'border-box',
    borderRadius: 3,
    background: 'white',
    outline: 0,
    cursor: 'pointer',
    display: 'flex',
    justifyContent: 'center',
    color: '#282828',
};
const transformTopRight = { transform: 'translate(0%, -100%)' };
const transformBottomRight = { transform: 'translate(0%, 0%)' };
const transformBottomLeft = { transform: 'translate(-100%, 0%)' };

const renderInlineToolButton = ({
    positionName,
    onScalingChange,
    onRotationChange,
    onDeleteClick,
    selectedObject,
    components: { InlineToolboxButton },
}) => {
    if (!selectedObject) {
        return null;
    }
    switch (positionName) {
        case 'topRight':
            return (
                !selectedObject.locked && (
                    <InlineToolboxButton
                        style={{ ...toolboxButtonStyle, ...transformTopRight }}
                        onTouchStart={onRotationChange}
                        onMouseDown={onRotationChange}
                    >
                        <IconRotate style={{ alignSelf: 'center' }} />
                    </InlineToolboxButton>
                )
            );
        case 'bottomRight':
            return (
                !selectedObject.locked && (
                    <InlineToolboxButton
                        style={{ ...toolboxButtonStyle, ...transformBottomRight }}
                        onTouchStart={onScalingChange}
                        onMouseDown={onScalingChange}
                    >
                        <IconScale style={{ transform: 'rotate(-45deg)', alignSelf: 'center' }} />
                    </InlineToolboxButton>
                )
            );
        case 'bottomLeft':
            return (
                <InlineToolboxButton
                    style={{ ...toolboxButtonStyle, ...transformBottomLeft }}
                    onClick={onDeleteClick}
                >
                    <IconDelete style={{ alignSelf: 'center' }} />
                </InlineToolboxButton>
            );
        case 'topLeft':
            // not used
            return null;
    }
};

const AngleLabel = ({ angleLabel }) => {
    const isLocked = useSelector(state =>
        get(getSelectedDesignProductionMethod(state), 'designElementsLocked')
    );
    return !isLocked && <Typography>{angleLabel}</Typography>;
};
AngleLabel.propTypes = {
    angleLabel: PropTypes.node,
};

const renderAngleLabel = angleLabel => {
    return <AngleLabel angleLabel={angleLabel} />;
};

const ChildrenOnlyFragment = ({ children }) => <>{children}</>;
ChildrenOnlyFragment.propTypes = {
    children: PropTypes.node,
};

const renderInlineToolbox = ({ visualizationOverlayMode }) => ({ components: { InlineToolbox } }) => (
    <InlineToolbox
        renderToolboxButton={renderInlineToolButton}
        renderAngleLabel={renderAngleLabel}
        ContainerComponent={visualizationOverlayMode ? InlineToolboxPortal : ChildrenOnlyFragment}
    />
);

renderInlineToolButton.propTypes = {
    positionName: PropTypes.string,
    onScalingChange: PropTypes.func,
    onRotationChange: PropTypes.func,
    onDeleteClick: PropTypes.func,
    components: PropTypes.element,
};
renderInlineToolbox.propTypes = {
    components: PropTypes.element,
};

export const DefaultDesigner = ({ visualizationOverlayMode, ...props }) => {
    return (
        <Designer
            renderStandardToolbox={renderStandardToolbox({ visualizationOverlayMode })}
            renderSelectionToolbox={() => null /*disable the default*/}
            renderInlineToolbox={renderInlineToolbox({ visualizationOverlayMode })}
            renderRulers={getConf('displayEditorRulers', true) ? null : noop}
            fillContainer
            {...props}
        />
    );
};

DefaultDesigner.propTypes = {
    visualizationOverlayMode: PropTypes.bool.isRequired,
};
