typeEdit.vue 8.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346
  1. <script>
  2. import axios from "axios";
  3. import {rCode} from "../map/rcodeMap_esm";
  4. import {handle} from "../until/handle";
  5. import InputRow from "./public/form/inputRow.vue";
  6. import RoundedTitle from "./public/roundedTitle.vue";
  7. import dbField_esm, {db_base} from "../map/dbField_esm";
  8. import {FormVerify} from "kind-form-verify";
  9. import {fieldCheck} from "../until/form/fieldVerify";
  10. import Pop from "./public/pop.vue";
  11. import PopCard from "./public/popCard.vue";
  12. import ImageTable from "./public/imageTable.vue";
  13. import {urlAddParam} from "@/until/url";
  14. const emptyType = {
  15. type_name: '',
  16. type_logo: '',
  17. type_sort: 0,
  18. type_key: ''
  19. }
  20. let formVerify = null;
  21. export default {
  22. name: 'typeEdit',
  23. components: {ImageTable, PopCard, Pop, RoundedTitle, InputRow},
  24. props: {
  25. },
  26. data () {
  27. return {
  28. isInitialized: false,
  29. title: '编辑类型',
  30. typeId: '',
  31. formType: {
  32. type_name: {
  33. val: "",
  34. oldVal: "",
  35. init: "",
  36. msg: "",
  37. state: 0,
  38. },
  39. type_logo: {
  40. val: '',
  41. init: '',
  42. msg: '',
  43. reCheckField: 'fileData',
  44. state: 0
  45. },
  46. type_sort: {
  47. val: 0,
  48. oldVal: 0,
  49. init: 0,
  50. msg: "",
  51. state: 0,
  52. },
  53. type_key: {
  54. val: "",
  55. oldVal: "",
  56. init: "",
  57. msg: "",
  58. state: 0,
  59. reCheckField: 'type_name',
  60. },
  61. seo_key: {
  62. val: "",
  63. oldVal: "",
  64. init: "",
  65. msg: "",
  66. state: 0,
  67. }
  68. },
  69. api: '',
  70. queryParams : {},
  71. showLogoDialog: false,
  72. fileType: db_base.fileType.svg,
  73. loading: false,
  74. }
  75. },
  76. computed: {
  77. tags () {
  78. // 拆分tags
  79. let tags = this.formType.seo_key.val
  80. if (!tags) {
  81. return [];
  82. }
  83. // 去除空字符串
  84. tags = tags.replace(/\s/g,'')
  85. let tagArr = tags.split(',')
  86. // 标签去重
  87. tagArr = [...new Set(tagArr)]
  88. // 移除空标签
  89. tagArr = tagArr.filter(item => item)
  90. return tagArr
  91. }
  92. },
  93. mounted() {
  94. // fieldCheck.checkField('type',this.form.type.val)
  95. // formVerify.checkForm(this.form, true);
  96. console.log(formVerify);
  97. },
  98. methods: {
  99. /**
  100. * 初始化编辑器
  101. * @param id
  102. * @param title
  103. * @param api
  104. * @param object
  105. */
  106. init (title, api, object, queryParams) {
  107. this.api = api
  108. console.log('init')
  109. console.log(queryParams)
  110. this.queryParams = queryParams ? queryParams : {}
  111. if (!api){
  112. this.$message.error('请设置api地址')
  113. throw new Error('请设置api地址')
  114. }
  115. let type = {
  116. ...emptyType,
  117. ...object
  118. }
  119. if(object) {
  120. this.typeId = object.type_id
  121. this.title = `编辑${title}`
  122. }else{
  123. this.typeId = ''
  124. this.title = `新增${title}`
  125. }
  126. this.formType.type_name.init = type.type_name
  127. this.formType.type_logo.init = type.type_logo
  128. this.formType.type_sort.init = type.type_sort
  129. this.formType.type_key.init = type.type_key
  130. this.formType.seo_key.init = type.seo_key
  131. this.isInitialized = true
  132. formVerify = new FormVerify(
  133. this.formType,
  134. fieldCheck,
  135. )
  136. formVerify.init()
  137. formVerify.onLog = (msg) => {
  138. console.log(msg);
  139. };
  140. },
  141. updateQueryParams(params){
  142. this.queryParams = params
  143. },
  144. initForm() {
  145. },
  146. close () {
  147. this.isInitialized = false
  148. this.$emit('close')
  149. },
  150. handleSave () {
  151. this.executeSubmitData()
  152. },
  153. deleteTag(tag){
  154. let tagArr = this.tags
  155. let index = tagArr.indexOf(tag)
  156. tagArr.splice(index, 1)
  157. this.formType.seo_key.val = tagArr.join(',')
  158. this.formType.seo_key.msg = ''
  159. },
  160. handleCancel () {
  161. this.close()
  162. },
  163. handleReset() {
  164. this.initForm()
  165. },
  166. openLogoHandle() {
  167. this.showLogoDialog = true
  168. },
  169. closeLogoHandle() {
  170. this.showLogoDialog = false
  171. },
  172. selectImageHandle(fileData){
  173. console.log('okHandle');
  174. console.log(fileData);
  175. this.showLogoDialog = false;
  176. // 选择封面图片
  177. this.formType.type_logo.val = fileData.filePath;
  178. this.formType.type_logo.init = fileData.filePath;
  179. this.formType.type_logo.msg = '';
  180. this.formType.type_logo.state = 0;
  181. this.formType.type_logo.showText = fileData.filePath;
  182. },
  183. async executeSubmitData(){
  184. if(!this.isInitialized)
  185. {
  186. throw new Error('请先初始化类别编辑器')
  187. }
  188. let url = this.api;
  189. // 拼接param参数
  190. if(this.typeId){
  191. this.queryParams.id = this.typeId
  192. }
  193. url = urlAddParam(url, this.queryParams)
  194. console.log(url)
  195. // 检测参数
  196. if(!formVerify.check()) {
  197. return this.$message.error('参数错误')
  198. }
  199. let params = formVerify.getFormData()
  200. console.log(this.queryParams)
  201. params = {
  202. ...params,
  203. ...this.queryParams,
  204. }
  205. console.log(params)
  206. let [err, res] = await handle(axios.post(url, params))
  207. if(err){
  208. this.$message.error(`[${this.title}] 失败:${err.message}`)
  209. console.log(err)
  210. return err
  211. }
  212. let result = res.data
  213. if(result.code !== rCode.OK) {
  214. this.$message.error(`[${this.title}] 失败:${result.msg}`)
  215. return result
  216. }
  217. this.$message.success(`[${this.title}] 成功`)
  218. this.close()
  219. }
  220. }
  221. }
  222. </script>
  223. <template>
  224. <div class="w-full ">
  225. <rounded-title class="text-xl">
  226. <span>{{ title }}</span>
  227. </rounded-title>
  228. <input-row class="mt-2" :msg="formType.type_name.msg"
  229. label="类型名称">
  230. <a-input v-model="formType.type_name.val" placeholder="类型名称"></a-input>
  231. </input-row>
  232. <input-row class="mt-2" :msg="formType.type_logo.msg"
  233. label="类型logo">
  234. <div class="svg-upload">
  235. <svg-icon :svgHref="formType.type_logo.val"></svg-icon>
  236. <div v-if="!formType.type_logo.val" class="null-box">
  237. 选择图标
  238. </div>
  239. <div class="absolute w-full h-full left-0 top-0
  240. justify-center text-white bg-gray-400
  241. items-center text-2xl flex opacity-0 hover:opacity-70"
  242. @click="openLogoHandle"
  243. >
  244. 点击选择图标文件
  245. </div>
  246. </div>
  247. </input-row>
  248. <input-row class="mt-2" :msg="formType.type_sort.msg"
  249. label="排序">
  250. <a-input-number v-model="formType.type_sort.val"
  251. placeholder="排序"></a-input-number>
  252. </input-row>
  253. <input-row class="mt-2" :msg="formType.type_key.msg"
  254. label="类型关键字key">
  255. <a-tooltip>
  256. <template slot="title">
  257. 用于浏览器的搜索关键字, 优化用户访问体验, 禁止重复, 为英文字母
  258. </template>
  259. <a-input v-model="formType.type_key.val" placeholder="类型关键字key"></a-input>
  260. </a-tooltip>
  261. </input-row>
  262. <input-row class="mt-2" :msg="formType.seo_key.msg"
  263. label="seo关键字">
  264. <a-tooltip>
  265. <template slot="title">
  266. 搜索引擎关注的关键字,多个用英文逗号隔开
  267. </template>
  268. <a-input v-model="formType.seo_key.val" placeholder="seo关键字"></a-input>
  269. </a-tooltip>
  270. </input-row>
  271. <input-row class="mt-2"
  272. label="">
  273. <div class="tags">
  274. <a-tag
  275. v-for="tag in tags"
  276. :key="tag"
  277. color="#2db7f5"
  278. closable @close="deleteTag"
  279. >
  280. {{ tag }}
  281. </a-tag>
  282. </div>
  283. </input-row>
  284. <div class="mt-2">
  285. <a-button type="primary" @click="handleReset">重置</a-button>
  286. <a-button type="primary" @click="handleSave">确认</a-button>
  287. </div>
  288. <pop :show="showLogoDialog" :loading="loading">
  289. <pop-card>
  290. <template slot="close-group">
  291. <a-button type="danger" @click="closeLogoHandle">关闭</a-button>
  292. </template>
  293. <image-table
  294. class="w-full h-full"
  295. :fileType="fileType"
  296. @cancel="closeLogoHandle"
  297. @ok="selectImageHandle">
  298. </image-table>
  299. </pop-card>
  300. </pop>
  301. </div>
  302. </template>
  303. <style scoped>
  304. .svg-upload{
  305. width: 90px;
  306. height: 90px;
  307. display: flex;
  308. justify-content: center;
  309. align-items: center;
  310. position: relative;
  311. border: 1px solid #ccc;
  312. border-radius: 5px;
  313. font-size: 45px;
  314. }
  315. .svg-upload .null-box{
  316. width: 100%;
  317. height: 100%;
  318. display: flex;
  319. justify-content: center;
  320. align-items: center;
  321. font-size: 20px;
  322. }
  323. .tags{
  324. width: 100%;
  325. display: flex;
  326. flex-wrap: wrap;
  327. justify-content: flex-start;
  328. align-items: center;
  329. }
  330. </style>