提交 301e50c8 编写于 作者: A afc163

Merge pull request #563 from ant-design/develop-0.10.0

0.10.0 Release
......@@ -2,12 +2,15 @@
"extends": ["eslint-config-airbnb"],
"env": {
"browser": true,
"node": true
"node": true,
"mocha": true,
"jest": true,
"es6": true
},
"ecmaFeatures": {
"jsx": true
"jsx": true,
"experimentalObjectRestSpread": true
},
"parser": "babel-eslint",
"plugins": [
"react",
"babel"
......@@ -38,6 +41,7 @@
"space-before-blocks": 0,
"space-before-function-paren": 0,
"spaced-comment": 0,
"vars-on-top": 0
"vars-on-top": 0,
"id-length": 0
}
}
language: node_js
node_js:
- "iojs"
- "4"
......@@ -4,17 +4,88 @@
---
## 0.9.4 `2015-11-04`
## 0.10.0 `2015-11-20`
- 全面兼容 `react@0.14.x`
- 新增 [时间选择 Timepicker](http://ant.design/components/timepicker/)[日历 Calendar](http://ant.design/components/calendar/)[加载中 Spin](http://ant.design/components/spin/) 组件。
- [Button](http://ant.design/components/button/)[Iconfont](http://ant.design/components/icon/)[Layout](http://ant.design/components/layout/)[Form](http://ant.design/components/form/) [Input](http://ant.design/components/form/#demo-input) 等样式模块改造为 React 组件。
- 新增 [Queue-anim](http://ant.design/components/queue-anim/) 组件,更换了原来的 enter-animation。
- 全新的[字体图标](/components/icon)
- 全面更新视觉风格,补充更多图标。[#313](https://github.com/ant-design/ant-design/issues/313)
- 调整字体基线,告别对图标位置的特殊调节。(感谢 [iconfont.cn](http://iconfont.cn) 的鼎力支持)
- Datepicker、Dropdown、Select、Popover、Popconfirm 等浮层组件添加在空间不足的情况下自动调整位置功能。
- Popover、Tooltip、Popconfirm 组件支持 12 个方向。[#312](https://github.com/ant-design/ant-design/issues/312)
- 优先使用苹方字体。
- 统一 size 属性的可选值为 `small` `default` `large`
- 开始初步补充[测试用例](https://github.com/ant-design/ant-design/tree/1a3a19793c0791201666fdcf0dbd12a30fad4be0/tests)
- 提供主色系更换的方案。[#384](https://github.com/ant-design/ant-design/issues/384)
- 添加[色彩换算工具](http://ant.design/spec/colors#色彩换算工具)
- 添加布局和导航规范,以及[常用布局](http://ant.design/spec/layout/)
- 文档支持标题和演示的锚点,方便分享文档和演示代码。
- 提供多版本的文档,在[主站](http://ant.design)的右下角提供切换按钮。
- [antd-bin](https://github.com/ant-tool/xtool) 升级到 `0.10`
- 拆分出 [antd-init](https://github.com/ant-design/antd-init)[antd-build](https://github.com/ant-design/antd-build)
- 提供代理功能。
- 提供 UI 测试功能。
#### 组件变更
- Table
- 支持单选。[演示](/components/table/#demo-row-selection-radio-props)
- 选择模式支持默认选中和不可用效果。[演示](/components/table/#demo-row-selection-props)
- 列支持了 `colSpan``rowSpan` 配置。[演示](/components/table/#demo-colspan-rowspan)
- 新增 `loading` 属性。
- 筛选增加 `filterMultiple` 属性,支持单选的配置。
- Datepicker
- 添加国际化支持。
- 添加手动输入和清除功能。
- 优化了视觉样式。
- 修复不标准的日期格式导致显示错误的问题。
-`onChange` 属性代替 `onSelect` 属性。
- Validation 修复了 对 Datepicker、Input-number、Select 的支持,并添加了相关演示。
- Carousel 的依赖 react-slick 升级到 0.9.x,相关 API 也相应更新。
- Tree 组件支持完全受控模式。[#397](https://github.com/ant-design/ant-design/issues/397)
- Input Number
- 组件输入体验优化,现在可以键入任意字符,失焦时格式化为合法值。
- 修复不支持小数 step 的问题。[#530](https://github.com/ant-design/ant-design/issues/530)
- Tabs 新增[垂直页签功能](http://ant.design/components/tabs/#demo-vertical-left)
- Upload 组件视觉优化,新增高级浏览器下的上传进度展示。[#311](https://github.com/ant-design/ant-design/issues/311)
- Menu
- 视觉效果大幅优化。
- 新增 [dark 主题](http://ant.design/components/menu/#demo-theme) 的样式。
- 修复一个链接点击区域的问题。[#535](https://github.com/ant-design/ant-design/issues/535)
- Dropdown 用 onClick 代替 onSelect 作为推荐的使用方式,因为原有的 onSelect 只在变化时触发。
- Slider
- 新增[双滑块功能](http://ant.design/components/slider/#demo-range)
- 优化 marks 属性的使用逻辑,使其可以和具体数值进行绑定。[slider#26](https://github.com//react-component/slider/issues/26)
- 属性命名优化,用 `dots` 代替了 `withDots` 属性,用 `included` 代替了 `isIncluded`
- Badge 当 `count` 为 0 时不展示。
- Progress 新增 `format` 属性,能够自定义展示的进度文案。
- Modal 新增 `confirmLoading` 属性。
- 新增 Radio.Button 的失效样式。
- 提供 IE8 下的圆角按钮[兼容方案](http://ant.design/components/button/#ie8-border-radius-support)
- `antd.Notification()` 修正为 `antd.notification()`
- 另有巨量样式的修复和优化。
> 备注:
>
> - [计划和推进 issue](https://github.com/ant-design/ant-design/issues/276)
> - [0.10 升级指南](/docs/upgrade-to-0.10)
## 0.9.3 ~ 0.9.5 `2015-11-04`
* 增加对 React 版本的检测提示机制,0.9.x 序列只能使用 `react@~0.13.3`
## 0.9.2 `2015-10-26`
* Tooltip 的 title 为空时不展示浮层。[9b53117](9b5311791e73270c7c16a602ac74dd59719a5f76)
* 修复 Upload 文件列表链接的 target 属性。[340a170](340a1702b6a7b065ac02d417c891e1886dfe470d)
* 修复 Datepicker 设置 defaultValue 时星期顺序错误的问题。[9ef1450](9ef14500f3abfcc7081f8dceab8187ec835e3918)
* Tooltip 的 title 为空时不展示浮层。[9b53117](https://github.com/ant-design/ant-design/commit/9b5311791e73270c7c16a602ac74dd59719a5f76)
* 修复 Upload 文件列表链接的 target 属性。[340a170](https://github.com/ant-design/ant-design/commit/340a1702b6a7b065ac02d417c891e1886dfe470d)
* 修复 Datepicker 设置 defaultValue 时星期顺序错误的问题。[9ef1450](https://github.com/ant-design/ant-design/commit/9ef14500f3abfcc7081f8dceab8187ec835e3918)
* 修复一些小的样式问题。
## 0.9.1 `2015-09-26`
* 添加 Pagination pageSize 发生变化的回调。[#317](https://github.com/ant-design/ant-design/issues/317)
......
# Ant Design [![](https://img.shields.io/travis/ant-design/ant-design.svg?style=flat-square)](https://travis-ci.org/ant-design/ant-design) [![npm package](https://img.shields.io/npm/v/antd.svg?style=flat-square)](https://www.npmjs.org/package/antd) [![Join the chat at https://gitter.im/ant-design/ant-design](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/ant-design/ant-design?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
An enterprise-class UI design language and React-based implementation.
![](https://t.alipayobjects.com/images/rmsweb/T11aVgXc4eXXXXXXXX.svg)
## Features
- An enterprise-class graphical design language and framework for financial applications
- Rich library of UI components base on [React Component](http://react-component.github.io/badgeboard/).
- A Component development model based on React.
- Backed by the npm ecosystem.
- webpack-based debug builds supporting ES6
## Usage example
```jsx
import { Datepicker } from 'antd';
React.render(<Datepicker />, mountNode);
```
## Links
- [Home page](http://ant.design/)
- [Documentation](http://ant.design/docs/introduce)
- [Components](http://ant.design/components/)
- [Build/Debug tools](https://github.com/ant-design/antd-bin)
- [Roadmap](https://github.com/ant-design/ant-design/issues/9)
- [ChangeLog](CHANGELOG.md)
- [React modules](http://react-component.github.io/)
- [React style guide](https://github.com/react-component/react-component.github.io/blob/master/docs/en-US/component-code-style.md)
- [React component design guide](https://github.com/react-component/react-component.github.io/blob/master/docs/en-US/component-design.md)
- [Developer Instruction](https://github.com/ant-design/ant-design/wiki/%E7%BD%91%E7%AB%99%E5%92%8C%E7%BB%84%E4%BB%B6%E5%BC%80%E5%8F%91%E8%AF%B4%E6%98%8E)
- [Versioning Release Note](https://github.com/ant-design/ant-design/wiki/%E7%89%88%E6%9C%AC%E5%8F%91%E5%B8%83%E6%B5%81%E7%A8%8B)
## Contributing
We welcome all contributions, please submit any ideas as [pull requests](https://github.com/ant-design/ant-design/pulls) or as a [GitHub issue](https://github.com/ant-design/ant-design/issues).
# Ant Design [![](https://img.shields.io/travis/ant-design/ant-design.svg?style=flat-square)](https://travis-ci.org/ant-design/ant-design) [![npm package](https://img.shields.io/npm/v/antd.svg?style=flat-square)](https://www.npmjs.org/package/antd) [![NPM downloads](http://img.shields.io/npm/dm/antd.svg?style=flat-square)](https://npmjs.org/package/antd) [![Join the chat at https://gitter.im/ant-design/ant-design](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/ant-design/ant-design?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
一套企业级的 UI 设计语言和 React 实现。
<p align="center">
<a href="http://ant.design">
<img width="360" src="https://t.alipayobjects.com/images/rmsweb/T1B9hfXcdvXXXXXXXX.svg">
</a>
</p>
## 特性
- 提炼自企业级后台产品的交互语言和视觉风格。
- [React Component](http://react-component.github.io/badgeboard/) 基础上二次封装的丰富实用的 UI 组件。
- 基于 React 的组件化开发模式。
- 背靠 npm 生态圈。
- 基于 webpack 的调试构建方案,支持 ES6。
## 安装
```bash
npm install antd
```
## 示例
- 使用全部组件
```jsx
import { Datepicker } from 'antd';
ReactDOM.render(<Datepicker />, mountNode);
```
- 按需使用
```jsx
import 'antd/lib/index.css'; // 只需在页面入口模块引用一次
import Datepicker from 'antd/lib/datepicker';
ReactDOM.render(<Datepicker />, mountNode);
```
## 浏览器支持
现代浏览器和 IE8 及以上。
## 链接
- [首页](http://ant.design/)
- [文档和组件](http://ant.design/docs/introduce)
- [构建调试工具](https://github.com/ant-design/antd-bin)
- [开发计划](https://github.com/ant-design/ant-design/issues/9)
- [修改记录](CHANGELOG.md)
- [React 模块](http://react-component.github.io/)
- [React 代码规范](https://github.com/react-component/react-component.github.io/blob/master/docs/zh-cn/component-code-style.md)
- [组件设计原则](https://github.com/react-component/react-component.github.io/blob/master/docs/zh-cn/component-design.md)
- [网站和组件开发说明](https://github.com/ant-design/ant-design/wiki/%E7%BD%91%E7%AB%99%E5%92%8C%E7%BB%84%E4%BB%B6%E5%BC%80%E5%8F%91%E8%AF%B4%E6%98%8E)
- [版本发布手册](https://github.com/ant-design/ant-design/wiki/%E7%89%88%E6%9C%AC%E5%8F%91%E5%B8%83%E6%B5%81%E7%A8%8B)
## 如何贡献
我们欢迎任何形式的贡献,有任何建议或意见您可以进行 [Pull Request](https://github.com/ant-design/ant-design/pulls),或者给我们 [提问](https://github.com/ant-design/ant-design/issues)
# Ant Design [![](https://img.shields.io/travis/ant-design/ant-design.svg?style=flat-square)](https://travis-ci.org/ant-design/ant-design) [![npm package](https://img.shields.io/npm/v/antd.svg?style=flat-square)](https://www.npmjs.org/package/antd) [![Join the chat at https://gitter.im/ant-design/ant-design](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/ant-design/ant-design?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
# Ant Design [![](https://img.shields.io/travis/ant-design/ant-design.svg?style=flat-square)](https://travis-ci.org/ant-design/ant-design) [![npm package](https://img.shields.io/npm/v/antd.svg?style=flat-square)](https://www.npmjs.org/package/antd) [![NPM downloads](http://img.shields.io/npm/dm/antd.svg?style=flat-square)](https://npmjs.org/package/antd) [![Join the chat at https://gitter.im/ant-design/ant-design](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/ant-design/ant-design?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
一套企业级的 UI 设计语言和 React 实现。
An enterprise-class UI design language and React-based implementation.
<p align="center">
<a href="http://ant.design">
<img width="360" src="https://t.alipayobjects.com/images/rmsweb/T1B9hfXcdvXXXXXXXX.svg">
</a>
</p>
![](https://t.alipayobjects.com/images/rmsweb/T11aVgXc4eXXXXXXXX.svg)
## 特性
## Features
- 提炼自企业级后台产品的交互语言和视觉风格。
- [React Component](http://react-component.github.io/badgeboard/) 基础上二次封装的丰富实用的 UI 组件。
- 基于 React 的组件化开发模式。
- 背靠 npm 生态圈。
- 基于 webpack 的调试构建方案,支持 ES6。
- An enterprise-class graphical design language and framework for financial applications
- Rich library of UI components base on [React Component](http://react-component.github.io/badgeboard/).
- A Component development model based on React.
- Backed by the npm ecosystem.
- webpack-based debug builds supporting ES6
## Install
## 示例
```jsx
import { Datepicker } from 'antd';
React.render(<Datepicker />, mountNode);
```bash
npm install antd
```
## 链接
## Usage example
- Use all components
```jsx
import { Datepicker } from 'antd';
ReactDOM.render(<Datepicker />, mountNode);
```
- Use on demand
```jsx
import 'antd/lib/index.css'; // only need to import once in entry module
import Datepicker from 'antd/lib/datepicker';
ReactDOM.render(<Datepicker />, mountNode);
```
## Browser Support
Normal browsers and Internet Explorer 8+.
## Links
- [Home page](http://ant.design/)
- [Documentation and Components](http://ant.design/docs/introduce)
- [Components](http://ant.design/components/)
- [Build/Debug tools](https://github.com/ant-design/antd-bin)
- [Roadmap](https://github.com/ant-design/ant-design/issues/9)
- [ChangeLog](CHANGELOG.md)
- [React modules](http://react-component.github.io/)
- [React style guide](https://github.com/react-component/react-component.github.io/blob/master/docs/en-US/component-code-style.md)
- [React component design guide](https://github.com/react-component/react-component.github.io/blob/master/docs/en-US/component-design.md)
- [Developer Instruction](https://github.com/ant-design/ant-design/wiki/%E7%BD%91%E7%AB%99%E5%92%8C%E7%BB%84%E4%BB%B6%E5%BC%80%E5%8F%91%E8%AF%B4%E6%98%8E)
- [Versioning Release Note](https://github.com/ant-design/ant-design/wiki/%E7%89%88%E6%9C%AC%E5%8F%91%E5%B8%83%E6%B5%81%E7%A8%8B)
- [首页](http://ant.design/)
- [文档](http://ant.design/docs/introduce)
- [组件](http://ant.design/components/)
- [构建调试 antd-bin](https://github.com/ant-design/antd-bin)
- [开发计划](https://github.com/ant-design/ant-design/issues/9)
- [修改记录](CHANGELOG.md)
- [React 模块](http://react-component.github.io/)
- [React 代码规范](https://github.com/react-component/react-component.github.io/blob/master/docs/zh-cn/component-code-style.md)
- [组件设计原则](https://github.com/react-component/react-component.github.io/blob/master/docs/zh-cn/component-design.md)
- [网站和组件开发说明](https://github.com/ant-design/ant-design/wiki/%E7%BD%91%E7%AB%99%E5%92%8C%E7%BB%84%E4%BB%B6%E5%BC%80%E5%8F%91%E8%AF%B4%E6%98%8E)
- [版本发布手册](https://github.com/ant-design/ant-design/wiki/%E7%89%88%E6%9C%AC%E5%8F%91%E5%B8%83%E6%B5%81%E7%A8%8B)
## 如何贡献
## Contributing
我们欢迎任何形式的贡献,有任何建议或意见您可以进行 [Pull Request](https://github.com/ant-design/ant-design/pulls),或者给我们 [提问](https://github.com/ant-design/ant-design/issues)
We welcome all contributions, please submit any ideas as [pull requests](https://github.com/ant-design/ant-design/pulls) or as a [GitHub issue](https://github.com/ant-design/ant-design/issues).
......@@ -7,11 +7,11 @@
---
````jsx
var Affix = antd.Affix;
import { Affix, Button } from 'antd';
React.render(
ReactDOM.render(
<Affix>
<button className="ant-btn ant-btn-primary">固定在顶部</button>
<Button type="primary">固定在顶部</Button>
</Affix>
, document.getElementById('components-affix-demo-basic'));
````
......@@ -7,11 +7,11 @@
---
````jsx
var Affix = antd.Affix;
import { Affix, Button } from 'antd';
React.render(
ReactDOM.render(
<Affix offset={75}>
<button className="ant-btn ant-btn-primary">固定在距离顶部 75px 的位置</button>
<Button type="primary">固定在距离顶部 75px 的位置</Button>
</Affix>
, document.getElementById('components-affix-demo-offset'));
````
import React from 'react';
import ReactDOM from 'react-dom';
import rcUtil from 'rc-util';
function getScroll(w, top) {
......@@ -52,7 +53,7 @@ let Affix = React.createClass({
handleScroll() {
let affix = this.state.affix;
let scrollTop = getScroll(window, true);
let elemOffset = getOffset(this.getDOMNode());
let elemOffset = getOffset(ReactDOM.findDOMNode(this));
if (!affix && (elemOffset.top - this.props.offset) < scrollTop) {
this.setState({
......@@ -60,7 +61,7 @@ let Affix = React.createClass({
affixStyle: {
top: this.props.offset,
left: elemOffset.left,
width: this.getDOMNode().offsetWidth
width: ReactDOM.findDOMNode(this).offsetWidth
}
});
}
......
......@@ -7,8 +7,8 @@
---
````jsx
var Alert = antd.Alert;
import { Alert } from 'antd';
React.render(<Alert message="成功提示的文案" type="success" />
ReactDOM.render(<Alert message="成功提示的文案" type="success" />
, document.getElementById('components-alert-demo-basic'));
````
......@@ -7,13 +7,13 @@
---
````jsx
var Alert = antd.Alert;
import { Alert } from 'antd';
var onClose = function(e) {
const onClose = function(e) {
console.log(e, '我要被关闭啦!');
};
React.render(<div>
ReactDOM.render(<div>
<Alert message="警告提示的文案"
type="warn"
closable
......@@ -24,4 +24,4 @@ React.render(<div>
closable
onClose={onClose} />
</div>, document.getElementById('components-alert-demo-closable'));
````
\ No newline at end of file
````
......@@ -7,10 +7,10 @@
---
````jsx
var Alert = antd.Alert;
var link = <a href="javascript:;">不再提醒</a>
import { Alert } from 'antd';
const link = <a href="javascript:;">不再提醒</a>;
React.render(
ReactDOM.render(
<Alert message="消息提示的文案" type="info" closeText={link} />
, document.getElementById('components-alert-demo-close-type'));
````
......@@ -7,9 +7,9 @@
---
````jsx
var Alert = antd.Alert;
import { Alert } from 'antd';
React.render(<div>
ReactDOM.render(<div>
<Alert message="成功提示的文案"
description="成功提示的辅助性文字介绍成功提示的辅助性文字介绍成功提示的辅助性文字介绍成功提示的辅助性文字介绍"
type="success" />
......
......@@ -7,9 +7,9 @@
---
````jsx
var Alert = antd.Alert;
import { Alert } from 'antd';
React.render(<div>
ReactDOM.render(<div>
<Alert message="成功提示的文案" type="success" />
<Alert message="消息提示的文案" type="info" />
<Alert message="警告提示的文案" type="warn" />
......
import React from 'react';
import ReactDOM from 'react-dom';
import Animate from 'rc-animate';
import Icon from '../icon';
export default React.createClass({
getDefaultProps() {
......@@ -14,7 +16,7 @@ export default React.createClass({
};
},
handleClose(e) {
let dom = React.findDOMNode(this);
let dom = ReactDOM.findDOMNode(this);
dom.style.height = dom.offsetHeight + 'px';
// Magic code
// 重复一次后才能正确设置 height
......@@ -35,22 +37,23 @@ export default React.createClass({
},
render() {
let iconClass = this.props.description ?
'ant-alert-with-description-icon anticon-' : 'ant-alert-icon anticon-';
'ant-alert-with-description-icon' : 'ant-alert-icon';
let iconType = '';
switch (this.props.type) {
case 'success':
iconClass += 'check-circle';
iconType = 'check-circle';
break;
case 'info':
iconClass += 'info-circle';
iconType = 'info-circle';
break;
case 'error':
iconClass += 'exclamation-circle';
iconType = 'exclamation-circle';
break;
case 'warn':
iconClass += 'question-circle';
iconType = 'question-circle';
break;
default:
iconClass += 'default';
iconType = 'default';
}
let html;
let closeName = !this.state.closing ? ' ' + this.props.prefixCls + '-close' : '';
......@@ -60,7 +63,7 @@ export default React.createClass({
<span className="ant-alert-with-description-close-icon-x"></span>
</a> : '';
html = <div data-show={this.state.closing} className={'ant-alert-with-description ant-alert-with-description-' + this.props.type + closeName}>
<i className={'anticon ' + iconClass}></i>
<Icon className={iconClass} type={iconType} />
<p className={'ant-alert-with-description-message'}>{this.props.message}</p>
<span className={'ant-alert-with-description-description'}>{this.props.description}</span>
{close}
......@@ -68,7 +71,7 @@ export default React.createClass({
} else {
if (this.props.closeText) {
html = <div data-show={this.state.closing} className={'ant-alert ant-alert-' + this.props.type + closeName}>
<i className={'anticon ' + iconClass}></i>
<Icon className={iconClass} type={iconType} />
<span className={'ant-alert-description'}>{this.props.message}</span>
<span onClick={this.handleClose} className={'ant-alert-close-text'}>{this.props.closeText}</span>
</div>;
......@@ -78,7 +81,7 @@ export default React.createClass({
<span className="ant-alert-close-icon-x"></span>
</a> : '';
html = <div data-show={this.state.closing} className={'ant-alert ant-alert-' + this.props.type + closeName}>
<i className={'anticon ' + iconClass}></i>
<Icon className={iconClass} type={iconType} />
<span className={'ant-alert-description'}>{this.props.message}</span>
{close}
</div>;
......
......@@ -7,13 +7,13 @@
---
````jsx
var Badge = antd.Badge;
import { Badge } from 'antd';
React.render(<div>
<Badge count="99">
ReactDOM.render(<div>
<Badge count={99}>
<a href="#" className="head-example"></a>
</Badge>
<Badge count="200">
<Badge count={200}>
<a href="#" className="head-example"></a>
</Badge>
</div>, document.getElementById('components-badge-demo-99plus'));
......
......@@ -7,10 +7,10 @@
---
````jsx
var Badge = antd.Badge;
import { Badge } from 'antd';
React.render(
<Badge count="5">
ReactDOM.render(
<Badge count={5}>
<a href="#" className="head-example"></a>
</Badge>
, document.getElementById('components-badge-demo-basic'));
......
# 动态
- order: 4
展示动态变化的效果。
---
````jsx
import { Badge, Button, Icon } from 'antd';
const ButtonGroup = Button.Group;
const Test = React.createClass({
getInitialState() {
return {
count: 5,
show: true,
};
},
increase() {
const count = this.state.count + 1;
this.setState({ count });
},
decline() {
let count = this.state.count - 1;
if (count < 0) {
count = 0;
}
this.setState({ count });
},
onClick() {
this.setState({
show: !this.state.show
});
},
onNumberClick(){
const count = this.state.count;
this.setState({
count: count ? 0 : 5
});
},
render() {
return <div>
<Badge count={this.state.count}>
<a href="#" className="head-example"></a>
</Badge>
<Badge dot={this.state.show}>
<a href="#">一个链接</a>
</Badge>
<div style={{ marginTop: 10 }}>
<ButtonGroup>
<Button type="ghost" onClick={this.decline}>
<Icon type="minus" />
</Button>
<Button type="ghost" onClick={this.increase}>
<Icon type="plus" />
</Button>
</ButtonGroup>
<Button type="ghost" onClick={this.onClick} style={{marginLeft:10}}>点切换</Button>
<Button type="ghost" onClick={this.onNumberClick} style={{marginLeft:10}}>数字切换</Button>
</div>
</div>;
}
});
ReactDOM.render(
<Test />
, document.getElementById('components-badge-demo-change'));
````
......@@ -7,11 +7,11 @@
---
````jsx
var Badge = antd.Badge;
import { Badge, Icon } from 'antd';
React.render(<div>
ReactDOM.render(<div>
<Badge dot={true}>
<i className="anticon anticon-notification"></i>
<Icon type="notification" />
</Badge>
<Badge dot={true}>
<a href="#">一个链接</a>
......
......@@ -7,11 +7,11 @@
---
````jsx
var Badge = antd.Badge;
import { Badge } from 'antd';
React.render(
ReactDOM.render(
<a href="#">
<Badge count="5">
<Badge count={5}>
<span className="head-example"></span>
</Badge>
</a>
......
import React, { cloneElement } from 'react';
const prefixCls = 'ant-badge';
import React from 'react';
import Animate from 'rc-animate';
class AntBadge extends React.Component {
constructor(props) {
super(props);
this.state = {
count: props.count
};
}
render() {
if (this.props.dot) {
return <span className={prefixCls} {...this.props}>
{this.props.children}
<sup className={prefixCls + '-dot'}></sup>
</span>;
}
let count = this.state.count;
if (!count) {
return cloneElement(this.props.children);
} else {
count = count >= 100 ? '99+' : count;
return (
<span className={prefixCls} title={this.state.count} {...this.props}>
{this.props.children}
<sup className={prefixCls + '-count'}>{count}</sup>
</span>
);
let { count, prefixCls } = this.props;
const dot = this.props.dot;
count = count >= 100 ? '99+' : count;
// dot mode don't need count
if (dot) {
count = '';
}
// null undefined "" "0" 0
const hidden = (!count || count === '0') && !dot;
const className = prefixCls + (dot ? '-dot' : '-count');
return (
<span className={prefixCls} title={count} {...this.props}>
{this.props.children}
<Animate component=""
showProp="data-show"
transitionName={prefixCls + '-zoom'}
transitionAppear={true}>
{
hidden ? null :
<sup data-show={!hidden} className={className}>
{count}
</sup>
}
</Animate>
</span>
);
}
}
AntBadge.defaultProps = {
prefixCls: prefixCls,
prefixCls: 'ant-badge',
count: null,
dot: false
};
......
......@@ -15,12 +15,12 @@
## API
```jsx
<Badge count="5">
<Badge count={5}>
<a href="#" className="head-example"></a>
</Badge>
```
| 参数 | 说明 | 类型 | 可选值 | 默认值 |
|----------------|----------------------------------|------------|---------|--------|
| count | 展示的数字,大于 99 时显示为 99+ | Number | | |
| count | 展示的数字,大于 99 时显示为 99+,为 0 时隐藏 | Number | | |
| dot | 不展示数字,只有一个小红点 | boolean | | false |
......@@ -7,9 +7,9 @@
---
````jsx
var Breadcrumb = require('antd/lib/breadcrumb');
import { Breadcrumb } from 'antd';
React.render(
ReactDOM.render(
<Breadcrumb>
<Breadcrumb.Item>首页</Breadcrumb.Item>
<Breadcrumb.Item href="">应用中心</Breadcrumb.Item>
......
......@@ -7,13 +7,11 @@
---
````jsx
var ReactRouter = require('react-router');
var Router = ReactRouter.Router;
var Route = ReactRouter.Route;
var Link = ReactRouter.Link;
var Breadcrumb = require('antd').Breadcrumb;
const ReactRouter = require('react-router');
let { Router, Route, Link } = ReactRouter;
import { Breadcrumb } from 'antd';
var Apps = React.createClass({
const Apps = React.createClass({
render() {
return <ul className="app-list">
<li><Link to="/apps/1">应用1</Link></li>
......@@ -22,7 +20,7 @@ var Apps = React.createClass({
}
});
var Home = React.createClass({
const Home = React.createClass({
render() {
return (<div>
<div className="demo-nav">
......@@ -41,7 +39,7 @@ var Home = React.createClass({
}
});
React.render((
ReactDOM.render((
<Router>
<Route name="home" breadcrumbName="首页" path="/" component={Home} ignoreScrollBehavior>
<Route name="apps" breadcrumbName="应用列表" path="apps" component={Apps}>
......
......@@ -7,15 +7,15 @@
---
````jsx
var Breadcrumb = require('antd/lib/breadcrumb');
import { Breadcrumb, Icon } from 'antd';
React.render(
ReactDOM.render(
<Breadcrumb>
<Breadcrumb.Item href="">
<i className="anticon anticon-home"></i>
<Icon type="home" />
</Breadcrumb.Item>
<Breadcrumb.Item href="">
<i className="anticon anticon-user"></i>
<Icon type="user" />
应用列表
</Breadcrumb.Item>
<Breadcrumb.Item>
......
import React from 'react';
import rcUtil from 'rc-util';
const prefix = 'ant-btn-group-';
export default class ButtonGroup extends React.Component {
render() {
const {size, className, ...others} = this.props;
// large => lg
// small => sm
const sizeCls = ({
'large': 'lg',
'small': 'sm'
})[size] || '';
const classes = rcUtil.classSet({
'ant-btn-group': true,
[prefix + sizeCls]: sizeCls,
[className]: className
});
return <div {...others} className={classes} />;
}
}
ButtonGroup.propTypes = {
size: React.PropTypes.string,
};
import React from 'react';
import rcUtil from 'rc-util';
import { findDOMNode } from 'react-dom';
const rxTwoCNChar = /^[\u4e00-\u9fa5]{2,2}$/;
const isTwoCNChar = rxTwoCNChar.test.bind(rxTwoCNChar);
function isString(str) {
return typeof str === 'string';
}
const prefix = 'ant-btn-';
// Insert one space between two chinese characters automatically.
function insertSpace(child) {
if (isString(child) && isTwoCNChar(child)) {
return child.split('').join(' ');
}
if (isString(child.type) && isTwoCNChar(child.props.children)) {
return React.cloneElement(child, {},
child.props.children.split('').join(' '));
}
return child;
}
export default class Button extends React.Component {
componentDidMount() {
if (window && window.PIE) {
window.PIE.attach(findDOMNode(this));
}
}
render() {
const props = this.props;
const {type, shape, size, onClick, className, htmlType, children, ...others} = props;
// large => lg
// small => sm
const sizeCls = ({
'large': 'lg',
'small': 'sm'
})[size] || '';
const classes = rcUtil.classSet({
'ant-btn': true,
[prefix + type]: type,
[prefix + shape]: shape,
[prefix + sizeCls]: sizeCls,
[prefix + 'loading']: ('loading' in props && props.loading !== false),
[className]: className
});
const kids = React.Children.map(children, insertSpace);
return <button {...others} type={htmlType || 'button'} className={classes} onClick={onClick}>
{kids}
</button>;
}
}
Button.propTypes = {
type: React.PropTypes.string,
shape: React.PropTypes.string,
size: React.PropTypes.string,
htmlType: React.PropTypes.string,
onClick: React.PropTypes.func,
loading: React.PropTypes.bool,
className: React.PropTypes.string,
};
Button.defaultProps = {
onClick() {},
};
# 标准按钮
# 按钮类型
- order: 1
- order: 0
`<button>` `<a>``<input>` 元素添加 `.ant-btn` 类即可使用 ant-design 提供的样式
按钮有三种类型:主按钮、次按钮、幽灵按钮
另外,通过使用下面的类可创建带有预定义样式的按钮,我们通过样式来显示重要程度的不同
通过设置 `type``primary` `ghost` 可分别创建主按钮、幽灵按钮,若不设置 `type` 值则为次按钮。不同的样式可以用来区别其重要程度
`.ant-btn-primary` `.ant-btn-ghost`
其中 `.ant-btn` 类定义了按钮的默认样式,语义上代表次按钮。
**注**: 当按钮文字为两个字时,中间需要**间隔一个字符**
主按钮和次按钮可独立使用,需要强引导用主按钮。幽灵按钮用于和主按钮组合。
---
````html
<button class="ant-btn">Button</button>
<a href="javascript:;" class="ant-btn" role="button">Link</a>
<input class="ant-btn" type="button" value="Input" />
<input class="ant-btn" type="submit" value="Submit" />
````jsx
import { Button } from 'antd';
<br>
<!-- Styled Button -->
<button class="ant-btn ant-btn-primary">主按钮</button>
<button class="ant-btn">次按钮</button>
<button class="ant-btn ant-btn-ghost">幽灵按钮</button>
ReactDOM.render(<div>
<Button type="primary">主按钮</Button>
<Button>次按钮</Button>
<Button type="ghost">幽灵按钮</Button>
</div>,
document.getElementById('components-button-demo-basic'))
````
<style>
#components-button-demo-basic .ant-btn {
margin-right: 8px;
margin-bottom: 12px;
}
</style>
# 按钮组合
- order: 6
- order: 5
将一系列的 `.ant-btn` 放入 `.ant-btn-group` 的容器中。
可以将多个 `Button` 放入 `Button.Group` 的容器中。
按钮组合尺寸
只要给 `.ant-btn-group` 加上 `.ant-btn-group-*` 类,即可设置不同的尺寸,目前支持大中小三种尺寸。
通过设置 `size``large` `small` 分别把按钮组合设为大、小尺寸。若不设置 `size`,则尺寸为中。
---
````html
````jsx
import { Button, Icon } from 'antd';
const ButtonGroup = Button.Group;
ReactDOM.render(<div>
<h4>基本组合</h4>
<div class="ant-btn-group">
<button class="ant-btn ant-btn-primary">确 定</button>
<button class="ant-btn ant-btn-primary">取 消</button>
</div>
<div class="ant-btn-group">
<button class="ant-btn"></button>
<button class="ant-btn"></button>
<button class="ant-btn"></button>
</div>
<div class="ant-btn-group">
<button class="ant-btn ant-btn-primary"></button>
<button class="ant-btn ant-btn-ghost"></button>
<button class="ant-btn ant-btn-ghost"></button>
<button class="ant-btn"></button>
</div>
<h4>带图标按钮组合 </h4>
<div class="ant-btn-group">
<button class="ant-btn ant-btn-primary">
<span class="anticon anticon-left"></span>
<span>后 退</span>
</button>
<button class="ant-btn ant-btn-primary">
<span>前 进</span>
<span class="anticon anticon-right"></span>
</button>
</div>
<div class="ant-btn-group">
<button class="ant-btn ant-btn-primary">
<span class="anticon anticon-cloud"></span>
</button>
<button class="ant-btn ant-btn-primary">
<span class="anticon anticon-cloud-download"></span>
</button>
</div>
<ButtonGroup>
<Button type="primary">确定</Button>
<Button type="primary">取消</Button>
</ButtonGroup>
<ButtonGroup>
<Button></Button>
<Button></Button>
<Button></Button>
</ButtonGroup>
<ButtonGroup>
<Button type="primary"></Button>
<Button type="ghost"></Button>
<Button type="ghost"></Button>
<Button></Button>
</ButtonGroup>
<h4>带图标按钮组合</h4>
<ButtonGroup>
<Button type="primary">
<Icon type="left" />
<span>后退</span>
</Button>
<Button type="primary">
前进
<Icon type="right" />
</Button>
</ButtonGroup>
<ButtonGroup>
<Button type="primary">
<Icon type="cloud" />
</Button>
<Button type="primary">
<Icon type="cloud-download" />
</Button>
</ButtonGroup>
<h4>多个组合</h4>
<div class="ant-btn-group">
<button class="ant-btn ant-btn-ghost">1</button>
<button class="ant-btn ant-btn-ghost">2</button>
<button class="ant-btn ant-btn-ghost">3</button>
<button class="ant-btn ant-btn-ghost">4</button>
<button class="ant-btn ant-btn-ghost">
<span>前 进</span>
<span class="anticon anticon-right"></span>
</button>
</div>
<ButtonGroup>
<Button type="ghost">1</Button>
<Button type="ghost">2</Button>
<Button type="ghost">3</Button>
<Button type="ghost">4</Button>
<Button type="ghost">
<span>前进</span>
<Icon type="right" />
</Button>
</ButtonGroup>
<h4>尺寸</h4>
<div class="ant-btn-group ant-btn-group-lg">
<button class="ant-btn ant-btn-ghost"></button>
<button class="ant-btn ant-btn-ghost"></button>
<button class="ant-btn ant-btn-ghost"></button>
</div>
<div class="ant-btn-group">
<button class="ant-btn ant-btn-ghost">默 认</button>
<button class="ant-btn ant-btn-ghost">默 认</button>
<button class="ant-btn ant-btn-ghost">默 认</button>
</div>
<div class="ant-btn-group ant-btn-group-sm">
<button class="ant-btn ant-btn-ghost"></button>
<button class="ant-btn ant-btn-ghost"></button>
<button class="ant-btn ant-btn-ghost"></button>
<ButtonGroup size="large">
<Button type="ghost"></Button>
<Button type="ghost"></Button>
<Button type="ghost"></Button>
</ButtonGroup>
<ButtonGroup>
<Button type="ghost">默认</Button>
<Button type="ghost">默认</Button>
<Button type="ghost">默认</Button>
</ButtonGroup>
<ButtonGroup size="small">
<Button type="ghost"></Button>
<Button type="ghost"></Button>
<Button type="ghost"></Button>
</ButtonGroup>
</div>
, document.getElementById('components-button-demo-button-group'));
````
<style>
.nico-insert-code h4 {
margin: 8px 0;
font-size: 12px;
line-height: 12px;
#components-button-demo-button-group h4 {
margin: 16px 0;
font-size: 14px;
line-height: 1;
font-weight: normal;
}
.nico-insert-code h4:first-child {
#components-button-demo-button-group h4:first-child {
margin-top: 0;
}
.nico-insert-code .ant-btn {
#components-button-demo-button-group .ant-btn {
margin-bottom: 8px;
}
#components-button-demo-button-group .ant-btn-group {
margin-right: 8px;
}
#components-button-demo-button-group .ant-btn {
margin-bottom: 12px;
}
</style>
# 不可用
- order: 3
添加 `disabled` 属性即可让按钮处于不可用状态,同时按钮样式也会改变。
---
````jsx
import { Button } from 'antd';
ReactDOM.render(<div>
<Button type="primary">主按钮</Button>
<Button type="primary" disabled>主按钮(失效)</Button>
<br />
<Button>次按钮</Button>
<Button disabled>次按钮(失效)</Button>
<br />
<Button type="ghost">幽灵按钮</Button>
<Button type="ghost" disabled>幽灵按钮(失效)</Button>
</div>
, document.getElementById('components-button-demo-disabled'));
````
<style>
#components-button-demo-disabled .ant-btn {
margin-right: 8px;
margin-bottom: 12px;
}
</style>
# 图标按钮
- order: 4
- order: 6
图标一般放在文字前面,也可以单独存在。
`Button` 内可以嵌套图标,图标可以放在文字前、后,也可以单独存在。
---
````html
<button class="ant-btn ant-btn-primary ant-btn-circle ant-btn-lg">
<i class="anticon anticon-search"></i>
</button>
<button class="ant-btn ant-btn-primary ant-btn-lg">
<i class="anticon anticon-search"></i>
````jsx
import { Button, Icon } from 'antd';
ReactDOM.render(<div>
<Button type="primary" shape="circle" size="large">
<Icon type="search" />
</Button>
<Button type="primary" size="large">
<Icon type="search" />
大按钮
</button>
</Button>
<button class="ant-btn ant-btn-primary ant-btn-circle">
<i class="anticon anticon-search"></i>
</button>
<button class="ant-btn ant-btn-primary">
<i class="anticon anticon-search"></i>
<Button type="primary" shape="circle">
<Icon type="search" />
</Button>
<Button type="primary">
<Icon type="search" />
中按钮
</button>
</Button>
<button class="ant-btn ant-btn-primary ant-btn-circle ant-btn-sm">
<i class="anticon anticon-search"></i>
</button>
<button class="ant-btn ant-btn-primary ant-btn-sm">
<i class="anticon anticon-search"></i>
<Button type="primary" shape="circle" size="small">
<Icon type="search" />
</Button>
<Button type="primary" size="small">
<Icon type="search" />
小按钮
</button>
<p></p>
<button class="ant-btn ant-btn-ghost ant-btn-circle-outline ant-btn-lg">
<i class="anticon anticon-search"></i>
</button>
<button class="ant-btn ant-btn-ghost ant-btn-circle-outline">
<i class="anticon anticon-search"></i>
</button>
<button class="ant-btn ant-btn-circle-outline ant-btn-sm">
<i class="anticon anticon-search"></i>
</button>
</Button>
<br />
<Button type="ghost" shape="circle-outline" size="large">
<Icon type="search" />
</Button>
<Button type="ghost" shape="circle-outline">
<Icon type="search" />
</Button>
<Button type="ghost" shape="circle-outline" size="small">
<Icon type="search" />
</Button>
</div>,
document.getElementById('components-button-demo-icon'));
````
<style>
#components-button-demo-icon .ant-btn {
margin-right: 8px;
margin-bottom: 12px;
}
</style>
# 加载中
- order: 7
- order: 4
加载按钮。最后一个按钮演示点击后进入加载状态。
添加 `loading` 属性即可让按钮处于加载状态,最后一个按钮演示点击后进入加载状态。
---
````jsx
var App = React.createClass({
import { Button } from 'antd';
const App = React.createClass({
getInitialState() {
return {
loading: false
......@@ -19,26 +21,25 @@ var App = React.createClass({
});
},
render() {
var loadingClass = this.state.loading ? 'ant-btn-loading' : '';
return <div>
<button className="ant-btn ant-btn-primary ant-btn-lg ant-btn-loading">
<Button type="primary" size="large" loading={true}>
加载中
</button>
<button className="ant-btn ant-btn-primary ant-btn-loading">
</Button>
<Button type="primary" loading={true}>
加载中
</button>
<button className="ant-btn ant-btn-primary ant-btn-sm ant-btn-loading">
</Button>
<Button type="primary" size="small" loading={true}>
加载中
</button>
</Button>
<br />
<button className={'ant-btn ant-btn-primary ' + loadingClass} onClick={this.enterLoading}>
<Button type="primary" loading={this.state.loading} onClick={this.enterLoading}>
点击变加载
</button>
</Button>
</div>;
}
});
React.render(<App />, document.getElementById('components-button-demo-loading'));
ReactDOM.render(<App />, document.getElementById('components-button-demo-loading'));
````
<style>
......
# 菜单按钮
- order: 5
**注**: 下拉按钮的 icon 大小统一成 **10px**
> 更多交互,详见 [Dropdown 下拉菜单](http://ant.design/components/dropdown/)。
---
````html
<button class="ant-btn ant-btn-primary ant-btn-menu">
<span>菜单按钮</span>
<span class="anticon anticon-down"></span>
</button>
<button class="ant-btn ant-btn-ghost ant-btn-circle ant-btn-menu">
<span class="anticon anticon-down"></span>
</button>
````
# 按钮形状
- order: 1
通过设置 `shape``circle` `circle-outline`,可以把按钮形状设为圆形,并且 `circle-outline` 在 hover 时会有动画效果。
---
````jsx
import { Button, Icon } from 'antd';
ReactDOM.render(<div>
<Button type="primary" shape="circle" size="large">
<Icon type="search" />
</Button>
<Button type="primary" shape="circle">
<Icon type="search" />
</Button>
<Button type="primary" shape="circle" size="small">
<Icon type="search" />
</Button>
<br />
<Button type="ghost" shape="circle-outline" size="large">
<Icon type="search" />
</Button>
<Button type="ghost" shape="circle-outline">
<Icon type="search" />
</Button>
<Button type="ghost" shape="circle-outline" size="small">
<Icon type="search" />
</Button>
</div>
, document.getElementById('components-button-demo-shape'));
````
<style>
#components-button-demo-shape .ant-btn {
margin-right: 8px;
margin-bottom: 12px;
}
</style>
......@@ -2,14 +2,25 @@
- order: 2
提供 大 中 小 三种尺寸。
按钮有大、中、小三种尺寸。
使用 `.ant-btn-lg` `.ant-btn-sm` 即可获得大 小尺寸,默认尺寸为中。
通过设置 `size``large` `small` 分别把按钮设为大、小尺寸。若不设置 `size`,则尺寸为中。
---
````html
<button class="ant-btn ant-btn-primary ant-btn-lg">大号按钮</button>
<button class="ant-btn ant-btn-primary">中号按钮(默认)</button>
<button class="ant-btn ant-btn-primary ant-btn-sm">小号按钮</button>
````jsx
import { Button } from 'antd';
ReactDOM.render(<div>
<Button type="primary" size="large">大号按钮</Button>
<Button type="primary">中号按钮(默认)</Button>
<Button type="primary" size="small">小号按钮</Button>
</div>
, document.getElementById('components-button-demo-size'));
````
<style>
#components-button-demo-size .ant-btn {
margin-right: 8px;
}
</style>
# 按钮状态
- order: 3
通过背景色透明度的变化来体现不同的操作状态,移入或点击元素可以查看状态。
失效状态:为 `<button>` 元素添加 `disabled` 属性,即可体现。
---
````html
<button class="ant-btn ant-btn-primary">主按钮</button>
<button class="ant-btn ant-btn-primary disabled">主按钮(失效)</button>
<p></p>
<button class="ant-btn">次按钮</button>
<button class="ant-btn disabled">次按钮(失效)</button>
<p></p>
<button class="ant-btn ant-btn-ghost">幽灵按钮</button>
<button class="ant-btn ant-btn-ghost disabled">幽灵按钮(失效)</button>
````
import Button from './button';
import ButtonGroup from './button-group';
Button.Group = ButtonGroup;
export default Button;
......@@ -13,29 +13,33 @@
标记了一个(或封装一组)操作命令,响应用户点击行为,触发相应的业务逻辑。
## 如何使用
## API
- 按钮的基础样式为 `ant-btn`
- 通过设置 Button 的属性来产生不同的按钮样式,推荐顺序为:`type` -> `shape` -> `size` -> `loading` -> `disabled`
- 通过类组装的形式来产生不同的按钮样式,推荐遵循如下顺序:
- 按钮的属性说明如下:
属性 | 说明 | 类型 | 默认值
-----|-----|-----|------
type | 设置按钮类型,可选值为 `primary` `ghost` 或者不设 | Enum | undefined
htmlType | 设置 `button` 原生的 `type` 值,可选值请参考 HTML标准 | Enum | `button`
shape | 设置按钮形状,可选值为 `circle` `circle-outline` 或者不设 | Enum | undefined
size | 设置按钮大小,可选值为 `small` `large` 或者不设 | Enum | undefined
loading | 设置按钮载入状态,存在为 `true`,不存在为 `false`,或直接设置值,如:`loading="true"` | Bool | false
onClick | `click` 事件的 handler | Function | `function() {}`
- `<Button>Hello world!</Button>` 最终会被渲染为 `<button>Hello world!</button>`,并且除了上表中的属性,其它属性都会直接传到 `<button></button>`
### IE8 border radius support
Ant Design 视觉上采用渐进降级的方案,在 IE8 下圆角按钮将降级为直角。
如果强烈需要圆角按钮,我们提供了 [css3pie](http://css3pie.com/) 的兼容方案。
使用时只需在 html 头部加入以下代码即可。
```html
<!--[if IE 8]>
<script src="https://t.alipayobjects.com/images/rmsweb/T1q8JiXftaXXXXXXXX.js"></script>
<![endif]-->
```
.ant-btn
&darr;
.ant-btn-primary | .ant-btn-ghost
&darr;
.ant-btn-circle | .ant-btn-circle-outline
&darr;
.ant-btn-lg | .ant-btn-sm
```
- 按钮的样式参数说明如下:
| 类名 | 说明 |
| ------------- | ------------- |
| `.ant-btn` | 按钮基础样式。 |
| `.ant-btn-primary` `.ant-btn-ghost` | 使用这些列出的类可以快速创建一个带有预定义样式的按钮。 |
| `.ant-btn-circle` `.ant-btn-circle-outline` | 用于创建圆形按钮,`.ant-btn-circle-outline` 为描边按钮。 |
| `.ant-btn-lg` `.ant-btn-sm` | 定义按钮大小尺寸,目前提供三种尺寸:大中小,默认为中。 |
| `.ant-btn-group` | 按钮组合,通过按钮组容器把一组按钮放在同一行里。 |
> 当按钮只有两个汉字时,需要在两字中加空格。
export const PREFIX_CLS = 'ant-fullcalendar';
import React, {PropTypes, Component} from 'react';
import {PREFIX_CLS} from './Constants';
import Select from '../select';
import {Group, Button} from '../radio';
function noop() {}
class Header extends Component {
getYearSelectElement(year) {
const {yearSelectOffset, yearSelectTotal, locale, prefixCls, fullscreen} = this.props;
const start = year - yearSelectOffset;
const end = start + yearSelectTotal;
const suffix = locale.year === '' ? '' : '';
const options = [];
for (let index = start; index < end; index++) {
options.push(<Option key={`${index}`}>{index + suffix}</Option> );
}
return (
<Select
style={{ width: 75 }}
size={ fullscreen ? null : 'small' }
dropdownMatchSelectWidth={false}
dropdownMenuStyle={{ minWidth: 103 }}
className={`${prefixCls}-year-select`}
onChange={this.onYearChange.bind(this)}
value={String(year)}>
{ options }
</Select>
);
}
getMonthSelectElement(month) {
const props = this.props;
const months = props.locale.format.months;
const {prefixCls, fullscreen} = props;
const options = [];
for (let index = 0; index < 12; index++) {
options.push(<Option key={`${index}`}>{months[index]}</Option>);
}
return (
<Select
style={{ minWidth: 70 }}
dropdownMenuStyle={{ minWidth: 125 }}
size={ fullscreen ? null : 'small' }
dropdownMatchSelectWidth={false}
className={`${prefixCls}-month-select`}
value={String(month)}
onChange={this.onMonthChange.bind(this)}>
{ options }
</Select>
);
}
onYearChange(year) {
const newValue = this.props.value.clone();
newValue.setYear(parseInt(year, 10));
this.props.onValueChange(newValue);
}
onMonthChange(month) {
const newValue = this.props.value.clone();
newValue.setMonth(parseInt(month, 10));
this.props.onValueChange(newValue);
}
onTypeChange(e) {
this.props.onTypeChange(e.target.value);
}
render() {
const {type, value, prefixCls, locale} = this.props;
const yearSelect = this.getYearSelectElement(value.getYear());
const monthSelect = type === 'date' ? this.getMonthSelectElement(value.getMonth()) : null;
const typeSwitch = (
<Group onChange={this.onTypeChange.bind(this)} value={type}>
<Button value="date">{locale.month}</Button>
<Button value="month">{locale.year}</Button>
</Group>
);
return (
<div className={`${prefixCls}-header`}>
{ yearSelect }
{ monthSelect }
{ typeSwitch }
</div>
);
}
}
Header.propTypes = {
value: PropTypes.object,
locale: PropTypes.object,
yearSelectOffset: PropTypes.number,
yearSelectTotal: PropTypes.number,
onValueChange: PropTypes.func,
onTypeChange: PropTypes.func,
prefixCls: PropTypes.string,
selectPrefixCls: PropTypes.string,
type: PropTypes.string,
};
Header.defaultProps = {
prefixCls: `${PREFIX_CLS}-header`,
yearSelectOffset: 10,
yearSelectTotal: 20,
onValueChange: noop,
onTypeChange: noop,
};
export default Header;
# 基本
- order: 0
一个通用的日历面板,支持年/月切换。
---
````jsx
import { Calendar } from 'antd';
function onPanelChange(value, mode) {
console.log(value, mode);
}
ReactDOM.render(
<Calendar onPanelChange={onPanelChange} />
, document.getElementById('components-calendar-demo-basic'));
````
# 卡片模式
- order: 10
用于嵌套在空间有限的容器中。
---
````jsx
import { Calendar } from 'antd';
function onPanelChange(value, mode) {
console.log(value, mode);
}
ReactDOM.render(
<div style={{ width: 290, border: '1px solid #d9d9d9', borderRadius: 4 }}>
<Calendar fullscreen={false} onPanelChange={onPanelChange} />
</div>
, document.getElementById('components-calendar-demo-card'));
````
# 自定义渲染
- order: 1
`dateCellRender``monthCellRender` 函数来自定义需要渲染的数据。
---
````jsx
import { Calendar } from 'antd';
function dateCellRender(value) {
return <div>自定义日数据</div>;
}
function monthCellRender(value) {
return <div>自定义月数据</div>;
}
ReactDOM.render(
<Calendar defaultValue={new Date('2010-10-10')}
dateCellRender={dateCellRender} monthCellRender={monthCellRender} />
, document.getElementById('components-calendar-demo-custom-render'));
````
# 国际化
- order: 4
通过 `locale` 配置时区、语言等, 默认支持 en_US, zh_CN
---
````jsx
import { Calendar } from 'antd';
import enUS from 'antd/lib/calendar/locale/en_US';
function onPanelChange(value, mode) {
console.log(value, mode);
}
ReactDOM.render(
<Calendar onPanelChange={onPanelChange} locale={enUS}/>
, document.getElementById('components-calendar-demo-locale'));
````
# 通知事项日历演示
- order: 2
一个复杂的应用实例。
---
````jsx
import { Calendar } from 'antd';
function getListData(value) {
var listData;
switch (value.getDayOfMonth()) {
case 8:
listData = [
{ type: 'warn', content: '这里是警告事项.' },
{ type: 'normal', content: '这里是普通事项.' }
]; break;
case 10:
listData = [
{ type: 'warn', content: '这里是警告事项.' },
{ type: 'normal', content: '这里是普通事项.' },
{ type: 'error', content: '这里是错误事项.' }
]; break;
case 15:
listData = [
{ type: 'warn', content: '这里是警告事项.' },
{ type: 'normal', content: '这里是普通事项好长啊。。....' },
{ type: 'error', content: '这里是错误事项.' },
{ type: 'error', content: '这里是错误事项.' },
{ type: 'error', content: '这里是错误事项.' },
{ type: 'error', content: '这里是错误事项.' }
]; break;
}
return listData || [];
}
function dateCellRender(value) {
let listData = getListData(value);
return <ul className="events">
{listData.map((item, index) =>
<li key={index}>
<span className={`event-${item.type}`}></span>
{item.content}
</li>
)}
</ul>;
}
function getMonthData(value) {
if (value.getMonth() === 8) {
return 1394;
}
}
function monthCellRender(value) {
let num = getMonthData(value);
return num ? <div className="notes-month">
<section>{num}</section>
<span>待办事项数</span>
</div> : null;
}
ReactDOM.render(
<Calendar dateCellRender={dateCellRender} monthCellRender={monthCellRender} />
, document.getElementById('components-calendar-demo-notice-calendar'));
````
````css
.events {
line-height: 24px;
list-style: none;
margin: 0;
padding: 0;
}
.events li {
color: #999;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
.events li span {
vertical-align: middle;
}
.events li span:first-child {
font-size: 9px;
margin-right: 4px;
}
.event-warn {
color: #fac450;
}
.event-normal {
color: #2db7f5;
}
.event-error {
color: #f60;
}
.notes-month {
text-align: center;
}
.notes-month section {
font-size: 28px;
}
````
import React, {PropTypes, Component} from 'react';
import GregorianCalendar from 'gregorian-calendar';
import zhCN from './locale/zh_CN';
import FullCalendar from 'rc-calendar/lib/FullCalendar';
import {PREFIX_CLS} from './Constants';
import Header from './Header';
function noop () { return null; }
function zerofixed (v) {
if (v < 10) return '0' + v;
return v + '';
}
class Calendar extends Component {
constructor(props) {
super(props);
this.state = {
value: this.parseDateFromValue(props.value || new Date()),
mode: props.mode,
};
}
parseDateFromValue(value) {
const date = new GregorianCalendar(this.props.locale);
date.setTime(+value);
return date;
}
componentWillReceiveProps(nextProps) {
if ('value' in nextProps) {
this.setState({
value: this.parseDateFromValue(nextProps.value)
});
}
}
monthCellRender(value, locale) {
const prefixCls = this.props.prefixCls;
const month = value.getMonth();
return <div className={`${prefixCls}-month`}>
<div className={`${prefixCls}-value`}>
{locale.format.shortMonths[month]}
</div>
<div className={`${prefixCls}-content`}>
{this.props.monthCellRender(value)}
</div>
</div>;
}
dateCellRender(value) {
const prefixCls = this.props.prefixCls;
return <div className={`${prefixCls}-date`}>
<div className={`${prefixCls}-value`}>
{zerofixed(value.getDayOfMonth())}
</div>
<div className={`${prefixCls}-content`}>
{this.props.dateCellRender(value)}
</div>
</div>;
}
setValue(value) {
if (!('value' in this.props) && this.state.value !== value) {
this.setState({ value });
}
this.props.onPanelChange(value, this.state.mode);
}
setType(type) {
const mode = (type === 'date') ? 'month' : 'year';
if (this.state.mode !== mode) {
this.setState({ mode });
this.props.onPanelChange(this.state.value, mode);
}
}
onPanelSelect(value, e) {
if (e && e.target === 'month') {
// Because the fullcalendars'type will automaticlly change to 'date' when select month cell
// but we didn't want this, so we force update view to get things right
// since ours 'mode' would not change.
this.forceUpdate();
}
}
render() {
const props = this.props;
const {value, mode} = this.state;
const {locale, prefixCls, style, className, fullscreen} = props;
const type = (mode === 'year') ? 'month' : 'date';
let cls = className || '';
if (fullscreen) {
cls += (' ' + prefixCls + '-fullscreen');
}
return (
<div className={cls} style={style}>
<Header
fullscreen={fullscreen}
type={type}
value={value}
locale={locale.lang}
prefixCls={prefixCls}
onTypeChange={this.setType.bind(this)}
onValueChange={this.setValue.bind(this)}/>
<FullCalendar
{...props}
locale={locale.lang}
type={type}
prefixCls={prefixCls}
showHeader={false}
onSelect={this.onPanelSelect.bind(this)}
value={value}
monthCellRender={this.monthCellRender.bind(this)}
dateCellRender={this.dateCellRender.bind(this)} />
</div>
);
}
}
Calendar.propTypes = {
monthCellRender: PropTypes.func,
dateCellRender: PropTypes.func,
fullscreen: PropTypes.bool,
locale: PropTypes.object,
prefixCls: PropTypes.string,
className: PropTypes.string,
style: PropTypes.object,
onPanelChange: PropTypes.func,
value: PropTypes.instanceOf(Date),
};
Calendar.defaultProps = {
monthCellRender: noop,
dateCellRender: noop,
locale: zhCN,
fullscreen: true,
prefixCls: PREFIX_CLS,
onPanelChange: noop,
mode: 'month',
};
export default Calendar;
# Calendar
- category: Components
- type: 展示
- chinese: 日历
- cols: 1
---
按照日历形式展示数据的容器。
## 何时使用
当数据是日期或按照日期划分时,例如日程、课表、价格日历等,农历等。目前支持年/月切换。
## API
```html
<Calendar
dateCellRender={dateCellRender}
monthCellRender={monthCellRender}
onPanelChange={onPanelChange}
/>
```
| 参数 | 说明 | 类型 | 默认值 |
|--------------|----------------|----------|--------------|
| value | 展示日期 | Date | 当前日期 |
| defaultValue | 默认展示日期 | Date | 当前日期 |
| mode | 初始模式,`month/year` | string | month |
| fullscreen | 是否全屏显示 | bool | true |
| dateCellRender | 自定义渲染日期单元格| function([GregorianCalendar](https://github.com/yiminghe/gregorian-calendar/))| 无 |
| monthCellRender | 自定义渲染月单元格 | function([GregorianCalendar](https://github.com/yiminghe/gregorian-calendar/)) | 无 |
| locale | 国际化配置 | object | [默认配置](https://github.com/ant-design/ant-design/issues/424) |
| onPanelChange| 日期面板变化回调 | function(date, mode) | 无 |
module.exports = require('../../datepicker/locale/en_US');
module.exports = require('../../datepicker/locale/zh_CN');
......@@ -7,9 +7,9 @@
---
````jsx
var Carousel = antd.Carousel;
import { Carousel } from 'antd';
React.render(
ReactDOM.render(
<Carousel autoplay="true">
<div><h3>1</h3></div>
<div><h3>2</h3></div>
......
......@@ -7,10 +7,14 @@
---
````jsx
var Carousel = antd.Carousel;
import { Carousel } from 'antd';
React.render(
<Carousel>
function onChange(a, b, c) {
console.log(a, b, c);
}
ReactDOM.render(
<Carousel afterChange={onChange}>
<div><h3>1</h3></div>
<div><h3>2</h3></div>
<div><h3>3</h3></div>
......
......@@ -7,9 +7,9 @@
---
````jsx
var Carousel = antd.Carousel;
import { Carousel } from 'antd';
React.render(
ReactDOM.render(
<Carousel effect="fade">
<div><h3>1</h3></div>
<div><h3>2</h3></div>
......
......@@ -7,9 +7,9 @@
---
````jsx
var Carousel = antd.Carousel;
import { Carousel } from 'antd';
React.render(
ReactDOM.render(
<Carousel vertical="true">
<div><h3>1</h3></div>
<div><h3>2</h3></div>
......
// matchMedia polyfill for
// https://github.com/WickyNilliams/enquire.js/issues/82
if (typeof window !== 'undefined') {
const matchMediaPolyfill = function matchMediaPolyfill() {
return {
matches: false,
addListener: function () {
},
removeListener: function () {
}
};
};
window.matchMedia = window.matchMedia || matchMediaPolyfill;
}
import Carousel from 'react-slick';
import React from 'react';
import assign from 'object-assign';
......
......@@ -19,12 +19,14 @@
| 参数 | 说明 | 类型 | 默认值 |
|------------------|----------------------------------------------|----------|---------------------------------|
| effect | 动画效果函数,可取 scrollx, fade | String | scrollx |
| arrow | 是否显示前后翻页箭头 | Boolean | false |
| dots | 是否显示面板指示点 | Boolean | true |
| vertical | 垂直显示 | Boolean | false |
| autoplay | 是否自动切换 | Boolean | false |
| easing | 动画效果 | String | linear |
| onChange | 切换面板的回调 | Function | 无
| beforeChange | 切换面板的回调 | function(from, to) | 无
| afterChange | 切换面板的回调 | function(current) | 无
更多参数可参考:https://github.com/akiran/react-slick
<style>
.ant-carousel .slick-slide {
......
......@@ -7,13 +7,14 @@
---
````jsx
var Checkbox = antd.Checkbox;
var container = document.getElementById('components-checkbox-demo-basic');
import { Checkbox } from 'antd';
const container = document.getElementById('components-checkbox-demo-basic');
function onChange(e) {
console.log('checked = ' + e.target.checked);
}
React.render(<label>
ReactDOM.render(<label>
<Checkbox defaultChecked={false} onChange={onChange} />
Checkbox
</label>, container);
......
......@@ -7,15 +7,15 @@
---
````jsx
var Checkbox = antd.Checkbox;
var container = document.getElementById('components-checkbox-demo-controller');
import { Checkbox, Button } from 'antd';
const container = document.getElementById('components-checkbox-demo-controller');
var App = React.createClass({
const App = React.createClass({
getInitialState() {
return {
checked: true,
disabled: false
}
};
},
render() {
var label = (this.state.checked ? '选中' : '取消') + '-' +
......@@ -30,15 +30,15 @@ var App = React.createClass({
</label>
</p>
<p>
<button className="ant-btn ant-btn-primary ant-btn-sm"
<Button type="primary" size="small"
onClick={this.toggleChecked}>
{!this.state.checked ? "选中":"取消"}
</button>
<button style={{'marginLeft': '10px'}}
className="ant-btn ant-btn-primary ant-btn-sm"
</Button>
<Button style={{'marginLeft': '10px'}}
type="primary" size="small"
onClick={this.toggleDisable}>
{!this.state.disabled ? "不可用":"可用"}
</button>
</Button>
</p>
</div>;
},
......@@ -56,5 +56,5 @@ var App = React.createClass({
}
});
React.render(<App />, container);
ReactDOM.render(<App />, container);
````
......@@ -7,10 +7,10 @@ checkbox 不可用。
---
````jsx
var Checkbox = antd.Checkbox;
var container = document.getElementById('components-checkbox-demo-disable');
import { Checkbox } from 'antd';
const container = document.getElementById('components-checkbox-demo-disable');
React.render(<div>
ReactDOM.render(<div>
<Checkbox defaultChecked={false} disabled={true}/>
<br />
<Checkbox defaultChecked={true} disabled={true}/>
......
......@@ -7,16 +7,16 @@
---
````jsx
var Collapse = antd.Collapse;
var Panel = Collapse.Panel;
import { Collapse } from 'antd';
const Panel = Collapse.Panel;
var text = `
const text = `
A dog is a type of domesticated animal.
Known for its loyalty and faithfulness,
it can be found as a welcome guest in many households across the world.
`;
React.render(
ReactDOM.render(
<Collapse accordion={true}>
<Panel header={`This is panel header 1`} key="1">
<p>{text}</p>
......
......@@ -7,20 +7,20 @@
---
````jsx
var Collapse = antd.Collapse;
var Panel = Collapse.Panel;
import { Collapse } from 'antd';
const Panel = Collapse.Panel;
function callback(key) {
console.log(key);
}
var text = `
const text = `
A dog is a type of domesticated animal.
Known for its loyalty and faithfulness,
it can be found as a welcome guest in many households across the world.
`;
React.render(
ReactDOM.render(
<Collapse defaultActiveKey={["1"]} onChange={callback}>
<Panel header={`This is panel header 1`} key="1">
<p>{text}</p>
......
......@@ -7,20 +7,20 @@
---
````jsx
var Collapse = antd.Collapse;
var Panel = Collapse.Panel;
import { Collapse } from 'antd';
const Panel = Collapse.Panel;
function callback(key) {
console.log(key);
}
var text = `
const text = `
A dog is a type of domesticated animal.
Known for its loyalty and faithfulness,
it can be found as a welcome guest in many households across the world.
`;
React.render(
ReactDOM.render(
<Collapse onChange={callback} accordion={true}>
<Panel header={`This is panel header 1`} key="1">
<Collapse defaultActiveKey="1">
......
......@@ -7,10 +7,9 @@
---
````jsx
// or require('antd/lib/datepicker');
var Datepicker = antd.Datepicker;
import { Datepicker } from 'antd';
React.render(
<Datepicker defaultValue="2012-12-12" />
ReactDOM.render(
<Datepicker defaultValue="2015-12-12" />
, document.getElementById('components-datepicker-demo-basic'));
````
......@@ -7,9 +7,9 @@
---
````jsx
var Datepicker = antd.Datepicker;
import { Datepicker } from 'antd';
React.render(
<Datepicker value="2015-06-06" disabled={true} />
ReactDOM.render(
<Datepicker defaultValue="2015-06-06" disabled={true} />
, document.getElementById('components-datepicker-demo-disabled'));
````
......@@ -7,9 +7,9 @@
---
````jsx
var Datepicker = antd.Datepicker;
import { Datepicker } from 'antd';
React.render(
<Datepicker value="2015/01/01" format="yyyy/MM/dd" />
ReactDOM.render(
<Datepicker defaultValue="2015/01/01" format="yyyy/MM/dd" />
, document.getElementById('components-datepicker-demo-formatter'));
````
# 国际化
- order: 9
通过 `locale` 配置时区、语言等, 默认支持 en_US, zh_CN
---
````jsx
import { Datepicker } from 'antd';
import enUS from 'antd/lib/datepicker/locale/en_US';
import assign from 'object-assign'
const App = React.createClass({
getInitialState() {
return {
locale: assign({}, enUS, {
timezoneOffset: 0 * 60,
firstDayOfWeek: 0,
minimalDaysInFirstWeek: 1
})
};
},
render() {
return <Datepicker showTime={true} locale={this.state.locale} />;
}
});
ReactDOM.render(<App />, document.getElementById('components-datepicker-demo-locale'));
````
# 范围
# 指定不可选择日期
- order: 3
- order: 6
设置 `disabledDate` 方法,来确定不可选时段。
......@@ -9,13 +9,14 @@
---
````jsx
var Datepicker = antd.Datepicker;
var disabledDate = function(current, value) {
import { Datepicker } from 'antd';
const disabledDate = function(current, value) {
// can not select days after today
return current.getTime() > Date.now();
return current && current.getTime() > Date.now();
};
React.render(
ReactDOM.render(
<Datepicker disabledDate={disabledDate} />
, document.getElementById('components-datepicker-demo-range'));
````
......@@ -2,23 +2,23 @@
- order: 2
通过设置选择日期的回调事件 `onSelect`,完成交互行为。
通过设置选择日期的回调事件 `onChange`,完成交互行为。
---
````jsx
var Datepicker = antd.Datepicker;
import { Datepicker } from 'antd';
var Picker = React.createClass({
const Picker = React.createClass({
handleChange: function(value) {
console.log(new Date(value.getTime()));
},
render: function() {
return <Datepicker onSelect={this.handleChange} />
return <Datepicker onChange={this.handleChange} />
}
});
React.render(
ReactDOM.render(
<Picker />
, document.getElementById('components-datepicker-demo-select'));
````
......@@ -7,9 +7,9 @@
---
````jsx
var Datepicker = antd.Datepicker;
import { Datepicker } from 'antd';
React.render(
ReactDOM.render(
<div>
<Datepicker size="large" />
<Datepicker />
......
# 日期范围选择
- order: 7
设置 `disabledDate` 方法,来约束开始和结束日期。
---
````jsx
import { Datepicker } from 'antd';
const DateRange = React.createClass({
getInitialState() {
return {
startValue: null,
endValue: null
};
},
disabledStartDate(startValue) {
if (!startValue || !this.state.endValue) {
return false;
}
return startValue.getTime() >= this.state.endValue.getTime();
},
disabledEndDate(endValue) {
if (!endValue || !this.state.startValue) {
return false;
}
return endValue.getTime() <= this.state.startValue.getTime();
},
onChange(field, value) {
console.log(field,'change',value);
this.setState({
[field]: value,
});
},
render() {
return <div>
<Datepicker disabledDate={this.disabledStartDate}
value={this.state.startValue}
placeholder="开始日期"
onChange={this.onChange.bind(this,'startValue')} />
<Datepicker disabledDate={this.disabledEndDate}
value={this.state.endValue}
placeholder="结束日期"
onChange={this.onChange.bind(this,'endValue')} />
</div>;
}
});
ReactDOM.render(
<DateRange />
, document.getElementById('components-datepicker-demo-start-end'));
````
......@@ -7,10 +7,9 @@
---
````jsx
var Datepicker = antd.Datepicker;
import { Datepicker } from 'antd';
React.render(
<Datepicker showTime={true} format="yyyy-MM-dd HH:mm:ss" />
ReactDOM.render(
<Datepicker showTime={true} format="yyyy-MM-dd HH:mm:ss" defaultValue="2015-11-11 11:11:11"/>
, document.getElementById('components-datepicker-demo-time'));
````
import React from 'react';
import Calendar, {MonthCalendar, Picker as Datepicker} from 'rc-calendar';
import Calendar from 'rc-calendar';
import MonthCalendar from 'rc-calendar/lib/MonthCalendar';
import Datepicker from 'rc-calendar/lib/Picker';
import GregorianCalendar from 'gregorian-calendar';
import zhCn from 'gregorian-calendar/lib/locale/zh-cn';
import CalendarLocale from 'rc-calendar/lib/locale/zh-cn';
import defaultLocale from './locale/zh_CN';
import CalendarLocale from 'rc-calendar/lib/locale/zh_CN';
import DateTimeFormat from 'gregorian-calendar-format';
// 和顶部文案保持一致
import Locale from 'gregorian-calendar-format/lib/locale/zh-cn';
Locale.shortMonths = ['1月', '2月', '3月', '4月', '5月', '6月',
'7月', '8月', '9月', '10月', '11月', '12月'];
// 以下两行代码
// 给没有初始值的日期选择框提供本地化信息
let defaultCalendarValue = new GregorianCalendar(zhCn);
defaultCalendarValue.setTime(Date.now());
import objectAssign from 'object-assign';
function createPicker(TheCalendar) {
return React.createClass({
getDefaultProps() {
return {
format: 'yyyy-MM-dd',
transitionName: 'slide-up',
popupStyle: {},
onSelect: null, // 向前兼容
onChange() {
}, // onChange 可用于 Validator
locale: {},
align: {
offset: [0, -10],
},
open: false
};
},
getInitialState() {
let value;
if (this.props.value) {
value = new GregorianCalendar(zhCn);
value.setTime(new Date(this.props.value).valueOf());
}
return {
value: value
value: this.parseDateFromValue(this.props.value || this.props.defaultValue)
};
},
componentWillReceiveProps(nextProps) {
if ('value' in nextProps) {
let value = null;
if (nextProps.value) {
value = new GregorianCalendar(zhCn);
value.setTime(new Date(nextProps.value).valueOf());
}
this.setState({
value: value
value: this.parseDateFromValue(nextProps.value)
});
}
},
getDefaultProps() {
return {
format: 'yyyy-MM-dd',
placeholder: '请选择日期',
transitionName: 'slide-up',
onSelect() {
getLocale() {
// 统一合并为完整的 Locale
let locale = objectAssign({}, defaultLocale, this.props.locale);
locale.lang = objectAssign({}, defaultLocale.lang, this.props.locale.lang);
return locale;
},
getFormatter() {
const formats = this.formats = this.formats || {};
const format = this.props.format;
if (formats[format]) {
return formats[format];
}
formats[format] = new DateTimeFormat(format, this.getLocale().lang.format);
return formats[format];
},
parseDateFromValue(value) {
if (value) {
if (typeof value === 'string') {
return this.getFormatter().parse(value, {locale: this.getLocale()});
} else if (value instanceof Date) {
let date = new GregorianCalendar(this.getLocale());
date.setTime(value);
return date;
}
};
} else if (value === null) {
return value;
}
return undefined;
},
// remove input readonly warning
handleInputChange() {
},
handleChange(v) {
toggleOpen(e) {
this.setState({
value: v
open: e.open
});
this.props.onSelect(new Date(v.getTime()));
},
handleChange(value) {
this.setState({value});
const timeValue = value ? new Date(value.getTime()) : null;
// onSelect 为向前兼容.
if (this.props.onSelect) {
require('util-deprecate')(
this.props.onSelect,
'onSelect property of Datepicker is deprecated, use onChange instead'
)(timeValue);
}
this.props.onChange(timeValue);
},
render() {
let calendar = (
// 以下两行代码
// 给没有初始值的日期选择框提供本地化信息
// 否则会以周日开始排
let defaultCalendarValue = new GregorianCalendar(this.getLocale());
defaultCalendarValue.setTime(Date.now());
const placeholder = ('placeholder' in this.props)
? this.placeholder : this.getLocale().lang.placeholder;
const calendar = (
<TheCalendar
disabledDate={this.props.disabledDate}
locale={CalendarLocale}
orient={['top', 'left']}
locale={this.getLocale().lang}
defaultValue={defaultCalendarValue}
dateInputPlaceholder={placeholder}
showTime={this.props.showTime}
prefixCls="ant-calendar"
showOk={this.props.showTime}
showClear={false} />
showClear={true}/>
);
let sizeClass = '';
if (this.props.size === 'large') {
sizeClass = ' ant-input-lg';
} else if (this.props.size === 'small') {
sizeClass = ' ant-input-sm';
}
let defaultValue;
if (this.props.defaultValue) {
defaultValue = new GregorianCalendar(zhCn);
defaultValue.setTime(new Date(this.props.defaultValue).valueOf());
let pickerClass = 'ant-calendar-picker';
if (this.state.open) {
pickerClass += ' ant-calendar-picker-open';
}
return (
return <span className={pickerClass}>
<Datepicker
transitionName={this.props.transitionName}
disabled={this.props.disabled}
trigger={<span className="ant-calendar-picker-icon" />}
calendar={calendar}
adjustOrientOnCalendarOverflow={{x: true, y: false}}
formatter={new DateTimeFormat(this.props.format)}
value={this.state.value}
defaultValue={defaultValue}
prefixCls="ant-calendar-picker"
style={this.props.style}
prefixCls="ant-calendar-picker-container"
style={this.props.popupStyle}
align={this.props.align}
onOpen={this.toggleOpen}
onClose={this.toggleOpen}
onChange={this.handleChange}>
<input
placeholder={this.props.placeholder}
className={'ant-calendar-picker-input ant-input' + sizeClass}/>
{
({value}) => {
return (
<span>
<input disabled={this.props.disabled}
onChange={this.handleInputChange}
value={value && this.getFormatter().format(value)}
placeholder={placeholder}
className={'ant-calendar-picker-input ant-input' + sizeClass}/>
<span className="ant-calendar-picker-icon"/>
</span>
);
}
}
</Datepicker>
);
</span>;
}
});
}
const AntDatePicker = createPicker(Calendar);
const AntMonthPicker = createPicker(MonthCalendar);
const AntCalendar = React.createClass({
......@@ -111,7 +162,7 @@ const AntCalendar = React.createClass({
};
},
render() {
return <Calendar {...this.props}/>;
return <Calendar {...this.props} />;
}
});
......
......@@ -6,16 +6,16 @@
---
输入或选择日期/时间的控件。
输入或选择日期的控件。
## 何时使用
当用户需要输入一个日期/时间,可以点击标准输入框,弹出日期面板进行选择。支持键盘操作
当用户需要输入一个日期,可以点击标准输入框,弹出日期面板进行选择
## API
```html
<Datepicker value="2015-01-01" />
<Datepicker defaultValue="2015-01-01" />
```
| 参数 | 说明 | 类型 | 默认值 |
......@@ -24,13 +24,15 @@
| defaultValue | 默认日期 | string | 无 |
| format | 展示的日期格式 | string | "yyyy-MM-dd" |
| disabledDate | 不可选择的日期 | function | 无 |
| onSelect | 选择日期的回调 | function | 无 |
| onChange | 时间发生变化的回调,发生在用户选择时间时 | function(Date value) | 无 |
| showTime | 显示时间选择条 | boolean | false |
| disabled | 禁用 | bool | false |
| calendarStyle | 格外的弹出日历样式,例如 zIndex | object | {} |
| size | 输入框大小,`large` 高度为 32px,`small` 为 22px,默认是 28px | string | 无 |
| locale | 国际化配置 | object | [默认配置](https://github.com/ant-design/ant-design/issues/424) |
<style>
.code-box-demo .ant-calendar-picker {
margin: 0 12px 12px 0;
margin: 0 8px 12px 0;
}
</style>
import objectAssign from 'object-assign';
import GregorianCalendarLocale from 'gregorian-calendar/lib/locale/en_US';
import CalendarLocale from 'rc-calendar/lib/locale/en_US';
// 统一合并为完整的 Locale
let locale = objectAssign({}, GregorianCalendarLocale);
locale.lang = objectAssign({
placeholder: 'Select a date'
}, CalendarLocale);
// All settings at:
// https://github.com/ant-design/ant-design/issues/424
export default locale;
import objectAssign from 'object-assign';
import GregorianCalendarLocale from 'gregorian-calendar/lib/locale/zh_CN';
import CalendarLocale from 'rc-calendar/lib/locale/zh_CN';
// 统一合并为完整的 Locale
let locale = objectAssign({}, GregorianCalendarLocale);
locale.lang = objectAssign({
placeholder: '请选择日期'
}, CalendarLocale);
// All settings at:
// https://github.com/ant-design/ant-design/issues/424
export default locale;
......@@ -7,10 +7,9 @@
---
````jsx
var Menu = antd.Menu;
var Dropdown = antd.Dropdown;
import { Menu, Dropdown, Button, Icon } from 'antd';
var menu = <Menu>
const menu = <Menu>
<Menu.Item>
<a target="_blank" href="http://www.alipay.com/">第一个菜单项</a>
</Menu.Item>
......@@ -22,11 +21,11 @@ var menu = <Menu>
</Menu.Item>
</Menu>;
React.render(
ReactDOM.render(
<Dropdown overlay={menu}>
<button className="ant-btn ant-btn-menu">
某按钮 <i className="anticon anticon-down"></i>
</button>
<Button>
某按钮 <Icon type="down" />
</Button>
</Dropdown>
, document.getElementById('components-dropdown-demo-basic'));
````
......
......@@ -7,23 +7,22 @@
---
````jsx
var Menu = antd.Menu;
var Dropdown = antd.Dropdown;
var onSelect = function ({key}){
alert('选中了菜单' + key);
import { Menu, Dropdown, Button, Icon } from 'antd';
const onClick = function({key}) {
console.log('点击了菜单' + key);
};
var menu = <Menu onSelect={onSelect}>
const menu = <Menu onClick={onClick}>
<Menu.Item key="1">第一个菜单项</Menu.Item>
<Menu.Item key="2">第二个菜单项</Menu.Item>
<Menu.Item key="3">第三个菜单项</Menu.Item>
</Menu>;
React.render(
ReactDOM.render(
<Dropdown overlay={menu}>
<button className="ant-btn ant-btn-menu">
鼠标移入,点击菜单 <i className="anticon anticon-down"></i>
</button>
<Button>
鼠标移入,点击菜单 <Icon type="down" />
</Button>
</Dropdown>
, document.getElementById('components-dropdown-demo-event'));
````
......@@ -7,10 +7,9 @@
---
````jsx
var Menu = antd.Menu;
var Dropdown = antd.Dropdown;
import { Menu, Dropdown, Button, Icon } from 'antd';
var menu = <Menu>
const menu = <Menu>
<Menu.Item key="0">
<a target="_blank" href="http://www.alipay.com/">第一个菜单项</a>
</Menu.Item>
......@@ -21,11 +20,11 @@ var menu = <Menu>
<Menu.Item key="3" disabled>第三个菜单项(不可用)</Menu.Item>
</Menu>;
React.render(
ReactDOM.render(
<Dropdown overlay={menu}>
<button className="ant-btn ant-btn-menu">
鼠标移入 <i className="anticon anticon-down"></i>
</button>
<Button>
鼠标移入 <Icon type="down" />
</Button>
</Dropdown>
, document.getElementById('components-dropdown-demo-item'));
````
......@@ -7,10 +7,9 @@
---
````jsx
var Menu = antd.Menu;
var Dropdown = antd.Dropdown;
import { Menu, Dropdown, Button, Icon } from 'antd';
var menu = <Menu>
const menu = <Menu>
<Menu.Item key="0">
<a href="http://www.alipay.com/">第一个菜单项</a>
</Menu.Item>
......@@ -21,16 +20,16 @@ var menu = <Menu>
<Menu.Item key="3">第三个菜单项</Menu.Item>
</Menu>;
React.render(<div>
<Dropdown overlay={menu} trigger="click">
<button className="ant-btn ant-btn-primary ant-btn-menu">
点击触发 <i className="anticon anticon-down"></i>
</button>
ReactDOM.render(<div>
<Dropdown overlay={menu} trigger={["click"]}>
<Button type="primary">
点击触发 <Icon type="down" />
</Button>
</Dropdown>
<Dropdown overlay={menu}>
<button className="ant-btn ant-btn-menu">
鼠标移入 <i className="anticon anticon-down"></i>
</button>
<Button>
鼠标移入 <Icon type="down" />
</Button>
</Dropdown>
</div>, document.getElementById('components-dropdown-demo-trigger'));
````
......@@ -5,7 +5,7 @@ export default React.createClass({
getDefaultProps: function () {
return {
transitionName: 'slide-up',
prefixCls: 'ant-dropdown'
prefixCls: 'ant-dropdown',
};
},
render: function () {
......
......@@ -20,7 +20,7 @@
|-------------|------------------|--------------------|--------------|
| trigger | 触发下拉的行为 | "click" or "hover" | hover |
| overlay | 菜单节点 | React.Element | 无 |
| onSelect | 选择后的回调 | function(e) {} | 无 |
| onClick | 点击菜单后的回调 | function({key,keyPath,item,domEvent}) {} | 无 |
菜单可由 `antd.Menu` 取得,可设置 `onSelect` 回调,菜单还包括菜单项 `antd.Menu.Item`,分割线 `antd.Menu.Divider`
......
# 进场和离场
- order: 1
自动。
---
````jsx
var EnterAnimation = antd.EnterAnimation;
var Test = React.createClass({
getInitialState() {
return {
show: true
}
},
onClick() {
this.setState({
show: !this.state.show
})
},
render() {
return (
<div>
<div style={{marginBottom: 20}}>
<button className="ant-btn ant-btn-primary" onClick={this.onClick}>切换</button>
</div>
<EnterAnimation>
{this.state.show ?
<div className="demo-content" key='a'>
<div className="demo-kp">
<ul>
<li></li>
<li></li>
<li></li>
</ul>
</div>
<div className="demo-listBox">
<div className="demo-list">
<div className="title"></div>
<ul>
<li></li>
<li></li>
<li></li>
</ul>
</div>
</div>
</div> : null}
</EnterAnimation>
</div>
);
}
});
React.render(<Test />
, document.getElementById('components-enter-animation-demo-basic'));
````
<style>
#components-enter-animation-demo-basic {
text-align: center;
overflow: hidden;
margin: 20px auto;
}
</style>
# 指定节点动画进出场
- order: 3
通过加上 `enter-data` 属性来指定需要动画进场的元素,并且可以定义每个元素的动画效果。
---
````jsx
var EnterAnimation = antd.EnterAnimation;
var Test = React.createClass({
getInitialState() {
return {
enter: {
type: 'right',
interval: .1,
},
leave: {
type:'left',
interval: 0.03
},
show: true
}
},
onClick() {
this.setState({
show: !this.state.show
})
},
render() {
return (
<div>
<div style={{marginBottom: 20}}>
<button className="ant-btn ant-btn-primary" onClick={this.onClick}>切换</button>
</div>
<EnterAnimation enter={this.state.enter} leave={this.state.leave}>
{this.state.show ? <div key='enter-data'>
<div className="demo-content">
<div className="demo-kp">
<ul>
<li enter-data></li>
<li enter-data></li>
<li enter-data></li>
</ul>
</div>
<div className="demo-listBox">
<div className="demo-list">
<div className="title" enter-data={{type: 'bottom', queueId: 1}}></div>
<ul>
<li enter-data={{type: 'bottom', queueId: 1}}></li>
<li enter-data={{type: 'bottom', queueId: 1}}></li>
<li enter-data={{type: 'bottom', queueId: 1}}></li>
</ul>
</div>
</div>
</div>
</div> : null}
</EnterAnimation>
</div>
)
}
});
React.render(<Test />
, document.getElementById('components-enter-animation-demo-enter-data'));
````
<style>
#components-enter-animation-demo-enter-data {
text-align: center;
overflow: hidden;
margin: 18px auto;
}
</style>
# 配置进出场的样式
- order: 2
配置进出场动画样式。
---
````jsx
var EnterAnimation = antd.EnterAnimation;
var Test = React.createClass({
getInitialState() {
return {
enter:{
type: 'right',
interval: 0.3,
callback:() => {
console.log('enter');
}
},
leave:{
type: 'left',
interval: .1,
callback:() => {
console.log('leave');
}
},
show:true,
}
},
onClick() {
this.setState({
show:!this.state.show,
})
},
render() {
return (
<div>
<div style={{marginBottom: 20}}>
<button className="ant-btn ant-btn-primary" onClick={this.onClick}>切换</button>
</div>
<EnterAnimation enter={this.state.enter} leave={this.state.leave}>
{this.state.show ?
<div className="demo-content" key='demo'>
<div className="demo-kp">
<ul>
<li></li>
<li></li>
<li></li>
</ul>
</div>
<div className="demo-listBox">
<div className="demo-list">
<div className="title"></div>
<ul>
<li></li>
<li></li>
<li></li>
</ul>
</div>
</div>
</div> : null}
</EnterAnimation>
</div>
);
}
});
React.render(<Test />
, document.getElementById('components-enter-animation-demo-enter-leave'));
````
<style>
#components-enter-animation-demo-enter-leave {
text-align: center;
overflow: hidden;
margin: 20px auto;
}
</style>
# 页面的进场和离场
- order: 5
页面的进场和离场。
---
````jsx
var EnterAnimation = antd.EnterAnimation;
var Test = React.createClass({
getInitialState() {
return {
show: true,
enter:{
type:'right',
ease:'cubic-bezier(0.19, 1, 0.22, 1)'
},
leave:{
type:'left',
ease:'cubic-bezier(0.455, 0.03, 0.515, 0.955)',
reverse:true,
interval:0.05
}
}
},
onClick() {
this.setState({
show: !this.state.show
})
},
render() {
return (
<div>
<div style={{marginBottom: 20}}>
<button className="ant-btn ant-btn-primary" onClick={this.onClick}>切换</button>
</div>
<EnterAnimation enter={this.state.enter} leave={this.state.leave}>
{this.state.show ? <div key='a'>
<div className="demo-header" enter-data leave-data={{type:'alpha'}}>
<div className="logo" leave-data={{type:'left'}}>
<img width="30" src="https://t.alipayobjects.com/images/rmsweb/T1B9hfXcdvXXXXXXXX.svg" />
<span>logo</span>
</div>
<ul >
<li enter-data leave-data={{type:'right'}}></li>
<li enter-data leave-data={{type:'right'}}></li>
<li enter-data leave-data={{type:'right'}}></li>
<li enter-data leave-data={{type:'right'}}></li>
<li enter-data leave-data={{type:'right'}}></li>
</ul>
</div>
<div className="demo-content" >
<div className="demo-title" enter-data={{type:'bottom'}} leave-data={{type:'bottom',queueId:1}}>我是标题</div>
<div className="demo-kp">
<ul>
<li enter-data={{interval:0.05}} leave-data={{type:'bottom',queueId:1}}></li>
<li enter-data={{interval:0.05}} leave-data={{type:'bottom',queueId:1}}></li>
<li enter-data={{interval:0.05}} leave-data={{type:'bottom',queueId:1,delay:0.2}}></li>
</ul>
</div>
<div className="demo-title" enter-data={{type:'bottom'}} leave-data={{type:'bottom',queueId:2}}>我是标题</div>
<div className="demo-listBox">
<div className="demo-list">
<div className="title" enter-data={{type:'bottom'}} leave-data={{queueId:2}}></div>
<ul>
<li enter-data={{type:'bottom'}} leave-data={{queueId:2}}></li>
<li enter-data={{type:'bottom'}} leave-data={{queueId:2}}></li>
<li enter-data={{type:'bottom'}} leave-data={{queueId:2}}></li>
<li enter-data={{type:'bottom'}} leave-data={{queueId:2}}></li>
<li enter-data={{type:'bottom'}} leave-data={{queueId:2}}></li>
</ul>
</div>
</div>
</div>
<div className="demo-footer" enter-data={{type:'bottom'}} leave-data={{queueId:2}}></div>
</div> : null}
</EnterAnimation>
</div>
);
}
});
React.render(<Test />
, document.getElementById('components-enter-animation-demo-page'));
````
<style>
#components-enter-animation-demo-page {
text-align: center;
overflow: hidden;
margin: 20px auto;
}
</style>
# Router 默认进出场
- order: 7
router 组合的进场与出场动画。
---
````jsx
var ReactRouter = require('react-router');
var Router = ReactRouter.Router;
var Route = ReactRouter.Route;
var Link = ReactRouter.Link;
var EnterAnimation = antd.EnterAnimation;
var Menu = antd.Menu;
var App = React.createClass({
getInitialState: function () {
return {};
},
clickPage() {
this.setState({
enter: {delay: 0.3},
leave: {delay: 0}
});
},
render() {
var key = this.props.location.pathname;
return (
<div>
<Menu style={{marginBottom: 20}} mode="horizontal">
<Menu.Item key='home'>
<Link to="/" onClick={this.clickPage}>首页</Link>
</Menu.Item>
<Menu.Item key='page1'>
<Link to="/page1" onClick={this.clickPage}>Page 1</Link>
</Menu.Item>
<Menu.Item key='page2'>
<Link to="/page2" onClick={this.clickPage}>Page 2</Link>
</Menu.Item>
</Menu>
<EnterAnimation className='demo-router-wap' enter={this.state.enter} leave={this.state.leave}>
{React.cloneElement(this.props.children || <div key='home' className='demo-router-child'><h1>Home</h1><div>这是首页</div></div>, {key: key})}
</EnterAnimation>
</div>
);
}
});
var Page1 = React.createClass({
render() {
return (
<div className="demo-router-child">
<h1>Page 1</h1>
<p><Link to="/page2">A link to page 2 should be active</Link>依次进场</p>
<p><Link to="/page2">A link to page 2 should be active</Link>依次进场</p>
<p><Link to="/page2">A link to page 2 should be active</Link>依次进场</p>
<p><Link to="/page2">A link to page 2 should be active</Link>依次进场</p>
<p><Link to="/page2">A link to page 2 should be active</Link>改变样式</p>
</div>
);
}
});
var Page2 = React.createClass({
render() {
return (
<div className="demo-router-child">
<h1>Page 2</h1>
<p><Link to="/page1">a link to page 1 </Link>我是页面2.</p>
<p><Link to="/page1">a link to page 1 </Link>我是页面2.</p>
<p><Link to="/page1">a link to page 1 </Link>我是页面2.</p>
<p><Link to="/page1">a link to page 1 </Link>我是页面2.</p>
</div>
);
}
});
React.render((
<Router>
<Route path="/" component={App} ignoreScrollBehavior>
<Route path="page1" component={Page1} />
<Route path="page2" component={Page2} />
</Route>
</Router>
), document.getElementById('components-enter-animation-demo-router'));
````
<style>
#components-enter-animation-demo-router {
text-align: center;
}
.demo-router-wap{
position: relative;
transition: height .5s;
width: 300px;
margin: auto;
}
.demo-router-child{
text-align:left;
}
</style>
# 默认
- order: 0
最简单的进场例子。
---
````jsx
var EnterAnimation = antd.EnterAnimation;
React.render(
<EnterAnimation>
<ul key="key">
<li>依次进场</li>
<li>依次进场</li>
<li>依次进场</li>
<li>依次进场</li>
<li>依次进场</li>
<li>依次进场</li>
<li>依次进场</li>
<li>依次进场</li>
</ul>
</EnterAnimation>
, document.getElementById('components-enter-animation-demo-simple'));
````
# style 自定义样式动画进出场
- order: 4
通过加上属性里的 `style` 来自定义 CSS 动画进出场。
---
````jsx
var EnterAnimation = antd.EnterAnimation;
var Test = React.createClass({
getInitialState() {
return {
enter: {
style: {
transform: "translateX(50px)",
opacity: 0
},
interval: .1,
},
leave: {
interval: 0.03
},
show: true
}
},
onClick() {
this.setState({
show: !this.state.show
})
},
render() {
return (
<div>
<div style={{marginBottom: 20}}>
<button className="ant-btn ant-btn-primary" onClick={this.onClick}>切换</button>
</div>
<EnterAnimation enter={this.state.enter} leave={this.state.leave}>
{this.state.show ? <div key='enter-data'>
<div className="demo-content">
<div className="demo-kp">
<ul>
<li enter-data></li>
<li enter-data></li>
<li enter-data></li>
</ul>
</div>
<div className="demo-listBox">
<div className="demo-list">
<div className="title" enter-data={{style: {transform: 'translateY(30px)', opacity: 0}, queueId: 1}}></div>
<ul>
<li enter-data={{style: {transform: 'translateY(30px)', opacity: 0}, queueId: 1}}></li>
<li enter-data={{style: {transform: 'translateY(30px)', opacity: 0}, queueId: 1}}></li>
<li enter-data={{style: {transform: 'translateY(30px)', opacity: 0}, queueId: 1}}></li>
</ul>
</div>
</div>
</div>
</div> : null}
</EnterAnimation>
</div>
)
}
});
React.render(<Test />
, document.getElementById('components-enter-animation-demo-style'));
````
<style>
#components-enter-animation-demo-style {
text-align: center;
overflow: hidden;
margin: 18px auto;
}
</style>
import React from 'react';
import EnterAnimation from 'enter-animation';
class AntEnterAnimation extends React.Component {
render() {
return <EnterAnimation {...this.props} />;
}
}
AntEnterAnimation.to = EnterAnimation.to;
export default AntEnterAnimation;
import React from 'react';
import rcUtil from 'rc-util';
const cx = rcUtil.classSet;
class Form extends React.Component {
render() {
const prefixCls = this.props.prefixCls;
const formClassName = {
[`${prefixCls}-horizontal`]: this.props.horizontal,
[`${prefixCls}-inline`]: this.props.inline,
};
const classes = cx(formClassName);
return (
<form {...this.props} className={classes}>
{this.props.children}
</form>
);
}
}
Form.propTypes = {
prefixCls: React.PropTypes.string,
horizontal: React.PropTypes.bool,
inline: React.PropTypes.bool,
children: React.PropTypes.any,
onSubmit: React.PropTypes.func,
};
Form.defaultProps = {
prefixCls: 'ant-form',
};
module.exports = Form;
import React from 'react';
import rcUtil from 'rc-util';
const cx = rcUtil.classSet;
function prefixClsFn(prefixCls, ...args) {
return args.map((s)=> {
return prefixCls + '-' + s;
}).join(' ');
}
class FormItem extends React.Component {
_getLayoutClass(colDef) {
if (!colDef) {
return '';
}
const {span, offset} = colDef;
const col = span ? 'col-' + span : '';
const offsetCol = offset ? ' col-offset-' + offset : '';
return col + offsetCol;
}
renderHelp() {
const prefixCls = this.props.prefixCls;
return (
<div className={this.props.help ? prefixClsFn(prefixCls, 'explain') : ''} key="help">
{this.props.help}
</div>
);
}
renderValidateWrapper(c1, c2) {
let classes = '';
if (this.props.validateStatus) {
classes = cx(
{
'has-feedback': this.props.hasFeedback,
'has-success': this.props.validateStatus === 'success',
'has-warning': this.props.validateStatus === 'warning',
'has-error': this.props.validateStatus === 'error',
'is-validating': this.props.validateStatus === 'validating',
}
);
}
return (
<div className={classes}>
{c1} {c2}
</div>
);
}
renderWrapper(children) {
const wrapperCol = this.props.wrapperCol;
return (
<div className={this._getLayoutClass(wrapperCol)} key="wrapper">
{children}
</div>
);
}
renderLabel() {
const labelCol = this.props.labelCol;
const required = this.props.required ? 'required' : '';
return this.props.label ? (
<label htmlFor={this.props.id} className={this._getLayoutClass(labelCol)} required={required} key="label">
{this.props.label}
</label>
) : null;
}
renderChildren() {
return [
this.renderLabel(),
this.renderWrapper(
this.renderValidateWrapper(
this.props.children,
this.renderHelp()
)
),
];
}
// 判断是否要 `.ant-form-item-compact` 样式类
_isCompact(children) {
const compactControls = ['checkbox', 'radio', 'radio-group', 'static', 'file'];
let isCompact = false;
if (!Array.isArray(children)) {
children = [children];
}
children.map((child, i) => {
const type = child.props && child.props.type;
let prefixCls = child.props && child.props.prefixCls;
prefixCls = prefixCls ? prefixCls.substring(prefixCls.indexOf('-') + 1) : '';
if ((type && compactControls.indexOf(type) > -1) || (prefixCls && compactControls.indexOf(prefixCls) > -1)) {
isCompact = true;
} else if (child.props && typeof child.props.children === 'object') {
isCompact = this._isCompact(child.props.children);
}
});
return isCompact;
}
renderFormItem(children) {
const props = this.props;
const prefixCls = props.prefixCls;
const itemClassName = {
[`${prefixCls}-item`]: true,
[`${prefixCls}-item-compact`]: this._isCompact(props.children),
};
return (
<div className={cx(itemClassName)}>
{children}
</div>
);
}
render() {
const children = this.renderChildren();
return this.renderFormItem(children);
}
}
FormItem.propTypes = {
prefixCls: React.PropTypes.string,
label: React.PropTypes.node,
labelCol: React.PropTypes.object,
help: React.PropTypes.node,
validateStatus: React.PropTypes.oneOf(['', 'success', 'warning', 'error', 'validating']),
hasFeedback: React.PropTypes.bool,
wrapperCol: React.PropTypes.object,
className: React.PropTypes.string,
children: React.PropTypes.node,
};
FormItem.defaultProps = {
hasFeedback: false,
required: false,
prefixCls: 'ant-form',
};
module.exports = FormItem;
import React from 'react';
function prefixClsFn(prefixCls, ...args) {
return args.map((s)=> {
return prefixCls + '-' + s;
}).join(' ');
}
function ieGT9() {
if (typeof document === undefined) {
return false;
}
const documentMode = document.documentMode || 0;
return documentMode > 9;
}
class Group extends React.Component {
render() {
return (
<div className={this.props.className}>
{this.props.children}
</div>
);
}
}
Group.propTypes = {
className: React.PropTypes.string,
children: React.PropTypes.any,
};
Group.defaultProps = {
className: 'ant-input-group',
};
class Input extends React.Component {
renderLabledInput(children) {
const props = this.props;
const wrapperClassName = prefixClsFn(props.prefixCls, 'input-group');
const addonClassName = prefixClsFn(wrapperClassName, 'addon');
const addonBefore = props.addonBefore ? (
<span className={addonClassName}>
{props.addonBefore}
</span>
) : null;
const addonAfter = props.addonAfter ? (
<span className={addonClassName}>
{props.addonAfter}
</span>
) : null;
return (
<div className={(addonBefore || addonAfter) ? wrapperClassName : ''}>
{addonBefore}
{children}
{addonAfter}
</div>
);
}
renderInput() {
const props = this.props;
const prefixCls = props.prefixCls;
let inputClassName = prefixClsFn(prefixCls, 'input');
if (!props.type) {
return props.children;
}
switch (props.size) {
case 'small': inputClassName = prefixClsFn(prefixCls, 'input', 'input-sm'); break;
case 'large': inputClassName = prefixClsFn(prefixCls, 'input', 'input-lg'); break;
default:
}
let placeholder = props.placeholder;
if(placeholder && ieGT9()){
placeholder = null;
}
switch (props.type) {
case 'textarea':
return <textarea {...props} placeholder={placeholder} className={inputClassName} ref="input" />;
default:
inputClassName = props.className ? props.className : inputClassName;
return <input {...props} placeholder={placeholder} className={inputClassName} ref="input"/>;
}
}
render() {
return this.renderLabledInput(this.renderInput());
}
}
Input.propTypes = {
type: React.PropTypes.string,
id: React.PropTypes.oneOfType([
React.PropTypes.string,
React.PropTypes.number,
]),
size: React.PropTypes.oneOf(['small', 'default', 'large']),
disabled: React.PropTypes.bool,
value: React.PropTypes.any,
defaultValue: React.PropTypes.any,
className: React.PropTypes.string,
addonBefore: React.PropTypes.node,
addonAfter: React.PropTypes.node,
prefixCls: React.PropTypes.string,
};
Input.defaultProps = {
defaultValue: '',
disabled: false,
prefixCls: 'ant',
type: 'text',
};
module.exports = Input;
module.exports.Group = Group;
function merge() {
const ret = {};
const args = [].slice.call(arguments, 0);
args.forEach((a)=> {
Object.keys(a).forEach((k)=> {
ret[k] = a[k];
});
});
return ret;
}
const ValueMixin = {
setValue(field, e) {
let v = e;
const target = e && e.target;
if (target) {
if ((target.nodeName + '').toLowerCase() === 'input' &&
target.type === 'checkbox') {
v = target.checked;
} else {
v = e.target.value;
}
}
const newFormData = {};
newFormData[field] = v;
this.setState({
formData: merge(this.state.formData, newFormData),
});
},
};
export default ValueMixin;
# 禁用状态
- order: 2
- order: 7
1) 单独为输入设置 `disabled` 属性;
1) 单独为输入控件设置 `disabled` 属性;
2) 为 `<fieldset>` 设置 `disabled` 属性,可以禁用 `<fieldset>` 中包含的所有控件。
---
#### 禁用的表单控件
<br>
````html
<form class="ant-form-horizontal">
<div class="ant-form-item">
<label class="col-5">禁用的输入框:</label>
<div class="col-12">
<input class="ant-input" type="text" value="我是禁用的" disabled>
</div>
</div>
</form>
````
#### 禁用的 fieldset
<br>
````html
<form class="ant-form-horizontal">
<fieldset disabled>
<div class="ant-form-item ant-form-item-compact">
<label for="userName" class="col-5" required>用户名:</label>
<div class="col-12">
<p class="ant-form-text">大眼萌 minion</p>
</div>
</div>
<div class="ant-form-item">
<label for="password" class="col-5" required>密码:</label>
<div class="col-12">
<input class="ant-input" type="password" id="password" value="123456"/>
</div>
</div>
<div class="row">
<div class="col-12 col-offset-5">
<input type="submit" class="ant-btn ant-btn-primary" value="确 定" />
</div>
</div>
</fieldset>
</form>
````jsx
import {Row, Col, Button, Input, Form} from 'antd';
const FormItem = Form.Item;
ReactDOM.render(
<Form horizontal>
<FormItem
label="单独禁用输入框:"
labelCol={{span:5}}
wrapperCol={{span:12}}>
<Input defaultValue="我是禁用的" disabled />
</FormItem>
<fieldset disabled>
<legend>禁用的 fieldset</legend>
<FormItem
id="userName"
label="用户名:"
labelCol={{span:5}}
wrapperCol={{span:12}}
required={true} >
<p className="ant-form-text">大眼萌 minion</p>
</FormItem>
<FormItem
id="password"
label="密码:"
labelCol={{span:5}}
wrapperCol={{span:12}}
required={true} >
<Input type="password" defaultValue="123456" id="password" />
</FormItem>
<Row>
<Col span="12" offset="5">
<Button htmlType="submit" type="primary">确定</Button>
</Col>
</Row>
</fieldset>
</Form>
, document.getElementById('components-form-demo-disabled'));
````
......@@ -9,80 +9,87 @@
---
````jsx
var Select = antd.Select;
var Option = Select.Option;
var Checkbox = antd.Checkbox;
var Radio = antd.Radio;
var RadioGroup = antd.Radio.Group;
import {Form, Input, Select, Checkbox, Radio} from 'antd';
const FormItem = Form.Item;
const Option = Select.Option;
const RadioGroup = Radio.Group;
function handleSelectChange(value) {
console.log('selected ' + value);
}
React.render(
<form className="ant-form-horizontal">
<div className="ant-form-item">
<label htmlFor="control-input" className="col-6">输入框:</label>
<div className="col-14">
<input type="text" className="ant-input" id="control-input" placeholder="Please enter..." />
</div>
</div>
<div className="ant-form-item">
<label htmlFor="control-textarea" className="col-6">文本域:</label>
<div className="col-14">
<textarea className="ant-input" id="control-textarea"></textarea>
</div>
</div>
<div className="ant-form-item">
<label className="col-6">Select 选择器:</label>
<div className="col-14">
<Select size="large" defaultValue="lucy" style={{width:200}} onChange={handleSelectChange}>
ReactDOM.render(
<Form horizontal>
<FormItem
id="control-input"
label="输入框:"
labelCol={{span: 6}}
wrapperCol={{span: 14}}>
<Input id="control-input" placeholder="Please enter..." />
</FormItem>
<FormItem
id="control-textarea"
label="文本域:"
labelCol={{span: 6}}
wrapperCol={{span: 14}}>
<Input type="textarea" id="control-textarea"/>
</FormItem>
<FormItem
id="select"
label="Select 选择器:"
labelCol={{span: 6}}
wrapperCol={{span: 14}}>
<Select id="select" size="large" defaultValue="lucy" style={{width:200}} onChange={handleSelectChange}>
<Option value="jack">jack</Option>
<Option value="lucy">lucy</Option>
<Option value="disabled" disabled>disabled</Option>
<Option value="yiminghe">yiminghe</Option>
< Option value="yiminghe">yiminghe</Option>
</Select>
</div>
</div>
<div className="ant-form-item ant-form-item-compact">
<label className="col-6">Checkbox 多选框:</label>
<div className="col-18">
<label className="ant-checkbox-vertical">
<Checkbox />选项一
</label>
<label className="ant-checkbox-vertical">
<Checkbox />选项二
</label>
<label className="ant-checkbox-vertical">
<Checkbox disabled={true} />选项三(不可选)
</label>
</div>
</div>
<div className="ant-form-item ant-form-item-compact">
<label className="col-6">Checkbox 多选框:</label>
<div className="col-18">
<label className="ant-checkbox-inline">
<Checkbox />选项一
</label>
<label className="ant-checkbox-inline">
<Checkbox />选项二
</label>
<label className="ant-checkbox-inline">
<Checkbox />选项三
</label>
</div>
</div>
<div className="ant-form-item ant-form-item-compact">
<label className="col-6">Radio 单选框:</label>
<div className="col-18">
<RadioGroup value="b">
<Radio value="a">A</Radio>
<Radio value="b">B</Radio>
<Radio value="c">C</Radio>
<Radio value="d">D</Radio>
</RadioGroup>
</div>
</div>
</form>
</FormItem>
<FormItem
label="Checkbox 多选框:"
labelCol={{span: 6}}
wrapperCol={{span: 18}} >
<label className="ant-checkbox-vertical">
<Checkbox />选项一
</label>
<label className="ant-checkbox-vertical">
<Checkbox />选项二
</label>
<label className="ant-checkbox-vertical">
<Checkbox disabled={true} />选项三(不可选)
</label>
</FormItem>
<FormItem
label="Checkbox 多选框:"
labelCol={{span: 6}}
wrapperCol={{span: 18}} >
<label className="ant-checkbox-inline">
<Checkbox />选项一
</label>
<label className="ant-checkbox-inline">
<Checkbox />选项二
</label>
<label className="ant-checkbox-inline">
<Checkbox />选项三
</label>
</FormItem>
<FormItem
label="Radio 单选框:"
labelCol={{span: 6}}
wrapperCol={{span: 18}} >
<RadioGroup value="b">
<Radio value="a">A</Radio>
<Radio value="b">B</Radio>
<Radio value="c">C</Radio>
<Radio value="d">D</Radio>
</RadioGroup>
</FormItem>
</Form>
, document.getElementById('components-form-demo-form-controls'));
````
# 水平排列的表单
- order: 0
- order: 2
`<form>` 标签添加 `.ant-form-horizontal` 类(这让 `.ant-form-item` 表现为栅格系统中的 `row`),并结合使用我们提供的 [栅格系统](http://ant.design/components/layout/),可以实现 label 标签和表单控件的水平排列
示例展示了如何通过使用 `Form.ValueMixin` 来获取和更新表单提交的数值
如需将一行静态文本和 `<label>` 标签置于同一行,则只需为标签添加 `.ant-form-text` 类即可。
`label` 标签添加 `required` 属性,表示该项必选。
**注意**:在我们的设计里,表单域(`.ant-form-item`) 为静态文本、`checkbox``radio`以及`input[type="file"]`的,其高度不同于一般的表单域,需要在 `.ant-form-item` 类后再加上 **`.ant-form-item-compact`**
**注意:** 你需要为每个输入控件声明 `name` 属性。
---
````jsx
var Checkbox = antd.Checkbox;
var Radio = antd.Radio;
var RadioGroup = antd.Radio.Group;
import {Form, Input, Button, Checkbox, Radio, Row, Col, message} from 'antd';
const FormItem = Form.Item;
const RadioGroup = Radio.Group;
const Demo = React.createClass({
mixins: [Form.ValueMixin],
getInitialState() {
return {
formData: {
userName: '大眼萌 minion',
password: undefined,
gender: 'male',
remark: undefined,
agreement: undefined,
}
};
},
handleSubmit(e) {
e.preventDefault();
message.success("收到表单值~~~ :" + JSON.stringify(this.state.formData, function(k, v) {
if (typeof v === 'undefined') {
return '';
}
return v;
}));
},
render() {
const formData = this.state.formData;
return (
<Form horizontal onSubmit={this.handleSubmit}>
<FormItem
label="用户名:"
labelCol={{span: 6}}
wrapperCol={{span: 6}}
required={true} >
<p className="ant-form-text" id="userName" name="userName">大眼萌 minion</p>
</FormItem>
<FormItem
id="password"
label="密码:"
labelCol={{span: 6}}
wrapperCol={{span: 14}}
required={true} >
<Input type="password" id="password" name="password" placeholder="请输入密码" value={formData.password} onChange={this.setValue.bind(this, 'password')} />
</FormItem>
<FormItem
label="您的性别:"
labelCol={{span: 6}}
wrapperCol={{span: 14}}
required={true} >
<RadioGroup value="male" name="gender" value={formData.gender} onChange={this.setValue.bind(this, 'gender')} >
<Radio value="male">男的</Radio>
<Radio value="female">女的</Radio>
</RadioGroup>
</FormItem>
<FormItem
id="remark"
label="备注:"
labelCol={{span: 6}}
wrapperCol={{span: 14}}
required={true}
help="随便写点什么" >
<Input type="textarea" placeholder="随便写" id="remark" name="remark" value={formData.remark} onChange={this.setValue.bind(this, 'remark')} />
</FormItem>
<FormItem
wrapperCol={{span: 14, offset: 6}} >
<label>
<Checkbox name="agreement" value={formData.agreement} onChange={this.setValue.bind(this, 'agreement')} /> 同意
</label>
</FormItem>
<Row>
<Col span="16" offset="6">
<Button type="primary" htmlType="submit">确定</Button>
</Col>
</Row>
</Form>
);
}
});
React.render(
<form className="ant-form-horizontal">
<div className="ant-form-item ant-form-item-compact">
<label htmlFor="userName" className="col-6" required>用户名:</label>
<div className="col-6">
<p className="ant-form-text">大眼萌 minion</p>
</div>
</div>
<div className="ant-form-item">
<label htmlFor="password" className="col-6" required>密码:</label>
<div className="col-14">
<input className="ant-input" type="password" id="password" placeholder="请输入密码"/>
</div>
</div>
<div className="ant-form-item ant-form-item-compact">
<label className="col-6" required>您的性别:</label>
<div className="col-14">
<RadioGroup value="male">
<Radio value="male">男的</Radio>
<Radio value="female">女的</Radio>
</RadioGroup>
</div>
</div>
<div className="ant-form-item">
<label htmlFor="remark" className="col-6" required>备注:</label>
<div className="col-14">
<textarea className="ant-input" id="remark" placeholder="随便写"></textarea>
<p className="ant-form-explain">随便写点什么</p>
</div>
</div>
<div className="ant-form-item ant-form-item-compact">
<div className="col-14 col-offset-6">
<label>
<Checkbox /> 同意
</label>
</div>
</div>
<div className="row">
<div className="col-16 col-offset-6">
<input type="submit" className="ant-btn ant-btn-primary" value="确 定" />
</div>
</div>
</form>
, document.getElementById('components-form-demo-horizontal-form'));
ReactDOM.render(<Demo />, document.getElementById('components-form-demo-horizontal-form'));
````
# 行内排列的表单
# 平行排列
- order: 1
你可以为 `<form>` 标签添加 `.ant-form-inline` 类可使其表现为 inline-block 级别的控件
行内排列,常用于登录界面
---
````jsx
var Checkbox = antd.Checkbox;
React.render(
<form className="ant-form-inline">
<div className="ant-form-item">
<label htmlFor="userName">账户:</label>
<input className="ant-input" type="text" id="userName" placeholder="请输入账户名" />
</div>
<div className="ant-form-item">
<label htmlFor="password2">密码:</label>
<input className="ant-input" type="password" id="password2" placeholder="请输入密码" />
</div>
<div className="ant-form-item">
<label className="ant-checkbox-inline">
<Checkbox /> 记住我
</label>
</div>
<input type="submit" className="ant-btn ant-btn-primary" value="登 录" />
</form>
, document.getElementById('components-form-demo-inline-form'));
import {Form, Input, Button, Checkbox, message} from 'antd';
const FormItem = Form.Item;
const Demo = React.createClass({
mixins: [Form.ValueMixin],
getInitialState() {
return {
formData: {
userName: undefined,
password: undefined,
agreement: undefined,
}
};
},
handleSubmit(e) {
e.preventDefault();
message.success("收到表单值~~~ :" + JSON.stringify(this.state.formData, function(k, v) {
if (typeof v === 'undefined') {
return '';
}
return v;
}));
},
render() {
const formData = this.state.formData;
return (
<Form inline onSubmit={this.handleSubmit}>
<FormItem
id="userName"
label="账户:">
<Input placeholder="请输入账户名" id="userName" name="userName" onChange={this.setValue.bind(this, 'userName')} value={formData.userName} />
</FormItem>
<FormItem
id="password"
label="密码:">
<Input type="password" placeholder="请输入密码" id="password" name="password" onChange={this.setValue.bind(this, 'password')} value={formData.password} />
</FormItem>
<FormItem>
<label className="ant-checkbox-inline">
<Checkbox name="agreement" value={formData.agreement} onChange={this.setValue.bind(this, 'agreement')} /> 记住我
</label>
</FormItem>
<Button type="primary" htmlType="submit">登录</Button>
</Form>
);
}
});
ReactDOM.render(<Demo />, document.getElementById('components-form-demo-inline-form'));
````
# 输入框组合
- order: 4
各类输入框的组合展现。
---
````jsx
import {Form, Input, Select, Row, Col} from 'antd';
const FormItem = Form.Item;
const InputGroup = Input.Group;
const Option = Select.Option;
ReactDOM.render(
<Form horizontal>
<FormItem
label="标签输入框:"
labelCol={{span: 6}}
wrapperCol={{span: 16}}>
<Input addonBefore="Http://" defaultValue="mysite.com" id="site1"/>
</FormItem>
<FormItem
label="标签输入框:"
labelCol={{span: 6}}
wrapperCol={{span: 16}}>
<Input addonBefore="Http://" addonAfter=".com" defaultValue="mysite" id="site2"/>
</FormItem>
<FormItem
label="select 标签输入框:"
labelCol={{span: 6}}
wrapperCol={{span: 16}}>
<InputGroup>
<Input id="site4" placeholder="www.mysite" />
<div className="ant-input-group-wrap">
<Select defaultValue=".com" style={{width:70}}>
<Option value=".com">.com</Option>
<Option value=".jp">.jp</Option>
<Option value=".cn">.cn</Option>
<Option value=".org">.org</Option>
</Select>
</div>
</InputGroup>
</FormItem>
<FormItem
label="输入身份证:"
labelCol={{span: 6}}
wrapperCol={{span: 16}}>
<InputGroup>
<Col span="6">
<Input id="certNo1" />
</Col>
<Col span="6">
<Input id="certNo2" />
</Col>
<Col span="6">
<Input id="certNo3" />
</Col>
<Col span="6">
<Input id="certNo4" />
</Col>
</InputGroup>
</FormItem>
<FormItem
label="电话号码:"
labelCol={{span: 6}}
wrapperCol={{span: 16}}>
<Row>
<Col span="4">
<Input id="tel1" defaultValue="086" />
</Col>
<Col span="2">
<p className="ant-form-split">--</p>
</Col>
<Col span="18">
<InputGroup>
<Col span="8">
<Input id="tel1" />
</Col>
<Col span="8">
<Input id="tel2" />
</Col>
<Col span="8">
<Input id="tel3" />
</Col>
</InputGroup>
</Col>
</Row>
</FormItem>
</Form>
, document.getElementById('components-form-demo-input-group'));
````
# Input 尺寸
- order: 6
我们为定义了 `.ant-input` 类的输入框提供了三种尺寸:大(-lg)、中(默认)、小(-sm),往类名添加以上后缀即可。
但是在 `<form>` 表单里面,我们只使用**大尺寸**, 即高度为 **32px**,作为唯一的尺寸。
---
````html
<div class="row">
<div class="ant-input-group">
<div class="col-6">
<input class="ant-input ant-input-lg" type="text" id="largeInput" placeholder="大尺寸"/>
</div>
<div class="col-6">
<input class="ant-input" type="text" id="defaultInput" placeholder="默认尺寸"/>
</div>
<div class="col-6">
<input class="ant-input ant-input-sm" type="text" id="smallInput" placeholder="小尺寸"/>
</div>
</div>
</div>
````
# Input 输入框
- order: 0
我们为 `<Input />` 输入框定义了三种尺寸(大、默认、小),具体使用详见 [API](/components/form/#input)
注意: 在表单里面,我们只使用**大尺寸**, 即高度为 **32px**,作为唯一的尺寸。
---
````jsx
import {Row, Col, Input} from 'antd';
const InputGroup = Input.Group;
ReactDOM.render(
<Row>
<InputGroup>
<Col span="6">
<Input id="largeInput" size="large" placeholder="大尺寸" />
</Col>
<Col span="6">
<Input id="defaultInput" placeholder="默认尺寸" />
</Col>
<Col span="6">
<Input id="smallInput" placeholder="小尺寸" size="small" />
</Col>
</InputGroup>
</Row>
, document.getElementById('components-form-demo-input'));
````
# Input 输入框集合
- order: 5
带标签的输入框:使用 `.ant-input-group` 类并结合 `.ant-input-group-addon` 类可以创建带标签的输入框。
---
````jsx
var Select = antd.Select;
var Option = Select.Option;
React.render(
<form className="ant-form-horizontal">
<div className="ant-form-item">
<label className="col-6" htmlFor="site1">标签输入框:</label>
<div className="col-16">
<div className="ant-input-group">
<span className="ant-input-group-addon" id="basic-addon1">Http://</span>
<input type="text" id="site1" className="ant-input" defaultValue="mysite.com" />
</div>
</div>
</div>
<div className="ant-form-item">
<label className="col-6" htmlFor="site3">标签输入框:</label>
<div className="col-16">
<div className="ant-input-group">
<span className="ant-input-group-addon" id="basic-addon3">Http://</span>
<input type="text" className="ant-input" id="site3" defaultValue="mysite" />
<span className="ant-input-group-addon" id="basic-addon4">.com</span>
</div>
</div>
</div>
<div className="ant-form-item">
<label className="col-6" htmlFor="site4">select 标签输入框:</label>
<div className="col-16">
<div className="ant-input-group">
<input type="text" className="ant-input" id="site4" placeholder="www.mysite" />
<div className="ant-input-group-wrap">
<Select defaultValue=".com" style={{width:70}}>
<Option value=".com">.com</Option>
<Option value=".jp">.jp</Option>
<Option value=".cn">.cn</Option>
<Option value=".org">.org</Option>
</Select>
</div>
</div>
</div>
</div>
<div className="ant-form-item">
<label className="col-6" htmlFor="certNo1">输入身份证:</label>
<div className="col-16">
<div className="ant-input-group">
<div className="col-6">
<input className="ant-input" type="text" id="certNo1" />
</div>
<div className="col-6">
<input className="ant-input" type="text" id="certNo2" />
</div>
<div className="col-6">
<input className="ant-input" type="text" id="certNo3" />
</div>
<div className="col-6">
<input className="ant-input" type="text" id="certNo4" />
</div>
</div>
</div>
</div>
<div className="ant-form-item">
<label className="col-6" htmlFor="tel1">电话号码:</label>
<div className="col-16">
<div className="row">
<div className="col-4">
<input className="ant-input" type="text" id="tel1" defaultValue="086" />
</div>
<div className="col-2">
<p className="ant-form-split">--</p>
</div>
<div className="col-18">
<div className="ant-input-group">
<div className="col-8">
<input className="ant-input" type="text" id="tel1" />
</div>
<div className="col-8">
<input className="ant-input" type="text" id="tel2" />
</div>
<div className="col-8">
<input className="ant-input" type="text" id="tel3" />
</div>
</div>
</div>
</div>
</div>
</div>
</form>
, document.getElementById('components-form-demo-inputs'));
````
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册