diy-img-icon-set.php 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418
  1. <template id="diy-img-icon-set">
  2. <diy-style-contain :title="title" :show-title="showTitle" :contain-style="containStyle">
  3. <div v-for="(item, index) in iconList" :key="index" :style="[iconSetStyle]" @click="closePop">
  4. <div class="icon-set-title" v-if="item.title">{{ item.title }}</div>
  5. <div class="icon-set-list">
  6. <!-- 关闭图标 -->
  7. <div class="icon-set-close" flex="cross:center" @click.stop="closeHandle(item, index)" v-if="showClose">
  8. <i class="el-icon-close"></i>
  9. </div>
  10. <!-- 删除弹窗 -->
  11. <diy-confirm-popup
  12. :title="popTitle"
  13. :show="cardIndex == index && visible"
  14. confirm-text="删除"
  15. :show-confrim-btn="showConfrimBtn"
  16. @close="closePop"
  17. @confirm="delCards($event, index)"
  18. ></diy-confirm-popup>
  19. <div v-if="item.slot">
  20. <slot :name="item.slot" :item="item" :index="index"></slot>
  21. </div>
  22. <!-- 内容 -->
  23. <div class="icon-set-items" flex="cross:center" v-if="set_style != 'text'">
  24. <div class="icon-set-list-name diy-text-font">{{ type == 1 ? '图片' : '图标' }}</div>
  25. <div class="icon-set-list-content">
  26. <com-attachment :multiple="false" :max="1" type="images" @selected="coverPic($event, item)">
  27. <div class="content-upload" :style="{width: widthImg + 'px', height: heightImg + 'px'}" flex="cross:center main:center" v-if="!item.img">
  28. <i class="el-icon-plus"></i>
  29. </div>
  30. <div class="content-img" :style="{width: widthImg + 'px', height: heightImg + 'px'}" flex="cross:center main:center" v-else>
  31. <el-image style="width: 100%; height: 100%;border-radius: 8px;" :src="item.img"></el-image>
  32. <div class="img-replace">替换</div>
  33. <div class="icon-close" @click.stop="delPic(item, index)">
  34. <i class="el-icon-close"></i>
  35. </div>
  36. </div>
  37. </com-attachment>
  38. <div class="tips-text" v-if="suggestText">{{ suggestText }}</div>
  39. </div>
  40. </div>
  41. <!-- <div class="icon-set-items" flex="cross:center" v-if="set_style != 'text' && type == 1 && tagSwitch">-->
  42. <!-- <div class="icon-set-list-name diy-text-font">标签</div>-->
  43. <!-- <div class="icon-set-list-content" flex="cross:center">-->
  44. <!-- <el-switch v-model="item.is_show_tag" active-color="#2D8CF0" inactive-color="#999999" @change="iconSetChange($event, item, 'is_show_tag')"></el-switch>-->
  45. <!-- <span class="diy-text-font" style="padding-left: 7px;font-weight: 500;">{{ item.is_show_tag ? '开启' : '关闭' }}</span>-->
  46. <!-- </div>-->
  47. <!-- </div>-->
  48. <!-- <div class="icon-set-items" flex="cross:center" v-if="item.is_show_tag && set_style != 'text' && type == 1">-->
  49. <!-- <div class="icon-set-list-name diy-text-font">标签内容</div>-->
  50. <!-- <div class="icon-set-list-content" flex="cross:center">-->
  51. <!-- <el-input size="small" v-model="item.tags" placeholder="请输入内容" maxlength="2" @input="iconSetChange($event, item, 'tags')" show-word-limit></el-input>-->
  52. <!-- </div>-->
  53. <!-- </div>-->
  54. <!-- <div class="icon-set-items" flex="cross:center" v-if="item.is_show_tag && set_style != 'text' && type == 1">-->
  55. <!-- <div class="icon-set-list-name diy-text-font">标签背景</div>-->
  56. <!-- <div class="icon-set-list-content" flex="cross:center">-->
  57. <!-- <el-color-picker flex="cross:center" v-model="item.tagsBgColor" :show-alpha="showAlpha" @change="iconSetChange($event, item, 'tagsBgColor')"></el-color-picker>-->
  58. <!-- </div>-->
  59. <!-- </div>-->
  60. <!-- <div class="icon-set-items" flex="cross:center" v-if="item.is_show_tag && set_style != 'text' && type == 1">-->
  61. <!-- <div class="icon-set-list-name diy-text-font">标签文字</div>-->
  62. <!-- <div class="icon-set-list-content" flex="cross:center">-->
  63. <!-- <el-color-picker flex="cross:center" v-model="item.tagsTextColor" :show-alpha="showAlpha" @change="iconSetChange($event, item, 'tagsTextColor')"></el-color-picker>-->
  64. <!-- </div>-->
  65. <!-- </div>-->
  66. <div class="icon-set-items" flex="cross:center" v-if="set_style != 'image'">
  67. <div class="icon-set-list-name diy-text-font">文字</div>
  68. <div class="icon-set-list-content" flex="cross:center">
  69. <el-input size="small" v-model="item.btnText" placeholder="请输入内容" @input="iconSetChange($event, item, 'btnText')" maxlength="5" show-word-limit></el-input>
  70. </div>
  71. </div>
  72. <div class="icon-set-items" flex="cross:center" v-if="set_style != 'image'">
  73. <div class="icon-set-list-name diy-text-font">提示文字</div>
  74. <div class="icon-set-list-content" flex="cross:center">
  75. <el-input size="small" v-model="item.btnTips" placeholder="请输入内容" @input="iconSetChange($event, item, 'btnTips')" maxlength="6" show-word-limit></el-input>
  76. </div>
  77. </div>
  78. <div class="icon-set-items" flex="cross:center" v-if="showLink">
  79. <div class="icon-set-list-name diy-text-font">链接</div>
  80. <div class="icon-set-list-content" flex="cross:center">
  81. <com-pick-link @selected="selectedUrl($event, item)" :default-tabs="defaultTabs">
  82. <diy-url :text="item.link_params && (item.link_params.title || item.link_params.open_type)" @add="addUrl(index)"></diy-url>
  83. </com-pick-link>
  84. </div>
  85. </div>
  86. </div>
  87. </div>
  88. <div class="add-btns" @click="addClick" v-if="showAddBtn && list.length < maxIconLength">+ 添加<span v-if="maxIconLength">{{ list.length }}/{{ maxIconLength }}</span></div>
  89. </diy-style-contain>
  90. </template>
  91. <script>
  92. /**
  93. * 图标设置组件
  94. *
  95. */
  96. Vue.component('diy-img-icon-set', {
  97. template: '#diy-img-icon-set',
  98. name: 'diy-img-icon-set',
  99. props: {
  100. title: { // 组件标题, 传值显示标题, 不传就不显示
  101. type: String,
  102. default: ''
  103. },
  104. containStyle: { // 包裹容器的样式
  105. type: Object,
  106. default: () => {}
  107. },
  108. /**
  109. * list 的数据格式
  110. * {
  111. title: '', // 标题,有就显示,没有就不显示
  112. img: 'resources/img/decorate/default_btn1.png', // 图片
  113. icon: 'el-icon-setting', // 图标
  114. is_show_tag: false, // 是否展示标签
  115. tags: '热门', // 标签内容
  116. tagsBgColor: '#f83287', // 标签背景色
  117. tagsTextColor: '#ffffff', // 标签文字颜色
  118. btnText: '按钮文字' // 按钮文字
  119. btnTips:'提示文字'
  120. link_params: null, // 链接内容
  121. }
  122. */
  123. list: {
  124. type: Array,
  125. default: () => {
  126. return []
  127. }
  128. },
  129. widthImg: { // 图片的宽度
  130. type: Number,
  131. default: 50
  132. },
  133. heightImg: { // 图片的高度
  134. type: Number,
  135. default: 50
  136. },
  137. showClose: { // 是否展示删除按钮
  138. type: Boolean,
  139. default: true
  140. },
  141. tagSwitch: { // 是否需要标签开关
  142. type: Boolean,
  143. default: false
  144. },
  145. showLink: { // 是否展示链接
  146. type: Boolean,
  147. default: false
  148. },
  149. type: { // 图标类型,1 图片 || 2 图标
  150. type: Number,
  151. default: 1
  152. },
  153. showAlpha: { // 透明度
  154. type: Boolean,
  155. default: false
  156. },
  157. btnStyle: { // 按钮样式 1: 图片加文字 2: 图片 3: text: 文字
  158. type: Number,
  159. default: 1
  160. },
  161. maxIconLength: { // 最多添加数量
  162. type: Number,
  163. default: 0
  164. },
  165. showAddBtn: { // 是否展示添加按钮
  166. type: Boolean,
  167. default: false
  168. },
  169. suggestText: { // 图片建议尺寸
  170. type: String,
  171. default: ''
  172. },
  173. iconSetStyle: { // 按钮列表的样式
  174. type: Object,
  175. default: () => {}
  176. },
  177. imgUrl: { // 添加的列表展示的图片
  178. type: String,
  179. default: ''
  180. },
  181. defaultTabs: {
  182. type: Array,
  183. default: () => {
  184. return ["mall", "addons", "other"]
  185. }
  186. }
  187. },
  188. data() {
  189. return {
  190. visible: false,
  191. cardIndex: 0,
  192. is_show_close: false,
  193. iconList: [],
  194. popTitle: '确定删除吗',
  195. showConfrimBtn: true,
  196. urlPop: false,
  197. urlIndex: -1,
  198. // defaultTabs: ["mall", "addons", "other"],
  199. }
  200. },
  201. computed: {
  202. set_style() {
  203. return this.btnStyle == 1 ? 'image_text' : this.btnStyle == 2 ? 'image' : 'text'
  204. },
  205. showTitle() {
  206. return this.title ? true : false
  207. }
  208. },
  209. watch: {
  210. list: {
  211. deep:true,
  212. immediate: true,
  213. handler(val) {
  214. console.log(val, '--------')
  215. this.iconList = val
  216. this.changes()
  217. }
  218. }
  219. },
  220. created() {
  221. },
  222. methods: {
  223. updatePop(boo){
  224. console.log(boo)
  225. this.urlPop = !this.urlPop;
  226. },
  227. selectedUrl(e, item) {
  228. let info = e[0]
  229. console.log(info, 'info')
  230. item.link_params = info
  231. this.$forceUpdate()
  232. this.$emit('change', this.iconList)
  233. },
  234. // 图片添加链接
  235. addUrl(index){
  236. this.urlIndex = index;
  237. this.urlPop=true;
  238. },
  239. closeHandle(it, i) {
  240. if (this.iconList.length == 1) {
  241. this.popTitle = '至少保留1个'
  242. this.showConfrimBtn = false
  243. }
  244. this.cardIndex = i
  245. this.visible = true
  246. },
  247. closePop(){
  248. this.visible = false
  249. },
  250. changes() {
  251. this.$emit('change', this.iconList)
  252. },
  253. coverPic(e, item) {
  254. let img = e[0].url
  255. item.img = img
  256. this.changes()
  257. },
  258. delPic(it, i) {
  259. it.img = ''
  260. this.changes()
  261. },
  262. addClick() {
  263. if (this.iconList.length >= this.maxIconLength) {
  264. return;
  265. }
  266. let obj = {
  267. // img: this.dynamicImgSrc(this.imgUrl),
  268. img: this.imgUrl,
  269. icon: 'el-icon-setting',
  270. is_show_tag: false,
  271. tags: '热门',
  272. tagsBgColor: '#f83287',
  273. tagsTextColor: '#ffffff',
  274. btnText: '按钮文字',
  275. btnTips:'按钮提示',
  276. link_params: null,
  277. }
  278. this.iconList.push(obj)
  279. console.log(this.iconList, 'hehe')
  280. this.changes()
  281. },
  282. iconSetChange(e, item, name) {
  283. item[name] = e
  284. this.changes()
  285. },
  286. delCards(e, i) {
  287. this.visible = false
  288. this.iconList.splice(i, 1)
  289. this.changes()
  290. }
  291. }
  292. })
  293. </script>
  294. <style>
  295. .icon-set-list-content .com-pick-link-content {
  296. width: 310px;
  297. }
  298. .icon-set-list-content .diy-url {
  299. padding: 9px 15px;
  300. }
  301. .popover-tips {
  302. font-size: 12px;
  303. text-align: center;
  304. padding-bottom: 5px;
  305. }
  306. .icon-set-list {
  307. position: relative;
  308. border-radius: 8px;
  309. background-color: #F4F3F7;
  310. /* padding: 18px 12px; */
  311. padding: 15px 30px 15px 12px;
  312. margin-bottom: 20px;
  313. }
  314. .icon-set-title {
  315. line-height: 1;
  316. color: #47565d;
  317. font-weight: bolder;
  318. margin-bottom: 20px;
  319. }
  320. .icon-set-close {
  321. display: none;
  322. position: absolute;
  323. top: 10px;
  324. right: 0;
  325. width: 30px;
  326. height: 30px;
  327. color: #999;
  328. cursor: pointer;
  329. }
  330. .icon-set-list:hover .icon-set-close {
  331. display: block;
  332. }
  333. .icon-set-items {
  334. margin-bottom: 20px;
  335. }
  336. .icon-set-items:last-child {
  337. margin-bottom: 0;
  338. }
  339. .icon-set-list-name {
  340. width: 60px;
  341. text-align: right;
  342. padding-right: 8px;
  343. margin-right: 15px;
  344. }
  345. .content-upload {
  346. width: 50px;
  347. height: 50px;
  348. border-radius: 8px;
  349. cursor: pointer;
  350. background-color: #E3E3E3;
  351. color: #fff;
  352. }
  353. .content-img {
  354. position: relative;
  355. width: 50px;
  356. height: 50px;
  357. border-radius: 8px;
  358. cursor: pointer;
  359. }
  360. .icon-close {
  361. display: none;
  362. position: absolute;
  363. top: -8px;
  364. left: 35px;
  365. width: 20px;
  366. height: 20px;
  367. border-radius: 50%;
  368. background-color: rgba(0, 0, 0, .3);
  369. color: #fff;
  370. text-align: center;
  371. }
  372. .img-replace {
  373. display: none;
  374. position: absolute;
  375. bottom: 0;
  376. width: 100%;
  377. background-color: rgba(0, 0, 0, .3);
  378. color: #fff;
  379. text-align: center;
  380. font-size: 12px;
  381. padding: 2px 0;
  382. }
  383. .content-img:hover .icon-close,
  384. .content-img:hover .img-replace {
  385. display: block;
  386. }
  387. .icon-set-list-content {
  388. flex: 1;
  389. }
  390. .icon-set-list-content .el-switch__labe {
  391. font-size: 15px;
  392. color: #999999 !important;
  393. font-weight: 700;
  394. padding-left: 5px;
  395. }
  396. .icon-set-items .el-color-picker {
  397. height: auto;
  398. }
  399. .add-btns {
  400. border: 1px dashed #707070;
  401. line-height: 32px;
  402. height: 34px;
  403. border-radius: 5px;
  404. text-align: center;
  405. cursor: pointer;
  406. color: var(--textGray, #999999);
  407. }
  408. .diy-url {
  409. margin-left: 0 !important;
  410. }
  411. </style>