mirror of
https://github.com/ant-design/ant-design.git
synced 2026-02-09 10:59:19 +08:00
Compare commits
544 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
f1ff04a1ce | ||
|
|
11353c7a60 | ||
|
|
29b99bbf69 | ||
|
|
56a0badded | ||
|
|
124d702f88 | ||
|
|
9e2d1be3d6 | ||
|
|
73b806e159 | ||
|
|
fae30906b2 | ||
|
|
22bb5ea1b3 | ||
|
|
5e635654ed | ||
|
|
1d75c19895 | ||
|
|
644c43f4e0 | ||
|
|
63476680bd | ||
|
|
fdcc665c80 | ||
|
|
027a69b0f0 | ||
|
|
cf77d46493 | ||
|
|
f96a57ec25 | ||
|
|
4cd73289b3 | ||
|
|
56c4882f30 | ||
|
|
be1a353301 | ||
|
|
2381b78af2 | ||
|
|
f58ac72a88 | ||
|
|
a479bc8fe3 | ||
|
|
94f6f5ab9f | ||
|
|
24bd1f09da | ||
|
|
d4a65d14ba | ||
|
|
033acfd0f4 | ||
|
|
b14c5820e0 | ||
|
|
33f2863e68 | ||
|
|
7470b3e5c5 | ||
|
|
6728760402 | ||
|
|
7ae966873a | ||
|
|
8d14469293 | ||
|
|
57a6535a4c | ||
|
|
ec6d38b749 | ||
|
|
997db86d76 | ||
|
|
7a142993a1 | ||
|
|
1819a9dba0 | ||
|
|
c0e7cad5bc | ||
|
|
2774efdc7d | ||
|
|
5306d32cda | ||
|
|
0e0a16c5c0 | ||
|
|
f4f967ec8e | ||
|
|
0002062eb8 | ||
|
|
2468456350 | ||
|
|
afe381e861 | ||
|
|
d75e8f4dc1 | ||
|
|
c73b1c091f | ||
|
|
15b2e92df1 | ||
|
|
32ca98c2cd | ||
|
|
8fca14fd7d | ||
|
|
adf9a11b8b | ||
|
|
016b04f4d3 | ||
|
|
ca2edd2b1d | ||
|
|
d3fe6380df | ||
|
|
bbf302cc93 | ||
|
|
b4c2d9bf8f | ||
|
|
658660a158 | ||
|
|
f051e8828e | ||
|
|
5ea2775197 | ||
|
|
f978a01802 | ||
|
|
b58142081c | ||
|
|
c821b2cf03 | ||
|
|
64cde2e905 | ||
|
|
1cff3f77f0 | ||
|
|
a1040e5ce1 | ||
|
|
ce3c503ecd | ||
|
|
02075784d6 | ||
|
|
752aa86dbb | ||
|
|
d3fdb1ae87 | ||
|
|
11cdde70ef | ||
|
|
21b97c7d49 | ||
|
|
ebe59bb08b | ||
|
|
563f36385c | ||
|
|
4647e8391a | ||
|
|
fd65f75d71 | ||
|
|
48f915de65 | ||
|
|
6d885bb171 | ||
|
|
4660a7f69e | ||
|
|
e87b4649a4 | ||
|
|
c64d6f3a0f | ||
|
|
7e341a1be9 | ||
|
|
00df19d3e3 | ||
|
|
8be1ffdfe0 | ||
|
|
ccc84d796c | ||
|
|
3455644a52 | ||
|
|
9985334e3c | ||
|
|
c3e404f6ea | ||
|
|
f267d4fda7 | ||
|
|
ae718f8f70 | ||
|
|
31b472e209 | ||
|
|
2be1ac90df | ||
|
|
a0ea479108 | ||
|
|
2f1312cce3 | ||
|
|
291d666922 | ||
|
|
02bcdee3c3 | ||
|
|
ae5aeeca0e | ||
|
|
65a4555491 | ||
|
|
7f56e95541 | ||
|
|
0b92ea29e6 | ||
|
|
98aa1a5997 | ||
|
|
df6304631e | ||
|
|
5fab148a86 | ||
|
|
bdd47786af | ||
|
|
b87158ccd9 | ||
|
|
6cfc8be796 | ||
|
|
663e3c4231 | ||
|
|
c879aea3c2 | ||
|
|
b56c5bb9e3 | ||
|
|
c1ef10da49 | ||
|
|
a570b25e0a | ||
|
|
7866f177cc | ||
|
|
cf65eade1f | ||
|
|
76aa90f67b | ||
|
|
34f9ab05b0 | ||
|
|
ec4522ca32 | ||
|
|
ceeae97eb8 | ||
|
|
28b75ce8da | ||
|
|
27908bf42e | ||
|
|
b276ca65fc | ||
|
|
01468cdc54 | ||
|
|
092e2e1ac6 | ||
|
|
d39e5ca4bc | ||
|
|
f29dd1afa0 | ||
|
|
4e8d4d4186 | ||
|
|
803a8d4ccc | ||
|
|
2ca31c7cac | ||
|
|
ba51e65c3d | ||
|
|
d79562075a | ||
|
|
dc1455ecc4 | ||
|
|
f4865e85d0 | ||
|
|
bcb686b5c0 | ||
|
|
8c50e283f6 | ||
|
|
ca6578fa11 | ||
|
|
e66a43a4c5 | ||
|
|
b89b98374d | ||
|
|
37e407aa82 | ||
|
|
fb073bf0a4 | ||
|
|
4d8e008927 | ||
|
|
1a606524dd | ||
|
|
f471f74da4 | ||
|
|
c2a1b225f3 | ||
|
|
6d953b4c7c | ||
|
|
1087ec4501 | ||
|
|
97993b3bed | ||
|
|
cf38545e2c | ||
|
|
88a22815b8 | ||
|
|
e44faf9d48 | ||
|
|
6d4c4e12d1 | ||
|
|
98b899d0cc | ||
|
|
0ee47a3538 | ||
|
|
4be5e25d68 | ||
|
|
93f95df33a | ||
|
|
9f48f665a6 | ||
|
|
253da716f3 | ||
|
|
4602786606 | ||
|
|
a108566d5e | ||
|
|
3090930ae3 | ||
|
|
17085264f2 | ||
|
|
fc40e52bae | ||
|
|
91bd7f22c0 | ||
|
|
476b09bf7d | ||
|
|
46092adbea | ||
|
|
113c5e1264 | ||
|
|
a55a6161ea | ||
|
|
7fd451ee46 | ||
|
|
32a93ee88a | ||
|
|
44f2d7c8c2 | ||
|
|
c8339d5b1b | ||
|
|
3ea67ded23 | ||
|
|
43caba2067 | ||
|
|
d7e4578b89 | ||
|
|
6d9245eb14 | ||
|
|
e25a6fa583 | ||
|
|
160bc58c09 | ||
|
|
7843fda14d | ||
|
|
a3704c1d92 | ||
|
|
970824c98a | ||
|
|
c73a3ac62d | ||
|
|
5699e61fd0 | ||
|
|
616f7d50ef | ||
|
|
c5df2c0fac | ||
|
|
45bb286cd6 | ||
|
|
2699f5075c | ||
|
|
5476bf1afe | ||
|
|
ddcd8ad701 | ||
|
|
1f22b567d2 | ||
|
|
a71c2d39c5 | ||
|
|
49568de7c3 | ||
|
|
74036396fe | ||
|
|
4564324621 | ||
|
|
07656e7c50 | ||
|
|
679d377e87 | ||
|
|
eb5e1c644a | ||
|
|
292aacc156 | ||
|
|
ed5d2f0731 | ||
|
|
153e24ec95 | ||
|
|
710aec32c4 | ||
|
|
fb60b67f9e | ||
|
|
1b8cdaf45a | ||
|
|
afeaa724b9 | ||
|
|
d362ae7ff6 | ||
|
|
dfb7c9a99a | ||
|
|
4cae512dbf | ||
|
|
841de74d18 | ||
|
|
c45c6877f8 | ||
|
|
b1a136d208 | ||
|
|
6f42cceb4a | ||
|
|
c2cb6ea1b1 | ||
|
|
1f98c85e8a | ||
|
|
fd51d4f6f2 | ||
|
|
a277669aba | ||
|
|
b55d43924d | ||
|
|
5121a5d634 | ||
|
|
ac337976be | ||
|
|
b013c6231f | ||
|
|
6fa32a81b8 | ||
|
|
a976111396 | ||
|
|
d6122ab872 | ||
|
|
18b1b4740f | ||
|
|
e0fb571ebc | ||
|
|
ef9a425cc8 | ||
|
|
aa3c703c18 | ||
|
|
82ee32b97b | ||
|
|
5f3b38a38c | ||
|
|
4414162a5d | ||
|
|
9ef865e25e | ||
|
|
de1a21c8c8 | ||
|
|
8dea7fbe15 | ||
|
|
e2fe1d5c3d | ||
|
|
f7322df4ee | ||
|
|
82bb807932 | ||
|
|
7ed490fbb7 | ||
|
|
e51a1016d8 | ||
|
|
da7b7ca2a0 | ||
|
|
164fc24ddd | ||
|
|
ca4f159145 | ||
|
|
234b02195c | ||
|
|
e14ee95e8f | ||
|
|
1f8e83c649 | ||
|
|
6c5794e8ee | ||
|
|
5000fa6b87 | ||
|
|
e0e94ef709 | ||
|
|
2fd64b4997 | ||
|
|
d516b444b1 | ||
|
|
69faeb9145 | ||
|
|
2ea1fb48a4 | ||
|
|
cbf7d27664 | ||
|
|
6c1f601ab8 | ||
|
|
75048619a2 | ||
|
|
47ac6720e3 | ||
|
|
30d74aa7d5 | ||
|
|
ec95e2fb5b | ||
|
|
706009f2be | ||
|
|
2944236cf6 | ||
|
|
335d526dcc | ||
|
|
5c9a75c8bc | ||
|
|
50565eef0f | ||
|
|
7156c7526d | ||
|
|
afa40dd919 | ||
|
|
50fc55ddc8 | ||
|
|
8c013e25f1 | ||
|
|
6995db850e | ||
|
|
38083e5a9f | ||
|
|
a84be2c043 | ||
|
|
276d7d2662 | ||
|
|
691d0ca606 | ||
|
|
509a368e56 | ||
|
|
7b8007087a | ||
|
|
d45bd4c79d | ||
|
|
970dd7f34e | ||
|
|
24975d1d15 | ||
|
|
e834d6a1a6 | ||
|
|
a7f010dd36 | ||
|
|
41ba920fd7 | ||
|
|
8ab0e32758 | ||
|
|
56336717ab | ||
|
|
2d175a0a62 | ||
|
|
f847c23c46 | ||
|
|
02f9212124 | ||
|
|
628b71d44e | ||
|
|
c9bb2df977 | ||
|
|
2bb90710b9 | ||
|
|
5de62ff8d3 | ||
|
|
2d37a00fc2 | ||
|
|
b8d14936e9 | ||
|
|
155c22efd4 | ||
|
|
24398cd3e5 | ||
|
|
7410034522 | ||
|
|
a0cf537f6d | ||
|
|
c3f1004c4f | ||
|
|
07387e4ded | ||
|
|
765ce7bb67 | ||
|
|
b758855186 | ||
|
|
07fa42dc9c | ||
|
|
c6ddb6ef7c | ||
|
|
fd96b1e7f4 | ||
|
|
8a69058364 | ||
|
|
d1c73231a1 | ||
|
|
3ec39dcb62 | ||
|
|
18b3664e79 | ||
|
|
852438cfa8 | ||
|
|
1fbaf0b5b5 | ||
|
|
1055a83bde | ||
|
|
424166d335 | ||
|
|
0e82e14030 | ||
|
|
e8a671d426 | ||
|
|
d59ebf6fc2 | ||
|
|
f0d94d476b | ||
|
|
8df1da99d9 | ||
|
|
45f01f1f26 | ||
|
|
1da9dd6942 | ||
|
|
d8404a5972 | ||
|
|
2ab49d7b3c | ||
|
|
e5913f3de2 | ||
|
|
6f3bbce39b | ||
|
|
54087d7488 | ||
|
|
a334065edb | ||
|
|
56e98e1cdc | ||
|
|
6e2ec48ba6 | ||
|
|
cd27b559fb | ||
|
|
7ed1d78150 | ||
|
|
f913542626 | ||
|
|
dda322e7aa | ||
|
|
a1f0e58fce | ||
|
|
193e77fdd9 | ||
|
|
744a0c49b5 | ||
|
|
e064af5eb9 | ||
|
|
dcd6a05432 | ||
|
|
e20111d918 | ||
|
|
5ed3ba72b4 | ||
|
|
ece8eaa7ad | ||
|
|
76ecce0942 | ||
|
|
5d0287615d | ||
|
|
55315649bc | ||
|
|
7b6fd3128c | ||
|
|
7f2957b23b | ||
|
|
d1fc49f885 | ||
|
|
4bb18780e5 | ||
|
|
269326abaa | ||
|
|
ca0cfc2cd0 | ||
|
|
d644484236 | ||
|
|
029890a5ab | ||
|
|
7eb3c04a1e | ||
|
|
f056e517b9 | ||
|
|
74fc3fd710 | ||
|
|
406f611135 | ||
|
|
6e8d9c4079 | ||
|
|
2aa3e7149d | ||
|
|
c74f204158 | ||
|
|
a580826675 | ||
|
|
8b34ffce3f | ||
|
|
7cd8b34015 | ||
|
|
734dcc142a | ||
|
|
2850804feb | ||
|
|
c43d59dbb4 | ||
|
|
12c1272354 | ||
|
|
2c8072cb98 | ||
|
|
b115f000f9 | ||
|
|
349d03e384 | ||
|
|
257d90fce1 | ||
|
|
6f04d7c1a7 | ||
|
|
0bd2ed9378 | ||
|
|
721c00e925 | ||
|
|
759baedadd | ||
|
|
9560c310a2 | ||
|
|
7288dfbaf9 | ||
|
|
d4850c418f | ||
|
|
dcc15110b4 | ||
|
|
d6bd53927e | ||
|
|
a1064fcf14 | ||
|
|
41660c3814 | ||
|
|
dce02dd5f9 | ||
|
|
5e18c37cce | ||
|
|
dd050bed0c | ||
|
|
51f9da1c34 | ||
|
|
4ed1c17cd6 | ||
|
|
9dd5becfc8 | ||
|
|
7701714615 | ||
|
|
6e95c29a1d | ||
|
|
23e1ad362b | ||
|
|
941d8f7c6b | ||
|
|
a9ba48f7c1 | ||
|
|
3f942d6cf5 | ||
|
|
5908b11652 | ||
|
|
c7bcea8559 | ||
|
|
e5faf12d19 | ||
|
|
d759d1f489 | ||
|
|
41c60f6469 | ||
|
|
58845101c2 | ||
|
|
62d4bbd573 | ||
|
|
91387c2fa6 | ||
|
|
b4789e585d | ||
|
|
397cfc96c0 | ||
|
|
a46dc5135c | ||
|
|
f659fecce7 | ||
|
|
8b8f186ce0 | ||
|
|
8604a9a2d2 | ||
|
|
e803524350 | ||
|
|
ad50514b8c | ||
|
|
dfd70ae634 | ||
|
|
801330cac7 | ||
|
|
2c3bf07d39 | ||
|
|
c1b1765a1b | ||
|
|
4f4240227e | ||
|
|
31ee4bea30 | ||
|
|
69dc8e5fc4 | ||
|
|
f3d5607f13 | ||
|
|
3016ef052a | ||
|
|
1d0b459349 | ||
|
|
f64bee9de5 | ||
|
|
b95d9ff5ab | ||
|
|
bfe94b2a80 | ||
|
|
7f7e66070e | ||
|
|
b177350280 | ||
|
|
05ee2bf036 | ||
|
|
c79913b896 | ||
|
|
d900bec8b4 | ||
|
|
a068e58dd4 | ||
|
|
0690e7137d | ||
|
|
8b93a6bc26 | ||
|
|
f6930d5f1b | ||
|
|
1a4527944f | ||
|
|
16ce16ebd3 | ||
|
|
386d56f38c | ||
|
|
edeec8e503 | ||
|
|
46e3930d62 | ||
|
|
1d7350cccd | ||
|
|
290b739cd1 | ||
|
|
2ea366c16c | ||
|
|
7c9820baeb | ||
|
|
a9818876e9 | ||
|
|
c6a5f61373 | ||
|
|
f6fcdd8602 | ||
|
|
462f4432d7 | ||
|
|
36e234de97 | ||
|
|
07e32342a0 | ||
|
|
84b23d6b11 | ||
|
|
52c26872cb | ||
|
|
aed50b2cc0 | ||
|
|
9582855255 | ||
|
|
948120e224 | ||
|
|
144cca268d | ||
|
|
68dc19cf25 | ||
|
|
d9bb1560ce | ||
|
|
2e010aea39 | ||
|
|
cc9c6390b8 | ||
|
|
6b4d7b3622 | ||
|
|
055d3b406c | ||
|
|
66d86fe8e4 | ||
|
|
7bbe2dee7c | ||
|
|
1b39188ea4 | ||
|
|
c592235f3d | ||
|
|
d9eaffb0c8 | ||
|
|
34960cb662 | ||
|
|
c70a04935b | ||
|
|
5699ee9a0c | ||
|
|
8223681d26 | ||
|
|
7cc44cb750 | ||
|
|
4ff91a7536 | ||
|
|
1446e799c4 | ||
|
|
d88c3c9fbd | ||
|
|
0159679ab1 | ||
|
|
cf6ed2ae36 | ||
|
|
fc2edb386c | ||
|
|
19c69eb071 | ||
|
|
c3aa6ec367 | ||
|
|
ad1a97d0aa | ||
|
|
d08b259256 | ||
|
|
1aeb2dcbf2 | ||
|
|
4e4273ec5b | ||
|
|
81209c70c3 | ||
|
|
2923cd8799 | ||
|
|
b25260b954 | ||
|
|
68cdef6b5c | ||
|
|
cd8c6e7154 | ||
|
|
52fa259538 | ||
|
|
5e1f611863 | ||
|
|
087c64649d | ||
|
|
454ba1b8d5 | ||
|
|
e1766f2b6b | ||
|
|
0790d06e62 | ||
|
|
cad92a5b49 | ||
|
|
3e5e51049b | ||
|
|
5b50e11192 | ||
|
|
3cc00cb834 | ||
|
|
9b3858adbf | ||
|
|
f99bbf5c2e | ||
|
|
f3d4ccc045 | ||
|
|
3639f048f5 | ||
|
|
7cd8fb042f | ||
|
|
e8802c3992 | ||
|
|
7a6a8149e6 | ||
|
|
519e8cfed2 | ||
|
|
df101a72ec | ||
|
|
b1f066ec2a | ||
|
|
f162e13d6b | ||
|
|
cc80b3c1c6 | ||
|
|
b3d42ffb93 | ||
|
|
a0f93bfa83 | ||
|
|
b172ebb3c6 | ||
|
|
5e8aa0cafd | ||
|
|
e2e0fa291b | ||
|
|
bc2d84f444 | ||
|
|
ae9e4420c8 | ||
|
|
c269f65d08 | ||
|
|
562697423b | ||
|
|
6898eb19e5 | ||
|
|
7c0c2cd18c | ||
|
|
9e82dee23b | ||
|
|
eb828f0eba | ||
|
|
54474acbcc | ||
|
|
820d9d7880 | ||
|
|
1d5e119d26 | ||
|
|
d45e9e510b | ||
|
|
beaa01d4ef | ||
|
|
123741a623 | ||
|
|
3992678141 | ||
|
|
82addcccc1 | ||
|
|
3bdff8ec8c | ||
|
|
3c06ea5fff | ||
|
|
5b4aa4cd55 | ||
|
|
2802643c12 | ||
|
|
8d36dc6fe5 | ||
|
|
849f080999 | ||
|
|
83f176f2f6 | ||
|
|
779d904f53 | ||
|
|
8a1736c1d0 | ||
|
|
3cd55c905b | ||
|
|
833498269d | ||
|
|
07f5c62ef8 | ||
|
|
4cc69cdd3f | ||
|
|
d533a7715b | ||
|
|
59db4e46c6 | ||
|
|
7bff95cf73 | ||
|
|
bd14d75419 | ||
|
|
17e77af99b | ||
|
|
38b51372e6 | ||
|
|
27dc9bc853 | ||
|
|
dba62729b0 | ||
|
|
b110b8787b | ||
|
|
998fa8816e | ||
|
|
51a2798eb5 | ||
|
|
fdd9ef7d18 |
@@ -12,7 +12,7 @@
|
||||
"experimentalObjectRestSpread": true
|
||||
},
|
||||
"plugins": [
|
||||
"markdown",
|
||||
"markdown-antd",
|
||||
"react",
|
||||
"babel"
|
||||
],
|
||||
@@ -29,7 +29,6 @@
|
||||
"no-param-reassign": 0,
|
||||
"no-this-before-super": 2,
|
||||
"no-undef": 2,
|
||||
"no-unused-vars": [2, { "vars": "all", "args": "none" }],
|
||||
"babel/object-shorthand": 0,
|
||||
"react/jsx-no-duplicate-props": 2,
|
||||
"react/sort-comp": 0,
|
||||
|
||||
12
.lesshintrc
Normal file
12
.lesshintrc
Normal file
@@ -0,0 +1,12 @@
|
||||
{
|
||||
"propertyOrdering": false,
|
||||
"hexLength": "short",
|
||||
"stringQuotes": false,
|
||||
"decimalZero": false,
|
||||
"importantRule": false,
|
||||
"zeroUnit": "no_unit",
|
||||
"qualifyingElement": false,
|
||||
"duplicateProperty": false,
|
||||
"importPath": false,
|
||||
"finalNewline": false
|
||||
}
|
||||
@@ -1,6 +0,0 @@
|
||||
{
|
||||
"import": false,
|
||||
"require-newline": false,
|
||||
"leading-zero": false,
|
||||
"single-comment": false
|
||||
}
|
||||
193
CHANGELOG.md
193
CHANGELOG.md
@@ -4,7 +4,149 @@
|
||||
|
||||
---
|
||||
|
||||
## 0.10.2 `2015-11-25`
|
||||
## 0.11.3 `fixing`
|
||||
|
||||
- 修复 TimePicker 受控模式点选即关闭面板的问题。[#818](https://github.com/ant-design/ant-design/issues/818)
|
||||
- 修复一个两栏的 TimePicker 点击右边空白处无法关闭面板的问题。[#826](https://github.com/ant-design/ant-design/issues/826)
|
||||
- 修复 Table `pagination.onChange` 指定无效的问题。[#824](https://github.com/ant-design/ant-design/issues/824)
|
||||
- 修复 Transfer 搜索功能失效的问题。
|
||||
- 修复 DatePicker 的 MonthPicker 样式错乱的问题。
|
||||
- 修复二维码图标,新增一个扫描图标。[#772](https://github.com/ant-design/ant-design/issues/772)
|
||||
|
||||
## 0.11.2
|
||||
|
||||
`2015-01-03`
|
||||
|
||||
- 新增了[贡献文档](https://github.com/ant-design/ant-design/blob/master/CONTRIBUTING.md)。
|
||||
- 修复一个 DatePicker 中选择的国际化文案问题。[#771](https://github.com/ant-design/ant-design/issues/771)
|
||||
- 增加了一个高级搜索类型表单的[演示](http://ant.design/components/form/#demo-advanced-search-form)。
|
||||
- Dropdown 支持多级的下拉菜单。[演示](http://ant.design/components/dropdown/#demo-sub-menu)
|
||||
- Table
|
||||
- 新增 `rowSelection.onChange` 和 `rowSelection.selectedRowKeys`,完善选择功能。
|
||||
- 更新 dataSource 时,选中项现在会被清空。
|
||||
- 修复一个全选框和禁用的选择项配合的问题。
|
||||
- 修复 `0.11.1`版本 menu 内嵌型菜单(inline)选中后关闭的问题。
|
||||
- 修复 `0.11.1`版本对 React 版本要求太严的问题,对应的警告提示对于 `0.14.x` 将不再出现。
|
||||
- 组件和文档的样式小调整。
|
||||
|
||||
## 0.11.1
|
||||
|
||||
`2015-12-29`
|
||||
|
||||
- 修复一个 Table 无法修改 pageSize 的问题。
|
||||
- 修复一个 Table 子表格展开的对齐问题。
|
||||
- 修复一个 Chrome 下部分图标左侧切边的问题。
|
||||
- 修复搜索输入框在表单下使用的样式问题。[#762](https://github.com/ant-design/ant-design/issues/762)
|
||||
|
||||
## 0.11.0
|
||||
|
||||
`2015-12-28`
|
||||
|
||||
- **移除默认加载的样式文件,样式现在需要独立加载。**
|
||||
- 按钮圆角调整为 `6px`。
|
||||
- Modal、Popconfirm、Table、TimePicker 支持国际化配置。
|
||||
- 新增虚线型按钮。
|
||||
- 新增 [通用搜索框](http://ant.design/components/form/#demo-search-input) 样式。
|
||||
- 新增图片上传列表样式[演示](http://ant.design/components/upload/#demo-picture-style)。
|
||||
- **部分设计资源开放 [下载](http://ant.design/spec/tools),包括 Axure 组件库和 Iconfont 字体打包文件。**
|
||||
- 新增 [吊顶规范](http://ant.design/spec/layout/#demo-ceiling)。
|
||||
- 组件演示页面增加锚点。
|
||||
- 新增穿梭框 [Transfer](http://ant.design/components/transfer/) 组件。
|
||||
- 新增小尺寸的 Switch 开关组件。
|
||||
- 增加更多的图标。[#](https://github.com/ant-design/ant-design/commit/087c64649d73206a4d62e52f9b3f6042c1d28608#diff-dc1a1f4794c1c4ee3b083381d4c50c47R180)
|
||||
- 全局微调了警告和错误状态色。
|
||||
- Select
|
||||
- 选中样式进行了调整。
|
||||
- 在标签/多选模式下,选中或删除选项增加了动画效果。
|
||||
- Alert
|
||||
- 默认样式不展示图标。
|
||||
- 带描述的警告框图标改为描线图标。
|
||||
- `type="warn"` 图标修改。
|
||||
- Dropdown 新增带菜单触发的按钮 `Dropdown.Button`。[演示](http://ant.design/components/dropdown/#demo-dropdown-button)
|
||||
- Menu
|
||||
- 新增 `Menu.ItemGroup` 用于把菜单项分组。
|
||||
- onOpen 和 onClose 函数的参数新增了 `keyPath` 数据,可用于制作手风琴类型的菜单。
|
||||
- Badge
|
||||
- 徽章可以独立使用。[演示](http://ant.design/components/badge/#demo-no-wrapper)
|
||||
- 支持设置封顶的 `99+` 的数字。[演示](http://ant.design/components/badge/#demo-overflow)
|
||||
- Slider
|
||||
- 增加 `onAfterChange` 事件。[演示](http://ant.design/components/slider/#demo-event)
|
||||
- 现在设置 `tipFormatter={null}` 可以隐藏 `Tooltip`。
|
||||
- 双滑块拖动体验优化,一个滑块在拖动时可以直接跨过另一滑块。
|
||||
- Breadcrumb 可以自定义分隔符。[演示](http://ant.design/components/breadcrumb/#demo-separator)
|
||||
- Popconfirm 添加 `visible` 属性,使其可以控制是否显示。[演示](http://ant.design/components/popconfirm/#demo-dynamic-trigger)
|
||||
- 修复 Icon `ref` 引起的报错。
|
||||
- 修复 Calendar 组件无法切换年/月的问题。[#757](https://github.com/ant-design/ant-design/issues/757)
|
||||
- Checkbox 新增 `Checkbox.Group`,现可以方便的 [生成一组选择框](http://ant.design/components/checkbox/#demo-group)
|
||||
- Tabs
|
||||
- 新增 [卡片式页签](http://ant.design/components/tabs/#demo-card)。
|
||||
- 调整 [新增和关闭页签](http://ant.design/components/tabs/#demo-editable-card) 的样式。
|
||||
- 现在支持页签的四个位置 `tabPosition="top|right|bottom|left"`。
|
||||
- 移除 `animation` 属性,并在 `tabPosition="top|bottom"` 时默认启用切换动画。
|
||||
- Timepicker
|
||||
- **重命名为 TimePicker。**
|
||||
- 新增 `value` 属性。
|
||||
- 新增属性 `disabledHours` `disabledMinutes` `disabledSeconds`。[演示](http://ant.design/components/time-picker/#picker-demo-disable-options)
|
||||
- 移除 `hourOptions` `minuteOptions` `secondOptions`,新增 `hideDisabled` 属性用于替代。
|
||||
- Datepicker
|
||||
- **重命名为 DatePicker。**
|
||||
- 新增 [日期范围选择控件](http://ant.design/components/date-picker/#picker-demo-range)。
|
||||
- 修改 `showTime` 的交互。[演示](http://ant.design/components/date-picker/#picker-demo-time)
|
||||
- 修正为受控组件。
|
||||
- Table
|
||||
- **移除 `dataSource` 的远程模式。**
|
||||
- 新增 [紧凑型表格](http://ant.design/components/table/#demo-size)。
|
||||
- 允许监听分页的 `onShowSizeChange`。[演示](http://ant.design/components/table/#demo-paging)
|
||||
- 优化表格对树形数据的显示。[演示](http://ant.design/components/table/#demo-indent-size)
|
||||
- 优化了筛选菜单的样式,并添加了最大高度。[演示](http://ant.design/components/table/#demo-head)。
|
||||
- 修复 column.key 设置失效的问题。[#642](https://github.com/ant-design/ant-design/issues/642)
|
||||
- 修复设置时 rowKey 时单选会导致全部选中的问题。[#697](https://github.com/ant-design/ant-design/issues/697)
|
||||
- 修复一个列重新渲染导致选项错乱的问题。[#418](https://github.com/ant-design/ant-design/issues/418#issuecomment-163093580)
|
||||
- 修复选择列无法设置宽度的问题。[#649](https://github.com/ant-design/ant-design/issues/649)
|
||||
- Form
|
||||
- 修复了 Textarea 无法输入的问题。[#646](https://github.com/ant-design/ant-design/issues/646)
|
||||
- 修复了 Textarea 设置 `cols` 和 `rows` 属性失效的问题。[#694](https://github.com/ant-design/ant-design/issues/694)
|
||||
- 修复无法设置 `className` 的问题。[#711](https://github.com/ant-design/ant-design/issues/711)
|
||||
- 修复 Upload 组件在 `beforeUpload` 返回 `false` 后依然更新上传列表问题。[#757](https://github.com/ant-design/ant-design/issues/757)
|
||||
- 工具
|
||||
- 替换 `antd build` 为 [atool-build](https://github.com/ant-tool/atool-build),重构并改善了 webpack 配置的自定义方式。
|
||||
- 替换 `antd server` 为 [dora](https://github.com/dora-js/dora),一个完全插件化的开发服务器,支持[代理转发和数据 Mock](https://github.com/dora-js/dora-plugin-proxy)、[atool-build](https://github.com/dora-js/dora-plugin-atool-build)、[热替换](https://github.com/dora-js/dora-plugin-hmr)。
|
||||
- 新增 babel 插件 [babel-plugin-antd](https://github.com/ant-design/babel-plugin-antd),转换 `import {Button} from 'antd'` 为 `import Button from 'antd/lib/button'`。
|
||||
- 发布了 `antd-init@0.6.x`,支持以上改动。
|
||||
|
||||
> [0.11 升级指南](http://ant.design/docs/upgrade-notes#0-10-gt-0-11)
|
||||
|
||||
---
|
||||
|
||||
## 0.10.5
|
||||
|
||||
`2016-01-04`
|
||||
|
||||
- 修复 Table 更新 dataSource 后,选中项没有置空的问题。[#793](https://github.com/ant-design/ant-design/issues/793)
|
||||
|
||||
## 0.10.4
|
||||
|
||||
`2015-11-30`
|
||||
|
||||
- 将 media-match 加入默认的 polyfill 文件中。[5626974](https://github.com/ant-design/ant-design/commit/562697423b1139eb324c1dceb051c143f4870ed7)
|
||||
- 修复了 [MonthPicker](http://ant.design/components/datepicker/#demo-month-picker) 报错问题,并增加了相关演示。
|
||||
- 修复 RadioGroup 中的 Radio/RadioButton 无法单独设置 disabled 的问题。[#603](https://github.com/ant-design/ant-design/issues/603)
|
||||
- 修复今天是不可选日期时的一个展示问题。[#606](https://github.com/ant-design/ant-design/issues/606)
|
||||
|
||||
|
||||
## 0.10.3
|
||||
|
||||
`2015-11-26`
|
||||
|
||||
- 和 0.9.x 保持一致默认引入 `antd/lib/index.css`(而非 less 文件),方便第三方引用。引用 less 文件进行变量配置的可自行 `import 'antd/style/index.less'`。[#593](https://github.com/ant-design/ant-design/issues/593)
|
||||
- 升级 Pagination,增加 `defaultCurrent` 属性,修正原来的 `current` 为[完全受控属性](https://facebook.github.io/react/docs/forms.html#controlled-components)。
|
||||
- Pagination 的改动也修复了 Table 切换数据源后回到[第一页的例子](http://ant.design/components/table/#demo-ajax)。
|
||||
- 对演示和样式代码增加了 lint 检查。
|
||||
|
||||
|
||||
## 0.10.2
|
||||
|
||||
`2015-11-25`
|
||||
|
||||
- Slider 新增 `tipFormatter` 用于格式化 Tooltip 的内容。
|
||||
- 优化 Badge 动画效果。
|
||||
@@ -15,7 +157,9 @@
|
||||
- InputNumber 同时设置 `size` `className` 时会有冲突。
|
||||
|
||||
|
||||
## 0.10.1 `2015-11-20`
|
||||
## 0.10.1
|
||||
|
||||
`2015-11-20`
|
||||
|
||||
- 修改内部组件的引用结构,方便工具优化。[#566](https://github.com/ant-design/ant-design/pull/566)
|
||||
- 移除了演示中没有使用过的 `antd.ButtonGroup`,依然用 `const ButtonGroup = Button.Group` 来使用。
|
||||
@@ -28,7 +172,9 @@
|
||||
- 修复 Datepicker 的 `style` 和 `calendarStyle` 属性失效的问题,并将 `calendarStyle` 更名为 `popupStyle`。
|
||||
|
||||
|
||||
## 0.10.0 `2015-11-20`
|
||||
## 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/) 组件。
|
||||
@@ -42,7 +188,7 @@
|
||||
- 优先使用苹方字体。
|
||||
- 统一 size 属性的可选值为 `small` `default` `large`。
|
||||
- 开始初步补充[测试用例](https://github.com/ant-design/ant-design/tree/1a3a19793c0791201666fdcf0dbd12a30fad4be0/tests)。
|
||||
- 提供主色系更换的方案。[#384](https://github.com/ant-design/ant-design/issues/384)
|
||||
- 提供主色系更换的[方案](https://github.com/ant-tool/xtool/tree/master/examples/customize-antd-theme)。[#384](https://github.com/ant-design/ant-design/issues/384)
|
||||
- 添加[色彩换算工具](http://ant.design/spec/colors#色彩换算工具)。
|
||||
- 添加布局和导航规范,以及[常用布局](http://ant.design/spec/layout/)。
|
||||
- 文档支持标题和演示的锚点,方便分享文档和演示代码。
|
||||
@@ -94,15 +240,20 @@
|
||||
> 备注:
|
||||
>
|
||||
> - [计划和推进 issue](https://github.com/ant-design/ant-design/issues/276)
|
||||
> - [0.10 升级指南](http://ant.design/docs/upgrade-to-0.10)
|
||||
> - [0.10 升级指南](http://ant.design/docs/upgrade-notes#0-0-gt-0-10)
|
||||
|
||||
---
|
||||
|
||||
## 0.9.3 ~ 0.9.5 `2015-11-04`
|
||||
## 0.9.3 ~ 0.9.5
|
||||
|
||||
`2015-11-04`
|
||||
|
||||
* 增加对 React 版本的检测提示机制,0.9.x 序列只能使用 `react@~0.13.3`。
|
||||
|
||||
|
||||
## 0.9.2 `2015-10-26`
|
||||
## 0.9.2
|
||||
|
||||
`2015-10-26`
|
||||
|
||||
* Tooltip 的 title 为空时不展示浮层。[9b53117](https://github.com/ant-design/ant-design/commit/9b5311791e73270c7c16a602ac74dd59719a5f76)
|
||||
* 修复 Upload 文件列表链接的 target 属性。[340a170](https://github.com/ant-design/ant-design/commit/340a1702b6a7b065ac02d417c891e1886dfe470d)
|
||||
@@ -110,7 +261,9 @@
|
||||
* 修复一些小的样式问题。
|
||||
|
||||
|
||||
## 0.9.1 `2015-09-26`
|
||||
## 0.9.1
|
||||
|
||||
`2015-09-26`
|
||||
|
||||
* 添加 Pagination pageSize 发生变化的回调。[#317](https://github.com/ant-design/ant-design/issues/317)
|
||||
* 升级依赖 rc-upload 到 1.6.x,修复 IE8/9 下的兼容性问题。
|
||||
@@ -129,7 +282,9 @@
|
||||
* 部分组件交互和视觉效果修正。
|
||||
|
||||
|
||||
## 0.9.0 `2015-09-14`
|
||||
## 0.9.0
|
||||
|
||||
`2015-09-14`
|
||||
|
||||
* 新增 [timeline](components/timeline/) 和 [badge](components/badge/) 组件。
|
||||
* 优化弹出层类组件的动画效果,使其更加流畅。
|
||||
@@ -168,7 +323,9 @@
|
||||
* 支持和 react-router 结合使用。
|
||||
|
||||
|
||||
## 0.8.0 `2015-08-25`
|
||||
## 0.8.0
|
||||
|
||||
`2015-08-25`
|
||||
|
||||
这个版本是第一个稳定版,组件经过三期迭代,基本到齐,并有大量改进和变化,不向下兼容。
|
||||
|
||||
@@ -180,12 +337,16 @@
|
||||
* 排查并修复 IE 和 safari 等浏览器的兼容问题。
|
||||
* 大量代码重构,演示代码补充,文档更新、以及样式上的优化。
|
||||
|
||||
## 0.7.3 `2015-07-30`
|
||||
## 0.7.3
|
||||
|
||||
`2015-07-30`
|
||||
|
||||
* 小幅重构了 Table 分页,修复了分页导致的数据不展示的问题。
|
||||
* 更新了部分文档。
|
||||
|
||||
## 0.7.2 `2015-07-27`
|
||||
## 0.7.2
|
||||
|
||||
`2015-07-27`
|
||||
|
||||
* 修复本地模式下 pagination 为 false 时数据无法显示的 [问题](https://github.com/ant-design/ant-design/commit/1954586665e59031eae5d2c8b2cdb08f83d64fcb)。
|
||||
* 重构了 message 组件。
|
||||
@@ -193,14 +354,18 @@
|
||||
* 部分代码切换至 ES6 模式。
|
||||
* 修正了部分组件的样式和演示,优化部分动画。
|
||||
|
||||
## 0.7.1 `2015-07-22`
|
||||
## 0.7.1
|
||||
|
||||
`2015-07-22`
|
||||
|
||||
* 修复了 Table 组件的 pagination 为 false 时分页未消失的 [问题](https://github.com/ant-design/ant-design/commit/01a6c0f1e6707b72a54ef30d073d148a87b391a8)。
|
||||
* select 组件[选中后默认显示标签内容](https://github.com/ant-design/ant-design/issues/50)(原来是显示 value)。
|
||||
* 修正了部分组件的样式和演示。
|
||||
* 打包文件为 [umd 模式](https://github.com/ant-design/ant-design/commit/9b7b940cb417429d8fc57d83e252991b043d0f2f)。
|
||||
|
||||
## 0.7.0 `2015-07-21`
|
||||
## 0.7.0
|
||||
|
||||
`2015-07-21`
|
||||
|
||||
* 第一个公开版本,发布 `layout`、`iconfont`、`button`、`form`、`checkbox`、`radio`、`switch`、`slider`、`input-number`、`datepicker`、`select`、`tabs`、`steps`、`breadcrumb`、`collapse`、`pagination`、`modal`、`message`、`dropdown`、`popover`、`popconfirm`、`tooltip`、`progress`、`table` 等组件。
|
||||
* 发布 [Ant Design 首页](http://ant.design/) 和入门文档。
|
||||
|
||||
52
CONTRIBUTING.md
Normal file
52
CONTRIBUTING.md
Normal file
@@ -0,0 +1,52 @@
|
||||
# Contributing to Ant Design
|
||||
|
||||
The following is a set of guidelines for contributing to Ant Design. Please spend several minutes in reading these guidelines before you create an issue or pull request.
|
||||
|
||||
Anyway, these are just guidelines, not rules, use your best judgment and feel free to propose changes to this document in a pull request.
|
||||
|
||||
|
||||
## Do your homework before asking a question
|
||||
|
||||
It's a great idea to read Eric Steven Raymond's [How To Ask Questions The Smart Way](http://www.catb.org/esr/faqs/smart-questions.html) twice before asking a question. But if you are busy now, I recommend to read [Don't post homework questions](http://www.catb.org/esr/faqs/smart-questions.html#homework) first.
|
||||
|
||||
The following guidelines are about *How to avoid Homework Questions*.
|
||||
|
||||
### 1. Read the documentation.
|
||||
|
||||
It sad but true that someone just glance(not read) [Ant Design's documentation](http://ant.design/). Please read the documentation closely. What's more, you can modify and run our demo with [JSFiddle](http://jsfiddle.net/9zrstuto/70/). It's helpful to understand our documentation.
|
||||
|
||||
Tips: choose the corresponding documentation with versions selector which in the bottom-right corner.
|
||||
|
||||
### 2. Make sure that your question is about Ant Design, not React
|
||||
|
||||
Someone may think all of the questions that he/she meets in developing are about Ant Design, but it's not true. So, please read [React's documentaion](http://facebook.github.io/react/docs/getting-started.html) or just Google(not Baidu, seriously) your questions with keywork *React* first. If you are sure that your question is about Ant Design, go ahead.
|
||||
|
||||
### 3. Read the FAQ and search the issues list of Ant Design
|
||||
|
||||
Your questions may be asked and solved by others. So please spend several minutes on searching. Remember [DRY](https://en.wikipedia.org/wiki/Don%27t_repeat_yourself), both code and questions.
|
||||
|
||||
P.S.
|
||||
1. [FAQ](https://github.com/ant-design/ant-design/wiki/FAQ)
|
||||
1. [Issues list](https://github.com/ant-design/ant-design/issues)
|
||||
|
||||
|
||||
## Providing a demo while reporting a bug
|
||||
|
||||
It would be helpful to provide a demo which can re-produce the bug 100%. Please fork this [Fiddle](http://jsfiddle.net/0dso5y0x/) and re-produce the bug you met. Then, create an issue like this [example](https://github.com/ant-design/ant-design/issues/new?title=%E8%AF%B7%E5%A1%AB%E5%86%99%E7%AE%80%E6%B4%81%E6%9C%89%E6%95%88%E7%9A%84%E6%A0%87%E9%A2%98&body=**%E9%97%AE%E9%A2%98%E6%8F%8F%E8%BF%B0**%0A%0A%EF%BC%88%E6%8F%8F%E8%BF%B0%E4%B8%80%E4%B8%8B%E9%97%AE%E9%A2%98%EF%BC%89%0A%0A**%E5%8F%91%E7%94%9F%E7%8E%AF%E5%A2%83**%0A%0A-%20antd%20%E7%89%88%E6%9C%AC%EF%BC%9A%0A-%20%E6%93%8D%E4%BD%9C%E7%B3%BB%E7%BB%9F%E5%8F%8A%E7%89%88%E6%9C%AC%EF%BC%9A%0A-%20%E6%B5%8F%E8%A7%88%E5%99%A8%E5%8F%8A%E7%89%88%E6%9C%AC%EF%BC%9A%0A-%20%E5%9C%A8%E7%BA%BF%E6%BC%94%E7%A4%BA%E5%9C%B0%E5%9D%80%EF%BC%9A%0A%0A**%E9%87%8D%E7%8E%B0%E6%AD%A5%E9%AA%A4**%0A%0A1.%20...%0A2.%20...%0A). The most important thing is: double check before claiming that you have found a bug.
|
||||
|
||||
|
||||
## Tips about Feature Request
|
||||
|
||||
If you believe that Ant Design should provide some features, but it does not. You could create an issue to discuss. However, Ant Design is not Swiss Army Knife, there are some features which Ant Design will not support:
|
||||
|
||||
1. Request or operate data
|
||||
|
||||
|
||||
## Tips about Pull Request
|
||||
|
||||
It's welcomed to pull request. And there are some tips about that:
|
||||
|
||||
1. It is a good habit to create a feature request issue to disscuss whether the feature is necessary before you implement it.
|
||||
1. Run `npm run lint` and fix those errors before committing in order to keep consistent code style.
|
||||
1. Rebase before creating a PR to keep commit history clear.
|
||||
1. Add some descriptions and refer relative issues for you PR.
|
||||
@@ -1,20 +1,18 @@
|
||||
<p align="center">
|
||||
<a href="http://ant.design">
|
||||
<img width="320" src="https://t.alipayobjects.com/images/rmsweb/T1B9hfXcdvXXXXXXXX.svg">
|
||||
</a>
|
||||
</p>
|
||||
|
||||
# Ant Design [](https://travis-ci.org/ant-design/ant-design) [](https://www.npmjs.org/package/antd) [](https://npmjs.org/package/antd) [](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。
|
||||
- 提炼和服务企业级中后台产品的交互语言和视觉风格。
|
||||
- [React Component](http://react-component.github.io/badgeboard/) 上精心封装的高质量 UI 库。
|
||||
- 基于 npm + webpack + babel 的工作流,支持 ES2015。
|
||||
|
||||
|
||||
## 安装
|
||||
@@ -25,20 +23,19 @@ npm install antd
|
||||
|
||||
## 示例
|
||||
|
||||
- 使用全部组件
|
||||
```jsx
|
||||
import { DatePicker } from 'antd';
|
||||
ReactDOM.render(<DatePicker />, mountNode);
|
||||
```
|
||||
|
||||
```jsx
|
||||
import { Datepicker } from 'antd';
|
||||
ReactDOM.render(<Datepicker />, mountNode);
|
||||
```
|
||||
引入样式:
|
||||
|
||||
- 按需使用
|
||||
```jsx
|
||||
import 'antd/lib/index.css'; // or 'antd/style/index.less'
|
||||
```
|
||||
|
||||
按需加载可通过此写法 `import DatePicker from 'antd/lib/date-picker'` 或使用插件 [babel-plugin-antd](https://github.com/ant-design/babel-plugin-antd)。
|
||||
|
||||
```jsx
|
||||
import 'antd/lib/index.css'; // 只需在页面入口模块引用一次
|
||||
import Datepicker from 'antd/lib/datepicker';
|
||||
ReactDOM.render(<Datepicker />, mountNode);
|
||||
```
|
||||
|
||||
## 浏览器支持
|
||||
|
||||
@@ -47,11 +44,11 @@ npm install antd
|
||||
## 链接
|
||||
|
||||
- [首页](http://ant.design/)
|
||||
- [文档和组件](http://ant.design/docs/introduce)
|
||||
- [构建调试工具](https://github.com/ant-design/antd-bin)
|
||||
- [开发计划](https://github.com/ant-design/ant-design/issues/9)
|
||||
- [React UI 库](http://ant.design/docs/react/introduce)
|
||||
- [修改记录](CHANGELOG.md)
|
||||
- [React 模块](http://react-component.github.io/)
|
||||
- [开发脚手架](https://github.com/ant-design/antd-init/)
|
||||
- [本地调试工具集](https://github.com/dora-js/dora/)
|
||||
- [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)
|
||||
|
||||
48
README.md
48
README.md
@@ -1,16 +1,18 @@
|
||||
<p align="center">
|
||||
<a href="http://ant.design">
|
||||
<img width="320" src="https://t.alipayobjects.com/images/rmsweb/T1B9hfXcdvXXXXXXXX.svg">
|
||||
</a>
|
||||
</p>
|
||||
|
||||
# Ant Design [](https://travis-ci.org/ant-design/ant-design) [](https://www.npmjs.org/package/antd) [](https://npmjs.org/package/antd) [](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.
|
||||
|
||||

|
||||
|
||||
## Features
|
||||
|
||||
- An enterprise-class graphical design language and framework for financial applications
|
||||
- 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
|
||||
- A npm + webpack + babel workflow, supporting ES2015.
|
||||
|
||||
## Install
|
||||
|
||||
@@ -20,20 +22,19 @@ npm install antd
|
||||
|
||||
## Usage example
|
||||
|
||||
- Use all components
|
||||
```jsx
|
||||
import { DatePicker } from 'antd';
|
||||
ReactDOM.render(<DatePicker />, mountNode);
|
||||
```
|
||||
|
||||
```jsx
|
||||
import { Datepicker } from 'antd';
|
||||
ReactDOM.render(<Datepicker />, mountNode);
|
||||
```
|
||||
Import style:
|
||||
|
||||
- Use on demand
|
||||
```jsx
|
||||
import 'antd/lib/index.css'; // or 'antd/style/index.less'
|
||||
```
|
||||
|
||||
Use components on demand by writing as `import DatePicker from 'antd/lib/date-picker'` or use [babel-plugin-antd](https://github.com/ant-design/babel-plugin-antd).
|
||||
|
||||
```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
|
||||
|
||||
@@ -43,14 +44,13 @@ 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)
|
||||
- [React UI library](http://ant.design/docs/react/introduce)
|
||||
- [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)
|
||||
- [Scaffold tool](https://github.com/ant-design/antd-init/)
|
||||
- [Debug tools set](https://github.com/dora-js/dora)
|
||||
- [React components](http://react-component.github.io/)
|
||||
- [React style guide](https://github.com/react-component/react-component.github.io/blob/master/docs/zh-cn/component-code-style.md)
|
||||
- [React component design guide](https://github.com/react-component/react-component.github.io/blob/master/docs/zh-cn/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)
|
||||
|
||||
|
||||
@@ -13,5 +13,5 @@ ReactDOM.render(
|
||||
<Affix>
|
||||
<Button type="primary">固定在顶部</Button>
|
||||
</Affix>
|
||||
, document.getElementById('components-affix-demo-basic'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
@@ -13,5 +13,5 @@ ReactDOM.render(
|
||||
<Affix offset={75}>
|
||||
<Button type="primary">固定在距离顶部 75px 的位置</Button>
|
||||
</Affix>
|
||||
, document.getElementById('components-affix-demo-offset'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
@@ -10,5 +10,5 @@
|
||||
import { Alert } from 'antd';
|
||||
|
||||
ReactDOM.render(<Alert message="成功提示的文案" type="success" />
|
||||
, document.getElementById('components-alert-demo-basic'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
# 可关闭的警告提示
|
||||
|
||||
- order: 1
|
||||
- order: 2
|
||||
|
||||
显示关闭按钮,点击可关闭警告提示。
|
||||
|
||||
@@ -23,5 +23,5 @@ ReactDOM.render(<div>
|
||||
type="error"
|
||||
closable
|
||||
onClose={onClose} />
|
||||
</div>, document.getElementById('components-alert-demo-closable'));
|
||||
</div>, mountNode);
|
||||
````
|
||||
|
||||
15
components/alert/demo/close-text.md
Normal file
15
components/alert/demo/close-text.md
Normal file
@@ -0,0 +1,15 @@
|
||||
# 自定义关闭
|
||||
|
||||
- order: 5
|
||||
|
||||
可以自定义关闭,自定义的文字会替换原先的关闭 `Icon`。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Alert } from 'antd';
|
||||
|
||||
ReactDOM.render(
|
||||
<Alert message="消息提示的文案" type="info" closeText="不再提醒" />
|
||||
, mountNode);
|
||||
````
|
||||
@@ -1,16 +0,0 @@
|
||||
# 自定义关闭
|
||||
|
||||
- order: 4
|
||||
|
||||
可以自定义关闭,自定义的文字会替换原先的关闭 `Icon`。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Alert } from 'antd';
|
||||
const link = <a href="#">不再提醒</a>;
|
||||
|
||||
ReactDOM.render(
|
||||
<Alert message="消息提示的文案" type="info" closeText={link} />
|
||||
, document.getElementById('components-alert-demo-close-type'));
|
||||
````
|
||||
@@ -1,6 +1,6 @@
|
||||
# 含有辅助性文字介绍
|
||||
|
||||
- order: 2
|
||||
- order: 3
|
||||
|
||||
含有辅助性文字介绍的警告提示。
|
||||
|
||||
@@ -24,5 +24,5 @@ ReactDOM.render(<div>
|
||||
message="错误提示的文案"
|
||||
description="错误提示的辅助性文字介绍错误提示的辅助性文字介绍错误提示的辅助性文字介绍错误提示的辅助性文字介绍错误提示的辅助性文字介绍错误提示的辅助性文字介绍"
|
||||
type="error" />
|
||||
</div>, document.getElementById('components-alert-demo-description'));
|
||||
</div>, mountNode);
|
||||
````
|
||||
|
||||
36
components/alert/demo/icon.md
Normal file
36
components/alert/demo/icon.md
Normal file
@@ -0,0 +1,36 @@
|
||||
# 图标
|
||||
|
||||
- order: 4
|
||||
|
||||
可口的图标让信息类型更加醒目。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Alert } from 'antd';
|
||||
|
||||
ReactDOM.render(<div>
|
||||
<Alert message="成功提示的文案" type="success" showIcon />
|
||||
<Alert message="消息提示的文案" type="info" showIcon />
|
||||
<Alert message="警告提示的文案" type="warn" showIcon />
|
||||
<Alert message="错误提示的文案" type="error" showIcon />
|
||||
<Alert message="成功提示的文案"
|
||||
description="成功提示的辅助性文字介绍成功提示的辅助性文字介绍成功提示的辅助性文字介绍成功提示的辅助性文字介绍"
|
||||
type="success"
|
||||
showIcon />
|
||||
<Alert message="消息提示的文案"
|
||||
description="消息提示的辅助性文字介绍消息提示的辅助性文字介绍消息提示的辅助性文字介绍"
|
||||
type="info"
|
||||
showIcon />
|
||||
<Alert
|
||||
message="警告提示的文案"
|
||||
description="警告提示的辅助性文字介绍警告提示的辅助性文字介绍"
|
||||
type="warn"
|
||||
showIcon />
|
||||
<Alert
|
||||
message="错误提示的文案"
|
||||
description="错误提示的辅助性文字介绍错误提示的辅助性文字介绍错误提示的辅助性文字介绍错误提示的辅助性文字介绍错误提示的辅助性文字介绍错误提示的辅助性文字介绍"
|
||||
type="error"
|
||||
showIcon />
|
||||
</div>, mountNode);
|
||||
````
|
||||
@@ -1,6 +1,6 @@
|
||||
# 四种样式
|
||||
|
||||
- order: 3
|
||||
- order: 1
|
||||
|
||||
共有四种样式`success`、`info`、`warn`、`error`。
|
||||
|
||||
@@ -15,5 +15,5 @@ ReactDOM.render(<div>
|
||||
<Alert message="警告提示的文案" type="warn" />
|
||||
<Alert message="错误提示的文案" type="error" />
|
||||
</div>,
|
||||
document.getElementById('components-alert-demo-style'));
|
||||
mountNode);
|
||||
````
|
||||
|
||||
@@ -2,11 +2,14 @@ import React from 'react';
|
||||
import ReactDOM from 'react-dom';
|
||||
import Animate from 'rc-animate';
|
||||
import Icon from '../icon';
|
||||
import classNames from 'classnames';
|
||||
|
||||
export default React.createClass({
|
||||
getDefaultProps() {
|
||||
return {
|
||||
prefixCls: 'ant-alert'
|
||||
prefixCls: 'ant-alert',
|
||||
showIcon: false,
|
||||
onClose() {}
|
||||
};
|
||||
},
|
||||
getInitialState() {
|
||||
@@ -26,9 +29,7 @@ export default React.createClass({
|
||||
this.setState({
|
||||
closing: false
|
||||
});
|
||||
if (this.props.onClose) {
|
||||
this.props.onClose.call(this, e);
|
||||
}
|
||||
this.props.onClose.call(this, e);
|
||||
},
|
||||
animationEnd() {
|
||||
this.setState({
|
||||
@@ -37,10 +38,12 @@ export default React.createClass({
|
||||
});
|
||||
},
|
||||
render() {
|
||||
let iconClass = this.props.description ?
|
||||
'ant-alert-with-description-icon' : 'ant-alert-icon';
|
||||
let {
|
||||
closable, description, type, prefixCls, message, closeText, showIcon
|
||||
} = this.props;
|
||||
|
||||
let iconType = '';
|
||||
switch (this.props.type) {
|
||||
switch (type) {
|
||||
case 'success':
|
||||
iconType = 'check-circle';
|
||||
break;
|
||||
@@ -51,49 +54,44 @@ export default React.createClass({
|
||||
iconType = 'exclamation-circle';
|
||||
break;
|
||||
case 'warn':
|
||||
iconType = 'question-circle';
|
||||
iconType = 'exclamation-circle';
|
||||
break;
|
||||
default:
|
||||
iconType = 'default';
|
||||
}
|
||||
let html;
|
||||
let closeName = !this.state.closing ? ' ' + this.props.prefixCls + '-close' : '';
|
||||
if (this.props.description) {
|
||||
let close = this.props.closable ?
|
||||
<a onClick={this.handleClose} className={'ant-alert-with-description-close-icon'}>
|
||||
<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}>
|
||||
<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}
|
||||
</div>;
|
||||
} else {
|
||||
if (this.props.closeText) {
|
||||
html = <div data-show={this.state.closing} className={'ant-alert ant-alert-' + this.props.type + closeName}>
|
||||
<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>;
|
||||
} else {
|
||||
let close = this.props.closable ?
|
||||
<a onClick={this.handleClose} className={'ant-alert-close-icon'}>
|
||||
<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}>
|
||||
<Icon className={iconClass} type={iconType} />
|
||||
<span className={'ant-alert-description'}>{this.props.message}</span>
|
||||
{close}
|
||||
</div>;
|
||||
}
|
||||
|
||||
// use outline icon in alert with description
|
||||
if (!!description) {
|
||||
iconType += '-o';
|
||||
}
|
||||
return this.state.closed ? null : <Animate
|
||||
component=""
|
||||
showProp="data-show"
|
||||
transitionName="slide-up"
|
||||
onEnd={this.animationEnd}>
|
||||
{html}
|
||||
</Animate>;
|
||||
|
||||
let alertCls = classNames({
|
||||
[prefixCls]: true,
|
||||
[prefixCls + '-' + type]: true,
|
||||
[prefixCls + '-close']: !this.state.closing,
|
||||
[prefixCls + '-with-description']: !!description,
|
||||
[prefixCls + '-no-icon']: !showIcon,
|
||||
});
|
||||
|
||||
// closeable when closeText is assigned
|
||||
if (closeText) {
|
||||
closable = true;
|
||||
}
|
||||
|
||||
return this.state.closed ? null : (
|
||||
<Animate component=""
|
||||
showProp="data-show"
|
||||
transitionName="slide-up"
|
||||
onEnd={this.animationEnd}>
|
||||
<div data-show={this.state.closing} className={alertCls}>
|
||||
{showIcon ? <Icon className="ant-alert-icon" type={iconType} /> : null}
|
||||
<span className={prefixCls + '-message'}>{message}</span>
|
||||
<span className={prefixCls + '-description'}>{description}</span>
|
||||
{closable ? <a onClick={this.handleClose} className={prefixCls + '-close-icon'}>
|
||||
{closeText || <Icon type="cross" />}
|
||||
</a> : null}
|
||||
</div>
|
||||
</Animate>
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
@@ -23,3 +23,4 @@
|
||||
| message | 必选参数,警告提示内容 | String | 无 |
|
||||
| description | 可选参数,警告提示的辅助性文字介绍 | String | 无 |
|
||||
| onClose | 可选参数,关闭时触发的回调函数 | Function | 无 |
|
||||
| showIcon | 可选参数,是否显示辅助图标 | Boolean | false |
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import React, { createElement } from 'react';
|
||||
import assign from 'object-assign';
|
||||
import { isCssAnimationSupported } from 'css-animation';
|
||||
|
||||
function getNumberArray(num) {
|
||||
return num ?
|
||||
@@ -98,7 +99,8 @@ class AntScrollNumber extends React.Component {
|
||||
const props = assign({}, this.props, {
|
||||
className: `${this.props.prefixCls} ${this.props.className}`
|
||||
});
|
||||
if (typeof document !== 'undefined' && typeof window !== 'undefined') {
|
||||
const isBrowser = (typeof document !== 'undefined' && typeof window !== 'undefined');
|
||||
if (isBrowser && isCssAnimationSupported) {
|
||||
return createElement(
|
||||
this.props.component,
|
||||
props,
|
||||
@@ -119,7 +121,7 @@ AntScrollNumber.defaultProps = {
|
||||
count: null,
|
||||
component: 'sup',
|
||||
onAnimated: function() {},
|
||||
height: 20
|
||||
height: 18,
|
||||
};
|
||||
|
||||
AntScrollNumber.propTypes = {
|
||||
|
||||
@@ -16,5 +16,5 @@ ReactDOM.render(<div>
|
||||
<Badge count={200}>
|
||||
<a href="#" className="head-example"></a>
|
||||
</Badge>
|
||||
</div>, document.getElementById('components-badge-demo-99plus'));
|
||||
</div>, mountNode);
|
||||
````
|
||||
|
||||
@@ -13,7 +13,7 @@ ReactDOM.render(
|
||||
<Badge count={5}>
|
||||
<a href="#" className="head-example"></a>
|
||||
</Badge>
|
||||
, document.getElementById('components-badge-demo-basic'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
````css
|
||||
|
||||
@@ -69,5 +69,5 @@ const Test = React.createClass({
|
||||
|
||||
ReactDOM.render(
|
||||
<Test />
|
||||
, document.getElementById('components-badge-demo-change'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
@@ -16,7 +16,7 @@ ReactDOM.render(<div>
|
||||
<Badge dot>
|
||||
<a href="#">一个链接</a>
|
||||
</Badge>
|
||||
</div>, document.getElementById('components-badge-demo-dot'));
|
||||
</div>, mountNode);
|
||||
````
|
||||
|
||||
<style>
|
||||
|
||||
@@ -15,5 +15,5 @@ ReactDOM.render(
|
||||
<span className="head-example"></span>
|
||||
</Badge>
|
||||
</a>
|
||||
, document.getElementById('components-badge-demo-link'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
19
components/badge/demo/no-wrapper.md
Normal file
19
components/badge/demo/no-wrapper.md
Normal file
@@ -0,0 +1,19 @@
|
||||
# 独立使用
|
||||
|
||||
- order: 0
|
||||
|
||||
不包裹任何元素即是独立使用,可自定样式展现。
|
||||
|
||||
> 在右上角的 badge 则限定为红色。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Badge } from 'antd';
|
||||
|
||||
ReactDOM.render(<div>
|
||||
<Badge count={25} />
|
||||
<Badge count={4} style={{backgroundColor: '#fff', color: '#999', borderColor: '#d9d9d9'}} />
|
||||
<Badge count={109} style={{backgroundColor: '#87d068'}} />
|
||||
</div>, mountNode);
|
||||
````
|
||||
20
components/badge/demo/overflow.md
Normal file
20
components/badge/demo/overflow.md
Normal file
@@ -0,0 +1,20 @@
|
||||
# 封顶数字
|
||||
|
||||
- order: 6
|
||||
|
||||
超过 `overflowCount` 的会显示为 `${overflowCount}+`。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Badge } from 'antd';
|
||||
|
||||
ReactDOM.render(<div>
|
||||
<Badge count={99} overflowCount={10}>
|
||||
<a href="#" className="head-example"></a>
|
||||
</Badge>
|
||||
<Badge count={1000} overflowCount={999}>
|
||||
<a href="#" className="head-example"></a>
|
||||
</Badge>
|
||||
</div>, mountNode);
|
||||
````
|
||||
@@ -1,6 +1,7 @@
|
||||
import React from 'react';
|
||||
import Animate from 'rc-animate';
|
||||
import ScrollNumber from './ScrollNumber';
|
||||
import classNames from 'classnames';
|
||||
|
||||
class AntBadge extends React.Component {
|
||||
constructor(props) {
|
||||
@@ -8,10 +9,10 @@ class AntBadge extends React.Component {
|
||||
}
|
||||
|
||||
render() {
|
||||
let { count, prefixCls } = this.props;
|
||||
let { count, prefixCls, overflowCount, className, style, children } = this.props;
|
||||
const dot = this.props.dot;
|
||||
|
||||
count = count >= 100 ? '99+' : count;
|
||||
count = count > overflowCount ? `${overflowCount}+` : count;
|
||||
|
||||
// dot mode don't need count
|
||||
if (dot) {
|
||||
@@ -20,18 +21,24 @@ class AntBadge extends React.Component {
|
||||
|
||||
// null undefined "" "0" 0
|
||||
const hidden = (!count || count === '0') && !dot;
|
||||
const className = prefixCls + (dot ? '-dot' : '-count');
|
||||
const scrollNumberCls = prefixCls + (dot ? '-dot' : '-count');
|
||||
const badgeCls = classNames({
|
||||
[className]: !!className,
|
||||
[prefixCls]: true,
|
||||
[`${prefixCls}-not-a-wrapper`]: !children,
|
||||
});
|
||||
|
||||
return (
|
||||
<span className={prefixCls} title={count} {...this.props}>
|
||||
{this.props.children}
|
||||
<span className={badgeCls} title={count} {...this.props} style={null}>
|
||||
{children}
|
||||
<Animate component=""
|
||||
showProp="data-show"
|
||||
transitionName={prefixCls + '-zoom'}
|
||||
transitionAppear>
|
||||
{
|
||||
hidden ? null :
|
||||
<ScrollNumber data-show={!hidden} className={className} count={count} />
|
||||
<ScrollNumber data-show={!hidden} className={scrollNumberCls}
|
||||
count={count} style={style} />
|
||||
}
|
||||
</Animate>
|
||||
</span>
|
||||
@@ -43,6 +50,7 @@ AntBadge.defaultProps = {
|
||||
prefixCls: 'ant-badge',
|
||||
count: null,
|
||||
dot: false,
|
||||
overflowCount: 99,
|
||||
};
|
||||
|
||||
AntBadge.propTypes = {
|
||||
@@ -51,6 +59,7 @@ AntBadge.propTypes = {
|
||||
React.PropTypes.number
|
||||
]),
|
||||
dot: React.PropTypes.bool,
|
||||
overflowCount: React.PropTypes.number,
|
||||
};
|
||||
|
||||
export default AntBadge;
|
||||
|
||||
@@ -20,7 +20,13 @@
|
||||
</Badge>
|
||||
```
|
||||
|
||||
|
||||
```jsx
|
||||
<Badge count={5} />
|
||||
```
|
||||
|
||||
| 参数 | 说明 | 类型 | 可选值 | 默认值 |
|
||||
|----------------|----------------------------------|------------|---------|--------|
|
||||
| count | 展示的数字,大于 99 时显示为 99+,为 0 时隐藏 | Number | | |
|
||||
| count | 展示的数字,大于 overflowCount 时显示为 `${overflowCount}+`,为 0 时隐藏 | Number | | |
|
||||
| overflowCount | 展示封顶的数字值 | Number | | 99 |
|
||||
| dot | 不展示数字,只有一个小红点 | boolean | | false |
|
||||
|
||||
@@ -16,5 +16,5 @@ ReactDOM.render(
|
||||
<Breadcrumb.Item href="">应用列表</Breadcrumb.Item>
|
||||
<Breadcrumb.Item>某应用</Breadcrumb.Item>
|
||||
</Breadcrumb>
|
||||
, document.getElementById('components-breadcrumb-demo-basic'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
@@ -41,13 +41,13 @@ const Home = React.createClass({
|
||||
|
||||
ReactDOM.render((
|
||||
<Router>
|
||||
<Route name="home" breadcrumbName="首页" path="/" component={Home} ignoreScrollBehavior>
|
||||
<Route name="home" breadcrumbName="首页" path="/" component={Home}>
|
||||
<Route name="apps" breadcrumbName="应用列表" path="apps" component={Apps}>
|
||||
<Route name="app" breadcrumbName="应用:id" path=":id" />
|
||||
</Route>
|
||||
</Route>
|
||||
</Router>
|
||||
), document.getElementById('components-breadcrumb-demo-router'));
|
||||
), mountNode);
|
||||
````
|
||||
|
||||
<style>
|
||||
|
||||
20
components/breadcrumb/demo/separator.md
Normal file
20
components/breadcrumb/demo/separator.md
Normal file
@@ -0,0 +1,20 @@
|
||||
# 分隔符
|
||||
|
||||
- order: 3
|
||||
|
||||
使用 `separator=">"` 可以自定义分隔符。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Breadcrumb } from 'antd';
|
||||
|
||||
ReactDOM.render(
|
||||
<Breadcrumb separator=">">
|
||||
<Breadcrumb.Item>首页</Breadcrumb.Item>
|
||||
<Breadcrumb.Item href="">应用中心</Breadcrumb.Item>
|
||||
<Breadcrumb.Item href="">应用列表</Breadcrumb.Item>
|
||||
<Breadcrumb.Item>某应用</Breadcrumb.Item>
|
||||
</Breadcrumb>
|
||||
, mountNode);
|
||||
````
|
||||
@@ -22,6 +22,6 @@ ReactDOM.render(
|
||||
应用
|
||||
</Breadcrumb.Item>
|
||||
</Breadcrumb>
|
||||
, document.getElementById('components-breadcrumb-demo-withicon'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
|
||||
@@ -1,52 +1,79 @@
|
||||
import React from 'react';
|
||||
import React, { cloneElement } from 'react';
|
||||
|
||||
let prefixCls = 'ant-breadcrumb';
|
||||
|
||||
let BreadcrumbItem = React.createClass({
|
||||
const BreadcrumbItem = React.createClass({
|
||||
getDefaultProps() {
|
||||
return {
|
||||
prefixCls: 'ant-breadcrumb',
|
||||
separator: '/',
|
||||
};
|
||||
},
|
||||
propTypes: {
|
||||
href: React.PropTypes.string
|
||||
prefixCls: React.PropTypes.string,
|
||||
separator: React.PropTypes.oneOfType([
|
||||
React.PropTypes.string,
|
||||
React.PropTypes.element,
|
||||
]),
|
||||
href: React.PropTypes.string,
|
||||
},
|
||||
render() {
|
||||
let link = <a className={prefixCls + '-link'} {...this.props}>{this.props.children}</a>;
|
||||
let slash = <span className={prefixCls + '-slash'}>/</span>;
|
||||
const { prefixCls, separator, children } = this.props;
|
||||
let link = <a className={prefixCls + '-link'} {...this.props}>{children}</a>;
|
||||
if (typeof this.props.href === 'undefined') {
|
||||
link = <span className={prefixCls + '-link'} {...this.props}>{this.props.children}</span>;
|
||||
link = <span className={prefixCls + '-link'} {...this.props}>{children}</span>;
|
||||
}
|
||||
return <span>{link}{slash}</span>;
|
||||
return <span>
|
||||
{link}
|
||||
<span className={prefixCls + '-separator'}>{separator}</span>
|
||||
</span>;
|
||||
}
|
||||
});
|
||||
|
||||
let Breadcrumb = React.createClass({
|
||||
const Breadcrumb = React.createClass({
|
||||
getDefaultProps() {
|
||||
return {
|
||||
prefixCls: 'ant-breadcrumb',
|
||||
separator: '/',
|
||||
};
|
||||
},
|
||||
propTypes: {
|
||||
prefixCls: React.PropTypes.string,
|
||||
separator: React.PropTypes.oneOfType([
|
||||
React.PropTypes.string,
|
||||
React.PropTypes.element,
|
||||
]),
|
||||
router: React.PropTypes.object,
|
||||
routes: React.PropTypes.array,
|
||||
params: React.PropTypes.object
|
||||
},
|
||||
render() {
|
||||
let crumbs;
|
||||
let ReactRouter = this.props.router;
|
||||
let routes = this.props.routes;
|
||||
let params = this.props.params;
|
||||
const { separator, prefixCls, router, routes, params, children } = this.props;
|
||||
const ReactRouter = router;
|
||||
if (routes && routes.length > 0 && ReactRouter) {
|
||||
let Link = ReactRouter.Link;
|
||||
crumbs = routes.map(function(route, i) {
|
||||
if (!route.breadcrumbName) {
|
||||
return null;
|
||||
}
|
||||
let name = route.breadcrumbName.replace(/\:(.*)/g, function(replacement, key) {
|
||||
const name = route.breadcrumbName.replace(/\:(.*)/g, function(replacement, key) {
|
||||
return params[key] || replacement;
|
||||
});
|
||||
let link;
|
||||
let path = route.path.indexOf('/') === 0 ? route.path : ('/' + route.path);
|
||||
const path = route.path.indexOf('/') === 0 ? route.path : ('/' + route.path);
|
||||
if (i === routes.length - 1) {
|
||||
link = <span>{name}</span>;
|
||||
} else {
|
||||
link = <Link to={path} params={params}>{name}</Link>;
|
||||
}
|
||||
return <BreadcrumbItem key={name}>{link}</BreadcrumbItem>;
|
||||
return <BreadcrumbItem separator={separator} key={name}>{link}</BreadcrumbItem>;
|
||||
});
|
||||
} else {
|
||||
crumbs = this.props.children;
|
||||
crumbs = React.Children.map(children, (element, index) => {
|
||||
return cloneElement(element, {
|
||||
separator,
|
||||
key: index,
|
||||
});
|
||||
});
|
||||
}
|
||||
return (
|
||||
<div className={prefixCls}>
|
||||
|
||||
@@ -27,11 +27,12 @@
|
||||
|
||||
### Breadcrumb
|
||||
|
||||
| 参数 | 说明 | 类型 | 可选值 | 默认值 |
|
||||
|-----------|------------------------------------------|------------|---------|--------|
|
||||
| router | 可传入 react-router 的实例 | Object | | - |
|
||||
| routes | router 的路由栈信息 | Array | | - |
|
||||
| params | 路由的参数 | Object | | - |
|
||||
| 参数 | 说明 | 类型 | 可选值 | 默认值 |
|
||||
|-----------|-----------------------------------|-------------------|---------|--------|
|
||||
| router | 可传入 react-router 的实例 | Object | | - |
|
||||
| routes | router 的路由栈信息 | Array | | - |
|
||||
| params | 路由的参数 | Object | | - |
|
||||
| separator | 分隔符自定义 | String or Element | | '/' |
|
||||
|
||||
### Breadcrumb.Item
|
||||
|
||||
|
||||
@@ -17,8 +17,9 @@ ReactDOM.render(<div>
|
||||
<Button type="primary">主按钮</Button>
|
||||
<Button>次按钮</Button>
|
||||
<Button type="ghost">幽灵按钮</Button>
|
||||
<Button type="dashed">虚线按钮</Button>
|
||||
</div>,
|
||||
document.getElementById('components-button-demo-basic'));
|
||||
mountNode);
|
||||
````
|
||||
|
||||
<style>
|
||||
|
||||
@@ -79,7 +79,7 @@ ReactDOM.render(<div>
|
||||
<Button type="ghost">小</Button>
|
||||
</ButtonGroup>
|
||||
</div>
|
||||
, document.getElementById('components-button-demo-button-group'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
<style>
|
||||
|
||||
@@ -18,8 +18,11 @@ ReactDOM.render(<div>
|
||||
<br />
|
||||
<Button type="ghost">幽灵按钮</Button>
|
||||
<Button type="ghost" disabled>幽灵按钮(失效)</Button>
|
||||
<br />
|
||||
<Button type="dashed">虚线按钮</Button>
|
||||
<Button type="dashed" disabled>虚线按钮(失效)</Button>
|
||||
</div>
|
||||
, document.getElementById('components-button-demo-disabled'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
<style>
|
||||
|
||||
@@ -46,7 +46,7 @@ ReactDOM.render(<div>
|
||||
<Icon type="search" />
|
||||
</Button>
|
||||
</div>,
|
||||
document.getElementById('components-button-demo-icon'));
|
||||
mountNode);
|
||||
````
|
||||
|
||||
<style>
|
||||
|
||||
@@ -2,23 +2,25 @@
|
||||
|
||||
- order: 4
|
||||
|
||||
添加 `loading` 属性即可让按钮处于加载状态,最后一个按钮演示点击后进入加载状态。
|
||||
添加 `loading` 属性即可让按钮处于加载状态,最后两个按钮演示点击后进入加载状态。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Button } from 'antd';
|
||||
import { Button, Icon } from 'antd';
|
||||
|
||||
const App = React.createClass({
|
||||
getInitialState() {
|
||||
return {
|
||||
loading: false
|
||||
loading: false,
|
||||
iconLoading: false,
|
||||
};
|
||||
},
|
||||
enterLoading() {
|
||||
this.setState({
|
||||
loading: true
|
||||
});
|
||||
this.setState({ loading: true });
|
||||
},
|
||||
enterIconLoading() {
|
||||
this.setState({ iconLoading: true });
|
||||
},
|
||||
render() {
|
||||
return <div>
|
||||
@@ -35,11 +37,14 @@ const App = React.createClass({
|
||||
<Button type="primary" loading={this.state.loading} onClick={this.enterLoading}>
|
||||
点击变加载
|
||||
</Button>
|
||||
<Button type="primary" loading={this.state.iconLoading} onClick={this.enterIconLoading}>
|
||||
<Icon type="poweroff" />点击变加载
|
||||
</Button>
|
||||
</div>;
|
||||
}
|
||||
});
|
||||
|
||||
ReactDOM.render(<App />, document.getElementById('components-button-demo-loading'));
|
||||
ReactDOM.render(<App />, mountNode);
|
||||
````
|
||||
|
||||
<style>
|
||||
|
||||
@@ -30,7 +30,7 @@ ReactDOM.render(<div>
|
||||
<Icon type="search" />
|
||||
</Button>
|
||||
</div>
|
||||
, document.getElementById('components-button-demo-shape'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
<style>
|
||||
|
||||
@@ -16,7 +16,7 @@ ReactDOM.render(<div>
|
||||
<Button type="primary">中号按钮(默认)</Button>
|
||||
<Button type="primary" size="small">小号按钮</Button>
|
||||
</div>
|
||||
, document.getElementById('components-button-demo-size'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
<style>
|
||||
|
||||
@@ -15,5 +15,5 @@ function onPanelChange(value, mode) {
|
||||
|
||||
ReactDOM.render(
|
||||
<Calendar onPanelChange={onPanelChange} />
|
||||
, document.getElementById('components-calendar-demo-basic'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
@@ -17,5 +17,5 @@ ReactDOM.render(
|
||||
<div style={{ width: 290, border: '1px solid #d9d9d9', borderRadius: 4 }}>
|
||||
<Calendar fullscreen={false} onPanelChange={onPanelChange} />
|
||||
</div>
|
||||
, document.getElementById('components-calendar-demo-card'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
@@ -10,15 +10,15 @@
|
||||
import { Calendar } from 'antd';
|
||||
|
||||
function dateCellRender(value) {
|
||||
return <div>自定义日数据</div>;
|
||||
return <div>自定义日数据 {value.getDayOfMonth()}</div>;
|
||||
}
|
||||
|
||||
function monthCellRender(value) {
|
||||
return <div>自定义月数据</div>;
|
||||
return <div>自定义月数据 {value.getMonth()}</div>;
|
||||
}
|
||||
|
||||
ReactDOM.render(
|
||||
<Calendar defaultValue={new Date('2010-10-10')}
|
||||
dateCellRender={dateCellRender} monthCellRender={monthCellRender} />
|
||||
, document.getElementById('components-calendar-demo-custom-render'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
@@ -16,5 +16,5 @@ function onPanelChange(value, mode) {
|
||||
|
||||
ReactDOM.render(
|
||||
<Calendar onPanelChange={onPanelChange} locale={enUS}/>
|
||||
, document.getElementById('components-calendar-demo-locale'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
@@ -66,7 +66,7 @@ function monthCellRender(value) {
|
||||
|
||||
ReactDOM.render(
|
||||
<Calendar dateCellRender={dateCellRender} monthCellRender={monthCellRender} />
|
||||
, document.getElementById('components-calendar-demo-notice-calendar'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
|
||||
|
||||
@@ -68,14 +68,6 @@ class Calendar extends Component {
|
||||
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;
|
||||
@@ -99,11 +91,11 @@ class Calendar extends Component {
|
||||
onValueChange={this.setValue.bind(this)}/>
|
||||
<FullCalendar
|
||||
{...props}
|
||||
Select={noop}
|
||||
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)} />
|
||||
|
||||
@@ -1 +1 @@
|
||||
module.exports = require('../../datepicker/locale/en_US');
|
||||
module.exports = require('../../date-picker/locale/en_US');
|
||||
|
||||
@@ -1 +1 @@
|
||||
module.exports = require('../../datepicker/locale/zh_CN');
|
||||
module.exports = require('../../date-picker/locale/zh_CN');
|
||||
|
||||
@@ -16,6 +16,6 @@ ReactDOM.render(
|
||||
<div><h3>3</h3></div>
|
||||
<div><h3>4</h3></div>
|
||||
</Carousel>
|
||||
, document.getElementById('components-carousel-demo-autoplay'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
|
||||
@@ -20,5 +20,5 @@ ReactDOM.render(
|
||||
<div><h3>3</h3></div>
|
||||
<div><h3>4</h3></div>
|
||||
</Carousel>
|
||||
, document.getElementById('components-carousel-demo-basic'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
@@ -16,6 +16,6 @@ ReactDOM.render(
|
||||
<div><h3>3</h3></div>
|
||||
<div><h3>4</h3></div>
|
||||
</Carousel>
|
||||
, document.getElementById('components-carousel-demo-fade'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
|
||||
@@ -16,5 +16,5 @@ ReactDOM.render(
|
||||
<div><h3>3</h3></div>
|
||||
<div><h3>4</h3></div>
|
||||
</Carousel>
|
||||
, document.getElementById('components-carousel-demo-vertical'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
58
components/checkbox/Group.jsx
Normal file
58
components/checkbox/Group.jsx
Normal file
@@ -0,0 +1,58 @@
|
||||
import React from 'react';
|
||||
import Checkbox from './index';
|
||||
|
||||
export default React.createClass({
|
||||
getDefaultProps() {
|
||||
return {
|
||||
options: [],
|
||||
onChange() {},
|
||||
};
|
||||
},
|
||||
propTypes: {
|
||||
defaultValue: React.PropTypes.array,
|
||||
value: React.PropTypes.array,
|
||||
options: React.PropTypes.array.isRequired,
|
||||
onChange: React.PropTypes.func,
|
||||
},
|
||||
getInitialState() {
|
||||
const { value, defaultValue } = this.props;
|
||||
return {
|
||||
value: value || defaultValue || [],
|
||||
};
|
||||
},
|
||||
componentWillReceiveProps(nextProps) {
|
||||
if ('value' in nextProps) {
|
||||
this.setState({
|
||||
value: nextProps.value,
|
||||
});
|
||||
}
|
||||
},
|
||||
toggleOption(option) {
|
||||
const optionIndex = this.state.value.indexOf(option);
|
||||
const value = this.state.value;
|
||||
if (optionIndex === - 1) {
|
||||
value.push(option);
|
||||
} else {
|
||||
value.splice(optionIndex, 1);
|
||||
}
|
||||
if (!('value' in this.props)) {
|
||||
this.setState({ value });
|
||||
}
|
||||
this.props.onChange(value);
|
||||
},
|
||||
render() {
|
||||
const options = this.props.options;
|
||||
return <div className="ant-checkbox-group">
|
||||
{
|
||||
options.map(option =>
|
||||
<label className="ant-checkbox-group-item" key={option}>
|
||||
<Checkbox disabled={this.props.disabled}
|
||||
checked={this.state.value.indexOf(option) !== -1}
|
||||
onChange={this.toggleOption.bind(this, option)} />
|
||||
{option}
|
||||
</label>
|
||||
)
|
||||
}
|
||||
</div>;
|
||||
},
|
||||
});
|
||||
@@ -8,7 +8,6 @@
|
||||
|
||||
````jsx
|
||||
import { Checkbox } from 'antd';
|
||||
const container = document.getElementById('components-checkbox-demo-basic');
|
||||
|
||||
function onChange(e) {
|
||||
console.log('checked = ' + e.target.checked);
|
||||
@@ -17,5 +16,5 @@ function onChange(e) {
|
||||
ReactDOM.render(<label>
|
||||
<Checkbox defaultChecked={false} onChange={onChange} />
|
||||
Checkbox
|
||||
</label>, container);
|
||||
</label>, mountNode);
|
||||
````
|
||||
|
||||
@@ -8,7 +8,6 @@
|
||||
|
||||
````jsx
|
||||
import { Checkbox, Button } from 'antd';
|
||||
const container = document.getElementById('components-checkbox-demo-controller');
|
||||
|
||||
const App = React.createClass({
|
||||
getInitialState() {
|
||||
@@ -42,19 +41,19 @@ const App = React.createClass({
|
||||
</p>
|
||||
</div>;
|
||||
},
|
||||
toggleChecked(e) {
|
||||
toggleChecked() {
|
||||
this.setState({checked: !this.state.checked});
|
||||
},
|
||||
toggleDisable(e) {
|
||||
toggleDisable() {
|
||||
this.setState({disabled: !this.state.disabled});
|
||||
},
|
||||
onChange(e) {
|
||||
console.log('checked = ', e.target.checked);
|
||||
this.setState({
|
||||
checked: e.target.checked
|
||||
checked: e.target.checked,
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
ReactDOM.render(<App />, container);
|
||||
ReactDOM.render(<App />, mountNode);
|
||||
````
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
不可用
|
||||
# 不可用
|
||||
|
||||
- order: 1
|
||||
|
||||
@@ -8,11 +8,10 @@ checkbox 不可用。
|
||||
|
||||
````jsx
|
||||
import { Checkbox } from 'antd';
|
||||
const container = document.getElementById('components-checkbox-demo-disable');
|
||||
|
||||
ReactDOM.render(<div>
|
||||
<Checkbox defaultChecked={false} disabled />
|
||||
<br />
|
||||
<Checkbox defaultChecked disabled />
|
||||
</div>, container);
|
||||
</div>, mountNode);
|
||||
````
|
||||
|
||||
20
components/checkbox/demo/group.md
Normal file
20
components/checkbox/demo/group.md
Normal file
@@ -0,0 +1,20 @@
|
||||
# Checkbox 组
|
||||
|
||||
- order: 3
|
||||
|
||||
方便的生成一个 Checkbox 组。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Checkbox } from 'antd';
|
||||
const CheckboxGroup = Checkbox.Group;
|
||||
|
||||
function onChange(checkedValues) {
|
||||
console.log('checked = ', checkedValues);
|
||||
}
|
||||
|
||||
ReactDOM.render(
|
||||
<CheckboxGroup options={['Apple', 'Pear', 'Orange']} defaultValue={['Apple']} onChange={onChange} />
|
||||
, mountNode);
|
||||
````
|
||||
@@ -1,13 +1,18 @@
|
||||
import Checkbox from 'rc-checkbox';
|
||||
import RcCheckbox from 'rc-checkbox';
|
||||
import React from 'react';
|
||||
import Group from './Group';
|
||||
|
||||
export default React.createClass({
|
||||
const Checkbox = React.createClass({
|
||||
getDefaultProps() {
|
||||
return {
|
||||
prefixCls: 'ant-checkbox'
|
||||
};
|
||||
},
|
||||
render() {
|
||||
return <Checkbox {...this.props} />;
|
||||
return <RcCheckbox {...this.props} />;
|
||||
}
|
||||
});
|
||||
|
||||
Checkbox.Group = Group;
|
||||
|
||||
export default Checkbox;
|
||||
|
||||
@@ -10,8 +10,8 @@
|
||||
|
||||
## 何时使用
|
||||
|
||||
- 需要表示开关状态/两种状态之间的切换时;
|
||||
- 和 `switch`的区别是,切换 `switch` 会直接触发状态改变,而 `checkbox` 一般用于状态标记,需要和提交操作配合。
|
||||
- 在一组可选项中进行多项选择时;
|
||||
- 单独使用可以表示两种状态之间的切换,和 `switch` 类似。区别在于切换 `switch` 会直接触发状态改变,而 `checkbox` 一般用于状态标记,需要和提交操作配合。
|
||||
|
||||
## API
|
||||
|
||||
@@ -19,6 +19,15 @@
|
||||
|
||||
| 参数 | 说明 | 类型 | 可选值 |默认值 |
|
||||
|-----------|------------------------------------------|------------|-------|--------|
|
||||
| checked | 指定当前是否选中 | boolean | | false |
|
||||
| defaultChecked | 初始是否选中 | boolean | | false |
|
||||
| onChange | 变化时回调函数 | Function(e:Event) | | | |
|
||||
| checked | 指定当前是否选中 | boolean | | false |
|
||||
| defaultChecked | 初始是否选中 | boolean | | false |
|
||||
| onChange | 变化时回调函数 | Function(e:Event) | | | |
|
||||
|
||||
### Checkbox Group
|
||||
|
||||
| 参数 | 说明 | 类型 | 可选值 | 默认值 |
|
||||
|-----------|------------------------------------------|------------|---------|--------|
|
||||
| defaultValue | 默认选中的选项 | array | | [] |
|
||||
| value | 指定选中的选项| array | | [] |
|
||||
| options | 指定可选项 | array | | [] |
|
||||
| onChange | 变化时回调函数 | Function(checkedValue) | | | |
|
||||
|
||||
@@ -28,5 +28,5 @@ ReactDOM.render(
|
||||
<p>{text}</p>
|
||||
</Panel>
|
||||
</Collapse>
|
||||
, document.getElementById('components-collapse-demo-accordion'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
@@ -32,5 +32,5 @@ ReactDOM.render(
|
||||
<p>{text}</p>
|
||||
</Panel>
|
||||
</Collapse>
|
||||
, document.getElementById('components-collapse-demo-basic'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
@@ -36,5 +36,5 @@ ReactDOM.render(
|
||||
<p>{text}</p>
|
||||
</Panel>
|
||||
</Collapse>
|
||||
, document.getElementById('components-collapse-demo-mix'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
47
components/date-picker/PickerMixin.jsx
Normal file
47
components/date-picker/PickerMixin.jsx
Normal file
@@ -0,0 +1,47 @@
|
||||
import objectAssign from 'object-assign';
|
||||
import defaultLocale from './locale/zh_CN';
|
||||
import DateTimeFormat from 'gregorian-calendar-format';
|
||||
import GregorianCalendar from 'gregorian-calendar';
|
||||
|
||||
export default {
|
||||
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() {
|
||||
},
|
||||
toggleOpen(e) {
|
||||
this.setState({
|
||||
open: e.open
|
||||
});
|
||||
},
|
||||
};
|
||||
136
components/date-picker/RangePicker.jsx
Normal file
136
components/date-picker/RangePicker.jsx
Normal file
@@ -0,0 +1,136 @@
|
||||
import React from 'react';
|
||||
import GregorianCalendar from 'gregorian-calendar';
|
||||
import RangeCalendar from 'rc-calendar/lib/RangeCalendar';
|
||||
import DatePicker from 'rc-calendar/lib/Picker';
|
||||
import TimePicker from 'rc-time-picker';
|
||||
import classNames from 'classnames';
|
||||
import PickerMixin from './PickerMixin';
|
||||
|
||||
export default React.createClass({
|
||||
getDefaultProps() {
|
||||
return {
|
||||
defaultValue: [],
|
||||
format: 'yyyy-MM-dd',
|
||||
startPlaceholder: '开始日期',
|
||||
endPlaceholder: '结束日期',
|
||||
transitionName: 'slide-up',
|
||||
popupStyle: {},
|
||||
onChange() {
|
||||
}, // onChange 可用于 Validator
|
||||
locale: {},
|
||||
align: {
|
||||
offset: [0, -9],
|
||||
},
|
||||
open: false
|
||||
};
|
||||
},
|
||||
getInitialState() {
|
||||
const {value, defaultValue} = this.props;
|
||||
const start = (value && value[0]) || defaultValue[0];
|
||||
const end = (value && value[1]) || defaultValue[1];
|
||||
return {
|
||||
value: [
|
||||
this.parseDateFromValue(start),
|
||||
this.parseDateFromValue(end)
|
||||
]
|
||||
};
|
||||
},
|
||||
mixins: [ PickerMixin ],
|
||||
componentWillReceiveProps(nextProps) {
|
||||
if ('value' in nextProps) {
|
||||
const start = this.parseDateFromValue(nextProps.value[0]);
|
||||
const end = this.parseDateFromValue(nextProps.value[1]);
|
||||
this.setState({
|
||||
value: [start, end]
|
||||
});
|
||||
}
|
||||
},
|
||||
handleChange(value) {
|
||||
if (!('value' in this.props)) {
|
||||
this.setState({ value });
|
||||
}
|
||||
const startTime = value[0] ? new Date(value[0].getTime()) : null;
|
||||
const endTime = value[1] ? new Date(value[1].getTime()) : null;
|
||||
this.props.onChange([startTime, endTime]);
|
||||
},
|
||||
render() {
|
||||
const locale = this.getLocale();
|
||||
// 以下两行代码
|
||||
// 给没有初始值的日期选择框提供本地化信息
|
||||
// 否则会以周日开始排
|
||||
let defaultCalendarValue = new GregorianCalendar(locale);
|
||||
defaultCalendarValue.setTime(Date.now());
|
||||
|
||||
const {disabledDate, showTime, size, startPlaceholder, endPlaceholder,
|
||||
transitionName, disabled, popupStyle, align, style} = this.props;
|
||||
const state = this.state;
|
||||
|
||||
const timePicker = showTime
|
||||
? <TimePicker prefixCls="ant-time-picker"
|
||||
placeholder={locale.lang.timePlaceholder}
|
||||
transitionName="slide-up" />
|
||||
: null;
|
||||
|
||||
const calendarClassName = classNames({
|
||||
['ant-calendar-time']: this.props.showTime,
|
||||
});
|
||||
|
||||
const calendar = <RangeCalendar prefixCls="ant-calendar"
|
||||
className={calendarClassName}
|
||||
timePicker={timePicker}
|
||||
disabledDate={disabledDate}
|
||||
dateInputPlaceholder={[startPlaceholder, endPlaceholder]}
|
||||
locale={locale.lang}
|
||||
defaultValue={defaultCalendarValue}
|
||||
showClear />;
|
||||
|
||||
const pickerClass = classNames({
|
||||
'ant-calendar-picker': true,
|
||||
'ant-calendar-picker-open': state.open
|
||||
});
|
||||
|
||||
const pickerInputClass = classNames({
|
||||
'ant-calendar-range-picker': true,
|
||||
'ant-input': true,
|
||||
'ant-input-lg': size === 'large',
|
||||
'ant-input-sm': size === 'small',
|
||||
});
|
||||
|
||||
return (<span className={pickerClass} style={style}>
|
||||
<DatePicker
|
||||
transitionName={transitionName}
|
||||
disabled={disabled}
|
||||
calendar={calendar}
|
||||
value={state.value}
|
||||
prefixCls="ant-calendar-picker-container"
|
||||
style={popupStyle}
|
||||
align={align}
|
||||
onOpen={this.toggleOpen}
|
||||
onClose={this.toggleOpen}
|
||||
onChange={this.handleChange}>
|
||||
{
|
||||
({value}) => {
|
||||
const start = value[0];
|
||||
const end = value[1];
|
||||
return (
|
||||
<span className={pickerInputClass} disabled={disabled}>
|
||||
<input disabled={disabled}
|
||||
onChange={this.handleInputChange}
|
||||
value={start && this.getFormatter().format(start)}
|
||||
placeholder={startPlaceholder}
|
||||
className="ant-calendar-range-picker-input" />
|
||||
<span className="ant-calendar-range-picker-separator"> ~ </span>
|
||||
<input disabled={disabled}
|
||||
onChange={this.handleInputChange}
|
||||
value={end && this.getFormatter().format(end)}
|
||||
placeholder={endPlaceholder}
|
||||
className="ant-calendar-range-picker-input" />
|
||||
<span className="ant-calendar-picker-icon" />
|
||||
</span>
|
||||
);
|
||||
}
|
||||
}
|
||||
</DatePicker>
|
||||
</span>);
|
||||
}
|
||||
});
|
||||
17
components/date-picker/demo/basic.md
Normal file
17
components/date-picker/demo/basic.md
Normal file
@@ -0,0 +1,17 @@
|
||||
# 基本
|
||||
|
||||
- order: 0
|
||||
|
||||
最简单的用法。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { DatePicker } from 'antd';
|
||||
|
||||
function onChange(value) {
|
||||
console.log(value);
|
||||
}
|
||||
|
||||
ReactDOM.render(<DatePicker onChange={onChange} />, mountNode);
|
||||
````
|
||||
@@ -9,14 +9,14 @@
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Datepicker } from 'antd';
|
||||
import { DatePicker } from 'antd';
|
||||
|
||||
const disabledDate = function(current, value) {
|
||||
const disabledDate = function(current) {
|
||||
// can not select days after today
|
||||
return current && current.getTime() > Date.now();
|
||||
};
|
||||
|
||||
ReactDOM.render(
|
||||
<Datepicker disabledDate={disabledDate} />
|
||||
, document.getElementById('components-datepicker-demo-range'));
|
||||
<DatePicker disabledDate={disabledDate} />
|
||||
, mountNode);
|
||||
````
|
||||
15
components/date-picker/demo/disabled.md
Normal file
15
components/date-picker/demo/disabled.md
Normal file
@@ -0,0 +1,15 @@
|
||||
# 禁用
|
||||
|
||||
- order: 5
|
||||
|
||||
选择框的不可用状态。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { DatePicker } from 'antd';
|
||||
|
||||
ReactDOM.render(
|
||||
<DatePicker defaultValue="2015-06-06" disabled />
|
||||
, mountNode);
|
||||
````
|
||||
15
components/date-picker/demo/formatter.md
Normal file
15
components/date-picker/demo/formatter.md
Normal file
@@ -0,0 +1,15 @@
|
||||
# 日期格式
|
||||
|
||||
- order: 1
|
||||
|
||||
使用 `format` 属性,可以自定义你需要的日期显示格式,如 `yyyy/MM/dd`。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { DatePicker } from 'antd';
|
||||
|
||||
ReactDOM.render(
|
||||
<DatePicker defaultValue="2015/01/01" format="yyyy/MM/dd" />
|
||||
, mountNode);
|
||||
````
|
||||
@@ -1,14 +1,14 @@
|
||||
# 国际化
|
||||
|
||||
- order: 9
|
||||
- order: 10
|
||||
|
||||
通过 `locale` 配置时区、语言等, 默认支持 en_US, zh_CN
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Datepicker } from 'antd';
|
||||
import enUS from 'antd/lib/datepicker/locale/en_US';
|
||||
import { DatePicker } from 'antd';
|
||||
import enUS from 'antd/lib/date-picker/locale/en_US';
|
||||
import assign from 'object-assign';
|
||||
|
||||
const App = React.createClass({
|
||||
@@ -17,15 +17,15 @@ const App = React.createClass({
|
||||
locale: assign({}, enUS, {
|
||||
timezoneOffset: 0 * 60,
|
||||
firstDayOfWeek: 0,
|
||||
minimalDaysInFirstWeek: 1
|
||||
minimalDaysInFirstWeek: 1,
|
||||
})
|
||||
};
|
||||
},
|
||||
render() {
|
||||
return <Datepicker locale={this.state.locale} />;
|
||||
return <DatePicker locale={this.state.locale} />;
|
||||
}
|
||||
});
|
||||
|
||||
ReactDOM.render(<App />, document.getElementById('components-datepicker-demo-locale'));
|
||||
ReactDOM.render(<App />, mountNode);
|
||||
````
|
||||
|
||||
15
components/date-picker/demo/month-picker.md
Normal file
15
components/date-picker/demo/month-picker.md
Normal file
@@ -0,0 +1,15 @@
|
||||
# 月选择器
|
||||
|
||||
- order: 9
|
||||
|
||||
使用 `MonthPicker` 实现月选择器.
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { DatePicker } from 'antd';
|
||||
const MonthPicker = DatePicker.MonthPicker;
|
||||
ReactDOM.render(
|
||||
<MonthPicker defaultValue="2015-12" />
|
||||
, mountNode);
|
||||
````
|
||||
21
components/date-picker/demo/range.md
Normal file
21
components/date-picker/demo/range.md
Normal file
@@ -0,0 +1,21 @@
|
||||
# 日期范围二
|
||||
|
||||
- order: 8
|
||||
|
||||
使用 `RangePicker` 实现日期范围选择有更好的交互体验。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { DatePicker } from 'antd';
|
||||
const RangePicker = DatePicker.RangePicker;
|
||||
|
||||
function onChange(value) {
|
||||
console.log('From: ', value[0], ', to: ', value[1]);
|
||||
}
|
||||
ReactDOM.render(<div>
|
||||
<RangePicker style={{width: 184}} onChange={onChange} />
|
||||
<br />
|
||||
<RangePicker showTime format="yyyy-MM-dd HH:mm:ss" onChange={onChange} />
|
||||
</div>, mountNode);
|
||||
````
|
||||
19
components/date-picker/demo/size.md
Normal file
19
components/date-picker/demo/size.md
Normal file
@@ -0,0 +1,19 @@
|
||||
# 三种大小
|
||||
|
||||
- order: 1
|
||||
|
||||
三种大小的输入框,大的用在表单中,中的为默认。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { DatePicker } from 'antd';
|
||||
|
||||
ReactDOM.render(
|
||||
<div>
|
||||
<DatePicker size="large" />
|
||||
<DatePicker />
|
||||
<DatePicker size="small" />
|
||||
</div>
|
||||
, mountNode);
|
||||
````
|
||||
@@ -1,13 +1,13 @@
|
||||
# 日期范围选择
|
||||
# 日期范围一
|
||||
|
||||
- order: 7
|
||||
|
||||
设置 `disabledDate` 方法,来约束开始和结束日期。
|
||||
可以设置 `disabledDate` 方法,来约束开始和结束日期。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Datepicker } from 'antd';
|
||||
import { DatePicker } from 'antd';
|
||||
|
||||
const DateRange = React.createClass({
|
||||
getInitialState() {
|
||||
@@ -36,11 +36,11 @@ const DateRange = React.createClass({
|
||||
},
|
||||
render() {
|
||||
return <div>
|
||||
<Datepicker disabledDate={this.disabledStartDate}
|
||||
<DatePicker disabledDate={this.disabledStartDate}
|
||||
value={this.state.startValue}
|
||||
placeholder="开始日期"
|
||||
onChange={this.onChange.bind(this, 'startValue')} />
|
||||
<Datepicker disabledDate={this.disabledEndDate}
|
||||
<DatePicker disabledDate={this.disabledEndDate}
|
||||
value={this.state.endValue}
|
||||
placeholder="结束日期"
|
||||
onChange={this.onChange.bind(this, 'endValue')} />
|
||||
@@ -50,5 +50,5 @@ const DateRange = React.createClass({
|
||||
|
||||
ReactDOM.render(
|
||||
<DateRange />
|
||||
, document.getElementById('components-datepicker-demo-start-end'));
|
||||
, mountNode);
|
||||
````
|
||||
19
components/date-picker/demo/time.md
Normal file
19
components/date-picker/demo/time.md
Normal file
@@ -0,0 +1,19 @@
|
||||
# 日期时间选择
|
||||
|
||||
- order: 4
|
||||
|
||||
增加选择时间功能。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { DatePicker } from 'antd';
|
||||
|
||||
function onChange(value) {
|
||||
console.log('选择了时间:', value);
|
||||
}
|
||||
|
||||
ReactDOM.render(
|
||||
<DatePicker showTime format="yyyy-MM-dd HH:mm:ss" onChange={onChange} style={{width: 160}} />
|
||||
, mountNode);
|
||||
````
|
||||
53
components/date-picker/demo/with-time-picker.md
Normal file
53
components/date-picker/demo/with-time-picker.md
Normal file
@@ -0,0 +1,53 @@
|
||||
# 日期时间选择二
|
||||
|
||||
- order: 4
|
||||
- hidden: true
|
||||
|
||||
和 [时间选择框](/components/timepicer) 配合使用。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { DatePicker, TimePicker } from 'antd';
|
||||
|
||||
const DateTimePicker = React.createClass({
|
||||
handleChange(from, value) {
|
||||
this.result = this.result || new Date();
|
||||
if (!value) {
|
||||
if (from === 'date') {
|
||||
this.selectedDate = false;
|
||||
} else {
|
||||
this.selectedTime = false;
|
||||
}
|
||||
return;
|
||||
}
|
||||
if (from === 'date') {
|
||||
this.result.setFullYear(value.getFullYear());
|
||||
this.result.setMonth(value.getMonth());
|
||||
this.result.setDate(value.getDate());
|
||||
this.selectedDate = true;
|
||||
} else {
|
||||
this.result.setHours(value.getHours());
|
||||
this.result.setMinutes(value.getMinutes());
|
||||
this.result.setSeconds(value.getSeconds());
|
||||
this.selectedTime = true;
|
||||
}
|
||||
if (this.selectedDate && this.selectedTime) {
|
||||
this.props.onSelect(this.result);
|
||||
}
|
||||
},
|
||||
render() {
|
||||
return <div>
|
||||
<DatePicker onChange={this.handleChange.bind(null, 'date')} />
|
||||
<TimePicker onChange={this.handleChange.bind(null, 'time')} />
|
||||
</div>;
|
||||
}
|
||||
});
|
||||
|
||||
function onSelect(value) {
|
||||
console.log('选择了时间:', value);
|
||||
}
|
||||
|
||||
ReactDOM.render(<DateTimePicker onSelect={onSelect} />
|
||||
, mountNode);
|
||||
````
|
||||
@@ -1,21 +1,21 @@
|
||||
import React from 'react';
|
||||
import Calendar from 'rc-calendar';
|
||||
import MonthCalendar from 'rc-calendar/lib/MonthCalendar';
|
||||
import Datepicker from 'rc-calendar/lib/Picker';
|
||||
import DatePicker from 'rc-calendar/lib/Picker';
|
||||
import GregorianCalendar from 'gregorian-calendar';
|
||||
import defaultLocale from './locale/zh_CN';
|
||||
import CalendarLocale from 'rc-calendar/lib/locale/zh_CN';
|
||||
import DateTimeFormat from 'gregorian-calendar-format';
|
||||
import objectAssign from 'object-assign';
|
||||
import AntRangePicker from './RangePicker';
|
||||
import PickerMixin from './PickerMixin';
|
||||
import TimePicker from 'rc-time-picker';
|
||||
import classNames from 'classnames';
|
||||
|
||||
function createPicker(TheCalendar) {
|
||||
function createPicker(TheCalendar, defaultFormat) {
|
||||
return React.createClass({
|
||||
getDefaultProps() {
|
||||
return {
|
||||
format: 'yyyy-MM-dd',
|
||||
format: defaultFormat || 'yyyy-MM-dd',
|
||||
transitionName: 'slide-up',
|
||||
popupStyle: {},
|
||||
onSelect: null, // 向前兼容
|
||||
onChange() {
|
||||
}, // onChange 可用于 Validator
|
||||
locale: {},
|
||||
@@ -30,6 +30,7 @@ function createPicker(TheCalendar) {
|
||||
value: this.parseDateFromValue(this.props.value || this.props.defaultValue)
|
||||
};
|
||||
},
|
||||
mixins: [ PickerMixin ],
|
||||
componentWillReceiveProps(nextProps) {
|
||||
if ('value' in nextProps) {
|
||||
this.setState({
|
||||
@@ -37,53 +38,11 @@ function createPicker(TheCalendar) {
|
||||
});
|
||||
}
|
||||
},
|
||||
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() {
|
||||
},
|
||||
toggleOpen(e) {
|
||||
this.setState({
|
||||
open: e.open
|
||||
});
|
||||
},
|
||||
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);
|
||||
if (!('value' in this.props)) {
|
||||
this.setState({ value });
|
||||
}
|
||||
const timeValue = value ? new Date(value.getTime()) : null;
|
||||
this.props.onChange(timeValue);
|
||||
},
|
||||
render() {
|
||||
@@ -96,14 +55,27 @@ function createPicker(TheCalendar) {
|
||||
|
||||
const placeholder = ('placeholder' in this.props)
|
||||
? this.props.placeholder : locale.lang.placeholder;
|
||||
|
||||
const timePicker = this.props.showTime
|
||||
? <TimePicker prefixCls="ant-time-picker"
|
||||
placeholder={locale.lang.timePlaceholder}
|
||||
transitionName="slide-up" />
|
||||
: null;
|
||||
|
||||
const calendarClassName = classNames({
|
||||
['ant-calendar-time']: this.props.showTime,
|
||||
['ant-calendar-month']: MonthCalendar === TheCalendar,
|
||||
});
|
||||
|
||||
const calendar = (
|
||||
<TheCalendar
|
||||
disabledDate={this.props.disabledDate}
|
||||
locale={locale.lang}
|
||||
timePicker={timePicker}
|
||||
defaultValue={defaultCalendarValue}
|
||||
dateInputPlaceholder={placeholder}
|
||||
showTime={this.props.showTime}
|
||||
prefixCls="ant-calendar"
|
||||
className={calendarClassName}
|
||||
showOk={this.props.showTime}
|
||||
showClear />
|
||||
);
|
||||
@@ -121,7 +93,7 @@ function createPicker(TheCalendar) {
|
||||
}
|
||||
|
||||
return <span className={pickerClass}>
|
||||
<Datepicker
|
||||
<DatePicker
|
||||
transitionName={this.props.transitionName}
|
||||
disabled={this.props.disabled}
|
||||
calendar={calendar}
|
||||
@@ -135,7 +107,7 @@ function createPicker(TheCalendar) {
|
||||
{
|
||||
({value}) => {
|
||||
return (
|
||||
<span>
|
||||
<span>
|
||||
<input disabled={this.props.disabled}
|
||||
onChange={this.handleInputChange}
|
||||
value={value && this.getFormatter().format(value)}
|
||||
@@ -144,17 +116,17 @@ function createPicker(TheCalendar) {
|
||||
className={'ant-calendar-picker-input ant-input' + sizeClass}/>
|
||||
<span className="ant-calendar-picker-icon"/>
|
||||
</span>
|
||||
);
|
||||
);
|
||||
}
|
||||
}
|
||||
</Datepicker>
|
||||
</DatePicker>
|
||||
</span>;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
const AntDatePicker = createPicker(Calendar);
|
||||
const AntMonthPicker = createPicker(MonthCalendar);
|
||||
const AntMonthPicker = createPicker(MonthCalendar, 'yyyy-MM');
|
||||
|
||||
const AntCalendar = React.createClass({
|
||||
getDefaultProps() {
|
||||
@@ -169,6 +141,7 @@ const AntCalendar = React.createClass({
|
||||
});
|
||||
|
||||
AntDatePicker.Calendar = AntCalendar;
|
||||
AntDatePicker.RangePicker = AntRangePicker;
|
||||
AntDatePicker.MonthPicker = AntMonthPicker;
|
||||
|
||||
export default AntDatePicker;
|
||||
@@ -1,4 +1,4 @@
|
||||
# Datepicker
|
||||
# DatePicker
|
||||
|
||||
- category: Components
|
||||
- chinese: 日期选择框
|
||||
@@ -14,10 +14,15 @@
|
||||
|
||||
## API
|
||||
|
||||
### DatePicker
|
||||
|
||||
```html
|
||||
<Datepicker defaultValue="2015-01-01" />
|
||||
<DatePicker defaultValue="2015-01-01" />
|
||||
```
|
||||
|
||||
> 注意:`0.11+` 后 `Datepicker` 改名为 `DatePicker`。
|
||||
|
||||
|
||||
| 参数 | 说明 | 类型 | 默认值 |
|
||||
|--------------|----------------|----------|--------------|
|
||||
| value | 日期 | string | 无 |
|
||||
@@ -30,6 +35,19 @@
|
||||
| popupStyle | 格外的弹出日历样式 | object | {} |
|
||||
| size | 输入框大小,`large` 高度为 32px,`small` 为 22px,默认是 28px | string | 无 |
|
||||
| locale | 国际化配置 | object | [默认配置](https://github.com/ant-design/ant-design/issues/424) |
|
||||
| showTime | 增加时间选择功能 | bool | false |
|
||||
| onOk | 点击确定按钮的回调 | function | 无 |
|
||||
|
||||
### RangePicker
|
||||
|
||||
| 参数 | 说明 | 类型 | 默认值 |
|
||||
|--------------|----------------|----------|--------------|
|
||||
| value | 日期 | [string, string] | 无 |
|
||||
| defaultValue | 默认日期 | [string, string] | 无 |
|
||||
| format | 展示的日期格式 | string | "yyyy-MM-dd HH:mm:ss" |
|
||||
| onChange | 时间发生变化的回调,发生在用户选择时间时 | function([Date start, Date end]) | 无 |
|
||||
|
||||
`disabled` `style` `popupStyle` `size` `locale` `showTime` `onOk` 属性与 DatePicker 的一致。
|
||||
|
||||
<style>
|
||||
.code-box-demo .ant-calendar-picker {
|
||||
@@ -5,7 +5,8 @@ import CalendarLocale from 'rc-calendar/lib/locale/en_US';
|
||||
// 统一合并为完整的 Locale
|
||||
let locale = objectAssign({}, GregorianCalendarLocale);
|
||||
locale.lang = objectAssign({
|
||||
placeholder: 'Select a date'
|
||||
placeholder: 'Select date',
|
||||
timePlaceholder: 'Select time',
|
||||
}, CalendarLocale);
|
||||
|
||||
// All settings at:
|
||||
@@ -5,9 +5,13 @@ import CalendarLocale from 'rc-calendar/lib/locale/zh_CN';
|
||||
// 统一合并为完整的 Locale
|
||||
let locale = objectAssign({}, GregorianCalendarLocale);
|
||||
locale.lang = objectAssign({
|
||||
placeholder: '请选择日期'
|
||||
placeholder: '请选择日期',
|
||||
timePlaceholder: '请选择时间',
|
||||
}, CalendarLocale);
|
||||
|
||||
// should add whitespace between char in Button
|
||||
locale.lang.ok = '确 定';
|
||||
|
||||
// All settings at:
|
||||
// https://github.com/ant-design/ant-design/issues/424
|
||||
|
||||
@@ -1,15 +0,0 @@
|
||||
# 基本
|
||||
|
||||
- order: 0
|
||||
|
||||
最简单的用法。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Datepicker } from 'antd';
|
||||
|
||||
ReactDOM.render(
|
||||
<Datepicker defaultValue="2015-12-12" />
|
||||
, document.getElementById('components-datepicker-demo-basic'));
|
||||
````
|
||||
@@ -1,15 +0,0 @@
|
||||
# 禁用
|
||||
|
||||
- order: 5
|
||||
|
||||
选择框的不可用状态。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Datepicker } from 'antd';
|
||||
|
||||
ReactDOM.render(
|
||||
<Datepicker defaultValue="2015-06-06" disabled />
|
||||
, document.getElementById('components-datepicker-demo-disabled'));
|
||||
````
|
||||
@@ -1,15 +0,0 @@
|
||||
# 日期格式
|
||||
|
||||
- order: 1
|
||||
|
||||
使用 `format` 属性,可以自定义你需要的日期显示格式,如 `yyyy/MM/dd`。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Datepicker } from 'antd';
|
||||
|
||||
ReactDOM.render(
|
||||
<Datepicker defaultValue="2015/01/01" format="yyyy/MM/dd" />
|
||||
, document.getElementById('components-datepicker-demo-formatter'));
|
||||
````
|
||||
@@ -1,24 +0,0 @@
|
||||
# 选择日期
|
||||
|
||||
- order: 2
|
||||
|
||||
通过设置选择日期的回调事件 `onChange`,完成交互行为。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Datepicker } from 'antd';
|
||||
|
||||
const Picker = React.createClass({
|
||||
handleChange: function(value) {
|
||||
console.log(new Date(value.getTime()));
|
||||
},
|
||||
render: function() {
|
||||
return <Datepicker onChange={this.handleChange} />;
|
||||
}
|
||||
});
|
||||
|
||||
ReactDOM.render(
|
||||
<Picker />
|
||||
, document.getElementById('components-datepicker-demo-select'));
|
||||
````
|
||||
@@ -1,19 +0,0 @@
|
||||
# 三种大小
|
||||
|
||||
- order: 1
|
||||
|
||||
三种大小的输入框,大的用在表单中,中的为默认。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Datepicker } from 'antd';
|
||||
|
||||
ReactDOM.render(
|
||||
<div>
|
||||
<Datepicker size="large" />
|
||||
<Datepicker />
|
||||
<Datepicker size="small" />
|
||||
</div>
|
||||
, document.getElementById('components-datepicker-demo-size'));
|
||||
````
|
||||
@@ -1,43 +0,0 @@
|
||||
# 日期时间选择
|
||||
|
||||
- order: 4
|
||||
|
||||
和 [时间选择框](/components/timepicer) 配合使用。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Datepicker, Timepicker } from 'antd';
|
||||
|
||||
let result = new Date();
|
||||
let selectdDate, selectdTime;
|
||||
function handleChange(from, value) {
|
||||
if (!value) {
|
||||
if (from === 'date') {
|
||||
selectdDate = false;
|
||||
} else {
|
||||
selectdTime = false;
|
||||
}
|
||||
return;
|
||||
}
|
||||
if (from === 'date') {
|
||||
result.setFullYear(value.getFullYear());
|
||||
result.setMonth(value.getMonth());
|
||||
result.setDate(value.getDate());
|
||||
selectdDate = true;
|
||||
} else {
|
||||
result.setHours(value.getHours());
|
||||
result.setMinutes(value.getMinutes());
|
||||
result.setSeconds(value.getSeconds());
|
||||
selectdTime = true;
|
||||
}
|
||||
if (selectdDate && selectdTime) {
|
||||
console.log('选择结果是:' + result);
|
||||
}
|
||||
}
|
||||
|
||||
ReactDOM.render(<div>
|
||||
<Datepicker onChange={handleChange.bind(null, 'date')} />
|
||||
<Timepicker onChange={handleChange.bind(null, 'time')} />
|
||||
</div>, document.getElementById('components-datepicker-demo-time'));
|
||||
````
|
||||
@@ -7,7 +7,7 @@
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Menu, Dropdown, Button, Icon } from 'antd';
|
||||
import { Menu, Dropdown, Icon } from 'antd';
|
||||
|
||||
const menu = <Menu>
|
||||
<Menu.Item>
|
||||
@@ -23,15 +23,9 @@ const menu = <Menu>
|
||||
|
||||
ReactDOM.render(
|
||||
<Dropdown overlay={menu}>
|
||||
<Button>
|
||||
某按钮 <Icon type="down" />
|
||||
</Button>
|
||||
<a className="ant-dropdown-link" href="#">
|
||||
触发链接 <Icon type="down" />
|
||||
</a>
|
||||
</Dropdown>
|
||||
, document.getElementById('components-dropdown-demo-basic'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
<style>
|
||||
.code-box-demo .ant-btn {
|
||||
margin-right: 6px;
|
||||
}
|
||||
</style>
|
||||
|
||||
30
components/dropdown/demo/dropdown-button.md
Normal file
30
components/dropdown/demo/dropdown-button.md
Normal file
@@ -0,0 +1,30 @@
|
||||
# 带下拉框的按钮
|
||||
|
||||
- order: 4
|
||||
|
||||
左边是按钮,右边是额外的相关功能菜单。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Menu, Dropdown } from 'antd';
|
||||
const DropdownButton = Dropdown.Button;
|
||||
|
||||
const menu = <Menu>
|
||||
<Menu.Item>
|
||||
<a target="_blank" href="http://www.alipay.com/">第一个菜单项</a>
|
||||
</Menu.Item>
|
||||
<Menu.Item>
|
||||
<a target="_blank" href="http://www.taobao.com/">第二个菜单项</a>
|
||||
</Menu.Item>
|
||||
<Menu.Item>
|
||||
<a target="_blank" href="http://www.tmall.com/">第三个菜单项</a>
|
||||
</Menu.Item>
|
||||
</Menu>;
|
||||
|
||||
ReactDOM.render(
|
||||
<DropdownButton overlay={menu} type="primary">
|
||||
某功能按钮
|
||||
</DropdownButton>
|
||||
, mountNode);
|
||||
````
|
||||
@@ -7,7 +7,7 @@
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Menu, Dropdown, Button, Icon } from 'antd';
|
||||
import { Menu, Dropdown, Icon } from 'antd';
|
||||
const onClick = function({key}) {
|
||||
console.log('点击了菜单' + key);
|
||||
};
|
||||
@@ -20,9 +20,9 @@ const menu = <Menu onClick={onClick}>
|
||||
|
||||
ReactDOM.render(
|
||||
<Dropdown overlay={menu}>
|
||||
<Button>
|
||||
<a className="ant-dropdown-link" href="#">
|
||||
鼠标移入,点击菜单 <Icon type="down" />
|
||||
</Button>
|
||||
</a>
|
||||
</Dropdown>
|
||||
, document.getElementById('components-dropdown-demo-event'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Menu, Dropdown, Button, Icon } from 'antd';
|
||||
import { Menu, Dropdown, Icon } from 'antd';
|
||||
|
||||
const menu = <Menu>
|
||||
<Menu.Item key="0">
|
||||
@@ -22,9 +22,9 @@ const menu = <Menu>
|
||||
|
||||
ReactDOM.render(
|
||||
<Dropdown overlay={menu}>
|
||||
<Button>
|
||||
<a className="ant-dropdown-link" href="#">
|
||||
鼠标移入 <Icon type="down" />
|
||||
</Button>
|
||||
</a>
|
||||
</Dropdown>
|
||||
, document.getElementById('components-dropdown-demo-item'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
29
components/dropdown/demo/sub-menu.md
Normal file
29
components/dropdown/demo/sub-menu.md
Normal file
@@ -0,0 +1,29 @@
|
||||
# 多级菜单
|
||||
|
||||
- order: 5
|
||||
|
||||
传入的菜单里有多个层级。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Menu, Dropdown, Icon } from 'antd';
|
||||
const SubMenu = Menu.SubMenu;
|
||||
|
||||
const menu = <Menu>
|
||||
<Menu.Item>第一个菜单项</Menu.Item>
|
||||
<Menu.Item>第二个菜单项</Menu.Item>
|
||||
<SubMenu title="子菜单">
|
||||
<Menu.Item>第三个菜单项</Menu.Item>
|
||||
<Menu.Item>第四个菜单项</Menu.Item>
|
||||
</SubMenu>
|
||||
</Menu>;
|
||||
|
||||
ReactDOM.render(
|
||||
<Dropdown overlay={menu}>
|
||||
<a className="ant-dropdown-link" href="#">
|
||||
多级菜单 <Icon type="down" />
|
||||
</a>
|
||||
</Dropdown>
|
||||
, mountNode);
|
||||
````
|
||||
@@ -2,12 +2,12 @@
|
||||
|
||||
- order: 2
|
||||
|
||||
点击或鼠标移入触发。
|
||||
默认是移入触发菜单,可以点击触发。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Menu, Dropdown, Button, Icon } from 'antd';
|
||||
import { Menu, Dropdown, Icon } from 'antd';
|
||||
|
||||
const menu = <Menu>
|
||||
<Menu.Item key="0">
|
||||
@@ -22,14 +22,9 @@ const menu = <Menu>
|
||||
|
||||
ReactDOM.render(<div>
|
||||
<Dropdown overlay={menu} trigger={['click']}>
|
||||
<Button type="primary">
|
||||
<a className="ant-dropdown-link" href="#">
|
||||
点击触发 <Icon type="down" />
|
||||
</Button>
|
||||
</a>
|
||||
</Dropdown>
|
||||
<Dropdown overlay={menu}>
|
||||
<Button>
|
||||
鼠标移入 <Icon type="down" />
|
||||
</Button>
|
||||
</Dropdown>
|
||||
</div>, document.getElementById('components-dropdown-demo-trigger'));
|
||||
</div>, mountNode);
|
||||
````
|
||||
|
||||
36
components/dropdown/dropdown-button.jsx
Normal file
36
components/dropdown/dropdown-button.jsx
Normal file
@@ -0,0 +1,36 @@
|
||||
import React from 'react';
|
||||
import Button from '../button';
|
||||
import Icon from '../icon';
|
||||
import Dropdown from './dropdown';
|
||||
const ButtonGroup = Button.Group;
|
||||
|
||||
const align = {
|
||||
points: ['tr', 'br'],
|
||||
overlay: {
|
||||
adjustX: 1,
|
||||
adjustY: 1,
|
||||
},
|
||||
offset: [0, 3],
|
||||
targetOffset: [0, 0],
|
||||
};
|
||||
|
||||
export default React.createClass({
|
||||
getDefaultProps() {
|
||||
return {
|
||||
align: align,
|
||||
type: 'default',
|
||||
};
|
||||
},
|
||||
render() {
|
||||
return <ButtonGroup className="ant-dropdown-button">
|
||||
<Button type={this.props.type}>
|
||||
{this.props.children}
|
||||
</Button>
|
||||
<Dropdown {...this.props}>
|
||||
<Button type={this.props.type}>
|
||||
<Icon type="down" />
|
||||
</Button>
|
||||
</Dropdown>
|
||||
</ButtonGroup>;
|
||||
}
|
||||
});
|
||||
20
components/dropdown/dropdown.jsx
Normal file
20
components/dropdown/dropdown.jsx
Normal file
@@ -0,0 +1,20 @@
|
||||
import React from 'react';
|
||||
import Dropdown from 'rc-dropdown';
|
||||
|
||||
export default React.createClass({
|
||||
getDefaultProps: function () {
|
||||
return {
|
||||
transitionName: 'slide-up',
|
||||
prefixCls: 'ant-dropdown',
|
||||
};
|
||||
},
|
||||
render: function () {
|
||||
const { overlay, ...otherProps } = this.props;
|
||||
const menu = React.cloneElement(overlay, {
|
||||
openTransitionName: 'zoom-big',
|
||||
});
|
||||
return (
|
||||
<Dropdown {...otherProps} overlay={menu} />
|
||||
);
|
||||
}
|
||||
});
|
||||
@@ -1,16 +1,5 @@
|
||||
import React from 'react';
|
||||
import Dropdown from 'rc-dropdown';
|
||||
import Dropdown from './dropdown';
|
||||
import DropdownButton from './dropdown-button';
|
||||
|
||||
export default React.createClass({
|
||||
getDefaultProps: function () {
|
||||
return {
|
||||
transitionName: 'slide-up',
|
||||
prefixCls: 'ant-dropdown',
|
||||
};
|
||||
},
|
||||
render: function () {
|
||||
return (
|
||||
<Dropdown {...this.props} />
|
||||
);
|
||||
}
|
||||
});
|
||||
Dropdown.Button = DropdownButton;
|
||||
export default Dropdown;
|
||||
|
||||
@@ -19,10 +19,18 @@
|
||||
| 成员 | 说明 | 类型 | 默认值 |
|
||||
|-------------|------------------|--------------------|--------------|
|
||||
| trigger | 触发下拉的行为 | "click" or "hover" | hover |
|
||||
| overlay | 菜单节点 | React.Element | 无 |
|
||||
| onClick | 点击菜单后的回调 | function({key,keyPath,item,domEvent}) {} | 无 |
|
||||
| overlay | 菜单节点 | [Menu](/components/menu) | 无 |
|
||||
|
||||
|
||||
菜单可由 `antd.Menu` 取得,可设置 `onSelect` 回调,菜单还包括菜单项 `antd.Menu.Item`,分割线 `antd.Menu.Divider`。
|
||||
|
||||
> 注意: Menu.Item 必须设置唯一的 key 属性。
|
||||
|
||||
### DropdownButton
|
||||
|
||||
| 成员 | 说明 | 类型 | 默认值 |
|
||||
|-------------|------------------|--------------------|--------------|
|
||||
| type | 按钮类型,和 [Button](/components/button) 一致 | String | 'default' |
|
||||
| onClick | 点击左侧按钮的回调,和 [Button](/components/button) 一致 | Function | 无 |
|
||||
| trigger | 触发下拉的行为 | "click" or "hover" | hover |
|
||||
| overlay | 菜单节点 | [Menu](/components/menu) | 无 |
|
||||
|
||||
@@ -3,15 +3,15 @@ import classNames from 'classnames';
|
||||
|
||||
class Form extends React.Component {
|
||||
render() {
|
||||
const prefixCls = this.props.prefixCls;
|
||||
const formClassName = {
|
||||
const { prefixCls, className } = this.props;
|
||||
const formClassName = classNames({
|
||||
[className]: !!className,
|
||||
[`${prefixCls}-horizontal`]: this.props.horizontal,
|
||||
[`${prefixCls}-inline`]: this.props.inline,
|
||||
};
|
||||
const classes = classNames(formClassName);
|
||||
});
|
||||
|
||||
return (
|
||||
<form {...this.props} className={classes}>
|
||||
<form {...this.props} className={formClassName}>
|
||||
{this.props.children}
|
||||
</form>
|
||||
);
|
||||
|
||||
@@ -87,7 +87,7 @@ class FormItem extends React.Component {
|
||||
if (!Array.isArray(children)) {
|
||||
children = [children];
|
||||
}
|
||||
children.map((child, i) => {
|
||||
children.map((child) => {
|
||||
const type = child.props && child.props.type;
|
||||
let prefixCls = child.props && child.props.prefixCls;
|
||||
prefixCls = prefixCls ? prefixCls.substring(prefixCls.indexOf('-') + 1) : '';
|
||||
@@ -108,6 +108,7 @@ class FormItem extends React.Component {
|
||||
const itemClassName = {
|
||||
[`${prefixCls}-item`]: true,
|
||||
[`${prefixCls}-item-compact`]: this._isCompact(props.children),
|
||||
[`${prefixCls}-item-with-help`]: !!props.help,
|
||||
};
|
||||
|
||||
return (
|
||||
|
||||
121
components/form/demo/advanced-search-form.md
Normal file
121
components/form/demo/advanced-search-form.md
Normal file
@@ -0,0 +1,121 @@
|
||||
# 高级搜索
|
||||
|
||||
- order: 10
|
||||
|
||||
三列栅格式的表单排列方式,常用于数据表格的高级搜索。
|
||||
|
||||
有部分定制的样式代码,由于输入标签长度不确定,需要根据具体情况自行调整。
|
||||
|
||||
---
|
||||
|
||||
````jsx
|
||||
import { Form, Input, Row, Col, Button } from 'antd';
|
||||
const FormItem = Form.Item;
|
||||
|
||||
ReactDOM.render(
|
||||
<Form horizontal className="advanced-search-form">
|
||||
<Row>
|
||||
<Col span="8">
|
||||
<FormItem
|
||||
label="搜索名称:"
|
||||
labelCol={{span: 10}}
|
||||
wrapperCol={{span: 14}}>
|
||||
<Input placeholder="请输入搜索名称" />
|
||||
</FormItem>
|
||||
<FormItem
|
||||
label="较长搜索名称:"
|
||||
labelCol={{span: 10}}
|
||||
wrapperCol={{span: 14}}>
|
||||
<Input placeholder="请输入搜索名称" />
|
||||
</FormItem>
|
||||
<FormItem
|
||||
label="搜索名称:"
|
||||
labelCol={{span: 10}}
|
||||
wrapperCol={{span: 14}}>
|
||||
<Input placeholder="请输入搜索名称" />
|
||||
</FormItem>
|
||||
</Col>
|
||||
<Col span="8">
|
||||
<FormItem
|
||||
label="搜索名称:"
|
||||
labelCol={{span: 10}}
|
||||
wrapperCol={{span: 14}}>
|
||||
<Input placeholder="请输入搜索名称" />
|
||||
</FormItem>
|
||||
<FormItem
|
||||
label="较长搜索名称:"
|
||||
labelCol={{span: 10}}
|
||||
wrapperCol={{span: 14}}>
|
||||
<Input placeholder="请输入搜索名称" />
|
||||
</FormItem>
|
||||
<FormItem
|
||||
label="搜索名称:"
|
||||
labelCol={{span: 10}}
|
||||
wrapperCol={{span: 14}}>
|
||||
<Input placeholder="请输入搜索名称" />
|
||||
</FormItem>
|
||||
</Col>
|
||||
<Col span="8">
|
||||
<FormItem
|
||||
label="搜索名称:"
|
||||
labelCol={{span: 10}}
|
||||
wrapperCol={{span: 14}}>
|
||||
<Input placeholder="请输入搜索名称" />
|
||||
</FormItem>
|
||||
<FormItem
|
||||
label="较长搜索名称:"
|
||||
labelCol={{span: 10}}
|
||||
wrapperCol={{span: 14}}>
|
||||
<Input placeholder="请输入搜索名称" />
|
||||
</FormItem>
|
||||
<FormItem
|
||||
label="搜索名称:"
|
||||
labelCol={{span: 10}}
|
||||
wrapperCol={{span: 14}}>
|
||||
<Input placeholder="请输入搜索名称" />
|
||||
</FormItem>
|
||||
</Col>
|
||||
</Row>
|
||||
<Row>
|
||||
<Col span="8" offset="16" style={{textAlign: 'right'}}>
|
||||
<Button type="primary" htmlType="submit">搜索</Button>
|
||||
<Button type="ghost">清除条件</Button>
|
||||
</Col>
|
||||
</Row>
|
||||
</Form>
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
````css
|
||||
/* 定制样式 */
|
||||
|
||||
.advanced-search-form {
|
||||
padding: 16px 8px;
|
||||
background: #f8f8f8;
|
||||
border: 1px solid #d9d9d9;
|
||||
border-radius: 6px;
|
||||
}
|
||||
|
||||
/* 由于输入标签长度不确定,所以需要微调使之看上去居中 */
|
||||
.advanced-search-form > .row {
|
||||
margin-left: -10px;
|
||||
}
|
||||
|
||||
.advanced-search-form > .row > .col-8 {
|
||||
padding: 0 8px;
|
||||
}
|
||||
|
||||
.advanced-search-form .ant-form-item {
|
||||
margin-bottom: 16px;
|
||||
}
|
||||
|
||||
.advanced-search-form .ant-btn + .ant-btn {
|
||||
margin-left: 8px;
|
||||
}
|
||||
````
|
||||
|
||||
<style>
|
||||
#components-form-demo-advanced-search-form .ant-form-horizontal {
|
||||
max-width: none;
|
||||
}
|
||||
</style>
|
||||
@@ -46,5 +46,5 @@ ReactDOM.render(
|
||||
</Row>
|
||||
</fieldset>
|
||||
</Form>
|
||||
, document.getElementById('components-form-demo-disabled'));
|
||||
, mountNode);
|
||||
````
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user