suggestion-option.tsx 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357
  1. import { defineComponent, onMounted, reactive, ref } from 'vue';
  2. import styles from './suggestion-option.module.less';
  3. import {
  4. NButton,
  5. NForm,
  6. NFormItem,
  7. NInput,
  8. NSelect,
  9. NSpace,
  10. useMessage,
  11. NUpload,
  12. UploadFileInfo,
  13. NImage
  14. } from 'naive-ui';
  15. import { useUserStore } from '/src/store/modules/users';
  16. import bgLine from '../images/bg-line.png';
  17. import chioseAdd from '../images/chioseAdd.png';
  18. import CSelect from '../../CSelect';
  19. import { policy } from '../../upload-file/api';
  20. import suggestClose from '../images/suggestClose.png';
  21. import inFront from '../images/inFront.png';
  22. import inBack from '../images/inBack.png';
  23. import submitBtn from '../images/submitBtn.png';
  24. import sealing from '../images/sealing.png'
  25. import boxBg from '../images/boxBg.png'
  26. import {
  27. addSuggestion,
  28. getSuggestionList,
  29. sysParamConfigPage
  30. } from '../modals/api';
  31. export default defineComponent({
  32. name: 'train-update',
  33. emits: ['close', 'submit'],
  34. setup(props, { emit }) {
  35. const message = useMessage();
  36. const userStore = useUserStore();
  37. const forms = reactive({
  38. suggestionTypeId: null,
  39. clientType: 'TEACHER',
  40. content: '',
  41. attachmentUrls: '',
  42. type: 'APP',
  43. mobileNo: userStore.getUserInfo.phone
  44. });
  45. const state = reactive([]) as any;
  46. const isubmit = ref(false)
  47. const suggestionTypeList = ref([] as any);
  48. const ossUploadUrl = `https://gyt.ks3-cn-beijing.ksyuncs.com/`;
  49. const uploadRef = ref();
  50. const fileListRef = ref<UploadFileInfo[]>([]);
  51. const formsRef = ref();
  52. const btnLoading = ref(false);
  53. const tempFiileBuffer = ref();
  54. const email = ref('');
  55. const phone = ref('');
  56. const onSubmit = async () => {
  57. // if (!forms.suggestionTypeId) {
  58. // message.error('请选择反馈类型');
  59. // return;
  60. // }
  61. // if (!forms.content) {
  62. // message.error('请填写反馈信息');
  63. // return;
  64. // }
  65. formsRef.value?.validate(async (err: any) => {
  66. if (err) {
  67. return;
  68. }
  69. const attachmentUrlsList = fileListRef.value.map((item: any) => {
  70. console.log(item, 'item');
  71. const name = item.name;
  72. // const suffix = name.slice(name.lastIndexOf('.'));
  73. const fileName = `${item.id + name}`;
  74. const url = ossUploadUrl + fileName;
  75. return url;
  76. });
  77. const attachmentUrls = attachmentUrlsList.join(',');
  78. try {
  79. const res = await addSuggestion({ ...forms, attachmentUrls });
  80. isubmit.value = true;
  81. // message.success('提交成功');
  82. setTimeout(()=>{
  83. onReset()
  84. emit('close');
  85. },3000)
  86. } catch (e) {
  87. console.log(e);
  88. }
  89. console.log('onSubmit');
  90. })
  91. };
  92. const onReset = ()=>{
  93. forms.suggestionTypeId=null
  94. forms.clientType='TEACHER'
  95. forms.content= ''
  96. forms.attachmentUrls= ''
  97. forms.type= 'APP'
  98. forms.mobileNo= userStore.getUserInfo.phone
  99. }
  100. const onBeforeUpload = async (options: any) => {
  101. console.log(options, 'onBeforeUpload');
  102. const file = options.file;
  103. // 文件大小
  104. let isLt2M = true;
  105. const size = 2;
  106. if (size) {
  107. isLt2M = file.file.size / 1024 / 1024 < size;
  108. if (!isLt2M) {
  109. message.error(`文件大小不能超过${size}M`);
  110. return false;
  111. }
  112. }
  113. if (!isLt2M) {
  114. return isLt2M;
  115. }
  116. // 是否裁切
  117. try {
  118. btnLoading.value = true;
  119. const name = file.file.name;
  120. const fileName = `${file.id + name}`;
  121. const obj = {
  122. filename: fileName,
  123. bucketName: 'gyt',
  124. postData: {
  125. filename: fileName,
  126. acl: 'public-read',
  127. key: fileName,
  128. unknowValueField: []
  129. }
  130. };
  131. const { data } = await policy(obj);
  132. state.push({
  133. id: file.id,
  134. tempFiileBuffer: file.file,
  135. policy: data.policy,
  136. signature: data.signature,
  137. acl: 'public-read',
  138. key: fileName,
  139. KSSAccessKeyId: data.kssAccessKeyId,
  140. name: fileName
  141. });
  142. } catch {
  143. //
  144. // message.error('上传失败')
  145. btnLoading.value = false;
  146. return false;
  147. }
  148. return true;
  149. };
  150. const onFinish = (options: any) => {
  151. // const url =
  152. const name = options.file.name;
  153. // const suffix = name.slice(name.lastIndexOf('.'));
  154. const fileName = `${options.file.id + name}`;
  155. const url = ossUploadUrl + fileName;
  156. // urlList.value.push(url);
  157. // onFinishAfter(options);
  158. };
  159. const onRemove = async (event: any) => {
  160. console.log(event);
  161. btnLoading.value = false;
  162. };
  163. const getTypeList = async () => {
  164. try {
  165. const res = await getSuggestionList({ rows: 9999, page: 1 });
  166. suggestionTypeList.value = res.data.rows;
  167. } catch (e) {
  168. console.log(e);
  169. }
  170. };
  171. const getPhoneInfo = async () => {
  172. try {
  173. const { data } = await sysParamConfigPage({
  174. page: 1,
  175. rows: 999,
  176. group: 'OTHER'
  177. });
  178. const rows = data.rows || [];
  179. email.value = rows.find((item: any) => {
  180. return item.paramName == 'customer_service_email';
  181. }).paramValue;
  182. phone.value = rows.find((item: any) => {
  183. return item.paramName == 'customer_service_phone';
  184. }).paramValue;
  185. console.log(email.value, phone.value);
  186. } catch (e) {
  187. console.log('请求报错');
  188. console.log(e);
  189. }
  190. };
  191. const imglist = [inFront,inBack,submitBtn,sealing,boxBg]
  192. const loadImg = (imgList:any) => {
  193. for (let i = 0; i < imgList.length; i++) {
  194. const img = new Image()
  195. // let currentSrc = ''
  196. img.src = imgList[i]
  197. img.onload = function (e) {
  198. console.log('加载完毕', e,img.complete );
  199. }
  200. img.onerror = function (e) {
  201. console.log('加载错误', e);
  202. }
  203. }
  204. }
  205. loadImg(imglist)
  206. onMounted(() => {
  207. getTypeList();
  208. getPhoneInfo();
  209. });
  210. return () => (
  211. <div class={styles.suggestOption}>
  212. <div class={[styles.updatePassword,isubmit.value?styles.isAni:'']}>
  213. <div class={[styles.formWrap,isubmit.value?styles.isAni:'']}>
  214. <NImage
  215. class={styles.closeBtn}
  216. src={suggestClose}
  217. previewDisabled onClick={() => {onReset();emit('close')}}></NImage>
  218. <NImage class={styles.bgLine} src={bgLine} previewDisabled></NImage>
  219. <h2 class={styles.formTitle}>意见反馈</h2>
  220. <div class={styles.formWrapInfo}>
  221. <NForm
  222. labelAlign="right"
  223. labelPlacement="left"
  224. labelWidth={'auto'}
  225. ref={formsRef}
  226. model={forms}
  227. requireMarkPlacement="left">
  228. {/* <NFormItem
  229. path="currentClass"
  230. label=""
  231. class={styles.phoneContainer}>
  232. <p class={styles.phone}>{forms.mobile}</p>
  233. </NFormItem> */}
  234. <NFormItem
  235. rule={[
  236. {
  237. required: true,
  238. message: '请选择反馈类型'
  239. }
  240. ]}
  241. path="suggestionTypeId">
  242. <CSelect
  243. class={styles.suggestSelect}
  244. value-field="id"
  245. label-field="name"
  246. style={{ width: '227px!important' }}
  247. {...({
  248. options: suggestionTypeList.value,
  249. placeholder: '反馈类型(必选)',
  250. clearable: true,
  251. inline: true
  252. } as any)}
  253. v-model:value={forms.suggestionTypeId}></CSelect>
  254. </NFormItem>
  255. <NFormItem
  256. path="content"
  257. rule={[
  258. {
  259. required: true,
  260. message: '请输入反馈内容'
  261. }
  262. ]}>
  263. <NInput
  264. class={styles.countInput}
  265. type="textarea"
  266. rows={5}
  267. placeholder={'请输入反馈内容'}
  268. maxlength={200}
  269. resizable={false}
  270. showCount
  271. v-model:value={forms.content}></NInput>
  272. </NFormItem>
  273. <NFormItem>
  274. <NUpload
  275. list-type="image-card"
  276. accept=".jpg,jpeg,.png"
  277. v-model:fileList={fileListRef.value}
  278. ref={uploadRef}
  279. multiple={true}
  280. max={5}
  281. data={(file: any) => {
  282. const item = state.find((c: any) => {
  283. return c.id == file.file.id;
  284. });
  285. const { id, tempFiileBuffer, ...more } = item;
  286. return { ...more };
  287. }}
  288. showPreviewButton
  289. action={ossUploadUrl}
  290. onBeforeUpload={(options: any) => onBeforeUpload(options)}
  291. onRemove={(options: any) => onRemove(options)}
  292. onFinish={(options: any) => onFinish(options)}>
  293. <div class={styles.addInput}>
  294. <NImage previewDisabled src={chioseAdd}></NImage>
  295. <p> 点击上传图片</p>
  296. <p>(最多五张)</p>
  297. </div>
  298. </NUpload>
  299. </NFormItem>
  300. {/* {phone.value || email.value ? (
  301. <NFormItem>
  302. <div class={styles.messageWrap}>
  303. {phone.value ? <p>客服电话:{phone.value}</p> : null}
  304. {email.value ? <p>邮箱:{email.value}</p> : null}
  305. </div>
  306. </NFormItem>
  307. ) : null} */}
  308. {/* <NSpace class={styles.updateBtnGroup}>
  309. <NButton
  310. strong
  311. type="default"
  312. round
  313. onClick={() => emit('close')}>
  314. 取消
  315. </NButton>
  316. <NButton strong type="primary" round onClick={() => onSubmit()}>
  317. 确认
  318. </NButton>
  319. </NSpace> */}
  320. </NForm>
  321. </div>
  322. </div>
  323. <div class={[styles.inBack,isubmit.value?styles.isAni:'']}>
  324. </div>
  325. {/* <div class={styles.inBackBottom}></div> boxBg */}
  326. <NImage src={boxBg} class={styles.inBackBottom} previewDisabled></NImage>
  327. <NImage src={inFront} class={styles.inFront} previewDisabled></NImage>
  328. <NImage src={sealing} class={[styles.sealing,isubmit.value?styles.isAni:'']} previewDisabled></NImage>
  329. {!isubmit.value?<>
  330. <NImage src={submitBtn} onClick={()=>{onSubmit()}} class={styles.submitBtn} previewDisabled></NImage>
  331. <div class={styles.messageWrap}>
  332. {phone.value ? <p>客服电话:{phone.value}</p> : null}
  333. {email.value ? <p>邮箱:{email.value}</p> : null}
  334. </div>
  335. </>:null}
  336. </div>
  337. </div>
  338. );
  339. }
  340. });