sorry,rebuild folder structure,cry..

This commit is contained in:
zuiidea
2017-03-21 16:43:14 +08:00
parent 30141661c2
commit 3585852fff
68 changed files with 250 additions and 209 deletions
@@ -39,8 +39,7 @@ const leaveAnim = [
},
]
const TableBodyWrapper = ({ body, page = 1, current }) => {
// 切换分页去除动画;
const AnimTableBody = ({ body, page = 1, current }) => {
if (current !== +page) {
return body
}
@@ -58,10 +57,10 @@ const TableBodyWrapper = ({ body, page = 1, current }) => {
)
}
TableBodyWrapper.propTypes = {
AnimTableBody.propTypes = {
body: PropTypes.element,
page: PropTypes.any,
current: PropTypes.number.isRequired,
}
export default TableBodyWrapper
export default AnimTableBody
+1 -1
View File
@@ -1,5 +1,5 @@
{
"name": "table",
"name": "DataTable",
"version": "0.0.0",
"private": true,
"main": "./DataTable.js"
@@ -4,7 +4,8 @@ import { Dropdown, Button, Icon, Menu } from 'antd'
const DropOption = ({ onMenuClick, menuOptions = [], buttonStyle, dropdownProps }) => {
const menu = menuOptions.map(item => <Menu.Item key={item.key}>{item.name}</Menu.Item>)
return (<Dropdown
overlay={<Menu onClick={onMenuClick} {...dropdownProps}>{menu}</Menu>}
overlay={<Menu onClick={onMenuClick}>{menu}</Menu>}
{...dropdownProps}
>
<Button style={{ border: 'none', ...buttonStyle }}>
<Icon style={{ marginRight: 2 }} type="bars" />
+6
View File
@@ -0,0 +1,6 @@
{
"name": "DropOption",
"version": "0.0.0",
"private": true,
"main": "./DropOption.js"
}
+14
View File
@@ -0,0 +1,14 @@
import React, { PropTypes } from 'react'
import './iconfont.less'
const Iconfont = ({ type }) => <span
dangerouslySetInnerHTML={{
__html: `<svg class="iconfont" aria-hidden="true"><use xlink:href="#anticon-${type}"></use></svg>`,
}}
/>
Iconfont.propTypes = {
type: PropTypes.string,
}
export default Iconfont
@@ -1,4 +1,4 @@
:global .ico {
:global .iconfont {
width: 1em;
height: 1em;
vertical-align: -0.15em;
+6
View File
@@ -0,0 +1,6 @@
{
"name": "Iconfont",
"version": "0.0.0",
"private": true,
"main": "./Iconfont.js"
}
+8
View File
@@ -0,0 +1,8 @@
import Header from './Header'
import Menu from './Menu'
import Bread from './Bread'
import Sider from './Sider'
import Footer from './Footer'
import styles from './Layout.less'
export { Header, Menu, Bread, Sider, Footer, styles }
@@ -1,6 +1,6 @@
import React, { PropTypes } from 'react'
import ReactDOM from 'react-dom'
import styles from './search.less'
import styles from './Search.less'
import { Input, Select, Button, Icon } from 'antd'
class Search extends React.Component {
+6
View File
@@ -0,0 +1,6 @@
{
"name": "Search",
"version": "0.0.0",
"private": true,
"main": "./Search.js"
}
-41
View File
@@ -1,41 +0,0 @@
import React, { PropTypes } from 'react'
import { Table, Tag } from 'antd'
import styles from './browser.less'
import { color } from '../../utils'
const status = {
1: {
color: color.green,
},
2: {
color: color.red,
},
3: {
color: color.blue,
},
4: {
color: color.yellow,
},
}
function Browser ({ data }) {
const columns = [
{
title: 'name',
dataIndex: 'name',
className: styles.name,
}, {
title: 'percent',
dataIndex: 'percent',
className: styles.percent,
render: (text, it) => <Tag color={status[it.status].color}>{text}%</Tag>,
},
]
return <Table pagination={false} showHeader={false} columns={columns} rowKey={(record, key) => key} dataSource={data} />
}
Browser.propTypes = {
data: PropTypes.array,
}
export default Browser
-7
View File
@@ -1,7 +0,0 @@
.percent {
text-align: right!important;
}
.name {
text-align: left!important;
}
-53
View File
@@ -1,53 +0,0 @@
import React, { PropTypes } from 'react'
import { Table, Tag } from 'antd'
import styles from './comments.less'
import { color } from '../../utils'
const status = {
1: {
color: color.green,
text: 'APPROVED',
},
2: {
color: color.yellow,
text: 'PENDING',
},
3: {
color: color.red,
text: 'REJECTED',
},
}
function Comments ({ data }) {
const columns = [
{
title: 'avatar',
dataIndex: 'avatar',
width: 48,
className: styles.avatarcolumn,
render: text => <span style={{ backgroundImage: `url(${text})` }} className={styles.avatar} />,
}, {
title: 'content',
dataIndex: 'content',
render: (text, it) => <div>
<h5 className={styles.name}>{it.name}</h5>
<p className={styles.content}>{it.content}</p>
<div className={styles.daterow}>
<Tag color={status[it.status].color}>{status[it.status].text}</Tag>
<span className={styles.date}>{it.date}</span>
</div>
</div>,
},
]
return (
<div className={styles.comments}>
<Table pagination={false} showHeader={false} columns={columns} rowKey={(record, key) => key} dataSource={data.filter((item, key) => key < 3)} />
</div>
)
}
Comments.propTypes = {
data: PropTypes.array,
}
export default Comments
-43
View File
@@ -1,43 +0,0 @@
@import "../vars.less";
.comments {
:global .ant-table-thead > tr > th {
background: #fff;
border-bottom: solid 1px @border-color-base;
}
.avatar {
width: 48px;
height: 48px;
background-position: center;
background-size: cover;
border-radius: 50%;
background: #f8f8f8;
display: inline-block;
}
.content {
text-align: left;
color: #757575;
}
.date {
color: #a3a3a3;
line-height: 30px;
}
.daterow {
display: flex;
justify-content: space-between;
}
.name {
font-size: 14px;
color: #474747;
text-align: left;
}
.avatarcolumn {
vertical-align: top;
}
}
-43
View File
@@ -1,43 +0,0 @@
import React, { PropTypes } from 'react'
import styles from './completed.less'
import classnames from 'classnames'
import { color } from '../../utils'
import { AreaChart, Area, XAxis, YAxis, CartesianGrid, Tooltip, Legend, ResponsiveContainer } from 'recharts'
function Completed ({ data }) {
return (
<div className={styles.sales}>
<div className={styles.title}>TEAM TOTAL COMPLETED</div>
<ResponsiveContainer minHeight={360}>
<AreaChart data={data}>
<Legend verticalAlign="top"
content={prop => {
const { payload } = prop
return (<ul className={classnames({ [styles.legend]: true, clearfix: true })}>
{payload.map((item, key) => <li key={key}><span className={styles.radiusdot} style={{ background: item.color }} />{item.value}</li>)}
</ul>)
}}
/>
<XAxis dataKey="name" axisLine={{ stroke: color.borderBase, strokeWidth: 1 }} tickLine={false} />
<YAxis axisLine={false} tickLine={false} />
<CartesianGrid vertical={false} stroke={color.borderBase} strokeDasharray="3 3" />
<Tooltip
wrapperStyle={{ border: 'none', boxShadow: '4px 4px 40px rgba(0, 0, 0, 0.05)' }}
content={content => {
const list = content.payload.map((item, key) => <li key={key} className={styles.tipitem}><span className={styles.radiusdot} style={{ background: item.color }} />{`${item.name}:${item.value}`}</li>)
return <div className={styles.tooltip}><p className={styles.tiptitle}>{content.label}</p><ul>{list}</ul></div>
}}
/>
<Area type="monotone" dataKey="Task complete" stroke={color.grass} fill={color.grass} strokeWidth={2} dot={{ fill: '#fff' }} activeDot={{ r: 5, fill: '#fff', stroke: color.green }} />
<Area type="monotone" dataKey="Cards Complete" stroke={color.sky} fill={color.sky} strokeWidth={2} dot={{ fill: '#fff' }} activeDot={{ r: 5, fill: '#fff', stroke: color.blue }} />
</AreaChart>
</ResponsiveContainer>
</div>
)
}
Completed.propTypes = {
data: PropTypes.array,
}
export default Completed
-50
View File
@@ -1,50 +0,0 @@
@import "../vars.less";
.sales {
.title {
margin-left: 32px;
font-size: 16px;
}
}
.radiusdot {
width: 12px;
height: 12px;
margin-right: 8px;
border-radius: 50%;
display: inline-block;
}
.legend {
color: @dark-half;
text-align: right;
color: #999;
font-size: 14px;
li {
height: 48px;
line-height: 48px;
display: inline-block;
&+li {
margin-left: 24px;
}
}
}
.tooltip {
background: #fff;
padding: 20px;
font-size: 14px;
.tiptitle {
font-weight: 700;
font-size: 16px;
margin-bottom: 8px;
}
.tipitem {
height: 32px;
line-height: 32px;
}
}
-61
View File
@@ -1,61 +0,0 @@
import React, { PropTypes } from 'react'
import styles from './cpu.less'
import { color } from '../../utils'
import CountUp from 'react-countup'
import { LineChart, Line, XAxis, YAxis, CartesianGrid, ResponsiveContainer } from 'recharts'
const countUpProps = {
start: 0,
duration: 2.75,
useEasing: true,
useGrouping: true,
separator: ',',
}
function Cpu ({ usage, space, cpu, data }) {
return (<div className={styles.cpu}>
<div className={styles.number}>
<div className={styles.item}>
<p>usage</p>
<p><CountUp
end={usage}
suffix="GB"
{...countUpProps}
/></p>
</div>
<div className={styles.item}>
<p>space</p>
<p><CountUp
end={space}
suffix="GB"
{...countUpProps}
/></p>
</div>
<div className={styles.item}>
<p>cpu</p>
<p><CountUp
end={cpu}
suffix="%"
{...countUpProps}
/></p>
</div>
</div>
<ResponsiveContainer minHeight={300}>
<LineChart data={data} margin={{ left: -40 }}>
<XAxis dataKey="name" axisLine={{ stroke: color.borderBase, strokeWidth: 1 }} tickLine={false} />
<YAxis axisLine={false} tickLine={false} />
<CartesianGrid vertical={false} stroke={color.borderBase} strokeDasharray="3 3" />
<Line type="monotone" connectNulls dataKey="cpu" stroke={color.blue} fill={color.blue} />
</LineChart>
</ResponsiveContainer>
</div>)
}
Cpu.propTypes = {
data: PropTypes.array,
usage: PropTypes.number,
space: PropTypes.number,
cpu: PropTypes.number,
}
export default Cpu
-40
View File
@@ -1,40 +0,0 @@
.cpu {
.number {
display: flex;
height: 64px;
justify-content: space-between;
margin-bottom: 32px;
.item {
text-align: center;
height: 64px;
width: 100%;
position: relative;
&+.item {
&::before {
content: '';
display: block;
width: 1px;
height: 40px;
position: absolute;
background: #f5f5f5;
top: 12px;
}
}
p {
color: #757575;
&:first-child {
font-size: 16px;
}
&:last-child {
font-size: 20px;
font-weight: 700;
}
}
}
}
}
-36
View File
@@ -1,36 +0,0 @@
import React, { PropTypes } from 'react'
import { Icon, Card } from 'antd'
import CountUp from 'react-countup'
import styles from './numberCard.less'
function NumberCard ({ icon, color, title, number, countUp }) {
return (
<Card className={styles.numberCard} bordered={false} bodyStyle={{ padding: 0 }}>
<Icon className={styles.iconWarp} style={{ color }} type={icon} />
<div className={styles.content}>
<p className={styles.title}>{title || 'No Title'}</p>
<p className={styles.number}>
<CountUp
start={0}
end={number}
duration={2.75}
useEasing
useGrouping
separator=","
{...countUp || {}}
/>
</p>
</div>
</Card>
)
}
NumberCard.propTypes = {
icon: PropTypes.string,
color: PropTypes.string,
title: PropTypes.string,
number: PropTypes.number,
countUp: PropTypes.object,
}
export default NumberCard
-33
View File
@@ -1,33 +0,0 @@
@import "../vars.less";
.numberCard {
padding: 32px;
font-family: monospace;
margin-bottom: 24px;
cursor: pointer;
.iconWarp {
font-size: 54px;
float: left;
}
.content {
width: 100%;
padding-left: 78px;
.title {
line-height: 16px;
font-size: 16px;
margin-bottom: 8px;
height: 16px;
.text-overflow();
}
.number {
line-height: 32px;
font-size: 24px;
height: 32px;
.text-overflow();
}
}
}
-28
View File
@@ -1,28 +0,0 @@
import React, { PropTypes } from 'react'
import styles from './quote.less'
function Quote ({ name, content, title, avatar }) {
return (
<div className={styles.quote}>
<div className={styles.inner}>
{content}
</div>
<div className={styles.footer}>
<div className={styles.description}>
<p>-{name}-</p>
<p>{title}</p>
</div>
<div className={styles.avatar} style={{ backgroundImage: `url(${avatar})` }} />
</div>
</div>
)
}
Quote.propTypes = {
name: PropTypes.string,
content: PropTypes.string,
title: PropTypes.string,
avatar: PropTypes.string,
}
export default Quote
-52
View File
@@ -1,52 +0,0 @@
@import "../vars.less";
.quote {
color: #fff;
height: 100%;
width: 100%;
padding: 24px;
font-size: 16px;
font-weight: 700;
.inner {
text-overflow: ellipsis;
word-wrap: normal;
display: -webkit-box;
-webkit-box-orient: vertical;
-webkit-line-clamp: 4;
overflow: hidden;
text-indent: 24px;
}
.footer {
position: relative;
margin-top: 14px;
.description {
width: 100%;
p {
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
margin-right: 64px;
text-align: right;
&:last-child {
font-weight: 100;
}
}
}
.avatar {
width: 48px;
height: 48px;
background-position: center;
background-size: cover;
border-radius: 50%;
position: absolute;
right: 0;
top: 0;
}
}
}
-55
View File
@@ -1,55 +0,0 @@
import React, { PropTypes } from 'react'
import { Table, Tag } from 'antd'
import styles from './recentSales.less'
import { color } from '../../utils'
const status = {
1: {
color: color.green,
text: 'SALE',
},
2: {
color: color.yellow,
text: 'REJECT',
},
3: {
color: color.red,
text: 'TAX',
},
4: {
color: color.blue,
text: 'EXTENDED',
},
}
function RecentSales ({ data }) {
const columns = [
{
title: 'NAME',
dataIndex: 'name',
}, {
title: 'STATUS',
dataIndex: 'status',
render: text => <Tag color={status[text].color}>{status[text].text}</Tag>,
}, {
title: 'DATE',
dataIndex: 'date',
render: text => new Date(text).format('yyyy-MM-dd'),
}, {
title: 'PRICE',
dataIndex: 'price',
render: (text, it) => <span style={{ color: status[it.status].color }}>${text}</span>,
},
]
return (
<div className={styles.recentsales}>
<Table pagination={false} columns={columns} rowKey={(record, key) => key} dataSource={data.filter((item, key) => key < 5)} />
</div>
)
}
RecentSales.propTypes = {
data: PropTypes.array,
}
export default RecentSales
@@ -1,8 +0,0 @@
@import "../vars.less";
.recentsales {
:global .ant-table-thead > tr > th {
background: #fff;
border-bottom: solid 1px @border-color-base;
}
}
-44
View File
@@ -1,44 +0,0 @@
import React, { PropTypes } from 'react'
import styles from './sales.less'
import classnames from 'classnames'
import { color } from '../../utils'
import { LineChart, Line, XAxis, YAxis, CartesianGrid, Tooltip, Legend, ResponsiveContainer } from 'recharts'
function Sales ({ data }) {
return (
<div className={styles.sales}>
<div className={styles.title}>Yearly Sales</div>
<ResponsiveContainer minHeight={360}>
<LineChart data={data}>
<Legend verticalAlign="top"
content={prop => {
const { payload } = prop
return (<ul className={classnames({ [styles.legend]: true, clearfix: true })}>
{payload.map((item, key) => <li key={key}><span className={styles.radiusdot} style={{ background: item.color }} />{item.value}</li>)}
</ul>)
}}
/>
<XAxis dataKey="name" axisLine={{ stroke: color.borderBase, strokeWidth: 1 }} tickLine={false} />
<YAxis axisLine={false} tickLine={false} />
<CartesianGrid vertical={false} stroke={color.borderBase} strokeDasharray="3 3" />
<Tooltip
wrapperStyle={{ border: 'none', boxShadow: '4px 4px 40px rgba(0, 0, 0, 0.05)' }}
content={content => {
const list = content.payload.map((item, key) => <li key={key} className={styles.tipitem}><span className={styles.radiusdot} style={{ background: item.color }} />{`${item.name}:${item.value}`}</li>)
return <div className={styles.tooltip}><p className={styles.tiptitle}>{content.label}</p><ul>{list}</ul></div>
}}
/>
<Line type="monotone" dataKey="Food" stroke={color.purple} strokeWidth={3} dot={{ fill: color.purple }} activeDot={{ r: 5, strokeWidth: 0 }} />
<Line type="monotone" dataKey="Clothes" stroke={color.red} strokeWidth={3} dot={{ fill: color.red }} activeDot={{ r: 5, strokeWidth: 0 }} />
<Line type="monotone" dataKey="Electronics" stroke={color.green} strokeWidth={3} dot={{ fill: color.green }} activeDot={{ r: 5, strokeWidth: 0 }} />
</LineChart>
</ResponsiveContainer>
</div>
)
}
Sales.propTypes = {
data: PropTypes.array,
}
export default Sales
-50
View File
@@ -1,50 +0,0 @@
@import "../vars.less";
.sales {
.title {
margin-left: 32px;
font-size: 16px;
}
}
.radiusdot {
width: 12px;
height: 12px;
margin-right: 8px;
border-radius: 50%;
display: inline-block;
}
.legend {
color: @dark-half;
text-align: right;
color: #999;
font-size: 14px;
li {
height: 48px;
line-height: 48px;
display: inline-block;
&+li {
margin-left: 24px;
}
}
}
.tooltip {
background: #fff;
padding: 20px;
font-size: 14px;
.tiptitle {
font-weight: 700;
font-size: 16px;
margin-bottom: 8px;
}
.tipitem {
height: 32px;
line-height: 32px;
}
}
Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.0 MiB

-54
View File
@@ -1,54 +0,0 @@
import React, { PropTypes } from 'react'
import { Button } from 'antd'
import styles from './user.less'
import CountUp from 'react-countup'
import { color } from '../../utils'
const countUpProps = {
start: 0,
duration: 2.75,
useEasing: true,
useGrouping: true,
separator: ',',
}
function User ({ avatar, name, email, sales, sold }) {
return (<div className={styles.user}>
<div className={styles.header}>
<div className={styles.headerinner}>
<div className={styles.avatar} style={{ backgroundImage: `url(${avatar})` }} />
<h5 className={styles.name}>{name}</h5>
<p>{email}</p>
</div>
</div>
<div className={styles.number}>
<div className={styles.item}>
<p>EARNING SALES</p>
<p style={{ color: color.green }}><CountUp
end={sales}
prefix="$"
{...countUpProps}
/></p>
</div>
<div className={styles.item}>
<p>ITEM SOLD</p>
<p style={{ color: color.blue }}><CountUp
end={sold}
{...countUpProps}
/></p>
</div>
</div>
<div className={styles.footer}>
<Button type="ghost" size="large">View Profile</Button>
</div>
</div>)
}
User.propTypes = {
avatar: PropTypes.string,
name: PropTypes.string,
email: PropTypes.string,
sales: PropTypes.number,
sold: PropTypes.number,
}
export default User
-97
View File
@@ -1,97 +0,0 @@
@import "../vars.less";
.user {
.header {
display: flex;
justify-content: center;
text-align: center;
color: #fff;
height: 200px;
background-image: ~ "url(./user-background.png)";
background-repeat: no-repeat;
background-size: cover;
align-items: center;
.headerinner {
z-index: 2;
}
&::after {
content: '';
background: @purple;
position: absolute;
width: 100%;
height: 200px;
left: 0;
top: 0;
opacity: 0.4;
z-index: 1;
}
.avatar {
width: 64px;
height: 64px;
background-position: center;
background-size: cover;
border-radius: 50%;
display: inline-block;
}
.name {
font-size: 16px;
}
}
.number {
display: flex;
height: 116px;
justify-content: space-between;
border-bottom: solid 1px #f5f5f5;
.item {
text-align: center;
height: 116px;
width: 100%;
position: relative;
padding: 30px 0;
&+.item {
&::before {
content: '';
display: block;
width: 1px;
height: 116px;
position: absolute;
background: #f5f5f5;
top: 0;
}
}
p {
color: #757575;
&:first-child {
font-size: 16px;
}
&:last-child {
font-size: 20px;
font-weight: 700;
}
}
}
}
.footer {
height: 116px;
display: flex;
justify-content: center;
align-items: center;
:global .ant-btn {
color: @purple;
border-color: @purple;
padding: 6px 16px;
}
}
}
-27
View File
@@ -1,27 +0,0 @@
import React, { PropTypes } from 'react'
import styles from './weather.less'
function Weather ({ city, icon, dateTime, temperature, name }) {
return (<div className={styles.weather}>
<div className={styles.left}>
<div className={styles.icon} style={{
backgroundImage: `url(${icon})`,
}} />
<p>{name}</p>
</div>
<div className={styles.right}>
<h1 className={styles.temperature}>{`${temperature}°`}</h1>
<p className={styles.description}>{city},{dateTime}</p>
</div>
</div>)
}
Weather.propTypes = {
city: PropTypes.string,
icon: PropTypes.string,
dateTime: PropTypes.string,
temperature: PropTypes.string,
name: PropTypes.string,
}
export default Weather
-47
View File
@@ -1,47 +0,0 @@
@import "../vars.less";
.weather {
color: #fff;
height: 204px;
padding: 24px;
justify-content: space-between;
display: flex;
font-size: 14px;
.left {
display: flex;
flex-direction: column;
width: 64px;
padding-top: 55px;
.icon {
width: 64px;
height: 64px;
background-position: center;
background-size: cover;
}
p {
margin-top: 16px;
}
}
.right {
display: flex;
flex-direction: column;
width: 50%;
.temperature {
font-size: 36px;
text-align: right;
height: 64px;
}
.description {
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
text-align: right;
}
}
}
+7 -1
View File
@@ -1,3 +1,9 @@
import DataTable from './DataTable'
import DropOption from './DropOption'
import Iconfont from './Iconfont'
import Search from './Search'
import * as Layout from './Layout/index.js'
export { DataTable }
import layer from './layer'
export { Layout, DataTable, DropOption, Iconfont, Search, layer }
+6
View File
@@ -0,0 +1,6 @@
{
"name": "layer",
"version": "0.0.0",
"private": true,
"main": "./layer.js"
}
+1 -1
View File
@@ -1,6 +1,6 @@
import React, { PropTypes } from 'react'
import { Breadcrumb, Icon } from 'antd'
import styles from './main.less'
import styles from './Layout.less'
import { menu } from '../../utils'
let pathSet = []
-67
View File
@@ -1,67 +0,0 @@
body {
height: 100%;
overflow-y: hidden;
background-color: #f8f8f8;
}
// scrollbar
::-webkit-scrollbar-thumb {
background-color: #e6e6e6;
}
::-webkit-scrollbar {
width: 8px;
height: 8px;
}
:global .ant-breadcrumb {
& > span {
&:last-child {
color: #999;
font-weight: normal;
}
}
}
:global .ant-breadcrumb-link {
.anticon + span {
margin-left: 4px;
}
}
:global .ant-table {
.ant-table-thead > tr > th {
text-align: center;
}
.ant-table-tbody > tr > td {
text-align: center;
}
&.ant-table-small {
.ant-table-thead > tr > th {
background: #f7f7f7;
}
.ant-table-body > table {
padding: 0;
}
}
}
:global .ant-table-pagination {
float: none!important;
display: table;
margin: 16px auto !important;
}
:global .ant-popover-inner {
border: none;
border-radius: 0;
box-shadow: 0 0 20px rgba(100, 100, 100, 0.2);
}
:global .ant-form-item-control {
vertical-align: middle;
}
@import "../skin.less";
+1 -1
View File
@@ -1,5 +1,5 @@
import React from 'react'
import styles from './main.less'
import styles from './Layout.less'
import { config } from '../../utils'
const Footer = () => <div className={styles.footer}>
+2 -2
View File
@@ -1,7 +1,7 @@
import React, { PropTypes } from 'react'
import { Menu, Icon, Popover } from 'antd'
import styles from './main.less'
import Menus from './menu'
import styles from './Layout.less'
import Menus from './Menu'
const SubMenu = Menu.SubMenu
+2 -2
View File
@@ -1,8 +1,8 @@
import React, { PropTypes } from 'react'
import { Icon, Switch } from 'antd'
import styles from './main.less'
import styles from './Layout.less'
import { config } from '../../utils'
import Menus from './menu'
import Menus from './Menu'
function Sider ({ siderFold, darkTheme, location, changeTheme, navOpenKeys, changeOpenKeys }) {
const menusProps = {
+66
View File
@@ -1,6 +1,72 @@
@import "./vars.less";
body {
height: 100%;
overflow-y: hidden;
background-color: #f8f8f8;
}
::-webkit-scrollbar-thumb {
background-color: #e6e6e6;
}
::-webkit-scrollbar {
width: 8px;
height: 8px;
}
:global {
.ant-breadcrumb {
& > span {
&:last-child {
color: #999;
font-weight: normal;
}
}
}
.ant-breadcrumb-link {
.anticon + span {
margin-left: 4px;
}
}
.ant-table {
.ant-table-thead > tr > th {
text-align: center;
}
.ant-table-tbody > tr > td {
text-align: center;
}
&.ant-table-small {
.ant-table-thead > tr > th {
background: #f7f7f7;
}
.ant-table-body > table {
padding: 0;
}
}
}
.ant-table-pagination {
float: none!important;
display: table;
margin: 16px auto !important;
}
.ant-popover-inner {
border: none;
border-radius: 0;
box-shadow: 0 0 20px rgba(100, 100, 100, 0.2);
}
.ant-form-item-control {
vertical-align: middle;
}
.ant-modal-mask {
background-color: rgba(55, 55, 55, 0.2);
}
-14
View File
@@ -1,14 +0,0 @@
import React, { PropTypes } from 'react'
import './ico.less'
const Ico = ({ type }) => <span
dangerouslySetInnerHTML={{
__html: `<svg class="ico" aria-hidden="true"><use xlink:href="#anticon-${type}"></use></svg>`,
}}
/>
Ico.propTypes = {
type: PropTypes.string,
}
export default Ico
-7
View File
@@ -1,7 +0,0 @@
import Ico from './ico.js'
import Search from './search.js'
import DropOption from './dropOption.js'
import layer from './layer.js'
export { Ico, Search, DropOption, layer }
-115
View File
@@ -1,115 +0,0 @@
import React, { PropTypes } from 'react'
import { Table, Modal } from 'antd'
import styles from './list.less'
import classnames from 'classnames'
import TableBodyWrapper from '../common/TableBodyWrapper'
import { DropOption } from '../ui/index'
const confirm = Modal.confirm
function list ({ loading, dataSource, pagination, onPageChange, onDeleteItem, onEditItem, isMotion, location }) {
const handleMenuClick = (record, e) => {
if (e.key === '1') {
onEditItem(record)
} else if (e.key === '2') {
confirm({
title: '您确定要删除这条记录吗?',
onOk () {
onDeleteItem(record.id)
},
})
}
}
const columns = [
{
title: '头像',
dataIndex: 'avatar',
key: 'avatar',
width: 64,
className: styles.avatar,
render: (text) => <img alt={'avatar'} width={24} src={text} />,
}, {
title: '姓名',
dataIndex: 'name',
key: 'name',
}, {
title: '昵称',
dataIndex: 'nickName',
key: 'nickName',
}, {
title: '年龄',
dataIndex: 'age',
key: 'age',
render: (text) => <span>{text}岁</span>,
}, {
title: '性别',
dataIndex: 'isMale',
key: 'isMale',
render: (text) => <span>{text
? '男'
: '女'}</span>,
}, {
title: '电话',
dataIndex: 'phone',
key: 'phone',
}, {
title: '邮箱',
dataIndex: 'email',
key: 'email',
}, {
title: '住址',
dataIndex: 'address',
key: 'address',
}, {
title: '创建时间',
dataIndex: 'createTime',
key: 'createTime',
}, {
title: '操作',
key: 'operation',
width: 100,
render: (text, record) => {
return <DropOption onMenuClick={e => handleMenuClick(record, e)} menuOptions={[{ key: '1', name: '编辑' }, { key: '2', name: '删除' }]} />
},
},
]
const getBodyWrapperProps = {
page: location.query.page,
current: pagination.current,
}
const getBodyWrapper = body => { return isMotion ? <TableBodyWrapper {...getBodyWrapperProps} body={body} /> : body }
return (
<div>
<Table
className={classnames({ [styles.table]: true, [styles.motion]: isMotion })}
bordered
scroll={{ x: 1200 }}
columns={columns}
dataSource={dataSource}
loading={loading}
onChange={onPageChange}
pagination={pagination}
simple
rowKey={record => record.id}
getBodyWrapper={getBodyWrapper}
/>
</div>
)
}
list.propTypes = {
loading: PropTypes.bool,
dataSource: PropTypes.array,
pagination: PropTypes.object,
onPageChange: PropTypes.func,
onDeleteItem: PropTypes.func,
onEditItem: PropTypes.func,
isMotion: PropTypes.bool,
location: PropTypes.object,
}
export default list
-93
View File
@@ -1,93 +0,0 @@
.table {
td.avatar {
img {
border-radius: 50%;
}
}
:global {
.ant-table-tbody > tr > td,
.ant-table-thead > tr > th {
height: 62px;
}
}
&.motion {
:global {
.ant-table-tbody > tr > td,
.ant-table-thead > tr > th {
&:nth-child(1) {
width: 6%;
}
&:nth-child(2) {
width: 8%;
}
&:nth-child(3) {
width: 8%;
}
&:nth-child(4) {
width: 6%;
}
&:nth-child(5) {
width: 6%;
}
&:nth-child(6) {
width: 8%;
}
&:nth-child(7) {
width: 16%;
}
&:nth-child(8) {
width: 20%;
}
&:nth-child(9) {
width: 14%;
}
&:nth-child(10) {
width: 8%;
}
}
.ant-table-thead {
& > tr {
transition: none;
display: block;
& > th {
display: inline-flex;
align-items: center;
justify-content: center;
}
}
}
.ant-table-tbody {
& > tr {
transition: none;
display: block;
border-bottom: 1px solid #f5f5f5;
& > td {
border-bottom: none;
display: inline-flex;
align-items: center;
justify-content: center;
}
&.ant-table-expanded-row-level-1 > td {
height: auto;
}
}
}
}
}
}
-148
View File
@@ -1,148 +0,0 @@
import React, { PropTypes } from 'react'
import { Form, Input, InputNumber, Radio, Modal } from 'antd'
const FormItem = Form.Item
const formItemLayout = {
labelCol: {
span: 6,
},
wrapperCol: {
span: 14,
},
}
const modal = ({
visible,
type,
item = {},
onOk,
onCancel,
form: {
getFieldDecorator,
validateFields,
getFieldsValue,
},
}) => {
function handleOk () {
validateFields((errors) => {
if (errors) {
return
}
const data = {
...getFieldsValue(),
key: item.key,
}
onOk(data)
})
}
const modalOpts = {
title: `${type === 'create' ? '新建用户' : '修改用户'}`,
visible,
onOk: handleOk,
onCancel,
wrapClassName: 'vertical-center-modal',
}
return (
<Modal {...modalOpts}>
<Form layout="horizontal">
<FormItem label="姓名:" hasFeedback {...formItemLayout}>
{getFieldDecorator('name', {
initialValue: item.name,
rules: [
{
required: true,
message: '姓名未填写',
},
],
})(<Input />)}
</FormItem>
<FormItem label="昵称:" hasFeedback {...formItemLayout}>
{getFieldDecorator('nickName', {
initialValue: item.nickName,
rules: [
{
required: true,
message: '昵称未填写',
},
],
})(<Input />)}
</FormItem>
<FormItem label="性别" hasFeedback {...formItemLayout}>
{getFieldDecorator('isMale', {
initialValue: item.isMale,
rules: [
{
required: true,
type: 'boolean',
message: '请选择性别',
},
],
})(
<Radio.Group>
<Radio value>男</Radio>
<Radio value={false}>女</Radio>
</Radio.Group>
)}
</FormItem>
<FormItem label="年龄:" hasFeedback {...formItemLayout}>
{getFieldDecorator('age', {
initialValue: item.age,
rules: [
{
required: true,
type: 'number',
message: '年龄未填写',
},
],
})(<InputNumber min={18} max={100} />)}
</FormItem>
<FormItem label="电话:" hasFeedback {...formItemLayout}>
{getFieldDecorator('phone', {
initialValue: item.phone,
rules: [
{
required: true,
message: '不能为空',
},
],
})(<Input />)}
</FormItem>
<FormItem label="邮箱:" hasFeedback {...formItemLayout}>
{getFieldDecorator('email', {
initialValue: item.email,
rules: [
{
required: true,
message: '不能为空',
},
],
})(<Input />)}
</FormItem>
<FormItem label="住址:" hasFeedback {...formItemLayout}>
{getFieldDecorator('address', {
initialValue: item.address,
rules: [
{
required: true,
message: '不能为空',
},
],
})(<Input />)}
</FormItem>
</Form>
</Modal>
)
}
modal.propTypes = {
form: PropTypes.object.isRequired,
visible: PropTypes.bool,
type: PropTypes.string,
item: PropTypes.object,
onCancel: PropTypes.func,
onOk: PropTypes.func,
}
export default Form.create()(modal)
-50
View File
@@ -1,50 +0,0 @@
import React, { PropTypes } from 'react'
import { Form, Button, Row, Col, Switch } from 'antd'
import SearchGroup from '../ui/search'
const search = ({
field,
keyword,
onSearch,
onAdd,
isMotion,
switchIsMotion,
}) => {
const searchGroupProps = {
field,
keyword,
size: 'large',
select: true,
selectOptions: [{ value: 'name', name: '姓名' }, { value: 'address', name: '地址' }],
selectProps: {
defaultValue: field || 'name',
},
onSearch: (value) => {
onSearch(value)
},
}
return (
<Row gutter={24}>
<Col lg={8} md={12} sm={16} xs={24} style={{ marginBottom: 16 }}>
<SearchGroup {...searchGroupProps} />
</Col>
<Col lg={{ offset: 8, span: 8 }} md={12} sm={8} xs={24} style={{ marginBottom: 16, textAlign: 'right' }}>
<Switch style={{ marginRight: 16 }} defaultChecked={isMotion} onChange={switchIsMotion} checkedChildren={'动画开'} unCheckedChildren={'动画关'} />
<Button size="large" type="ghost" onClick={onAdd}>添加</Button>
</Col>
</Row>
)
}
search.propTypes = {
form: PropTypes.object.isRequired,
onSearch: PropTypes.func,
onAdd: PropTypes.func,
field: PropTypes.string,
keyword: PropTypes.string,
isMotion: PropTypes.bool,
switchIsMotion: PropTypes.func,
}
export default Form.create()(search)
-1
View File
@@ -1 +0,0 @@
Error: Source sample is missing.