signCustomer.jsx 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686
  1. import React from 'react';
  2. import {
  3. Radio,
  4. Icon,
  5. Button,
  6. AutoComplete,
  7. Cascader,
  8. Input,
  9. Select,
  10. Tabs,
  11. Spin,
  12. Popconfirm,
  13. Table,
  14. Switch,
  15. message,
  16. DatePicker,
  17. Upload,
  18. Form,
  19. Modal
  20. } from 'antd';
  21. import ajax from 'jquery/src/ajax/xhr.js';
  22. import $ from 'jquery/src/ajax';
  23. import moment from 'moment';
  24. import { citySelect, provinceList } from '@/NewDicProvinceList';
  25. import { socialAttribute, industry, auditStatusL, lvl, currentMember } from '@/dataDic.js';
  26. import { getSocialAttribute, beforeUploadFile, ShowModal } from "@/tools.js";
  27. import FollowDetail from './followDetail.jsx'
  28. import ShowModalDiv from "@/showModal.jsx";
  29. import ZhuanjiaoDetail from "@/zhuanjiaoDetail.jsx";
  30. import IntentionDetail from './intentionDetail/intentionDetail.jsx'
  31. import './customer.less';
  32. import {ChooseList} from "../../../order/orderNew/chooseList";
  33. const {TabPane} = Tabs
  34. const IntentionCustomer = Form.create()(React.createClass({
  35. loadData(pageNo, apiUrl) {
  36. this.setState({
  37. visitModul:false,
  38. loading: true,
  39. ispage:pageNo,
  40. modalVisible:false
  41. });
  42. let api=apiUrl?apiUrl:this.props.ApiUrl;
  43. $.ajax({
  44. method: "post",
  45. dataType: "json",
  46. crossDomain: false,
  47. url: globalConfig.context + api,
  48. data: {
  49. pageNo: pageNo || 1,
  50. pageSize: this.state.pagination.pageSize,
  51. name: this.state.nameSearch,
  52. province: !(this.state.addressSearch).length ? this.state.provinceSearch : this.state.addressSearch[0],
  53. city: !(this.state.addressSearch).length ? '' : this.state.addressSearch[1],
  54. startDate: this.state.releaseDate[0],
  55. endDate: this.state.releaseDate[1],
  56. },
  57. success: function(data) {
  58. ShowModal(this);
  59. let theArr = [];
  60. if(data.error.length || data.data.list == "") {
  61. if(data.error && data.error.length) {
  62. message.warning(data.error[0].message);
  63. };
  64. } else {
  65. for(let i = 0; i < data.data.list.length; i++) {
  66. let thisdata = data.data.list[i];
  67. let diqu=(thisdata.province==null?"":thisdata.province)+(thisdata.city==null?"":"-"+thisdata.city)+(thisdata.area==null?"":"-"+thisdata.area);
  68. thisdata.key = i;
  69. thisdata.id = thisdata.uid;
  70. thisdata.transferTime = thisdata.transferTime && thisdata.transferTime.split(" ")[0];
  71. thisdata.lastSignTime = thisdata.lastSignTime && thisdata.lastSignTime.split(" ")[0];
  72. thisdata.lastFollowTime = thisdata.lastFollowTime && thisdata.lastFollowTime.split(" ")[0];
  73. locationProvince : diqu
  74. theArr.push(thisdata);
  75. };
  76. this.state.pagination.current = data.data.pageNo;
  77. this.state.pagination.total = data.data.totalCount;
  78. };
  79. if(data.data&&data.data.list&&!data.data.list.length){
  80. this.state.pagination.current=0
  81. this.state.pagination.total=0
  82. };
  83. this.setState({
  84. dataSource: theArr,
  85. pagination: this.state.pagination,
  86. selectedRowKeys:[]
  87. });
  88. }.bind(this),
  89. }).always(function() {
  90. this.setState({
  91. loading: false
  92. });
  93. }.bind(this));
  94. },
  95. getInitialState() {
  96. return {
  97. addressSearch: [],
  98. orgCodeUrl: [],
  99. companyLogoUrl: [],
  100. visible: false,
  101. searchMore: true,
  102. releaseDate: [],
  103. visitModul: false,
  104. keys: false,
  105. detailApi: "",
  106. followData: {},
  107. selectedRowKeys: [],
  108. selectedRowKey: [],
  109. selectedRows: [],
  110. loading: false,
  111. defaultActiveKey: '',
  112. modalVisible: false,
  113. pagination: {
  114. defaultCurrent: 1,
  115. defaultPageSize: 10,
  116. showQuickJumper: true,
  117. pageSize: 10,
  118. onChange: function (page) {
  119. this.loadData(page);
  120. }.bind(this),
  121. showTotal: function (total) {
  122. return "共" + total + "条数据";
  123. },
  124. },
  125. columns: [
  126. {
  127. title: "客户名称",
  128. dataIndex: "name",
  129. key: "name",
  130. },
  131. {
  132. title: "地区",
  133. dataIndex: "locationProvince",
  134. key: "locationProvince",
  135. },
  136. {
  137. title: "最新签单日期",
  138. dataIndex: "transferTime",
  139. key: "transferTime",
  140. },
  141. // {
  142. // title: "最新跟进日期",
  143. // dataIndex: "lastFollowTime",
  144. // key: "lastFollowTime",
  145. // },
  146. // {
  147. // title: "剩余私有天数",
  148. // dataIndex: "surplusFollowTime",
  149. // key: "surplusFollowTime",
  150. // },
  151. // {
  152. // title: "剩余签单天数",
  153. // dataIndex: "surplusSignTime",
  154. // key: "surplusSignTime",
  155. // },
  156. // {
  157. // title: "联系人",
  158. // dataIndex: "contacts",
  159. // key: "contacts",
  160. // },
  161. // {
  162. // title: "联系电话",
  163. // dataIndex: "contactMobile",
  164. // key: "contactMobile",
  165. // },
  166. {
  167. title: "社会属性",
  168. dataIndex: "societyTag",
  169. key: "societyTag",
  170. render: (text) => {
  171. return getSocialAttribute(text);
  172. },
  173. },
  174. {
  175. title: "操作",
  176. dataIndex: "abc",
  177. key: "abc",
  178. render: (text, record, index) => {
  179. return (
  180. <div>
  181. <Button
  182. onClick={(e) => {
  183. e.stopPropagation(), this.visit(record);
  184. }}
  185. type="primary"
  186. >
  187. 客户跟进
  188. </Button>
  189. <Button
  190. style={{ marginLeft: 10 }}
  191. onClick={(e) => {
  192. e.stopPropagation(), this.zhuanjiaoDetail(record);
  193. }}
  194. type="primary"
  195. >
  196. 转交记录
  197. </Button>
  198. <Button
  199. style={{ marginLeft: 10 }}
  200. type="primary"
  201. onClick={(e)=>{
  202. e.stopPropagation();
  203. this.setState({
  204. defaultActiveKey: '6'
  205. },()=>{
  206. this.tableRowClick(record);
  207. })
  208. }}
  209. >
  210. 转交业务
  211. </Button>
  212. </div>
  213. );
  214. },
  215. },
  216. ],
  217. data: [],
  218. dataSource: [],
  219. };
  220. },
  221. zhuanjiaoDetail(record) {
  222. this.setState({
  223. zhuanjiaoVisible: true,
  224. zhuanjiaoId: record.id
  225. })
  226. },
  227. zhuanjiaoDetailCancel() {
  228. this.setState({
  229. zhuanjiaoVisible: false
  230. })
  231. },
  232. //进入新增拜访记录
  233. visit(e) {
  234. this.setState({
  235. followData:e,
  236. visitModul:true,
  237. modalVisible:false
  238. })
  239. },
  240. //列表删除功能
  241. delectRow() {
  242. let deletedIds;
  243. for(let idx = 0; idx < this.state.selectedRows.length; idx++) {
  244. let rowItem = this.state.selectedRows[idx];
  245. if(rowItem.id) {
  246. deletedIds = rowItem.id;
  247. };
  248. };
  249. this.setState({
  250. loading: true,
  251. selectedRowKeys: [],
  252. });
  253. $.ajax({
  254. method: "get",
  255. dataType: "json",
  256. crossDomain: false,
  257. url: globalConfig.context + "/api/admin/customer/deleteCustomer",
  258. data: {
  259. uid: deletedIds, //删除的ID
  260. }
  261. }).done(function(data) {
  262. if(!data.error.length) {
  263. message.success('删除成功!');
  264. this.setState({
  265. loading: false,
  266. });
  267. } else {
  268. message.warning(data.error[0].message);
  269. };
  270. this.loadData(this.state.ispage);
  271. }.bind(this));
  272. },
  273. componentWillMount() {
  274. //城市
  275. let Province = [];
  276. provinceList.map(function(item) {
  277. var id = String(item.id)
  278. Province.push(
  279. <Select.Option value={id} key={item.name}>{item.name}</Select.Option>
  280. )
  281. });
  282. //行业
  283. let intentionalArr = [];
  284. industry.map(function(item) {
  285. intentionalArr.push(
  286. <Select.Option value={item.value} key={item.key}>{item.key}</Select.Option>
  287. )
  288. });
  289. this.state.Provinces = Province;
  290. this.state.intentionalOption = intentionalArr;
  291. this.loadData();
  292. },
  293. closeDesc(e, s) {
  294. this.state.basicState=e
  295. this.state.visitModul=e;
  296. this.state.modalVisible=e;
  297. this.state.showDesc = e;
  298. this.setState({
  299. defaultActiveKey:''
  300. })
  301. if(s) {
  302. this.loadData(this.state.ispage);
  303. };
  304. },
  305. search() {
  306. this.loadData();
  307. },
  308. reset() {
  309. this.state.nameSearch = '';
  310. this.state.addressSearch = [];
  311. this.state.provinceSearch = undefined;
  312. this.state.citySearch = undefined;
  313. this.state.releaseDate[0] = undefined;
  314. this.state.releaseDate[1] = undefined;
  315. this.loadData();
  316. },
  317. searchSwitch() {
  318. this.setState({
  319. visitModul:false,
  320. searchMore: !this.state.searchMore
  321. });
  322. },
  323. //整行点击
  324. tableRowClick(record) {
  325. this.state.visitModul=false;
  326. this.state.RowData = record;
  327. this.setState({
  328. // selectedRowKeys: [],
  329. modalVisible:true,
  330. basicState:true,
  331. contactState:true,
  332. modalName: record.name
  333. })
  334. },
  335. //指定转交人自动补全
  336. supervisor(e){
  337. $.ajax({
  338. method: "get",
  339. dataType: "json",
  340. crossDomain: false,
  341. url: globalConfig.context + "/api/admin/customer/listAdminByName",
  342. data:{
  343. adminName:e
  344. },
  345. success: function (data) {
  346. let thedata=data.data;
  347. if (!thedata) {
  348. if (data.error && data.error.length) {
  349. message.warning(data.error[0].message);
  350. };
  351. thedata = {};
  352. };
  353. this.setState({
  354. customerArr:thedata,
  355. });
  356. }.bind(this),
  357. }).always(function () {
  358. this.setState({
  359. loading: false
  360. });
  361. }.bind(this));
  362. },
  363. componentWillReceiveProps(nextProps) {
  364. if(nextProps.ApiUrl!=this.props.ApiUrl) {
  365. if(!this.state.searchMore){
  366. this.state.searchMore=true
  367. }
  368. this.state.nameSearch = '';
  369. this.state.addressSearch = [];
  370. this.state.provinceSearch = undefined;
  371. this.state.citySearch = undefined;
  372. this.state.releaseDate[0] = undefined;
  373. this.state.releaseDate[1] = undefined;
  374. this.loadData(null,nextProps.ApiUrl);
  375. };
  376. },
  377. changeList(arr) {
  378. const newArr = [];
  379. this.state.columns.forEach(item => {
  380. arr.forEach(val => {
  381. if (val === item.title) {
  382. newArr.push(item);
  383. }
  384. });
  385. });
  386. this.setState({
  387. changeList: newArr
  388. });
  389. },
  390. //上级主管输入框失去焦点是判断客户是否存在
  391. selectAuto(value, options) {
  392. this.setState({
  393. auto: value,
  394. });
  395. },
  396. //值改变时请求客户名称
  397. httpChange(e) {
  398. if (e.length >= 1) {
  399. this.supervisor(e);
  400. }
  401. this.setState({
  402. auto: e,
  403. });
  404. },
  405. showConfirm(fn, record) {
  406. Modal.confirm({
  407. title: "提示",
  408. content: (
  409. <span style={{ color: "red" }}>
  410. 确定要转交以下客户吗?
  411. {
  412. this.state.selectedRows.map((value,index)=>(
  413. <div key={index} style={{marginTop:'5px',color: "#000"}}>
  414. {value.name}
  415. </div>
  416. ))
  417. }
  418. </span>
  419. ),
  420. onOk() {
  421. fn(record);
  422. },
  423. onCancel() {},
  424. });
  425. },
  426. //转交
  427. changeAssigner() {
  428. if (this.state.theTypes) {
  429. let changeIds = '';
  430. let oldAid = '';
  431. for (let idx = 0; idx < this.state.selectedRows.length; idx++) {
  432. let rowItem = this.state.selectedRows[idx];
  433. if (rowItem.id) {
  434. oldAid = rowItem.aid;
  435. changeIds = this.state.selectedRows.length-1 === idx ? changeIds +rowItem.id : changeIds + rowItem.id + ',' ;
  436. }
  437. }
  438. $.ajax({
  439. method: "get",
  440. dataType: "json",
  441. crossDomain: false,
  442. url: globalConfig.context + "/api/admin/customer/transferToOther",
  443. data: {
  444. uid: changeIds, //这一行数据的ID
  445. aid: this.state.theTypes, //指定转交人的ID
  446. oldAid: oldAid,
  447. operatorType:4
  448. },
  449. }).done(
  450. function (data) {
  451. if (!data.error.length) {
  452. message.success("转交成功!");
  453. this.setState({
  454. auto: "",
  455. loading: false,
  456. selectedRowKeys: [],
  457. });
  458. } else {
  459. message.warning(data.error[0].message);
  460. }
  461. this.loadData(
  462. Math.min(
  463. this.state.ispage == undefined ? 1 : this.state.ispage,
  464. Math.ceil((this.state.pagination.total - 1) / 10)
  465. )
  466. );
  467. }.bind(this)
  468. );
  469. } else {
  470. message.warning("请输入转交人姓名");
  471. }
  472. },
  473. blurChange(e) {
  474. let theType = "";
  475. let contactLists = this.state.customerArr || [];
  476. if (e) {
  477. contactLists.map(function (item) {
  478. if (item.name == e.toString()) {
  479. theType = item.id;
  480. }
  481. });
  482. }
  483. this.setState({
  484. theTypes: theType,
  485. });
  486. },
  487. render() {
  488. const rowSelection = {
  489. selectedRowKeys: this.state.selectedRowKeys,
  490. onChange: (selectedRowKeys, selectedRows) => {
  491. this.setState({
  492. modalVisible:false,
  493. selectedRows: selectedRows,
  494. selectedRowKeys: selectedRowKeys
  495. });
  496. },
  497. onSelect: (recordt, selected, selectedRows) => {
  498. this.setState({
  499. modalVisible:false,
  500. recordt: recordt.id
  501. })
  502. },
  503. };
  504. const hasSelected = this.state.selectedRowKeys.length > 0;
  505. const { RangePicker } = DatePicker;
  506. const dataSources=this.state.customerArr || [];
  507. const options = dataSources.map((group) =>
  508. <Select.Option key={group.id} value={group.name}>{group.name}</Select.Option>
  509. )
  510. const intentionState = this.props.intentionState ||'';
  511. return (
  512. <div className="user-content">
  513. <ShowModalDiv ShowModal={this.state.showModal} />
  514. {this.state.zhuanjiaoVisible ? (
  515. <ZhuanjiaoDetail
  516. cancel={this.zhuanjiaoDetailCancel}
  517. visible={this.state.zhuanjiaoVisible}
  518. type={1}
  519. id={this.state.zhuanjiaoId}
  520. />
  521. ) : (
  522. ""
  523. )}
  524. <div className="content-title">
  525. <span>{!intentionState ? "签单客户" : "签单客户"}</span>
  526. </div>
  527. <Tabs defaultActiveKey="1" className="test">
  528. <TabPane tab="搜索" key="1">
  529. <div className="user-search">
  530. <Input
  531. placeholder="客户名称"
  532. value={this.state.nameSearch}
  533. onChange={(e) => {
  534. this.setState({ nameSearch: e.target.value });
  535. }}
  536. />
  537. <Select
  538. placeholder="省"
  539. style={{ width: 80 }}
  540. value={this.state.provinceSearch}
  541. onChange={(e) => {
  542. this.setState({ provinceSearch: e });
  543. }}
  544. >
  545. {this.state.Provinces}
  546. </Select>
  547. <span style={{ marginRight: "10px" }}>
  548. <Cascader
  549. options={citySelect()}
  550. value={this.state.addressSearch}
  551. placeholder="选择城市"
  552. onChange={(e, pre) => {
  553. this.setState({ addressSearch: e });
  554. }}
  555. />
  556. </span>
  557. {/* <div className="clearfix" style={{ marginTop: "5px" }}>
  558. <div
  559. className="search-more"
  560. style={this.state.searchMore ? { display: "none" } : {}}
  561. > */}
  562. <span>签单时间:</span>
  563. <RangePicker
  564. value={[
  565. this.state.releaseDate[0]
  566. ? moment(this.state.releaseDate[0])
  567. : null,
  568. this.state.releaseDate[1]
  569. ? moment(this.state.releaseDate[1])
  570. : null,
  571. ]}
  572. onChange={(data, dataString) => {
  573. this.setState({ releaseDate: dataString });
  574. }}
  575. />
  576. {/* </div>
  577. </div> */}
  578. <Button
  579. type="primary"
  580. onClick={this.search}
  581. style={{ marginLeft: 10 }}
  582. >
  583. 搜索
  584. </Button>
  585. <Button onClick={this.reset}>重置</Button>
  586. {/* {adminData.isSuperAdmin?<Popconfirm title="是否删除?" onConfirm={this.delectRow} okText="是" cancelText="否">
  587. <Button type="danger" style={{marginLeft:'10px'}}
  588. disabled={!hasSelected}
  589. >删除<Icon type="minus" />
  590. </Button>
  591. </Popconfirm>:''
  592. }*/}
  593. {/* <span style={{ marginLeft: "10px", marginRight: "20px" }}>
  594. 更多搜索
  595. <Switch
  596. checked={!this.state.searchMore}
  597. onChange={this.searchSwitch}
  598. />
  599. </span> */}
  600. </div>
  601. </TabPane>
  602. <TabPane tab="操作" key="2">
  603. <div className="user-search">
  604. <AutoComplete
  605. className="certain-category-search"
  606. dropdownClassName="certain-category-search-dropdown"
  607. dropdownMatchSelectWidth={false}
  608. dropdownStyle={{ width: 120 }}
  609. style={{ width: "120px" }}
  610. dataSource={options}
  611. placeholder="输入转交人姓名"
  612. value={this.state.auto}
  613. onChange={this.httpChange}
  614. filterOption={true}
  615. onBlur={this.blurChange}
  616. onSelect={this.selectAuto}
  617. disabled={!hasSelected}
  618. >
  619. <Input />
  620. </AutoComplete>
  621. <Button
  622. type="primary"
  623. onClick={(e) => {
  624. e.stopPropagation();
  625. this.showConfirm(this.changeAssigner);
  626. }}
  627. disabled={!hasSelected}
  628. style={{ marginRight: 10 }}
  629. >
  630. 转交客户
  631. </Button>
  632. </div>
  633. </TabPane>
  634. <TabPane tab="更改表格显示数据" key="3">
  635. <div style={{ marginLeft: 10 }}>
  636. <ChooseList
  637. columns={this.state.columns}
  638. changeFn={this.changeList}
  639. changeList={this.state.changeList}
  640. top={55}
  641. margin={11}
  642. />
  643. </div>
  644. </TabPane>
  645. </Tabs>
  646. <div className="patent-table">
  647. <Spin spinning={this.state.loading}>
  648. <Table
  649. size="middle"
  650. columns={
  651. this.state.changeList
  652. ? this.state.changeList
  653. : this.state.columns
  654. }
  655. dataSource={this.state.dataSource}
  656. rowSelection={rowSelection}
  657. pagination={this.state.pagination}
  658. onRowClick={this.tableRowClick}
  659. />
  660. </Spin>
  661. </div>
  662. <FollowDetail
  663. followData={this.state.followData}
  664. visitModul={this.state.visitModul}
  665. closeDesc={this.closeDesc}
  666. loadData={this.loadData}
  667. />
  668. <IntentionDetail
  669. detailApi={this.props.detailApi}
  670. IntentionData={this.state.RowData}
  671. loadData={this.loadData}
  672. modalVisible={this.state.modalVisible}
  673. defaultActiveKey={this.state.defaultActiveKey}
  674. name={this.state.modalName}
  675. closeDesc={this.closeDesc}
  676. basicState={this.state.basicState}
  677. contactState={this.state.contactState}
  678. />
  679. </div>
  680. );
  681. }
  682. }));
  683. export default IntentionCustomer;