|
|
@@ -19,9 +19,9 @@
|
|
|
<text class="meta-date">{{ formatDate(article.publishedAt) }}</text>
|
|
|
<text class="meta-sep">|</text>
|
|
|
<text class="meta-readtime">{{ article.readTime || 3 }}分钟阅读</text>
|
|
|
- <text class="reading-time-badge" v-if="currentChildId && !readingCompleted">{{ formatReadingTime(readingSeconds) }}</text>
|
|
|
- <text class="reading-time-badge completed" v-else-if="currentChildId && readingCompleted">✅ 阅读完成</text>
|
|
|
- <text class="meta-sep" v-if="currentChildId">|</text>
|
|
|
+ <text class="reading-time-badge" v-if="isLogin && !readingCompleted">{{ formatReadingTime(readingSeconds) }}</text>
|
|
|
+ <text class="reading-time-badge completed" v-else-if="isLogin && readingCompleted">✅ 阅读完成</text>
|
|
|
+ <text class="meta-sep" v-if="isLogin">|</text>
|
|
|
<text class="meta-readcount">{{ article.viewCount || 0 }}人阅读</text>
|
|
|
</view>
|
|
|
<view class="detail-category-row">
|
|
|
@@ -85,7 +85,7 @@
|
|
|
</template>
|
|
|
|
|
|
<script>
|
|
|
-import { getArticleDetail, reportReadingTime, getShareQrCode, completeArticleRead, generateQuiz, submitQuiz, getMyMembership } from '@/utils/api.js'
|
|
|
+import { getArticleDetail, reportReadingTime, getShareQrCode, completeArticleRead, generateQuiz, submitQuiz } from '@/utils/api.js'
|
|
|
import shareMixin from '../../components/share-mixin.js'
|
|
|
import ContentSharePoster from '@/components/ContentSharePoster.vue'
|
|
|
import MpHtml from '@/components/mp-html/mp-html.vue'
|
|
|
@@ -99,7 +99,7 @@ export default {
|
|
|
articleId: '', article: null, loading: true, error: false, errorMsg: '',
|
|
|
readingSeconds: 0, lastReportedSeconds: 0, readingCompleted: false,
|
|
|
isTimerRunning: false, timerHandle: null, syncHandle: null,
|
|
|
- currentChildId: null,
|
|
|
+ currentChildId: null, isLogin: false,
|
|
|
showPoster: false, posterQrCode: '',
|
|
|
posterDimension: '', posterSummary: '', posterInviteText: '',
|
|
|
contentTagStyle: { p: 'font-size:32rpx;color:#444;line-height:1.8;', div: 'font-size:32rpx;color:#444;line-height:1.8;', section: 'font-size:32rpx;color:#444;line-height:1.8;', li: 'font-size:32rpx;color:#444;line-height:1.8;', blockquote: 'font-size:32rpx;color:#444;line-height:1.8;' },
|
|
|
@@ -132,11 +132,13 @@ export default {
|
|
|
if (aid) { this.articleId = aid; this.loadDetail(aid) }
|
|
|
else { this.error = true; this.errorMsg = '参数错误'; this.loading = false }
|
|
|
this.currentChildId = uni.getStorageSync('currentChildId') || null
|
|
|
+ this.isLogin = !!uni.getStorageSync('token')
|
|
|
},
|
|
|
onShow() {
|
|
|
var memberId = uni.getStorageSync('currentChildId')
|
|
|
- if (!this.article || this.error || !memberId) return
|
|
|
- this.startNewReadingSession()
|
|
|
+ if (!this.article || this.error) return
|
|
|
+ // 已登录用户(家长/孩子/规划师)均可计时,匿名用户不计时
|
|
|
+ if (this.isLogin) this.startNewReadingSession()
|
|
|
},
|
|
|
onHide() { this.pauseReadingTimer() },
|
|
|
onUnload() { this.pauseReadingTimer() },
|
|
|
@@ -195,9 +197,16 @@ export default {
|
|
|
this.lastReportedSeconds = 0
|
|
|
this.startReadingTimer()
|
|
|
},
|
|
|
+ // 获取当前操作对象的 memberId:优先 currentChildId(切换视角),否则用 userId
|
|
|
+ getActiveMemberId: function() {
|
|
|
+ var mid = uni.getStorageSync('currentChildId')
|
|
|
+ if (mid) return parseInt(mid)
|
|
|
+ var uid = uni.getStorageSync('userId')
|
|
|
+ return uid ? parseInt(uid) : null
|
|
|
+ },
|
|
|
startReadingTimer: function() {
|
|
|
- var memberId = uni.getStorageSync('currentChildId')
|
|
|
- if (!memberId) return
|
|
|
+ // 无登录态时不计时(匿名浏览只显示时长要求,不计时)
|
|
|
+ if (!this.isLogin) return
|
|
|
if (this.isTimerRunning || this.readingCompleted) return
|
|
|
this.isTimerRunning = true
|
|
|
var self = this
|
|
|
@@ -216,18 +225,18 @@ export default {
|
|
|
var delta = this.readingSeconds - this.lastReportedSeconds
|
|
|
if (delta <= 0) return
|
|
|
this.lastReportedSeconds = this.readingSeconds
|
|
|
- var memberId = uni.getStorageSync('currentChildId')
|
|
|
- if (!memberId || !this.article) return
|
|
|
- reportReadingTime({ articleId: this.article.id, memberId: parseInt(memberId), durationSeconds: delta })
|
|
|
+ var memberId = this.getActiveMemberId()
|
|
|
+ if (!this.isLogin || !this.article) return
|
|
|
+ reportReadingTime({ articleId: this.article.id, memberId: memberId || 0, durationSeconds: delta })
|
|
|
|
|
|
// 达到阅读时长自动完成
|
|
|
var targetSeconds = (this.article.readTime || 3) * 60
|
|
|
if (!this.readingCompleted && this.readingSeconds >= targetSeconds) {
|
|
|
this.readingCompleted = true
|
|
|
this.pauseReadingTimer()
|
|
|
- try { await completeArticleRead({ articleId: this.article.id, memberId: parseInt(memberId), durationSeconds: this.readingSeconds }) } catch (e) {}
|
|
|
+ try { await completeArticleRead({ articleId: this.article.id, memberId: memberId || 0, durationSeconds: this.readingSeconds }) } catch (e) {}
|
|
|
uni.showToast({ title: '阅读完成 +5能量', icon: 'success' })
|
|
|
- // 弹出答题
|
|
|
+ // 弹出答题(登录用户)
|
|
|
this.startQuiz()
|
|
|
}
|
|
|
},
|
|
|
@@ -260,15 +269,14 @@ export default {
|
|
|
},
|
|
|
// 答题
|
|
|
async startQuiz() {
|
|
|
+ if (!this.isLogin) {
|
|
|
+ uni.showToast({ title: '登录后即可完成知识测评', icon: 'none' })
|
|
|
+ setTimeout(function() { uni.navigateTo({ url: '/pages/login/login' }) }, 1500)
|
|
|
+ return
|
|
|
+ }
|
|
|
+ var memberId = this.getActiveMemberId()
|
|
|
try {
|
|
|
- var memRes = await getMyMembership()
|
|
|
- if (memRes.data && memRes.data.memberLevel && memRes.data.memberLevel === 'FREE') {
|
|
|
- uni.showToast({ title: '浠宝/福宝答题是会员专属', icon: 'none' })
|
|
|
- setTimeout(function() { uni.navigateTo({ url: '/pages/membership/upgrade' }) }, 1500)
|
|
|
- return
|
|
|
- }
|
|
|
- var memberId = uni.getStorageSync('currentChildId')
|
|
|
- var res = await generateQuiz({ articleId: this.articleId, memberId: parseInt(memberId || 0) })
|
|
|
+ var res = await generateQuiz({ articleId: this.articleId, memberId: memberId || 0 })
|
|
|
if (res.code === 200 && res.data && res.data.questions && res.data.questions.length > 0) {
|
|
|
this.quizRecordId = res.data.recordId
|
|
|
this.quizQuestions = res.data.questions
|
|
|
@@ -278,7 +286,7 @@ export default {
|
|
|
} catch (e) {}
|
|
|
},
|
|
|
async submitQuiz() {
|
|
|
- var memberId = uni.getStorageSync('currentChildId')
|
|
|
+ var memberId = this.getActiveMemberId()
|
|
|
var answers = []
|
|
|
for (var i = 0; i < this.quizQuestions.length; i++) {
|
|
|
answers.push(this.quizAnswers[i] || '')
|