index.js 5.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195
  1. import React, { Component } from 'react';
  2. import moment from 'moment';
  3. import './index.less';
  4. import { DatePicker, Calendar, Icon } from 'antd';
  5. export default class extends Component {
  6. constructor(props) {
  7. super(props);
  8. this.state = { key: 0 };
  9. this.loading = false;
  10. }
  11. dateRender(date) {
  12. const { dateRender, checkRefresh } = this.props;
  13. if (!this.loading && checkRefresh) {
  14. if (checkRefresh(date, () => this.needRefresh())) {
  15. this.loading = true;
  16. }
  17. }
  18. if (dateRender) return dateRender(date);
  19. return <div className="ant-calendar-date">{date.get('date')}</div>;
  20. }
  21. needRefresh() {
  22. this.setState({ key: this.state.key + 1 });
  23. this.loading = false;
  24. setTimeout(() => {
  25. this.setState({ key: this.state.key + 1 });
  26. }, 1);
  27. }
  28. render() {
  29. const { show, hideInput, disabledDate, theme = '', value, onChange, onClick } = this.props;
  30. return (
  31. <div
  32. ref={ref => {
  33. if (!this.ref) {
  34. this.ref = ref;
  35. this.setState({ load: false });
  36. }
  37. }}
  38. onClick={(event) => onClick && onClick(event)}
  39. className={`g-date-block ${hideInput ? 'hide-input' : ''}`}
  40. >
  41. <DatePicker
  42. open={show && this.ref}
  43. value={value}
  44. getCalendarContainer={() => this.ref.parentNode}
  45. dropdownClassName={`g-date ${theme} ${hideInput ? 'hide-input' : ''}`}
  46. disabledDate={disabledDate}
  47. dateRender={date => this.dateRender(date)}
  48. onChange={date => onChange(date)}
  49. />
  50. </div>
  51. );
  52. }
  53. }
  54. export class TwoDate extends Component {
  55. constructor(props) {
  56. super(props);
  57. const today = moment();
  58. this.state = {
  59. key: 0,
  60. value: null,
  61. leftValue: today.clone().subtract(1, 'month'),
  62. rightValue: today,
  63. };
  64. }
  65. dateRender(date) {
  66. const { checkRefresh } = this.props;
  67. if (!this.loading && checkRefresh) {
  68. if (checkRefresh(date, () => this.needRefresh())) {
  69. this.loading = true;
  70. }
  71. }
  72. return this.renderItem(date);
  73. }
  74. needRefresh() {
  75. this.setState({ key: this.state.key + 1 });
  76. this.loading = false;
  77. setTimeout(() => {
  78. this.setState({ key: this.state.key + 1 });
  79. }, 1);
  80. }
  81. renderItem(date) {
  82. const { value } = this.state;
  83. const { getType } = this.props;
  84. return (
  85. <div
  86. className={`ant-fullcalendar-date ${getType ? getType(date) : ''} ${value && value.diff(date) === 0 ? 'selected' : ''}`}
  87. >
  88. <div className="ant-fullcalendar-value">{date.get('date')}</div>
  89. </div>
  90. );
  91. }
  92. onLeftSelect(date) {
  93. const { onChange, startDate } = this.props;
  94. if (startDate && date.isBefore(startDate)) return;
  95. this.setState({
  96. value: date,
  97. leftValue: date,
  98. rightValue: date.clone().add(1, 'month'),
  99. });
  100. if (onChange) onChange(date);
  101. }
  102. onRightSelect(date) {
  103. const { onChange, endDate } = this.props;
  104. if (endDate && date.isAfter(endDate)) return;
  105. this.setState({
  106. value: date,
  107. rightValue: date,
  108. leftValue: date.clone().subtract(1, 'month'),
  109. });
  110. if (onChange) onChange(date);
  111. }
  112. leftHeadRender() {
  113. const { leftValue } = this.state;
  114. const { extendInfo } = this.props;
  115. return (
  116. <div className="t-c">
  117. <div style={{ left: 15, top: 0 }} className="p-a">
  118. <Icon
  119. className="m-r-5"
  120. type="double-left"
  121. onClick={() => this.onLeftSelect(leftValue.clone().subtract(1, 'year'))}
  122. />
  123. <Icon type="left" onClick={() => this.onLeftSelect(leftValue.clone().subtract(1, 'month'))} />
  124. </div>
  125. <span>{leftValue.year()}年 </span>
  126. <span>{leftValue.month() + 1}月 </span>
  127. <span className="t-4">{extendInfo && extendInfo(leftValue)}</span>
  128. </div>
  129. );
  130. }
  131. rightHeadRender() {
  132. const { rightValue } = this.state;
  133. const { extendInfo } = this.props;
  134. return (
  135. <div className="t-c">
  136. <span>{rightValue.year()}年 </span>
  137. <span>{rightValue.month() + 1}月 </span>
  138. <span className="t-4">{extendInfo && extendInfo(rightValue)}</span>
  139. <div style={{ right: 15, top: 0 }} className="p-a">
  140. <Icon type="right" onClick={() => this.onRightSelect(rightValue.clone().add(1, 'month'))} />
  141. <Icon
  142. className="m-l-5"
  143. type="double-right"
  144. onClick={() => this.onRightSelect(rightValue.clone().add(1, 'year'))}
  145. />
  146. </div>
  147. </div>
  148. );
  149. }
  150. render() {
  151. const { disabledDate } = this.props;
  152. const { leftValue, rightValue } = this.state;
  153. return (
  154. <div className="g-two-date">
  155. <div className="g-two-head">
  156. {this.leftHeadRender()}
  157. {this.rightHeadRender()}
  158. </div>
  159. <div className="g-two-body">
  160. <Calendar
  161. fullscreen={false}
  162. headerRender={data => this.leftHeadRender(data)}
  163. value={leftValue}
  164. disabledDate={disabledDate}
  165. dateFullCellRender={date => this.dateRender(date)}
  166. onSelect={date => this.onLeftSelect(date)}
  167. onPanelChange={date => this.onLeftSelect(date)}
  168. />
  169. <Calendar
  170. fullscreen={false}
  171. headerRender={data => this.rightHeadRender(data)}
  172. value={rightValue}
  173. disabledDate={disabledDate}
  174. dateFullCellRender={date => this.dateRender(date)}
  175. onSelect={date => this.onRightSelect(date)}
  176. onPanelChange={date => this.onRightSelect(date)}
  177. />
  178. </div>
  179. </div>
  180. );
  181. }
  182. }