coupon.js 23 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505
  1. define(['jquery', 'bootstrap', 'backend', 'table', 'form'], function ($, undefined, Backend, Table, Form) {
  2. var Controller = {
  3. index: function () {
  4. // 初始化表格参数配置
  5. Table.api.init({
  6. extend: {
  7. index_url: 'shop/coupon/index' + location.search,
  8. add_url: 'shop/coupon/add',
  9. edit_url: 'shop/coupon/edit',
  10. del_url: 'shop/coupon/del',
  11. multi_url: 'shop/coupon/multi',
  12. import_url: 'shop/coupon/import',
  13. table: 'shop_coupon',
  14. }
  15. });
  16. var table = $("#table");
  17. // 初始化表格
  18. table.bootstrapTable({
  19. url: $.fn.bootstrapTable.defaults.extend.index_url,
  20. pk: 'id',
  21. sortName: 'id',
  22. fixedColumns: true,
  23. fixedRightNumber: 1,
  24. columns: [
  25. [{
  26. checkbox: true
  27. },
  28. {
  29. field: 'id',
  30. title: __('Id')
  31. },
  32. {
  33. field: 'name',
  34. title: __('Name'),
  35. operate: 'LIKE'
  36. },
  37. {
  38. field: 'condition_name',
  39. title: __('Condition'),
  40. operate: false
  41. },
  42. {
  43. field: 'result',
  44. title: __('Result'),
  45. visible: false,
  46. searchList: {
  47. "0": __('Result 0'),
  48. "1": __('Result 1')
  49. },
  50. formatter: Table.api.formatter.normal
  51. },
  52. {
  53. field: 'result_data',
  54. title: __('Result'),
  55. operate: false,
  56. formatter: function (value, row) {
  57. if (row.result == 0) {
  58. return '订单满' + row.result_data.money + '元,打' + row.result_data.number + '折';
  59. } else {
  60. return '订单满' + row.result_data.money + '元,减' + row.result_data.number + '元';
  61. }
  62. }
  63. },
  64. // {
  65. // field: 'result_data',
  66. // title: __('Result_data'),
  67. // operate: 'LIKE'
  68. // },
  69. {
  70. field: 'give_num',
  71. title: __('Give_num'),
  72. operate: 'BETWEEN'
  73. },
  74. {
  75. field: 'allow_num',
  76. title: __('Allow_num'),
  77. operate: 'BETWEEN'
  78. },
  79. {
  80. field: 'received_num',
  81. title: __('Received_num'),
  82. operate: 'BETWEEN'
  83. },
  84. {
  85. field: 'is_private',
  86. title: __('Is_private'),
  87. searchList: {
  88. "yes": __('Is_private yes'),
  89. "no": __('Is_private no')
  90. },
  91. formatter: Table.api.formatter.normal
  92. },
  93. {
  94. field: 'is_open',
  95. title: __('Is_open'),
  96. searchList: {
  97. "0": __('Is_open 0'),
  98. "1": __('Is_open 1')
  99. },
  100. formatter: Table.api.formatter.normal
  101. },
  102. {
  103. field: 'url', title: __('Url'), operate: false, formatter: function (value, row, index) {
  104. return '<a href="' + row.url + '" target="_blank" class="btn btn-default btn-xs"><i class="fa fa-link"></i></a>';
  105. }
  106. },
  107. {
  108. field: 'status', title: __('Status'), operate: false, formatter: function (value, row, index) {
  109. return row.expired ? "<span class='text-danger'>已过期</span>" : "<span class='text-success'>正常</span>";
  110. }
  111. },
  112. {
  113. field: 'receive_times',
  114. title: __('Receive_times'),
  115. operate: 'RANGE',
  116. addclass: 'datetimerange',
  117. autocomplete: false
  118. },
  119. {
  120. field: 'use_times',
  121. title: __('Use_times'),
  122. operate: 'RANGE',
  123. addclass: 'datetimerange',
  124. autocomplete: false,
  125. formatter: function (value, row) {
  126. if (row.mode == 'fixation') {
  127. return value + '天';
  128. } else {
  129. return value;
  130. }
  131. }
  132. },
  133. {
  134. field: 'createtime',
  135. title: __('Createtime'),
  136. operate: 'RANGE',
  137. addclass: 'datetimerange',
  138. autocomplete: false,
  139. visible: false,
  140. formatter: Table.api.formatter.datetime
  141. },
  142. {
  143. field: 'updatetime',
  144. title: __('Updatetime'),
  145. operate: 'RANGE',
  146. addclass: 'datetimerange',
  147. autocomplete: false,
  148. visible: false,
  149. operate: false,
  150. formatter: Table.api.formatter.datetime
  151. },
  152. {
  153. field: 'operate',
  154. title: __('Operate'),
  155. table: table,
  156. events: Table.api.events.operate,
  157. formatter: Table.api.formatter.operate
  158. }
  159. ]
  160. ]
  161. });
  162. // 为表格绑定事件
  163. Table.api.bindevent(table);
  164. },
  165. select: function () {
  166. // 从URL参数中获取选择模式,默认为单选(优惠券通常单选)
  167. var urlParams = new URLSearchParams(window.location.search);
  168. var selectMode = urlParams.get('selectMode') || 'single'; // 'single' 或 'multiple'
  169. var maxSelect = parseInt(urlParams.get('maxSelect')) || 0; // 最大选择数量,0表示无限制
  170. // 初始化表格参数配置
  171. Table.api.init({
  172. extend: {
  173. index_url: 'shop/coupon/index' + location.search,
  174. table: 'shop_coupon',
  175. }
  176. });
  177. Table.config.dragsortfield = '';
  178. var table = $("#table");
  179. // 根据选择模式配置表格列
  180. var columns = [
  181. {field: 'id', title: 'ID', width: 60},
  182. {
  183. field: 'name',
  184. title: '优惠券信息',
  185. operate: 'LIKE',
  186. formatter: function (value, row, index) {
  187. var html = '<div>';
  188. html += '<div style="font-weight: bold; margin-bottom: 4px;">' + value + '</div>';
  189. // 优惠券条件和结果描述
  190. if (row.result_data) {
  191. html += '<div style="font-size: 12px; color: #666; margin-bottom: 2px;">';
  192. if (row.result == 0) {
  193. html += '满' + row.result_data.money + '元,打' + row.result_data.number + '折';
  194. } else {
  195. html += '满' + row.result_data.money + '元,减' + row.result_data.number + '元';
  196. }
  197. html += '</div>';
  198. }
  199. // 使用时间和状态
  200. html += '<div style="font-size: 11px; color: #999;">';
  201. if (row.receive_times) {
  202. html += '领取: ' + row.receive_times;
  203. }
  204. if (row.use_times) {
  205. if (row.receive_times) html += ' | ';
  206. html += '使用: ' + row.use_times;
  207. if (row.mode == 'fixation') {
  208. html += '天';
  209. }
  210. }
  211. html += '</div>';
  212. return html;
  213. }
  214. },
  215. {
  216. field: 'condition_name',
  217. title: '使用条件',
  218. width: 120,
  219. operate: false,
  220. formatter: function (value, row, index) {
  221. return '<span style="font-size: 12px;">' + (value || '-') + '</span>';
  222. }
  223. },
  224. {
  225. field: 'give_num',
  226. title: '发放/已领',
  227. width: 100,
  228. operate: false,
  229. formatter: function (value, row, index) {
  230. return '<div style="text-align: center; font-size: 12px;">' +
  231. '<div>发放: ' + (row.give_num || 0) + '</div>' +
  232. '<div style="color: #666;">已领: ' + (row.received_num || 0) + '</div>' +
  233. '</div>';
  234. }
  235. },
  236. {
  237. field: 'status',
  238. title: '状态',
  239. width: 80,
  240. operate: false,
  241. formatter: function (value, row, index) {
  242. if (row.expired) {
  243. return '<span class="label label-danger">已过期</span>';
  244. } else if (row.is_open == 1) {
  245. return '<span class="label label-success">正常</span>';
  246. } else {
  247. return '<span class="label label-warning">停用</span>';
  248. }
  249. }
  250. },
  251. // 操作列 - 添加选择按钮
  252. {
  253. field: 'operate',
  254. title: selectMode === 'single' ? '选择' : '操作',
  255. width: selectMode === 'single' ? 80 : 100,
  256. operate: false,
  257. formatter: function (value, row, index) {
  258. // 检查优惠券是否可选(未过期且开启)
  259. var disabled = row.expired || row.is_open != 1;
  260. var disabledClass = disabled ? ' disabled' : '';
  261. var disabledAttr = disabled ? ' disabled="disabled"' : '';
  262. var html = '';
  263. if (selectMode === 'single') {
  264. // 单选模式:蓝色选择按钮
  265. html = '<button class="btn btn-xs btn-primary btn-select-single' + disabledClass + '" data-id="' + row.id + '" data-index="' + index + '" title="' + (disabled ? '优惠券不可用' : '点击选择该优惠券') + '"' + disabledAttr + '>' +
  266. '<i class="fa fa-check"></i> 选择</button>';
  267. } else {
  268. // 多选模式:绿色选择按钮
  269. html = '<button class="btn btn-xs btn-success btn-select-multi' + disabledClass + '" data-id="' + row.id + '" data-index="' + index + '" data-selected="false" title="' + (disabled ? '优惠券不可用' : '点击添加到选择列表') + '"' + disabledAttr + '>' +
  270. '<i class="fa fa-plus"></i> 选择</button>';
  271. }
  272. return html;
  273. }
  274. }
  275. ];
  276. // 初始化表格
  277. table.bootstrapTable({
  278. url: $.fn.bootstrapTable.defaults.extend.index_url,
  279. pk: 'id',
  280. sortName: 'id',
  281. clickToSelect: false, // 禁用点击行选择
  282. columns: [columns]
  283. });
  284. // 存储选中的优惠券(用于按钮模式)
  285. var selectedCoupons = [];
  286. // 单选按钮点击事件
  287. $(document).on('click', '.btn-select-single:not(.disabled)', function () {
  288. var $btn = $(this);
  289. var id = $btn.data('id');
  290. var index = $btn.data('index');
  291. var rowData = table.bootstrapTable('getData')[index];
  292. // 直接选择优惠券并关闭弹窗
  293. Fast.api.close([rowData]);
  294. });
  295. // 多选按钮点击事件
  296. $(document).on('click', '.btn-select-multi:not(.disabled)', function () {
  297. var $btn = $(this);
  298. var id = $btn.data('id');
  299. var index = $btn.data('index');
  300. var isSelected = $btn.data('selected');
  301. var rowData = table.bootstrapTable('getData')[index];
  302. if (!isSelected) {
  303. // 检查最大选择限制
  304. if (maxSelect > 0 && selectedCoupons.length >= maxSelect) {
  305. Toastr.warning('最多只能选择 ' + maxSelect + ' 个优惠券');
  306. return;
  307. }
  308. // 添加到选中列表
  309. selectedCoupons.push(rowData);
  310. $btn.removeClass('btn-success').addClass('btn-danger')
  311. .html('<i class="fa fa-minus"></i> 取消选择')
  312. .attr('title', '点击从选择列表中移除')
  313. .data('selected', true);
  314. } else {
  315. // 从选中列表移除
  316. selectedCoupons = selectedCoupons.filter(function(item) {
  317. return item.id != id;
  318. });
  319. $btn.removeClass('btn-danger').addClass('btn-success')
  320. .html('<i class="fa fa-plus"></i> 选择')
  321. .attr('title', '点击添加到选择列表')
  322. .data('selected', false);
  323. }
  324. // 更新选中数量显示
  325. updateSelectedCount();
  326. });
  327. // 更新选中数量显示
  328. function updateSelectedCount() {
  329. var count = selectedCoupons.length;
  330. var countText = count > 0 ? '已选择 ' + count + ' 个优惠券' : '请选择优惠券';
  331. // 更新确认按钮文本
  332. $('.btn-coupon-select').text(countText === '请选择优惠券' ? '确认选择' : '确认选择 (' + count + ')');
  333. // 如果达到最大选择数量,禁用其他选择按钮
  334. if (maxSelect > 0 && count >= maxSelect) {
  335. $('.btn-select-multi[data-selected="false"]:not(.disabled)').prop('disabled', true).addClass('disabled');
  336. } else {
  337. $('.btn-select-multi[data-selected="false"]:not(.disabled)').prop('disabled', false).removeClass('disabled');
  338. }
  339. }
  340. // 确认按钮绑定事件(仅多选模式使用)
  341. $(document).on('click', '.btn-coupon-select', function () {
  342. var selectedRows = [];
  343. if (selectMode === 'single') {
  344. // 单选模式:不应该走到这里,因为单选时直接选择
  345. Layer.alert('单选模式请直接点击优惠券的选择按钮');
  346. return;
  347. } else {
  348. // 多选模式:使用按钮选择的优惠券
  349. selectedRows = selectedCoupons;
  350. }
  351. if (selectedRows.length === 0) {
  352. Layer.alert('请选择优惠券');
  353. return;
  354. }
  355. // 调用父窗口回调函数
  356. Fast.api.close(selectedRows);
  357. });
  358. // 在页面标题中显示选择模式
  359. var modeText = selectMode === 'single' ? '单选' : '多选';
  360. if (selectMode === 'multiple' && maxSelect > 0) {
  361. modeText += '(最多' + maxSelect + '个)';
  362. }
  363. $('.panel-heading, .layui-layer-title').each(function() {
  364. var currentTitle = $(this).text();
  365. if (currentTitle.indexOf('选择优惠券') !== -1 && currentTitle.indexOf(modeText) === -1) {
  366. $(this).text(currentTitle + ' - ' + modeText);
  367. } else if (currentTitle.indexOf('选择') !== -1 && currentTitle.indexOf('优惠券') === -1 && currentTitle.indexOf(modeText) === -1) {
  368. $(this).text(currentTitle.replace('选择', '选择优惠券') + ' - ' + modeText);
  369. }
  370. });
  371. // 显示选择模式提示信息
  372. $('#selection-info').show();
  373. $('#selection-mode-text').text(modeText);
  374. if (selectMode === 'single') {
  375. $('#selection-tip').html('<strong>单击任意优惠券的"选择"按钮即可完成选择</strong>');
  376. // 单选模式隐藏确认按钮
  377. $('#confirm-select-btn').hide();
  378. } else {
  379. var tipText = '点击优惠券的"选择"按钮添加到选择列表,绿色表示可选择,红色表示已选择';
  380. if (maxSelect > 0) {
  381. tipText += ',最多可选择' + maxSelect + '个优惠券';
  382. }
  383. $('#selection-tip').text(tipText);
  384. // 多选模式显示确认按钮
  385. $('#confirm-select-btn').show();
  386. }
  387. // 表格刷新后恢复选择状态
  388. table.on('refresh.bs.table load-success.bs.table', function () {
  389. if (selectMode === 'multiple') {
  390. // 恢复多选按钮状态
  391. setTimeout(function() {
  392. $('.btn-select-multi').each(function() {
  393. var $btn = $(this);
  394. var id = $btn.data('id');
  395. var isSelected = selectedCoupons.some(function(item) {
  396. return item.id == id;
  397. });
  398. if (isSelected && !$btn.hasClass('disabled')) {
  399. $btn.removeClass('btn-success').addClass('btn-danger')
  400. .html('<i class="fa fa-minus"></i> 取消选择')
  401. .attr('title', '点击从选择列表中移除')
  402. .data('selected', true);
  403. } else if (!$btn.hasClass('disabled')) {
  404. $btn.removeClass('btn-danger').addClass('btn-success')
  405. .html('<i class="fa fa-plus"></i> 选择')
  406. .attr('title', '点击添加到选择列表')
  407. .data('selected', false);
  408. }
  409. });
  410. // 更新选中数量显示
  411. updateSelectedCount();
  412. }, 100);
  413. }
  414. });
  415. // 为表格绑定事件
  416. Table.api.bindevent(table);
  417. },
  418. result: function () {
  419. //优惠模式切换
  420. $('#c-result').on('change', function () {
  421. if ($(this).val() == 0) {
  422. $('#text-a').html('打');
  423. $('#text-b').html('折');
  424. } else {
  425. $('#text-a').html('减');
  426. $('#text-b').html('元');
  427. }
  428. })
  429. //去掉日期的选项
  430. $('#c-receive_times').data('ranges', 1);
  431. $('#c-use_times').data('ranges', 1);
  432. let receive_times1 = '';
  433. let receive_times2 = '';
  434. let use_times1 = '';
  435. let use_times2 = '';
  436. //有效期模式切换
  437. $('.modes').click(function () {
  438. var value = $(this).val() //获取选中的radio的值
  439. if (value != 'fixation') {//固定日期
  440. receive_times2 = $('#c-receive_times').val();
  441. use_times2 = $('#c-use_times').val();
  442. $('#modetpl').html(Template('datestpl', {receive_times: receive_times1, use_times: use_times1}));
  443. //去掉日期的选项
  444. $('#c-receive_times').data('ranges', 1);
  445. $('#c-use_times').data('ranges', 1);
  446. Form.events.daterangepicker($("form[role=form]"));
  447. } else {//天数
  448. receive_times1 = $('#c-receive_times').val();
  449. use_times1 = $('#c-use_times').val();
  450. $('#modetpl').html(Template('fixationtpl', {receive_times: receive_times2, use_times: use_times2}));
  451. }
  452. });
  453. },
  454. add: function () {
  455. this.result();
  456. Controller.api.bindevent();
  457. },
  458. edit: function () {
  459. this.result();
  460. Controller.api.bindevent();
  461. },
  462. api: {
  463. bindevent: function () {
  464. Form.api.bindevent($("form[role=form]"));
  465. }
  466. }
  467. };
  468. return Controller;
  469. });