Jelajahi Sumber

Signed-off-by: 李妹妹 <1639016684@qq.com>

李妹妹 10 jam lalu
induk
melakukan
f2a9e865d2

+ 1 - 1
pages/shopping/productDetails.vue

@@ -185,7 +185,7 @@
 		</popupBottom>
 
 		<view class="loadding" v-if="loadding==true">
-			<image src="../..https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/app/vip/share.png"></image>
+			<image src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/app/vip/share.png"></image>
 			<text class="text">加载中...</text>
 		</view>
     <CustomToast ref="customToast">

+ 1 - 1
pages_company/managerOrder/productDetails.vue

@@ -185,7 +185,7 @@
 		</popupBottom>
 
 		<view class="loadding" v-if="loadding==true">
-			<image src="../..https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/app/vip/share.png"></image>
+			<image src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/app/vip/share.png"></image>
 			<text class="text">加载中...</text>
 		</view>
     <CustomToast ref="customToast">

+ 5650 - 0
pages_course/video - 副本.vue

@@ -0,0 +1,5650 @@
+<!-- 自动发课看课页面 -->
+<template>
+	<view class="content">
+		<!-- <view class="header-nav" :style="{height: `calc(88rpx + ${statusBarHeight}px)`,paddingTop: statusBarHeight + 'px'}">
+			<view class="arrow-left-warning" @click="navback" v-if="isOpen==1">
+				<u-icon name="arrow-left" size='22' color="#222" bold></u-icon>
+			</view>
+			<view class="arrow-left-warning" v-else @click="feedback">
+				<image :src="imgPath+'/app/image/warning.png'"></image>
+				<text>投诉</text>
+			</view>
+			<view class="header-title" :style="{width:menuButtonLeft + 'px',height:menuButtonH+'px',lineHeight:menuButtonH+'px'}">{{courseInfo.title}}</view>
+		</view> -->
+		<view class="notice-box" v-if="isLogin&&isAddKf==1">
+			
+			<view class="notice-marquee-wrap">
+				<view class="notice-marquee-track">
+					<view class="notice-text"><image src="/static/images/notice.png"></image>{{notice || '央广网独家溯源&nbsp;&nbsp;全品类100%经过国标检测'}}</view>
+					<view class="notice-text"><image src="/static/images/notice.png"></image>{{notice || '央广网独家溯源&nbsp;&nbsp;全品类100%经过国标检测'}}</view>
+					<!-- <view class="notice-text"><image src="/static/images/notice.png"></image>央广网独家溯源&nbsp;&nbsp;全品类100%经过国标检测</view> -->
+				</view>
+			</view>
+		</view>
+		<view class="video-box" :style="{'height':isShu?'calc(100vh - 264rpx)':'420rpx'}">
+			<!-- <image v-if="!isLogin || isAddKf!=1" class="video-poster" :src="courseInfo.imgUrl" mode="aspectFill">
+			</image> -->
+			<video 
+			@timeupdate="onTimeUpdate" 
+			@progress="progressChange" 
+			@error="videoErrorCallback" 
+			@play="getPlay"
+			@pause="getPause" 
+			@ended="getEnded"
+			@controlstoggle="controlstoggle"
+			@fullscreenchange="fullscreenchange"
+			:title="courseInfo.title"
+			style="width: 100%" 
+			:style="{'height':isShu?'100%':'420rpx'}"
+			:poster="poster"  
+			id="video-content-box"  
+			controls
+			:auto-pause-if-open-native="true"
+			:auto-pause-if-navigate="true"
+			:enable-progress-gesture="false" 
+			:show-progress="showProgress"
+			:picture-in-picture-mode="[]"
+			:show-background-playback-button="false"
+			:src="videoUrl">
+			<!-- 完课积分倒计时 -->
+			<cover-view v-if="remainTime > 0" class="progress-countdown">
+				<cover-view class="progress-title">完课积分</cover-view>
+				<!-- <cover-view class="progress-bar-bg">
+					<cover-view class="progress-bar-fill" :style="{ width: countdownPercentage + '%' }"></cover-view>
+				</cover-view> -->
+				<cover-view class="progress-text">
+					<cover-view class="progress-text-label">倒计时</cover-view>
+					<cover-view style="font-size: 13px;">{{ formattedCountdown.hours||'00' }}:{{ formattedCountdown.minutes||'00' }}:{{ formattedCountdown.seconds||"00" }}</cover-view>
+				</cover-view>
+			</cover-view>
+			<!-- 虚拟下单跑马灯:视频顶层覆盖,向上滚动淡出切换;!featuredCommentMediaPreviewShow 与 data 直连,避免 video 内 cover-view 对计算属性更新滞后 -->
+			<cover-view class="vip-order-cover-wrap vip-order-cover-wrap--triple" v-if="showFakeMarqueeOnVideoCover && !featuredCommentMediaPreviewShow && isTripleMarqueeMode && marqueeTriplePayloads.length">
+				<cover-view class="vip-order-cover-triple-panel vip-order-cover-triple-current" :class="[marqueeTripleSwitching ? 'vip-order-triple-leave' : '']">
+					<cover-view
+						class="vip-order-cover-item vip-order-cover-triple-item"
+						v-for="(row, idx) in marqueeTriplePayloads"
+						:key="'triple-current-' + idx + '-' + row.nickname + row.timeOffset"
+						:class="[row.type === 'self' ? 'vip-order-cover-self' : '']"
+					>
+						<cover-view class="vip-order-cover-content" v-if="row.type === 'virtual' || row.type === 'self'">
+							<cover-view class="vip-order-seg vip-order-seg-user">{{ row.nickname }}{{ row.maskedId }}</cover-view>
+							<cover-view class="vip-order-seg vip-order-seg-time">{{ row.timeOffset }}{{ row.suffix }}</cover-view>
+						</cover-view>
+						<cover-view class="vip-order-cover-content" v-else>
+							{{ row.fullText }}
+						</cover-view>
+					</cover-view>
+				</cover-view>
+				<cover-view v-if="marqueeTripleSwitching && marqueeTripleIncomingPayloads.length" class="vip-order-cover-triple-panel vip-order-cover-triple-incoming vip-order-triple-enter">
+					<cover-view
+						class="vip-order-cover-item vip-order-cover-triple-item"
+						v-for="(row, idx) in marqueeTripleIncomingPayloads"
+						:key="'triple-incoming-' + idx + '-' + row.nickname + row.timeOffset"
+						:class="[row.type === 'self' ? 'vip-order-cover-self' : '']"
+					>
+						<cover-view class="vip-order-cover-content" v-if="row.type === 'virtual' || row.type === 'self'">
+							<cover-view class="vip-order-seg vip-order-seg-user">{{ row.nickname }}{{ row.maskedId }}</cover-view>
+							<cover-view class="vip-order-seg vip-order-seg-time">{{ row.timeOffset }}{{ row.suffix }}</cover-view>
+						</cover-view>
+						<cover-view class="vip-order-cover-content" v-else>
+							{{ row.fullText }}
+						</cover-view>
+					</cover-view>
+				</cover-view>
+			</cover-view>
+			<cover-view class="vip-order-cover-wrap" v-else-if="showFakeMarqueeOnVideoCover && !featuredCommentMediaPreviewShow && marqueeDisplayPayload">
+				<cover-view
+					class="vip-order-cover-item vip-order-cover-current"
+					:class="[
+						marqueeSwitching ? 'vip-order-leave' : '',
+						marqueeDisplaySelf ? 'vip-order-cover-self' : ''
+					]"
+				>
+					<cover-view class="vip-order-cover-content" v-if="marqueeDisplayPayload.type === 'virtual' || marqueeDisplayPayload.type === 'self'">
+						<cover-view class="vip-order-seg vip-order-seg-user">{{ marqueeDisplayPayload.nickname }}{{ marqueeDisplayPayload.maskedId }}</cover-view>
+						<cover-view class="vip-order-seg vip-order-seg-time">{{ marqueeDisplayPayload.timeOffset }}{{ marqueeDisplayPayload.suffix }}</cover-view>
+					</cover-view>
+					<cover-view class="vip-order-cover-content" v-else>
+						{{ marqueeDisplayPayload.fullText }}
+					</cover-view>
+				</cover-view>
+				<cover-view
+					v-if="marqueeSwitching && marqueeIncomingPayload"
+					class="vip-order-cover-item vip-order-cover-incoming"
+					:class="[
+						'vip-order-enter',
+						marqueeIncomingSelf ? 'vip-order-cover-self' : ''
+					]"
+				>
+					<cover-view class="vip-order-cover-content" v-if="marqueeIncomingPayload.type === 'virtual' || marqueeIncomingPayload.type === 'self'">
+						<cover-view class="vip-order-seg vip-order-seg-user">{{ marqueeIncomingPayload.nickname }}{{ marqueeIncomingPayload.maskedId }}</cover-view>
+						<cover-view class="vip-order-seg vip-order-seg-time">{{ marqueeIncomingPayload.timeOffset }}{{ marqueeIncomingPayload.suffix }}</cover-view>
+					</cover-view>
+					<cover-view class="vip-order-cover-content" v-else>
+						{{ marqueeIncomingPayload.fullText }}
+					</cover-view>
+				</cover-view>
+			</cover-view>
+			<cover-view
+			  class="goods-cover" 
+			  :style="{ display:isFull&&cardPopup && currentCardItem ? 'block' : 'none'}"
+			  @click.stop="goBuy(currentCardItem)"
+			>
+			  <!-- 关闭按钮 -->
+			  <cover-view class="close-box" @click.stop="closeCardPopup">
+			    <cover-image src="/static/images/close.png"></cover-image>
+			  </cover-view>
+			
+			  <cover-view class="goods-cover-inner">
+			    <!-- 商品主图 -->
+			    <cover-view class="goods-cover-img">
+					<cover-image 
+					    style="width:150px;height:150px;object-fit:cover;"
+					    :src="currentCardItem.images"
+					    mode="aspectFit"
+					  ></cover-image>
+				</cover-view>
+			    <cover-view class="goods-cover-info">
+			      <cover-view class="goods-cover-title">{{ currentCardItem.productName || '-' }}</cover-view>
+			      
+			      <cover-view class="goods-cover-bottom">
+			        <cover-view class="goods-cover-tag">
+			          <cover-image class="goods-cover-tag-bg" src="/static/images/pbg.png" mode="widthFix"></cover-image>
+			          <cover-view class="goods-cover-tag-text">惊喜价</cover-view>
+			        </cover-view>
+			        
+			        <cover-view class="goods-cover-price">
+			          <cover-view class="unit">¥</cover-view>
+			          <cover-view class="price">
+			            {{ currentCardItem.price || '0.00' }}
+			          </cover-view>
+			        </cover-view>
+			      </cover-view>
+			    </cover-view>
+			  </cover-view>
+			</cover-view>
+			<!-- logo -->
+				<!-- 弹幕展示 -->
+				<!-- <template v-if="showDanmu==1&&openCommentStatus==2">
+					<text v-for="(item, index) in activeDanmus" :key="item.commentId" class="danmu-item danmuMove"
+						:style="item.danmustyle" @animationend="animationend(item,index)">
+						{{ item.content }}
+					</text>
+				</template> -->
+				<!-- <cover-view class="video-danmu-btnbox" :style="{display: openCommentStatus==2&&isfull&&crtShow&&isLogin&&isAddKf==1 ? 'block':'none'}">
+					<cover-image class="video-danmu-image" :src="imgPath+'/app/image/danmu_set.png'" @click="openDanmu(1)"></cover-image>
+				</cover-view> -->
+				<!-- <cover-image v-if="courseLogo" :class="isfull?'logo-full':'logo'" :src="courseLogo" mode="widthFix"></cover-image> -->
+			</video>
+		</view>
+		<!-- 商品卡片弹窗 -->
+		<view class="goods-card" :style="{'bottom':isShu?'280rpx':'220rpx'}" v-if="!isFull&&cardPopup && currentCardItem" @click.stop="goBuy(currentCardItem)">
+			<view class="close-box" @click.stop="closeCardPopup">
+				<image src="/static/images/close.png"></image>
+			</view>
+			<view class="goods-card-inner">
+				<image class="goods-card-img" :src="currentCardItem.images || currentCardItem.image" mode="aspectFill"></image>
+				<view class="goods-card-info">
+					<view class="goods-card-title">{{ currentCardItem.productName || '-' }}</view>
+					<view class="goods-card-bottom">
+						<view class="goods-card-tag">
+							<image class="goods-card-tag-bg" src="/static/images/pbg.png" mode="widthFix"></image>
+							<view class="goods-card-tag-text">惊喜价</view>
+						</view>
+						<view class="goods-card-price">
+							<view class="unit">¥</view>
+							<text class="price">
+								{{ currentCardItem.price || '0.00' }}
+							</text>
+						</view>
+					</view>
+				</view>
+			</view>
+		</view>
+		<!-- 弹幕方法 -->
+		<commentBox
+			v-if="openCommentStatus==2"
+			ref="danmuBox" 
+			:height="height" 
+			:urlOption="urlOption" 
+			:time="playTime"
+			:showDanmu="showDanmu"
+			:viewCommentNum="viewCommentNum"
+			:openCommentStatus="openCommentStatus"
+			@setInputText="setInputText" 
+			@getScrollTop="getScrollTop"
+			@getMore="getMore"
+			@getActiveDanmus="getActiveDanmus"></commentBox>
+		<!-- <view id="title-contentnav">
+			<view class="title-content" v-show="openCommentStatus!=1"> -->
+				<!-- 答题时展示小节课程名,其他展示课程名 -->
+				<!-- 小节课程名 -->
+				<!-- <view class="subtitlebox" v-if="isLogin&&isAddKf==1">
+					{{courseInfo.title}}
+				</view> -->
+				<!-- 课程名字 -->
+				<!-- <view class="miantitlebox" v-else>
+					{{courseInfo.courseName}}
+				</view>
+			</view>
+			<view class="tabbox" v-if="openCommentStatus==1">
+				<view :class="currentTab == nav.id ? 'tabbox-active':''" v-for="nav in navList" :key="nav.id" @click="handleTab(nav.id)">{{nav.name}}</view>
+			</view>
+		</view> -->
+		<!-- <scroll-view
+		class="scroll-view" 
+		:style="{height: height}" 
+		:scroll-top="scrollTop" 
+		:scroll-y="true" 
+		:refresher-enabled="currentTab==0"
+		:refresher-triggered="triggered"
+		@refresherrefresh="handleRefresher">
+			<template v-if="openCommentStatus==1">
+				<view v-show="currentTab==0">
+					<descInfoNav ref="descInfoNav" :isLogin="isLogin" :isAddKf="isAddKf" :courseInfo="courseInfo"></descInfoNav>
+				</view>
+				<view v-show="currentTab==2">
+					<commentBox 
+					ref="commentBox" 
+					:height="height" 
+					:urlOption="urlOption" 
+					:time="playTime"
+					:flagTime="flagTime"
+					:showDanmu="showDanmu"
+					:viewCommentNum="viewCommentNum"
+					:openCommentStatus="openCommentStatus"
+					@setInputText="setInputText" 
+					@getScrollTop="getScrollTop"
+					@getMore="getMore"></commentBox>
+				</view>
+			</template> -->
+			<!-- <view v-show="currentTab==1"> -->
+				<!-- <template v-if="openCommentStatus!=1&&(courseInfo.title || courseInfo.description)">
+					<descInfo ref="descInfo" :isLogin="isLogin" :isAddKf="isAddKf" :courseInfo="courseInfo"></descInfo>
+				</template> -->
+				<!-- 问题 -->
+				<!-- <template v-if="isLogin&&isAddKf==1">
+					<ques ref="ques" source="videoauto" :urlOption="urlOption" :quesList="quesList" :openCommentStatus="openCommentStatus" :treatmentPackage="treatmentPackage" :showTreatment="showTreatment" @handleAnswer="handleAnswer" @showBtnType="showBtnType"></ques>
+				</template> -->
+			<!-- </view> -->
+		<!-- </scroll-view> -->
+		<!-- 评价(多 Tab:评价得积分 / 栏目介绍 / 精选留言) -->
+		<view class="rating-box" :style="{paddingTop:visibleRatingTabCount == 1?'30rpx':'24rpx'}" v-if="isLogin&&isAddKf==1&&!isShu&&hasVisibleRatingTab">
+			<image class="bg" src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/app/vip/bg-back.png" mode="widthFix"></image>
+			<view class="tab-Box" v-if="visibleRatingTabCount > 1">
+				<view
+					v-if="showTabReviewPoints"
+					class="tab-item"
+					:class="{ 'tab-item--active': tabIndex == 0 }"
+					@click="selecTab(0)"
+				>
+					<view class="tab-item__surface">
+						<image v-if="tabIndex == 0" src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/zan-sel.png"></image>
+						<image v-else src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/sel.png"></image>
+						<text class="tab-item__text">评价得积分</text>
+					</view>
+				</view>
+				<view
+					v-if="showTabColumnIntro"
+					class="tab-item"
+					:class="{ 'tab-item--active': tabIndex == 1 }"
+					@click="selecTab(1)"
+				>
+					<view class="tab-item__surface">
+						<image v-if="tabIndex == 1" src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/des-sel.png"></image>
+						<image v-else src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/des.png"></image>
+						<text class="tab-item__text">栏目介绍</text>
+					</view>
+				</view>
+				<view
+					v-if="showTabFeaturedComments"
+					class="tab-item"
+					:class="{ 'tab-item--active': tabIndex == 2 }"
+					@click="selecTab(2)"
+				>
+					<view class="tab-item__surface">
+						<image v-if="tabIndex == 2" src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/pl-sel.png"></image>
+						<image v-else src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/pl.png"></image>
+						<text class="tab-item__text">精选留言</text>
+					</view>
+				</view>
+			</view>
+			<view class="tab-Box tab-Box--single" v-else-if="visibleRatingTabCount === 1">
+				<view v-if="showTabReviewPoints" class="tab-item tab-item--single">
+					<view class="tab-item__surface tab-item__surface--single">
+						<image src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/zan-sel.png" mode="aspectFit"></image>
+						<text class="tab-item__text tab-item__text--single">评价得积分</text>
+					</view>
+				</view>
+				<view v-if="showTabColumnIntro" class="tab-item tab-item--single">
+					<view class="tab-item__surface tab-item__surface--single">
+						<image src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/des-sel.png" mode="aspectFit"></image>
+						<text class="tab-item__text tab-item__text--single">栏目介绍</text>
+					</view>
+				</view>
+				<view v-if="showTabFeaturedComments" class="tab-item tab-item--single">
+					<view class="tab-item__surface tab-item__surface--single">
+						<image src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/pl-sel.png" mode="aspectFit"></image>
+						<text class="tab-item__text tab-item__text--single">精选留言</text>
+					</view>
+				</view>
+			</view>
+			<view class="rating-body" v-if="tabIndex == 0 && showTabReviewPoints">
+				<view class="rating-ques-block" v-for="(item,index) in quesList" :key="index">
+					<view class="title">{{item.title}}</view>
+					<view class="sat-box">
+						<view class="sat" v-for="(option,idx) in item.questionOption" :key="idx"  :class="aindex==option.indexId?'sat--active':''" @click="handleAnswer(item,option)">
+							<view class="sat-img-wrap" :class="rateBounceIndex==option.indexId?'sat-img-bounce':''">
+								<image :src="aindex==option.indexId?rateList[option.indexId].selIcon:rateList[option.indexId].icon" mode="aspectFit"></image>
+							</view>
+							<text :class="aindex==option.indexId?'active':''">{{option.name}}</text>
+						</view>
+					</view>
+				</view>
+			</view>
+			<view class="rating-body rating-body--plain" :style="{padding:courseInfo.courseIntroImg?'0rpx':'30rpx'}"  v-if="tabIndex === 1 && showTabColumnIntro">
+				<image
+					class="rating-intro-cover-img"
+					:src="courseInfo.courseIntroImg"
+					mode="widthFix"
+				></image>
+			</view>
+			<view class="rating-body rating-body--featured" v-if="tabIndex == 2 && showTabFeaturedComments">
+				<scroll-view
+					scroll-y
+					class="rating-msg-scroll"
+					:show-scrollbar="false"
+					scroll-with-animation
+					lower-threshold="100"
+					@scrolltolower="onFeaturedCommentScrollToLower"
+				>
+					<view v-if="featuredCommentLoading" class="rating-msg-empty">加载中...</view>
+					<template v-else>
+						<view
+							class="rating-msg-item"
+							v-for="(it, idx) in featuredCommentDisplayList"
+							:key="it.commentId"
+						>
+							<view class="rating-msg-avatar-wrap">
+								<image
+									class="rating-msg-avatar"
+									:src="getCommentAvatar(it) || 'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/head.png'"
+									mode="aspectFill"
+								/>
+							</view>
+							<view class="rating-msg-main">
+								<text class="rating-msg-name">{{ getCommentDisplayName(it) }}</text>
+								<view class="rating-msg-text">{{ getCommentTextOnly(it) }}</view>
+								<view v-if="getCommentVideoUrl(it)" class="rating-msg-media rating-msg-media--video">
+									<view class="rating-msg-video-wrap">
+										<video
+											:id="getFeaturedCommentVideoId(it, idx)"
+											class="rating-msg-video"
+											:src="getCommentVideoUrl(it)"
+											:poster="getCommentVideoPoster(it)"
+											:controls="false"
+											object-fit="fill"
+											:show-play-btn="false"
+											:show-center-play-btn="false"
+											:enable-progress-gesture="false"
+										></video>
+										<view
+											class="rating-msg-video-play-cover"
+											@tap.stop="openFeaturedCommentMediaPreview(it, idx, 'video')"
+										>
+											<image
+												class="rating-msg-video-play-icon"
+												src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/bofang.png"
+												mode="aspectFit"
+											/>
+										</view>
+									</view>
+								</view>
+								<view
+									v-else-if="commentImageUrls(it).length"
+									class="rating-msg-media rating-msg-media--imgs"
+								>
+									<image
+										v-for="(img, mi) in commentImageUrls(it)"
+										:key="mi"
+										:src="img"
+										mode="widthFix"
+										class="rating-msg-img"
+										@click="openFeaturedCommentMediaPreview(it, idx, 'image', mi)"
+									/>
+								</view>
+							</view>
+						</view>
+						<view v-if="!featuredCommentDisplayList.length" class="rating-msg-empty">暂无精选留言</view>
+						<view v-if="featuredCommentLoadingMore" class="rating-msg-load-more">加载中...</view>
+						<view
+							v-else-if="showFeaturedCommentNoMoreFooter"
+							class="rating-msg-load-more rating-msg-load-more--done"
+						>没有更多了</view>
+						<!-- 底部锚点:发布成功后 scroll-into-view 定位到底部 -->
+						<view id="fc-scroll-anchor" class="rating-msg-scroll-anchor"></view>
+					</template>
+				</scroll-view>
+			</view>
+		</view>
+		<!-- 线路 -->
+		<!-- <view class="video-line" @click="openPop" v-if="isLogin&&isAddKf==1">
+			<image :src="imgPath+'/app/image/changePlayer-icon.png'"></image>
+			<text>线路{{numberToChinese(lineIndex + 1)}}</text>
+		</view> -->
+		<!-- 线路弹窗 -->
+		<uni-popup ref="popup" type="bottom"  class="full-width-popup">
+			<view class="popupbox">
+				<view class="popupbox-head">
+					<text>线路选择</text>
+					<image class="close-icon" :src="imgPath+'/app/image/tc_close_icon.png'" mode="aspectFill" @click="close">
+					</image>
+				</view>
+				<view class="popupbox-content">
+					<view :class="lineIndex == index ? 'line-item line-active': 'line-item'"
+						v-for="(it,index) in lineList" :key="index" @click="handleLine(index)">
+						线路{{numberToChinese(index + 1)}}</view>
+				</view>
+			</view>
+		</uni-popup>
+		<!-- 温馨提示弹窗 -->
+		<uni-popup ref="tipsPopup" type="center" :is-mask-click="false">
+			<view class="tipsPopup-mask">
+				<image class="red_envelope_top" :src="imgPath+'/app/image/red_envelope_img.png'" mode="aspectFill"></image>
+				<view class="tipsPopup">
+					<image class="tipsPopup-close"  :src="imgPath+'/app/image/course_close_white_icon.png'" mode="aspectFill"
+						@click="closeTipsPop"></image>
+					<view class="tipsPopup-line">
+						<view class="tipsPopup-box">
+							<view class="tipsPopup-head">
+								<image class="tipsPopup-head-title" :src="imgPath+'/app/image/tips_title_img.png'"
+									mode="widthFix"></image>
+							</view>
+							<view class="tipsPopup-content">
+								<view class="tipsPopup-content-title">亲爱的用户,</view>
+								<view>您已经观看课程一半的时间了,请注意休息并保持专注。</view>
+							</view>
+							<view class="tipsPopup-btn-box">
+								<view class="tipsPopup-btn" @click="closeTipsPop">继续观看领奖励</view>
+							</view>
+						</view>
+					</view>
+				</view>
+			</view>
+		</uni-popup>
+		<!-- 发送弹幕 -->
+		<view class="video-line danmu-line" @click="openDanmu(0)" v-if="isLogin&&isAddKf==1&&openCommentStatus==2">
+			<image class="set_image"  :src="imgPath+'/app/image/danmu_set_black.png'" mode="aspectFill"></image>
+			<text>发弹幕</text>
+		</view>
+		<!-- 发送弹幕弹窗 -->
+		<uni-popup ref="danmuPopup" type="bottom" style="z-index: 999;" @change="changeShowPopup">
+			<view class="danmuPopup" :style="{marginLeft:isfull ? statusBarHeight+'px': 0,marginBottom: danmuboxHeight+'px'}">
+				<view class="danmuPopup-head border-line">
+					<image class="danmu-icon" :src="showDanmu==0? imgPath+'/app/image/danmu-off.png':imgPath+'/app/image/danmu-on.png'" mode="heightFix" @click="switchDanmu()"></image>
+					<view class="u-border">
+						<input 
+						class="danmuPopup-input" 
+						placeholder="发个弹幕吧~" 
+						border="border"
+						:focus="focus"
+						:adjustPosition="false" 
+						:autoBlur="false" 
+						maxlength="50"
+						v-model.trim="inputText" />
+						<text style="font-size: 24rpx;color: #bbb;margin-left: 10rpx;">{{inputText?inputText.trim().length:0}}/50</text>
+					</view>
+					<button class="danmuPopup-send" @click="handleChatInput">发送</button>
+				</view>
+			</view>
+		</uni-popup>
+		<!-- 答题弹窗 -->
+		<uni-popup ref="answerPopup" type="center" :show="answerPopup">
+			<view :class="errTitle == '恭喜你,回答正确' ? 'answerPopup-box bg':'answerPopup-box'">
+				<!-- 正确 -->
+				<image class="tipimg" v-if="errTitle == '恭喜你,回答正确'" :src="imgPath+'/app/image/course_answer_img.png'"
+					mode="aspectFill"></image>
+				<!-- 错误 -->
+				<image class="tipimg" v-else :src="imgPath+'/app/image/course_answer_incorrectly_img.png'" mode="aspectFill">
+				</image>
+				<view class="answerPopup-title">{{errTitle}}</view>
+				<view class="answerPopup-desc" v-if="isOpen!=1" v-html="errDesc"></view>
+				<!-- 选择奖励 -->
+				<view class="reward-list" v-if="errTitle == '恭喜你,回答正确'&&isOpen!=1">
+					<radio-group class="reward-list-group" @change="rewardChange">
+						<label class="reward-list-option" v-for="(item, index) in rewardType" :key="item.value">
+							<radio :value="item.value+ ''" :checked="item.value == currentReward"
+								activeBorderColor="#FF5C03" activeBackgroundColor="#FF5C03"
+								style="transform:scale(0.7)" />
+							<view :style="{color: item.value == currentReward ? '#FF5C03':''}">{{item.name}}</view>
+						</label>
+					</radio-group>
+				</view>
+				<!-- 错误题目 -->
+				<view class="errQuesbox" v-if="errQues&&errQues.length>0">
+					<view class="errQuesbox-item textOne" v-for="(it,index) in errQues" :key="index">{{it.title}}</view>
+				</view>
+				<view class="answerPopup-btn" v-if="errTitle == '恭喜你,回答正确'" @click="closeAnswerPopup">确认</view>
+				<view class="tipsPopup-btn-box" v-else
+					:style="{marginTop: errQues&&errQues.length>0 ? '40rpx':'54rpx'}">
+					<view class="tipsPopup-btn" @click="closeAnswerPopup">{{remain > 0 ? '重新答题': '确认'}}</view>
+				</view>
+			</view>
+		</uni-popup>
+		<!-- 可以答题提示 -->
+		<!-- <view class="answerTip" v-if="isLogin&&currentTab!=1&&openCommentStatus==1&&showAnswerTip" @click="handleTab(1)">
+			<text>开始</text>
+			<text>答题</text>
+		</view> -->
+		<!-- 客服二维码弹窗 -->
+		<uni-popup ref="kfPopup" type="center" :mask-click="false">
+			<view class="kfqrcode-box">
+				<image class="kfqrcode" :src="qrcode" show-menu-by-longpress="true"></image>
+				<view v-show="qrcodeMsg" style="margin-top: 30rpx;" v-html="qrcodeMsg"></view>
+				<image class="kfqrcode-close" :src="imgPath+'/app/image/course_close_white_icon.png'" mode="aspectFill"
+					@click="closeKFPop"></image>
+			</view>
+		</uni-popup>
+		<!-- 购物车弹窗 -->
+		<u-popup :show="isCart" @close="closeShop" round="20rpx" bgColor="#fff">
+			<scroll-view class="scroll-view" style="height:500rpx;box-sizing: border-box;padding: 24rpx;" scroll-y="true" enable-flex>
+				<goodsList ref="goodsList" :treatmentPackage="displayProductList" :urlOption="urlOption"></goodsList>
+			</scroll-view>
+		</u-popup>
+		<!-- 更多操作弹窗 -->
+		<u-popup :show="isMore" @close="closeMore" round="20rpx" bgColor="#fff">
+			<view class="more-actions-popup">
+				<view class="more-action-item" @click="navgetTo('/pages_user/user/storeOrder?status=')">
+					<u-icon name="shopping-cart" color="#FF233C" size="40"></u-icon>
+					<view class="action-label">我的订单</view>
+				</view>
+				<view class="more-action-item" @click="navgetTo('/pages_user/user/integralLogsList')">
+					<u-icon name="calendar" color="#FF233C" size="40"></u-icon>
+					<view class="action-label">积分记录</view>
+				</view>
+				<view class="more-action-item" @click="navgetTo('/pages_user/user/integralGoodsList')">
+					<u-icon name="gift" color="#FF233C" size="40"></u-icon>
+					<view class="action-label">兑换好礼</view>
+				</view>
+			</view>
+		</u-popup>
+		<u-popup
+			:show="featuredMediaActionSheetShow"
+			mode="bottom"
+			round="20rpx"
+			bgColor="#fff"
+			:duration="300"
+			@close="closeFeaturedMediaActionSheet"
+		>
+			<view class="fc-media-actions-sheet">
+				<view class="fc-media-actions-sheet-item" @tap.stop="onFeaturedMediaSheetPick(0)">相册图片</view>
+				<view class="fc-media-actions-sheet-item" @tap.stop="onFeaturedMediaSheetPick(1)">相册视频</view>
+				<!-- <view class="fc-media-actions-sheet-gap"></view> -->
+				<view
+					class="fc-media-actions-sheet-item fc-media-actions-sheet-cancel"
+					@tap.stop="closeFeaturedMediaActionSheet"
+				>取消</view>
+			</view>
+		</u-popup>
+		<!-- footer -->
+		<view class="footer" v-if="videoId">
+			<view class="btns" :style="{'justify-content':isLogin&&isAddKf==1&&remainTime==0&&!showTabColumnIntro?'space-between':'flex-end'}">
+				<!-- <button
+					class="author-btn"
+					open-type="getPhoneNumber"
+					@getphonenumber="phoneLogin"  v-if="!isquestion&&authType==1">{{isLogin&&isAddKf==1 ? '提交答案领取奖励' : '立即学习'}}</button> -->
+				<!-- <button
+					class="author-btn"
+					open-type="getUserInfo" :disabled="userdisabled"
+					@getuserinfo="userInfologin"  v-if="authType==0&&!isquestion">{{isLogin&&isAddKf==1 ? '提交答案领取奖励' : '立即学习'}}</button> -->
+				
+				<template v-if="!isquestion && showTabReviewPoints">
+					<button class="author-btn" @click="openList" v-if="isLogin&&isAddKf==1&&isShu">评价得积分<image src="/static/images/jifen.png"></image>
+					</button>
+					<button class="author-btn" @click="submit" v-if="isLogin&&isAddKf==1&&remainTime==0&&!isShu&&tabIndex==0">评价得积分
+					<image src="/static/images/jifen.png"></image>
+					</button>
+				</template>
+				<button class="author-btn" @click="submit" v-if="!isLogin&&isAddKf!==1">立即学习</button>
+				<!-- <button
+					class="author-btn"
+					open-type="getUserInfo" :disabled="userdisabled"
+					@getuserinfo="userInfologin" v-if="authType==0&&!isLogin&&isAddKf!==1">立即学习</button> -->
+					<view v-if="tabIndex==2 && showTabFeaturedComments && !(showTabReviewPoints && isShu)" class="rating-msg-input-shell">
+						<view
+							v-if="featuredCommentMedia"
+							class="rating-msg-media-pill"
+							@click.stop="clearFeaturedCommentMedia"
+						>
+							<image
+								v-if="featuredCommentMedia.type === 'image'"
+								class="rating-msg-media-thumb"
+								:src="featuredCommentMedia.path"
+								mode="aspectFill"
+							/>
+							<image
+								v-else
+								class="rating-msg-media-thumb"
+								:src="featuredCommentMedia.thumbTempPath || featuredCommentMedia.path"
+								mode="aspectFill"
+							/>
+							<view v-if="featuredCommentMedia.type === 'video'" class="rating-msg-media-badge">视频</view>
+							<text class="rating-msg-media-x">×</text>
+						</view>
+						<view class="rating-msg-input rating-msg-input-trigger" @tap.stop="openFeaturedCommentComposer">
+							<text
+								class="rating-msg-input-trigger-text"
+								:class="{ 'is-ph': !featuredCommentInput }"
+							>{{ featuredCommentInput || '善言善语结善缘~' }}</text>
+						</view>
+						<view class="rating-msg-input-icon" @tap.stop="openFeaturedCommentComposer">
+							<image src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/upimg.png"></image>
+						</view>
+					</view>
+				<view class="author-cart" v-show="!(tabIndex === 2 && showTabFeaturedComments && isLogin && isAddKf == 1 && !isquestion && !isShu)">
+					<view class="more-box">
+						<image src="/static/images/more24.png" @click="showMore"></image>
+						<view class="tips">更多</view>
+					</view>
+					<image class="xianshi" v-if="showTreatment==0&&displayProductList.length>0&&!cardPopup" src="/static/images/xg.png"></image>
+					<view class="more-box" v-if="showTreatment==0">
+						<image  @click="showCart"  src="/static/images/cart.png"></image>
+						<view class="tips">去下单</view>
+					</view>
+				</view>
+			</view>
+		</view>
+		<view v-show="currentTab==2">
+			<view class="chatinput" :style="{bottom:danmuboxHeight>0?danmuboxHeight+'px':'calc(var(--window-bottom) + 24rpx)'}">
+				<input class="uni-input" v-model.trim="inputText" :adjustPosition="false" :autoBlur="false"  maxlength="140" placeholder="发消息···" confirm-type="send" @confirm="handleChatInput" />
+				<button class="send" @click="handleChatInput">发送</button>
+			</view>
+		</view>
+		<template v-if="tabIndex==2 && showTabFeaturedComments && !(showTabReviewPoints && isShu)">
+			<view
+				v-if="featuredCommentComposerActive"
+				class="featured-comment-composer-mask"
+				@tap="onFeaturedCommentComposerMaskTap"
+			></view>
+			<view
+				v-if="featuredCommentComposerActive"
+				class="featured-comment-composer-wrap"
+				:style="{ bottom: featuredCommentKeyboardBottomPx + 'px' }"
+			>
+				<view class="featured-comment-composer-inner">
+					<view
+						v-if="featuredCommentMedia"
+						class="fc-composer-media-pill"
+						@click.stop="clearFeaturedCommentMedia"
+					>
+						<image
+							v-if="featuredCommentMedia.type === 'image'"
+							class="fc-composer-media-thumb"
+							:src="featuredCommentMedia.path"
+							mode="aspectFill"
+						/>
+						<image
+							v-else
+							class="fc-composer-media-thumb"
+							:src="featuredCommentMedia.thumbTempPath || featuredCommentMedia.path"
+							mode="aspectFill"
+						/>
+						<view v-if="featuredCommentMedia.type === 'video'" class="fc-composer-media-badge">视频</view>
+						<text class="fc-composer-media-x">×</text>
+					</view>
+					<view class="featured-comment-composer-input-row">
+						<textarea
+							class="fc-composer-input"
+							v-model="featuredCommentInput"
+							type="text"
+							confirm-type="done"
+							:show-confirm-bar="false"
+							placeholder="善言善语结善缘~"
+							placeholder-class="fc-composer-ph"
+							:focus="featuredCommentInputFocused"
+							:adjust-position="false"
+							@focus="onFeaturedCommentComposerInputFocus"
+							@blur="onFeaturedCommentComposerInputBlur"
+						/>
+						<view class="fc-composer-input-icon" @click.stop="onFeaturedPickMedia">
+							<image src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/upimg.png"></image>
+						</view>
+					</view>
+					<view class="featured-comment-composer-publish" @tap.stop="submitFeaturedComment">发布</view>
+				</view>
+			</view>
+		</template>
+		<view
+			v-if="featuredCommentMediaPreviewShow"
+			class="fc-media-preview-mask"
+			@tap="closeFeaturedCommentMediaPreview"
+		>
+			<view class="fc-media-preview-card" @tap.stop="featuredCommentPreviewCardTap">
+				<view
+					v-if="featuredCommentMediaPreviewMode === 'image' && featuredCommentMediaPreviewUrls.length"
+					class="fc-media-preview-img-box"
+				>
+					<view class="fc-media-preview-slide">
+						<image
+							class="fc-media-preview-main-img"
+							:src="featuredCommentMediaPreviewUrls[featuredCommentMediaPreviewIndex]"
+							mode="aspectFit"
+						/>
+					</view>
+				</view>
+				<view
+					v-else-if="featuredCommentMediaPreviewMode === 'video' && featuredCommentMediaPreviewVideoUrl"
+					class="fc-media-preview-video-box"
+				>
+					<video
+						id="fc-media-preview-video"
+						class="fc-media-preview-video"
+						:src="featuredCommentMediaPreviewVideoUrl"
+						:poster="featuredCommentMediaPreviewPoster"
+						controls
+						:show-center-play-btn="true"
+						:show-play-btn="true"
+						:show-fullscreen-btn="false"
+						:auto-pause-if-open-native="false"
+						:auto-pause-if-navigate="true"
+						:enable-progress-gesture="true"
+						:show-background-playback-button="false"
+						@play="onFeaturedMediaPreviewModalVideoPlay"
+					/>
+				</view>
+				<view class="fc-media-preview-footer">
+					<scroll-view
+						v-if="featuredCommentMediaPreviewMode === 'image' && featuredCommentMediaPreviewUrls.length > 1"
+						scroll-x
+						class="fc-media-preview-thumbs"
+						:show-scrollbar="false"
+					>
+						<view class="fc-media-preview-thumbs-inner">
+							<image
+								v-for="(tu, ti) in featuredCommentMediaPreviewUrls"
+								:key="'t-' + ti"
+								class="fc-media-preview-thumb"
+								:class="{ 'fc-media-preview-thumb--active': ti === featuredCommentMediaPreviewIndex }"
+								:src="tu"
+								mode="aspectFill"
+								@tap.stop="setFeaturedMediaPreviewIndex(ti)"
+							/>
+						</view>
+					</scroll-view>
+					<view v-else class="fc-media-preview-thumbs-spacer" />
+					<view class="fc-media-preview-close" @tap.stop="closeFeaturedCommentMediaPreview">
+						<u-icon name="close-circle" color="#fff" size="30"></u-icon>
+					</view>
+				</view>
+			</view>
+		</view>
+		<ykscreenRecord></ykscreenRecord>
+		<courseExpiration v-if="showExpiration" :code="resCode" :msg="resMsg" :qrcode="qrcode"
+		:userId="user && user.userId ? user.userId : ''"></courseExpiration>
+	</view>
+</template>
+
+<script>
+	import ques from "./components/ques.vue"
+	import descInfo from "./components/descInfo.vue"
+	import descInfoNav from "./components/descInfoNav.vue"
+	import commentBox from "./components/commentBox.vue"
+	import goodsList from "./components/goodsList.vue"
+	import {TOKEN_KEYAuto,generateRandomString} from '@/utils/courseTool.js'
+	import { buildFakeOrderPool } from '@/utils/videovipFakeMarquee.js'
+	import ykscreenRecord from "@/components/yk-screenRecord/yk-screenRecord.vue"
+	import courseExpiration from './components/courseExpiration.vue'
+	import dayjs from 'dayjs';
+	import { mapGetters } from 'vuex';
+	
+	import {
+		getErrMsg,
+		getH5CourseByVideoId,
+		getH5CourseVideoDetails,
+		courseAnswer,
+		getFinishCourseVideo,
+		getIsAddKf,
+		getInternetTraffic,
+		getIntegralByH5Video,
+		sendReward,
+		loginByMp,
+		getRealLink,
+		loginByMiniApp
+	} from "@/api/courseAuto.js"
+	import {
+		getConfigByKey
+	} from "@/api/user.js"
+	import {
+		handleFsUserWx,
+		getRemainTime,
+		getCommentList,
+		addCommentWithMedia
+	} from '@/api/courseLook.js'
+	export default {
+		components: {
+			descInfoNav,
+			descInfo,
+			commentBox,
+			ques,
+			goodsList,
+			ykscreenRecord,
+			courseExpiration
+		},
+		data() {
+			return {
+				displayType:'',
+				isShu:false,//竖屏默认
+				notice:'',
+				aindex:null,
+				rateBounceIndex: null,
+				_rateBounceTimer: null,
+				rateList:[{
+					id:0,
+					icon:'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/app/vip/hsat.png',
+					name:'非常满意',
+					selIcon:'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/app/vip/hsat_sel.png'
+				},
+				{
+					id:1,
+					icon:'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/app/vip/sat.png',
+					name:'满意',
+					selIcon:'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/app/vip/sat_sel.png'
+				},
+				{
+					id:2,
+					icon:'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/app/vip/fari.png',
+					name:'一般',
+					selIcon:'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/app/vip/fari_sel.png'
+				},
+				{
+					id:3,
+					icon:'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/app/vip/unsat.png',
+					name:'不满意',
+					selIcon:'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/app/vip/unsat_sel.png'
+				}
+				],
+				resMsg:"",
+				resCode:'',
+				showExpiration:false,
+				code: '',
+				baseUrl:uni.getStorageSync('requestPath'),
+				// 1 红包 2 积分
+				rewardType: [{
+					name: '红包奖励',
+					value: 1
+				}, {
+					name: '积分奖励',
+					value: 2
+				}],
+				currentReward: 1,
+				player: null,
+				loading: true,
+				progress: 0,
+				statusBarHeight: uni.getSystemInfoSync().statusBarHeight,
+				scrollTop: 0,
+				height: '0px',
+				isLogin: false,
+				videoUrl: "",
+				videoId: "",
+				//现在的时长
+				/** 恢复前台 / seek 后短时间内跳过「快进」判定,避免 iOS、鸿蒙息屏后首帧 currentTime 抖动误报 */
+				_antiSeekSuppressExpireAt: 0,
+				_videoPageHadShownOnce: false,
+				playTime: 0,
+				//总时长
+				duration: 0,
+				playDuration: 0,
+				// 用于续播
+				playDurationSeek: 0,
+				// 温馨提醒时间节点,
+				tipsTime: 0,
+				tipsOpen: false,
+				config: {},
+				courseInfo: {},
+				quesList: [],
+				lineList: [],
+				// 错题
+				errQues: [],
+				// 答题机会
+				remain: 0,
+				errTitle: "",
+				errDesc: "",
+				showPlay: true,
+				showControls: false,
+				playStatus: "",
+				isAddKf: 0,
+				lineIndex: 0,
+				// 是否展开
+				isExpand: true,
+				textHeight: 0, //文本高度
+				qwUserId: "",
+				qrcode: "",
+				corpId: "",
+				qrcodeMsg: "",
+				urlOption: {},
+				bufferRate: 0, // 缓冲时间
+				uuId: "",
+				isEnded: false,
+				// 是否允许拖动进度条
+				videolinkType: 0,
+				ip: null,
+				checked: true,
+				isFinish: 0, // 是否完课
+				interval: null,
+				intervalIntegral: null, // 积分定时
+				options: {
+					sources: [{
+						src: ""
+					}],
+					poster: "",
+					live: false /* 是否直播 */ ,
+					controls: true,
+					autoplay: false,
+					licenseUrl: 'https://license.vod2.myqcloud.com/license/v2/1323137866_1/v_cube.license', // license 地址,参考准备工作部分,在视立方控制台申请 license 后可获得 licenseUrl,
+					LicenseKey: 'bcc5bd9a14b798b48c52ff005a21d926',
+					controlBar: {
+						volumePanel: false,
+						playbackRateMenuButton: false,
+						QualitySwitcherMenuButton: false,
+						// progressControl: false
+					},
+					plugins: {
+						// ProgressMarker: false,
+						ContextMenu: {
+							statistic: false
+						}
+					},
+				},
+				// 错误请求次数
+				errorCount: 0,
+				answerPopup: false,
+				sortLink:"",
+				// 课程是否过期
+				isExpire: false,
+				menuButtonLeft: 281,
+				menuButtonH: 45,
+				timer: null,
+				flag: false,
+				msg:'',
+				poster:'',
+				focus: false,
+				openDanmuType: 0,
+				danmuboxHeight: 0,
+				user: {},
+				crtShow: true,
+				courseLogo: '',
+				isfull: false,
+				isFull: false,
+				navList:[{
+					id: 0,
+					name: '介绍'
+				},{
+					id: 1,
+					name: '答题'
+				},{
+					id: 2,
+					name: '评论'
+				}],
+				currentTab: 1,
+				triggered: false,
+				// 没有更多
+				isMore: false,
+				isCart: false, // 购物车弹窗
+				inputText:"",
+				// 获取最多历史评论条数
+				viewCommentNum: 200,
+				// 1-开启评论;2-开启弹幕;3-关闭
+				openCommentStatus: 3,
+				showAnswerTip: false,
+				showDanmu: 1,
+				activeDanmus:[],
+				flagTime:0,
+				showProgress: true,
+				imgPath:this.$store.state.imgpath,
+				videoitem:null,
+				showTreatment: 1, // 1不展示,0展示疗法
+				treatmentPackage: [],
+				// 商品上下架/商品卡片弹窗状态
+				displayProductList: [], // 根据上架/下架时间过滤后的展示列表(用于购物车弹窗)
+				cardPopup: false, // 商品卡片弹窗
+				currentCardItem: null,
+				dismissedCardKey: '',
+				// 跑马灯数据就绪门禁:避免首次进入时使用旧状态导致闪现
+				marqueeDataReady: false,
+				// 虚拟下单跑马灯
+				fakeOrderPool: [],
+				marqueeTriplePayloads: [],
+				marqueeTripleIncomingPayloads: [],
+				marqueeTripleSwitching: false,
+				marqueeCurrentText: '',
+				marqueeSelfHighlight: false,
+				marqueeDisplayPayload: null,
+				marqueeDisplaySelf: false,
+				marqueeIncomingPayload: null,
+				marqueeIncomingSelf: false,
+				marqueeSwitching: false,
+				pendingSelfMarqueeFirst: false,
+				_fakeMarqueeStarted: false,
+				_fakeMarqueeEligiblePrev: undefined,
+				_marqueeStartDebounceTimer: null,
+				_fakeMarqueeTimer: null,
+				_marqueeSwitchTimer: null,
+				_marqueeTripleSwitchTimer: null,
+				_selfMarqueeClockTimer: null,
+				// 完课积分倒计时状态
+				remainTime: 0, // 倒计时(秒)
+				totalRemainTime: 0, // 总倒计时时长(秒,用于计算百分比)
+				countdownTimer: null, // 倒计时定时器
+				remainTimeReady: false, // 是否已从接口拉取到倒计时数据
+				hasReportedAfterCountdown: false, // 倒计时结束后是否已上报一次
+				// 是否公开课
+				isOpen: 0,
+				showBtn: 0,
+				isquestion: false,
+				fullscreenToggleLock: false,
+				fullscreenToggleTimer: null,
+				qwExternalId:'',
+				videoPlaying: false,
+				tabIndex: 0,
+				questionBankList: [],
+				defaultPageInfoList: [],
+				featuredCommentList: [],
+				featuredCommentInput: '',
+				featuredCommentLoading: false,
+				featuredCommentLoadingMore: false,
+				featuredCommentPageNum: 1,
+				featuredCommentPageSize: 10,
+				featuredCommentHasMore: true,
+				featuredCommentUserTotal: NaN,
+				featuredCommentDefaultTotal: NaN,
+				featuredCommentSending: false,
+				featuredCommentMedia: null,
+				videovipSuppressOnShowCourseFetchOnce: false,
+				_shouldResumeCourseVideoAfterFeaturedUpload: false,
+				_courseWasPlayingBeforeFeaturedCommentOpen: false,
+				featuredMediaActionSheetShow: false,
+				featuredCommentMediaPreviewShow: false,
+				featuredCommentMediaPreviewMode: 'image',
+				featuredCommentMediaPreviewUrls: [],
+				featuredCommentMediaPreviewIndex: 0,
+				featuredCommentMediaPreviewVideoUrl: '',
+				featuredCommentMediaPreviewPoster: '',
+				featuredCommentScrollIntoView: '',
+				featuredCommentComposerActive: false,
+				featuredCommentInputFocused: false,
+				featuredCommentKeyboardBottomPx: 0,
+			}
+		},
+		//发送给朋友
+		onShareAppMessage(res) {
+			return {
+				title: this.$store.state.logoname,
+				path: '/pages/about/index',
+				imageUrl: this.$store.state.imgpath+'/app/image/logoshare.png' //分享图标,路径可以是本地文件路径、代码包文件路径或者网络图片路径.支持PNG及JPG。显示图片长宽比是 5:4
+			}
+			
+		},
+		//分享到朋友圈
+		onShareTimeline(res) {
+			return {
+				title: this.$store.state.logoname,
+				path: '/pages/about/index',
+				imageUrl: this.$store.state.imgpath+'/app/image/logoshare.png' //分享图标,路径可以是本地文件路径、代码包文件路径或者网络图片路径.支持PNG及JPG。显示图片长宽比是 5:4
+			}
+			
+		},
+		computed:{
+			appid() {
+				return this.$store.state.appid
+			},
+			isSpare() {
+				return this.$store.state.isSpare
+			},
+			// 完课积分倒计时展示:格式化后的时间
+			formattedCountdown() {
+				return this.formatCountdown(this.remainTime);
+			},
+			// 完课积分倒计时展示:进度百分比
+			countdownPercentage() {
+				return this.getCountdownPercentage();
+			},
+			fakeMarqueeEligible() {
+				if (!this.marqueeDataReady) return false
+				if (this.showTreatment !== 0) return false
+				return Array.isArray(this.displayProductList) && this.displayProductList.length > 0
+			},
+			// 竖屏课打开小黄车 goodsList 时藏住视频内虚拟下单条;精选留言大图/视频预览由模板 !featuredCommentMediaPreviewShow 与 data 直连(同层 video 内 cover-view 更可靠)
+			showFakeMarqueeOnVideoCover() {
+				if (!this.fakeMarqueeEligible) return false
+				if (this.isShu && this.isCart) return false
+				return true
+			},
+			showTabReviewPoints() {
+				return Array.isArray(this.questionBankList) && this.questionBankList.length > 0
+			},
+			showTabColumnIntro() {
+				const img = this.courseInfo && this.courseInfo.courseIntroImg
+				return typeof img === 'string' && img.trim() !== ''
+			},
+			showTabFeaturedComments() {
+				return Array.isArray(this.defaultPageInfoList) && this.defaultPageInfoList.length > 0
+			},
+			featuredCommentDisplayList() {
+				const def = Array.isArray(this.defaultPageInfoList) ? this.defaultPageInfoList : []
+				if (!def.length) return []
+				const user = Array.isArray(this.featuredCommentList) ? this.featuredCommentList : []
+				return this._mergeFeaturedUserComments(user.slice(), def)
+			},
+			showFeaturedCommentNoMoreFooter() {
+				if (this.featuredCommentLoading || this.featuredCommentLoadingMore) return false
+				const list = this.featuredCommentDisplayList
+				if (!Array.isArray(list) || !list.length) return false
+				return !this.featuredCommentHasMore
+			},
+			visibleRatingTabCount() {
+				let n = 0
+				if (this.showTabReviewPoints) n++
+				if (this.showTabColumnIntro) n++
+				if (this.showTabFeaturedComments) n++
+				return n
+			},
+			hasVisibleRatingTab() {
+				return this.visibleRatingTabCount > 0
+			},
+			isTripleMarqueeMode() {
+				return !!(this.isShu || this.isFull)
+			},
+			...mapGetters(['coureLogin']),
+		},
+		watch: {
+		    coureLogin: {
+		      immediate: true,          // 页面一进入就检查一次
+		      handler(val) {
+		        if (val == 2&&this.isLogin) {
+					console.log("看课AppToken失效,请重新登录")
+					this.isLogin = false
+					this.isAddKf = 0
+					this.goLogin()
+		        }
+		      }
+		    },
+			isTripleMarqueeMode(now, was) {
+				if (!now || was) return
+				if (!this.fakeMarqueeEligible || !this._fakeMarqueeStarted) return
+				this.syncTripleMarqueeImmediate()
+			},
+			showTabReviewPoints(now, was) {
+				if (now && was !== true) {
+					this.tabIndex = 0
+				}
+			},
+			visibleRatingTabCount(n, o) {
+				if (n === 2 && this.showTabReviewPoints) {
+					this.tabIndex = 0
+				}
+				if (n !== 3) return
+				if (o != null && o >= 3) return
+				this.tabIndex = 0
+			},
+			/** 离开精选留言 Tab 时收起键盘输入层与选图弹层(与 videovip 行为一致) */
+			tabIndex(n) {
+				if (n !== 2) {
+					this._closeFeaturedCommentComposerUi()
+					this.closeFeaturedMediaActionSheet()
+				}
+			}
+		},
+		onLoad(option) {
+			this.getWebviewUrl()
+			uni.$on('usercode', (data) => {
+				console.log('huoqu ', data)
+				if(this.isSpare == 1&&data) {
+					this.code=data.code
+					this.goLogin(data)
+				}
+			})
+			this.videoContext = uni.createVideoContext('video-content-box', this)
+			if(!option.course){
+				if(option.videoitem){
+					this.isOpen = 1
+					this.urlOption=JSON.parse(option.videoitem)
+					this.urlOption = {
+						...this.urlOption,
+						isOpen: 1
+					}
+				}else{
+					const keys = decodeURIComponent(Object.keys(option)[0]);
+					this.urlOption = JSON.parse(keys.split('course=')[1])
+				}
+			}else{
+				this.isOpen = 0
+				this.urlOption = option.course ? JSON.parse(decodeURIComponent(option.course)) : {}
+			}
+			this.videoId = this.urlOption.videoId
+			this.qwUserId = this.urlOption.qwUserId || ''
+			this.qwExternalId = this.urlOption.qwExternalId || ''
+			this.corpId = this.urlOption.corpId || ''
+			this.videolinkType = this.urlOption.linkType || 0
+			this.urlOption.appId=wx.getAccountInfoSync().miniProgram.appId
+			var that=this;
+			if (this.videoId) {
+				this.getH5CourseByVideo()
+			}
+			this.sortLink = this.urlOption.link || ''
+			this.getMenuButton()
+			// #ifndef H5
+			uni.onKeyboardHeightChange(this.keyboardHeightChange);
+			// #endif
+		},
+		onShow() {
+			this.refreshVipPurchaseMarqueeFlag()
+			if (this._videoPageHadShownOnce) {
+				this._touchAntiSeekSuppress(2000)
+			} else {
+				this._videoPageHadShownOnce = true
+			}
+			this.tipsOpen = false
+			this.isExpand = true
+			// this.isLogin = this.$isLoginCourseAuto()
+			this.uuId = generateRandomString(16)
+			// 精选留言从相册/相机返回:勿停虚拟跑马灯、勿重置门禁(与 onHide 抑制停表共用标志)
+			if (this.videovipSuppressOnShowCourseFetchOnce) {
+				this.videovipSuppressOnShowCourseFetchOnce = false
+				return
+			}
+			this.stopFakeMarqueeLoop()
+			this.marqueeDataReady = false
+			this._fakeMarqueeEligiblePrev = undefined
+			if(uni.getStorageSync('auto_userInfo') && JSON.stringify(uni.getStorageSync('auto_userInfo'))!='{}') {
+				this.user = JSON.parse(uni.getStorageSync('auto_userInfo'))
+			} else {
+				this.user = {}
+			}
+
+			if((this.sortLink||this.isOpen==1)&&!this.code){
+				this.getLink()
+			} else {
+				if(this.code) return;
+				uni.showToast({
+					title: '链接地址有误',
+					icon: 'none'
+				});
+			}
+		},
+		mounted() {
+			//this.getIP()
+			this.getHeight()
+		},
+		onHide() {
+			this.closeFeaturedCommentMediaPreview()
+			this._closeFeaturedCommentComposerUi()
+			// this.player = uni.createVideoContext('video-content-box');
+			if (this.player) {
+				this.player.pause()
+			}
+			// 精选留言调起相册/相机时也会触发 onHide,勿停虚拟跑马灯(与 onShow 抑制拉课共用同一标志)
+			if (!this.videovipSuppressOnShowCourseFetchOnce) {
+				this.stopFakeMarqueeLoop()
+			}
+			this.stopCountdown()
+			// if (this.interval != null) {
+			// 	clearInterval(this.interval)
+			// 	this.interval = null
+			// }
+		},
+		onUnload() {
+			this.closeFeaturedCommentMediaPreview()
+			this._closeFeaturedCommentComposerUi()
+			this.closeFeaturedMediaActionSheet()
+			this._videoPageHadShownOnce = false
+			uni.$off('usercode')
+			if (this.interval != null) {
+				clearInterval(this.interval)
+				this.interval = null
+			}
+			if (this.fullscreenToggleTimer) {
+				clearTimeout(this.fullscreenToggleTimer)
+				this.fullscreenToggleTimer = null
+			}
+			if (this._rateBounceTimer) {
+				clearTimeout(this._rateBounceTimer)
+				this._rateBounceTimer = null
+			}
+			this.fullscreenToggleLock = false
+			this.stopCountdown()
+			this.clearIntegral()
+			this.stopFakeMarqueeLoop()
+			this.fakeOrderPool = []
+			// #ifndef H5
+			uni.offKeyboardHeightChange(this.keyboardHeightChange);
+			// #endif
+		},
+		beforeDestroy() {
+			this.closeFeaturedCommentMediaPreview()
+			this._closeFeaturedCommentComposerUi()
+			this.closeFeaturedMediaActionSheet()
+			uni.$off('usercode')
+			this.player = uni.createVideoContext('video-content-box');
+			if (this.player) {
+				this.player.stop()
+				this.player = null
+			}
+			if (this.interval != null) {
+				clearInterval(this.interval)
+				this.interval = null
+			}
+			if (this.fullscreenToggleTimer) {
+				clearTimeout(this.fullscreenToggleTimer)
+				this.fullscreenToggleTimer = null
+			}
+			if (this._rateBounceTimer) {
+				clearTimeout(this._rateBounceTimer)
+				this._rateBounceTimer = null
+			}
+			this.fullscreenToggleLock = false
+			this.stopCountdown()
+			this.clearIntegral()
+			this.stopFakeMarqueeLoop()
+			// #ifndef H5
+			uni.offKeyboardHeightChange(this.keyboardHeightChange);
+			// #endif
+		},
+		methods: {
+			_touchAntiSeekSuppress(ms = 2000) {
+				const until = Date.now() + ms
+				if (until > (this._antiSeekSuppressExpireAt || 0)) this._antiSeekSuppressExpireAt = until
+			},
+			_normalizePurchaseTs(ts) {
+				if (ts == null || ts === '') return 0
+				const n = typeof ts === 'number' ? ts : Number(ts)
+				return Number.isFinite(n) && n > 0 ? n : 0
+			},
+			_readVipSelfPurchaseTsMs() {
+				const row = uni.getStorageSync('videovip_myPurchase_' + this.videoId)
+				return this._normalizePurchaseTs(row && row.ts)
+			},
+			refreshVipPurchaseMarqueeFlag() {
+				const key = 'videovip_myPurchase_' + this.videoId
+				const consumedKey = 'videovip_myPurchaseMarqueeConsumed_' + this.videoId
+				const row = uni.getStorageSync(key)
+				const consumed = uni.getStorageSync(consumedKey)
+				const tsMs = this._normalizePurchaseTs(row && row.ts)
+				if (tsMs && Date.now() - tsMs <= 10 * 60 * 1000) {
+					const consumedTs = this._normalizePurchaseTs(consumed && consumed.ts)
+					this.pendingSelfMarqueeFirst = !(consumedTs > 0 && consumedTs === tsMs)
+				} else {
+					this.pendingSelfMarqueeFirst = false
+					if (row && row.ts != null && row.ts !== '') {
+						uni.removeStorageSync(key)
+						const consumedTs = this._normalizePurchaseTs(consumed && consumed.ts)
+						if (consumedTs > 0 && consumedTs === tsMs) uni.removeStorageSync(consumedKey)
+					}
+				}
+			},
+			_markSelfPurchaseMarqueeConsumed() {
+				const tsMs = this._readVipSelfPurchaseTsMs()
+				if (!tsMs) return
+				try {
+					uni.setStorageSync('videovip_myPurchaseMarqueeConsumed_' + this.videoId, { ts: tsMs })
+				} catch (e) {}
+			},
+			formatSelfPurchaseMarqueePayload() {
+				const tsMs = this._readVipSelfPurchaseTsMs()
+				if (!tsMs) {
+					return {
+						type: 'self',
+						nickname: '您本人',
+						maskedId: '',
+						timeOffset: '刚刚',
+						suffix: '已下单',
+						fullText: '您本人刚刚已下单'
+					}
+				}
+				const secTotal = Math.floor((Date.now() - tsMs) / 1000)
+				if (secTotal < 60) {
+					const text = `${Math.max(1, secTotal)}秒前`
+					return {
+						type: 'self',
+						nickname: '您本人',
+						maskedId: '',
+						timeOffset: text,
+						suffix: '已下单',
+						fullText: `您本人${text}已下单`
+					}
+				}
+				const min = Math.min(10, Math.floor(secTotal / 60))
+				const text = `${Math.max(1, min)}分钟前`
+				return {
+					type: 'self',
+					nickname: '您本人',
+					maskedId: '',
+					timeOffset: text,
+					suffix: '已下单',
+					fullText: `您本人${text}已下单`
+				}
+			},
+			_syncFakeMarqueeIfEligibleChanged() {
+				const val = this.fakeMarqueeEligible
+				if (val === this._fakeMarqueeEligiblePrev) return
+				this._fakeMarqueeEligiblePrev = val
+				if (val) {
+					if (this._marqueeStartDebounceTimer) {
+						clearTimeout(this._marqueeStartDebounceTimer)
+						this._marqueeStartDebounceTimer = null
+					}
+					this._marqueeStartDebounceTimer = setTimeout(() => {
+						this._marqueeStartDebounceTimer = null
+						if (this.fakeMarqueeEligible && !this._fakeMarqueeStarted) {
+							this.ensureFakeMarqueeStarted()
+						}
+					}, 50)
+				} else {
+					if (this._marqueeStartDebounceTimer) {
+						clearTimeout(this._marqueeStartDebounceTimer)
+						this._marqueeStartDebounceTimer = null
+					}
+					this.stopFakeMarqueeLoop()
+				}
+			},
+			ensureFakeMarqueeStarted() {
+				if (!this.fakeMarqueeEligible || this._fakeMarqueeStarted) return
+				this._fakeMarqueeStarted = true
+				if (!this.fakeOrderPool.length) {
+					this.fakeOrderPool = buildFakeOrderPool()
+				}
+				this.applyFakeMarqueeTick()
+				this.scheduleFakeMarqueeNext()
+				this._startSelfMarqueeClockIfNeeded()
+			},
+			applyFakeMarqueeTick() {
+				if (this.isTripleMarqueeMode) {
+					const rows = this.buildTripleMarqueePayloads()
+					this.setTripleMarqueeDisplayWithAnim(rows)
+					if (rows.some(item => item && item.type === 'self')) {
+						this.pendingSelfMarqueeFirst = false
+						this._markSelfPurchaseMarqueeConsumed()
+					}
+					if (rows.length) {
+						this.marqueeDisplayPayload = rows[0]
+						this.marqueeDisplaySelf = this.marqueeDisplayPayload.type === 'self'
+					}
+					return
+				}
+				this.marqueeTriplePayloads = []
+				this.marqueeTripleIncomingPayloads = []
+				this.marqueeTripleSwitching = false
+				const tsMs = this._readVipSelfPurchaseTsMs()
+				const purchaseOk = !!(tsMs && Date.now() - tsMs <= 10 * 60 * 1000)
+				if (purchaseOk && this.pendingSelfMarqueeFirst) {
+					const selfPayload = this.formatSelfPurchaseMarqueePayload()
+					this.marqueeCurrentText = selfPayload.fullText
+					this.marqueeSelfHighlight = true
+					this.pendingSelfMarqueeFirst = false
+					this._markSelfPurchaseMarqueeConsumed()
+					this.setMarqueeDisplayWithAnim(selfPayload, true)
+					return
+				}
+				this.marqueeSelfHighlight = false
+				if (!this.fakeOrderPool.length) {
+					this.fakeOrderPool = buildFakeOrderPool()
+				}
+				const line = this.fakeOrderPool.shift()
+				if (line) {
+					this.fakeOrderPool.push(line)
+					this.marqueeCurrentText = `${line.nickname}${line.maskedId}${line.timeOffset}${line.suffix}`
+					this.setMarqueeDisplayWithAnim({
+						type: 'virtual',
+						nickname: line.nickname,
+						maskedId: line.maskedId,
+						timeOffset: line.timeOffset,
+						suffix: line.suffix
+					}, false)
+				}
+			},
+			buildTripleMarqueePayloads() {
+				const rows = []
+				const hasSelf = this.hasRecentSelfPurchase() && this.pendingSelfMarqueeFirst
+				if (!this.fakeOrderPool.length) {
+					this.fakeOrderPool = buildFakeOrderPool()
+				}
+				let guard = 0
+				if (hasSelf) {
+					rows.push(this.formatSelfPurchaseMarqueePayload())
+				}
+				const targetVirtualCount = hasSelf ? 2 : 3
+				let virtualCount = 0
+				while (virtualCount < targetVirtualCount && this.fakeOrderPool.length && guard < 10) {
+					const line = this.fakeOrderPool.shift()
+					guard += 1
+					if (!line) break
+					this.fakeOrderPool.push(line)
+					rows.push({
+						type: 'virtual',
+						nickname: line.nickname,
+						maskedId: line.maskedId,
+						timeOffset: line.timeOffset,
+						suffix: line.suffix
+					})
+					virtualCount += 1
+				}
+				return rows.slice(0, 3)
+			},
+			hasRecentSelfPurchase() {
+				const tsMs = this._readVipSelfPurchaseTsMs()
+				return !!(tsMs && Date.now() - tsMs <= 10 * 60 * 1000)
+			},
+			refreshSelfPurchaseMarqueeDisplayedTiming() {
+				const fresh = this.formatSelfPurchaseMarqueePayload()
+				if (this.isTripleMarqueeMode && this.marqueeTriplePayloads.length) {
+					const upd = (arr) =>
+						arr.map((r) => (r && r.type === 'self' ? Object.assign({}, fresh) : r))
+					this.marqueeTriplePayloads = upd(this.marqueeTriplePayloads)
+					if (this.marqueeTripleIncomingPayloads.length) {
+						this.marqueeTripleIncomingPayloads = upd(this.marqueeTripleIncomingPayloads)
+					}
+				}
+				if (this.marqueeDisplayPayload && this.marqueeDisplayPayload.type === 'self') {
+					this.marqueeDisplayPayload = Object.assign({}, fresh)
+				}
+				if (this.marqueeIncomingPayload && this.marqueeIncomingPayload.type === 'self') {
+					this.marqueeIncomingPayload = Object.assign({}, fresh)
+				}
+			},
+			_startSelfMarqueeClockIfNeeded() {
+				if (this._selfMarqueeClockTimer != null) return
+				if (!this.hasRecentSelfPurchase()) return
+				this._selfMarqueeClockTimer = setInterval(() => {
+					if (!this._fakeMarqueeStarted || !this.hasRecentSelfPurchase()) {
+						this._stopSelfMarqueeClock()
+						return
+					}
+					this.refreshSelfPurchaseMarqueeDisplayedTiming()
+				}, 10000)
+			},
+			_stopSelfMarqueeClock() {
+				if (this._selfMarqueeClockTimer != null) {
+					clearInterval(this._selfMarqueeClockTimer)
+					this._selfMarqueeClockTimer = null
+				}
+			},
+			syncTripleMarqueeImmediate() {
+				if (!this.fakeMarqueeEligible || !this._fakeMarqueeStarted || !this.isTripleMarqueeMode) return
+				const rows = this.buildTripleMarqueePayloads()
+				if (!rows.length) return
+				this.setTripleMarqueeDisplayWithAnim(rows)
+				if (rows.some(item => item && item.type === 'self')) {
+					this.pendingSelfMarqueeFirst = false
+					this._markSelfPurchaseMarqueeConsumed()
+				}
+				if (rows[0]) {
+					this.marqueeDisplayPayload = rows[0]
+					this.marqueeDisplaySelf = rows[0].type === 'self'
+				}
+			},
+			setTripleMarqueeDisplayWithAnim(rows) {
+				if (!rows || !rows.length) return
+				if (!this.marqueeTriplePayloads.length) {
+					this.marqueeTriplePayloads = rows
+					this.marqueeTripleIncomingPayloads = []
+					this.marqueeTripleSwitching = false
+					return
+				}
+				if (this._marqueeTripleSwitchTimer) {
+					clearTimeout(this._marqueeTripleSwitchTimer)
+					this._marqueeTripleSwitchTimer = null
+				}
+				this.marqueeTripleIncomingPayloads = rows
+				this.marqueeTripleSwitching = true
+				this._marqueeTripleSwitchTimer = setTimeout(() => {
+					this.marqueeTriplePayloads = this.marqueeTripleIncomingPayloads
+					this.marqueeTripleIncomingPayloads = []
+					this.marqueeTripleSwitching = false
+					this._marqueeTripleSwitchTimer = null
+				}, 460)
+			},
+			setMarqueeDisplayWithAnim(payload, isSelf) {
+				if (!payload) return
+				if (!this.marqueeDisplayPayload) {
+					this.marqueeDisplayPayload = payload
+					this.marqueeDisplaySelf = !!isSelf
+					this.marqueeSwitching = false
+					this.marqueeIncomingPayload = null
+					this.marqueeIncomingSelf = false
+					return
+				}
+				if (this._marqueeSwitchTimer) {
+					clearTimeout(this._marqueeSwitchTimer)
+					this._marqueeSwitchTimer = null
+				}
+				this.marqueeIncomingPayload = payload
+				this.marqueeIncomingSelf = !!isSelf
+				this.marqueeSwitching = true
+				this._marqueeSwitchTimer = setTimeout(() => {
+					this.marqueeDisplayPayload = this.marqueeIncomingPayload
+					this.marqueeDisplaySelf = this.marqueeIncomingSelf
+					this.marqueeIncomingPayload = null
+					this.marqueeIncomingSelf = false
+					this.marqueeSwitching = false
+					this._marqueeSwitchTimer = null
+				}, 460)
+			},
+			scheduleFakeMarqueeNext() {
+				if (this._fakeMarqueeTimer) {
+					clearTimeout(this._fakeMarqueeTimer)
+					this._fakeMarqueeTimer = null
+				}
+				const delay = 4000 + Math.floor(Math.random() * 3001)
+				this._fakeMarqueeTimer = setTimeout(() => {
+					this._fakeMarqueeTimer = null
+					if (!this.fakeMarqueeEligible || !this._fakeMarqueeStarted) return
+					this.applyFakeMarqueeTick()
+					this.scheduleFakeMarqueeNext()
+				}, delay)
+			},
+			stopFakeMarqueeLoop() {
+				if (this._marqueeStartDebounceTimer) {
+					clearTimeout(this._marqueeStartDebounceTimer)
+					this._marqueeStartDebounceTimer = null
+				}
+				if (this._fakeMarqueeTimer) {
+					clearTimeout(this._fakeMarqueeTimer)
+					this._fakeMarqueeTimer = null
+				}
+				if (this._marqueeSwitchTimer) {
+					clearTimeout(this._marqueeSwitchTimer)
+					this._marqueeSwitchTimer = null
+				}
+				if (this._marqueeTripleSwitchTimer) {
+					clearTimeout(this._marqueeTripleSwitchTimer)
+					this._marqueeTripleSwitchTimer = null
+				}
+				this._fakeMarqueeStarted = false
+				this.marqueeSwitching = false
+				this.marqueeDisplayPayload = null
+				this.marqueeDisplaySelf = false
+				this.marqueeCurrentText = ''
+				this.marqueeSelfHighlight = false
+				this.marqueeIncomingPayload = null
+				this.marqueeIncomingSelf = false
+				this.marqueeTriplePayloads = []
+				this.marqueeTripleIncomingPayloads = []
+				this.marqueeTripleSwitching = false
+				this._stopSelfMarqueeClock()
+			},
+			closeCardPopup() {
+				if (this.currentCardItem) {
+					this.dismissedCardKey =
+						`${this.currentCardItem.productId || ''}_${this.currentCardItem.cardPopupTime || ''}_${this.currentCardItem.cardCloseTime || ''}`
+				}
+				this.cardPopup = false
+			},
+			openList(){
+				const wasShu = this.isShu
+				this.isShu=!this.isShu
+				if (wasShu && this.showTabReviewPoints) this.tabIndex = 0
+			},
+			_closeFeaturedCommentComposerUi() {
+				this.featuredCommentComposerActive = false
+				this.featuredCommentInputFocused = false
+				this.featuredCommentKeyboardBottomPx = 0
+			},
+			openFeaturedCommentComposer() {
+				this._expandLayoutIfPortraitFeaturedCommentsOnly()
+				this._courseWasPlayingBeforeFeaturedCommentOpen = this.videoPlaying && !this.isEnded
+				this.featuredCommentComposerActive = true
+				this.$nextTick(() => {
+					this.featuredCommentInputFocused = true
+				})
+			},
+			onFeaturedCommentComposerMaskTap() {
+				this._closeFeaturedCommentComposerUi()
+			},
+			onFeaturedCommentComposerInputFocus() {
+				this._expandLayoutIfPortraitFeaturedCommentsOnly()
+			},
+			onFeaturedCommentComposerInputBlur() {
+				this.featuredCommentInputFocused = false
+			},
+			_syncRatingTabIndex() {
+				const tabs = [
+					this.showTabReviewPoints,
+					this.showTabColumnIntro,
+					this.showTabFeaturedComments
+				]
+				if (!tabs.some(Boolean)) return
+				if (tabs[this.tabIndex]) return
+				const idx = tabs.findIndex(Boolean)
+				if (idx < 0) return
+				this.tabIndex = idx
+				if (idx === 2) {
+					this.loadFeaturedComments()
+				}
+			},
+			selecTab(idx){
+				if (idx === 0 && !this.showTabReviewPoints) return
+				if (idx === 1 && !this.showTabColumnIntro) return
+				if (idx === 2 && !this.showTabFeaturedComments) return
+				this.tabIndex = idx
+				if (idx === 2) {
+					this.loadFeaturedComments()
+				}
+			},
+			_resolveUserInfoObj() {
+				let u = this.user
+				if (!u || !Object.keys(u).length) {
+					try {
+						const raw = uni.getStorageSync('auto_userInfo')
+						if (typeof raw === 'string') u = JSON.parse(raw) || {}
+						else if (raw && typeof raw === 'object') u = raw
+						else u = {}
+					} catch (e) {
+						u = {}
+					}
+				}
+				return u && typeof u === 'object' ? u : {}
+			},
+			_pickUserCommentListFromCommentListRes(res) {
+				if (!res || res.code != 200) return []
+				const d = res.data
+				if (d && Array.isArray(d.list)) return d.list.slice()
+				if (Array.isArray(d)) return d.slice()
+				if (Array.isArray(res.list)) return res.list.slice()
+				if (d && Array.isArray(d.records)) return d.records.slice()
+				return []
+			},
+			_pickDefaultPageInfoListFromCommentListRes(res) {
+				if (!res || res.code != 200) return []
+				const dpi = res.defaultPageInfo || (res.data && res.data.defaultPageInfo)
+				if (dpi && Array.isArray(dpi.list)) return dpi.list.slice()
+				return []
+			},
+			_pickFeaturedUserCommentTotalFromRes(res) {
+				if (!res || res.code != 200) return NaN
+				const d = res.data
+				const tryNum = (v) => {
+					const t = Number(v)
+					return Number.isFinite(t) && t >= 0 ? t : NaN
+				}
+				if (d && typeof d === 'object' && !Array.isArray(d)) {
+					if (typeof d.userTotal !== 'undefined') {
+						const t = tryNum(d.userTotal)
+						if (Number.isFinite(t)) return t
+					}
+					if (typeof d.commentTotal !== 'undefined') {
+						const t = tryNum(d.commentTotal)
+						if (Number.isFinite(t)) return t
+					}
+					if (typeof d.listTotal !== 'undefined') {
+						const t = tryNum(d.listTotal)
+						if (Number.isFinite(t)) return t
+					}
+					if (typeof d.total !== 'undefined') {
+						const t = tryNum(d.total)
+						if (Number.isFinite(t)) return t
+					}
+				}
+				if (typeof res.userTotal !== 'undefined') {
+					const t = tryNum(res.userTotal)
+					if (Number.isFinite(t)) return t
+				}
+				if (typeof res.total !== 'undefined') {
+					const t = tryNum(res.total)
+					if (Number.isFinite(t)) return t
+				}
+				return NaN
+			},
+			_pickFeaturedDefaultTotalFromRes(res) {
+				if (!res || res.code != 200) return NaN
+				const dpi = res.defaultPageInfo || (res.data && res.data.defaultPageInfo)
+				if (dpi && typeof dpi.total !== 'undefined') {
+					const t = Number(dpi.total)
+					return Number.isFinite(t) && t >= 0 ? t : NaN
+				}
+				return NaN
+			},
+			_syncFeaturedCommentTotalsFromRes(res) {
+				const u = this._pickFeaturedUserCommentTotalFromRes(res)
+				const dt = this._pickFeaturedDefaultTotalFromRes(res)
+				this.featuredCommentUserTotal = Number.isFinite(u) ? u : NaN
+				this.featuredCommentDefaultTotal = Number.isFinite(dt) ? dt : NaN
+			},
+			_mergeFeaturedUserComments(prev, incoming) {
+				const a = Array.isArray(prev) ? prev : []
+				const b = Array.isArray(incoming) ? incoming : []
+				const keyOf = (it) => {
+					if (!it) return ''
+					if (it.commentId != null && it.commentId !== '') return 'c:' + it.commentId
+					if (it.id != null && it.id !== '') return 'i:' + it.id
+					return ''
+				}
+				const seen = new Set()
+				const out = []
+				for (let i = 0; i < a.length; i++) {
+					const k = keyOf(a[i])
+					if (k) seen.add(k)
+					out.push(a[i])
+				}
+				for (let j = 0; j < b.length; j++) {
+					const it = b[j]
+					const k = keyOf(it)
+					if (k) {
+						if (seen.has(k)) continue
+						seen.add(k)
+					}
+					out.push(it)
+				}
+				return out
+			},
+			_applyFeaturedCommentHasMore(res, pageUserList, mergedUserList) {
+				const pageLen = Array.isArray(pageUserList) ? pageUserList.length : 0
+				const mergedLen = Array.isArray(mergedUserList) ? mergedUserList.length : 0
+				const userTotal = this._pickFeaturedUserCommentTotalFromRes(res)
+				if (Number.isFinite(userTotal)) {
+					this.featuredCommentHasMore = mergedLen < userTotal
+				} else {
+					this.featuredCommentHasMore = pageLen >= this.featuredCommentPageSize
+				}
+				if (pageLen === 0) this.featuredCommentHasMore = false
+			},
+			onFeaturedCommentScrollToLower() {
+				if (this.tabIndex !== 2 || !this.showTabFeaturedComments) return
+				this.loadFeaturedComments({ append: true })
+			},
+			loadFeaturedComments(opts) {
+				if (!this.videoId || !this.urlOption.courseId) {
+					return Promise.resolve()
+				}
+				const o = opts || {}
+				const scrollToBottom = !!o.scrollToBottom
+				const append = !!o.append
+				if (append) {
+					if (!this.featuredCommentHasMore) return Promise.resolve()
+					if (this.featuredCommentLoading || this.featuredCommentLoadingMore) return Promise.resolve()
+					this.featuredCommentLoadingMore = true
+				} else {
+					if (this.featuredCommentLoading) return Promise.resolve()
+					this.featuredCommentPageNum = 1
+					this.featuredCommentHasMore = true
+					this.featuredCommentLoading = true
+				}
+				const pageNum = this.featuredCommentPageNum
+				return getCommentList({
+					pageNum,
+					pageSize: this.featuredCommentPageSize,
+					courseId: this.urlOption.courseId,
+					videoId: this.videoId,
+				}).then(res => {
+					if (append) {
+						this.featuredCommentLoadingMore = false
+					} else {
+						this.featuredCommentLoading = false
+					}
+					if (res.code == 200) {
+						const pageUser = this._pickUserCommentListFromCommentListRes(res)
+						this._syncFeaturedCommentTotalsFromRes(res)
+						if (!append) {
+							this.featuredCommentList = pageUser
+							this.defaultPageInfoList = this._pickDefaultPageInfoListFromCommentListRes(res)
+							this._applyFeaturedCommentHasMore(res, pageUser, this.featuredCommentList)
+							if (pageUser.length > 0) this.featuredCommentPageNum = pageNum + 1
+						} else {
+							this.featuredCommentList = this._mergeFeaturedUserComments(
+								this.featuredCommentList,
+								pageUser
+							)
+							this._applyFeaturedCommentHasMore(res, pageUser, this.featuredCommentList)
+							if (pageUser.length > 0) this.featuredCommentPageNum = pageNum + 1
+						}
+					} else {
+						if (!append) {
+							this.defaultPageInfoList = []
+							this.featuredCommentList = []
+							this.featuredCommentHasMore = false
+							this.featuredCommentUserTotal = NaN
+							this.featuredCommentDefaultTotal = NaN
+						}
+					}
+					this._syncRatingTabIndex()
+					if (scrollToBottom) {
+						this.$nextTick(() => {
+							this._scrollFeaturedCommentsToBottom()
+							setTimeout(() => this._scrollFeaturedCommentsToBottom(), 280)
+						})
+					}
+				}).catch(() => {
+					if (append) {
+						this.featuredCommentLoadingMore = false
+					} else {
+						this.featuredCommentLoading = false
+						this.featuredCommentList = []
+						this.defaultPageInfoList = []
+						this.featuredCommentHasMore = false
+						this.featuredCommentUserTotal = NaN
+						this.featuredCommentDefaultTotal = NaN
+					}
+					this._syncRatingTabIndex()
+				})
+			},
+			_scrollFeaturedCommentsToBottom() {
+				this.featuredCommentScrollIntoView = ''
+				this.$nextTick(() => {
+					this.featuredCommentScrollIntoView = 'fc-scroll-anchor'
+					setTimeout(() => {
+						this.featuredCommentScrollIntoView = ''
+					}, 400)
+				})
+			},
+			getCommentAvatar(it) {
+				if (!it) return ''
+				return it.avatar || it.headImg || it.headimg || it.userAvatar || ''
+			},
+			getCommentDisplayName(it) {
+				if (!it) return '用户'
+				if (it.nickName) return it.nickName
+				if (it.userId != null && it.userId !== '') {
+					return it.toNickName || '用户'
+				}
+				return '用户'
+			},
+			_urlsEmbeddedInCommentContent(it) {
+				const c = it && it.content
+				if (c == null || typeof c !== 'string') return []
+				const text = String(c).replace(/\u21b5/g, '\n')
+				const m = text.match(/https?:\/\/[^\s]+/gi) || []
+				const cleaned = m.map(u => u.replace(/[),.;!?]+$/g, ''))
+				return [...new Set(cleaned)]
+			},
+			_isEmbeddedCommentVideoUrl(u) {
+				if (!u) return false
+				return /\/comment\/video\//i.test(u) || /\.(mp4|m3u8|mov|webm|avi|mkv)(\?|#|$)/i.test(u)
+			},
+			_isEmbeddedCommentImageUrl(u) {
+				if (!u) return false
+				return /\/comment\/image\//i.test(u) || /\.(jpg|jpeg|png|gif|webp|bmp)(\?|#|$)/i.test(u)
+			},
+			_videoUrlFromCommentContent(it) {
+				const urls = this._urlsEmbeddedInCommentContent(it)
+				for (let i = 0; i < urls.length; i++) {
+					if (this._isEmbeddedCommentVideoUrl(urls[i])) return urls[i]
+				}
+				return ''
+			},
+			getCommentTextOnly(it) {
+				if (!it || it.content == null) return ''
+				let text = String(it.content).replace(/\u21b5/g, '\n')
+				const strip = new Set()
+				const v = this.getCommentVideoUrl(it)
+				if (v) strip.add(v)
+				const urls = this._urlsEmbeddedInCommentContent(it)
+				for (let i = 0; i < urls.length; i++) {
+					const u = urls[i]
+					if (this._isEmbeddedCommentVideoUrl(u)) strip.add(u)
+					else if (this._isEmbeddedCommentImageUrl(u) && u !== v) strip.add(u)
+				}
+				strip.forEach(u => {
+					text = text.split(u).join('')
+				})
+				return text.replace(/(\r?\n\s*){2,}/g, '\n').replace(/^\s+|\s+$/g, '').trim()
+			},
+			getCommentVideoUrl(it) {
+				if (!it) return ''
+				if (it.videoUrl) return it.videoUrl
+				if (it.video) return it.video
+				if (it.mediaType === 'video' && it.mediaUrl) return it.mediaUrl
+				return this._videoUrlFromCommentContent(it)
+			},
+			getCommentVideoPoster(it) {
+				if (!it) return ''
+				const raw =
+					it.videoCover || it.coverUrl || it.poster || it.thumbnail || ''
+				return typeof raw === 'string' ? raw.trim() : String(raw || '').trim()
+			},
+			commentImageUrls(it) {
+				if (!it) return []
+				const raw = it.images || it.imageUrl || it.imgUrl || it.picUrl || it.pic
+				let fromFields = []
+				if (raw) {
+					if (Array.isArray(raw)) fromFields = raw.filter(Boolean)
+					else fromFields = String(raw).split(',').map(s => s.trim()).filter(Boolean)
+				}
+				const videoUrl = this.getCommentVideoUrl(it)
+				const fromContent = this._urlsEmbeddedInCommentContent(it).filter(u =>
+					this._isEmbeddedCommentImageUrl(u) && !this._isEmbeddedCommentVideoUrl(u) && u !== videoUrl
+				)
+				return [...new Set([...fromFields, ...fromContent])]
+			},
+			_pauseCourseVideo() {
+				try {
+					const ctx =
+						this.videoContext ||
+						uni.createVideoContext('video-content-box', this)
+					this.videoContext = ctx
+					if (ctx && ctx.pause) ctx.pause()
+				} catch (e) {}
+				try {
+					if (this.player && this.player.pause) this.player.pause()
+				} catch (e2) {}
+			},
+			_resumeCourseVideoAfterFeaturedJob() {
+				if (!this._shouldResumeCourseVideoAfterFeaturedUpload) return
+				this._shouldResumeCourseVideoAfterFeaturedUpload = false
+				this._courseWasPlayingBeforeFeaturedCommentOpen = false
+				if (this.isEnded || !this.videoUrl || !this.videoId) return
+				const ctx =
+					this.videoContext ||
+					uni.createVideoContext('video-content-box', this)
+				this.videoContext = ctx
+				const tryPlay = () => {
+					try {
+						if (ctx && ctx.play) ctx.play()
+					} catch (e) {}
+				}
+				this.$nextTick(() => {
+					tryPlay()
+					setTimeout(tryPlay, 80)
+					setTimeout(tryPlay, 260)
+				})
+			},
+			getFeaturedCommentRowKey(it, idx) {
+				const id =
+					it && it.commentId != null && it.commentId !== ''
+						? String(it.commentId)
+						: it && it.id != null
+							? String(it.id)
+							: ''
+				return 'fc-' + idx + '-' + (id || 'n')
+			},
+			getFeaturedCommentVideoId(it, idx) {
+				return 'feat-comment-video-' + this.getFeaturedCommentRowKey(it, idx)
+			},
+		openFeaturedCommentMediaPreview(it, listIdx, mode, imageIndex) {
+			const m = mode === 'video' ? 'video' : 'image'
+			if (m === 'image') {
+				const urls = this.commentImageUrls(it).filter(u => u && !/^blob:/i.test(u))
+				if (!urls.length) return
+				const i = Math.min(
+					Math.max(0, Number(imageIndex) || 0),
+					urls.length - 1
+				)
+				this._pauseCourseVideo()
+				try {
+					if (this.getCommentVideoUrl(it)) {
+						const id = this.getFeaturedCommentVideoId(it, listIdx)
+						const c = uni.createVideoContext(id, this)
+						if (c && c.pause) c.pause()
+					}
+				} catch (e) {}
+				this.featuredCommentMediaPreviewMode = 'image'
+				this.featuredCommentMediaPreviewUrls = urls
+				this.featuredCommentMediaPreviewIndex = i
+				this.featuredCommentMediaPreviewVideoUrl = ''
+				this.featuredCommentMediaPreviewPoster = ''
+				this.featuredCommentMediaPreviewShow = true
+				return
+			}
+			const vurl = this.getCommentVideoUrl(it)
+			if (!vurl) return
+			this._pauseCourseVideo()
+			try {
+				const id = this.getFeaturedCommentVideoId(it, listIdx)
+				const c = uni.createVideoContext(id, this)
+				if (c && c.pause) c.pause()
+			} catch (e) {}
+			this.featuredCommentMediaPreviewMode = 'video'
+			this.featuredCommentMediaPreviewUrls = []
+			this.featuredCommentMediaPreviewIndex = 0
+			this.featuredCommentMediaPreviewVideoUrl = vurl
+			this.featuredCommentMediaPreviewPoster = this.getCommentVideoPoster(it) || ''
+			this.featuredCommentMediaPreviewShow = true
+			this._tryPlayFeaturedModalVideo()
+		},
+			_tryPlayFeaturedModalVideo() {
+				if (this.featuredCommentMediaPreviewMode !== 'video' || !this.featuredCommentMediaPreviewVideoUrl) {
+					return
+				}
+				const run = () => {
+					try {
+						const c = uni.createVideoContext('fc-media-preview-video', this)
+						if (c && c.play) c.play()
+					} catch (e) {}
+				}
+				this.$nextTick(() => {
+					run()
+					setTimeout(run, 100)
+					setTimeout(run, 280)
+				})
+			},
+			featuredCommentPreviewCardTap() {},
+			closeFeaturedCommentMediaPreview() {
+				if (!this.featuredCommentMediaPreviewShow) return
+				try {
+					const c = uni.createVideoContext('fc-media-preview-video', this)
+					if (c && c.pause) c.pause()
+				} catch (e) {}
+				this.featuredCommentMediaPreviewShow = false
+				this.featuredCommentMediaPreviewUrls = []
+				this.featuredCommentMediaPreviewVideoUrl = ''
+				this.featuredCommentMediaPreviewPoster = ''
+			},
+			setFeaturedMediaPreviewIndex(ti) {
+				const n = Number(ti)
+				if (
+					!Number.isFinite(n) ||
+					n < 0 ||
+					n >= (this.featuredCommentMediaPreviewUrls || []).length
+				) {
+					return
+				}
+				this.featuredCommentMediaPreviewIndex = n
+			},
+			onFeaturedMediaPreviewModalVideoPlay() {
+				this._pauseCourseVideo()
+				const list = this.featuredCommentDisplayList || []
+				for (let i = 0; i < list.length; i++) {
+					const row = list[i]
+					if (!this.getCommentVideoUrl(row)) continue
+					const vid = this.getFeaturedCommentVideoId(row, i)
+					try {
+						const c = uni.createVideoContext(vid, this)
+						if (c && c.pause) c.pause()
+					} catch (e) {}
+				}
+			},
+			_featuredMediaMaxBytes() {
+				return 100 * 1024 * 1024
+			},
+			_readFeaturedLocalFileSizeBytes(filePath) {
+				return new Promise((resolve) => {
+					const tryFsStat = () => {
+						let n = 0
+						// #ifdef MP-WEIXIN
+						try {
+							const fs = wx.getFileSystemManager && wx.getFileSystemManager()
+							if (fs && fs.statSync) {
+								const st = fs.statSync(filePath)
+								if (st && typeof st.size === 'number' && st.size > 0) n = st.size
+							}
+						} catch (e) {}
+						// #endif
+						return n
+					}
+					if (!filePath || typeof filePath !== 'string') {
+						resolve(0)
+						return
+					}
+					uni.getFileInfo({
+						filePath,
+						success: (fi) => {
+							let sz =
+								fi && fi.size != null ? Math.floor(Number(fi.size)) : 0
+							if (!Number.isFinite(sz) || sz <= 0) sz = tryFsStat()
+							resolve(sz)
+						},
+						fail: () => resolve(tryFsStat())
+					})
+				})
+			},
+			_alertFeaturedMediaLimit(content) {
+				uni.showModal({
+					title: '提示',
+					content:
+						content ||
+						'图片或视频大小不能超过100MB,请压缩或更换后再试。',
+					showCancel: false,
+					confirmText: '知道了'
+				})
+			},
+			_assertFeaturedLocalMediaUnderMaxBytes(filePath) {
+				const max = this._featuredMediaMaxBytes()
+				return new Promise((resolve) => {
+					if (!filePath || typeof filePath !== 'string') {
+						this._alertFeaturedMediaLimit('文件路径无效,请重新选择。')
+						resolve(false)
+						return
+					}
+					this._readFeaturedLocalFileSizeBytes(filePath).then((sz) => {
+						if (sz <= 0) {
+							uni.showToast({
+								title: '本地暂无法读取大小,请勿超过100MB',
+								icon: 'none',
+								duration: 2600
+							})
+							resolve(true)
+							return
+						}
+						if (sz > max) {
+							this._alertFeaturedMediaLimit()
+							resolve(false)
+							return
+						}
+						resolve(true)
+					})
+				})
+			},
+			_applyFeaturedMediaIfSizeOk(type, path, size, thumbTempPath) {
+				const max = this._featuredMediaMaxBytes()
+				const applyAccepted = () => {
+					this.featuredCommentMedia = {
+						type,
+						path,
+						thumbTempPath: thumbTempPath || ''
+					}
+				}
+				let bytes =
+					size != null && Number(size) > 0
+						? Math.floor(Number(size))
+						: 0
+				if (!Number.isFinite(bytes)) bytes = 0
+				const finalize = (n) => {
+					if (n > max) {
+						this._alertFeaturedMediaLimit()
+						return
+					}
+					applyAccepted()
+				}
+				if (bytes > 0) {
+					finalize(bytes)
+					return
+				}
+				this._readFeaturedLocalFileSizeBytes(path).then(finalize)
+			},
+			clearFeaturedCommentMedia() {
+				this.featuredCommentMedia = null
+				this._resumeCourseVideoAfterFeaturedJob()
+			},
+			_expandLayoutIfPortraitFeaturedCommentsOnly() {
+				if (this.displayType !== 'portrait') return
+				if (!this.isShu) return
+				if (!(this.visibleRatingTabCount === 1 && this.showTabFeaturedComments)) return
+				this.isShu = false
+				this.tabIndex = 2
+			},
+			_armFeaturedMediaPickerOnShowSuppress() {
+				this.videovipSuppressOnShowCourseFetchOnce = true
+				const clearIfStillArmed = () => {
+					setTimeout(() => {
+						if (this.videovipSuppressOnShowCourseFetchOnce) {
+							this.videovipSuppressOnShowCourseFetchOnce = false
+						}
+					}, 600)
+				}
+				return clearIfStillArmed
+			},
+			onFeaturedPickMedia() {
+				this._expandLayoutIfPortraitFeaturedCommentsOnly()
+				this.featuredMediaActionSheetShow = true
+			},
+			closeFeaturedMediaActionSheet() {
+				this.featuredMediaActionSheetShow = false
+			},
+			onFeaturedMediaSheetPick(tapIndex) {
+				this.closeFeaturedMediaActionSheet()
+				const afterSheetCloseMs = 350
+				setTimeout(() => {
+					if (tapIndex === 0) {
+						this._shouldResumeCourseVideoAfterFeaturedUpload =
+							!this.isEnded &&
+							(this.videoPlaying || this._courseWasPlayingBeforeFeaturedCommentOpen)
+						this._pauseCourseVideo()
+						const clearIfStillArmed = this._armFeaturedMediaPickerOnShowSuppress()
+						uni.chooseImage({
+							count: 1,
+							sizeType: ['compressed', 'original'],
+							sourceType: ['album', 'camera'],
+							success: (res) => {
+								const f0 = res.tempFiles && res.tempFiles[0]
+								const path =
+									(res.tempFilePaths && res.tempFilePaths[0]) ||
+									(f0 && f0.path) ||
+									''
+								if (!path) return
+								const size = f0 && f0.size != null ? f0.size : 0
+								this._applyFeaturedMediaIfSizeOk('image', path, size, '')
+							},
+							fail: () => {
+								// 勿在此处清 suppress:须由 onShow 消费,避免先于 onShow 清标志导致停跑马灯
+								this._resumeCourseVideoAfterFeaturedJob()
+							},
+							complete: clearIfStillArmed
+						})
+					} else if (tapIndex === 1) {
+						this._shouldResumeCourseVideoAfterFeaturedUpload =
+							!this.isEnded &&
+							(this.videoPlaying || this._courseWasPlayingBeforeFeaturedCommentOpen)
+						this._pauseCourseVideo()
+						const clearIfStillArmed = this._armFeaturedMediaPickerOnShowSuppress()
+						wx.chooseMedia({
+							count: 1,
+							mediaType: ['video'],
+							sourceType: ['album'],
+							maxDuration: 30,
+							success: (res) => {
+								const path = res.tempFiles[0].tempFilePath
+								if (!path) return
+								const size = res.tempFiles[0].size != null ? res.tempFiles[0].size : 0
+								this._applyFeaturedMediaIfSizeOk('video', path, size, res.tempFiles[0].thumbTempFilePath || '')
+							},
+							fail: () => {
+								// 勿在此处清 suppress:须由 onShow 消费,避免先于 onShow 清标志导致停跑马灯
+								this._resumeCourseVideoAfterFeaturedJob()
+							},
+							complete: clearIfStillArmed
+						})
+					}
+				}, afterSheetCloseMs)
+			},
+			async submitFeaturedComment() {
+				const raw = this.featuredCommentInput || ''
+				const text = raw.trim()
+				if (raw.length > 50) {
+					uni.showToast({
+						title: '留言不能超过50个字',
+						icon: 'none'
+					})
+					this._resumeCourseVideoAfterFeaturedJob()
+					return
+				}
+				const media = this.featuredCommentMedia
+				const hasMedia = !!(media && media.path)
+				if (!text && !hasMedia) {
+					uni.showToast({
+						title: '请输入留言或选择图片/视频',
+						icon: 'none'
+					})
+					return
+				}
+				const u = this._resolveUserInfoObj()
+				const userId = u.userId || ''
+				if (!userId) {
+					uni.showToast({
+						title: '请先登录',
+						icon: 'none'
+					})
+					this._resumeCourseVideoAfterFeaturedJob()
+					return
+				}
+				if (this.featuredCommentSending) return
+				if (hasMedia && media.path) {
+					const ok = await this._assertFeaturedLocalMediaUnderMaxBytes(media.path)
+					if (!ok) {
+						this._resumeCourseVideoAfterFeaturedJob()
+						return
+					}
+				}
+				this.featuredCommentSending = true
+				const done = (res) => {
+					this.featuredCommentSending = false
+					if (res.code == 200) {
+						this.featuredCommentInput = ''
+						this.featuredCommentMedia = null
+						this._closeFeaturedCommentComposerUi()
+						uni.showToast({
+							title: '发送成功',
+							icon: 'none'
+						})
+						this.loadFeaturedComments({
+							scrollToBottom: true
+						})
+					} else {
+						uni.showToast({
+							title: res.msg || '发送失败',
+							icon: 'none'
+						})
+					}
+				}
+				const fail = (err) => {
+					this.featuredCommentSending = false
+					const msg = err && err.message ? err.message : '网络异常,请重试'
+					uni.showToast({
+						title: msg,
+						icon: 'none'
+					})
+				}
+				const payload = {
+					toUserId: userId,
+					courseId: this.urlOption.courseId,
+					videoId: this.videoId,
+					type: 1,
+					content: text
+				}
+				if (hasMedia) {
+					if (media.type === 'video') {
+						payload.videoFiles = media.path
+					} else {
+						payload.imageFiles = media.path
+					}
+				}
+				uni.showLoading({
+					title: '发布中',
+					mask: true
+				})
+				addCommentWithMedia(payload)
+					.then((res) => {
+						uni.hideLoading()
+						done(res)
+					})
+					.catch((err) => {
+						uni.hideLoading()
+						fail(err)
+					})
+					.then(() => {
+						this.$nextTick(() => {
+							setTimeout(() => {
+								this._resumeCourseVideoAfterFeaturedJob()
+							}, 60)
+						})
+					})
+			},
+			getWebviewUrl() {
+				var data = {
+					key: 'course.config'
+				}
+					getConfigByKey(data).then(res => {
+						if (res.code == 200) {
+							console.log("getConfigByKey====", JSON.parse(res.data))
+							let data = JSON.parse(res.data)
+							this.notice = data.camelCase
+							uni.setStorageSync('setWebviewUrl',data.userCourseAuthDomain)
+						}else{
+							uni.showToast({
+								icon:'none',
+								title: res.msg,
+							});
+						}
+					})
+			},
+			numberToChinese(number) {
+				if (number) {
+					const chineseNumber = ['一', '二', '三', '四', '五', '六', '七', '八', '九'];
+					return chineseNumber[number - 1];
+				} else {
+					return ''
+				}
+			},
+			keyboardHeightChange(res) {
+				// #ifndef H5
+				console.log("this.danmuboxHeight",this.danmuboxHeight)
+				this.danmuboxHeight = res.height
+				const h = res && res.height != null ? res.height : 0
+				const prev = this.featuredCommentKeyboardBottomPx
+				this.featuredCommentKeyboardBottomPx = h
+				if (
+					this.featuredCommentComposerActive &&
+					prev > 0 &&
+					h === 0
+				) {
+					this.featuredCommentComposerActive = false
+					this.featuredCommentInputFocused = false
+				}
+				// #endif
+			},
+			getMenuButton(){
+				const menuButtonInfo = uni.getMenuButtonBoundingClientRect()
+				this.menuButtonLeft = menuButtonInfo.left
+				this.menuButtonH = menuButtonInfo.height
+			},
+			// 购物车
+			showCart() {
+				this.isCart = true
+			},
+			closeShop() {
+				this.isCart = false
+			},
+			// 更多
+			showMore() {
+				this.isMore = true
+			},
+			closeMore() {
+				this.isMore = false
+			},
+			navgetTo(url) {
+				uni.navigateTo({ url })
+			},
+			// 商品卡片跳转
+			goBuy(item) {
+				if (!item || !item.productId) return
+				uni.navigateTo({
+					url: '/pages/shopping/productDetails?productId=' + item.productId +
+						'&companyId=' + (this.urlOption.companyId || '') +
+						'&companyUserId=' + (this.urlOption.companyUserId || '') +
+						'&courseId=' + (this.urlOption.courseId || '') +
+						'&videoId=' + (this.urlOption.videoId || '') +
+						'&projectId=' + (this.urlOption.projectId || '') +
+						'&periodId=' + (this.urlOption.periodId || '')
+				})
+			},
+			// 倒计时格式化函数
+			formatCountdown(seconds) {
+				const totalSeconds = Math.max(0, Math.floor(Number(seconds) || 0))
+				const hours = Math.floor(totalSeconds / 3600)
+				const remainingAfterHours = totalSeconds % 3600
+				const minutes = Math.floor(remainingAfterHours / 60)
+				const secs = remainingAfterHours % 60
+				return {
+					hours: this.padZero(hours),
+					minutes: this.padZero(minutes),
+					seconds: this.padZero(secs),
+					total: totalSeconds
+				}
+			},
+			getCountdownPercentage() {
+				const total = Number(this.totalRemainTime) || 0
+				if (!total) return 0
+				const remain = Math.max(0, Number(this.remainTime) || 0)
+				const watched = Math.max(0, total - remain)
+				const percentage = (watched / total) * 100
+				return Math.min(100, Math.max(0, Number(percentage.toFixed(2))))
+			},
+			padZero(num) {
+				return num < 10 ? `0${num}` : num.toString()
+			},
+			// 启动完课积分倒计时(仅在播放时递减)
+			startCountdown() {
+				if (this.remainTime <= 0 || this.countdownTimer) return;
+				this.countdownTimer = setInterval(() => {
+					if (this.remainTime > 0) {
+						this.remainTime--;
+					}
+					if (this.remainTime <= 0 && this.countdownTimer) {
+						clearInterval(this.countdownTimer);
+						this.countdownTimer = null;
+						if (!this.hasReportedAfterCountdown) {
+							this.hasReportedAfterCountdown = true;
+							this.getFinishCourseVideo();
+							this.getInternetTraffic();
+						}
+					}
+				}, 1000);
+			},
+			// 停止完课积分倒计时(暂停/离开页面时调用)
+			stopCountdown() {
+				if (this.countdownTimer) {
+					clearInterval(this.countdownTimer)
+					this.countdownTimer = null
+				}
+			},
+			// 剩余倒计时
+			getRemainTime(userId) {
+				const data = {
+					videoId: this.videoId,
+					fsUserId: userId,
+					courseId: this.urlOption.courseId,
+					qwExternalId:this.urlOption.qwExternalId,
+					qwUserId:this.urlOption.qwUserId,
+					// projectId: this.urlOption.projectId,
+					// periodId: this.urlOption.periodId,
+					companyUserId: this.urlOption.companyUserId
+				}
+				getRemainTime(data).then(res => {
+					if (res.code == 200) {
+						const remain = Number(res.remainTime) || 0
+						this.remainTime = remain;
+						this.remainTimeReady = true
+						this.hasReportedAfterCountdown = remain <= 0
+						if (!this.totalRemainTime || remain > this.totalRemainTime) {
+							this.totalRemainTime = remain;
+						}
+					} else {
+						this.remainTimeReady = false
+						uni.showToast({
+							icon: 'none',
+							title: res.msg,
+						})
+					}
+				})
+			},
+		// 根据当前播放时间:1)扫描商品栏展示(上架/下架时间)2)控制商品卡片弹窗(弹出/关闭时间)
+		updateProductAndCardDisplay(currentSec) {
+			const toSeconds = (timeStr) => {
+				if (!timeStr || typeof timeStr !== 'string') return 0
+				const parts = timeStr.split(':')
+				if (parts.length !== 3) return 0
+				const h = parseInt(parts[0], 10) || 0
+				const m = parseInt(parts[1], 10) || 0
+				const s = parseInt(parts[2], 10) || 0
+				return h * 3600 + m * 60 + s
+			}
+			const hasValidShelfTime = (timeStr) => {
+				if (!timeStr || typeof timeStr !== 'string') return false
+				if (timeStr === '00:00:00') return false
+				return !!toSeconds(timeStr)
+			}
+			if (this.treatmentPackage.length === 0) {
+				this.displayProductList = []
+				this.cardPopup = false
+				this.currentCardItem = null
+				this._syncFakeMarqueeIfEligibleChanged()
+				return
+			}
+			// 按“上架时间”倒序排序,保证后上架商品展示在列表最前
+			const sortedTreatmentPackage = this.treatmentPackage.slice().sort((a, b) => {
+				const aOn = hasValidShelfTime(a.onShelfTime) ? toSeconds(a.onShelfTime) : 0
+				const bOn = hasValidShelfTime(b.onShelfTime) ? toSeconds(b.onShelfTime) : 0
+				if (bOn !== aOn) return bOn - aOn
+				// 上架时间相同则按下架时间倒序,进一步保证新近优先
+				const aOff = hasValidShelfTime(a.offShelfTime) ? toSeconds(a.offShelfTime) : 0
+				const bOff = hasValidShelfTime(b.offShelfTime) ? toSeconds(b.offShelfTime) : 0
+				return bOff - aOff
+			})
+			const videoDuration = this.duration || 0
+			// 1. 商品栏展示:按上架/下架时间过滤
+			this.displayProductList = sortedTreatmentPackage.filter(item => {
+				// 上架时间必填;下架时间可为空(为空表示一直展示到视频结束)
+				if (!hasValidShelfTime(item.onShelfTime)) return false
+				const onShelfSec = toSeconds(item.onShelfTime)
+				if (currentSec < onShelfSec) return false
+				const hasOffShelfTime = hasValidShelfTime(item.offShelfTime)
+				if (!hasOffShelfTime) return true
+				const offShelfSec = toSeconds(item.offShelfTime)
+				if (videoDuration > 0 && offShelfSec > videoDuration) return true
+				return currentSec < offShelfSec
+			})
+			//console.log('this.displayProductList',this.displayProductList)
+			// 2. 商品卡片弹窗:按弹出/关闭时间查找当前应展示的卡片
+			let activeCard = null
+			let activePopupSec = -1
+			for (let i = 0; i < sortedTreatmentPackage.length; i++) {
+				const item = sortedTreatmentPackage[i]
+				const popupStr = item.cardPopupTime
+				const closeStr = item.cardCloseTime
+				if (!popupStr || popupStr === '00:00:00') continue
+				const popupSec = toSeconds(popupStr)
+				if (!popupSec) continue
+				const closeSec = (closeStr && closeStr !== '00:00:00') ? toSeconds(closeStr) : null
+				if (currentSec >= popupSec && (closeSec == null || currentSec < closeSec)) {
+					// 同时命中多个弹窗时:优先展示“启动时间更晚”的后续弹窗
+					if (popupSec > activePopupSec) {
+						activePopupSec = popupSec
+						activeCard = item
+					} else if (popupSec === activePopupSec && activeCard) {
+						// 上架时间更晚优先(兜底)
+						const activeOn = hasValidShelfTime(activeCard.onShelfTime) ? toSeconds(activeCard.onShelfTime) : 0
+						const itemOn = hasValidShelfTime(item.onShelfTime) ? toSeconds(item.onShelfTime) : 0
+						if (itemOn > activeOn) activeCard = item
+					}
+				}
+			}
+			const activeCardKey = activeCard ?
+				`${activeCard.productId || ''}_${activeCard.cardPopupTime || ''}_${activeCard.cardCloseTime || ''}` :
+				''
+			if (!activeCardKey) {
+				this.dismissedCardKey = ''
+			}
+			this.cardPopup = !!activeCard && this.dismissedCardKey !== activeCardKey
+			//this.getVideoContainerHeight()
+			this.currentCardItem = activeCard
+			this._syncFakeMarqueeIfEligibleChanged()
+		},
+			//播放时间更新事件方法
+			onTimeUpdate(e){
+				let currentTime = Math.round(e.detail.currentTime)
+				if (this.playDurationSeek > 0) {
+					this.playTime = this.playDurationSeek
+					this.throttle(() => this.changeTime(this), 1000, false)
+				} else {
+					const suppressAntiSeek = Date.now() < (this._antiSeekSuppressExpireAt || 0)
+					if (!suppressAntiSeek && this.videolinkType != 1 && (currentTime - this.playTime > 3 || currentTime - this.playTime < -3)&&this.isFinish!=1) {
+						uni.showToast({
+							title: '不能快进哦',
+							icon: 'none',
+						});
+						currentTime = this.playTime
+						this.player.seek(this.playTime);
+					}
+					this.playTime = currentTime
+				}
+				if (Math.floor(e.detail.currentTime) != this.flagTime) {
+					this.flagTime = Math.floor(e.detail.currentTime)
+					let answerType = this.$store.state.answerType;
+					
+					this.showAnswerTip = answerType == 1 ? this.shouldShowByRate(this): this.shouldShowByLastMinute(this);
+					if(this.openCommentStatus == 2) {
+						this.$refs.danmuBox&&this.$refs.danmuBox.checkDanmu(this.flagTime)
+					}
+				}
+				// 基于播放时间动态更新商品上/下架列表、商品卡片弹窗,以及完课积分倒计时
+				this.updateProductAndCardDisplay(this.playTime)
+				this.startCountdown()
+			},
+			// 工具函数:保留两位小数的百分比(0~100)
+			calcPercent(play, total) {
+			  return Number(((play || 0) / (total || 1) * 100).toFixed(2));
+			},
+			
+			// 策略1:按完课领红包
+			shouldShowByRate({ playTime, duration, config }) {
+			  const finished = this.calcPercent(playTime, duration) >= Number(config?.answerRate || 100);
+			  return finished;
+			},
+			
+			// 策略2:完课且最后一分钟可领(第二次进来只看是否已完课)
+			shouldShowByLastMinute({ isEnded, isFinish, playTime, duration }) {
+			  const alreadyDone = isEnded || isFinish == 1;          // 已完课
+			  const inLastMinute = playTime >= (duration || 0) - 60;  // 最后一分钟
+			  return alreadyDone || inLastMinute;
+			},
+			changeTime(that,e) {
+				that.playDurationSeek = 0
+			},
+			videoErrorCallback(e) {
+				this.clearIntegral()
+				this.errorCount++
+				if (this.errorCount > 3) return
+				if (this.interval != null) {
+					clearInterval(this.interval)
+				}
+				this.getErrMsg(e.target.errMsg)
+				this.getH5CourseVideoDetails('error')
+			},
+			// 当开始/继续播放时触发play事件
+			getPlay() {
+				this.errorCount = 0
+				this.videoPlaying = true
+				// this.judgeDuration()
+				this.startCountdown()
+			},
+			getPause() {
+				this.videoPlaying = false
+				this.clearIntegral()
+				this.stopCountdown()
+			},
+			getEnded() {
+				this.videoPlaying = false
+				this.clearIntegral()
+				this.stopCountdown()
+				this.isEnded = true
+				this.showAnswerTip = true
+				// this.playDurationSeek = 0
+				this.isFinish = 1
+				this.showProgress = true
+				this.getFinishCourseVideo()
+			},
+			fullscreenchange(event) {
+				//this.isfull = event.detail.fullScreen
+				// if(this.isfull) {
+				// 	this.$refs.danmuBox&&this.$refs.danmuBox.initTracks()
+				// }
+				const isFullScreen = !!(event && event.detail && event.detail.fullScreen);
+				this.isFull = event.detail.fullScreen;
+				// 竖屏课程下:把全屏按钮当作布局切换按钮,禁止原生全屏停留
+				if (this.displayType === 'portrait') {
+					if (event && event.stopPropagation) event.stopPropagation();
+					if (event && event.preventDefault) event.preventDefault();
+					// 只在“进入全屏”时切换,避免 exitFullScreen 触发的 false 事件二次反转
+					if (!isFullScreen || this.fullscreenToggleLock) return;
+					this.fullscreenToggleLock = true;
+					const wasShu = this.isShu
+					this.isShu = !this.isShu;
+					if (!this.isShu && wasShu && this.showTabReviewPoints) this.tabIndex = 0
+					// 先让布局切换完成,再退出原生全屏,减少抖动闪频
+					setTimeout(() => {
+						if (this.videoContext && this.videoContext.exitFullScreen) {
+							this.videoContext.exitFullScreen();
+						}
+						this.isFull = false;
+						this.fullscreenToggleTimer = setTimeout(() => {
+							this.fullscreenToggleLock = false;
+							this.fullscreenToggleTimer = null;
+						}, 220);
+					}, 40);
+					//console.log(this.isFull,'this.isFull111 ')
+				}
+			},
+			controlstoggle(event) {
+				this.crtShow =  event.detail.show
+			},
+			getIP() {
+				uni.request({
+					url: 'https://ipinfo.io/json', //仅为示例,并非真实接口地址。
+					method: 'GET',
+					success: (res) => {
+						this.ip = res.data.ip
+					}
+				});
+			},
+			getHeight() {
+				this.height =
+					`calc(100vh - 420rpx - 160rpx)`
+				// setTimeout(()=>{
+				// 	const query = uni.createSelectorQuery().in(this);
+				// 	query
+				// 		.select("#title-contentnav")
+				// 		.boundingClientRect((data) => {
+				// 			if(data) {
+				// 				this.height =
+				// 					`calc(100vh - ${data.height}px - 420rpx - ${this.statusBarHeight}px - 75px - 88rpx)`
+				// 			}
+				// 		})
+				// 		.exec();
+				// },200)
+			},
+			updateTime() {
+				var that = this;
+				if (this.interval != null) {
+					clearInterval(this.interval)
+				}
+				this.interval = setInterval(function() {
+					that.getFinishCourseVideo()
+					that.getInternetTraffic()
+				}, 60000);
+			},
+			judgeDuration() {
+				var that = this;
+				if (this.intervalIntegral != null) {
+					clearInterval(this.intervalIntegral)
+					this.intervalIntegral = null
+				}
+				// 观看10分钟获得积分
+				this.intervalIntegral = setInterval(function() {
+					that.getIntegralByH5Video()
+				}, 600000);
+			},
+			clearIntegral() {
+				if (this.intervalIntegral != null) {
+					clearInterval(this.intervalIntegral)
+					this.intervalIntegral = null
+				}
+			},
+			getH5CourseByVideo() {
+				this.loading = true
+				getH5CourseByVideoId({
+					videoId: this.videoId
+				}).then(res => {
+						this.loading = false
+						if (res.code == 200) {
+							this.courseInfo = res.data
+							uni.setNavigationBarTitle({
+								title: this.courseInfo && this.courseInfo.title ? this.courseInfo.title : ''
+							});
+							this.$nextTick(() => {
+								this._syncRatingTabIndex()
+							})
+						}
+						this.getHeight()
+						this.$nextTick(()=>{
+							this.$refs.descInfo&&this.$refs.descInfo.getDescHeight()
+							this.$refs.descInfoNav&&this.$refs.descInfoNav.getDescHeight()
+						})
+					},
+					rej => {
+						this.loading = false
+					}
+				).catch(() => {
+					this.loading = false
+				})
+			},
+			getH5CourseVideoDetails(type) {
+				getH5CourseVideoDetails(this.urlOption).then(res => {
+						if (res.code == 200) {
+							this.config = res.config || {}
+							this.courseLogo = res.config&&res.config.courseLogo
+							this.isFinish = res.isFinish || 0
+							this.duration = res.course && res.course.duration ? res.course.duration : 0
+							this.playDuration = res.playDuration || 0
+							this.tipsTime = res.tipsTime || 0
+							this.displayType = res.course && res.course
+								.displayType != '' ? res.course.displayType :'landscape'
+							this.isShu = this.displayType=='landscape'?false:true
+							const showTreatmentFlag = res.course&&res.course.showProduct!=null ? res.course.showProduct : 1
+							this.treatmentPackage = res.course&&res.course.fsStoreProductScrms ? res.course.fsStoreProductScrms : []
+							this.showTreatment = showTreatmentFlag==0&&this.treatmentPackage.length>0 ? 0 : 1;
+							let lineList = []
+							if (res.course && res.course.lineOne) {
+								lineList.push(res.course.lineOne)
+							}
+							if (res.course && res.course.lineTwo) {
+								lineList.push(res.course.lineTwo)
+							}
+							if (res.course && res.course.lineThree) {
+								lineList.push(res.course.lineThree)
+							}
+							this.lineList = lineList
+							this.viewCommentNum = res.config&&res.config.viewCommentNum || 200
+		
+							const status = res.config&&res.config.openCommentStatus || 3
+							if(status != this.openCommentStatus) {
+								if(this.openCommentStatus != 3 && status==3) {
+									this.$refs.commentBox&&this.$refs.commentBox.closeWSocket()
+									this.$refs.danmuBox&&this.$refs.danmuBox.closeWSocket()
+								}
+								this.openCommentStatus = this.isOpen == 1 ? 3: status
+							}
+							this.currentTab = 1
+							if(this.openCommentStatus!=2 || this.showDanmu!=1) {
+								this.activeDanmus = []
+							}
+							if (!this.player || type == 'error') {
+								this.lineIndex = this.config.defaultLine
+								this.videoUrl = lineList[this.lineIndex]
+								this.poster= res.course && res.course.imgUrl ? res.course.imgUrl : ''
+								// this.options.sources = [{
+								// 	src: this.videoUrl
+								// }]
+								// this.options.poster = res.course && res.course.imgUrl ? res.course.imgUrl : ''
+								// this.initVideo()
+								this.playTime = this.playDuration >= this.duration ? 0 : this.playDuration
+								this.playDurationSeek = this.playTime
+								this.updateProductAndCardDisplay(this.playTime || 0)
+								setTimeout(()=>{
+									this.player = uni.createVideoContext('video-content-box');
+									this.player.seek(this.playTime)
+									this.player.play();
+									this._touchAntiSeekSuppress(2000)
+								},500);
+							} else {
+								// let div = document.querySelector(".vjs-progress-control");
+								// if(div) {
+								// 	if (this.isFinish == 1 || this.isEnded || this.videolinkType == 1) {
+								// 		div.style.pointerEvents = "auto";
+								// 	} else {
+								// 		div.style.pointerEvents = "none"; //禁止所有事件
+								// 	}
+								// }
+								this.playTime = this.playTime > this.playDuration ? this.playTime : this.playDuration >= this.duration ? 0 : this.playDuration
+								this.playDurationSeek = this.playTime
+								this.updateProductAndCardDisplay(this.playTime || 0)
+								this.player.seek(this.playTime)
+								this.player.play();
+								this._touchAntiSeekSuppress(2000)
+							}
+							this.updateTime();
+							this.$nextTick(() => {
+								this.marqueeDataReady = true
+								this._syncFakeMarqueeIfEligibleChanged()
+							})
+							const rawQ =
+								(res.course && res.course.questionBankList) ||
+								res.questionBankList ||
+								res.questions ||
+								[]
+							const qbl = Array.isArray(rawQ) ? rawQ : []
+							this.questionBankList = qbl
+							if (qbl.length === 0) {
+								this.isquestion = true
+								this.quesList = []
+							} else {
+								this.isquestion = false
+								this.quesList = qbl.map(item => ({
+									...item,
+									questionOption: JSON.parse(item.question),
+									answer: ''
+								}))
+							}
+							this.$nextTick(() => {
+								this._syncRatingTabIndex()
+							})
+						}
+						this.getHeight()
+						this.$nextTick(()=>{
+							this.$refs.descInfo&&this.$refs.descInfo.getDescHeight()
+							this.$refs.descInfoNav&&this.$refs.descInfoNav.getDescHeight()
+						})
+					},
+					rej => {}
+				)
+			},
+			goRate(index){
+				this.aindex = index
+				if (this._rateBounceTimer) {
+					clearTimeout(this._rateBounceTimer)
+					this._rateBounceTimer = null
+				}
+				this.rateBounceIndex = null
+				this.$nextTick(() => {
+					this.rateBounceIndex = index
+					this._rateBounceTimer = setTimeout(() => {
+						this.rateBounceIndex = null
+						this._rateBounceTimer = null
+					}, 480)
+				})
+			},
+			handleAnswer(item, option,index) {
+				// 完课积分倒计时:倒计时未结束前不允许答题
+				this.goRate(option.indexId)
+				if (Number(this.remainTime || 0) > 0) {
+					uni.showToast({
+						title: "完课倒计时结束再评分",
+						icon: "none"
+					})
+					return
+				}
+				if (item.type == 1) {
+					// 单选option
+					item.answer = option.name
+				} else if (item.type == 2) {
+					// 多选
+					let answer = item.answer ? item.answer.split(',') : []
+					if (answer.indexOf(option.name) === -1) {
+						answer.push(option.name)
+						item.answer = answer.join(',')
+					} else {
+						answer.splice(answer.indexOf(option.name), 1)
+						item.answer = answer.join(',')
+					}
+				}
+			},
+			submit() {
+				if(this.isExpire){
+					uni.showToast({
+						title: '课程已过期或链接无效',
+						icon: 'none'
+					});
+					return
+				}
+				// 登录
+				this.$isLoginCourseAuto().then(
+					res => {
+						if(res){
+							if (this.isAddKf == 1) {
+								// 答题
+								// 您已提交过答案,请领取红包
+								this.courseAnswer()
+							} else {
+								// 添加客服
+								if (this.videoId && this.qwUserId) {
+									this.getIsAddKf()
+								} else {
+									uni.showToast({
+										title: '请添加客服',
+										icon: 'none'
+									})
+								}
+							} 
+						} else{
+							this.goLogin()
+						}
+					},
+					rej => {}
+				);
+			},
+			// 答题
+			courseAnswer() {
+				// 完课积分倒计时:倒计时未结束前不允许提交
+				if (Number(this.remainTime || 0) > 0) {
+					uni.showToast({
+						title: "完课倒计时结束再评分",
+						icon: "none"
+					})
+					return
+				}
+				if (this.quesList.some(item => !item.answer)) {
+					uni.showToast({
+						title: "请选择评分",
+						icon: "none"
+					})
+					return
+				}
+				const questions = this.quesList.map(obj => {
+					const {
+						questionOption,
+						...rest
+					} = obj;
+					return rest;
+				});
+				const param = {
+					...this.urlOption,
+					questions: questions,
+					videoId: this.videoId,
+					duration: this.playTime,
+				}
+				this.errTitle = ""
+				this.errDesc = ""
+				this.errQues = []
+				courseAnswer(param).then(res => {
+						if (res.code == 200) {
+							if (res.incorrectQuestions) {
+								// 答题失败
+								if (res.incorrectQuestions.length > 0) {
+									this.errQues = res.incorrectQuestions
+								}
+								this.remain = res.remain || 0
+								if (res.remain > 0) {
+									this.errTitle = "很遗憾答错了"
+									this.errDesc = `<span style="color:#FF5C03">还有${res.remain}次机会,继续加油</span>`
+									this.$refs.answerPopup.open("center")
+								}
+							} else {
+								// 答题成功
+								this.errTitle = "完课积分已到账"
+								if (res.msg == '答题成功') {
+									this.closeAnswerPopup(1)
+								}
+								// this.errTitle = "恭喜你,回答正确"
+								// this.errDesc = `请选择奖励`
+								// this.$refs.answerPopup.open("center")
+								// if(this.isOpen==1) {
+								// 	this.$refs.answerPopup.open("center")
+								// 	return
+								// }
+								// this.closeAnswerPopup(1)
+							}
+						} else {
+							if (res.msg == "该课题到达答错次数限制") {
+								this.errTitle = "答题次数超过限制"
+								this.errDesc = "以后的课程要认真学习哦"
+								this.$refs.answerPopup.open("center")
+							} else {
+								uni.showToast({
+									title: res.msg,
+									icon: "none"
+								})
+							}
+						}
+					},
+					rej => {}
+				)
+			},
+			// 选择
+			rewardChange(e) {
+				this.currentReward = e.detail.value
+			},
+			closeAnswerPopup(type) {
+				//this.$refs.answerPopup.close()
+				// if(this.isOpen==1) {
+				// 	return
+				// }
+				uni.showLoading({
+					title: "加载中..."
+				})
+				if (this.errTitle == '完课积分已到账') {
+					let param = {
+						...this.urlOption,
+						rewardType: Number(this.currentReward),
+						source: 2,
+						appId: this.appid
+					}
+					if(type==1) {
+						param = {
+							...this.urlOption,
+							source: 2,
+							appId: this.appid
+						}
+					}
+					sendReward(param).then(res => {
+						if(res.isNew&&res.isNew==1) {
+							const packageInfo = res.data.packageInfo || ''
+							if(packageInfo) {
+								uni.setStorageSync('receive_package',packageInfo);
+								if(res.mchId) uni.setStorageSync('mchId',res.mchId);
+								uni.navigateTo({
+									url: '/pages_course/reward'
+								})
+							}
+						} else {
+							uni.showToast({
+								title: res.msg,
+								icon: 'none'
+							})
+						}
+					})
+				}
+			},
+			// 线路
+			openPop() {
+				this.$refs.popup.open('bottom')
+			},
+			close() {
+				this.$refs.popup.close()
+			},
+			handleLine(index) {
+				var that=this;
+				if (this.lineIndex == index && this.videoUrl == this.lineList[index]) {
+					this.close()
+					return
+				} else {
+					// let div = document.querySelector(".vjs-progress-control");
+					// if(div) {
+					// 	if (this.isFinish == 1 || this.isEnded || this.videolinkType == 1) {
+					// 		div.style.pointerEvents = "auto";
+					// 	} else {
+					// 		div.style.pointerEvents = "none"; //禁止所有事件
+					// 	}
+					// }
+					this.lineIndex = index
+					this.videoUrl = this.lineList[index]
+					this.tipsOpen = false
+					this.playDurationSeek = this.playTime || 0
+					this.player = uni.createVideoContext('video-content-box');
+					setTimeout(function(){
+						that.player.seek(that.playDurationSeek)
+						that.player.play();
+					},500);
+					// this.player.src(this.lineList[index])
+					// this.player.one('loadedmetadata', () => {
+					// 	this.player.currentTime(this.playDurationSeek);
+					// 	this.player.play();
+					// });
+					this.close()
+				}
+
+			},
+			// 温馨提示
+			openTipsPop() {
+				this.$refs.tipsPopup.open()
+				this.tipsOpen = true
+				this.pause()
+			},
+			closeTipsPop() {
+				this.$refs.tipsPopup.close()
+			},
+			// 客服
+			getIsAddKf() {
+				this.qrcode = ''
+				this.qrcodeMsg = ''
+				this.isAddKf = 0
+				// {videoId: this.videoId,qwUserId: this.qwUserId,corpId: this.corpId}
+				getIsAddKf(this.urlOption).then(res => {
+						if (res.code == 200) {
+							this.isAddKf = 1
+						this.isLogin = true
+							this.getH5CourseVideoDetails()
+						if (this.user && this.user.userId) {
+							this.getRemainTime(this.user.userId)
+							this.loadFeaturedComments()
+						}
+						this.getMp()
+						} else if (res.code == 400) {
+							this.isAddKf = 0
+							this.qrcode = res.qrcode
+							this.qrcodeMsg = res.msg
+							this.$refs.kfPopup.open()
+							this.initExpiration(res.msg,res.code)
+						} else if (res.code == 504) {
+							// 登录
+							this.goLogin()
+							this.initExpiration(res.msg,res.code)
+						} else if (res.code == 566) {
+							// 官方群发通用链接
+							const url = res.courseLink.realLink.split('?course=')[1]
+							this.urlOption = JSON.parse(url)
+							this.isAddKf = 1
+							this.isLogin = true
+							this.getH5CourseVideoDetails()
+							if (this.user && this.user.userId) {
+								this.getRemainTime(this.user.userId)
+								this.loadFeaturedComments()
+							}
+							// this.initExpiration(res.msg,res.code)
+						} else if (res.code == 567) {
+							// 群聊通用链接
+							this.urlOption = {
+								...this.urlOption,
+								qwExternalId: res.qwExternalId
+							}
+							this.isAddKf = 1
+							this.isLogin = true
+							this.getH5CourseVideoDetails()
+							if (this.user && this.user.userId) {
+								this.getRemainTime(this.user.userId)
+							}
+							// this.initExpiration(res.msg,res.code)
+						} else {
+							this.isAddKf = 0
+							uni.showToast({
+								title: res.msg,
+								icon: 'none'
+							});
+							this.initExpiration(res.msg,res.code)
+						}
+					},
+					err => {}
+				);
+			},
+			getMp(){
+				let provider = 'weixin'
+				uni.login({
+					provider: provider,
+					success: async loginRes => {
+						console.log(loginRes)
+						uni.getUserInfo({
+						   provider: provider,
+						   success: (infoRes)=> {
+							  //   uni.showToast({
+									// title: '处理中...',
+									// icon: 'loading'
+							  //   });
+								//console.log(infoRes,'infoRes')
+								loginByMiniApp({
+									code: loginRes.code,
+									encryptedData:infoRes.encryptedData,
+									iv:infoRes.iv,
+									appId:wx.getAccountInfoSync().miniProgram.appId,
+								}).then(res=>{
+									 //uni.hideLoading();
+									 if (res.code == 200) {
+										 uni.setStorageSync('userInfo',JSON.stringify(res.user));
+									 } else {
+										uni.showToast({
+											title: res.msg,
+											icon: 'none'
+										});
+									 }
+								 }).catch(err=>{
+									//uni.hideLoading();
+									uni.showToast({
+										icon:'none',
+										title: "登录失败,请重新登录",
+									});
+								});
+						   }
+						});
+					}
+				})
+			},
+			initExpiration(resMsg,resCode) {
+				if(resCode==401) return;
+				this.resMsg = resMsg
+				this.resCode = resCode
+				this.showExpiration = true
+			},
+			closeKFPop() {
+				this.$refs.kfPopup.close()
+			},
+			getFinishCourseVideo() {
+				if (!this.playTime || this.isAddKf!=1 ||!this.isLogin) return
+				// {videoId: this.videoId,duration:this.playTime}
+				const param = {
+					duration: this.playTime,
+					...this.urlOption
+				}
+				getFinishCourseVideo(param)
+			},
+			// 每十分钟获得积分
+			getIntegralByH5Video() {
+				if(this.isAddKf!=1||!this.isLogin) return
+				const param = {
+					duration: this.playTime,
+					...this.urlOption
+				}
+				getIntegralByH5Video(param).then(res => {
+					if (res.code == 200) {
+						uni.showToast({
+							title: "积分+10",
+							icon: "none"
+						})
+					}
+				})
+			},
+			progressChange(e) {
+				this.bufferRate = Math.ceil(e.detail.buffered)
+			},
+			// 缓冲
+			getInternetTraffic() {
+				if(!this.isLogin||this.isAddKf!=1) return
+				const playVideoTime = Math.ceil(this.playTime / this.duration * 100) // 播放百分比
+				if(this.bufferRate == 0 || this.bufferRate < playVideoTime) {
+					this.bufferRate = playVideoTime
+				}
+				if(this.bufferRate == 0 || Number(this.bufferRate.toFixed(2)) == 0) return
+				const param = {
+					...this.urlOption,
+					uuId: dayjs().format('YYYYMMDD') + this.uuId,
+					duration: this.playTime,
+					bufferRate: Number(this.bufferRate.toFixed(2)),
+				}
+				if(!param.bufferRate) return
+				getInternetTraffic(param)
+			},
+			getErrMsg(err) {
+				let msgerr = {
+					videoUrl: this.videoUrl,
+					lineIndex: this.lineIndex,
+					errTime: new Date(),
+					ip: this.ip,
+					errMsg: err
+				}
+				getErrMsg({
+					msg: JSON.stringify(msgerr)
+				})
+			},
+			goLogin(data) {
+				console.log(this.isSpare,'this.isSpare')
+				if(data || this.isSpare==1) {
+					this.loginFsUserWx(data)
+					return
+				}
+				let provider = 'weixin'
+				uni.login({
+					provider: provider,
+					success: async loginRes => {
+						uni.getUserInfo({
+						   provider: provider,
+						   success: (infoRes)=> {
+							    uni.showToast({
+									title: '处理中...',
+									icon: 'loading'
+							    });
+								loginByMp({
+									code: loginRes.code,
+									encryptedData:infoRes.encryptedData,
+									iv:infoRes.iv,
+									appId: this.appid
+								}).then(res=>{
+									 uni.hideLoading();
+									 if (res.code == 200) {
+										this.$store.commit('setCoureLogin', 1);
+										uni.setStorageSync(TOKEN_KEYAuto, res.token);
+										uni.setStorageSync('auto_userInfo', JSON.stringify(res.user));
+										this.user = res.user
+										this.isLogin = true
+										console.log("TOKEN_KEYAuto",TOKEN_KEYAuto)
+										this.getIsAddKf() 
+									 } else {
+										uni.showToast({
+											title: res.msg,
+											icon: 'none'
+										});
+									 }
+								 }).catch(err=>{
+									uni.hideLoading();
+									uni.showToast({
+										icon:'none',
+										title: "登录失败,请重新登录",
+									});
+								});
+						   }
+						});
+					}
+				})
+			},
+			getLink() {
+				let that = this;
+				this.msg = ''
+				if(this.isOpen==1) {
+					if (this.isLogin && this.isAddKf == 1) {
+						this.getH5CourseVideoDetails()
+					}
+					if (this.videoId &&this.isAddKf != 1) {
+						this.$isLoginCourseAuto().then(
+							isLogin => {
+								this.isLogin = isLogin
+								if(isLogin){
+									this.getIsAddKf() 
+								} else {
+									this.goLogin()
+								}
+							},
+							rej => {}
+						);
+					}
+					return
+				}
+				getRealLink({sortLink:this.sortLink}).then(res=>{
+					if(res.code == 200) {
+						this.isExpire = false
+						// 如果响应中包含真实链接,则跳转到真实链接
+						// window.location.href = res.realLink +"&sortLink="+this.sortLink+"&code="+this.code+"&time="+new Date().getTime()
+						if (this.isLogin && this.isAddKf == 1) {
+							this.getH5CourseVideoDetails()
+						}
+						if (this.videoId &&this.isAddKf != 1) {
+							this.$isLoginCourseAuto().then(
+								isLogin => {
+									this.isLogin = isLogin
+									if(isLogin){
+										this.getIsAddKf() 
+									} else {
+										this.goLogin()
+									}
+								},
+								rej => {}
+							);
+						}
+					} else {
+						this.isExpire = true
+						this.msg = '课程已过期或链接无效'
+						uni.showToast({
+							title: '课程已过期或链接无效',
+							icon: 'none'
+						});
+					}
+				}).catch(err=>{
+					this.isExpire = true
+					this.msg = '发生错误,请稍后再试'
+					uni.showToast({
+						title: '发生错误,请稍后再试',
+						icon: 'none'
+					});
+				})
+			},
+			/**
+			 * 节流原理:在一定时间内,只能触发一次
+			 *
+			 * @param {Function} func 要执行的回调函数
+			 * @param {Number} wait 延时的时间
+			 * @param {Boolean} immediate 是否立即执行
+			 * @return null
+			 */
+			throttle(func, wait = 1000, immediate = true) {
+			    if (immediate) {
+			        if (!this.flag) {
+			            this.flag = true
+			            // 如果是立即执行,则在wait毫秒内开始时执行
+			            typeof func === 'function' && func()
+			            this.timer = setTimeout(() => {
+			                this.flag = false
+			            }, wait)
+			        }
+			    } else if (!this.flag) {
+			        this.flag = true
+			        // 如果是非立即执行,则在wait毫秒内的结束处执行
+			        this.timer = setTimeout(() => {
+			            this.flag = false
+			            typeof func === 'function' && func()
+			        }, wait)
+			    }
+			},
+			// 弹幕
+			openDanmu(type) {
+				this.openDanmuType = type
+				this.inputText = ''
+				if(type == 1) {
+					this.player.exitFullScreen()
+				}
+				this.$refs.danmuPopup.open()
+			},
+			changeShowPopup(val) {
+				this.focus = val.show
+			},
+			switchDanmu() {
+				this.showDanmu = this.showDanmu == 1 ? 0:1
+				if(this.showDanmu == 0&&this.$refs.danmuBox) {
+					this.$refs.danmuPopup.close()
+					this.activeDanmus = []
+					this.$refs.danmuBox.activeDanmus = []
+					this.$refs.danmuBox.initTracks()
+				}
+			},
+			getScrollTop(res) {
+				if(this.currentTab == 2) {
+					this.scrollTop = res
+				} else {
+					this.scrollTop = 0
+				}
+			},
+			handleTab(index) {
+				this.currentTab = index
+				if(this.currentTab==2) {
+					if(this.$refs.commentBox) {
+						this.$refs.commentBox.msgs = []
+						this.$refs.commentBox.pageNum = 1
+						this.$refs.commentBox.getCommentsFun()
+					}
+				} else {
+					setTimeout(()=>{
+						this.scrollTop = 0
+					},100)
+				}
+			},
+			handleRefresher() {
+				this.triggered = true;
+				if (!this.isMore&&this.currentTab==2&&this.openCommentStatus==1) {
+					this.$nextTick(()=>{
+						this.$refs.commentBox&&this.$refs.commentBox.getCommentsFun()
+					})
+				}
+				setTimeout(() => {
+					this.triggered = false;
+				}, 500);
+			},
+			getMore(val) {
+				this.triggered = false;
+				this.isMore = val == 1
+			},
+			handleChatInput() {
+				this.inputText = this.inputText.trim()
+				if (this.inputText == "" || this.inputText.trim() == "") {
+					uni.showToast({
+						title: '请输入评论',
+						icon: "none"
+					})
+					return;
+				}
+				if(this.openCommentStatus==1) {
+					this.$refs.commentBox&&this.$refs.commentBox.handleInput(this.inputText)
+				} else if(this.openCommentStatus==2) {
+					this.$refs.danmuBox&&this.$refs.danmuBox.handleInput(this.inputText)
+				}
+			},
+			setInputText() {
+				this.inputText = ""
+				if(this.openCommentStatus==2) {
+					this.$refs.danmuPopup.close()
+				}
+			},
+			getActiveDanmus(val) {
+				this.activeDanmus = val.map(item=>({
+					...item,
+					danmustyle: {
+						top: item.top + 'px',
+						...item.style, 
+						'animation-duration': '8s'
+					}
+				}))
+			},
+			animationend(moveItem, i) {
+				// 移除动画结束的弹幕(性能优化)
+				if(this.openCommentStatus==2) {
+					this.$refs.danmuBox&&this.$refs.danmuBox.animationend(moveItem, i)
+				}
+			},
+			navback() {
+				const pages = getCurrentPages(); // 获取当前页面栈
+				if (pages.length > 1) {
+				   uni.navigateBack(); // 有上一页才返回
+				} else { 
+				  // 如果是首页,跳转到某个默认页面(如首页)
+				  uni.reLaunch({ url: '/pages/index/index' }); // 或者用 switchTab 如果是 tabBar 页面
+				}
+			},
+			feedback() {
+				const userId = this.user.userId || ''
+				const courseId = this.urlOption.courseId || ''
+				const videoId = this.urlOption.videoId || ''
+				const companyId = this.urlOption.companyId || ''
+				const companyUserId = this.urlOption.companyUserId || ''
+				uni.navigateTo({
+					url: './feedback?userId='+userId+'&courseId='+courseId+'&videoId='+videoId+'&companyId='+companyId+'&companyUserId='+companyUserId
+				})
+			},
+			// 公开课登录\备用登录
+			async loginFsUserWx(data){
+				if(data){
+					console.log('huoqu1222',data)
+					uni.showLoading({
+						title: '登录中'
+					})
+					uni.login({
+						provider: "weixin",
+						success: async loginRes => {
+							console.log(loginRes)
+							let code = loginRes.code // 获取开发code
+							handleFsUserWx({
+							   code: code,
+							   appId:this.appid,
+							   userId:data.userId
+							})
+							.then( res => {
+								uni.hideLoading();
+								if(res.code==200){
+									console.log("loginFsUserWx:",res)
+									// this.userinfos=uni.getStorageSync('userinfos')
+									let token = uni.getStorageSync('TOKEN_WEXIN');
+									let user = uni.getStorageSync('userInfo')
+									// this.userInfo=uni.getStorageSync('userInfo');
+									// this.isLogin = true
+									uni.setStorageSync(TOKEN_KEYAuto, token);
+									uni.setStorageSync('auto_userInfo', JSON.stringify(user));
+									this.user = user
+									this.isLogin = true
+									this.getIsAddKf() 
+								}else if(res.code==406){
+									uni.showToast({
+										icon:'none',
+										title: '该用户已成为其他销售会员',
+									});
+								}else{
+									uni.showToast({
+										icon:'none',
+										title: res.msg,
+									});
+								}
+							   
+							 })
+						},
+					})
+				}else{
+					uni.setStorageSync('H5course',{
+						companyId: this.urlOption.companyId,
+						companyUserId:this.urlOption.companyUserId,
+						type: 1, //1自动,其他手动
+					})
+					await this.$store.dispatch('getWebviewUrl');
+					uni.navigateTo({
+						url:'/pages_course/webview?H5course='+uni.getStorageSync('H5course')
+					})
+				}
+			},
+			showBtnType(value) {
+				this.showBtn = value
+				this.getHeight()
+			},
+			// getHeight() {
+			// 	setTimeout(()=>{
+			// 		const query = uni.createSelectorQuery().in(this);
+			// 		query
+			// 			.select("#title-contentnav")
+			// 			.boundingClientRect((data) => {
+			// 				if(data) {
+			// 					const footerH = this.showBtn==0? 75: 0
+			// 					this.height =
+			// 						`calc(100vh - ${data.height}px - 420rpx - ${this.statusBarHeight}px - ${footerH}px - 88rpx)`
+			// 				}
+			// 			})
+			// 			.exec();
+			// 	},200)
+			// },
+		}
+	}
+</script>
+
+<style scoped>
+.full-width-popup {
+  width: 100%;
+}
+</style>
+<style lang="scss" scoped>
+	@mixin u-flex($flexD, $alignI, $justifyC) {
+		display: flex;
+		flex-direction: $flexD;
+		align-items: $alignI;
+		justify-content: $justifyC;
+	}
+	.notice-box{
+		padding: 12rpx 18rpx;
+		background: #FFF8F8;
+		display: flex;
+		align-items: center;
+		image{
+			width:40rpx;
+			height:40rpx;
+			margin-right: 10rpx;
+			flex-shrink: 0;
+		}
+		.notice-marquee-wrap{
+			flex: 1;
+			min-width: 0;
+			overflow: hidden;
+			display: flex;
+			align-items: center;
+		}
+		.notice-marquee-track{
+			display: inline-flex;
+			white-space: nowrap;
+			animation: notice-marquee-scroll 20s linear infinite;
+		}
+		.notice-text{
+			flex-shrink: 0;
+			padding-right: 60rpx;
+			font-family: PingFangSC, PingFang SC;
+			font-weight: 600;
+			font-size: 32rpx;
+			line-height: 44rpx;
+			color: #FF0C4D;
+			display: flex;
+		}
+	}
+	@keyframes notice-marquee-scroll{
+		0%{ transform: translateX(0); }
+		100%{ transform: translateX(-50%); }
+	}
+	.vip-order-cover-wrap {
+		position: fixed;
+		left: 10px;
+		bottom:40px;
+		height: 26px;
+		z-index: 999;
+		display: inline-block;
+		overflow: visible;
+		pointer-events: none;
+		width: 200px;
+	}
+	.vip-order-cover-wrap--triple {
+		height: 110px;
+	}
+	.vip-order-cover-triple-panel {
+		display: flex;
+		align-items: flex-start;
+		flex-direction: column;
+		position: absolute;
+		left: 0;
+		right: auto;
+		top: 0;
+	}
+	.vip-order-cover-triple-current {
+		z-index: 1;
+	}
+	.vip-order-cover-triple-incoming {
+		z-index: 2;
+	}
+	.vip-order-cover-item {
+		position: absolute;
+		left: 0;
+		right: auto;
+		top: 0;
+		display: inline-flex;
+		align-items: center;
+		background: rgba(0,0,0,0.35);
+		border-radius: 26rpx;
+		text-align: center;
+		font-family: PingFangSC, PingFang SC;
+		font-size: 16px;
+		height: 26px;
+		line-height: 26px;
+		color: #fff;
+		font-weight: 400;
+		box-sizing: border-box;
+	}
+	.vip-order-cover-triple-item {
+		position: relative;
+		top: auto;
+		margin-bottom: 8px;
+	}
+	.vip-order-cover-triple-item:last-child {
+		margin-bottom: 0;
+	}
+	.vip-order-triple-enter {
+		animation: vip-order-triple-enter-up 0.46s ease-out forwards;
+	}
+	.vip-order-triple-leave {
+		animation: vip-order-triple-leave-up 0.46s ease-in forwards;
+	}
+	@keyframes vip-order-triple-enter-up {
+		0% {
+			opacity: 0;
+			transform: translateY(38px);
+		}
+		100% {
+			opacity: 1;
+			transform: translateY(0);
+		}
+	}
+	@keyframes vip-order-triple-leave-up {
+		0% {
+			opacity: 1;
+			transform: translateY(0);
+		}
+		78% {
+			opacity: 1;
+			transform: translateY(-34px);
+		}
+		100% {
+			opacity: 0;
+			transform: translateY(-38px);
+		}
+	}
+	.vip-order-cover-content {
+		display: flex;
+		align-items: center;
+		flex-wrap: nowrap;
+		white-space: nowrap;
+		overflow: visible;
+		justify-content: flex-start;
+		height: 26px;
+		line-height: 26px;
+		padding:0 8px;
+	}
+	.vip-order-seg {
+		display: inline-block;
+	}
+	.vip-order-seg-user {
+		color: #fff;
+	}
+	.vip-order-seg-time {
+		margin-left: 6px;
+	}
+	.vip-order-seg-suffix {
+		color: #fff;
+	}
+	.vip-order-cover-self {
+		background: rgba(230,0,26,0.5);
+		color: #fff;
+	}
+	.vip-order-cover-self .vip-order-seg-user {
+		color: #fff;
+	}
+	.vip-order-cover-self .vip-order-seg-time {
+		color: #fff;
+		margin-left: 6px;
+	}
+	.vip-order-cover-self .vip-order-seg-suffix {
+		color: #fff;
+	}
+	.vip-order-enter {
+		animation: vip-order-enter-up 0.46s ease-out forwards;
+	}
+	.vip-order-leave {
+		animation: vip-order-leave-up 0.46s ease-in forwards;
+	}
+	@keyframes vip-order-enter-up {
+		0% {
+			opacity: 0;
+			transform: translateY(24px);
+		}
+		100% {
+			opacity: 1;
+			transform: translateY(0);
+		}
+	}
+	@keyframes vip-order-leave-up {
+		0% {
+			opacity: 1;
+			transform: translateY(0);
+		}
+		100% {
+			opacity: 0;
+			transform: translateY(-24px);
+		}
+	}
+	.footer-tips {
+		position: fixed;
+		width: 100%;
+		bottom: 144rpx;
+		text-align: center;
+		font-family: PingFang SC, PingFang SC;
+		font-weight: 500;
+		font-size: 12px;
+		color: #bbb;
+		transform: scale(0.8);
+	}
+	
+	.btns {
+		//position: relative;
+		width: 100%;
+		height: 96rpx;
+		display: flex;
+		    align-items: center;
+		    justify-content: space-between;
+			.rating-msg-input-shell {
+				flex: 1;
+				min-width: 0;
+				display: flex;
+				align-items: center;
+				background: #f5f5f5;
+				border-radius: 48rpx;
+				padding: 24rpx 30rpx;
+				box-sizing: border-box;
+			}
+			.rating-msg-media-pill {
+				position: relative;
+				flex-shrink: 0;
+				width: 64rpx;
+				height: 64rpx;
+				margin-right: 16rpx;
+				border-radius: 12rpx;
+				overflow: hidden;
+			}
+			.rating-msg-media-thumb {
+				width: 100%;
+				height: 100%;
+				display: block;
+			}
+			.rating-msg-media-badge {
+				position: absolute;
+				left: 0;
+				right: 0;
+				bottom: 0;
+				font-size: 18rpx;
+				color: #fff;
+				text-align: center;
+				line-height: 1.4;
+				background: rgba(0, 0, 0, 0.45);
+			}
+			.rating-msg-media-x {
+				position: absolute;
+				top: -4rpx;
+				right: -4rpx;
+				width: 32rpx;
+				height: 32rpx;
+				line-height: 32rpx;
+				text-align: center;
+				font-size: 28rpx;
+				color: #fff;
+				background: rgba(0, 0, 0, 0.5);
+				border-radius: 50%;
+			}
+			.rating-msg-input {
+				flex: 1;
+				min-width: 0;
+				font-size: 32rpx;
+				color: rgba(0, 0, 0, 0.85);
+				height: 48rpx;
+				line-height: 48rpx;
+			}
+			.rating-msg-input-trigger {
+				overflow: hidden;
+			}
+			.rating-msg-input-trigger-text {
+				display: block;
+				font-size: 32rpx;
+				overflow: hidden;
+				text-overflow: ellipsis;
+				white-space: nowrap;
+				color: rgba(0, 0, 0, 0.85);
+				&.is-ph {
+					color: rgba(0, 0, 0, 0.28);
+				}
+			}
+			.rating-msg-input-icon {
+				flex-shrink: 0;
+				padding-left:24rpx;
+				display:flex;
+				image{
+					width:40rpx;
+					height:40rpx
+				}
+			}
+		.author-btn {
+			// z-index: 100;
+			// position: absolute;
+			// width: 100%;
+			flex:1;
+			height: 96rpx;
+			background: linear-gradient( 135deg, #FF5267 0%, #FF233C 100%);
+			border-radius: 50rpx;
+			font-family: PingFangSC, PingFang SC;
+			font-weight: 600;
+			font-style: normal;
+			font-size: 40rpx;
+			color: #FFFFFF;
+			text-align: center;
+			line-height: 96rpx;
+			display: flex;
+			    align-items: center;
+			    justify-content: center;
+			image{
+				margin-left: 4rpx;
+				width: 40rpx;
+				height: 40rpx;
+			}
+		}
+		.author-cart{
+			padding-left: 40rpx;
+			display: flex;
+			    align-items: center;
+				.more-box{
+					display: flex;
+					align-items: center;
+					flex-direction: column;
+					.tips{
+						font-family: PingFangSC, PingFang SC;
+						font-weight: 600;
+						font-size: 32rpx;
+						color: #222222;
+						line-height: 44rpx;
+						text-align: center;
+						margin-top: 12rpx;
+					}
+					image{
+						width: 80rpx;
+						height: 80rpx;
+					}
+					&:last-child{
+						margin-left: 40rpx;
+					}
+				}
+			.xianshi{
+				position: absolute;
+				z-index: 10;
+				right:20rpx;
+				bottom: 180rpx;
+				width: 214rpx;
+				height:90rpx;
+			}
+		}
+	}
+	.textOne {
+		overflow: hidden;
+		white-space: nowrap;
+		text-overflow: ellipsis;
+	}
+
+	.textTwo {
+		overflow: hidden;
+		text-overflow: ellipsis;
+		display: -webkit-box;
+		-webkit-line-clamp: 2;
+		-webkit-box-orient: vertical;
+	}
+	.header-nav {
+		height: 88rpx;
+		@include u-flex(row, center, flex-start);
+		overflow: hidden;
+		background-color: #fff;
+		box-sizing: border-box;
+		.header-title {
+			text-align: center;
+			overflow: hidden;
+			white-space: nowrap;
+			text-overflow: ellipsis;
+			padding: 0 10rpx 0 100rpx;
+			font-family: PingFang SC,PingFang SC;
+			font-weight: 500;
+			font-size: 15px;
+			color: #000;
+			box-sizing: border-box;
+		}
+	}
+	.reward-list {
+		width: 100%;
+		margin-top: 20rpx;
+		margin-bottom: -40rpx;
+
+		&-group {
+			font-family: PingFang SC, PingFang SC;
+			font-weight: 400;
+			font-size: 14px;
+			color: #222222;
+			@include u-flex(row, center, center);
+		}
+
+		&-option {
+			@include u-flex(row, center, flex-start);
+
+			&:first-child {
+				margin-right: 40rpx;
+			}
+		}
+	}
+
+	.err {
+		color: #f56c6c !important;
+	}
+
+	.kfqrcode-box {
+		background-color: #fff;
+		border-radius: 16rpx;
+		max-width: 560rpx;
+		padding: 60rpx 40rpx;
+		margin-top: -100rpx;
+		box-sizing: border-box;
+		@include u-flex(column, center, flex-start);
+		font-family: PingFang SC, PingFang SC;
+		font-weight: 400;
+		font-size: 34rpx;
+		color: #222;
+		position: relative;
+		text-align: center;
+
+		.kfqrcode {
+			height: 460rpx;
+			width: 460rpx;
+		}
+	}
+
+	.kfqrcode-close {
+		width: 64rpx;
+		height: 64rpx;
+		position: absolute;
+		bottom: -100rpx;
+		left: 50%;
+		transform: translateX(-50%);
+	}
+
+	.tipsPopup-mask {
+		position: relative;
+		width: 560rpx;
+		background-color: transparent;
+
+		.red_envelope_top {
+			width: 480rpx;
+			height: 360rpx;
+			margin: 0 auto;
+			display: inherit;
+		}
+	}
+
+	.tipsPopup-btn-box {
+		width: 456rpx;
+		height: 104rpx;
+		padding: 4rpx;
+		box-sizing: border-box;
+		background: linear-gradient(180deg, rgba(252, 209, 94, 1), rgba(254, 253, 251, 1));
+		border-radius: 52rpx;
+	}
+
+	.tipsPopup-btn {
+		width: 100%;
+		height: 100%;
+		background: linear-gradient(180deg, #FF9F22 0%, #FA1E05 100%);
+		border-radius: 52rpx 52rpx 52rpx 52rpx;
+		font-family: PingFang SC, PingFang SC;
+		font-weight: 500;
+		font-size: 36rpx;
+		color: #FFFFFF;
+		line-height: 96rpx;
+		text-align: center;
+	}
+
+	.tipsPopup {
+		width: 560rpx;
+		padding: 12rpx;
+		margin-top: -72rpx;
+		box-sizing: border-box;
+		background: linear-gradient(180deg, #FFFBEF 0%, #FFFFF5 43%, #F5EAC2 100%);
+		border-radius: 32rpx 32rpx 32rpx 32rpx;
+		position: relative;
+
+		&-close {
+			width: 64rpx;
+			height: 64rpx;
+			position: absolute;
+			right: 0;
+			top: -188rpx;
+		}
+
+		&-line {
+			padding: 3rpx;
+			box-sizing: border-box;
+			background: linear-gradient(180deg, rgba(247, 245, 220, 1), rgba(250, 220, 157, 1));
+			border-radius: 24rpx;
+		}
+
+		&-box {
+			padding: 0 40rpx 40rpx 40rpx;
+			box-sizing: border-box;
+			background: linear-gradient(180deg, #FFFBEF 0%, #FFFFF5 43%, #F5EAC2 100%);
+			border-radius: 24rpx;
+			@include u-flex(column, center, flex-start);
+		}
+
+		&-head {
+			@include u-flex(row, center, center);
+
+			&-title {
+				width: 364rpx;
+				height: auto;
+				margin-top: -22rpx;
+			}
+		}
+
+		&-content {
+			margin: 48rpx 0;
+			font-family: PingFang SC, PingFang SC;
+			font-weight: 500;
+			font-size: 32rpx;
+			color: #222222;
+			text-align: center;
+
+			&-title {
+				margin-bottom: 26rpx;
+				font-weight: 600;
+				font-size: 40rpx;
+				color: #FF5C03;
+			}
+		}
+	}
+
+	.video-controls-box {
+		width: 100%;
+		height: 420rpx;
+		overflow: hidden;
+		position: absolute;
+		bottom: 0;
+		left: 0;
+		z-index: 2;
+		background: rgba(0, 0, 0, 0.2);
+
+		.video-play {
+			height: 72rpx;
+			width: 72rpx;
+			position: absolute;
+			top: 50%;
+			left: 50%;
+			transform: translate(-50%, -50%);
+		}
+	}
+
+	.video-controls {
+		width: 100%;
+		height: 80rpx;
+		padding: 0 28rpx;
+		box-sizing: border-box;
+		position: absolute;
+		bottom: 0;
+		left: 0;
+		display: flex;
+		align-items: center;
+		justify-content: space-between;
+		background: linear-gradient(to top, #222 0%, transparent 80%);
+
+		.video-icon {
+			height: 44rpx;
+			width: 44rpx;
+		}
+	}
+    .rating-box{
+    	position: relative;
+    	padding:24rpx 0rpx 24rpx;
+    	z-index:0;
+    	height: calc(100vh - 488rpx);
+    	.bg {
+    		width: 100%;
+    		position: absolute;
+    		top: 0;
+    		left: 0;
+    		z-index: -1;
+    	}
+    	.tab-Box {
+    		display: flex;
+    		align-items: flex-end;
+    		justify-content: space-around;
+    		padding: 0 8rpx;
+    		margin-bottom: -2rpx;
+    		position: relative;
+    		z-index: 3;
+    	}
+    	.tab-Box--single {
+    		align-items: center;
+    		justify-content: flex-start;
+    		padding: 0 24rpx 0 16rpx;
+    		margin-bottom: 30rpx;
+    	}
+    	.tab-item--single {
+    		flex: 0 1 auto;
+    		justify-content: flex-start;
+    		padding: 0;
+    	}
+    	.tab-item__surface--single {
+    		flex-direction: row !important;
+    		align-items: center;
+    		justify-content: flex-start;
+    		width: auto;
+    		max-width: 100%;
+    		border-radius: 0;
+    		image {
+    			margin-top: 0!important;
+    			margin-right: 16rpx;
+    			flex-shrink: 0;
+    		}
+    	}
+    	.tab-item__text--single {
+    		padding-top: 0!important;
+    		padding-bottom: 0!important;
+    		text-align: left;
+    		font-weight: 600 !important;
+    		font-size: 40rpx !important;
+    		line-height: 56rpx !important;
+    	}
+    	.tab-item {
+    		display: flex;
+    		justify-content: center;
+    		min-width: 0;
+    		padding: 0 6rpx;
+    	}
+    	.tab-item__surface {
+    		width: 100%;
+    		display: flex;
+    		flex-direction: column;
+    		align-items: center;
+    		justify-content: flex-end;
+    		box-sizing: border-box;
+    		border-radius: 28rpx 28rpx 0 0;
+    		transition: background-color 0.28s ease, box-shadow 0.28s ease, transform 0.22s ease;
+    		image{
+    			margin-top: 12rpx;
+    			width: 40rpx;
+    			height: 40rpx;
+    		}
+    	}
+    	.tab-item--active .tab-item__surface {
+    		background:url('https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/active-bg.png') no-repeat center;
+    		background-size: 100% 100%;
+    		padding: 0 70rpx;
+    		transform: translateY(-2rpx);
+    	}
+    	.tab-item__text {
+    		padding-top: 10rpx;
+    		padding-bottom: 12rpx;
+    		font-family: PingFangSC, PingFang SC;
+    		font-weight: 400;
+    		font-size: 36rpx;
+    		line-height: 50rpx;
+    		color: #ff233c;
+    		text-align: center;
+    	}
+    	.tab-item--active .tab-item__text{
+    		font-weight: 600;
+    		font-size: 40rpx;
+    	}
+    	.rating-ques-block + .rating-ques-block {
+    		margin-top: 40rpx;
+    	}
+    	.rating-body--plain image {
+    		width: 100%;
+    	}
+    	.rating-intro-cover-img {
+    		width: 100%;
+    		height: auto;
+    		display: block;
+    	}
+    	.rating-msg-empty {
+    		padding: 80rpx 24rpx;
+    		text-align: center;
+    		font-size: 28rpx;
+    		color: rgba(0, 0, 0, 0.35);
+    	}
+    	.rating-body.rating-body--featured {
+    		display: flex;
+    		flex-direction: column;
+    		overflow: hidden;
+    		padding: 30rpx 24rpx 20rpx;
+    	}
+    	.rating-msg-scroll {
+    		height:100%;
+    		width: 100%;
+    		box-sizing: border-box;
+    	}
+    	.rating-msg-scroll-anchor {
+    		width: 100%;
+    		height: 1px;
+    	}
+    	.rating-msg-load-more {
+    		padding: 24rpx 0 32rpx;
+    		text-align: center;
+    		font-size: 26rpx;
+    		color: rgba(0, 0, 0, 0.4);
+    	}
+    	.rating-msg-load-more--done {
+    		color: rgba(0, 0, 0, 0.28);
+    	}
+    	.rating-msg-item {
+    		display: flex;
+    		flex-direction: row;
+    		align-items: flex-start;
+    		gap: 20rpx;
+    		padding-bottom: 40rpx;
+    		&:not(:first-child) {
+    			padding-top: 8rpx;
+    		}
+    	}
+    	.rating-msg-avatar-wrap {
+    		flex-shrink: 0;
+    		width: 64rpx;
+    	}
+    	.rating-msg-main {
+    		flex: 1;
+    		min-width: 0;
+    		display: flex;
+    		flex-direction: column;
+    		align-items: stretch;
+    	}
+    	.rating-msg-avatar {
+    		width: 64rpx;
+    		height: 64rpx;
+    		border-radius: 50%;
+    		flex-shrink: 0;
+    		background: #ffe4ec;
+    		display: block;
+    	}
+    	.rating-msg-name {
+    		font-size: 32rpx;
+    		color: rgba(0,0,0,0.65);
+    		font-family: PingFangSC, PingFang SC;
+    		font-weight: 400;
+    		line-height: 44rpx;
+    	}
+    	.rating-msg-text {
+    		margin-top: 12rpx;
+    		font-size: 28rpx;
+    		line-height: 44rpx;
+    		color: rgba(0, 0, 0, 0.85);
+    		word-break: break-word;
+    	}
+    	.rating-msg-media {
+    		margin-top: 12rpx;
+    		overflow: hidden;
+    	}
+    	.rating-msg-media--video {
+    		overflow: visible;
+    	}
+    	.rating-msg-video-wrap {
+    		position: relative;
+    		max-width: 320rpx;
+    	}
+    	.rating-msg-video {
+    		width: 100%;
+    		display: block;
+    		max-height: 240rpx;
+    	}
+    	.rating-msg-video-play-cover {
+    		position: absolute;
+    		left: 0;
+    		top: 0;
+    		right: 0;
+    		bottom: 0;
+    		z-index: 2;
+    		display: flex;
+    		align-items: center;
+    		justify-content: center;
+    		background: rgba(0, 0, 0, 0.18);
+    	}
+    	.rating-msg-video-play-icon {
+    		width: 88rpx;
+    		height: 88rpx;
+    		flex-shrink: 0;
+    	}
+    	.rating-msg-media--imgs {
+    		display: flex;
+    		flex-wrap: wrap;
+    		justify-content: flex-start;
+    		gap: 12rpx;
+    	}
+    	.rating-msg-img {
+    		flex-shrink: 0;
+    		max-width: 320rpx;
+    		height: auto;
+    	}
+    	.rating-body{
+    		position: relative;
+    		z-index: 1;
+    		padding:30rpx;
+    		box-sizing: border-box;
+    		background: #FFFFFF;
+    		border-radius: 30rpx 30rpx;
+    		height: calc(100% - 300rpx);
+    		overflow-y: auto;
+    		-webkit-overflow-scrolling: touch;
+    		margin-top: 0;
+    		.title{
+    			font-family: PingFangSC, PingFang SC;
+    			font-weight: 600;
+    			font-size: 40rpx;
+    			color: rgba(0,0,0,0.85);
+    			line-height: 56rpx;
+    		}
+    	}
+    	.sat-box{
+    		display: grid;
+    		grid-template-columns: repeat(2, 1fr);
+    		gap: 28rpx 24rpx;
+    		margin-top: 32rpx;
+    	}
+    	.sat{
+    		display: flex;
+    		flex-direction: column;
+    		align-items: center;
+    		justify-content: center;
+    		text-align: center;
+    		background: #F5F7FA;
+    		padding: 20rpx;
+    		border-radius: 20rpx;
+    		transition: background 0.3s ease, box-shadow 0.3s ease;
+    		.sat-img-wrap{
+    			width: 100rpx;
+    			height: 100rpx;
+    			display: flex;
+    			align-items: center;
+    			justify-content: center;
+    			will-change: transform;
+    			image{
+    				width: 100rpx;
+    				height: 100rpx;
+    				transition: transform 0.35s cubic-bezier(0.34, 1.3, 0.64, 1);
+    			}
+    		}
+    		.sat-img-bounce{
+    			animation: sat-rate-pop 0.48s cubic-bezier(0.34, 1.45, 0.64, 1);
+    		}
+    		text{
+    			margin-top: 10rpx;
+    			font-family: PingFangSC, PingFang SC;
+    		    font-weight: 400;
+    		    font-size: 36rpx;
+    			line-height: 50rpx;
+    			transition: color 0.32s ease, font-weight 0.28s ease, transform 0.28s ease;
+    			color: rgba(0,0,0,0.42);
+    		}
+    		.active{
+    			font-weight: 600;
+    			color: #FF233C;
+    		}
+    	}
+    	.sat.sat--active{
+    		background: #FFEEF0;
+    		//box-shadow: 0 4rpx 16rpx rgba(255, 92, 3, 0.12);
+    		.sat-img-wrap image{
+    			transform: scale(1.06);
+    		}
+    	}
+    }
+	.fc-media-actions-sheet {
+		display: flex;
+		flex-direction: column;
+		width: 100%;
+		box-sizing: border-box;
+		padding-bottom:68rpx;
+	}
+	.fc-media-actions-sheet-item {
+		padding: 30rpx 32rpx;
+		font-size: 32rpx;
+		color: #1e1e1e;
+		text-align: center;
+		border-bottom: 1rpx solid #f0f0f0;
+	}
+	.fc-media-actions-sheet-gap {
+		height: 16rpx;
+		background: #f3f5f9;
+		border-bottom: none;
+	}
+	.fc-media-actions-sheet-cancel {
+		border-bottom: none;
+		color: #666;
+	}
+	@keyframes sat-rate-pop{
+		0%{ transform: scale(1); }
+		28%{ transform: scale(1.2); }
+		52%{ transform: scale(0.94); }
+		76%{ transform: scale(1.06); }
+		100%{ transform: scale(1); }
+	}
+	.errQuesbox {
+		width: 100%;
+		max-height: 260rpx;
+		overflow-y: auto;
+		margin-top: 24rpx;
+		font-family: PingFang SC, PingFang SC;
+		font-weight: 500;
+		font-size: 30rpx;
+		color: #222222;
+
+		&-item {
+			width: 100%;
+			height: 128rpx;
+			line-height: 128rpx;
+			margin-bottom: 24rpx;
+			padding: 0 30rpx;
+			box-sizing: border-box;
+			overflow: hidden;
+			background: #fff;
+			border-radius: 16rpx 16rpx 16rpx 16rpx;
+			position: relative;
+
+			&::after {
+				content: "题目";
+				min-width: 64rpx;
+				height: 36rpx;
+				padding: 0 12rpx;
+				line-height: 36rpx;
+				background: #FF5C03;
+				box-sizing: border-box;
+				border-radius: 0rpx 0rpx 16rpx 0rpx;
+				text-align: center;
+				font-family: PingFang SC, PingFang SC;
+				font-weight: 500;
+				font-size: 20rpx;
+				color: #fff;
+				position: absolute;
+				left: 0;
+				top: 0;
+			}
+		}
+	}
+
+	.bg {
+		background: #fff !important;
+	}
+
+	.answerPopup {
+		&-box {
+			width: 560rpx;
+			background: linear-gradient(180deg, #FFFAF6 0%, #FEECD8 100%);
+			border-radius: 32rpx 32rpx 32rpx 32rpx;
+			background-color: #fff;
+			font-weight: 400;
+			padding: 32rpx;
+			box-sizing: border-box;
+			position: relative;
+			@include u-flex(column, center, flex-start);
+			font-family: PingFang SC, PingFang SC;
+			font-weight: 400;
+
+			.tipimg {
+				width: 206rpx;
+				height: 206rpx;
+				margin-bottom: 16rpx;
+			}
+		}
+
+		&-title {
+			font-weight: 600;
+			font-size: 36rpx;
+			color: #222222;
+		}
+
+		&-desc {
+			margin-top: 10rpx;
+			font-size: 28rpx;
+			color: #757575;
+		}
+
+		&-btn {
+			width: 464rpx;
+			height: 84rpx;
+			margin-top: 54rpx;
+			margin-bottom: 16rpx;
+			background: #FF5C03;
+			border-radius: 42rpx;
+			font-weight: 500;
+			font-size: 32rpx;
+			color: #FFFFFF;
+			text-align: center;
+			line-height: 84rpx;
+		}
+	}
+
+	.popupbox {
+		width: 100%;
+		background-color: #fff;
+		border-radius: 16rpx 16rpx 0 0;
+		padding: 24rpx 32rpx;
+		position: relative;
+
+		&-head {
+			height: 60rpx;
+			margin-bottom: 30rpx;
+			text-align: center;
+			overflow-y: auto;
+			color: #414858;
+			font-size: 32rpx;
+			font-weight: bold;
+			position: relative;
+
+			.close-icon {
+				position: absolute;
+				right: 0;
+				top: 0;
+				height: 40rpx;
+				width: 40rpx;
+			}
+		}
+
+		&-content {
+			height: 20vh;
+			overflow-y: auto;
+			display: flex;
+			align-items: flex-start;
+			flex-wrap: wrap;
+			gap: 32rpx;
+
+			.line-item {
+				display: inline-block;
+				min-width: 200rpx;
+				min-height: 60rpx;
+				padding: 0 20rpx;
+				box-sizing: border-box;
+				border-radius: 50rpx;
+				overflow: hidden;
+				background-color: #f7f7f7;
+				text-align: center;
+				color: #414858;
+				font-size: 28rpx;
+				line-height: 60rpx;
+			}
+
+			.line-active {
+				color: #f56c6c !important;
+				background-color: #fef0f0 !important;
+			}
+		}
+	}
+
+	.content {
+		//padding-bottom: calc(var(--window-bottom));
+		.video-box {
+			width: 100%;
+			height: 420rpx;
+			overflow: hidden;
+			position: relative;
+
+			#myVideo {
+				width: 100%;
+				height: 100%;
+			}
+		}
+
+		.video-poster {
+			width: 100%;
+			height: 420rpx;
+		}
+
+		.miantitlebox {
+			padding: 30rpx 0;
+			border-bottom: 2rpx solid #F5F7FA;
+			font-family: PingFang SC, PingFang SC;
+			font-weight: 500;
+			font-size: 36rpx;
+			color: #222222;
+		}
+
+		.subtitlebox {
+			padding: 30rpx 0;
+			border-bottom: 2rpx solid #F5F7FA;
+			font-family: PingFang SC, PingFang SC;
+			font-weight: 500;
+			font-size: 36rpx;
+			color: #222222;
+		}
+
+		.title-content {
+			padding: 0 32rpx;
+			background-color: #fff;
+			font-size: 28rpx;
+			line-height: 1.6;
+
+			.title {
+				font-size: 36rpx;
+				font-weight: 500;
+				color: #414858;
+			}
+
+			.time-or-subtitle {
+				margin-top: 12rpx;
+				color: #666666;
+			}
+		}
+
+		.video-line {
+			min-width: 140rpx;
+			max-width: 200rpx;
+			height: 60rpx;
+			padding: 0 20rpx;
+			box-sizing: border-box;
+			border-radius: 50rpx 0 0 50rpx;
+			overflow: hidden;
+			background-color: #fff;
+			text-align: center;
+			color: #888;
+			font-size: 28rpx;
+			line-height: 60rpx;
+			display: inline-flex;
+			align-items: center;
+			justify-content: center;
+			position: fixed;
+			right: 0;
+			z-index: 9;
+			bottom: calc(var(--window-bottom) + 280rpx);
+			box-shadow: 0 4rpx 10rpx rgba(0, 0, 0, .12);
+		
+			image {
+				flex-shrink: 0;
+				height: 34rpx;
+				width: 34rpx;
+				margin-right: 6rpx;
+			}
+		}
+		.danmu-line {
+			bottom: calc(var(--window-bottom) + 370rpx);
+			word-break: keep-all;
+			.set_image {
+				height: 40rpx;
+				width: 40rpx;
+			}
+		}
+
+		.fc-media-preview-mask {
+			position: fixed;
+			left: 0;
+			right: 0;
+			top: 0;
+			bottom: 0;
+			z-index: 10050;
+			background: rgba(0, 0, 0, 0.72);
+			display: flex;
+			align-items: center;
+			justify-content: center;
+			padding: 32rpx 24rpx calc(32rpx + env(safe-area-inset-bottom));
+			box-sizing: border-box;
+		}
+		.fc-media-preview-card {
+			width: 100%;
+			max-width: 630rpx;
+			overflow: hidden;
+			display: flex;
+			    flex-direction: column;
+			    align-items: center;
+		}
+		.fc-media-preview-img-box {
+			width: 100%;
+			height: 62vh;
+			max-height: 820rpx;
+		}
+		.fc-media-preview-slide {
+			width: 100%;
+			height: 100%;
+			display: flex;
+			align-items: center;
+			justify-content: center;
+			padding: 16rpx;
+			box-sizing: border-box;
+		}
+		.fc-media-preview-main-img {
+			width: 100%;
+			height: 100%;
+			max-height: 100%;
+		}
+		.fc-media-preview-video-box {
+			width: 100%;
+			height: 62vh;
+			max-height: 820rpx;
+			background: #000;
+			display: flex;
+			align-items: center;
+			justify-content: center;
+		}
+		.fc-media-preview-video {
+			width: 100%;
+			height: 100%;
+		}
+		.fc-media-preview-footer {
+			display: flex;
+			flex-direction: row;
+			align-items: center;
+			padding:30rpx;
+		}
+		.fc-media-preview-thumbs {
+			flex: 1;
+			min-width: 0;
+			height: 112rpx;
+			white-space: nowrap;
+		}
+		.fc-media-preview-thumbs-inner {
+			display: inline-flex;
+			flex-direction: row;
+			align-items: center;
+			gap: 16rpx;
+			padding-right: 8rpx;
+		}
+		.fc-media-preview-thumb {
+			width: 96rpx;
+			height: 96rpx;
+			flex-shrink: 0;
+			border-radius: 12rpx;
+			border: 3rpx solid transparent;
+			box-sizing: border-box;
+			background: #333;
+		}
+		.fc-media-preview-thumb--active {
+			border-color: #ff5c03;
+		}
+		.fc-media-preview-thumbs-spacer {
+			flex: 1;
+			min-height: 1rpx;
+		}
+		.fc-media-preview-close {
+			flex-shrink: 0;
+			display: flex;
+			align-items: center;
+			justify-content: center;
+		}
+
+		.featured-comment-composer-mask {
+			position: fixed;
+			left: 0;
+			right: 0;
+			top: 0;
+			bottom: 0;
+			background: rgba(0, 0, 0, 0.35);
+			z-index: 9998;
+		}
+
+		.featured-comment-composer-wrap {
+			position: fixed;
+			left: 0;
+			right: 0;
+			z-index: 9999;
+			background: #fff;
+			border-radius: 24rpx 24rpx 0 0;
+			padding: 20rpx 24rpx;
+			padding-bottom: calc(20rpx + env(safe-area-inset-bottom));
+			box-sizing: border-box;
+			box-shadow: 0 -4rpx 24rpx rgba(0, 0, 0, 0.06);
+		}
+
+		.featured-comment-composer-inner {
+			display: flex;
+			align-items: center;
+			gap: 24rpx;
+		}
+
+		.featured-comment-composer-input-row {
+			flex: 1;
+			min-width: 0;
+			display: flex;
+			align-items: flex-start;
+			background: #f5f5f5;
+			border-radius: 24rpx;
+			padding:20rpx;
+			box-sizing: border-box;
+		}
+
+		.fc-composer-input {
+			flex: 1;
+			min-width: 0;
+			font-size: 32rpx;
+			color: rgba(0, 0, 0, 0.85);
+			height:88rpx;
+			line-height: 44rpx;
+		}
+
+		.fc-composer-ph {
+			color: rgba(0, 0, 0, 0.28);
+			font-size: 32rpx;
+		}
+
+		.fc-composer-input-icon {
+			flex-shrink: 0;
+			margin-left: 12rpx;
+			display: flex;
+			align-items: center;
+			justify-content: center;
+
+			image {
+				width: 40rpx;
+				height: 40rpx;
+			}
+		}
+
+		.fc-composer-media-pill {
+			position: relative;
+			flex-shrink: 0;
+			width: 64rpx;
+			height: 64rpx;
+			border-radius: 12rpx;
+			overflow: hidden;
+		}
+
+		.fc-composer-media-thumb {
+			width: 100%;
+			height: 100%;
+			display: block;
+		}
+
+		.fc-composer-media-badge {
+			position: absolute;
+			left: 0;
+			right: 0;
+			bottom: 0;
+			font-size: 18rpx;
+			color: #fff;
+			text-align: center;
+			line-height: 1.4;
+			background: rgba(0, 0, 0, 0.45);
+		}
+
+		.fc-composer-media-x {
+			position: absolute;
+			top: -4rpx;
+			right: -4rpx;
+			width: 32rpx;
+			height: 32rpx;
+			line-height: 32rpx;
+			text-align: center;
+			font-size: 28rpx;
+			color: #fff;
+			background: rgba(0, 0, 0, 0.5);
+			border-radius: 50%;
+		}
+
+		.featured-comment-composer-publish {
+			flex-shrink: 0;
+			padding: 20rpx 40rpx;
+			background: linear-gradient( 135deg, #FF5267 0%, #FF233C 100%);
+			font-family: PingFangSC, PingFang SC;
+			font-weight: 600;
+			font-size: 40rpx;
+			color: #FFFFFF;
+			line-height: 56rpx;
+			text-align: center;
+			border-radius: 48rpx;
+		}
+
+		.footer {
+			//border-top: 1rpx solid #ededef;
+			background: #fff;
+			width: 100%;
+			position: fixed;
+			bottom: 0;
+			padding: 32rpx;
+			padding-bottom:68rpx;
+			box-sizing: border-box;
+			z-index: 0;
+		
+			&-btn {
+				width: 100%;
+				height: 98rpx;
+				background: #FF5C03;
+				border-radius: 49rpx 49rpx 49rpx 49rpx;
+				line-height: 98rpx;
+				text-align: center;
+				font-family: PingFang SC, PingFang SC;
+				font-weight: 600;
+				font-size: 32rpx;
+				color: #FFFFFF;
+				@include u-flex(row, center, center);
+		
+				&-img {
+					flex-shrink: 0;
+					width: 144rpx;
+					height: 144rpx;
+					margin-right: 8rpx;
+					margin-top: -24rpx;
+				}
+			}
+		
+			&-btn-border {
+				position: relative;
+		
+				&::after {
+					content: "";
+					background: linear-gradient(180deg, rgba(255, 255, 255, 0), rgba(255, 255, 255, 1));
+					position: absolute;
+					top: -2rpx;
+					left: 0;
+					height: 103rpx;
+					width: 100%;
+					z-index: -1;
+					border-radius: 49rpx 49rpx 49rpx 49rpx;
+					box-shadow: 0rpx 8rpx 11rpx 0rpx rgba(255, 92, 3, 0.3);
+					overflow: hidden;
+				}
+			}
+		}
+	}
+
+	.agreement {
+		display: inline-flex;
+		margin-top: 16rpx;
+		font-size: 24rpx;
+		color: #525252;
+		align-items: center;
+		justify-content: center;
+	}
+	 
+	.agreement {
+		display: inline-flex;
+		margin-top: 16rpx;
+		font-size: 24rpx;
+		color: #525252;
+		align-items: center;
+		justify-content: center;
+	}
+	.video-danmu-btnbox {
+		width: 50px;
+		height: 50px;
+		border-radius: 50%;
+		overflow: hidden;
+		position: absolute;
+		right: 10px;
+		bottom: calc(50% - 50px);
+		transform: translateY(-50%);
+		padding: 8px;
+		box-sizing: border-box;
+	}
+	.video-danmu-image {
+		width: 100%;
+		height: 100%;
+	}
+	.danmuPopup {
+		background-color: #fff;
+		padding-bottom: calc(var(--window-bottom) + 10px);
+		.u-border {
+			flex: 1;
+			@include u-flex(row,center,flex-start);
+			padding: 0 10rpx;
+			border-radius: 6px;
+			border: 1rpx solid #eee;
+		}
+		&-head {
+			width: 100%;
+			padding: 10px;
+			box-sizing: border-box;
+			overflow: hidden;
+			@include u-flex(row,center,flex-start);
+			.danmu-icon {
+				height: 24px;
+				width: 24px;
+				margin-right: 12px;
+			}
+		}
+		&-input {
+			flex: 1;
+			height: 35px;
+		}
+		&-send {
+			flex-shrink: 0;
+			height: 35px;
+			display: flex;
+			align-items: center;
+			justify-content: center;
+			padding: 5px 15px;
+			box-sizing: border-box;
+			background: #FF5C03 !important;
+			border-radius: 22px;
+			font-family: PingFang SC, PingFang SC;
+			font-weight: 500;
+			font-size: 15px;
+			color: #fff !important;
+			margin-left: 12px;
+			&::after {
+				border: none;
+			}
+		}
+		&-con {
+			background-color: #F5F7FA;
+			padding: 24px 12px 48px 12px;
+			font-family: PingFang SC, PingFang SC;
+			font-weight: 400;
+			font-size: 14px;
+			color: #757575;
+		}
+	}
+	.danmu-icon{
+		height: 24px;
+		width: 24px;
+		margin-right: 12px;
+	}
+	.logo {
+		display: inline-block;
+		width: 30px;
+		height: auto;
+		margin: 20px 0 0 10px;
+		pointer-events: none;
+		object-fit: cover;
+	}
+	.logo-full {
+		display: inline-block;
+		width: 40px;
+		height: auto;
+		margin: 50px 0 0 30px;
+		pointer-events: none;
+		object-fit: cover;
+	}
+	.tabbox {
+		@include u-flex(row, center, center);
+		border-bottom: 2rpx solid #F5F7FA;
+		height: 44px;
+		background-color: #fff;
+		view {
+			flex: 1;
+			padding: 20rpx 0;
+			margin-right: 40rpx;
+			text-align: center;
+		}
+		&-active {
+			position: relative;
+			&::after {
+				position: absolute;
+				bottom: 0;
+				left: 50%;
+				transform: translateX(-50%);
+				content: "";
+				width: 3rem;
+				border-bottom: 4px solid #FF5C03;
+			}
+		}
+	}
+	.chatinput {
+		position: fixed;
+		left: 32rpx;
+		right: 32rpx;
+		z-index: 999;
+		height: 96rpx;
+		background-color: green;
+		background: #FFFFFF;
+		box-shadow: 0rpx 8rpx 21rpx 0rpx rgba(0, 0, 0, 0.1);
+		border-radius: 24rpx 24rpx 24rpx 24rpx;
+		@include u-flex(row, center, center);
+		padding: 0 24rpx;
+		box-sizing: border-box;
+		.uni-input {
+			flex: 1;
+			margin-right: 32rpx;
+			font-size: 30rpx;
+		}
+	
+		.send {
+			font-family: PingFang SC, PingFang SC;
+			font-weight: 400;
+			font-size: 28rpx;
+			color: #FFFFFF !important;
+			flex-shrink: 0;
+			padding: 0 20rpx;
+			height: 72rpx;
+			background: #FF5C03 !important;
+			border-radius: 8rpx 8rpx 8rpx 8rpx;
+			&::after {
+				border: none;
+			}
+		}
+	}
+	.answerTip {
+		position: fixed;
+		right: 0;
+		z-index: 9;
+		bottom: calc(var(--window-bottom) + 380rpx);
+		box-shadow: 0rpx 8rpx 21rpx 0rpx rgba(0, 0, 0, 0.1);
+		border-radius: 24rpx 24rpx 24rpx 24rpx;
+		background-color: #ff5c03;
+		color: #fff;
+		border-radius: 50%;
+		height: 90rpx;
+		width: 90rpx;
+		font-size: 25rpx;
+		text-align: center;
+		padding: 10rpx;
+		@include u-flex(column, center, center);
+	}
+	.danmu-item {
+		position: absolute;
+		top: 0;
+		white-space: nowrap;
+		font-size: 16px;
+		height: 20px;
+		display: inline-flex;
+		box-sizing: border-box;
+		align-items: center;
+	}
+	.danmuMove {
+		// animation: mymove 8s linear forwards;
+		// animation-duration: 8s;
+		animation-timing-function: linear;
+		animation-delay: 0s;
+		animation-iteration-count: 1;
+		animation-direction: normal;
+		animation-fill-mode: forwards;
+		animation-play-state: running;
+		animation-name: mymove;
+		will-change: transform;
+	}
+	
+	@keyframes mymove {
+		from {
+			transform: translateX(100vw);
+		}
+	
+		to {
+			transform: translateX(-100%);
+		}
+	}
+	.arrow-left-warning {
+		position: absolute;
+		left: 24rpx;
+		height: 88rpx;
+		overflow: hidden;
+		color: #888;
+		font-size: 24rpx;
+		@include u-flex(column, center, center);
+		image {
+			flex-shrink: 0;
+			height: 36rpx;
+			width: 36rpx;
+		}
+	}
+	// 完课积分倒计时遮罩
+	.progress-countdown {
+		position: fixed;
+		right: 6px;
+		top: 6px;
+		z-index: 99999999;
+		// width: 112px;
+		height: 50px;
+		background: rgba(0, 0, 0, 0.45);
+		display: flex;
+		align-items: center;
+		justify-content: space-around;
+		padding: 0 8px;
+		flex-direction: column;
+		border-radius: 6px;
+		box-sizing: border-box;
+	}
+	.progress-title {
+		font-size: 16px;
+		color: #FF233C;
+		font-weight: 600;
+	}
+	.progress-bar-bg {
+		width: 86px;
+		height: 6px;
+		background: rgba(255, 255, 255, 0.8);
+		border-radius: 3px;
+		overflow: hidden;
+	}
+	.progress-bar-fill {
+		height: 100%;
+		background: #FF233C;
+		border-radius: 3px;
+		transition: width 1s linear;
+	}
+	.progress-text {
+		white-space: nowrap;
+		color: #fff;
+		font-size: 13px;
+		display: flex;
+		align-items: flex-start;
+		justify-content: center;
+	}
+	.progress-text-label {
+		font-size: 12px;
+		margin-right: 2px;
+	}
+
+	// 购物车/更多弹窗
+	.more-actions-popup {
+		border-radius: 20rpx 0 0 20rpx;
+		padding: 30rpx;
+		display: flex;
+		justify-content: space-between;
+
+		.more-action-item {
+			display: flex;
+			flex-direction: column;
+			align-items: center;
+
+			.action-icon {
+				width: 48rpx;
+				height: 48rpx;
+			}
+
+			.action-label {
+				color: #1e1e1e;
+				text-align: center;
+				margin-top: 10rpx;
+			}
+		}
+	}
+     /* 商品卡片样式 */
+     .goods-cover {
+       /* cover-view 在 video 内使用 absolute 比 fixed 更稳定 */
+       position: absolute;
+       right: 12px;
+     	 width: 150px;
+       z-index: 99999;
+       background: #FFFFFF;
+       border-radius: 10px;
+       overflow: hidden;
+       bottom: 40px;
+       &-inner {
+         display: flex;
+         flex-direction:column;
+       }
+     
+       &-img {
+         width:150px;
+         height:150px;
+         flex-shrink: 0;
+       }
+     
+       &-info {
+         flex: 1;
+         padding: 6px;
+         display: flex;
+         flex-direction: column;
+         justify-content: space-between;
+       }
+     
+       &-title {
+         font-family: PingFangSC, PingFang SC;
+         font-weight: 600;
+         font-size: 16px;
+         color: #000000D9;
+         line-height: 22px;
+         overflow: hidden;
+          width: 150px; /* 必须给宽度 */
+          white-space: nowrap; /* 关键 */
+          text-overflow: ellipsis;
+       }
+       &-bottom {
+         margin-top: 6px;
+         display: flex;
+         flex-direction: row;
+         align-items: center;
+       }
+     
+       &-tag {
+         position: relative;
+         width: 60px;
+         height: 22px;
+       }
+     
+       &-tag-bg {
+         width: 100%;
+         height: 100%;
+       }
+     
+       &-tag-text {
+         position: absolute;
+         left: 0;
+         top: 0;
+         width: 100%;
+         height: 100%;
+         text-align: center;
+         line-height: 22px;
+         font-size: 12px;
+         color: #FFFFFF;
+         font-weight: 500;
+       }
+       
+       &-price{
+         margin-left: 7px;
+         display: flex;
+         align-items:baseline;
+         .unit{
+           font-family: PingFangSC, PingFang SC;
+           font-weight: 600;
+           font-size: 16px;
+           color: #FF233C;
+         }
+         .price{
+           font-family: PingFangSC, PingFang SC;
+           font-weight: 600;
+           font-size: 24px;
+           color: #FF233C;
+         }
+       }
+       .close-box{
+         position: absolute;
+         top:10px;
+         right:10px;
+     	   z-index:9;
+         cover-image{
+           width: 15px;
+           height: 15px;
+         }
+       }
+     }
+	// 商品卡片弹窗
+	.goods-card {
+		position: absolute;
+		right: 24rpx;
+		bottom: 160rpx;
+		z-index: 9999;
+		width: 300rpx;
+		background: #FFFFFF;
+		border-radius: 20rpx 20rpx 0rpx 0rpx;
+		overflow: hidden;
+
+		&-inner {
+			display: flex;
+			flex-direction: column;
+		}
+
+		&-img {
+			width: 300rpx;
+			height: 300rpx;
+			flex-shrink: 0;
+		}
+
+		&-info {
+			flex: 1;
+			padding: 12rpx;
+			display: flex;
+			flex-direction: column;
+			justify-content: space-between;
+		}
+
+		&-title {
+			font-family: PingFangSC, PingFangSC;
+			font-weight: 600;
+			font-size: 32rpx;
+			color: rgba(0, 0, 0, 0.85);
+			line-height: 44rpx;
+			overflow: hidden;
+			text-overflow: ellipsis;
+			display: -webkit-box;
+			-webkit-line-clamp: 2;
+			-webkit-box-orient: vertical;
+		}
+
+		&-bottom {
+			margin-top: 12rpx;
+			display: flex;
+			flex-direction: row;
+			align-items: center;
+		}
+
+		&-tag {
+			position: relative;
+			width: 120rpx;
+			height: 44rpx;
+		}
+
+		&-tag-bg {
+			width: 100%;
+			height: 100%;
+		}
+
+		&-tag-text {
+			position: absolute;
+			left: 0;
+			top: 0;
+			width: 100%;
+			height: 100%;
+			text-align: center;
+			line-height: 44rpx;
+			font-size: 24rpx;
+			color: #FFFFFF;
+			font-weight: 500;
+		}
+
+		&-price {
+			margin-left: 14rpx;
+			display: flex;
+			align-items: baseline;
+
+			.unit {
+				font-family: PingFangSC, PingFangSC;
+				font-weight: 600;
+				font-size: 32rpx;
+				color: #FF233C;
+			}
+
+			.price {
+				font-family: PingFangSC, PingFangSC;
+				font-weight: 600;
+				font-size: 48rpx;
+				color: #FF233C;
+			}
+		}
+		.close-box{
+			position: absolute;
+			top:20rpx;
+			right:20rpx;
+			image{
+				width: 30rpx;
+				height: 30rpx;
+			}
+		}
+	}
+
+</style>

+ 91 - 81
pages_course/video.vue

@@ -268,68 +268,33 @@
 				</template> -->
 			<!-- </view> -->
 		<!-- </scroll-view> -->
-		<!-- 评价(多 Tab:评价得积分 / 栏目介绍 / 精选留言) -->
+		<!-- 评价(多 Tab:精选留言 / 栏目介绍 / 评价得积分) -->
 		<view class="rating-box" :style="{paddingTop:visibleRatingTabCount == 1?'30rpx':'24rpx'}" v-if="isLogin&&isAddKf==1&&!isShu&&hasVisibleRatingTab">
 			<image class="bg" src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/app/vip/bg-back.png" mode="widthFix"></image>
 			<view class="tab-Box" v-if="visibleRatingTabCount > 1">
 				<view
-					v-if="showTabReviewPoints"
+					v-for="tab in ratingTabList"
+					:key="tab.key"
 					class="tab-item"
-					:class="{ 'tab-item--active': tabIndex == 0 }"
-					@click="selecTab(0)"
+					:class="{ 'tab-item--active': tabIndex == tab.index }"
+					@click="selecTab(tab.index)"
 				>
 					<view class="tab-item__surface">
-						<image v-if="tabIndex == 0" src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/zan-sel.png"></image>
-						<image v-else src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/sel.png"></image>
-						<text class="tab-item__text">评价得积分</text>
-					</view>
-				</view>
-				<view
-					v-if="showTabColumnIntro"
-					class="tab-item"
-					:class="{ 'tab-item--active': tabIndex == 1 }"
-					@click="selecTab(1)"
-				>
-					<view class="tab-item__surface">
-						<image v-if="tabIndex == 1" src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/des-sel.png"></image>
-						<image v-else src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/des.png"></image>
-						<text class="tab-item__text">栏目介绍</text>
-					</view>
-				</view>
-				<view
-					v-if="showTabFeaturedComments"
-					class="tab-item"
-					:class="{ 'tab-item--active': tabIndex == 2 }"
-					@click="selecTab(2)"
-				>
-					<view class="tab-item__surface">
-						<image v-if="tabIndex == 2" src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/pl-sel.png"></image>
-						<image v-else src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/pl.png"></image>
-						<text class="tab-item__text">精选留言</text>
+						<image :src="tabIndex == tab.index ? tab.iconActive : tab.icon" mode="aspectFit"></image>
+						<text class="tab-item__text">{{ tab.label }}</text>
 					</view>
 				</view>
 			</view>
+			<!-- 仅一个 Tab:单行左对齐标题,无选中态(顺序:精选留言 / 栏目介绍 / 评价得积分) -->
 			<view class="tab-Box tab-Box--single" v-else-if="visibleRatingTabCount === 1">
-				<view v-if="showTabReviewPoints" class="tab-item tab-item--single">
-					<view class="tab-item__surface tab-item__surface--single">
-						<image src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/zan-sel.png" mode="aspectFit"></image>
-						<text class="tab-item__text tab-item__text--single">评价得积分</text>
-					</view>
-				</view>
-				<view v-if="showTabColumnIntro" class="tab-item tab-item--single">
+				<view v-for="tab in ratingTabList" :key="tab.key" class="tab-item tab-item--single">
 					<view class="tab-item__surface tab-item__surface--single">
-						<image src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/des-sel.png" mode="aspectFit"></image>
-						<text class="tab-item__text tab-item__text--single">栏目介绍</text>
-					</view>
-				</view>
-				<view v-if="showTabFeaturedComments" class="tab-item tab-item--single">
-					<view class="tab-item__surface tab-item__surface--single">
-						<image src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/pl-sel.png" mode="aspectFit"></image>
-						<text class="tab-item__text tab-item__text--single">精选留言</text>
+						<image :src="tab.iconActive" mode="aspectFit"></image>
+						<text class="tab-item__text tab-item__text--single">{{ tab.label }}</text>
 					</view>
 				</view>
 			</view>
-			<view class="rating-body" v-if="tabIndex == 0 && showTabReviewPoints">
+			<view class="rating-body" v-if="tabIndex == 2 && showTabReviewPoints">
 				<view class="rating-ques-block" v-for="(item,index) in quesList" :key="index">
 					<view class="title">{{item.title}}</view>
 					<view class="sat-box">
@@ -349,7 +314,7 @@
 					mode="widthFix"
 				></image>
 			</view>
-			<view class="rating-body rating-body--featured" v-if="tabIndex == 2 && showTabFeaturedComments">
+			<view class="rating-body rating-body--featured" v-if="tabIndex == 0 && showTabFeaturedComments">
 				<scroll-view
 					scroll-y
 					class="rating-msg-scroll"
@@ -588,7 +553,7 @@
 		</u-popup>
 		<!-- footer -->
 		<view class="footer" v-if="videoId">
-			<view class="btns" :style="{'justify-content':isLogin&&isAddKf==1&&remainTime==0&&!showTabColumnIntro?'space-between':'flex-end'}">
+			<view class="btns" :style="{'justify-content':isLogin&&isAddKf==1&&remainTime==0&&hasVisibleRatingTab&&!showTabColumnIntro?'space-between':'flex-end'}">
 				<!-- <button
 					class="author-btn"
 					open-type="getPhoneNumber"
@@ -598,10 +563,10 @@
 					open-type="getUserInfo" :disabled="userdisabled"
 					@getuserinfo="userInfologin"  v-if="authType==0&&!isquestion">{{isLogin&&isAddKf==1 ? '提交答案领取奖励' : '立即学习'}}</button> -->
 				
-				<template v-if="!isquestion && showTabReviewPoints">
-					<button class="author-btn" @click="openList" v-if="isLogin&&isAddKf==1&&isShu">评价得积分<image src="/static/images/jifen.png"></image>
-					</button>
-					<button class="author-btn" @click="submit" v-if="isLogin&&isAddKf==1&&remainTime==0&&!isShu&&tabIndex==0">评价得积分
+				<template>
+					<button class="author-btn" @click="openList" v-if="isLogin&&isAddKf==1&&isShu&&(showTabFeaturedComments || showTabColumnIntro || showTabReviewPoints)">{{ showTabFeaturedComments ? '去留言' : showTabColumnIntro ? '栏目介绍' : '评价得积分' }}
+					<image v-if="showTabReviewPoints&&!showTabFeaturedComments&&!showTabColumnIntro" src="/static/images/jifen.png"></image></button>
+					<button class="author-btn" @click="submit" v-if="isLogin&&isAddKf==1&&remainTime==0&&!isShu&&tabIndex==2">评价得积分
 					<image src="/static/images/jifen.png"></image>
 					</button>
 				</template>
@@ -610,7 +575,8 @@
 					class="author-btn"
 					open-type="getUserInfo" :disabled="userdisabled"
 					@getuserinfo="userInfologin" v-if="authType==0&&!isLogin&&isAddKf!==1">立即学习</button> -->
-					<view v-if="tabIndex==2 && showTabFeaturedComments && !(showTabReviewPoints && isShu)" class="rating-msg-input-shell">
+					<!-- 竖屏 isShu 下 rating 区隐藏;若仍停留在精选留言 tab,勿在 footer 展示留言框,只保留「评价得积分」按钮 -->
+					<view v-if="tabIndex==0 && showTabFeaturedComments&&!isShu" class="rating-msg-input-shell">
 						<view
 							v-if="featuredCommentMedia"
 							class="rating-msg-media-pill"
@@ -641,7 +607,7 @@
 							<image src="https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/upimg.png"></image>
 						</view>
 					</view>
-				<view class="author-cart" v-show="!(tabIndex === 2 && showTabFeaturedComments && isLogin && isAddKf == 1 && !isquestion && !isShu)">
+				<view class="author-cart" v-show="!(tabIndex === 0 && showTabFeaturedComments && isLogin && isAddKf == 1 && !isquestion && !isShu)">
 					<view class="more-box">
 						<image src="/static/images/more24.png" @click="showMore"></image>
 						<view class="tips">更多</view>
@@ -660,7 +626,7 @@
 				<button class="send" @click="handleChatInput">发送</button>
 			</view>
 		</view>
-		<template v-if="tabIndex==2 && showTabFeaturedComments && !(showTabReviewPoints && isShu)">
+		<template v-if="tabIndex==0 && showTabFeaturedComments && !(showTabReviewPoints && isShu)">
 			<view
 				v-if="featuredCommentComposerActive"
 				class="featured-comment-composer-mask"
@@ -703,7 +669,6 @@
 							placeholder-class="fc-composer-ph"
 							:focus="featuredCommentInputFocused"
 							:adjust-position="false"
-							@focus="onFeaturedCommentComposerInputFocus"
 							@blur="onFeaturedCommentComposerInputBlur"
 						/>
 						<view class="fc-composer-input-icon" @click.stop="onFeaturedPickMedia">
@@ -1142,11 +1107,39 @@
 				return !this.featuredCommentHasMore
 			},
 			visibleRatingTabCount() {
-				let n = 0
-				if (this.showTabReviewPoints) n++
-				if (this.showTabColumnIntro) n++
-				if (this.showTabFeaturedComments) n++
-				return n
+				return this.ratingTabList.length
+			},
+			/** 评价区 Tab 展示顺序:精选留言 → 栏目介绍 → 评价得积分(仅渲染有数据的项) */
+			ratingTabList() {
+				const tabs = []
+				if (this.showTabFeaturedComments) {
+					tabs.push({
+						key: 'featured',
+						index: 0,
+						label: '精选留言',
+						icon: 'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/pl.png',
+						iconActive: 'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/pl-sel.png'
+					})
+				}
+				if (this.showTabColumnIntro) {
+					tabs.push({
+						key: 'column',
+						index: 1,
+						label: '栏目介绍',
+						icon: 'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/des.png',
+						iconActive: 'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/des-sel.png'
+					})
+				}
+				if (this.showTabReviewPoints) {
+					tabs.push({
+						key: 'review',
+						index: 2,
+						label: '评价得积分',
+						icon: 'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/sel.png',
+						iconActive: 'https://bjzmky-1323137866.cos.ap-chongqing.myqcloud.com/video/zan-sel.png'
+					})
+				}
+				return tabs
 			},
 			hasVisibleRatingTab() {
 				return this.visibleRatingTabCount > 0
@@ -1173,22 +1166,30 @@
 				if (!this.fakeMarqueeEligible || !this._fakeMarqueeStarted) return
 				this.syncTripleMarqueeImmediate()
 			},
+			/** 精选留言 Tab 出现后默认高亮 */
+			showTabFeaturedComments(now, was) {
+				if (now && was !== true) {
+					this._selectDefaultRatingTab()
+				}
+			},
+			/**
+			 * 评价 Tab 晚于栏目介绍返回时,_syncRatingTabIndex 可能暂落在 tab=1;
+			 * 若有精选留言则仍默认高亮 tab=0,否则仅校正到当前第一个可见 Tab。
+			 */
 			showTabReviewPoints(now, was) {
 				if (now && was !== true) {
-					this.tabIndex = 0
+					this._selectDefaultRatingTab()
 				}
 			},
+			/** Tab 数量增加且含精选留言时,默认高亮精选留言 */
 			visibleRatingTabCount(n, o) {
-				if (n === 2 && this.showTabReviewPoints) {
-					this.tabIndex = 0
-				}
-				if (n !== 3) return
-				if (o != null && o >= 3) return
-				this.tabIndex = 0
+				if (n <= 0 || !this.showTabFeaturedComments) return
+				if (o != null && n <= o) return
+				this._selectDefaultRatingTab()
 			},
 			/** 离开精选留言 Tab 时收起键盘输入层与选图弹层(与 videovip 行为一致) */
 			tabIndex(n) {
-				if (n !== 2) {
+				if (n !== 0) {
 					this._closeFeaturedCommentComposerUi()
 					this.closeFeaturedMediaActionSheet()
 				}
@@ -1681,7 +1682,16 @@
 			openList(){
 				const wasShu = this.isShu
 				this.isShu=!this.isShu
-				if (wasShu && this.showTabReviewPoints) this.tabIndex = 0
+				if (wasShu && this.showTabFeaturedComments) this.tabIndex = 0
+			},
+			/** 有精选留言时默认 tabIndex=0,否则落到第一个可见 Tab */
+			_selectDefaultRatingTab() {
+				if (this.showTabFeaturedComments) {
+					this.tabIndex = 0
+					this.loadFeaturedComments()
+					return
+				}
+				this._syncRatingTabIndex()
 			},
 			_closeFeaturedCommentComposerUi() {
 				this.featuredCommentComposerActive = false
@@ -1707,25 +1717,25 @@
 			},
 			_syncRatingTabIndex() {
 				const tabs = [
-					this.showTabReviewPoints,
+					this.showTabFeaturedComments,
 					this.showTabColumnIntro,
-					this.showTabFeaturedComments
+					this.showTabReviewPoints
 				]
 				if (!tabs.some(Boolean)) return
 				if (tabs[this.tabIndex]) return
 				const idx = tabs.findIndex(Boolean)
 				if (idx < 0) return
 				this.tabIndex = idx
-				if (idx === 2) {
+				if (idx === 0) {
 					this.loadFeaturedComments()
 				}
 			},
 			selecTab(idx){
-				if (idx === 0 && !this.showTabReviewPoints) return
+				if (idx === 0 && !this.showTabFeaturedComments) return
 				if (idx === 1 && !this.showTabColumnIntro) return
-				if (idx === 2 && !this.showTabFeaturedComments) return
+				if (idx === 2 && !this.showTabReviewPoints) return
 				this.tabIndex = idx
-				if (idx === 2) {
+				if (idx === 0) {
 					this.loadFeaturedComments()
 				}
 			},
@@ -1847,7 +1857,7 @@
 				if (pageLen === 0) this.featuredCommentHasMore = false
 			},
 			onFeaturedCommentScrollToLower() {
-				if (this.tabIndex !== 2 || !this.showTabFeaturedComments) return
+				if (this.tabIndex !== 0 || !this.showTabFeaturedComments) return
 				this.loadFeaturedComments({ append: true })
 			},
 			loadFeaturedComments(opts) {
@@ -2257,7 +2267,7 @@
 				if (!this.isShu) return
 				if (!(this.visibleRatingTabCount === 1 && this.showTabFeaturedComments)) return
 				this.isShu = false
-				this.tabIndex = 2
+				this.tabIndex = 0
 			},
 			_armFeaturedMediaPickerOnShowSuppress() {
 				this.videovipSuppressOnShowCourseFetchOnce = true
@@ -2773,9 +2783,9 @@
 					// 只在“进入全屏”时切换,避免 exitFullScreen 触发的 false 事件二次反转
 					if (!isFullScreen || this.fullscreenToggleLock) return;
 					this.fullscreenToggleLock = true;
-					const wasShu = this.isShu
+					// const wasShu = this.isShu
 					this.isShu = !this.isShu;
-					if (!this.isShu && wasShu && this.showTabReviewPoints) this.tabIndex = 0
+					// if (!this.isShu && wasShu && this.showTabFeaturedComments) this.tabIndex = 0
 					// 先让布局切换完成,再退出原生全屏,减少抖动闪频
 					setTimeout(() => {
 						if (this.videoContext && this.videoContext.exitFullScreen) {

+ 5 - 5
pages_course/videovip.vue

@@ -538,7 +538,7 @@
 		<!-- <view class="footer-tips">重庆云联融智提供技术支持</view> -->
 		<!-- footer -->
 		<view class="footer" v-if="videoId">
-			<view class="btns" :style="{'justify-content':isLogin&&isAddKf==1&&remainTime==0&&!showTabColumnIntro?'space-between':'flex-end'}">
+			<view class="btns" :style="{'justify-content':isLogin&&isAddKf==1&&remainTime==0&&hasVisibleRatingTab&&!showTabColumnIntro?'space-between':'flex-end'}">
 				<!-- <button
 					class="author-btn"
 					open-type="getPhoneNumber"
@@ -548,9 +548,9 @@
 					open-type="getUserInfo" :disabled="userdisabled"
 					@getuserinfo="userInfologin"  v-if="authType==0&&!isquestion">{{isLogin&&isAddKf==1 ? '提交答案领取奖励' : '立即学习'}}</button> -->
 				
-				<template v-if="!isquestion && showTabReviewPoints">
-					<button class="author-btn" @click="openList" v-if="isLogin&&isAddKf==1&&isShu">{{ showTabFeaturedComments ? '精选留言' : showTabColumnIntro ? '栏目介绍' : '评价得积分' }}
-					<image  v-if="showTabReviewPoints" src="/static/images/jifen.png"></image></button>
+				<template>
+					<button class="author-btn" @click="openList" v-if="isLogin&&isAddKf==1&&isShu&& (showTabFeaturedComments || showTabColumnIntro || showTabReviewPoints)">{{ showTabFeaturedComments ? '去留言' : showTabColumnIntro ? '栏目介绍' : '评价得积分' }}
+					<image v-if="showTabReviewPoints&&!showTabFeaturedComments&&!showTabColumnIntro" src="/static/images/jifen.png"></image></button>
 					<button class="author-btn" @click="submit" v-if="isLogin&&isAddKf==1&&remainTime==0&&!isShu&&tabIndex==2">评价得积分
 					<image src="/static/images/jifen.png"></image>
 					</button>
@@ -561,7 +561,7 @@
 					open-type="getUserInfo" :disabled="userdisabled"
 					@getuserinfo="userInfologin" v-if="authType==0&&!isLogin&&isAddKf!==1">立即学习</button> -->
 					<!-- 竖屏 isShu 下 rating 区隐藏;若仍停留在精选留言 tab,勿在 footer 展示留言框,只保留「评价得积分」按钮(与 _expandLayoutIfPortraitFeaturedCommentsOnly 竖屏体验一致) -->
-					<view v-if="tabIndex==0 && showTabFeaturedComments && !(showTabReviewPoints && isShu)" class="rating-msg-input-shell">
+					<view v-if="tabIndex==0 && showTabFeaturedComments&&!isShu" class="rating-msg-input-shell">
 						<view
 							v-if="featuredCommentMedia"
 							class="rating-msg-media-pill"