index.jsx 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646
  1. import React, { Component } from 'react';
  2. import {
  3. Button, DatePicker,
  4. Input,
  5. message,
  6. Select,
  7. Spin,
  8. Table, Tabs,
  9. } from "antd";
  10. import './index.less';
  11. import $ from "jquery/src/ajax";
  12. import CustomerDetails from './customerDetails';
  13. import moment from "moment";
  14. import { ChooseList } from "../../../order/orderNew/chooseList";
  15. const { RangePicker } = DatePicker;
  16. const { TabPane } = Tabs;
  17. class DepartmentStatistics extends Component {
  18. constructor(props) {
  19. super(props);
  20. this.state = {
  21. superId: undefined,
  22. nameSearch: '',
  23. releaseDate: [moment(Date.now() - 777600000).format('YYYY-MM-DD'), moment(Date.now()).format('YYYY-MM-DD')],
  24. columns: [
  25. {
  26. title: "部门",
  27. dataIndex: "name",
  28. key: "name",
  29. width: '25%',
  30. },
  31. {
  32. title: "私有数",
  33. dataIndex: "userCount",
  34. key: "userCount",
  35. className: 'tableRowStyle',
  36. width: 120,
  37. render: (text, record) => {
  38. return (
  39. <div
  40. className={record.aid ? 'receiveCount' : ''}
  41. onClick={(e) => {
  42. if (record.aid) {
  43. e.stopPropagation();
  44. this.setState({
  45. customerVisible: true,
  46. aid: record.aid,
  47. aName: record.aName,
  48. type: 0,
  49. })
  50. }
  51. }}>
  52. {text}
  53. </div>
  54. );
  55. },
  56. },
  57. {
  58. title: "有效面谈数",
  59. dataIndex: "firstInterviewCount",
  60. key: "firstInterviewCount",
  61. // className: 'tableRowStyle',
  62. width: 120,
  63. },
  64. {
  65. title: "私有领取数",
  66. dataIndex: "receiveCount",
  67. key: "receiveCount",
  68. className: 'tableRowStyle',
  69. width: 120,
  70. render: (text, record) => {
  71. return (
  72. <div
  73. className={record.aid ? 'receiveCount' : ''}
  74. onClick={(e) => {
  75. if (record.aid) {
  76. e.stopPropagation();
  77. this.setState({
  78. customerVisible: true,
  79. aName: record.aName,
  80. aid: record.aid,
  81. type: 7,
  82. })
  83. }
  84. }}>
  85. {text}
  86. </div>
  87. );
  88. },
  89. },
  90. {
  91. title: "私有新增数",
  92. dataIndex: "newCount",
  93. key: "newCount",
  94. className: 'tableRowStyle',
  95. width: 120,
  96. render: (text, record) => {
  97. return (
  98. <div
  99. className={record.aid ? 'receiveCount' : ''}
  100. onClick={(e) => {
  101. if (record.aid) {
  102. e.stopPropagation();
  103. this.setState({
  104. customerVisible: true,
  105. aName: record.aName,
  106. aid: record.aid,
  107. type: 3,
  108. })
  109. }
  110. }}>
  111. {text}
  112. </div>
  113. );
  114. },
  115. },
  116. {
  117. title: "私有转交数",
  118. dataIndex: "transferCount",
  119. key: "transferCount",
  120. className: 'tableRowStyle',
  121. width: 120,
  122. render: (text, record) => {
  123. return (
  124. <div
  125. className={record.aid ? 'receiveCount' : ''}
  126. onClick={(e) => {
  127. if (record.aid) {
  128. e.stopPropagation();
  129. this.setState({
  130. customerVisible: true,
  131. aName: record.aName,
  132. aid: record.aid,
  133. type: 8,
  134. })
  135. }
  136. }}>
  137. {text}
  138. </div>
  139. );
  140. },
  141. },
  142. {
  143. title: "渠道数",
  144. dataIndex: "channelCount",
  145. key: "channelCount",
  146. className: 'tableRowStyle',
  147. width: 120,
  148. render: (text, record) => {
  149. return (
  150. <div
  151. className={record.aid ? 'receiveCount' : ''}
  152. onClick={(e) => {
  153. if (record.aid) {
  154. e.stopPropagation();
  155. this.setState({
  156. customerVisible: true,
  157. aid: record.aid,
  158. aName: record.aName,
  159. type: 1,
  160. })
  161. }
  162. }}>
  163. {text}
  164. </div>
  165. );
  166. },
  167. },
  168. {
  169. title: "签单数",
  170. dataIndex: "signCount",
  171. key: "signCount",
  172. className: 'tableRowStyle',
  173. width: 120,
  174. render: (text, record) => {
  175. return (
  176. <div
  177. className={record.aid ? 'receiveCount' : ''}
  178. onClick={(e) => {
  179. if (record.aid) {
  180. e.stopPropagation();
  181. this.setState({
  182. customerVisible: true,
  183. aName: record.aName,
  184. aid: record.aid,
  185. type: 2,
  186. })
  187. }
  188. }}>
  189. {text}
  190. </div>
  191. );
  192. },
  193. },
  194. {
  195. title: "渠道新增数",
  196. dataIndex: "channelNewCount",
  197. key: "channelNewCount",
  198. className: 'tableRowStyle',
  199. width: 120,
  200. render: (text, record) => {
  201. return (
  202. <div
  203. className={record.aid ? 'receiveCount' : ''}
  204. onClick={(e) => {
  205. if (record.aid) {
  206. e.stopPropagation();
  207. this.setState({
  208. customerVisible: true,
  209. aName: record.aName,
  210. aid: record.aid,
  211. type: 4,
  212. })
  213. }
  214. }}>
  215. {text}
  216. </div>
  217. );
  218. },
  219. },
  220. {
  221. title: "私有面谈数",
  222. dataIndex: "completeCount",
  223. key: "completeCount",
  224. className: 'tableRowStyle',
  225. width: 120,
  226. render: (text, record) => {
  227. return (
  228. <div
  229. className={record.aid ? 'receiveCount' : ''}
  230. onClick={(e) => {
  231. if (record.aid) {
  232. e.stopPropagation();
  233. this.setState({
  234. customerVisible: true,
  235. aName: record.aName,
  236. aid: record.aid,
  237. type: 5,
  238. })
  239. }
  240. }}>
  241. {text}
  242. </div>
  243. );
  244. },
  245. },
  246. {
  247. title: "渠道面谈数",
  248. dataIndex: "channelCompleteCount",
  249. key: "channelCompleteCount",
  250. className: 'tableRowStyle',
  251. width: 120,
  252. render: (text, record) => {
  253. return (
  254. <div
  255. className={record.aid ? 'receiveCount' : ''}
  256. onClick={(e) => {
  257. if (record.aid) {
  258. e.stopPropagation();
  259. this.setState({
  260. customerVisible: true,
  261. aName: record.aName,
  262. aid: record.aid,
  263. type: 6,
  264. })
  265. }
  266. }}>
  267. {text}
  268. </div>
  269. );
  270. },
  271. },
  272. {
  273. title: <div style={{ color: 'red' }}>
  274. <div>重点客户</div>
  275. <div>(一个月内预签)</div>
  276. </div>,
  277. dataIndex: "keynoteCount",
  278. key: "keynoteCount",
  279. className: 'tableRowStyle',
  280. width: 120,
  281. },
  282. {
  283. title: <div style={{ color: 'orange' }}>
  284. <div>意向客户</div>
  285. <div>(半年内预签)</div>
  286. </div>,
  287. dataIndex: "intentionCount",
  288. key: "intentionCount",
  289. className: 'tableRowStyle',
  290. width: 120,
  291. },
  292. {
  293. title: <div style={{ color: 'green' }}>
  294. <div>一般客户</div>
  295. <div>(一年以上预签)</div>
  296. </div>,
  297. dataIndex: "generalCount",
  298. key: "generalCount",
  299. className: 'tableRowStyle',
  300. width: 120,
  301. },
  302. ],
  303. contactsOption: null,
  304. loading: false,
  305. ispage: 1,
  306. aid: '',
  307. type: '',
  308. visible: false,
  309. exportPendingLoading: false,
  310. };
  311. this.loadData = this.loadData.bind(this);
  312. this.reset = this.reset.bind(this);
  313. this.selectSuperId = this.selectSuperId.bind(this);
  314. this.changeList = this.changeList.bind(this);
  315. this.exportExec = this.exportExec.bind(this);
  316. }
  317. componentDidMount() {
  318. this.selectSuperId();
  319. }
  320. loadData() {
  321. if (!this.state.superId) {
  322. message.warning('请选择部门后再搜索')
  323. return;
  324. }
  325. this.setState({
  326. loading: true,
  327. });
  328. let api = '/api/admin/customer/selectAllUser';
  329. let data = {};
  330. if (this.state.superId) {
  331. data.depId = this.state.superId;
  332. }
  333. if (this.state.nameSearch) {
  334. data.aName = this.state.nameSearch;
  335. }
  336. if (this.state.releaseDate[0]) {
  337. data.startTime = this.state.releaseDate[0]
  338. }
  339. if (this.state.releaseDate[1]) {
  340. data.endTime = this.state.releaseDate[1]
  341. }
  342. $.ajax({
  343. method: "get",
  344. dataType: "json",
  345. crossDomain: false,
  346. url: globalConfig.context + api,
  347. data: data,
  348. success: function (data) {
  349. let theArr = [];
  350. if (data.error.length !== 0) {
  351. if (data.error && data.error.length) {
  352. message.warning(data.error[0].message);
  353. }
  354. } else {
  355. data.data.children = data.data.list;
  356. data.data.children = data.data.children.concat(data.data.aList);
  357. theArr.push(data.data);
  358. theArr = this.handleTabsInfor(theArr);
  359. this.setState({
  360. ispage: data.data.pageNo,
  361. dataSource: theArr,
  362. });
  363. }
  364. }.bind(this),
  365. }).always(
  366. function () {
  367. this.setState({
  368. loading: false,
  369. });
  370. }.bind(this)
  371. );
  372. };
  373. exportExec() {
  374. message.config({
  375. duration: 20,
  376. });
  377. let loading = message.loading("下载中...");
  378. this.setState({
  379. exportPendingLoading: true,
  380. });
  381. let data = {
  382. depId: this.state.superId,
  383. aName: this.state.nameSearch,
  384. startTime: this.state.releaseDate[0],
  385. endTime: this.state.releaseDate[1],
  386. }
  387. $.ajax({
  388. method: "get",
  389. dataType: "json",
  390. crossDomain: false,
  391. url: '/api/admin/customer/selectAllUser/export',
  392. data,
  393. success: function (data) {
  394. if (data.error.length === 0) {
  395. this.download(data.data);
  396. } else {
  397. message.warning(data.error[0].message);
  398. }
  399. }.bind(this),
  400. }).always(
  401. function () {
  402. loading();
  403. this.setState({
  404. exportPendingLoading: false,
  405. });
  406. }.bind(this)
  407. );
  408. }
  409. download(fileName) {
  410. window.location.href =
  411. globalConfig.context + "/open/download?fileName=" + fileName;
  412. }
  413. //表格数据处理
  414. handleTabsInfor(infor) {
  415. for (let i = 0; i < infor.length; i++) {
  416. if (!infor[i].key) {
  417. infor[i].key = infor[i].id ? infor[i].id : (infor[i].aid ? infor[i].aid : i)
  418. }
  419. if (infor[i].children) {
  420. for (let c = 0; c < infor[i].children.length; c++) {
  421. infor[i].children[c].key = infor[i].children[c].id;
  422. infor[i].children[c].children = infor[i].children[c].list;
  423. if (infor[i].children[c].aName) { infor[i].children[c].name = infor[i].children[c].aName }
  424. if (infor[i].children[c].aList && Array.isArray(infor[i].children[c].aList) && infor[i].children[c].aList.length) {
  425. if (infor[i].children[c].children && Array.isArray(infor[i].children[c].children)) {
  426. for (let t of infor[i].children[c].aList) {
  427. t.key = t.aid;
  428. t.name = t.aName;
  429. }
  430. infor[i].children[c].children = infor[i].children[c].children.concat(infor[i].children[c].aList);
  431. }
  432. }
  433. this.handleTabsInfor(infor[i].children);
  434. }
  435. }
  436. }
  437. return infor;
  438. }
  439. reset() {
  440. this.setState({
  441. nameSearch: '',
  442. releaseDate: [moment(Date.now() - 777600000).format('YYYY-MM-DD'), moment(Date.now()).format('YYYY-MM-DD')],
  443. }, () => {
  444. this.loadData();
  445. });
  446. };
  447. //获取上级组织
  448. selectSuperId() {
  449. this.state.data = []
  450. $.ajax({
  451. method: "get",
  452. dataType: "json",
  453. crossDomain: false,
  454. url: globalConfig.context + "/api/admin/organization/selectSuperId",
  455. data: {},
  456. success: function (data) {
  457. let theArr = [];
  458. let theId = [];//用于保存上级组织的ID和名称
  459. let thedata = data.data;
  460. if (!thedata) {
  461. if (data.error && data.error.length) {
  462. message.warning(data.error[0].message);
  463. };
  464. thedata = {};
  465. };
  466. for (var i = 0; i < data.data.length; i++) {
  467. let theData = data.data[i];
  468. theArr.push(
  469. <Select.Option value={theData.id} key={theData.id}>{theData.name}</Select.Option>
  470. );
  471. theId.push(
  472. [theData.id, theData.name]
  473. );
  474. };
  475. this.setState({
  476. SuperArr: thedata,
  477. contactsOption: theArr,
  478. theId: theId,
  479. orderStatusOptions: data.data,
  480. });
  481. if (!this.state.superId) {
  482. this.setState({
  483. superId: data.data[0].id
  484. }, () => {
  485. this.loadData();
  486. })
  487. }
  488. }.bind(this),
  489. }).always(function () {
  490. this.setState({
  491. loading: false
  492. });
  493. }.bind(this));
  494. }
  495. changeList(arr) {
  496. const newArr = [];
  497. this.state.columns.forEach(item => {
  498. arr.forEach(val => {
  499. if (val === item.title) {
  500. newArr.push(item);
  501. }
  502. });
  503. });
  504. this.setState({
  505. changeList: newArr
  506. });
  507. }
  508. render() {
  509. return (
  510. <div className="user-content">
  511. <div className="content-title">
  512. <span>部门统计</span>
  513. </div>
  514. <Tabs
  515. defaultActiveKey="1"
  516. className="test">
  517. <TabPane tab="搜索" key="1">
  518. <div className="user-search" style={{ display: 'flex', alignItems: 'center' }}>
  519. <div>
  520. <Select
  521. showSearch
  522. optionFilterProp="children"
  523. placeholder="请选择部门"
  524. style={{ width: 200, marginLeft: 10 }}
  525. value={this.state.superId}
  526. onChange={(e) => { this.setState({ superId: e }) }}
  527. notFoundContent="未获取到上级组织列表">
  528. {this.state.contactsOption}
  529. </Select>
  530. </div>
  531. <Input
  532. placeholder="客户名称"
  533. value={this.state.nameSearch}
  534. style={{ width: 150, marginRight: 10, marginLeft: 10 }}
  535. onChange={(e) => {
  536. this.setState({ nameSearch: e.target.value });
  537. }}
  538. />
  539. <div style={{
  540. marginTop: '10px',
  541. }}>
  542. <RangePicker
  543. allowClear={window.adminData.shiroList.indexOf("11") == -1}
  544. disabledDate={(current) => {//“运营管理”角色只能查看部分时间段(暂时10天)的数据
  545. let iskeep = window.adminData.shiroList.indexOf("11") != -1
  546. return iskeep && current && current.valueOf() < Date.now() - 864000000;
  547. }}
  548. value={[
  549. this.state.releaseDate[0]
  550. ? moment(this.state.releaseDate[0])
  551. : null,
  552. this.state.releaseDate[1]
  553. ? moment(this.state.releaseDate[1])
  554. : null,
  555. ]}
  556. onChange={(data, dataString) => {
  557. this.setState({ releaseDate: dataString });
  558. }}
  559. />
  560. </div>
  561. <Button
  562. type="primary"
  563. style={{ marginLeft: "10px", marginRight: 10 }}
  564. onClick={() => {
  565. this.loadData();
  566. }}
  567. >
  568. 搜索
  569. </Button>
  570. <Button onClick={this.reset}>重置</Button>
  571. </div>
  572. </TabPane>
  573. <TabPane tab="更改表格显示数据" key="2">
  574. <div style={{ marginLeft: 10 }}>
  575. <ChooseList
  576. columns={this.state.columns}
  577. changeFn={this.changeList}
  578. changeList={this.state.changeList}
  579. top={55}
  580. margin={11}
  581. />
  582. </div>
  583. </TabPane>
  584. <TabPane tab="导出" key="3">
  585. <div style={{ float: "left" }}>
  586. <Button
  587. type='primary'
  588. loading={this.state.exportPendingLoading}
  589. onClick={this.exportExec}
  590. style={{ margin: 10 }}
  591. >
  592. 导出excel
  593. </Button>
  594. </div>
  595. </TabPane>
  596. </Tabs>
  597. <div className="patent-table">
  598. <Spin spinning={this.state.loading}>
  599. <Table
  600. size="middle"
  601. scroll={{ y: 550 }}
  602. columns={
  603. this.state.changeList
  604. ? this.state.changeList
  605. : this.state.columns
  606. }
  607. dataSource={this.state.dataSource}
  608. pagination={false}
  609. />
  610. </Spin>
  611. </div>
  612. {this.state.customerVisible ? <CustomerDetails
  613. aid={this.state.aid}
  614. type={this.state.type}
  615. aName={this.state.aName}
  616. startTime={this.state.releaseDate[0]}
  617. endTime={this.state.releaseDate[1]}
  618. visible={this.state.customerVisible}
  619. onCancel={() => {
  620. this.setState({
  621. customerVisible: false,
  622. aid: '',
  623. type: '',
  624. })
  625. }}
  626. /> : <div />}
  627. </div>
  628. )
  629. }
  630. }
  631. export default DepartmentStatistics;