|
@@ -0,0 +1,347 @@
|
|
|
+import { defineComponent, nextTick, onMounted, onUnmounted, reactive, ref } from 'vue'
|
|
|
+import styles from './index.module.less'
|
|
|
+import headTitle from './images/header-title.png'
|
|
|
+import headPhone from './images/header-phone.png'
|
|
|
+import headBg from './images/header-bg.png'
|
|
|
+import { Button, CellGroup, Field, Form, Radio, RadioGroup, Tag, showToast } from 'vant'
|
|
|
+import { useRoute, useRouter } from 'vue-router'
|
|
|
+
|
|
|
+// 乐团交付,乐团停止或关闭,有新的交付团;则不允许报名
|
|
|
+const classList: any = []
|
|
|
+for (let i = 1; i <= 40; i++) {
|
|
|
+ classList.push({ text: i + '班', value: i })
|
|
|
+}
|
|
|
+
|
|
|
+export default defineComponent({
|
|
|
+ name: 'pre-goods-apply',
|
|
|
+ setup() {
|
|
|
+ const route = useRoute()
|
|
|
+
|
|
|
+ // 获取是否已经看过训练工具图片
|
|
|
+ const state = reactive({
|
|
|
+ code: '' as any, // 微信授权code码
|
|
|
+ detail: {} as any, // 学员详情
|
|
|
+ toolImgStatus: false,
|
|
|
+ currentGrade: [
|
|
|
+ { text: '一年级', value: 1 },
|
|
|
+ { text: '二年级', value: 2 },
|
|
|
+ { text: '三年级', value: 3 },
|
|
|
+ { text: '四年级', value: 4 },
|
|
|
+ { text: '五年级', value: 5 },
|
|
|
+ { text: '六年级', value: 6 },
|
|
|
+ { text: '七年级', value: 7 },
|
|
|
+ { text: '八年级', value: 8 },
|
|
|
+ { text: '九年级', value: 9 }
|
|
|
+ ], // 年级数组列表
|
|
|
+ classList: classList,
|
|
|
+ subjectList: [] as any, // 选报声部列表
|
|
|
+ instrumentsInspectionDescribe: '', // 配置信息
|
|
|
+ inspectPopupStatus: false, // 查看说明
|
|
|
+ gradeStatus: false,
|
|
|
+ classStatus: false,
|
|
|
+ subjectStatus: false,
|
|
|
+ registerInfo: {} as any, // 乐团信息
|
|
|
+ goodsInfo: {} as any, // 商品
|
|
|
+ textBookInfo: {} as any, // 教材
|
|
|
+ inspectInfo: {} as any, // 乐器检查
|
|
|
+ vipYearInfo: {} as any, // 学练工具
|
|
|
+ inspectStatus: true,
|
|
|
+ // 是否开启微信登录(测试使用)默认为false
|
|
|
+ testIsWeixin: false,
|
|
|
+ details: [] as any, //
|
|
|
+ pattern: /^1(3|4|5|6|7|8|9)\d{9}$/,
|
|
|
+ nameReg: /^[\u4E00-\u9FA5]+$/,
|
|
|
+ paymentType: '',
|
|
|
+ musicPaymentType: '', // 乐团中对应支付方式
|
|
|
+ studentReadStatus: false, // 学生在读
|
|
|
+ dialogStatus: false,
|
|
|
+ dialogMessage: '',
|
|
|
+ dialogOrchestraStatus: false, // 是否为不同的乐团
|
|
|
+ dialogConfig: {} as any,
|
|
|
+ orderInfo: {
|
|
|
+ needPrice: 0,
|
|
|
+ originalPrice: 0
|
|
|
+ },
|
|
|
+ submitStatus: false
|
|
|
+ })
|
|
|
+ const forms = reactive({
|
|
|
+ username: null,
|
|
|
+ sex: null as any,
|
|
|
+ currentGrade: null,
|
|
|
+ currentGradeTxt: null, // 年级编号
|
|
|
+ currentClass: '', // 班级
|
|
|
+ currentClassTxt: null, // 年级编号
|
|
|
+ registerSubjectId: '',
|
|
|
+ registerSubjectTxt: null, // 所在选报声部
|
|
|
+ parentName: null,
|
|
|
+ groupBuyType: '' as any,
|
|
|
+ phone: null as any,
|
|
|
+ learningTools: null,
|
|
|
+ instrumentsBrand: null
|
|
|
+ })
|
|
|
+
|
|
|
+ const validator = (val: any) => {
|
|
|
+ // 校验函数返回 true 表示校验通过,false 表示不通过
|
|
|
+ return state.nameReg.test(val) && val.length >= 2 && val.length <= 15
|
|
|
+ }
|
|
|
+
|
|
|
+ const message = (value: any) => {
|
|
|
+ if (!value) {
|
|
|
+ return '请填写学员真实姓名'
|
|
|
+ } else if (!state.nameReg.test(value)) {
|
|
|
+ return '学员姓名必须为中文'
|
|
|
+ } else if (value.length < 2 || value.length > 15) {
|
|
|
+ return '学员姓名必须为2~15个字'
|
|
|
+ } else {
|
|
|
+ return ''
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ // 乐团报名
|
|
|
+ const onSubmit = async () => {
|
|
|
+ //
|
|
|
+ }
|
|
|
+
|
|
|
+ const messageContent = ref('')
|
|
|
+ const orchestraName = ref(route.query.orchestraName || '') // 乐团名称
|
|
|
+ const getMessage = (ev: any) => {
|
|
|
+ if (ev.data.api === 'payment-notes') {
|
|
|
+ messageContent.value = ev.data.message || ''
|
|
|
+ // document.body
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ onMounted(() => {
|
|
|
+ nextTick(() => {
|
|
|
+ // 是否加载完成
|
|
|
+ window.parent &&
|
|
|
+ window.parent.postMessage(
|
|
|
+ {
|
|
|
+ api: 'onLoad',
|
|
|
+ status: true
|
|
|
+ },
|
|
|
+ '*'
|
|
|
+ )
|
|
|
+ })
|
|
|
+
|
|
|
+ window.addEventListener('message', getMessage)
|
|
|
+ })
|
|
|
+
|
|
|
+ onUnmounted(() => {
|
|
|
+ window.removeEventListener('message', getMessage)
|
|
|
+ })
|
|
|
+ return () => (
|
|
|
+ <div class={styles.goodsApply}>
|
|
|
+ <img src={headBg} class={styles.headBg} />
|
|
|
+ <div class={styles.goodsHeader}>
|
|
|
+ <div class={styles.orchestraTitle}>
|
|
|
+ <img class={styles.headTitle} src={headTitle} />
|
|
|
+ <p class={[styles.name, 'van-multi-ellipsis--l3']}>{orchestraName.value}</p>
|
|
|
+ </div>
|
|
|
+ <img src={headPhone} class={styles.headPhone} />
|
|
|
+ </div>
|
|
|
+ <Form
|
|
|
+ validateFirst
|
|
|
+ errorMessageAlign="right"
|
|
|
+ scrollToError={true}
|
|
|
+ onSubmit={onSubmit}
|
|
|
+ onFailed={(e: any) => {
|
|
|
+ // 获取第一个校验错误的元素
|
|
|
+ nextTick(() => {
|
|
|
+ const isError = document.getElementsByClassName('van-field__error-message')
|
|
|
+ // 滚动到错误元素对应位置
|
|
|
+ isError[0]?.scrollIntoView({
|
|
|
+ block: 'center',
|
|
|
+ behavior: 'smooth'
|
|
|
+ })
|
|
|
+ })
|
|
|
+ }}
|
|
|
+ ref="form"
|
|
|
+ class={styles.form}
|
|
|
+ >
|
|
|
+ <CellGroup class={styles.applyCellGroup} border={false} style={{ display: 'none' }}>
|
|
|
+ <div class={[styles.title, styles.titleApply]}></div>
|
|
|
+ <Field
|
|
|
+ required
|
|
|
+ label="学员信息"
|
|
|
+ placeholder="请填写学员真实姓名"
|
|
|
+ inputAlign="right"
|
|
|
+ v-model={forms.username}
|
|
|
+ maxlength={15}
|
|
|
+ rules={[{ validator, message }]}
|
|
|
+ />
|
|
|
+ <Field
|
|
|
+ required
|
|
|
+ label="性别"
|
|
|
+ inputAlign="right"
|
|
|
+ rules={[{ required: true, message: '请选择性别' }]}
|
|
|
+ >
|
|
|
+ {{
|
|
|
+ input: () => (
|
|
|
+ <RadioGroup v-model={forms.sex}>
|
|
|
+ <Tag
|
|
|
+ size="large"
|
|
|
+ type="primary"
|
|
|
+ class={[styles.radioSection, forms.sex === 1 ? styles.active : '']}
|
|
|
+ >
|
|
|
+ <Radio class={styles.radioItem} name={1}></Radio>
|
|
|
+ 男生
|
|
|
+ </Tag>
|
|
|
+ <Tag
|
|
|
+ size="large"
|
|
|
+ type="primary"
|
|
|
+ class={[styles.radioSection, forms.sex === 0 ? styles.active : '']}
|
|
|
+ >
|
|
|
+ <Radio class={styles.radioItem} name={0}></Radio>女生
|
|
|
+ </Tag>
|
|
|
+ </RadioGroup>
|
|
|
+ )
|
|
|
+ }}
|
|
|
+ </Field>
|
|
|
+ <Field
|
|
|
+ required
|
|
|
+ label="年级"
|
|
|
+ inputAlign="right"
|
|
|
+ readonly
|
|
|
+ isLink
|
|
|
+ clickable={false}
|
|
|
+ placeholder="请选择年级"
|
|
|
+ v-model={forms.currentGradeTxt}
|
|
|
+ onClick={() => (state.gradeStatus = true)}
|
|
|
+ rules={[{ required: true, message: '请选择年级' }]}
|
|
|
+ />
|
|
|
+ <Field
|
|
|
+ required
|
|
|
+ label="班级"
|
|
|
+ inputAlign="right"
|
|
|
+ readonly
|
|
|
+ isLink
|
|
|
+ clickable={false}
|
|
|
+ placeholder="请选择班级"
|
|
|
+ v-model={forms.currentClassTxt}
|
|
|
+ onClick={() => (state.classStatus = true)}
|
|
|
+ rules={[{ required: true, message: '请选择班级' }]}
|
|
|
+ />
|
|
|
+ <Field
|
|
|
+ required
|
|
|
+ label="选报声部"
|
|
|
+ inputAlign="right"
|
|
|
+ readonly
|
|
|
+ isLink
|
|
|
+ clickable={false}
|
|
|
+ placeholder="请选择选报声部"
|
|
|
+ v-model={forms.registerSubjectTxt}
|
|
|
+ onClick={() => {
|
|
|
+ if (state.subjectList.length <= 0) {
|
|
|
+ showToast('暂无报名选报声部')
|
|
|
+ return
|
|
|
+ }
|
|
|
+ state.subjectStatus = true
|
|
|
+ }}
|
|
|
+ rules={[{ required: true, message: '请选择选报声部' }]}
|
|
|
+ />
|
|
|
+ </CellGroup>
|
|
|
+
|
|
|
+ <CellGroup class={styles.applyCellGroup} border={false}>
|
|
|
+ <div class={[styles.title, styles.titleParent]}></div>
|
|
|
+ <Field
|
|
|
+ required
|
|
|
+ label="家长姓名"
|
|
|
+ inputAlign="right"
|
|
|
+ placeholder="请填写家长真实姓名"
|
|
|
+ v-model={forms.parentName}
|
|
|
+ maxlength={15}
|
|
|
+ // rules={[{ required: true, message: '请填写家长真实姓名' }]}
|
|
|
+ />
|
|
|
+ <Field
|
|
|
+ required
|
|
|
+ label="手机号"
|
|
|
+ inputAlign="right"
|
|
|
+ placeholder="请输入手机号"
|
|
|
+ v-model={forms.phone}
|
|
|
+ maxlength={11}
|
|
|
+ type="tel"
|
|
|
+ // rules={[{ pattern: state.pattern, message: '输入监护人手机号码有误' }]}
|
|
|
+ />
|
|
|
+ </CellGroup>
|
|
|
+
|
|
|
+ <CellGroup class={styles.applyCellGroup} border={false}>
|
|
|
+ <div class={[styles.title, styles.titleTips]}></div>
|
|
|
+
|
|
|
+ <div class={styles.tipsContainer} v-html={messageContent.value}>
|
|
|
+ {/* <p class={styles.line}>
|
|
|
+ <i class={[styles.num, styles.numOne]}></i>
|
|
|
+ 为保障乐团训练质量,开训前,家长务必准备好①乐器和②管乐AI学练工具,准备方式不限;
|
|
|
+ </p>
|
|
|
+ <p class={styles.line}>
|
|
|
+ <i class={[styles.num, styles.numTwo]}></i>
|
|
|
+ 为了降低家长投入压力,可参与项目支持方提供的AI学练工具团购,政策如下:
|
|
|
+ <p class={[styles.child]}>
|
|
|
+ 1、支持方<span style="color: #F67146">免费</span>
|
|
|
+ 提供一支全新乐器供学生训练(可带回家) ;<br />
|
|
|
+ 2、乐器提供时间为一年,如期满继续训练,乐器将
|
|
|
+ <span style="color: #F67146">赠送</span>至学生以作鼓励;
|
|
|
+ <br />
|
|
|
+ 3、如期间或期满不再训练,家长归还乐器即可,
|
|
|
+ <span style="color: #F67146">无需额外支付</span>乐器费用。
|
|
|
+ </p>
|
|
|
+ </p> */}
|
|
|
+ </div>
|
|
|
+ </CellGroup>
|
|
|
+
|
|
|
+ <CellGroup class={styles.applyCellGroup} border={false}>
|
|
|
+ <div class={[styles.title, styles.titleTool]}></div>
|
|
|
+ <Field
|
|
|
+ required
|
|
|
+ label="请选择训练工具的准备方式:"
|
|
|
+ labelAlign="top"
|
|
|
+ rules={[{ required: true, message: '请选择训练工具的准备方式' }]}
|
|
|
+ >
|
|
|
+ {{
|
|
|
+ input: () => (
|
|
|
+ <RadioGroup v-model={forms.groupBuyType} class={styles.toolRadioGroup}>
|
|
|
+ <Tag
|
|
|
+ size="large"
|
|
|
+ type="primary"
|
|
|
+ class={[
|
|
|
+ styles.radioSectionTag,
|
|
|
+ styles.radioSection,
|
|
|
+ forms.groupBuyType === 'GROUP_BUY' ? styles.active : ''
|
|
|
+ ]}
|
|
|
+ >
|
|
|
+ <Radio
|
|
|
+ class={styles.radioItem}
|
|
|
+ name={'GROUP_BUY'}
|
|
|
+ disabled={true}
|
|
|
+ onClick={() => {
|
|
|
+ // if (!forms.registerSubjectId) {
|
|
|
+ // showToast('请选择选报声部')
|
|
|
+ // return
|
|
|
+ // }
|
|
|
+ }}
|
|
|
+ ></Radio>
|
|
|
+ 统一团购
|
|
|
+ <p class={styles.radioTip}>团购AI工具,乐器免费提供</p>
|
|
|
+ </Tag>
|
|
|
+ <Tag
|
|
|
+ size="large"
|
|
|
+ type="primary"
|
|
|
+ class={[
|
|
|
+ styles.radioSectionTag,
|
|
|
+ styles.radioSection,
|
|
|
+ forms.groupBuyType === 'SELF' ? styles.active : ''
|
|
|
+ ]}
|
|
|
+ >
|
|
|
+ <Radio class={styles.radioItem} name={'SELF'} disabled></Radio>自行准备
|
|
|
+ <p class={styles.radioTip}>AI工具和乐器自行准备</p>
|
|
|
+ </Tag>
|
|
|
+ </RadioGroup>
|
|
|
+ )
|
|
|
+ }}
|
|
|
+ </Field>
|
|
|
+ </CellGroup>
|
|
|
+ </Form>
|
|
|
+ </div>
|
|
|
+ )
|
|
|
+ }
|
|
|
+})
|