actDetail.vue 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474
  1. <template>
  2. <view class="body">
  3. <view class="content uni-column">
  4. <view class="uni-column top" :style="getBannerStyle()">
  5. <my-topbar :title="actRs.config.matchInfo.compName" @btnBackClick="btnBack"
  6. :showBack="userlevel > 0"></my-topbar>
  7. <view class="top-content uni-row">
  8. </view>
  9. </view>
  10. <view class="main uni-column">
  11. <view class="compBox uni-column">
  12. <view class="compName">
  13. <uni-tag :circle="true" :text="pubState[actRs.otherInfo.pubState]"
  14. :type="actRs.otherInfo.pubState > 1 ? 'primary' : 'warning'" size="small" />
  15. {{actRs.config.matchInfo.compName}}
  16. </view>
  17. <view class="comp_time">赛事日期:{{getActtime()}}</view>
  18. <view v-if="userlevel > 0" class="comp_time">( 联系人:{{actRs.config.matchInfo.contactName}}
  19. &nbsp;&nbsp; 电话:<a :href="'tel:' + actRs.config.matchInfo.phone"
  20. style='color: #ff5500;'>{{actRs.config.matchInfo.phone}}</a> )</view>
  21. <view class="introduce uni-column">
  22. <!-- <text class="introduce-title">赛事介绍</text> -->
  23. <text class="introduce-content" v-html="actRs.config.matchInfo.description"></text>
  24. </view>
  25. <view v-if="actRs.config.matchInfo.rules.length > 0" class="activityRules uni-column">
  26. <text class="activityRules-title">活动规则</text>
  27. <text class="activityRules-content" v-html="actRs.config.matchInfo.rules"></text>
  28. </view>
  29. </view>
  30. <view class="uni-row uni-jcse qrImgBox">
  31. <view class="uni-column">
  32. <image class="imgQrCode" :src="imgQrCodeWx"></image>
  33. <view class="qrMemo">(微信扫码)</view>
  34. <view class="qrMemo">查看赛事详情</view>
  35. </view>
  36. <view v-if="userlevel > 0" class="uni-column">
  37. <image class="imgQrCode" :src="imgQrCodeApp"></image>
  38. <view class="qrMemo">(彩图奔跑APP扫码)</view>
  39. <view class="qrMemo">查看赛事卡片<text v-if="userlevel > 0" style="color: #ff5500;"
  40. @click="qrCodeReset"> [重置]</text></view>
  41. </view>
  42. </view>
  43. </view>
  44. <view class="bottom uni-row uni-jcc">
  45. <button v-if="userlevel > 0" class="bottom-button" @click="btnActEdit">赛事修改</button>
  46. <button v-if="userlevel > 0 && actRs.otherInfo.pubState == 1" class="bottom-button" @click="btnActPublish">赛事发布</button>
  47. <button class="bottom-button" @click="btnRankList">排行榜</button>
  48. <!-- <button v-if="userlevel > 0" class="bottom-button" @click="btnTrack">场地直播</button> -->
  49. <button class="bottom-button" @click="btnUserList">玩家列表</button>
  50. </view>
  51. </view>
  52. <view class="qrcodeBox">
  53. <uv-qrcode ref="qrCodeWx" class="qrCode" size="300px" :value="qrCodeWx" :options="qrCodeOptWx"
  54. @complete="qrCodeWxComplete">
  55. </uv-qrcode>
  56. <uv-qrcode v-if="userlevel > 0" ref="qrCodeApp" class="qrCode" size="300px" :value="qrCodeApp"
  57. :options="qrCodeOptApp" @complete="qrCodeAppComplete">
  58. </uv-qrcode>
  59. </view>
  60. </view>
  61. </template>
  62. <script>
  63. import {
  64. mapState,
  65. mapGetters
  66. } from 'vuex';
  67. import tools from '/utils/tools.js';
  68. import card from '/utils/card.js';
  69. // import { tplStyleList, userLevel, pubState } from '/utils/define.js';
  70. import {
  71. pubState
  72. } from '/utils/define.js';
  73. import {
  74. apiCompInfoDetail,
  75. apiCompInfoPublish,
  76. apiCompQrCodeQuery,
  77. apiCompQrCodeReset,
  78. checkResCode
  79. } from '/utils/api.js';
  80. export default {
  81. data() {
  82. return {
  83. pubState: pubState, //发布状态 0:审核中 1:内测 2:已发布
  84. queryObj: {},
  85. queryString: "",
  86. compId: 0, // 赛事ID
  87. qrCodeWx: "",
  88. qrCodeOptWx: {
  89. margin: 5,
  90. // areaColor: "#f1f1f1",
  91. foregroundImageSrc: '/static/logo/wechat.png' // 指定二维码前景,一般可在中间放logo
  92. },
  93. imgQrCodeWx: "",
  94. qrCodeApp: "",
  95. qrCodeOptApp: {
  96. margin: 5,
  97. // areaColor: "#f1f1f1",
  98. foregroundImageSrc: '/static/logo.png' // 指定二维码前景,一般可在中间放logo
  99. },
  100. imgQrCodeApp: "",
  101. actRs: card.actRs,
  102. /* actRs: {
  103. otherInfo: {
  104. compId: 1,
  105. pubState: "内测",
  106. playNum: 26,
  107. signupState: false,
  108. createTime: 1735530373
  109. },
  110. config: {
  111. "tplInfo": {
  112. "styleId": 0,
  113. "matchLogo": "/static/run.png",
  114. "matchBanner": "static/banner/banner1.png",
  115. },
  116. "matchInfo": {
  117. "compName": "小飞龙系列定向赛",
  118. "description": " · 小飞龙定向赛再次来袭!这次有五个场地哟~<br> · 神秘“蛋叔”闪亮登场~<br> · 蛋叔放大招,百味豆换鸡蛋!<br> · 时不可待!冲鸭!<br><br> · 能不能把蛋叔整郁闷,就看你的啦~<br> · 还等啥?火速报名吧!",
  119. "rules": "<li>随时参赛、不限完赛次数、起点任选、实时排名 <li>起点 -各途经点 -结束点完整打卡为一次有效完赛",
  120. "maxNum": 20,
  121. "contactName": "王老师",
  122. "phone": "13335116666",
  123. "regBeginSecond": 1735530373,
  124. "regEndSecond": 1735950373,
  125. "compBeginSecond": 1736050373,
  126. "compEndSecond": 1736950373,
  127. }
  128. }
  129. } */
  130. }
  131. },
  132. computed: {
  133. ...mapState([
  134. 'username', // 映射 this.username 为 store.state.username
  135. 'userlevel',
  136. 'token'
  137. ]),
  138. ...mapGetters([
  139. 'metadata'
  140. ]),
  141. },
  142. onLoad(query) {
  143. // console.log(query);
  144. this.queryObj = query;
  145. this.queryString = tools.objectToQueryString(this.queryObj);
  146. // console.log(queryString);
  147. this.compId = query["compId"] ?? 0;
  148. this.compInfoDetail();
  149. this.getQrCodeWx();
  150. },
  151. methods: {
  152. getBannerStyle() {
  153. return card.getBannerStyle(this.actRs);
  154. },
  155. getActtime() {
  156. return tools.fmtMcTime3(this.actRs.config.matchInfo.compBeginSecond, this.actRs.config.matchInfo
  157. .compEndSecond);
  158. },
  159. // 自助赛事详情查询
  160. compInfoDetail() {
  161. uni.request({
  162. url: apiCompInfoDetail,
  163. header: this.metadata,
  164. method: "POST",
  165. data: {
  166. compId: this.compId
  167. },
  168. success: (res) => {
  169. // console.log("compInfoDetail", res);
  170. if (checkResCode(res)) {
  171. const data = res.data.data;
  172. this.actRs = data;
  173. if (this.userlevel > 0) {
  174. this.getQrCodeApp();
  175. }
  176. }
  177. },
  178. fail: (err) => {
  179. console.log("compInfoDetail err", err);
  180. },
  181. });
  182. },
  183. // 自助赛事发布
  184. compInfoPublish() {
  185. uni.request({
  186. url: apiCompInfoPublish,
  187. header: this.metadata,
  188. method: "POST",
  189. data: {
  190. compId: this.compId
  191. },
  192. success: (res) => {
  193. // console.log("compInfoPublish", res);
  194. if (checkResCode(res)) {
  195. // const data = res.data.data;
  196. uni.showToast({
  197. title: `赛事发布成功`,
  198. icon: 'none',
  199. duration: 3000
  200. });
  201. setTimeout(() => {
  202. this.$router.go(0); // 刷新当前页面
  203. }, 1000);
  204. }
  205. },
  206. fail: (err) => {
  207. console.log("compInfoPublish err", err);
  208. },
  209. });
  210. },
  211. getQrCodeWx() {
  212. this.qrCodeWx = process.env.OSS_URL + "#/pages/actManage/actDetail?compId=" + this.compId;
  213. },
  214. getQrCodeApp() {
  215. uni.request({
  216. url: apiCompQrCodeQuery,
  217. header: this.metadata,
  218. method: "POST",
  219. data: {
  220. compId: this.compId
  221. },
  222. success: (res) => {
  223. // console.log("getQrCodeApp", res);
  224. if (checkResCode(res)) {
  225. const data = res.data.data;
  226. this.qrCodeApp = "url:" + data.qrCode;
  227. }
  228. },
  229. fail: (err) => {
  230. console.log("getQrCodeApp err", err);
  231. },
  232. });
  233. },
  234. // 重置APP二维码
  235. qrCodeAppReset() {
  236. uni.request({
  237. url: apiCompQrCodeReset,
  238. header: this.metadata,
  239. method: "POST",
  240. data: {
  241. compId: this.compId
  242. },
  243. success: (res) => {
  244. // console.log("qrCodeAppReset", res);
  245. if (checkResCode(res)) {
  246. this.getQrCodeApp(); // 重新获取二维码
  247. uni.showToast({
  248. title: `二维码重置成功`,
  249. icon: 'none',
  250. duration: 3000
  251. });
  252. }
  253. },
  254. fail: (err) => {
  255. console.log("qrCodeAppReset err", err);
  256. },
  257. });
  258. },
  259. btnBack() {
  260. const url = "/pages/actManage/index";
  261. tools.appAction(url, "uni.switchTab");
  262. },
  263. btnActEdit() {
  264. this.queryObj.from = "actDetail";
  265. this.queryString = tools.objectToQueryString(this.queryObj);
  266. const url = '/pages/actCreate/actEdit?' + this.queryString;
  267. tools.appAction(url, "uni.navigateTo");
  268. },
  269. btnActPublish() {
  270. let that = this;
  271. uni.showModal({
  272. title: '提示',
  273. content: `赛事发布后将无法修改赛事内容\r\n您确定要继续吗?`,
  274. confirmText: '确定', //确定文本的文字
  275. cancelText: '取消', //确定文本的文字
  276. showCancel: true, //没有取消按钮的弹框
  277. success: function(res) {
  278. if (res.confirm) {
  279. that.compInfoPublish();
  280. } else if (res.cancel) {}
  281. }
  282. });
  283. },
  284. btnRankList() {
  285. const url = '/pages/actManage/rankList?' + this.queryString;
  286. tools.appAction(url, "uni.navigateTo");
  287. },
  288. btnTrack() {
  289. const url = '/pages/actManage/track?' + this.queryString;
  290. tools.appAction(url, "uni.navigateTo");
  291. },
  292. btnUserList() {
  293. const url = '/pages/actManage/userList?' + this.queryString;
  294. tools.appAction(url, "uni.navigateTo");
  295. },
  296. qrCodeReset() {
  297. let that = this;
  298. uni.showModal({
  299. title: '重置二维码',
  300. content: `重置后生成新码,旧码会失效\r\n您确定要继续吗?`,
  301. confirmText: '确定', //确定文本的文字
  302. cancelText: '取消', //确定文本的文字
  303. showCancel: true, //没有取消按钮的弹框
  304. success: function(res) {
  305. if (res.confirm) {
  306. that.qrCodeAppReset();
  307. } else if (res.cancel) {}
  308. }
  309. });
  310. },
  311. qrCodeWxComplete(res) {
  312. // console.log("[qrCodeWxComplete] res", res);
  313. this.$refs.qrCodeWx.toTempFilePath({
  314. success: (res) => {
  315. // console.log(res);
  316. this.imgQrCodeWx = res.tempFilePath;
  317. }
  318. });
  319. },
  320. qrCodeAppComplete(res) {
  321. // console.log("[qrCodeAppComplete] res", res);
  322. this.$refs.qrCodeApp.toTempFilePath({
  323. success: (res) => {
  324. // console.log(res);
  325. this.imgQrCodeApp = res.tempFilePath;
  326. }
  327. });
  328. }
  329. }
  330. }
  331. </script>
  332. <style scoped>
  333. .top {
  334. height: 170px;
  335. padding-top: 16px;
  336. flex-shrink: 0;
  337. background-repeat: no-repeat;
  338. background-size: cover;
  339. background-position: center;
  340. }
  341. .main {
  342. margin-bottom: 60px;
  343. overflow: scroll;
  344. }
  345. .compBox {
  346. width: 76%;
  347. margin-top: 20px;
  348. }
  349. .compName {
  350. width: 90%;
  351. font-size: 19px;
  352. font-weight: 500;
  353. text-align: center;
  354. }
  355. .comp_time {
  356. margin-top: 8px;
  357. font-size: 12px;
  358. font-weight: 400;
  359. color: #808080;
  360. }
  361. .introduce {
  362. width: 100%;
  363. margin-top: 12px;
  364. margin-bottom: 10px;
  365. align-items: flex-start;
  366. justify-content: space-around;
  367. }
  368. .introduce-title {
  369. color: #333333;
  370. font-size: 15px;
  371. line-height: 30px;
  372. font-family: Source Han Sans CN;
  373. }
  374. .introduce-content {
  375. color: #333333;
  376. font-size: 14px;
  377. line-height: 23px;
  378. font-family: Source Han Sans CN;
  379. }
  380. .activityRules {
  381. width: 100%;
  382. margin-top: 5px;
  383. margin-bottom: 10px;
  384. padding: 10px 15px;
  385. align-items: flex-start;
  386. justify-content: space-around;
  387. border-radius: 9px;
  388. background: #EBEBEB;
  389. }
  390. .activityRules-title {
  391. color: #333333;
  392. font-size: 14px;
  393. line-height: 25px;
  394. font-weight: 500;
  395. font-family: Source Han Sans CN;
  396. }
  397. .activityRules-content {
  398. color: #333333;
  399. font-size: 13px;
  400. line-height: 23px;
  401. font-family: Source Han Sans CN;
  402. }
  403. .bottom {
  404. position: fixed;
  405. bottom: 0;
  406. width: 100%;
  407. height: 40px;
  408. background-color: #ffffff;
  409. border-top: #E5E5E5 solid 1px;
  410. }
  411. .bottom-button {
  412. height: 30px;
  413. background: #FFB40B;
  414. font-size: 14px;
  415. font-weight: 400;
  416. line-height: 30px;
  417. }
  418. .qrImgBox {
  419. width: 90%;
  420. }
  421. .qrCode {
  422. visibility: hidden;
  423. }
  424. .imgQrCode {
  425. width: 120px;
  426. height: 120px;
  427. margin-top: 20px;
  428. margin-bottom: 6px;
  429. border: 2px solid;
  430. }
  431. .qrMemo {
  432. font-size: 12px;
  433. line-height: 18px;
  434. }
  435. .qrcodeBox {
  436. height: 0px;
  437. overflow: hidden;
  438. }
  439. </style>