MBTI人格测试 uniapp

career.vue 20KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726
  1. <template>
  2. <view class="page-wrap">
  3. <view class="share-wrap">
  4. <button open-type="share">
  5. <view class="share-btn">邀请好友测试</view>
  6. </button>
  7. </view>
  8. <!-- 跑马灯 -->
  9. <view class="box">
  10. <text class="title"
  11. >温馨提示:请在心态平和的情况下开始答题,每题考虑时间不宜超过10秒钟,选项之间无对错好坏之分,请选择与你实际做法相符的,而不是你认为怎样做是对的!</text
  12. >
  13. </view>
  14. <view class="progress-wrap box-shadow">
  15. <view>进度</view>
  16. <view class="bar-wrap">
  17. <u-line-progress
  18. active-color="#f0865e"
  19. :percent="((option.currentIdx + 1) / option.choices.length) * 100"
  20. height="40"
  21. striped
  22. striped-active
  23. :show-percent="false"
  24. />
  25. </view>
  26. <view class="tips"
  27. >{{ option.currentIdx + 1 }}/{{ option.choices.length }}</view
  28. >
  29. </view>
  30. <form class="section section_gap" @submit="onSubmit" @reset="onReset">
  31. <!-- 第一部分 -->
  32. <view class="group1">
  33. <block v-for="(item, index) in 7" :key="index">
  34. <view v-show="option.currentIdx === index" class="group-wrap box-shadow">
  35. <view :class="['section__title', 'num' + index]">
  36. <text>{{ option.title[index] }}</text>
  37. </view>
  38. <view class="two">
  39. <radio-group
  40. name="radio-group"
  41. @change="onRadioChange"
  42. :data-index="index"
  43. >
  44. <label>
  45. <view class="first">
  46. <radio value="radio1" />
  47. <text>{{ option.toptext[index] }}</text>
  48. </view>
  49. </label>
  50. <label>
  51. <view class="first">
  52. <radio value="radio2" />
  53. <text>{{ option.bottext[index] }}</text>
  54. </view>
  55. </label>
  56. </radio-group>
  57. </view>
  58. </view>
  59. </block>
  60. </view>
  61. <!-- 分割线 -->
  62. <!-- <view class="fgx"></view> -->
  63. <!-- 第二部分 -->
  64. <view class="group2">
  65. <block v-for="(item, index) in 7" :key="index">
  66. <view v-show="option.currentIdx === 7 + index" class="group-wrap box-shadow">
  67. <view :class="['section__title', 'num' + (7 + index)]">
  68. <text>{{ option.title2[index] }}</text>
  69. </view>
  70. <view class="two">
  71. <radio-group
  72. name="radio-group"
  73. @change="onRadioChange"
  74. :data-index="7 + index"
  75. >
  76. <label>
  77. <view class="first">
  78. <radio value="radio1" />
  79. <text>{{ option.toptext2[index] }}</text>
  80. </view>
  81. </label>
  82. <label>
  83. <view class="first">
  84. <radio value="radio2" />
  85. <text>{{ option.bottext2[index] }}</text>
  86. </view>
  87. </label>
  88. </radio-group>
  89. </view>
  90. </view>
  91. </block>
  92. </view>
  93. <!-- 分割线 -->
  94. <!-- <view class="fgx"></view> -->
  95. <!-- 第三部分 -->
  96. <view class="group3">
  97. <block v-for="(item, index) in 7" :key="index">
  98. <view v-show="option.currentIdx === 14 + index" class="group-wrap box-shadow">
  99. <view :class="['section__title', 'num' + (14 + index)]">
  100. <text>{{ option.title3[index] }}</text>
  101. </view>
  102. <view class="two">
  103. <radio-group
  104. name="radio-group"
  105. @change="onRadioChange"
  106. :data-index="14 + index"
  107. >
  108. <label>
  109. <view class="first">
  110. <radio value="radio1" />
  111. <text>{{ option.toptext3[index] }}</text>
  112. </view>
  113. </label>
  114. <label>
  115. <view class="first">
  116. <radio value="radio2" />
  117. <text>{{ option.bottext3[index] }}</text>
  118. </view>
  119. </label>
  120. </radio-group>
  121. </view>
  122. </view>
  123. </block>
  124. </view>
  125. <!-- 分割线 -->
  126. <!-- <view class="fgx"></view> -->
  127. <!-- 第四部分 -->
  128. <view class="group4">
  129. <block v-for="(item, index) in 7" :key="index">
  130. <view v-show="option.currentIdx === 21 + index" class="group-wrap box-shadow">
  131. <view :class="['section__title', 'num' + (21 + index)]">
  132. <text>{{ option.title4[index] }}</text>
  133. </view>
  134. <view class="two">
  135. <radio-group
  136. name="radio-group"
  137. @change="onRadioChange"
  138. :data-index="21 + index"
  139. >
  140. <label>
  141. <view class="first">
  142. <radio value="radio1" />
  143. <text>{{ option.toptext4[index] }}</text>
  144. </view>
  145. </label>
  146. <label>
  147. <view class="first">
  148. <radio value="radio2" />
  149. <text>{{ option.bottext4[index] }}</text>
  150. </view>
  151. </label>
  152. </radio-group>
  153. </view>
  154. </view>
  155. </block>
  156. </view>
  157. <!-- 分割线 -->
  158. <!-- <view class="fgx"></view> -->
  159. <!-- 按钮 -->
  160. <view class="btn">
  161. <!-- bindtap 事件是在手指触摸屏幕后立即触发,响应速度更快,适用于交互频繁的场景。-->
  162. <!-- bindclick 事件是在手指触摸屏幕后、手指离开屏幕后 300ms 内触发,响应速度较慢,适用于一些需要判断手势的场景。-->
  163. <!-- <button class="btn1" formType="submit">提交</button> -->
  164. <view class="btn-wrap" @click="onClickChangePage('pre')">上一题</view>
  165. <view class="btn-wrap m-30" @click="onClickChangePage('next')"
  166. >下一题</view
  167. >
  168. <button class="btn2" formType="reset" @click="MoveToTop">
  169. 重新测试
  170. </button>
  171. </view>
  172. </form>
  173. </view>
  174. </template>
  175. <script>
  176. const app = getApp();
  177. export default {
  178. components: {},
  179. data() {
  180. return {
  181. appName: app.globalData.$appInfo.appName,
  182. pageContentTop: app.globalData.pageContentTop,
  183. option: {
  184. title: [
  185. "1.你倾向从何处得到力量:",
  186. "2.当你参加一个社交聚会时,你会:",
  187. "3.下列哪一件事听起来比较吸引你?",
  188. "4.在约会中,你通常:",
  189. "5.过去,你遇见你大部分的异性朋友是:",
  190. "6.你倾向拥有:",
  191. "7.过去,你的朋友和同事倾向对你说:",
  192. ],
  193. toptext: [
  194. "别人",
  195. "在夜色很深时,一旦你开始投入,也许就是最晚离开的那一个",
  196. "与情人到有很多人且社交活动频繁的地方",
  197. "整体来说很健谈",
  198. "在宴会中、夜总会、工作上、休闲活动中、会议上或当朋友介绍我给他们的朋友时",
  199. "很多认识的人和很亲密的朋友",
  200. "你难道不可以安静一会儿吗?",
  201. ],
  202. bottext: [
  203. "自己的想法",
  204. "在夜晚刚开始的时候,我就疲倦了并且想回家",
  205. "待在家中与情人做一些特别的事情,例如说观赏一部有趣的录影带并享用你最喜欢的外卖食物",
  206. "较安静并保留,直到你觉得舒服",
  207. "通过私人的方式,例如个人广告、录影约会,或是由亲密的朋友和家人介绍",
  208. "一些很亲密的朋友和一些认识的人",
  209. "可以请你从你的世界中出来一下吗",
  210. ],
  211. title2: [
  212. "8.你倾向通过以下哪种方式收集信息:",
  213. "9.你倾向相信:",
  214. "10.当你置身于一段关系中时,你倾向相信:",
  215. "11.当你对一个约会觉得放心时,你偏向谈论:",
  216. "12.你是这种人:",
  217. "13.你是这类型的人:",
  218. "14.你通常:",
  219. ],
  220. toptext2: [
  221. "你对有可能发生之事的想像和期望",
  222. "你的直觉",
  223. "永远有进步的空间",
  224. "未来,关于改进或发明事物和生活的种种可能性。例如,你也许会谈论一个新的科学发明,或一个更好的方法来表达你的感受",
  225. "喜欢先纵观全局",
  226. "与其活在现实中,不如活在想像里",
  227. "偏向于去想像一大堆关于即将来临的约会的事情",
  228. ],
  229. bottext2: [
  230. "你对目前状况的实际认知",
  231. "你直接的观察和现成的经验",
  232. "若它没有被破坏,不予修补",
  233. "实际的、具体的、关于“此时此地”的事物。例如,你也许会谈论品酒的好方法,或你即将要参加的新奇旅程",
  234. "喜欢先掌握细节",
  235. "与其活在想像里,不如活在现实中",
  236. "偏向于拘谨地想像即将来临的约会,只期待让它自然地发生",
  237. ],
  238. title3: [
  239. "15.你倾向如此做决定:",
  240. "16.你倾向比较能够察觉到:",
  241. "17.当和某人分手时:",
  242. "18.当与一个人交往时,你倾向于看重:",
  243. "19.当你不同意情人的想法时:",
  244. "20.认识你的人倾向形容你为:",
  245. "21.你把大部分和别人的相遇视为:",
  246. ],
  247. toptext3: [
  248. "首先依你的心意,然后依你的逻辑",
  249. "当人们需要情感上的支持时",
  250. "你通常让自己的情绪深陷其中,很难抽身出来",
  251. "情感上的相容性:表达爱意和对另一半的需求很敏感",
  252. "你尽可能地避免伤害对方的感情;若是会对对方造成伤害的话,你就不会说",
  253. "热情和敏感",
  254. "友善及重要的",
  255. ],
  256. bottext3: [
  257. "首先依你的逻辑,然后依你的心意",
  258. "当人们不合逻辑时",
  259. "虽然你觉得受伤,但一旦下定决心,你会直截了当地将过去恋人的影子甩开",
  260. "智慧上的相容性:沟通重要的想法;客观地讨论和辩论事情",
  261. "你通常毫无保留地说话,并且对情人直言不讳,因为对的就是对的",
  262. "逻辑和明确",
  263. "另有目的",
  264. ],
  265. title4: [
  266. "22.若你有时间和金钱,你的朋友邀请你到国外度假,并且在前一天才通知,你会:",
  267. "23.在第一次约会中:",
  268. "24.你偏好:",
  269. "25.你选择的生活充满着:",
  270. "26.哪一项较常见:",
  271. "27.你是这种喜欢……的人:",
  272. "28.你是此类型的人:",
  273. ],
  274. toptext4: [
  275. "必须先检查你的时间表",
  276. "若你所约的人来迟了,你会很不高兴",
  277. "事先知道约会的行程:要去哪里、有谁参加、你会在那里多久、该如何打扮",
  278. "日程表和组织",
  279. "你准时出席而其他人都迟到",
  280. "下定决心并且做出最后肯定的结论",
  281. "喜欢在一段时间里专心于一件事情直到完成",
  282. ],
  283. bottext4: [
  284. "立刻收拾行装",
  285. "一点儿都不在乎,因为你自己常常迟到",
  286. "让约会自然地发生,不做太多事先的计划",
  287. "自然发生和弹性",
  288. "其他人都准时出席而你迟到",
  289. "放宽你的选择面并且持续收集信息",
  290. "享受同时进行好几件事情",
  291. ],
  292. choices: [
  293. null,
  294. null,
  295. null,
  296. null,
  297. null,
  298. null,
  299. null,
  300. null,
  301. null,
  302. null,
  303. null,
  304. null,
  305. null,
  306. null,
  307. null,
  308. null,
  309. null,
  310. null,
  311. null,
  312. null,
  313. null,
  314. null,
  315. null,
  316. null,
  317. null,
  318. null,
  319. null,
  320. null,
  321. ],
  322. currentIdx: 0,
  323. },
  324. };
  325. },
  326. onLoad() {
  327. app.handleSetNavTitle();
  328. },
  329. onShow() {},
  330. onPullDownRefresh() {},
  331. onReachBottom() {},
  332. onShareAppMessage(res) {
  333. // 如果要自定义分享内容,可以设置shareTicket和query参数
  334. return {
  335. title: '免费MBTI人格测试bot,快来试试吧~',
  336. path: '/pages/home/home',
  337. desc:'免费MBTI人格测试bot,快来试试吧~',
  338. imageUrl: '/static/imgs/mbti1.jpg',
  339. success(res){
  340. uni.showToast({
  341. title:'分享成功'
  342. })
  343. },
  344. fail(res){
  345. uni.showToast({
  346. title:'分享失败',
  347. icon:'none'
  348. })
  349. }
  350. }
  351. },
  352. methods: {
  353. onRadioChange(e) {
  354. let index = e.currentTarget.dataset.index;
  355. let value = e.detail.value;
  356. let choices = this.option.choices;
  357. choices[index] = value;
  358. // console.log(choices);
  359. this.option.choices = choices;
  360. if (this.option.currentIdx !== this.option.choices.length - 1) {
  361. this.option.currentIdx = index + 1;
  362. } else {
  363. this.onSubmit();
  364. }
  365. },
  366. onSubmit(e) {
  367. let choices = this.option.choices;
  368. console.log("choices => ", choices);
  369. for (let i = 0; i < choices.length; i++) {
  370. if (choices[i] === null) {
  371. // 如果有未做完题目,使用 `uni.pageScrollTo` 方法滚动页面到未做完题目所在的位置
  372. uni.showToast({
  373. title: "请完成所有题目",
  374. icon: "none",
  375. duration: 2000,
  376. });
  377. let jump = ".num" + i;
  378. uni.pageScrollTo({
  379. selector: jump,
  380. duration: 300,
  381. /*success: data => {
  382. console.log('scroll success', data);
  383. },
  384. fail: data => {
  385. console.log('scroll fail', data);
  386. },
  387. complete: data => {
  388. console.log('scroll complete', data);
  389. }*/
  390. });
  391. this.option.currentIdx = i;
  392. return;
  393. }
  394. }
  395. /* function CountAnswer */
  396. {
  397. let E = 0,
  398. I = 0,
  399. N = 0,
  400. S = 0,
  401. F = 0,
  402. T = 0,
  403. J = 0,
  404. P = 0;
  405. let choices = this.option.choices;
  406. let testResult;
  407. for (let i = 0; i < choices.length; i++) {
  408. if (i < 7) {
  409. if (choices[i] == "radio1") E++;
  410. else I++;
  411. continue;
  412. }
  413. if (i < 14) {
  414. if (choices[i] == "radio1") N++;
  415. else S++;
  416. continue;
  417. }
  418. if (i < 21) {
  419. if (choices[i] == "radio1") F++;
  420. else T++;
  421. continue;
  422. }
  423. if (i < 28) {
  424. if (choices[i] == "radio1") J++;
  425. else P++;
  426. }
  427. }
  428. if (E > I) testResult = "E";
  429. else testResult = "I";
  430. if (N > S) testResult += "N";
  431. else testResult += "S";
  432. if (F > T) testResult += "F";
  433. else testResult += "T";
  434. if (J > P) testResult += "J";
  435. else testResult += "P";
  436. console.log(testResult);
  437. app.globalData.testResult = testResult; // 保存到全局
  438. uni.navigateTo({
  439. url: "/pages/result/result",
  440. });
  441. }
  442. },
  443. onReset() {
  444. this.option.choices = this.option.choices.map(() => null);
  445. this.option.currentIdx = 0;
  446. },
  447. onClickChangePage(type) {
  448. if (type === "pre") {
  449. if (this.option.currentIdx === 0) {
  450. return false;
  451. } else {
  452. this.option.currentIdx--;
  453. }
  454. } else if (type === "next") {
  455. if (this.option.currentIdx === this.option.choices.length - 1) {
  456. return false;
  457. } else if (!this.option.choices[this.option.currentIdx]) {
  458. uni.showToast({
  459. title: "请完成当前题目",
  460. icon: "none",
  461. duration: 2000,
  462. });
  463. } else {
  464. this.option.currentIdx++;
  465. }
  466. }
  467. },
  468. MoveToTop: function () {
  469. uni.showToast({
  470. title: "重置成功",
  471. icon: "none",
  472. duration: 2000,
  473. });
  474. // 最好是先显示提示后滚动;否则就会先回去之后再提示(感觉那样有些奇怪)
  475. uni.pageScrollTo({
  476. scrollTop: 0, // 回到顶端
  477. duration: 300,
  478. });
  479. },
  480. },
  481. };
  482. </script>
  483. <style lang="scss" scoped>
  484. .page-wrap {
  485. min-height: 100vh;
  486. width: 750rpx;
  487. background-color: #ECF0F3;
  488. }
  489. /* pages/career/career.wxss */
  490. /* 跑马灯 */
  491. .box {
  492. width: 750rpx;
  493. margin: 10rpx auto;
  494. background: #feece7;
  495. border-radius: 10rpx;
  496. padding: 10rpx;
  497. box-sizing: border-box;
  498. overflow: hidden;
  499. }
  500. .title {
  501. white-space: nowrap;
  502. animation: 25s loop linear infinite normal;
  503. display: inline-block;
  504. vertical-align: top;
  505. font-size: 26rpx;
  506. color: #ec6e40;
  507. opacity: 0.8;
  508. }
  509. @keyframes loop {
  510. 0% {
  511. transform: translateX(700rpx);
  512. -webkit-transform: translateX(700rpx);
  513. }
  514. 100% {
  515. transform: translateX(-100%);
  516. -webkit-transform: translateX(-100%);
  517. }
  518. }
  519. @-webkit-keyframes loop {
  520. 0% {
  521. transform: translateX(600rpx);
  522. -webkit-transform: translateX(600rpx);
  523. }
  524. 100% {
  525. transform: translateX(-100%);
  526. -webkit-transform: translateX(-100%);
  527. }
  528. }
  529. /* 选择题 */
  530. .section {
  531. background-color: rgb(255, 247, 240);
  532. border-radius: 10rpx;
  533. width: 710rpx;
  534. margin: 10rpx auto;
  535. }
  536. .section .group1,
  537. .group2,
  538. .group3,
  539. .group4 {
  540. /* border: deepskyblue solid 1px; */
  541. width: 700rpx;
  542. margin: 40rpx auto;
  543. }
  544. .group-wrap {
  545. background-color: #fff;
  546. // border: 2rpx solid #f0865e;
  547. padding: 20rpx 40rpx;
  548. border-radius: 40rpx;
  549. }
  550. .section__title {
  551. /* border: rgb(0, 255, 34) solid 1px; */
  552. margin-top: 20rpx;
  553. }
  554. .two {
  555. /* border: rgb(255, 0, 221) solid 1px; */
  556. margin-top: 100rpx;
  557. margin-bottom: 40rpx;
  558. }
  559. radio-group {
  560. margin-left: 10rpx;
  561. }
  562. radio {
  563. transform: scale(0.9);
  564. }
  565. text {
  566. font-size: 30rpx;
  567. color: #666666;
  568. margin-top: 2rpx;
  569. }
  570. .section__title text {
  571. color: #f0865e;
  572. font-size: 34rpx;
  573. font-weight: bold;
  574. }
  575. .two .first {
  576. margin: 50rpx 0;
  577. display: flex;
  578. }
  579. /* 分割线 */
  580. .fgx {
  581. border: rgb(224, 224, 224) solid;
  582. margin-top: 30rpx;
  583. }
  584. /* 按钮 */
  585. .btn {
  586. width: 100%;
  587. display: flex;
  588. align-items: center;
  589. justify-content: center;
  590. margin-top: 100rpx;
  591. }
  592. .btn-wrap {
  593. background: linear-gradient(90deg, #FF9048 0%, #fd6a68 100%);
  594. color: rgb(255, 255, 255);
  595. font-size: 28rpx;
  596. width: 25%;
  597. display: flex;
  598. align-items: center;
  599. justify-content: center;
  600. height: 80rpx;
  601. border-radius: 10rpx;
  602. }
  603. .m-30 {
  604. margin: 0 40rpx;
  605. }
  606. .btn button {
  607. /* border: tomato solid 1px; */
  608. background-color: limegreen;
  609. color: rgb(255, 255, 255);
  610. font-size: 28rpx;
  611. height: 80rpx;
  612. line-height: 80rpx;
  613. text-align: center;
  614. margin: 0;
  615. width: 25%;
  616. }
  617. .btn .btn2 {
  618. background: linear-gradient(90deg, #FF9048 0%, #fd6a68 100%);
  619. }
  620. .progress-wrap {
  621. margin: 40rpx 20rpx 0;
  622. // border: 2rpx solid #f0865e;
  623. display: flex;
  624. justify-content: center;
  625. padding: 40rpx 100rpx;
  626. border-radius: 40rpx;
  627. background-color: #fff;
  628. .bar-wrap {
  629. margin: 0 30rpx;
  630. width: 300rpx;
  631. }
  632. .tips {
  633. width: 80rpx;
  634. }
  635. }
  636. .share-wrap {
  637. button::after {
  638. border: none;
  639. }
  640. button {
  641. position: relative;
  642. display: block;
  643. margin-left: auto;
  644. margin-right: auto;
  645. padding-left: 0px;
  646. padding-right: 0px;
  647. box-sizing: border-box;
  648. text-align: center;
  649. text-decoration: none;
  650. line-height: 1.35;
  651. -webkit-tap-highlight-color: transparent;
  652. overflow: hidden;
  653. color: #000;
  654. font-size: 32rpx;
  655. background-color: #fff;
  656. width: 100%;
  657. height: 100%;
  658. }
  659. .share-btn {
  660. padding: 15rpx 10rpx;
  661. background: linear-gradient(90deg, #FF9048 0%, #fd6a68 100%);
  662. color: #fff;
  663. font-weight: 600;
  664. font-size: 26rpx;
  665. position: fixed;
  666. right: 0;
  667. bottom: 20%;
  668. border-radius: 40rpx 0 0 40rpx;
  669. }
  670. }
  671. .box-shadow {
  672. background-color: #fff;
  673. border-radius: 20px;
  674. box-shadow:
  675. inset rgba(0, 0, 0, 0.1) 0 5rpx 12rpx,
  676. inset rgba(252, 255, 255, 0.5) 0 5rpx 12rpx,
  677. rgba(0, 0, 0, 0.2) 0 5rpx 12rpx -5rpx;
  678. }
  679. </style>