Browse Source

添加报名页面

lex 1 year ago
parent
commit
a53c2683a7

+ 8 - 0
src/router/router-root.ts

@@ -9,6 +9,14 @@ export default [
     }
   },
   {
+    path: '/register-member',
+    name: 'register-member',
+    component: () => import('@/views/student-register/register-member'),
+    meta: {
+      title: '报名'
+    }
+  },
+  {
     path: '/goods-list',
     component: () => import('@/views/student-register/shop-mall/goods-list'),
     meta: {

+ 107 - 0
src/views/student-register/register-member/index.module.less

@@ -0,0 +1,107 @@
+.registerModal {
+  background: #FFF4E2;
+  overflow: hidden;
+  min-height: 100vh;
+}
+
+.memberNumer {
+  margin: 12px 12px 0;
+  background: linear-gradient(90deg, #FF8633 0%, #FFB047 100%);
+  border-radius: 10px;
+  padding: 12px 16px;
+  display: flex;
+  align-items: center;
+  font-size: 14px;
+  color: #fff;
+  font-weight: bold;
+
+  .iconGift {
+    width: 20px;
+    height: 20px;
+    margin-right: 6px;
+  }
+}
+
+.infoTitle {
+  width: 315px;
+  height: 31px;
+  display: block;
+  margin: 14px auto 10px;
+}
+
+.registerForm {
+  background: #FFFFFF;
+  box-shadow: 0px 1px 6px 0px #F0D8C8;
+  border-radius: 18px;
+  margin: 12px 12px 0;
+  overflow: hidden;
+
+  .tips {
+    padding-top: 4px;
+    font-size: 12px;
+    font-weight: 400;
+    color: #FF5A56;
+    line-height: 17px;
+  }
+
+  :global {
+    .van-cell {
+      padding: 14px 14px;
+
+    }
+
+    .van-field__label {
+      font-size: 16px;
+      font-weight: 600;
+      color: #5B2C03;
+      line-height: 22px;
+      margin-bottom: 8px;
+    }
+
+    .van-field__control {
+      font-size: 16px;
+    }
+  }
+
+  .codeText {
+    color: #FFCF7C;
+    font-size: 14px;
+    font-weight: 600;
+
+    &.codeTextDisabled {
+      color: #ccc;
+    }
+  }
+}
+
+.submitBtn {
+  margin: 16px 12px 22px;
+  width: calc(100% - 24px);
+  height: 46px;
+  border-radius: 12px;
+  font-size: 16px;
+  font-weight: 600;
+  color: #5B2C03 !important;
+  line-height: 22px;
+}
+
+.radioSection {
+  position: relative;
+  min-width: 32px;
+  justify-content: center;
+  padding-left: 14px;
+  padding-right: 14px;
+}
+
+.radioItem {
+  position: absolute;
+  top: 0;
+  left: 0;
+  right: 0;
+  bottom: 0;
+  opacity: 0;
+}
+
+.radioSection+.radioSection {
+  margin-left: 12px;
+}

+ 404 - 0
src/views/student-register/register-member/index.tsx

@@ -0,0 +1,404 @@
+import {
+  computed,
+  defineComponent,
+  nextTick,
+  onMounted,
+  reactive,
+  ref
+} from 'vue';
+import styles from './index.module.less';
+// import infoTitle from '../images/info-title.png';
+import {
+  Button,
+  CountDown,
+  Field,
+  Form,
+  Picker,
+  Popup,
+  Radio,
+  RadioGroup,
+  Tag,
+  showToast
+} from 'vant';
+import OWxTip from '@/components/m-wx-tip';
+import MProtocol from '@/components/m-protocol';
+import MImgCode from '@/components/m-img-code';
+import { checkPhone } from '@/helpers/utils';
+import request from '@/helpers/request';
+import { useStudentRegisterStore } from '@/store/modules/student-register-store';
+import { setLoginInit, state } from '@/state';
+import iconGift from '../images/icon-gift.png';
+import { useRoute, useRouter } from 'vue-router';
+import MSticky from '@/components/m-sticky';
+const classList: any = [];
+for (let i = 1; i <= 40; i++) {
+  classList.push({ text: i + '班', value: i });
+}
+
+export default defineComponent({
+  name: 'register-modal',
+  emits: ['close', 'submit'],
+  setup(props, { emit }) {
+    const route = useRoute();
+    const router = useRouter();
+    const studentRegisterStore = useStudentRegisterStore();
+    // 初始化学校编号
+    studentRegisterStore.setShoolId(route.query.sId as any);
+    const countDownRef = ref();
+    const gradeList = computed(() => {
+      let tempList: any = [];
+      const five = [
+        { text: '一年级', value: 1 },
+        { text: '二年级', value: 2 },
+        { text: '三年级', value: 3 },
+        { text: '四年级', value: 4 },
+        { text: '五年级', value: 5 }
+      ];
+      const one = [{ text: '六年级', value: 6 }];
+      const three = [
+        { text: '七年级', value: 7 },
+        { text: '八年级', value: 8 },
+        { text: '九年级', value: 9 }
+      ];
+      if (props.gradeYear === 'FIVE_YEAR_SYSTEM') {
+        tempList.push([...five]);
+      } else if (props.gradeYear === 'SIX_YEAR_SYSTEM') {
+        tempList.push([...five, ...one]);
+      } else if (props.gradeYear === 'THREE_YEAR_SYSTEM') {
+        tempList.push([...three]);
+      } else if (props.gradeYear === 'FORE_YEAR_SYSTEM') {
+        tempList.push([...one, ...three]);
+      } else {
+        tempList.push([...five, ...one, ...three]);
+      }
+      return tempList;
+    });
+    const forms = reactive({
+      countDownStatus: true,
+      countDownTime: 1000 * 120, // 倒计时时间
+      modelValue: false, // 是否选中协议
+      imgCodeStatus: false,
+      gradeNumText: '',
+      currentClassText: '',
+      gradeStatus: false,
+      classStatus: false,
+      loading: false,
+      schoolId: route.query.sId as any,
+      gradeYear: null,
+      schoolType: null,
+      giftVipDay: null
+    });
+    const studentInfo = reactive({
+      autoRegister: true,
+      client_id: 'cooleshow-student',
+      client_secret: 'cooleshow-student',
+      extra: {
+        nickname: '',
+        currentGradeNum: '',
+        currentClass: '',
+        gender: 1
+      },
+      grant_type: 'password',
+      loginType: 'SMS',
+      password: '',
+      username: ''
+    });
+
+    const onCodeSend = () => {
+      forms.countDownStatus = false;
+      nextTick(() => {
+        countDownRef.value.start();
+      });
+    };
+
+    const onSendCode = () => {
+      // 发送验证码
+      if (!checkPhone(studentInfo.username)) {
+        return showToast('请输入正确的手机号码');
+      }
+      forms.imgCodeStatus = true;
+    };
+
+    const validatePhone = computed(() => {
+      return checkPhone(studentInfo.username) ? true : false;
+    });
+
+    const onFinished = () => {
+      forms.countDownStatus = true;
+      countDownRef.value.reset();
+    };
+
+    const onSubmit = async () => {
+      try {
+        if (checkForm()) return;
+        forms.loading = true;
+        const { extra, ...res } = studentInfo;
+        const { data } = await request.post('/edu-app/userlogin', {
+          hideLoading: false,
+          requestType: 'form',
+          data: {
+            ...res,
+            extra: JSON.stringify({
+              ...extra,
+              schoolId: forms.schoolId
+            })
+          }
+        });
+
+        setTimeout(() => {
+          showToast('报名成功');
+          router.push('/download');
+        }, 100);
+      } catch {
+      } finally {
+        forms.loading = false;
+      }
+    };
+
+    const checkForm = () => {
+      if (!checkPhone(studentInfo.username)) {
+        showToast('请输入正确的手机号码');
+        return true;
+      } else if (!studentInfo.password) {
+        showToast('请输入验证码');
+        return true;
+      } else if (!studentInfo.extra.nickname) {
+        showToast('请输入学生姓名');
+        return true;
+      } else if (!studentInfo.extra.currentGradeNum) {
+        showToast('请选择所在年级');
+        return true;
+      } else if (!studentInfo.extra.currentClass) {
+        showToast('请选择所在班级');
+        return true;
+      }
+      return false;
+    };
+
+    const getRegisterGoods = async () => {
+      try {
+        const { data } = await request.get('/edu-app/open/school/detail', {
+          params: {
+            id: forms.schoolId
+          },
+          noAuthorization: true // 是否请求接口的时候添加toekn
+        });
+
+        forms.giftVipDay = data.giftVipDay;
+        forms.schoolType = data.schoolType;
+        forms.gradeYear = data.gradeYear;
+      } catch {}
+    };
+
+    onMounted(() => {
+      getRegisterGoods();
+    });
+    return () => (
+      <div class={styles.registerModal}>
+        {forms.giftVipDay ? (
+          <div class={styles.memberNumer}>
+            <img src={iconGift} class={styles.iconGift} />
+
+            <p>
+              现在报名赠送会员 <span>{forms.giftVipDay}</span> 天
+            </p>
+          </div>
+        ) : (
+          ''
+        )}
+
+        <Form labelAlign="top" class={styles.registerForm}>
+          <Field
+            clearable
+            label="联系方式(直接监护人)"
+            placeholder="请输入手机号码"
+            type="tel"
+            autocomplete="off"
+            v-model={studentInfo.username}
+            maxlength={11}>
+            {{
+              label: () => (
+                <div>
+                  联系方式(直接监护人)
+                  <p class={styles.tips}>手机号是音乐数字课堂的唯一登录账户</p>
+                </div>
+              )
+            }}
+          </Field>
+          <Field
+            center
+            clearable
+            label="验证码"
+            placeholder="请输入验证码"
+            autocomplete="off"
+            type="number"
+            v-model={studentInfo.password}
+            maxlength={6}>
+            {{
+              button: () =>
+                forms.countDownStatus ? (
+                  <span
+                    class={[
+                      styles.codeText,
+                      !validatePhone.value ? styles.codeTextDisabled : ''
+                    ]}
+                    onClick={onSendCode}>
+                    获取验证码
+                  </span>
+                ) : (
+                  <CountDown
+                    ref={(el: any) => (countDownRef.value = el)}
+                    auto-start={false}
+                    time={forms.countDownTime}
+                    onFinish={onFinished}
+                    format="ss秒"
+                  />
+                )
+            }}
+          </Field>
+          <Field
+            clearable
+            label="学生姓名"
+            placeholder="请输入学生姓名"
+            autocomplete="off"
+            maxlength={14}
+            v-model={studentInfo.extra.nickname}
+          />
+          <Field
+            clearable
+            label="学生性别"
+            placeholder="请选择性别"
+            autocomplete="off"
+            // v-model={studentInfo.extra.nickname}
+          >
+            {{
+              input: () => (
+                <RadioGroup
+                  checked-color="#ffcb75"
+                  v-model={studentInfo.extra.gender}
+                  direction="horizontal">
+                  <Tag
+                    size="large"
+                    type="primary"
+                    color={
+                      !(studentInfo.extra.gender === 1) ? '#EAEAEA' : '#ffcb75'
+                    }
+                    textColor={
+                      !(studentInfo.extra.gender === 1) ? '#AAA' : '#5B2C03'
+                    }
+                    class={styles.radioSection}
+                    round>
+                    <Radio class={styles.radioItem} name={1}></Radio>男
+                  </Tag>
+                  <Tag
+                    size="large"
+                    type="primary"
+                    color={
+                      !(studentInfo.extra.gender === 0) ? '#EAEAEA' : '#ffcb75'
+                    }
+                    textColor={
+                      !(studentInfo.extra.gender === 0) ? '#AAA' : '#5B2C03'
+                    }
+                    class={styles.radioSection}
+                    round>
+                    <Radio class={styles.radioItem} name={0}></Radio>女
+                  </Tag>
+                </RadioGroup>
+              )
+            }}
+          </Field>
+          <Field
+            clearable
+            label="所在年级"
+            placeholder="请选择年级"
+            isLink
+            readonly
+            clickable={false}
+            modelValue={forms.gradeNumText}
+            onClick={() => (forms.gradeStatus = true)}
+          />
+          <Field
+            clearable
+            label="所在班级"
+            placeholder="请选择班级"
+            isLink
+            readonly
+            clickable={false}
+            modelValue={forms.currentClassText}
+            onClick={() => (forms.classStatus = true)}
+          />
+        </Form>
+        {/* <MProtocol
+          center
+          v-model:modelValue={forms.modelValue}
+          prototcolType="REGISTER"
+        /> */}
+
+        <MSticky position="bottom">
+          <Button
+            type="primary"
+            class={styles.submitBtn}
+            color="linear-gradient(121deg, #FFD892 0%, #FFCB75 100%)"
+            block
+            onClick={onSubmit}
+            disabled={forms.loading}
+            loading={forms.loading}>
+            确认
+          </Button>
+        </MSticky>
+
+        {forms.imgCodeStatus ? (
+          <MImgCode
+            v-model:value={forms.imgCodeStatus}
+            phone={studentInfo.username}
+            onClose={() => {
+              forms.imgCodeStatus = false;
+            }}
+            onSendCode={onCodeSend}
+          />
+        ) : null}
+
+        {/* 年级 */}
+        <Popup
+          v-model:show={forms.gradeStatus}
+          position="bottom"
+          round
+          safeAreaInsetBottom
+          lazyRender={false}
+          class={'popupBottomSearch'}>
+          <Picker
+            showToolbar
+            columns={gradeList.value as any}
+            onCancel={() => (forms.gradeStatus = false)}
+            onConfirm={(val: any) => {
+              const selectedOption = val.selectedOptions[0];
+              studentInfo.extra.currentGradeNum = selectedOption.value;
+              forms.gradeNumText = selectedOption.text;
+              forms.gradeStatus = false;
+            }}
+          />
+        </Popup>
+        {/* 班级 */}
+        <Popup
+          v-model:show={forms.classStatus}
+          position="bottom"
+          round
+          class={'popupBottomSearch'}>
+          <Picker
+            showToolbar
+            columns={classList}
+            onCancel={() => (forms.classStatus = false)}
+            onConfirm={(val: any) => {
+              const selectedOption = val.selectedOptions[0];
+              studentInfo.extra.currentClass = selectedOption.value;
+              forms.currentClassText = selectedOption.text;
+              forms.classStatus = false;
+            }}
+          />
+        </Popup>
+        {/* 是否在微信中打开 */}
+        <OWxTip />
+      </div>
+    );
+  }
+});