当前位置: 首页 > ds >正文

小程序视频播放,与父视图一致等样式设置

初始设置的代码:

WXML的代码

<view class="card-wrapper"> <!-- 视频播放容器(默认隐藏) --> <view class="video-container" wx:if="{{isPlaying}}"> <video id="cardVideo" class="card-video" src="{{item.videoUrl}}" autoplay controls bindplay="onVideoPlay" bindpause="onVideoPause" bindended="onVideoEnd" ></video> <view class="video-close-btn" bindtap="togglePlay"> <image src="https://images.biliq.com/images/miniprogram/paopao2.0/paopaoCard/close.png" mode="aspectFit" /> </view> </view> <!-- 封面图容器(播放时隐藏) --> <view class="banner-mask" wx:if="{{!isPlaying}}"> <image class="banner-img" src="{{item.cover}}" mode="aspectFill" /> <!-- 播放按钮 --> <view class="play-mask" bindtap="togglePlay"> <image class="play-icon" src="https://images.biliq.com/images/miniprogram/paopao2.0/paopaoCard/play.png" mode="aspectFit" /> </view> <!-- 点赞、转发、导航 --> <view class="action-bar-wrapper"> <actionBar class="action-bar" item="{{item}}" bind:action="onAction" /> </view> </view> <!-- 名称区域 --> <view class="desc-mask" wx:if="{{!isPlaying}}"> <!-- 名称 --> <text class="banner-title">{{item.title}}</text> <!-- 挂载件 --> <actionMount wx:if="{{item.ismount}}" class="has-mount" item="{{item}}" bind:action="onAction" /> <!-- 无挂载 --> <view wx:elif="{{!item.ismount}}" class="no-mount" item="{{item}}" bind:action="onAction" /> <!-- 详情 --> <view wx:if="{{!item.ismount}}" class="more-mask" bindtap="handleDatail"> <image class="more-img" src="https://images.biliq.com/images/miniprogram/paopao2.0/paopaoCard/more.png" /> </view> </view> <!-- 标签区域 --> <view class="tag-list" wx:if="{{!isPlaying}}"> <block wx:for="{{item.tags}}" wx:key="index" wx:if="{{index < 3}}"> <view class="tag-mask {{item.spotag ? 'has-spot' : ''}}"> <image class="spot-tag" wx:if="{{item.spotag}}" src="https://images.biliq.com/images/miniprogram/paopao2.0/paopaoCard/spotag.png" mode="aspectFit" /> <text class="tag">{{item.text}}</text> </view> </block> </view> </view>

JS的代码

