RightPopup.vue 7.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276
  1. <template>
  2. <!-- 右侧弹框 -->
  3. <van-popup :value="levitatedSphereVisible" @input="showChange" position="right" class="levitated-sphere-drawer"
  4. overlay-class="levitated-sphere-overlay" :overlay-style="{'background-color': 'transparent !important'}">
  5. <div class="flex-column" style="min-width: 50px;">
  6. <div class="flex-column-container">
  7. <div>
  8. <div v-for="item in definitionList" :key="item.key"
  9. :class="['tc drawer-item mb-4', {active: actDefinition === item.name}]"
  10. @click.prevent="definitionFun(item)">
  11. {{item.name}}
  12. </div>
  13. <!-- <div class="tc drawer-item mb-4" @click.prevent="resolutionRatio">
  14. 分辨率
  15. </div> -->
  16. <div class="tc drawer-item mb-4" @click.prevent="volumeControl(24)">
  17. 音量 +
  18. </div>
  19. <div class="tc drawer-item" @click.prevent="volumeControl(25)">
  20. 音量 -
  21. </div>
  22. </div>
  23. </div>
  24. <div class="exit">
  25. <template v-for="(item, index) in exitList">
  26. <div :key="item.key" :class="['tc', {'mb-4': index !== exitList.length - 1}, item.key]"
  27. @click.prevent="exitFun(item.key)">
  28. <img :src="item.img" alt="">
  29. <div class="drawer-item">
  30. {{item.name}}
  31. </div>
  32. </div>
  33. </template>
  34. </div>
  35. </div>
  36. </van-popup>
  37. </template>
  38. <script>
  39. import * as uni from '../../../static/static/js/uni.webview.1.5.2.js';
  40. export default {
  41. name: 'RightPopup',
  42. props: {
  43. // 拉流渲染引擎实例
  44. engine: {
  45. type: Object,
  46. default: () => ({})
  47. },
  48. userCardId: {
  49. type: String,
  50. default: ''
  51. },
  52. // popup是否显示
  53. levitatedSphereVisible: {
  54. type: Boolean,
  55. default: false
  56. },
  57. // 清晰度默认值
  58. definitionValue: {
  59. type: String,
  60. default: ()=> localStorage.getItem('definitionValue') ?? '自动',
  61. },
  62. // 清晰度列表
  63. definitionList: {
  64. type: Array,
  65. default: () => [{
  66. name: '自动',
  67. value: 2800
  68. }, {
  69. name: '高清',
  70. value: 2800
  71. }, {
  72. name: '标清',
  73. value: 1500,
  74. }, {
  75. name: '流畅',
  76. value: 1000,
  77. }]
  78. },
  79. // 清晰度对应分辨率和帧率列表
  80. resolutionRatioList: {
  81. type: Object,
  82. default: () => ({
  83. '自动': { width: 720, height: 1280, fps: 30 },
  84. '高清': { width: 720, height: 1280, fps: 30 },
  85. '标清': { width: 540, height: 960, fps: 25 },
  86. '流畅': { width: 360, height: 640, fps: 20 },
  87. })
  88. },
  89. // url中获取的参数, 父组件传递
  90. parametersData: {
  91. type: Object,
  92. default: () => ({})
  93. },
  94. },
  95. data() {
  96. return {
  97. // 当前清晰度
  98. actDefinition: this.definitionValue,
  99. }
  100. },
  101. computed: {
  102. // 右侧弹框退出相关按钮
  103. exitList() {
  104. let arr = [{
  105. name: '剪贴版',
  106. key: "shearplate",
  107. img: '../static/img/wx/jianqieban_icon.png'
  108. }, {
  109. name: '退出',
  110. key: 'signout',
  111. img: '../static/img/wx/tuichu_icon.png'
  112. }]
  113. if ([1, 2, 3].includes(+this.parametersData.userCardType)) {
  114. arr.push({
  115. name: '退出并下机',
  116. key: 'dormant',
  117. img: '../static/img/wx/tuichu_icon.png'
  118. })
  119. }
  120. return arr
  121. }
  122. },
  123. methods: {
  124. showChange(val){
  125. this.$emit('update:levitatedSphereVisible', val);
  126. },
  127. // 清晰度 画质
  128. definitionFun(item) {
  129. try {
  130. this.actDefinition = item.name;
  131. // 设置日志参数 推流质量
  132. // logReportObj.setParams({ imageQuality: item.name });
  133. localStorage.setItem('definitionValue', item.name);
  134. // 设置码率
  135. this.setBitrate(item);
  136. this.$emit('update:levitatedSphereVisible', false);
  137. } catch (err) {
  138. console.log(err)
  139. }
  140. },
  141. // 设置码率
  142. setBitrate(item) {
  143. // 设置码率和是否允许自动
  144. this.engine?.setCustomBitrate(item.value, item.name === '自动');
  145. // 获取并设置编码器分辨率和帧率
  146. const config = this.resolutionRatioList[item.name];
  147. if (config) {
  148. this.engine?.setEncoderSize(config);
  149. }
  150. },
  151. // 分辨率 已无用,2.0sdk只能固定的几个分辨率值 resolutionRatioList
  152. resolutionRatio() {
  153. request.get('/api/resources/v5/machine/resolution/getResolvingPower', { params: { userCardId: this.parametersData.userCardId } }).then(res => {
  154. if (res.success) {
  155. this.resolutionRatioList = res.data.map(item => {
  156. item.height = item.high
  157. return item
  158. })
  159. }
  160. })
  161. },
  162. // 音量控制 24: 音量+ 25: 音量-
  163. volumeControl(value) {
  164. this.engine.sendKey && this.engine.sendKey(value);
  165. },
  166. // 退出相关按钮操作
  167. exitFun(key) {
  168. switch (key) {
  169. case 'dormant': // 退出并下机
  170. this.$dialog.alert({
  171. title: '提示',
  172. message: '确定退出云手机并下机',
  173. confirmButtonText: '确定',
  174. confirmButtonColor: '#3cc51f',
  175. showCancelButton: true,
  176. beforeClose: (action, done) => {
  177. if (action === 'cancel') done()
  178. if (action === 'confirm') {
  179. this.downline(done)
  180. }
  181. }
  182. })
  183. break;
  184. case 'shearplate': // 剪贴板
  185. // 打开剪贴板
  186. this.$emit('shearplate');
  187. // 关闭popup
  188. this.$emit('update:levitatedSphereVisible', false);
  189. break;
  190. case 'signout':
  191. // 关闭popup
  192. this.$emit('update:levitatedSphereVisible', false);
  193. this.$emit('exit');
  194. break;
  195. }
  196. },
  197. // 退出并下机
  198. async downline(fun = () => {}) {
  199. try {
  200. const res = await this.$axios.get('/resources/yearMember/downline?userCardId=${this.userCardId}`');
  201. if(!res.status){
  202. fun(true);
  203. // 判断是否是顶级窗口(不是嵌套在 iframe 中)目前只有ios的浏览器中才会是顶级窗口
  204. const isTopWindow = window.parent === window.self;
  205. if(isTopWindow){
  206. // 通信给h5项目告知是退出并下机
  207. parent.postMessage({ type: 'exit' }, '*');
  208. uni.postMessage({ data: { type: 'exit' }});
  209. }
  210. this.$emit('exit');
  211. return
  212. }
  213. fun(false)
  214. this.$toast(res.msg);
  215. } catch (error) {
  216. console.log(error);
  217. }
  218. },
  219. }
  220. }
  221. </script>
  222. <style lang="less" scoped>
  223. .levitated-sphere-drawer {
  224. height: 100%;
  225. max-height: none !important;
  226. min-width: 1rem;
  227. color: #fff;
  228. background-color: rgba(2, 2, 6, 0.5);
  229. padding: 30px 10px 0;
  230. box-sizing: border-box;
  231. }
  232. .levitated-sphere-drawer .drawer-item {
  233. line-height: 30px;
  234. border-radius: 3px;
  235. -moz-user-select: none;
  236. -webkit-user-select: none;
  237. -ms-user-select: none;
  238. -khtml-user-select: none;
  239. user-select: none;
  240. }
  241. .levitated-sphere-drawer .drawer-item.active {
  242. background: rgb(255, 255, 255);
  243. color: #000;
  244. }
  245. .levitated-sphere-drawer .exit {
  246. line-height: 30px;
  247. }
  248. .levitated-sphere-drawer .exit img {
  249. width: 24px;
  250. height: 24px;
  251. }
  252. .flex-column {
  253. height: 100%;
  254. display: flex;
  255. flex-direction: column;
  256. }
  257. .flex-column-container {
  258. flex: 1;
  259. overflow-y: auto;
  260. }
  261. .tc {
  262. text-align: center;
  263. }
  264. </style>