index.js 8.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299
  1. import { unit } from '@ant-design/cssinjs';
  2. import { operationUnit, resetComponent, resetIcon, textEllipsis } from '../../style';
  3. import { genStyleHooks, mergeToken } from '../../theme/internal';
  4. const genTransferCustomizeStyle = token => {
  5. const {
  6. antCls,
  7. componentCls,
  8. listHeight,
  9. controlHeightLG
  10. } = token;
  11. const tableCls = `${antCls}-table`;
  12. const inputCls = `${antCls}-input`;
  13. return {
  14. [`${componentCls}-customize-list`]: {
  15. [`${componentCls}-list`]: {
  16. flex: '1 1 50%',
  17. width: 'auto',
  18. height: 'auto',
  19. minHeight: listHeight,
  20. minWidth: 0
  21. },
  22. // =================== Hook Components ===================
  23. [`${tableCls}-wrapper`]: {
  24. [`${tableCls}-small`]: {
  25. border: 0,
  26. borderRadius: 0,
  27. [`${tableCls}-selection-column`]: {
  28. width: controlHeightLG,
  29. minWidth: controlHeightLG
  30. }
  31. },
  32. [`${tableCls}-pagination${tableCls}-pagination`]: {
  33. margin: 0,
  34. padding: token.paddingXS
  35. }
  36. },
  37. [`${inputCls}[disabled]`]: {
  38. backgroundColor: 'transparent'
  39. }
  40. }
  41. };
  42. };
  43. const genTransferStatusColor = (token, color) => {
  44. const {
  45. componentCls,
  46. colorBorder
  47. } = token;
  48. return {
  49. [`${componentCls}-list`]: {
  50. borderColor: color,
  51. '&-search:not([disabled])': {
  52. borderColor: colorBorder
  53. }
  54. }
  55. };
  56. };
  57. const genTransferStatusStyle = token => {
  58. const {
  59. componentCls
  60. } = token;
  61. return {
  62. [`${componentCls}-status-error`]: Object.assign({}, genTransferStatusColor(token, token.colorError)),
  63. [`${componentCls}-status-warning`]: Object.assign({}, genTransferStatusColor(token, token.colorWarning))
  64. };
  65. };
  66. const genTransferListStyle = token => {
  67. const {
  68. componentCls,
  69. colorBorder,
  70. colorSplit,
  71. lineWidth,
  72. itemHeight,
  73. headerHeight,
  74. transferHeaderVerticalPadding,
  75. itemPaddingBlock,
  76. controlItemBgActive,
  77. colorTextDisabled,
  78. colorTextSecondary,
  79. listHeight,
  80. listWidth,
  81. listWidthLG,
  82. fontSizeIcon,
  83. marginXS,
  84. paddingSM,
  85. lineType,
  86. antCls,
  87. iconCls,
  88. motionDurationSlow,
  89. controlItemBgHover,
  90. borderRadiusLG,
  91. colorBgContainer,
  92. colorText,
  93. controlItemBgActiveHover
  94. } = token;
  95. const contentBorderRadius = unit(token.calc(borderRadiusLG).sub(lineWidth).equal());
  96. return {
  97. display: 'flex',
  98. flexDirection: 'column',
  99. width: listWidth,
  100. height: listHeight,
  101. border: `${unit(lineWidth)} ${lineType} ${colorBorder}`,
  102. borderRadius: token.borderRadiusLG,
  103. '&-with-pagination': {
  104. width: listWidthLG,
  105. height: 'auto'
  106. },
  107. '&-search': {
  108. [`${iconCls}-search`]: {
  109. color: colorTextDisabled
  110. }
  111. },
  112. '&-header': {
  113. display: 'flex',
  114. flex: 'none',
  115. alignItems: 'center',
  116. height: headerHeight,
  117. // border-top is on the transfer dom. We should minus 1px for this
  118. padding: `${unit(token.calc(transferHeaderVerticalPadding).sub(lineWidth).equal())} ${unit(paddingSM)} ${unit(transferHeaderVerticalPadding)}`,
  119. color: colorText,
  120. background: colorBgContainer,
  121. borderBottom: `${unit(lineWidth)} ${lineType} ${colorSplit}`,
  122. borderRadius: `${unit(borderRadiusLG)} ${unit(borderRadiusLG)} 0 0`,
  123. '> *:not(:last-child)': {
  124. marginInlineEnd: 4 // This is magic and fixed number, DO NOT use token since it may change.
  125. },
  126. '> *': {
  127. flex: 'none'
  128. },
  129. '&-title': Object.assign(Object.assign({}, textEllipsis), {
  130. flex: 'auto',
  131. textAlign: 'end'
  132. }),
  133. '&-dropdown': Object.assign(Object.assign({}, resetIcon()), {
  134. fontSize: fontSizeIcon,
  135. transform: 'translateY(10%)',
  136. cursor: 'pointer',
  137. '&[disabled]': {
  138. cursor: 'not-allowed'
  139. }
  140. })
  141. },
  142. '&-body': {
  143. display: 'flex',
  144. flex: 'auto',
  145. flexDirection: 'column',
  146. fontSize: token.fontSize,
  147. // https://blog.csdn.net/qq449245884/article/details/107373672/
  148. minHeight: 0,
  149. '&-search-wrapper': {
  150. position: 'relative',
  151. flex: 'none',
  152. padding: paddingSM
  153. }
  154. },
  155. '&-content': {
  156. flex: 'auto',
  157. margin: 0,
  158. padding: 0,
  159. overflow: 'auto',
  160. listStyle: 'none',
  161. borderRadius: `0 0 ${contentBorderRadius} ${contentBorderRadius}`,
  162. '&-item': {
  163. display: 'flex',
  164. alignItems: 'center',
  165. minHeight: itemHeight,
  166. padding: `${unit(itemPaddingBlock)} ${unit(paddingSM)}`,
  167. transition: `all ${motionDurationSlow}`,
  168. '> *:not(:last-child)': {
  169. marginInlineEnd: marginXS
  170. },
  171. '> *': {
  172. flex: 'none'
  173. },
  174. '&-text': Object.assign(Object.assign({}, textEllipsis), {
  175. flex: 'auto'
  176. }),
  177. '&-remove': Object.assign(Object.assign({}, operationUnit(token)), {
  178. color: colorBorder,
  179. '&:hover, &:focus': {
  180. color: colorTextSecondary
  181. }
  182. }),
  183. [`&:not(${componentCls}-list-content-item-disabled)`]: {
  184. '&:hover': {
  185. backgroundColor: controlItemBgHover,
  186. cursor: 'pointer'
  187. },
  188. [`&${componentCls}-list-content-item-checked:hover`]: {
  189. backgroundColor: controlItemBgActiveHover
  190. }
  191. },
  192. '&-checked': {
  193. backgroundColor: controlItemBgActive
  194. },
  195. '&-disabled': {
  196. color: colorTextDisabled,
  197. cursor: 'not-allowed'
  198. }
  199. },
  200. // Do not change hover style when `oneWay` mode
  201. [`&-show-remove ${componentCls}-list-content-item:not(${componentCls}-list-content-item-disabled):hover`]: {
  202. background: 'transparent',
  203. cursor: 'default'
  204. }
  205. },
  206. '&-pagination': {
  207. padding: token.paddingXS,
  208. textAlign: 'end',
  209. borderTop: `${unit(lineWidth)} ${lineType} ${colorSplit}`,
  210. [`${antCls}-pagination-options`]: {
  211. paddingInlineEnd: token.paddingXS
  212. }
  213. },
  214. '&-body-not-found': {
  215. flex: 'none',
  216. width: '100%',
  217. margin: 'auto 0',
  218. color: colorTextDisabled,
  219. textAlign: 'center'
  220. },
  221. '&-footer': {
  222. borderTop: `${unit(lineWidth)} ${lineType} ${colorSplit}`
  223. },
  224. // fix: https://github.com/ant-design/ant-design/issues/44489
  225. '&-checkbox': {
  226. lineHeight: 1
  227. }
  228. };
  229. };
  230. const genTransferStyle = token => {
  231. const {
  232. antCls,
  233. iconCls,
  234. componentCls,
  235. marginXS,
  236. marginXXS,
  237. fontSizeIcon,
  238. colorBgContainerDisabled
  239. } = token;
  240. return {
  241. [componentCls]: Object.assign(Object.assign({}, resetComponent(token)), {
  242. position: 'relative',
  243. display: 'flex',
  244. alignItems: 'stretch',
  245. [`${componentCls}-disabled`]: {
  246. [`${componentCls}-list`]: {
  247. background: colorBgContainerDisabled
  248. }
  249. },
  250. [`${componentCls}-list`]: genTransferListStyle(token),
  251. [`${componentCls}-operation`]: {
  252. display: 'flex',
  253. flex: 'none',
  254. flexDirection: 'column',
  255. alignSelf: 'center',
  256. margin: `0 ${unit(marginXS)}`,
  257. verticalAlign: 'middle',
  258. gap: marginXXS,
  259. [`${antCls}-btn ${iconCls}`]: {
  260. fontSize: fontSizeIcon
  261. }
  262. }
  263. })
  264. };
  265. };
  266. const genTransferRTLStyle = token => {
  267. const {
  268. componentCls
  269. } = token;
  270. return {
  271. [`${componentCls}-rtl`]: {
  272. direction: 'rtl'
  273. }
  274. };
  275. };
  276. export const prepareComponentToken = token => {
  277. const {
  278. fontSize,
  279. lineHeight,
  280. controlHeight,
  281. controlHeightLG,
  282. lineWidth
  283. } = token;
  284. const fontHeight = Math.round(fontSize * lineHeight);
  285. return {
  286. listWidth: 180,
  287. listHeight: 200,
  288. listWidthLG: 250,
  289. headerHeight: controlHeightLG,
  290. itemHeight: controlHeight,
  291. itemPaddingBlock: (controlHeight - fontHeight) / 2,
  292. transferHeaderVerticalPadding: Math.ceil((controlHeightLG - lineWidth - fontHeight) / 2)
  293. };
  294. };
  295. // ============================== Export ==============================
  296. export default genStyleHooks('Transfer', token => {
  297. const transferToken = mergeToken(token);
  298. return [genTransferStyle(transferToken), genTransferCustomizeStyle(transferToken), genTransferStatusStyle(transferToken), genTransferRTLStyle(transferToken)];
  299. }, prepareComponentToken);