index.jsx 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141
  1. import { Input, Button, Spin, message } from 'antd'
  2. import React, { useState, useEffect, useRef } from 'react'
  3. import styles from '@/pages/Customer/Company/components/ConnectCompany/index.less'
  4. import { SearchOutlined, CloseOutlined } from '@ant-design/icons'
  5. import { useDebounceFn } from 'ahooks'
  6. import { useDispatch } from 'dva'
  7. import { apiAddClient, linkBusiWithClient, queryClient } from '@/services/customer'
  8. import consts from '@/basic/consts'
  9. import { formatValues } from '@/components/LazyCascader'
  10. import AddClient from '../AddClient'
  11. const ConnectClient = ({ dataId, onSelect, preUrl }) => {
  12. const dispatch = useDispatch()
  13. const scrollRef = useRef()
  14. const [state, setState] = useState({
  15. laoding: true,
  16. client: [],
  17. searchVal: '',
  18. current: 1,
  19. pageSize: 10,
  20. total: 0
  21. })
  22. const initData = async params => {
  23. const { data: { client, total } = { client: [], total: 0 }, code = -1 } = await queryClient(
  24. params
  25. )
  26. if (code === consts.RET_CODE.SUCCESS) {
  27. if (params?.current === 1) {
  28. scrollRef.current?.scrollTo({ top: 0 })
  29. // 请求的是第一页或者搜索框
  30. setState({ ...state, client, total, laoding: false, searchVal: params?.search })
  31. } else {
  32. setState({
  33. ...state,
  34. client: state.client.concat(client),
  35. total,
  36. searchVal: params?.search,
  37. laoding: false,
  38. current: params?.current || 1
  39. })
  40. }
  41. }
  42. }
  43. useEffect(() => {
  44. initData({ current: 1, pageSize: 10 })
  45. }, [])
  46. const onChange = e => {
  47. const { value = '' } = e.target || e.currentTarget
  48. initData({ search: value, current: 1, pageSize: state.pageSize })
  49. }
  50. const { run: handleInputChange } = useDebounceFn(onChange)
  51. const closeModal = () => {
  52. dispatch({
  53. type: 'single/changeModal'
  54. })
  55. }
  56. const addConfirm = async values => {
  57. const payload = formatValues(values)
  58. const { code = -1, msg = '新增成功' } = await apiAddClient(payload)
  59. if (code === consts.RET_CODE.SUCCESS) {
  60. if (Object.hasOwnProperty.call(values, `${preUrl}Id`)) {
  61. message.success('新增成功并且绑定成功')
  62. onSelect(values.name)
  63. closeModal()
  64. } else {
  65. message.success(msg)
  66. initData()
  67. }
  68. }
  69. }
  70. // 商机关联联系人
  71. const connectClient = async clientId => {
  72. const { code = -1 } = await linkBusiWithClient({ id: dataId, clientId })
  73. if (code === consts.RET_CODE.SUCCESS) {
  74. onSelect()
  75. closeModal()
  76. }
  77. }
  78. const handleListScroll = () => {
  79. // 未滚动到底部
  80. if (
  81. scrollRef.current.scrollHeight - scrollRef.current.clientHeight <=
  82. scrollRef.current.scrollTop
  83. ) {
  84. // 已到底部
  85. state.current * state.pageSize < state.total &&
  86. initData({ current: state.current + 1, pageSize: state.pageSize, search: state.searchVal })
  87. }
  88. }
  89. // const { run: listScroller } = useThrottleFn(handleListScroll)
  90. return (
  91. <div className={['ant-modal-content', styles.modalContainer].join(' ')}>
  92. <div className={styles.modalHeader}>
  93. <Input
  94. prefix={<SearchOutlined />}
  95. className={styles.inputSearch}
  96. placeholder="输入联系人名称搜索"
  97. onChange={handleInputChange}
  98. />
  99. <span className={styles.closeIcon}>
  100. <CloseOutlined onClick={closeModal} />
  101. </span>
  102. </div>
  103. <div className={styles.modalContent} ref={scrollRef} onScroll={handleListScroll}>
  104. <Spin spinning={state.laoding}>
  105. {state.client.map(item => (
  106. <div key={item.id} className={styles.card}>
  107. <span className="w-1/6">{item.clientName}</span>
  108. <span className="w-1/6">{item.position}</span>
  109. <span className="w-1/6">{item.telephone}</span>
  110. <span className="w-1/2 flex justify-between">
  111. <span>{item.companyName}</span>
  112. <Button type="primary" size="small" onClick={() => connectClient(item.id)}>
  113. 选择ta
  114. </Button>
  115. </span>
  116. </div>
  117. ))}
  118. </Spin>
  119. </div>
  120. <div className={styles.modalFooter}>
  121. <AddClient
  122. onConfirm={addConfirm}
  123. dataId={dataId}
  124. dataType={preUrl}
  125. buttonProps={{ ghost: true }}
  126. btnTitle={'添加并关联到新联系人'}
  127. />
  128. </div>
  129. </div>
  130. )
  131. }
  132. export default ConnectClient