Skip to content

Commit

Permalink
feat: 增加Drawer 抽屉组件, 优化 Modal 组件
Browse files Browse the repository at this point in the history
  • Loading branch information
lijinke666 committed Sep 4, 2018
1 parent d75ed28 commit f139bb6
Show file tree
Hide file tree
Showing 14 changed files with 1,424 additions and 32 deletions.
636 changes: 636 additions & 0 deletions components/drawer/__tests__/__snapshots__/index.test.js.snap

Large diffs are not rendered by default.

67 changes: 67 additions & 0 deletions components/drawer/__tests__/index.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
import React from 'react';
import { render, shallow, mount } from 'enzyme';
import assert from 'power-assert';
import toJson from 'enzyme-to-json';
import Drawer from '../index';

describe('<Drawer/>', () => {
it('should render a <Drawer/> components', () => {
const wrapper = render(
<div>
<Drawer title="基本使用" visible>
<span>基本使用</span>
</Drawer>
<Drawer title="基本使用" visible width={500}>
<span>无 footer</span>
</Drawer>
<Drawer title="基本使用" visible width={500} zIndex={9999}>
<span>无 footer</span>
</Drawer>
</div>
);
expect(toJson(wrapper)).toMatchSnapshot();
});

it('should can not clicked with set maskClosable false', () => {
const onCancelClick = jest.fn();
const wrapper = mount(
<Drawer visible={true} onCancel={onCancelClick}>
<span>关闭回调</span>
</Drawer>
);
wrapper.find('.cuke-drawer').simulate('click');
assert(wrapper.props().visible === true);
expect(onCancelClick).not.toHaveBeenCalled();
});

it('should render custom direction', () => {
const wrapper = mount(
<div>
<Drawer visible placement="left">
<span>关闭回调</span>
</Drawer>
<Drawer visible placement="top">
<span>关闭回调</span>
</Drawer>
<Drawer visible placement="right">
<span>关闭回调</span>
</Drawer>
<Drawer visible placement="bottom">
<span>关闭回调</span>
</Drawer>
</div>
);
expect(toJson(wrapper)).toMatchSnapshot();
});

it('should can trigger onClose event', () => {
const onCancelClick = jest.fn();
const wrapper = shallow(
<Drawer title="关闭回调" visible onClose={onCancelClick}>
<span>关闭回调</span>
</Drawer>
);
wrapper.find('.cuke-drawer').simulate('click');
expect(onCancelClick).not.toHaveBeenCalled();
});
});
136 changes: 136 additions & 0 deletions components/drawer/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,136 @@
import React, { PureComponent, Fragment } from 'react';
import PropTypes from 'prop-types';
import { createPortal } from 'react-dom'; //传送门 将节点挂载在root 节点之外
import cls from 'classnames';
import { CloseIcon } from '../icon';

const placements = ['right', 'top', 'bottom', 'left'];
export default class Drawer extends PureComponent {
state = {
init: false
};
static defaultProps = {
prefixCls: 'cuke-drawer',
visible: false,
getTargetAtNode: () => document.body,
title: '',
onClose: () => {},
maskClosable: true,
closable: true,
showMask: true,
width: 300,
zIndex: 999,
placement: placements[0]
};
static propTypes = {
title: PropTypes.oneOfType([PropTypes.string, PropTypes.object]),
content: PropTypes.oneOfType([PropTypes.string, PropTypes.object]),
confirmLoading: PropTypes.bool,
visible: PropTypes.bool,
closable: PropTypes.bool,
maskClosable: PropTypes.bool,
showMask: PropTypes.bool,
zIndex: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
width: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
placement: PropTypes.oneOf(placements),
getTargetAtNode: PropTypes.func,
onClose: PropTypes.func
};
constructor(props) {
super(props);
}
disableScroll = () => {
document.body.style.overflow = 'hidden';
//滚动条的宽度 防止鬼畜
document.body.style.paddingRight = '15px';
};
enableScroll = () => {
document.body.style.overflow = '';
document.body.style.paddingRight = 0;
};
componentWillReceiveProps({ visible }) {
if (visible === true) {
this.disableScroll();
this.setState({
init: true
});
} else {
this.enableScroll();
}
}
render() {
const {
prefixCls,
children,
title,
visible,
onClose,
className,
getTargetAtNode,
closable,
maskClosable,
showMask,
width,
zIndex,
placement,
style,
...attr
} = this.props;

const { init } = this.state;

const initModalAnimate = init
? { [`${prefixCls}-open`]: visible, [`${prefixCls}-close`]: !visible }
: { [`${prefixCls}-open`]: visible };

const initMaskAnimate = init
? {
[`${prefixCls}-mask-show`]: visible,
[`${prefixCls}-mask-hide`]: !visible
}
: { [`${prefixCls}-mask-show`]: visible };

const maskClickHandle = maskClosable ? { onClick: onClose } : {};

return createPortal(
<Fragment>
{showMask ? (
<div
className={cls(`${prefixCls}-mask`, initMaskAnimate)}
{...maskClickHandle}
/>
) : (
undefined
)}
<div role="dialog" tabIndex="-1" className={cls(`${prefixCls}-wrap`)}>
<div
className={cls(
prefixCls,
className,
initModalAnimate,
`${prefixCls}-${placement}`
)}
ref={node => (this.modal = node)}
style={{
...style,
width,
zIndex
}}
{...attr}
>
<section className={`${prefixCls}-header`}>
<h2 className={`${prefixCls}-title`}>{title}</h2>
{closable ? (
<CloseIcon className={`${prefixCls}-close`} onClick={onClose} />
) : (
undefined
)}
</section>
<section className={`${prefixCls}-content`}>{children}</section>
</div>
</div>
</Fragment>,
getTargetAtNode()
);
}
}
150 changes: 150 additions & 0 deletions components/drawer/styles.less
Original file line number Diff line number Diff line change
@@ -0,0 +1,150 @@
@import "../styles/vars.less";
@import "../styles/animate.less";
@import "../styles/mixins.less";

