index.jsx 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609
  1. import React, { Component } from 'react';
  2. import {
  3. AutoComplete,
  4. Button,
  5. Cascader,
  6. DatePicker,
  7. Icon,
  8. Input,
  9. message,
  10. Modal,
  11. Select,
  12. Spin,
  13. Table,
  14. Tabs,
  15. Tag, Tooltip
  16. } from "antd";
  17. import { citySelect, provinceList } from '@/NewDicProvinceList';
  18. import { getSocialAttribute, ShowModal } from "@/tools.js";
  19. import ShowModalDiv from "@/showModal.jsx";
  20. import moment from "moment";
  21. import $ from "jquery/src/ajax";
  22. import IntentionDetail from "../../NEW/intentionCustomer/intentionDetail/intentionDetail";
  23. import { ChooseList } from "../../../order/orderNew/chooseList";
  24. const { TabPane } = Tabs;
  25. const { RangePicker } = DatePicker;
  26. class CustomerFollow extends Component {
  27. constructor(props) {
  28. super(props);
  29. this.state = {
  30. nameSearch: '',
  31. provinceSearch: undefined,
  32. addressSearch: '',
  33. level: undefined,
  34. releaseDate: [],
  35. selectedRowKeys: [],
  36. sortType: 0,
  37. filteredInfo: null,
  38. sortedInfo: null,
  39. columns: [
  40. {
  41. title: "客户名称",
  42. dataIndex: "name",
  43. key: "name",
  44. render: text => {
  45. return (
  46. <Tooltip title={text}>
  47. <div
  48. // style={{
  49. // maxWidth: '150px',
  50. // overflow: 'hidden',
  51. // textOverflow: "ellipsis",
  52. // whiteSpace: 'nowrap',
  53. // }}
  54. >{text}</div>
  55. </Tooltip>
  56. )
  57. }
  58. },
  59. {
  60. title: "地区",
  61. dataIndex: "locationProvince",
  62. key: "locationProvince",
  63. },
  64. // {
  65. // title: "联系人",
  66. // dataIndex: "contacts",
  67. // key: "contacts",
  68. // },
  69. // {
  70. // title: "联系电话",
  71. // dataIndex: "contactMobile",
  72. // key: "contactMobile",
  73. // },
  74. {
  75. title: "社会性质",
  76. dataIndex: "societyTag",
  77. key: "societyTag",
  78. render: (text) => {
  79. return getSocialAttribute(text);
  80. },
  81. },
  82. {
  83. title: "客户初始时间",
  84. dataIndex: "transferTime",
  85. key: "transferTime",
  86. },
  87. // {
  88. // title: "剩余私有天数",
  89. // dataIndex: "surplusFollowTime",
  90. // key: "surplusFollowTime",
  91. // },
  92. // {
  93. // title: "剩余签单天数",
  94. // dataIndex: "surplusSignTime",
  95. // key: "surplusSignTime",
  96. // },
  97. {
  98. title: "最新跟进时间",
  99. dataIndex: "lastFollowTime",
  100. key: "lastFollowTime",
  101. //0无 1转换倒序 2转换正序
  102. sorter: true,
  103. sortOrder: (this.sortedInfo || {}).columnKey === 'lastFollowTime' && (this.sortedInfo || {}).order,
  104. filteredValue: (this.filteredInfo || {}).lastFollowTime || null,
  105. },
  106. {
  107. title: "客户等级",
  108. dataIndex: "level",
  109. key: "level",
  110. render: (text) => {
  111. if (text === 0) {
  112. return <Tag color="#87d068">一般客户</Tag>;
  113. } else if (text === 1) {
  114. return <Tag color="#D2691E">意向客户</Tag>;
  115. } else if (text === 2) {
  116. return <Tag color="#FF0000">重点客户</Tag>;
  117. } else {
  118. return "";
  119. }
  120. },
  121. },
  122. {
  123. title: "跟进人",
  124. dataIndex: "aName",
  125. key: "aName",
  126. },
  127. {
  128. title: "跟进操作",
  129. dataIndex: "abc",
  130. key: "abc",
  131. render: (text, record, index) => {
  132. return (
  133. <div>
  134. <Button
  135. onClick={(e) => {
  136. e.stopPropagation();
  137. this.setState({
  138. tabsKey: "4",
  139. }, () => {
  140. this.tableRowClick(record)
  141. })
  142. }}
  143. type="primary"
  144. >
  145. {this.props.isEditGuidanceLv ? '指导' : '查看指导'}
  146. </Button>
  147. </div>
  148. );
  149. },
  150. },
  151. ],
  152. provinces: [],
  153. dataSource: [],
  154. categoryArr: [],
  155. modalName: '',
  156. modalVisible: false,
  157. basicState: false,
  158. contactState: false,
  159. rowData: {},
  160. pagination: {
  161. defaultCurrent: 1,
  162. defaultPageSize: 10,
  163. showQuickJumper: true,
  164. pageSize: 10,
  165. onChange: function (page) {
  166. this.loadData(page);
  167. }.bind(this),
  168. showTotal: function (total) {
  169. return "共" + total + "条数据";
  170. },
  171. },
  172. loading: false,
  173. ispage: 1,
  174. guidance: '',
  175. tabsKey: '',
  176. };
  177. this.callback = this.callback.bind(this);
  178. this.loadData = this.loadData.bind(this);
  179. this.reset = this.reset.bind(this);
  180. this.tableRowClick = this.tableRowClick.bind(this);
  181. this.closeDesc = this.closeDesc.bind(this);
  182. this.releaseGuidance = this.releaseGuidance.bind(this);
  183. this.changeList = this.changeList.bind(this);
  184. }
  185. componentDidMount() {
  186. this.loadData();
  187. this.category();
  188. //城市
  189. let Province = [];
  190. provinceList.map(function (item) {
  191. let id = String(item.id);
  192. Province.push(
  193. <Select.Option value={id} key={item.name}>
  194. {item.name}
  195. </Select.Option>
  196. );
  197. });
  198. this.setState({
  199. provinces: Province
  200. })
  201. }
  202. callback() {
  203. }
  204. loadData(pageNo) {
  205. this.setState({
  206. loading: true,
  207. });
  208. let api = '/api/admin/customer/listFollowManagement';
  209. $.ajax({
  210. method: "get",
  211. dataType: "json",
  212. crossDomain: false,
  213. url: globalConfig.context + api,
  214. data: {
  215. pageNo: pageNo || 1,
  216. pageSize: this.state.pagination.pageSize,
  217. level: this.state.level ? this.state.level : undefined,
  218. name: this.state.nameSearch,
  219. province: !this.state.addressSearch.length
  220. ? this.state.provinceSearch
  221. : this.state.addressSearch[0],
  222. city: !this.state.addressSearch.length
  223. ? ""
  224. : this.state.addressSearch[1],
  225. startDate: this.state.releaseDate[0],
  226. endDate: this.state.releaseDate[1],
  227. sortType: this.state.sortType,
  228. },
  229. success: function (data) {
  230. ShowModal(this);
  231. let theArr = [];
  232. if (data.error.length !== 0) {
  233. if (data.error && data.error.length) {
  234. message.warning(data.error[0].message);
  235. }
  236. } else {
  237. for (let i = 0; i < data.data.list.length; i++) {
  238. let thisdata = data.data.list[i];
  239. let diqu =
  240. (thisdata.province == null ? "" : thisdata.province) +
  241. (thisdata.city == null ? "" : "-" + thisdata.city) +
  242. (thisdata.area == null ? "" : "-" + thisdata.area);
  243. thisdata.key = i;
  244. thisdata.id = thisdata.uid;
  245. thisdata.lastFollowTime = thisdata.lastFollowTime && thisdata.lastFollowTime.split(" ")[0];
  246. thisdata.transferTime = thisdata.transferTime && thisdata.transferTime.split(" ")[0];
  247. thisdata.surplusFollowTime = thisdata.surplusFollowTime && thisdata.surplusFollowTime.split(" ")[0];
  248. thisdata.surplusSignTime = thisdata.surplusSignTime && thisdata.surplusSignTime.split(" ")[0];
  249. thisdata.locationProvince = diqu;
  250. theArr.push(thisdata);
  251. }
  252. this.state.pagination.current = data.data.pageNo;
  253. this.state.pagination.total = data.data.totalCount;
  254. if (data.data && data.data.list && !data.data.list.length) {
  255. this.state.pagination.current = 0;
  256. this.state.pagination.total = 0;
  257. }
  258. this.setState({
  259. ispage: data.data.pageNo,
  260. dataSource: theArr,
  261. pagination: this.state.pagination,
  262. });
  263. }
  264. }.bind(this),
  265. }).always(
  266. function () {
  267. this.setState({
  268. loading: false,
  269. });
  270. }.bind(this)
  271. );
  272. };
  273. reset() {
  274. this.setState({
  275. nameSearch: '',
  276. provinceSearch: undefined,
  277. addressSearch: '',
  278. level: undefined,
  279. releaseDate: [],
  280. selectedRowKeys: [],
  281. sortType: 0,
  282. filteredInfo: null,
  283. sortedInfo: null,
  284. }, () => {
  285. this.loadData();
  286. });
  287. };
  288. //品类数据获取
  289. category() {
  290. $.ajax({
  291. method: "get",
  292. dataType: "json",
  293. crossDomain: false,
  294. url: globalConfig.context + "/api/admin/Varieties/getSuperList",
  295. data: {},
  296. success: function (data) {
  297. let thedata = data.data;
  298. let theArr = [];
  299. if (!thedata) {
  300. if (data.error && data.error.length) {
  301. message.warning(data.error[0].message);
  302. }
  303. } else {
  304. thedata.map(function (item, index) {
  305. theArr.push({
  306. value: item.id,
  307. key: item.cname,
  308. });
  309. });
  310. }
  311. this.setState({
  312. categoryArr: theArr,
  313. });
  314. }.bind(this),
  315. });
  316. }
  317. tableRowClick(record) { //key 控制弹窗初始显示第几级
  318. this.setState({
  319. selectedRowKeys: [],
  320. modalVisible: true,
  321. basicState: true,
  322. contactState: true,
  323. modalName: record.name,
  324. rowData: record,
  325. });
  326. };
  327. closeDesc(e, s) {
  328. this.setState({
  329. basicState: e,
  330. visitModul: e,
  331. modalVisible: e,
  332. showDesc: e,
  333. tabsKey: '',
  334. })
  335. if (s) {
  336. this.loadData(this.state.ispage);
  337. }
  338. }
  339. //发布指导意见
  340. releaseGuidance() {
  341. if (!this.state.guidance) {
  342. message.info('指导意见不能为空')
  343. return;
  344. }
  345. this.setState({
  346. loading: true,
  347. });
  348. let _this = this;
  349. $.ajax({
  350. method: "get",
  351. dataType: "json",
  352. crossDomain: false,
  353. url: globalConfig.context + "/api/admin/customer/pushReleaseUser",
  354. data: {
  355. guidance: this.state.guidance,
  356. },
  357. success: function (data) {
  358. let thedata = data.data;
  359. if (!thedata) {
  360. if (data.error && data.error.length) {
  361. message.warning(data.error[0].message);
  362. }
  363. } else {
  364. message.success("发布成功");
  365. _this.loadData(this.state.ispage);
  366. }
  367. }.bind(this),
  368. }).always(
  369. function () {
  370. this.setState({
  371. loading: false,
  372. });
  373. }.bind(this)
  374. );
  375. }
  376. changeList(arr) {
  377. const newArr = [];
  378. this.state.columns.forEach(item => {
  379. arr.forEach(val => {
  380. if (val === item.title) {
  381. newArr.push(item);
  382. }
  383. });
  384. });
  385. this.setState({
  386. changeList: newArr
  387. });
  388. }
  389. render() {
  390. let { sortedInfo, filteredInfo, columns } = this.state;
  391. return (
  392. <div className="user-content">
  393. <ShowModalDiv ShowModal={this.state.showModal} onClose={() => { this.setState({ showModal: false }) }} />
  394. <div className="content-title">
  395. <span>指导意见</span>
  396. </div>
  397. <Tabs defaultActiveKey="1" className="test">
  398. <TabPane tab="搜索" key="1">
  399. <div className="user-search">
  400. <Input
  401. placeholder="客户名称"
  402. value={this.state.nameSearch}
  403. style={{ width: 150, marginRight: 10, marginLeft: 10 }}
  404. onChange={(e) => {
  405. this.setState({ nameSearch: e.target.value });
  406. }}
  407. />
  408. <Select
  409. placeholder="选择地区"
  410. style={{ width: 80 }}
  411. value={this.state.provinceSearch}
  412. onChange={(e) => {
  413. this.setState({ provinceSearch: e });
  414. }}
  415. >
  416. {this.state.provinces}
  417. </Select>
  418. <span style={{ marginRight: "10px" }}>
  419. <Cascader
  420. options={citySelect()}
  421. value={this.state.addressSearch}
  422. placeholder="选择城市"
  423. onChange={(e, pre) => {
  424. this.setState({ addressSearch: e });
  425. }}
  426. />
  427. </span>
  428. <Select
  429. style={{ width: 120 }}
  430. value={this.state.level}
  431. onChange={(e) => {
  432. this.setState({ level: e });
  433. }}
  434. placeholder="选择客户等级"
  435. >
  436. <Select.Option value="0">一般客户</Select.Option>
  437. <Select.Option value="1">意向客户</Select.Option>
  438. <Select.Option value="2">重点客户</Select.Option>
  439. </Select>
  440. <RangePicker
  441. value={[
  442. this.state.releaseDate[0]
  443. ? moment(this.state.releaseDate[0])
  444. : null,
  445. this.state.releaseDate[1]
  446. ? moment(this.state.releaseDate[1])
  447. : null,
  448. ]}
  449. onChange={(data, dataString) => {
  450. this.setState({ releaseDate: dataString });
  451. }}
  452. />
  453. <Button
  454. type="primary"
  455. style={{ marginLeft: "10px", marginRight: 10 }}
  456. onClick={() => {
  457. this.loadData();
  458. }}
  459. >
  460. 搜索
  461. </Button>
  462. <Button onClick={this.reset}>重置</Button>
  463. </div>
  464. </TabPane>
  465. <TabPane tab="更改表格显示数据" key="2">
  466. <div style={{ marginLeft: 10 }}>
  467. <ChooseList
  468. columns={columns}
  469. changeFn={this.changeList}
  470. changeList={this.state.changeList}
  471. top={55}
  472. margin={11}
  473. />
  474. </div>
  475. </TabPane>
  476. </Tabs>
  477. <div className="patent-table">
  478. <Spin spinning={this.state.loading}>
  479. <Table
  480. columns={
  481. this.state.changeList
  482. ? this.state.changeList
  483. : columns
  484. }
  485. dataSource={this.state.dataSource}
  486. pagination={this.state.pagination}
  487. onRowClick={this.tableRowClick}
  488. style={{
  489. cursor: 'pointer',
  490. }}
  491. onChange={(pagination, filters, sorter) => {
  492. //0 正序 1倒序
  493. if (sorter.order === 'ascend') { //倒序
  494. this.setState({
  495. sortType: 1
  496. }, () => {
  497. this.loadData(pagination.current)
  498. });
  499. } else if (sorter.order === 'descend') { //正序
  500. this.setState({
  501. sortType: 0
  502. }, () => {
  503. this.loadData(pagination.current)
  504. });
  505. } else if (typeof sorter.order === 'undefined') { //正常
  506. this.setState({
  507. sortType: 0
  508. }, () => {
  509. this.loadData(pagination.current)
  510. });
  511. }
  512. this.setState({
  513. filteredInfo: filters,
  514. sortedInfo: sorter,
  515. });
  516. }
  517. }
  518. />
  519. </Spin>
  520. </div>
  521. <IntentionDetail
  522. isGuidanceLv={this.props.isGuidanceLv}
  523. isEditGuidanceLv={this.props.isEditGuidanceLv}
  524. categoryArr={this.state.categoryArr}
  525. detailApi={this.props.detailApi}
  526. IntentionData={this.state.rowData}
  527. modalVisible={this.state.modalVisible}
  528. tabsKey={this.state.tabsKey}
  529. name={this.state.modalName}
  530. closeDesc={this.closeDesc}
  531. basicState={this.state.basicState}
  532. contactState={this.state.contactState}
  533. />
  534. <Modal
  535. maskClosable={false}
  536. className="customeDetails"
  537. title="指导意见"
  538. width='500px'
  539. visible={this.state.guidanceVisible}
  540. onOk={() => {
  541. this.setState({
  542. guidanceVisible: false,
  543. guidance: '',
  544. }, () => {
  545. this.loadData(this.state.ispage);
  546. })
  547. }}
  548. onCancel={() => {
  549. this.setState({
  550. guidanceVisible: false,
  551. guidance: '',
  552. }, () => {
  553. this.loadData(this.state.ispage);
  554. })
  555. }}
  556. footer=''
  557. >
  558. <Spin spinning={this.state.loading}>
  559. <div style={{
  560. display: 'flex',
  561. flexFlow: 'column',
  562. }}>
  563. <Input
  564. style={{ width: '400px', height: '50px' }}
  565. placeholder="请输入指导意见"
  566. type={'textarea'}
  567. onChange={(e) => {
  568. this.setState({
  569. guidance: e.target.value,
  570. })
  571. }}
  572. />
  573. <Button
  574. type="primary"
  575. style={{ marginTop: "10px", marginBottom: '10px' }}
  576. onClick={() => {
  577. this.releaseGuidance();
  578. }}
  579. >
  580. 确定
  581. </Button>
  582. </div>
  583. </Spin>
  584. </Modal>
  585. </div>
  586. )
  587. }
  588. }
  589. export default CustomerFollow;