bdLook.vue 6.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250
  1. <template>
  2. <view class="content">
  3. <view class="player-content">
  4. <!-- <live-player src="https://domain/pull_stream" mode="RTC" autoplay bindstatechange="statechange" binderror="error" style="width: 300px; height: 225px;" /> -->
  5. <!-- #ifdef MP-WEIXIN -->
  6. <live-player
  7. id="livePlayer"
  8. class="live-player"
  9. catchtouchmove
  10. :src="sourceUrl"
  11. autoplay
  12. background-mute
  13. object-fit="contain"
  14. sound-mode="speaker"
  15. mode="live"
  16. @statechange="statechange"
  17. @error="error"
  18. @click="handleControlbar"
  19. >
  20. <view class="player-tool" :style="{ bottom: showControlbar ? '0' : '-60rpx' }">
  21. <view class="tools">
  22. <view class="full-screen" @tap.stop="handleFullScreen()">
  23. <!-- <text class="iconfont">&#xe824;</text>
  24. <text class="iconfont" v-else>&#xe67e;</text>
  25. -->
  26. <u-icon v-if="!fullScreenFlag" name="setting"></u-icon>
  27. <u-icon name="setting-fill"></u-icon>
  28. </view>
  29. <view class="cruise" @tap.stop="handleCruise()" v-if="streamIndex == 2"><text class="iconfont">&#xe625;</text></view>
  30. </view>
  31. </view>
  32. </live-player>
  33. <!-- #endif -->
  34. </view>
  35. </view>
  36. </template>
  37. <script>
  38. export default {
  39. data() {
  40. return {
  41. roomid: '', //获取直播间roomid
  42. isPlaySource: false, //是否有播放源
  43. isVideoLive: false, //是否是直播
  44. isAutoplay: true, //是否自动播放
  45. videoMsg: '', //video消息
  46. sourceUrl: 'https://domain/pull_stream"', //播放路径
  47. showControlbar: true,
  48. timer: null
  49. };
  50. },
  51. watch: {
  52. showControlbar(val, oldVal) {
  53. if (val) {
  54. this.timer = setTimeout(() => {
  55. this.showControlbar = false;
  56. }, 5000);
  57. } else {
  58. clearTimeout(this.timer);
  59. }
  60. }
  61. },
  62. onLoad(opt) {
  63. let item = JSON.parse(opt.item);
  64. this.roomid = item.roomid || '';
  65. console.log(JSON.parse(opt.item), item, this.roomid);
  66. this.getLiveList(); //视频流列表
  67. // #ifdef MP-WEIXIN
  68. this.playerCtx = uni.createLivePlayerContext('livePlayer');
  69. // #endif
  70. },
  71. created() {
  72. // #ifdef MP-WEIXIN
  73. //自定义控制栏自动隐藏的实现
  74. setTimeout(() => {
  75. this.showControlbar = false;
  76. }, 10000);
  77. // #endif
  78. },
  79. methods: {
  80. statechange(e) {
  81. console.log('live-player code:', e.detail.code);
  82. let code = e.detail.code;
  83. if (code === 2001) {
  84. this.$api.toast('2001: 已经连接服务器');
  85. } else if (code === 2002) {
  86. this.$api.toast('2002: 已经连接 RTMP 服务器,开始拉流');
  87. } else if (code === 2003) {
  88. this.$api.toast('2003: 网络接收到首个视频数据包(IDR)');
  89. } else if (code === 2004) {
  90. this.$api.toast('2004: 视频播放开始');
  91. } else if (code === 2008) {
  92. this.$api.toast('解码器启动,如遇不播放或卡顿,请尝试重新播放', 3000);
  93. } else if (code === 2009) {
  94. console.warn('2009: 视频分辨率改变');
  95. } else if (code === 2101) {
  96. this.$api.toast('2101: 当前视频帧解码失败');
  97. } else if (code === 2102) {
  98. this.$api.toast('2102: 当前音频帧解码失败');
  99. } else if (code === 2103) {
  100. this.$api.toast('2103: 网络断连, 已启动自动重连');
  101. } else if (code === 2104) {
  102. this.$api.toast('2104: 网络来包不稳:可能是下行带宽不足,或由于主播端出流不均匀');
  103. } else if (code === 2105) {
  104. this.$api.toast('2105: 当前视频播放出现卡顿');
  105. } else if (code === 2106) {
  106. this.$api.toast('2106: 硬解启动失败,采用软解');
  107. } else if (code === 2107) {
  108. this.$api.toast('2107: 当前视频帧不连续,可能丢帧');
  109. } else if (code === 2108) {
  110. this.$api.toast('2108: 当前流硬解第一个I帧失败,SDK自动切软解');
  111. } else if (code === 3001) {
  112. this.$api.toast('3001: RTMP -DNS解析失败');
  113. } else if (code === 3002) {
  114. this.$api.toast('3002: RTMP服务器连接失败');
  115. } else if (code === 3003) {
  116. this.$api.toast('3003: RTMP服务器握手失败');
  117. } else if (code === 3005) {
  118. this.$api.toast('3005: RTMP 读/写失败,之后会发起网络重试');
  119. } else if (code === -2301) {
  120. this.$api.toast('-2301: 网络断连,且经多次重连抢救无效,更多重试请自行重启播放');
  121. } else if (code === -2302) {
  122. this.$api.toast('-2302: 获取加速拉流地址失败');
  123. }
  124. },
  125. error(e) {
  126. console.error('live-player error:', e.detail.errMsg);
  127. },
  128. handleControlbar() {
  129. this.showControlbar = !this.showControlbar;
  130. },
  131. getLiveList() {
  132. console.log(this.roomid);
  133. let val = this.roomid;
  134. this.$api
  135. .request('live/get_url', {
  136. roomid: val
  137. })
  138. .then(data => {
  139. console.log(data);
  140. console.log(this.roomid);
  141. if (data.code == 200) {
  142. this.sourceUrl = data.data.pushAddr;
  143. } else {
  144. this.$api.toast(data.msg);
  145. }
  146. });
  147. },
  148. // 巡航
  149. handleCruise() {
  150. // #ifdef MP-WEIXIN
  151. uni.vibrateShort();
  152. // #endif
  153. },
  154. //全屏功能的实现
  155. handleFullScreen() {
  156. var that = this;
  157. if (!that.fullScreenFlag) {
  158. //全屏
  159. that.playerCtx.requestFullScreen({
  160. success: res => {
  161. that.fullScreenFlag = true;
  162. console.log('我要执行了');
  163. },
  164. fail: res => {
  165. console.log('fullscreen fail');
  166. },
  167. direction: 90
  168. });
  169. } else {
  170. //缩小
  171. that.playerCtx.exitFullScreen({
  172. success: res => {
  173. that.fullScreenFlag = false;
  174. console.log('我要执行了');
  175. },
  176. fail: res => {
  177. console.log('exit fullscreen success');
  178. }
  179. });
  180. }
  181. }
  182. }
  183. };
  184. </script>
  185. <style lang="scss" scoped>
  186. .content {
  187. width: 100%;
  188. height: 100%;
  189. display: flex;
  190. flex-direction: column;
  191. .player-content {
  192. position: relative;
  193. width: 100%;
  194. height: 100vh;
  195. display: flex;
  196. background-size: 100% 100%;
  197. .live-player {
  198. width: 100%;
  199. height: 100%;
  200. position: relative;
  201. }
  202. }
  203. }
  204. //播放器弹出工具
  205. .player-tool {
  206. width: 100%;
  207. height: 60rpx;
  208. background-image: linear-gradient(0deg, rgba(0, 0, 0, 0.6), transparent);
  209. display: flex;
  210. align-items: center;
  211. justify-content: space-between;
  212. position: absolute;
  213. left: 0;
  214. padding: 0 45rpx;
  215. transition: all 0.3s;
  216. .tools {
  217. height: 100%;
  218. width: auto;
  219. display: flex;
  220. align-items: center;
  221. .full-screen {
  222. height: 100%;
  223. display: flex;
  224. align-items: center;
  225. justify-content: center;
  226. .iconfont {
  227. color: #fff;
  228. font-weight: bold;
  229. }
  230. }
  231. .cruise {
  232. display: flex;
  233. align-items: center;
  234. justify-content: center;
  235. margin-left: 25rpx;
  236. .iconfont {
  237. color: #e45a3e;
  238. font-size: 45rpx;
  239. }
  240. }
  241. }
  242. }
  243. </style>