@prefixCls : cuke-drawer;

.@{prefixCls}{
pointer-events: auto;
background-color: @modal-bg-color;
z-index:@modal-z-index;
transform-origin: bottom center;
outline: none;
position: relative;
padding:0;
width: @cuke-drawer-width;
height: 100%;
list-style:none;
transform: scale(0);

&.@{prefixCls}-open{
pointer-events: auto;
}
&.@{prefixCls}-close{
pointer-events: none;
}

&-left {
top:0;
left:0;
&.@{prefixCls}-open{
animation: cuke-drawer-slide-in-left @cuke-drawer-animate-type forwards;
}
&.@{prefixCls}-close{
animation: cuke-drawer-slide-out-left @cuke-drawer-animate-type forwards;
}
}

&-right {
top:0;
right:-100%;
&.@{prefixCls}-open{
animation: cuke-drawer-slide-in-right @cuke-drawer-animate-type forwards;
}
&.@{prefixCls}-close{
animation: cuke-drawer-slide-out-right @cuke-drawer-animate-type forwards;
}
}

&-top {
top:0;
left:0;
width:100% !important;
height: @cuke-drawer-height;
&.@{prefixCls}-open{
animation: cuke-drawer-slide-in-top @cuke-drawer-animate-type forwards;
}
&.@{prefixCls}-close{
animation: cuke-drawer-slide-out-top @cuke-drawer-animate-type forwards;
}
}

&-bottom {
bottom:0;
left:0;
width:100% !important;
height: @cuke-drawer-height;
&.@{prefixCls}-open{
animation: cuke-drawer-slide-in-bottom @cuke-drawer-animate-type forwards;
}
&.@{prefixCls}-close{
animation: cuke-drawer-slide-out-bottom @cuke-drawer-animate-type forwards;
}
}

&-header{
padding: @modal-header-padding;
border-bottom:1px solid @border-color;
line-height: 40px;
text-align: center;
position: relative;
.@{prefixCls}-title{
font-size: @modal-title-font-size;
color:@font-color;
margin:0;
font-weight:500;
}
.@{prefixCls}-close{
position: absolute;
right: 20px;
top:13px;
cursor: pointer;
color: @modal-close-font-color;
font-size: @modal-close-font-size;
&,i{
transition:all .3s @animate-type;
}
&:hover{
transform: rotate(90deg);
&,i{
color:@primary-color;
}
}
}
}
&-content{
padding: @modal-padding;
background-clip: padding-box;
height: auto;
overflow-y: auto;
margin: 0 auto;
line-height: 1.5;
word-wrap: break-word;
max-height: 100vh;
}
}

.@{prefixCls}-wrap {
position: fixed;
overflow: auto;
left:0;
right:0;
bottom:0;
top:0;
z-index: @modal-z-index;
outline: 0;
pointer-events: none;
-webkit-overflow-scrolling: touch;
}

.@{prefixCls}-mask{
position: fixed;
background-color: @modal-mask-color;
left:0;
top:0;
bottom:0;
top:0;
width:100%;
height:100%;
z-index: @modal-z-index;
pointer-events: none;
transform: scale(0);
&-show{
pointer-events: auto;
animation: cuke-mask-fade-in @default-transition forwards;
}
&-hide {
pointer-events: none;
animation: cuke-mask-fade-out @default-transition forwards;
}
}
2 changes: 1 addition & 1 deletion components/dropdown/__tests__/index.test.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import React from 'react';
import assert from 'power-assert';
import { render, mount, shallow } from 'enzyme';
import { render, shallow } from 'enzyme';
import toJson from 'enzyme-to-json';
import Dropdown from '../index';

Expand Down
1 change: 0 additions & 1 deletion components/dropdown/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,6 @@ export default class Dropdown extends PureComponent {
static propTypes = {
prefixCls: PropTypes.string.isRequired,
onVisibleChange: PropTypes.func,
animating: PropTypes.bool,
trigger: PropTypes.oneOf(Object.values(triggerTypes)),
animate: PropTypes.oneOf(animateType),
overlay: PropTypes.oneOfType([
Expand Down
1 change: 1 addition & 0 deletions components/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,3 +21,4 @@ export { default as backTop } from "./backTop";
export { default as Tabs } from "./tabs";
export { default as Badge } from "./badge";
export { default as Dropdown } from "./dropdown";
export { default as Drawer } from "./drawer";
Loading

0 comments on commit f139bb6

Please sign in to comment.