Component({ properties: { item: Object }, data: { isPlaying: false, videoContext: null }, methods: { // 切换播放状态 togglePlay() { if (this.data.isPlaying) { // 如果正在播放,则暂停并隐藏视频 this.data.videoContext.pause(); this.setData({ isPlaying: false }); } else { // 如果未播放,则显示视频并播放 this.setData({ isPlaying: true }, () => { this.data.videoContext = wx.createVideoContext('cardVideo', this); this.data.videoContext.play(); }); } }, // 视频开始播放 onVideoPlay() { console.log('视频开始播放'); }, // 视频暂停 onVideoPause() { console.log('视频已暂停'); }, // 视频播放结束 onVideoEnd() { this.setData({ isPlaying: false }); }, // 其他原有方法... onAction(e) { // 原有逻辑 }, handleDatail() { // 原有逻辑 } }, // 组件卸载时销毁视频实例 detached() { if (this.data.videoContext) { this.data.videoContext.pause(); } } });

WXSS的代码

.card-wrapper { position: relative; width: 100%; border-radius: 12rpx; overflow: hidden; } /* 视频容器样式 */ .video-container { position: relative; width: 100%; height: 0; padding-bottom: 56.25%; /* 16:9 比例 */ } .card-video { position: absolute; top: 0; left: 0; width: 100%; height: 100%; } .video-close-btn { position: absolute; top: 20rpx; right: 20rpx; width: 60rpx; height: 60rpx; z-index: 10; } .video-close-btn image { width: 100%; height: 100%; } /* 原有样式保持不变 */ .banner-mask { position: relative; width: 100%; height: 0; padding-bottom: 56.25%; /* 16:9 比例 */ } .banner-img { position: absolute; top: 0; left: 0; width: 100%; height: 100%; } .play-mask { position: absolute; top: 0; left: 0; width: 100%; height: 100%; display: flex; justify-content: center; align-items: center; background-color: rgba(0, 0, 0, 0.3); } .play-icon { width: 100rpx; height: 100rpx; } /* 其他原有样式... */

上述代码展示效果如下

上述代码可以实现视频播放,但是样式不是很好看,我们可以增加一些设置,比如视频和父视图的卡片一样,视频居中展示播放等等,下面是优化后的代码。

WXML的代码

<view class="card-wrapper">

<!-- 视频播放容器(默认隐藏) -->

<view class="video-container" wx:if="{{isPlaying}}">

<!-- 修改为绝对定位的视频包装器 -->

<view class="video-wrapper">

<video

id="cardVideo"

class="card-video"

src="{{item.videoUrl}}"

autoplay

controls

bindplay="onVideoPlay"

bindpause="onVideoPause"

bindended="onVideoEnd"

></video>

</view>

<!-- 关闭按钮 -->

<view class="video-close-btn" bindtap="togglePlay">

<image src="https://images.biliq.com/images/miniprogram/paopao2.0/paopaoCard/close.png" mode="aspectFit" />

</view>

</view>

<!-- 封面图容器(播放时隐藏) -->

<view class="banner-mask" wx:if="{{!isPlaying}}">

<!-- 封面 -->

<image class="banner-img" src="{{item.cover}}" mode="aspectFill" />

<!-- 播放 -->

<view class="play-mask" bindtap="togglePlay">

<image class="play-icon" src="{{isPlaying ? '' : 'https://images.biliq.com/images/miniprogram/paopao2.0/paopaoCard/play.png'}}" mode="aspectFit}}" />

</view>

<!-- 点赞、转发 -->

<view class="action-bar-wrapper">

<actionBar class="action-bar" item="{{item}}" bind:action="onAction" />

</view>

</view>

<!-- 名称区域 -->

<view class="desc-mask" wx:if="{{!isPlaying}}">

<text class="banner-title">{{item.name}}</text>

<view class="more-mask" bind:tap="onDatail">

<image class="more-img" src="https://images.biliq.com/images/miniprogram/paopao2.0/paopaoCard/more.png" />

</view>

<!-- 标签区域 -->

<view class="tag-list">

<block wx:for="{{item.tags}}" wx:key="index" wx:if="{{index < 3}}">

<view class="tag-mask">

<text class="tag">{{item.text}}</text>

</view>

</block>

</view>

</view>

</view>

WXSS的代码

.card-wrapper{

position: absolute;

top: 0;

left: 0;

width: 100%;

height: 100%;

color: #fff;

padding: 0;

}

/* 视频容器样式 - 关键修改 */

.video-container {

position: relative;

width: 100%;

height: 100%;

background: #000;

display: flex;

flex-direction: column; /* 改为列方向布局 */

}

/* 视频包装器 - 移除绝对定位 */

.video-wrapper {

flex: 1; /* 占据剩余空间 */

position: relative;

width: 100%;

padding-bottom: 56.25%; /* 保持16:9比例 */

}

/* 视频样式调整 */

.card-video {

position: absolute;

top: 0;

left: 0;

width: 100%;

height: 100%;

background: #000;

}

/* 强制原生控件在底部 */

.card-video::webkit-media-controls {

position: absolute;

bottom: 0;

width: 100%;

}

.video-close-btn {

position: absolute;

top: 35rpx;

right: 20rpx;

width: 60rpx;

height: 60rpx;

z-index: 10;

display: flex;

justify-content: center;

align-items: center;

}

.video-close-btn image {

width: 100%;

height: 100%;

}


/* 封面图 */

.banner-mask {

position: absolute;

top: 0;

left: 0;

width: 100%;

height: 100%;

margin: 0;

overflow: hidden;

}

.banner-img {

width: 100%;

height: 100%;

border-radius: 20rpx;

}

.play-mask{

position: absolute;

top: 50%;

left: 50%;

transform: translate(-50%, -50%);

width: 88rpx;

height: 88rpx;

padding: 0;

background: none;

display: flex;

justify-content: center;

align-items: center;

}

.play-icon{

width: 100%;

height: 100%;

}

/* 描述区域 */

.desc-mask{

position: absolute;

display: inline-flex;/* 改为inline-flex使宽度自适应内容 */

align-items: center;

left: 30rpx;

height: 104rpx;

bottom: 40rpx;

border-radius: 20rpx;

background-color: rgba(29, 52, 59, 0.4);

backdrop-filter: blur(10rpx);

padding: 0 24rpx;

gap: 5rpx; /* title 与 more-mask 间距 5rpx */

}

.banner-title{

height: 48rpx;

font-weight: 600;

font-size: 34rpx;

color: #FFFFFF;

white-space: nowrap; /* 防止换行 */

}

.more-mask{

flex-shrink: 0;

width: 45rpx;

height: 45rpx;

display: flex;

align-items: center;

justify-content: center;

}

.more-img{

width: 26rpx;

height: 26rpx;

}

/* 标签 */

.tag-list{

position: absolute;

left: 5rpx;

bottom: 114rpx;

display: flex;

flex-wrap: wrap;

gap: 10rpx;

align-items: center;

padding: 6rpx 12rpx;

z-index: 1; /* 确保在desc-mask上层 */

}

.tag-mask{

display: inline-flex; /* 行内弹性布局 */

align-items: center;

background: rgba(0, 0, 0, 0.4);

border-radius: 22rpx;

height: 44rpx;

padding: 5rpx 15rpx;/* 动态宽度由内容撑开 */

}

.tag{

font-weight: 500;

font-size: 20rpx;

color: #E0ED42;

line-height: 28rpx;

text-align: justify;

/* 确保文字不换行 */

white-space: nowrap;

margin-right: 5rpx;

}

/* 收藏、转发 */

.action-bar-wrapper {

position: absolute;

right: 30rpx;

bottom: 30rpx;

width: 60rpx;

height: 380rpx;

z-index: 999;

}

.action-bar {

width: 100%;

height: 100%;

display: flex;

flex-direction: column;

align-items: center;

justify-content: space-between;

gap: 20rpx;

}


http://www.xdnf.cn/news/16741.html

相关文章:

  • Python爬虫01_Requests第一血获取响应数据
  • 【Python】数据可视化之聚类图
  • logtrick 按位或最大的最小子数组长度
  • Apache Ignite 的对等类加载(Peer Class Loading, P2P Class Loading)机制
  • 快速了解逻辑回归
  • 6、微服务架构常用十种设计模式
  • PLC如何进行远程维护远程上下载程序?
  • QT项目 -仿QQ音乐的音乐播放器(第三节)
  • 基于dcmtk的dicom工具 第九章 以json文件或sqlite为数据源的worklist服务(附工程源码)
  • Qt 移动应用性能优化策略
  • 复现cacti的RCE(CVE-2022-46169)
  • TDengine 中 TDgpt 异常检测的机器学习算法
  • Leetcode——41. 缺失的第一个正数
  • 数学建模——非线性规划
  • 大文档免费翻译方法分享
  • 政策合规性前端设计:工业数据安全的可视化技术规范与落地实践
  • C语言进阶(指针2.函数指针和指针函数,二级指针,指针数组和数组指针,void*指针)
  • 数据结构 排序(2)---选择排序
  • 使用鼠标在Canvas上绘制矩形
  • PDF转Word免费工具!批量处理PDF压缩,合并, OCR识别, 去水印, 签名等全功能详解
  • Shader开发(四)计算机图形学中的颜色定义
  • Java 大视界 -- Java 大数据机器学习模型在金融信用评级模型优化与信用风险动态管理中的应用(371)
  • Day23-二叉树的层序遍历(广度优先搜素)
  • [明道云]-基础教学2-工作表字段 vs 控件:选哪种?
  • Redis 跨主机连接超时分析:从网络波动到架构优化
  • 个人健康管理小程序(消息订阅、Echarts图形化分析)
  • TGD第八篇:二维应用——图像边缘检测
  • ftp加ssl,升级ftps
  • 三维扫描相机:工业自动化的智慧之眼——迁移科技赋能智能制造新纪元
  • 从东南亚出发:小程序容器技术如何助力 App 快速打入全球市场?