import React from 'react'; import './index.less'; import { Icon } from 'antd'; import Page from '@src/containers/Page'; import Assets from '@src/components/Assets'; import { asyncSMessage } from '@src/services/AsyncTools'; import { formatDate } from '@src/services/Tools'; import UserLayout from '../../../layouts/User'; import UserAction from '../../../components/UserAction'; import menu from '../index'; import Tabs from '../../../components/Tabs'; import More from '../../../components/More'; import Button from '../../../components/Button'; import Switch from '../../../components/Switch'; import TotalSort from '../../../components/TotalSort'; import Modal from '../../../components/Modal'; import UserTable from '../../../components/UserTable'; import { My } from '../../../stores/my'; import { User } from '../../../stores/user'; import { Order } from '../../../stores/order'; import { Textbook } from '../../../stores/textbook'; import { DataType } from '../../../../Constant'; import { Main } from '../../../stores/main'; import { Question } from '../../../stores/question'; const dataHistoryColumns = [ { title: '更新时间', key: 'time', width: 120 }, { title: '位置', key: 'position', width: 120 }, { title: '原内容', key: 'originContent', width: 120 }, { title: '更改为', key: 'content', width: 120 }, { title: '更新至', key: 'version', width: 90 }, ]; const textbookHistoryColumns = [ { title: '更新时间', key: 'createTime', width: 120 }, { title: '版本', key: 'version', width: 90 }, { title: '内容', key: 'content', width: 360 }, ]; const openColumns = [ { title: '商品名称', key: 'title', width: 240 }, { title: '开通期限', key: 'endTime', width: 240 }, { title: '操作', key: 'handler', width: 90 }, ]; export default class extends Page { initState() { return { tab: 'data', sortMap: {}, filterMap: {}, }; } initData() { const data = Object.assign(this.state, this.state.search); if (data.order) { data.sortMap = { [data.order]: data.direction }; } data.filterMap = this.state.search; this.setState(data); const { tab } = this.state; switch (tab) { case 'textbook': this.refreshTextbook(); break; case 'examination': this.refreshExamination(); break; case 'vip': this.refreshVip(); break; case 'cal': break; case 'data': default: this.refreshData(); break; } } refreshTextbook() { Main.getService('textbook').then(result => { this.setState({ service: result }); }); Textbook.getInfo() .then(result => { const { latest } = result; result.day = parseInt((new Date().getTime() - new Date(result.latest.startDate).getTime()) / 86400000, 10); result.expireDay = result.expireTime && parseInt((new Date().getTime() - new Date(result.expireTime).getTime()) / 86400000, 10); const list = []; list.push({ subject: 'quant', number: latest.quantNumber, time: latest.quantTime, version: latest.quantVersion }); list.push({ subject: 'rc', number: latest.rcNumber, time: latest.rcTime, version: latest.rcVersion }); list.push({ subject: 'ir', number: latest.irNumber, time: latest.irTime, version: latest.irVersion }); this.setState({ data: result, list }); }); } textbookHistory({ page, size, subject }) { Textbook.listHistory({ subject }) .then(result => { this.setState({ updateList: result.map(row => { row.version = row[`${subject}Version`]; row.content = row[`${subject}Content`]; row.createTime = formatDate(row.createTime, 'YYYY-MM-DD\nHH:mm:ss'); return row; }), updateTotal: result.length, updatePage: page, updateData: { page, size, subject, columns: textbookHistoryColumns, type: 'textbook' }, }); }); } refreshExamination() { Main.getService('qx_cat').then(result => { this.setState({ service: result }); }); Question.getExaminationInfo(result => { result.expireDay = result.expireTime && parseInt((new Date().getTime() - new Date(result.expireTime).getTime()) / 86400000, 10); this.setState({ data: result }); }); } refreshVip() { Main.getService('vip').then(result => { this.setState({ service: result }); }); } recordList({ page, size, service, isUse }) { Order.listRecord({ page, size, productType: 'service', service, isUse }) .then(result => { this.setState({ updateList: result.map(row => { row.handler = <a onClick={() => { this.open(row.id); }}>立即开通</a>; row.endTime = `${formatDate(row.endTime, 'YYYY-MM-DD')} 前`; return row; }), updateTotal: result.length, updatePage: page, updateData: { page, size, service, isUse, columns: isUse ? [] : openColumns, type: 'record' }, }); }); } refreshData() { const dataTypeSelect = DataType.map(row => { row.title = row.label; row.key = row.value; return row; }); dataTypeSelect.unshift({ title: '全部', key: '', }); this.setState({ dataTypeSelect }); Main.dataStruct().then(result => { const structs = result.filter(row => row.level === 1).map(row => { row.title = `${row.titleZh}${row.titleEn}`; row.key = `${row.id}`; return row; }); structs.unshift({ title: '全部', key: '', }); this.setState({ structs, }); }); My.listData(Object.assign({}, this.state.search)) .then(result => { result = { list: [{ title: '123123', latestTime: '', id: 1, number: 10, version: '1231', }], }; this.setState({ list: result.list.map(row => { row.time = formatDate(row.time, 'YYYY-MM-DD HH:mm:ss'); return row; }), total: result.total, }); }); } dataHistory({ dataId, page, size }) { My.listDataHistory({ page, size, dataId }) .then(result => { result.list = result.list.map(row => { row.time = formatDate(row.time, 'YYYY-MM-DD\nHH:mm:ss'); return row; }); this.setState({ updateList: result.list, updateTotal: result.total, updatePage: page, updateData: { page, size, dataId, columns: dataHistoryColumns, type: 'data' } }); }); } onFilter(value) { this.search(value); } onSort(value) { const keys = Object.keys(value); this.search({ order: keys.length ? keys[0] : null, direction: keys.length ? value[keys[0]] : null }); } onTabChange(tab) { const data = { tab }; this.refreshQuery(data); } submitComment() { const { comment } = this.state; My.addComment(comment.channel, comment.position, comment.content) .then(() => { this.setState({ showComment: false, showFinish: true, comment: {} }); }); } submitFeedbackError() { const { feedbackError } = this.state; My.addFeedbackErrorData(feedbackError.dataId, feedbackError.title, feedbackError.position, feedbackError.originContent, feedbackError.content) .then(() => { this.setState({ showFinish: true, showFeedbackError: false, feedbackError: {} }); }); } submitFeedback() { const { feedback } = this.state; My.addTextbookFeedback('', feedback.target, feedback.content) .then(() => { this.setState({ showFinish: true, showFeedback: false, feedbackError: {} }); }); } subscribe(value) { My.subscribeData(value) .then(() => { const { info } = this.props.user; info.dataEmailSubscribe = value; User.infoHandle(info); }) .catch(err => { asyncSMessage(err.message, 'warn'); }); } open(recordId) { Order.useRecord(recordId).then(() => { asyncSMessage('开通成功'); this.refresh(); }); } renderView() { const { config } = this.props; return <UserLayout active={config.key} menu={menu} center={this.renderDetail()} />; } renderDetail() { const { tab, comment = {}, showComment, showFinish, showUpdate, updateList, updateTotal, updateData = {} } = this.state; return ( <div className="table-layout"> <Tabs border type="division" theme="theme" size="small" space={2.5} width={100} active={tab} tabs={[ { key: 'data', title: '资料' }, { key: 'textbook', title: '机经' }, { key: 'examination', title: '模考' }, { key: 'vip', title: 'VIP' }, { key: 'cal', title: '考分计算器' }, ]} onChange={key => this.onTabChange(key)} /> {this[`renderTab${tab}`]()} <Modal show={showUpdate} maskClosable close={false} body={false} width={630} onClose={() => this.setState({ showUpdate: false, updateList: [] })} > <UserTable size="small" columns={updateData.columns} data={updateList} current={updateData.page} onChangePage={(page) => { updateData.page = page; if (updateData.type === 'data') { this.dataHistory(updateData); } else if (updateData.type === 'textbook') { this.textbookHistory(updateData); } else if (updateData.type === 'record') { this.recordList(updateData); } }} total={updateTotal} /> </Modal> <Modal show={showComment} title="评价" onConfirm={() => comment.content && this.submitComment()} onCancel={() => this.setState({ showComment: false, comment: {} })}> <textarea value={comment.content} className="b-c-1 w-10 p-10" rows={6} placeholder="您的看法对我们来说很重要!" onChange={(e) => { comment.content = e.target.value; this.setState({ comment }); }} /> <div className="b-b m-t-2" /> </Modal> <Modal show={showFinish} title="提交成功" confirmText="好的,知道了" btnAlign="center" onConfirm={() => this.setState({ showFinish: false })} > <div className="t-2 t-s-18"> <Icon type="check" className="t-5 m-r-5" /> 您的每一次反馈都是千行进步的动力。 </div> </Modal> </div> ); } renderTabdata() { const { list = [], filterMap = {}, sortMap = {}, structs, dataTypeSelect } = this.state; const { info } = this.props.user; return ( <div className="tab-1-layout"> <UserAction selectList={[{ label: '学科', key: 'structId', select: structs, }, { label: '资料形式', key: 'dataType', select: dataTypeSelect, }]} sortList={[{ right: true, label: '销量', key: 'sale_number' }, { right: true, label: '更新时间', key: 'latest_time' }]} sortMap={sortMap} filterMap={filterMap} onFilter={value => this.onFilter(value)} onSort={value => this.onSort(value)} right={ <div className="email"> 邮箱订阅 <Switch checked={info.dataEmailSubscribe} onChange={() => { this.subscribe(!info.dataEmailSubscribe); }} /> </div> } /> <div className="data-layout"> {list.map(item => { return ( <div className="data-item"> <Assets name="sun_blue" src={item.cover} /> <div className="fixed"> <div className="btns"> <Button size="small" radius onClick={() => { openLink(item.resource); }}> 阅读 </Button> <div className="white" onClick={() => { openLink(item.resource); }}>下载</div> </div> </div> <div className="title"> <span>版本{item.version}</span> {item.title} </div> <div className="date">{formatDate(item.latestTime, 'YYYY-MM-DD HH:mm:ss')}</div> <More menu={[{ label: '纠错', key: 'feedback' }, { label: '评价', key: 'comment' }, { label: '更新', key: 'update' }]} onClick={(value) => { const { key } = value; if (key === 'comment') { this.setState({ showComment: true, comment: { channel: 'course_data', position: item.id } }); } else if (key === 'update') { this.setState({ showUpdate: true }); this.dataHistory({ dataId: item.id, page: 1, size: 10 }); } else if (key === 'feedback') { this.setState({ showFeedbackError: true, feedbackError: { dataId: item.id, title: item.title } }); } }} /> </div> ); })} </div> </div> ); } renderTabtextbook() { const { data = {}, list = [], service } = this.state; const { latest = {}, day } = data; return ( <div className="tab-2-layout"> <UserAction left={ <div className="total-log"> <span>最新换库</span> <span>{latest.startDate ? formatDate(latest.startDate, 'YYYY-MM-DD') : ''}</span> <span> 已换库<b>{day}</b>天 </span> </div> } right={!data.hasService && data.unUseRecord && <div className="email" onClick={() => { this.recordList({ page: 1, size: 10, service: 'textbook', isUse: false }); }}>待开通</div>} /> {data.hasService && <div className="data-layout"> {list.map(item => { return ( <div className="data-item"> <Assets name="sun_blue" /> <div className="title"> 已更新至<b>{item.num}</b>题 </div> <div className="date">{item.date}</div> <More menu={[{ label: '更新', key: 'update' }, { label: '反馈', key: 'feedback' }, { label: '评价', key: 'comment' }]} onClick={(value) => { const { key } = value; if (key === 'comment') { this.setState({ showComment: true, comment: { channel: 'library' } }); } else if (key === 'update') { this.setState({ showUpdate: true }); this.textbookHistory({ page: 1, size: 100, subject: item.subject }); } else if (key === 'feedback') { this.setState({ showFeedback: true }); } }} /> </div> ); })} </div>} {!data.hasService && !data.unUseRecord && <div className="tip-layout"> <div className="t1">还未购买本月机经</div> <div className="desc">¥ {service && service.package && service.package[0].price}</div> <Button radius size="lager" width={150}> 立即购买 </Button> </div>} {data.hasService && <div className="tip-layout"> <div className="t1">使用中</div> <div className="t2">距离到期还有 {data.expireDay} 天</div> </div>} {!data.hasService && data.unUseRecord && <div className="tip-layout"> <div className="t2">请于{formatDate(data.unUseRecord.endTime, 'YYYY-MM-DD')}前开通</div> <Button radius size="lager" width={150} onClick={() => { this.open(data.unUseRecord.id); }}> 立即开通 </Button> </div>} </div> ); } renderTabexamination() { const { data = {}, service } = this.state; return ( <div className="tab-3-layout"> <UserAction right={data.unUseRecord && <div className="email" onClick={() => { this.recordList({ page: 1, size: 10, service: 'qx_cat', isUse: false }); }}>待开通</div>} /> {!data.hasService && !data.unUseRecord && !data.expireTime && <div className="tip-layout"> <div className="t1">未购买</div> <div className="desc">¥ {service && service.package && service.package[0].price}</div> <Button radius size="lager" width={150}> 立即购买 </Button> </div>} {!data.hasService && data.unUseRecord && <div className="tip-layout"> <div className="t2">请于{formatDate(data.unUseRecord.endTime, 'YYYY-MM-DD')}前开通</div> <Button radius size="lager" width={150} onClick={() => { this.open(data.unUseRecord.id); }}> 立即开通 </Button> </div>} {data.hasService && <div className="tip-layout"> <div className="t1">使用中</div> <div className="t2">距离到期还有 {data.expireDay} 天</div> </div>} {!data.hasService && !data.unUseRecord && data.expireTime && <div className="tip-layout"> <div className="t3">已过期</div> <div className="date">{formatDate(data.startTime, 'YYYY-MM-DD')} ~ {formatDate(data.expireTime, 'YYYY-MM-DD')}</div> <div className="desc">¥ {service && service.package && service.package[0].price}</div> <Button radius size="lager" width={150}> 立即购买 </Button> </div>} </div> ); } renderTabvip() { const { data } = this.state; return ( <div className="tab-4-layout"> {!data.hasService && !data.unUseRecord && !data.expireTime && <div className="tip-layout"> <div className="t2">未购买</div> <Button radius size="lager" width={150}> 立即购买 </Button> </div>} {data.hasService && <div className="tip-layout"> <div className="t1">使用中</div> <div className="desc">{formatDate(data.expireTime, 'YYYY-MM-DD')} 到期</div> <Button radius size="lager" width={150}> 续费 </Button> </div>} {!data.hasService && !data.unUseRecord && data.expireTime && <div className="tip-layout"> <div className="t1">已过期</div> <div className="desc">{formatDate(data.startTime, 'YYYY-MM-DD')} ~ {formatDate(data.expireTime, 'YYYY-MM-DD')}</div> <Button radius size="lager" width={150}> 立即购买 </Button> </div>} </div> ); } renderTabcal() { const { data = {} } = this.state; return ( <div className="tab-5-layout"> <TotalSort value={data.value || 650} onChange={(value) => { data.value = value; this.setState({ data }); }} /> </div> ); } }