page.js 7.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259
  1. import React, { Component } from 'react';
  2. import { Link } from 'react-router-dom';
  3. import './index.less';
  4. import Page from '@src/containers/Page';
  5. import { formatDate, formatMonth, getMap, formatPercent } from '@src/services/Tools';
  6. import Ratio from '../../../components/Ratio';
  7. import UserAction from '../../../components/UserAction';
  8. import UserPagination from '../../../components/UserPagination';
  9. import { ExperienceScore, ExperienceDay, PrepareStatus, ExperiencePercent } from '../../../../Constant';
  10. import { Main } from '../../../stores/main';
  11. import { My } from '../../../stores/my';
  12. import { Course } from '../../../stores/course';
  13. const PrepareStatusMap = getMap(PrepareStatus, 'value', 'label');
  14. const ExperiencePercentMap = getMap(ExperiencePercent, 'value', 'label');
  15. const colorList = ['#2754E0', '#3F86EA', '#41A6F3', '#9BD4FF'];
  16. export default class extends Page {
  17. initState() {
  18. const prepareStatusSelect = PrepareStatus.map(row => {
  19. return {
  20. title: row.label,
  21. key: row.value,
  22. };
  23. });
  24. prepareStatusSelect.unshift({
  25. title: '全部',
  26. key: '',
  27. });
  28. const experienceDaySelect = ExperienceDay.map(row => {
  29. return {
  30. title: row.label,
  31. key: row.value,
  32. };
  33. });
  34. experienceDaySelect.unshift({
  35. title: '全部',
  36. key: '',
  37. });
  38. const experienceScoreSelect = ExperienceScore.map(row => {
  39. return {
  40. title: row.label,
  41. key: row.value,
  42. };
  43. });
  44. experienceScoreSelect.unshift({
  45. title: '全部',
  46. key: '',
  47. });
  48. const experiencePercentSelect = ExperiencePercent.map(row => {
  49. return {
  50. title: row.label,
  51. key: row.value,
  52. };
  53. });
  54. experiencePercentSelect.unshift({
  55. title: '全部',
  56. key: '',
  57. });
  58. return {
  59. prepareStatusSelect,
  60. experienceDaySelect,
  61. experienceScoreSelect,
  62. experiencePercentSelect,
  63. };
  64. }
  65. init() {
  66. Main.getExperience()
  67. .then(result => {
  68. const totalScoreNumber = result.score.reduce((x, y) => x + y, 0);
  69. const totalPercentNumber = result.percent.reduce((x, y) => x + y, 0);
  70. const scoreList = ExperienceScore.map((row, index) => {
  71. const percent = formatPercent(result.score[index] || 0, totalScoreNumber);
  72. return {
  73. color: colorList[index],
  74. label: `${row.label} ${percent} ${result.score[index] || 0}人`,
  75. value: percent,
  76. };
  77. });
  78. const percentList = ExperiencePercent.map((row, index) => {
  79. const percent = formatPercent(result.percent[index] || 0, totalPercentNumber);
  80. return {
  81. color: colorList[index],
  82. label: `${row.label} ${percent} ${result.percent[index] || 0}人`,
  83. value: percent,
  84. };
  85. });
  86. this.setState({ data: result, scoreList, percentList });
  87. });
  88. }
  89. initData() {
  90. const data = Object.assign(this.state, this.state.search);
  91. if (data.order) {
  92. data.sortMap = { [data.order]: data.direction };
  93. }
  94. data.filterMap = this.state.search;
  95. this.setState(data);
  96. Course.listExperience(Object.assign({}, this.state.search))
  97. .then(result => {
  98. this.setState({ list: result.list, total: result.total });
  99. });
  100. }
  101. onFilter(value) {
  102. this.search(value, false);
  103. this.initData();
  104. }
  105. onChangePage(page) {
  106. this.search({ page }, false);
  107. this.initData();
  108. }
  109. renderView() {
  110. return (
  111. <div>
  112. <div className="top content t-8">
  113. <Link to="/course">千行课堂</Link> > <span className="t-1">学员表现</span>
  114. </div>
  115. {this.renderDetail()}
  116. </div>
  117. );
  118. }
  119. renderDetail() {
  120. const { filterMap, list, data = {}, scoreList, percentList, total, page } = this.state;
  121. const { prepareStatusSelect, experienceDaySelect, experienceScoreSelect, experiencePercentSelect } = this.state;
  122. return [
  123. <div className="center">
  124. <div className="content">
  125. <div className="total-list">
  126. <div className="total-item">
  127. <div className="title">学员人数</div>
  128. <div className="label">{data.number || 0}</div>
  129. </div>
  130. <div className="total-item">
  131. <div className="title">考分分布</div>
  132. <Ratio
  133. size="small"
  134. values={scoreList || []}
  135. />
  136. </div>
  137. <div className="total-item">
  138. <div className="title">出分周期</div>
  139. <div className="label">{data.period || 0}天</div>
  140. </div>
  141. <div className="total-item">
  142. <div className="title">提分比例</div>
  143. <Ratio
  144. size="small"
  145. values={percentList || []}
  146. />
  147. </div>
  148. </div>
  149. <UserAction
  150. selectList={[
  151. {
  152. key: 'prepareStatus',
  153. placeholder: '身份',
  154. select: prepareStatusSelect,
  155. },
  156. {
  157. key: 'experienceDay',
  158. placeholder: '备考周期',
  159. select: experienceDaySelect,
  160. },
  161. {
  162. key: 'experienceScore',
  163. placeholder: '分手成绩',
  164. select: experienceScoreSelect,
  165. },
  166. {
  167. key: 'experiencePercent',
  168. placeholder: '提分幅度',
  169. select: experiencePercentSelect,
  170. },
  171. ]}
  172. filterMap={filterMap}
  173. onFilter={value => this.onFilter(value)}
  174. />
  175. {list.map(item => {
  176. return <Article data={item} />;
  177. })}
  178. {total > 0 && list.length > 0 && (
  179. <UserPagination total={total} current={page} pageSize={this.state.search.size} onChange={p => this.onChangePage(p)} />
  180. )}
  181. </div>
  182. </div>,
  183. ];
  184. }
  185. }
  186. class Article extends Component {
  187. constructor(props) {
  188. super(props);
  189. this.state = {};
  190. }
  191. onCollect() {
  192. const { data } = this.props;
  193. const { collect } = this.state;
  194. let collectStatus = false;
  195. if (collect !== undefined) {
  196. collectStatus = collect;
  197. } else {
  198. collectStatus = data.collect;
  199. }
  200. if (!collectStatus) {
  201. My.addExperienceCollect(data.id)
  202. .then(() => {
  203. this.setState({ collect: true });
  204. });
  205. } else {
  206. My.delExperienceCollect(data.id)
  207. .then(() => {
  208. this.setState({ collect: false });
  209. });
  210. }
  211. }
  212. render() {
  213. const { data } = this.props;
  214. const { collect } = this.state;
  215. let collectStatus = false;
  216. if (collect !== undefined) {
  217. collectStatus = collect;
  218. } else {
  219. collectStatus = data.collect;
  220. }
  221. return (
  222. <div className="article-item p-t-2 b-b" onClick={() => linkTo(`/course/experience/detail/${data.id}`)}>
  223. <div className="t-1 t-s-14 f-w-b">
  224. {data.title}
  225. <div className="f-r t-3 t-s-12 f-w-d">
  226. <span>{data.updateTime && formatDate(data.updateTime, 'YYYY-MM-DD HH:mm:ss')}</span>
  227. <span className="m-l-2">阅读 {data.viewNumber}</span>
  228. <span className="m-l-2 c-p" onClick={(e) => {
  229. e.stopPropagation();
  230. this.onCollect();
  231. }}>
  232. {collectStatus ? '收藏' : '取消收藏'}
  233. </span>
  234. </div>
  235. </div>
  236. <div className="t-1 t-s-12 m-b-2">
  237. <span className="m-r-2">{data.user ? data.user.nickname : data.nickname}</span>
  238. <span className="m-r-2">{PrepareStatusMap[data.prepareStatus]}</span>
  239. <span className="m-r-2">备考:{!!data.experienceDay && formatMonth(data.experienceDay, false)}</span>
  240. <span className="m-r-2">
  241. {data.experienceScore}分 /提分 {ExperiencePercentMap[data.experiencePercent]}
  242. </span>
  243. </div>
  244. <div className="t-2 m-b-2 detail">{data.description}</div>
  245. </div>
  246. );
  247. }
  248. }