blob: e2743c9f5d80bd03e42b75ed5eda6e2478df491b [file] [log] [blame]
/**
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import * as React from "react";
import { SFC } from "react";
import styled from "styled-components";
import { get } from "../../../utils/theme";
import { mq } from "../../../styles/responsive";
const OpenProps = {
opened: true
};
const IconFirst = p => (!p.opened ? "0px" : "10px");
const IconMiddle = p => (!p.opened ? "1" : "0");
const IconLast = p => (!p.opened ? "0px" : "-6px");
const IconRotate = p => (!p.opened ? "0deg" : "45deg");
const Icon = styled.div`
position: relative;
width: 23px;
height: 32px;
transform: translateX(${p => (p.opened ? "-2px" : "-1px")})
translateY(${p => (p.opened ? "0" : "2px")})
scale(${p => (p.opened ? 0.8 : 1)});
`;
Icon.defaultProps = OpenProps;
const sidebarBg = get("colors.sidebarBg");
const sidebarPrimary = get("colors.sidebarPrimary");
const sidebarText = get("colors.sidebarText");
const primaryColor = get("colors.primary");
const backgroundColor = get("colors.background");
const textColor = get("colors.text");
const IconLine = styled.span`
content: "";
display: block;
position: absolute;
width: 100%;
height: 2px;
left: 0;
right: 0;
background: ${p => (p.opened ? sidebarText(p) : textColor(p))};
transition: transform 0.3s, opacity 0.3s;
&:nth-of-type(1) {
top: -2px;
transform: translateY(${IconFirst}) rotate(${IconRotate});
}
&:nth-of-type(2) {
top: 6px;
opacity: ${IconMiddle};
}
&:nth-of-type(3) {
top: 14px;
transform: translateY(${IconLast}) rotate(-${IconRotate});
}
`;
IconLine.defaultProps = OpenProps;
const translateX = p => (!p.opened ? "10px" : "-6px");
const translateY = p => (!p.opened ? "4px" : "0px");
const radii = get("radii");
const ToggleButton = styled.button`
cursor: pointer;
z-index: 99;
position: absolute;
display: flex;
align-items: center;
justify-content: center;
padding: 5px 6px;
width: 33px;
height: 30px;
top: ${p => (p.opened ? "3px" : "2px")};
right: ${p => (p.opened ? "-39px" : "-27px")};
transform: translateX(${translateX}) translateY(${translateY});
transition: transform 0.3s;
outline: none;
border: none;
background: ${p => (p.opened ? sidebarBg(p) : backgroundColor(p))};
border-radius: ${p => (p.opened ? `0 0 ${radii(p)} 0` : `${radii(p)}`)};
&:before {
position: absolute;
content: "";
top: -3px;
left: 0;
width: calc(100% + 1px);
height: ${p => (p.opened ? "3px" : 0)};
background: ${p => sidebarPrimary(p) || primaryColor(p)};
}
${mq({
display: ["block", "block", "block", "none"]
})};
`;
ToggleButton.defaultProps = OpenProps;
// interface HamburgerProps extends OpenProps {
// onClick: (ev: React.SyntheticEvent<any>) => void
// }
const HamburgerProps = Object.assign({}, OpenProps, {
onClick: ev => null
});
export const Hamburger = ({ opened, onClick }) => (
<ToggleButton opened={opened} onClick={onClick}>
<Icon opened={opened}>
<IconLine opened={opened} />
<IconLine opened={opened} />
<IconLine opened={opened} />
</Icon>
</ToggleButton>
);