You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

511 lines
12 KiB

2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
2 months ago
  1. <script setup>
  2. import {onMounted, reactive, ref} from 'vue'
  3. import {ElMessage, ElMessageBox} from 'element-plus'
  4. import request from '@/util/http'
  5. import {useAdminStore} from "@/store/index.js";
  6. import {storeToRefs} from "pinia";
  7. import {findMenuById, permissionMapping} from "@/utils/menuTreePermission.js"
  8. /*
  9. ====================工具方法=========================
  10. */
  11. /*
  12. ====================数据===================================
  13. */
  14. // 查询当前登录的信息
  15. const adminData = ref({
  16. id: '',
  17. adminName: ''
  18. })
  19. // 默认 编辑板块是关的
  20. const regeEdit = ref(false)
  21. // 表单引用(根据id获取信息后 将内容存到编辑表单)
  22. const editFormRef = ref(null)
  23. //汇率表格数据
  24. const tableData = ref([])
  25. //搜索对象
  26. const getObj = ref({
  27. pageNum: 1,
  28. pageSize: 10
  29. })
  30. const total = ref(0)
  31. // 编辑方法 表单
  32. const rateEdit = ref({
  33. id: null,
  34. rateName: '',
  35. num: null,
  36. adminId: null,
  37. updateTime: Date.now(),
  38. })
  39. //货币条目
  40. const rateNames = [
  41. {
  42. value: 'USD',
  43. label: 'USD'
  44. },
  45. {
  46. value: 'HKD',
  47. label: 'HKD'
  48. },
  49. {
  50. value: 'THB',
  51. label: 'THB'
  52. },
  53. {
  54. value: 'VND',
  55. label: 'VND'
  56. },
  57. {
  58. value: 'CAD',
  59. label: 'CAD'
  60. },
  61. {
  62. value: 'MYR',
  63. label: 'MYR'
  64. },
  65. {
  66. value: 'KRW',
  67. label: 'KRW'
  68. },
  69. {
  70. value: 'JPY',
  71. label: 'JPY'
  72. },
  73. {
  74. value: 'CNY',
  75. label: 'CNY'
  76. }
  77. ]
  78. // 汇率校验
  79. const checkFreeGoldRadio = function (rule, value, callback) {
  80. if (value == '0' || value == null || value == '') {
  81. callback(new Error('请输入汇率比'))
  82. } else if (value < 0 || isNaN(value)) {
  83. callback(new Error('请输入正确的格式'))
  84. } else {
  85. callback()
  86. }
  87. }
  88. // 定义表单验证规则
  89. const rules = reactive({
  90. // rateName: [{required: true, message: '请选择货币名称', trigger: 'blur'}],
  91. num: [{validator: checkFreeGoldRadio, trigger: 'blur'}],
  92. })
  93. // 表单大小
  94. const formSize = ref('default')
  95. /*
  96. ====================方法=========================
  97. */
  98. // 获取当前登录信息
  99. const getAdminData = async function () {
  100. try {
  101. const result = await request({
  102. url: '/admin/userinfo',
  103. data: {}
  104. })
  105. adminData.value = result
  106. rateEdit.value.adminId = adminData.value.id
  107. console.log('请求成功', result)
  108. } catch (error) {
  109. console.log('请求失败', error)
  110. }
  111. }
  112. // 获取所有汇率 列表
  113. const getAllRate = async function (val) {
  114. try {
  115. // 搜索参数页码赋值
  116. if (typeof val === 'number') {
  117. getObj.value.pageNum = val;
  118. }
  119. // 发送POST请求
  120. const result = await request({
  121. url: '/rate/selectAll',
  122. method: 'POST',
  123. data: {
  124. pageNum: getObj.value.pageNum,
  125. pageSize: getObj.value.pageSize,
  126. }
  127. });
  128. // 将响应结果存储到响应式数据中
  129. console.log('这是汇率列表 请求成功', result);
  130. // 存储表格数据
  131. tableData.value = result.data.list;
  132. // 存储分页总条目
  133. total.value = result.data.total;
  134. } catch (error) {
  135. console.log('请求失败', error);
  136. ElMessage.error('请求失败');
  137. }
  138. }
  139. // 获取分页数据
  140. const handlePageSizeChange = function (val) {
  141. getObj.value.pageSize = val
  142. getAllRate()
  143. }
  144. // 获取分页数据
  145. const handleCurrentChange = function (val) {
  146. getObj.value.pageNum = val
  147. getAllRate()
  148. }
  149. //查询已有的数据(根据id)
  150. const getEditData = async function (row) {
  151. try {
  152. console.log('搜索参数', getObj.value)
  153. // 发送POST请求
  154. const result = await request({
  155. url: '/rate/selectById',
  156. data: {id: row.id}
  157. })
  158. // 将响应结果存储到响应式数据中
  159. console.log('根据id查 请求成功', result)
  160. // 存储表格数据
  161. // rateEdit.value = result.data
  162. // 只赋部分的
  163. rateEdit.value.id = row.id
  164. rateEdit.value.rateName = row.rateName
  165. rateEdit.value.num = row.num
  166. console.log('根据id获取的数据', rateEdit.value)
  167. rateEdit.value.adminId = adminData.value.id
  168. } catch (error) {
  169. console.log('请求失败', error)
  170. }
  171. }
  172. const adminStore = useAdminStore();
  173. const {menuTree} = storeToRefs(adminStore);
  174. // 编辑汇率
  175. const editRate = async function () {
  176. if (findMenuById(menuTree.value, permissionMapping.Exchange_Rate_Modification)) {
  177. // 提交前验证 汇率是否为数字
  178. rateEdit.value.num = parseFloat(rateEdit.value.num);
  179. try {
  180. console.log('搜索参数', rateEdit.value)
  181. // 发送POST请求
  182. const result = await request({
  183. url: '/rate/update',
  184. data: rateEdit.value
  185. })
  186. // 将响应结果存储到响应式数据中
  187. console.log('请求成功', result)
  188. await getAllRate()
  189. } catch (error) {
  190. console.log('请求失败', error)
  191. }
  192. }else {
  193. ElMessage.error('没有权限')
  194. }
  195. }
  196. // 添加前验证
  197. const edit = () => {
  198. editFormRef.value.validate(async (valid) => {
  199. if (valid) {
  200. try {
  201. await ElMessageBox.confirm("确认修改?");
  202. await editRate();
  203. console.log("修改成功");
  204. regeEdit.value = false;
  205. } catch (error) {
  206. console.log("取消修改", error);
  207. regeEdit.value = false;
  208. }
  209. } else {
  210. ElMessage({
  211. type: "error",
  212. message: "请检查输入内容",
  213. });
  214. }
  215. });
  216. };
  217. // 关闭编辑弹窗时重置表单
  218. const cancelEdit = () => {
  219. regeEdit.value = false
  220. }
  221. // 关闭编辑弹窗
  222. const handleEditDialogClose = () => {
  223. if (editFormRef.value) {
  224. getAllRate()
  225. }
  226. }
  227. // 日期格式化
  228. function formatDate(value) {
  229. if (!value) return ''
  230. const date = new Date(value)
  231. const year = date.getFullYear()
  232. const month = (date.getMonth() + 1).toString().padStart(2, '0')
  233. const day = date.getDate().toString().padStart(2, '0')
  234. const hours = date.getHours().toString().padStart(2, '0')
  235. const minutes = date.getMinutes().toString().padStart(2, '0')
  236. const seconds = date.getSeconds().toString().padStart(2, '0')
  237. return `${year}-${month}-${day} ${hours}:${minutes}:${seconds}`
  238. }
  239. // 输入框过滤
  240. function handleInput(value) {
  241. // 检查是否使用了中文句号
  242. if (value.includes('。') || /[^\d.]/g.test(value)) {
  243. ElMessage.warning('请输入正确的符号');
  244. // value = value.replace('。', '.');
  245. }
  246. // 处理多个小数点的情况,保留第一个,移除后续的
  247. const parts = value.split('.');
  248. if (parts.length > 2) {
  249. value = parts[0] + '.' + parts.slice(1).join('');
  250. ElMessage.warning('只能包含一个小数点');
  251. }
  252. // 禁止输入负数
  253. if (value.startsWith('-')) {
  254. ElMessage.warning('不允许输入负数');
  255. value = value.substring(1);
  256. }
  257. // 最多两位小数,超过时才显示提示
  258. if (value.includes('.')) {
  259. const parts = value.split('.')
  260. // 限制整数部分最多六位
  261. if (parts[0].length > 6) {
  262. parts[0] = parts[0].slice(0, 6)
  263. ElMessage.info('整数部分最多允许六位')
  264. }
  265. // 限制小数部分最多两位
  266. if (parts[1].length > 2) {
  267. parts[1] = parts[1].slice(0, 2)
  268. value = parts[0] + '.' + parts[1]
  269. ElMessage.info('最多允许两位小数')
  270. } else {
  271. value = parts[0] + '.' + parts[1]
  272. }
  273. } else {
  274. // 纯整数时限制最多六位
  275. if (value.length > 6) {
  276. value = value.slice(0, 6)
  277. ElMessage.info('整数部分最多允许六位')
  278. }
  279. }
  280. // 小数点前没有数字时补0
  281. if (value.startsWith('.')) {
  282. value = '0' + value;
  283. // 需求没有,注释,先不显示
  284. // ElMessage.info('已自动补充前导0');
  285. }
  286. // 更新表单值
  287. rateEdit.value.num = value;
  288. return value;
  289. }
  290. /*
  291. ====================监听=========================
  292. */
  293. /*
  294. ====================挂载=========================
  295. */
  296. // 挂载
  297. onMounted(async function () {
  298. await getAllRate()
  299. await getAdminData()
  300. })
  301. </script>
  302. <template>
  303. <!-- 这是主页面 -->
  304. <el-row>
  305. <el-col>
  306. <el-card class="box-card" style="max-width: 100%">
  307. <!-- 表格 -->
  308. <div>
  309. <el-table
  310. :data="tableData"
  311. v-if="(tableData.flag = 1)"
  312. >
  313. <el-table-column
  314. type="index"
  315. label="序号"
  316. width="100px"
  317. fixed="left"
  318. >
  319. <template #default="scope">
  320. <span>{{
  321. scope.$index + 1 + (getObj.pageNum - 1) * getObj.pageSize
  322. }}</span>
  323. </template>
  324. </el-table-column>
  325. <el-table-column prop="rateName" label="货币名称" :span="2"/>
  326. <el-table-column prop="num" label="汇率" :span="2">
  327. <template #default="scope">
  328. <p>
  329. {{ scope.row.num }} 1
  330. </p>
  331. </template>
  332. </el-table-column>
  333. <el-table-column prop="updateTime" label="添加时间" :span="3">
  334. <template #default="scope">
  335. <span>{{ formatDate(scope.row.updateTime) }}</span>
  336. </template>
  337. </el-table-column>
  338. <el-table-column label="操作" :span="3">
  339. <template #default="scope">
  340. <el-button
  341. type="text"
  342. @click="
  343. () => {
  344. regeEdit = true
  345. getEditData(scope.row)
  346. }
  347. "
  348. >编辑
  349. </el-button
  350. >
  351. </template>
  352. </el-table-column>
  353. </el-table>
  354. </div>
  355. <!-- 分页 -->
  356. <div class="pagination">
  357. <el-pagination
  358. background
  359. :page-size="getObj.pageSize"
  360. :page-sizes="[5, 10, 20, 50, 100]"
  361. layout="total, sizes, prev, pager, next, jumper"
  362. :total="total"
  363. @size-change="handlePageSizeChange"
  364. @current-change="handleCurrentChange"
  365. ></el-pagination>
  366. </div>
  367. </el-card>
  368. </el-col>
  369. </el-row>
  370. <!-- 这是编辑弹窗 -->
  371. <el-dialog
  372. v-model="regeEdit"
  373. title="修改汇率"
  374. width="500"
  375. :close-on-click-modal="false"
  376. @close="handleEditDialogClose"
  377. >
  378. <template #footer>
  379. <el-form
  380. ref="editFormRef"
  381. style="max-width: 600px"
  382. :model="rateEdit"
  383. :rules="rules"
  384. label-width="auto"
  385. class="demo-ruleForm"
  386. :size="formSize"
  387. status-icon
  388. >
  389. <el-form-item prop="rateName" label="货币名称:">
  390. <el-input
  391. v-model="rateEdit.rateName"
  392. disabled
  393. style="width: 240px"
  394. />
  395. </el-form-item>
  396. <el-form-item prop="num" label="汇率:">
  397. <el-input
  398. v-model="rateEdit.num"
  399. @update:modelValue="handleInput"
  400. style="width: 120px"
  401. />
  402. <span class="unit">:1</span>
  403. <span class="rate-tip">
  404. (提示当前规则每
  405. <span>{{ rateEdit.num }}</span>
  406. <span>{{ rateEdit.rateName }}</span>可兑换 1 新币)
  407. </span>
  408. </el-form-item>
  409. <el-form-item label="提交人:">
  410. <el-input disabled :value="adminData.adminName" style="width: 240px"/>
  411. </el-form-item>
  412. <el-form-item>
  413. <div class="dialog-footer">
  414. <el-button type="primary" @click="edit">修改</el-button>
  415. <el-button @click="cancelEdit">取消</el-button>
  416. </div>
  417. </el-form-item>
  418. </el-form>
  419. </template>
  420. </el-dialog>
  421. </template>
  422. <style scoped>
  423. .pagination {
  424. margin-top: 20px;
  425. display: flex;
  426. }
  427. .box-card {
  428. margin-top: 20px;
  429. }
  430. .button-item {
  431. margin-left: 10px;
  432. }
  433. .add-item {
  434. margin-bottom: 10px;
  435. }
  436. .unit {
  437. margin-left: 10px;
  438. }
  439. .el-card {
  440. padding: 0px;
  441. }
  442. .pagination {
  443. display: flex;
  444. }
  445. .status {
  446. display: flex;
  447. }
  448. .rate-tip {
  449. hyphens: auto;
  450. }
  451. </style>