base.js 4.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174
  1. import {
  2. getAssetUrl,
  3. getThumbnailUrl
  4. } from '@/api/asset'
  5. import { create } from './utils'
  6. export default {
  7. provide () {
  8. return {
  9. control: this
  10. }
  11. },
  12. props: {
  13. program: {
  14. type: Object,
  15. required: true
  16. }
  17. },
  18. data () {
  19. return {
  20. scale: 100,
  21. minScale: 100,
  22. maxScale: 100,
  23. padding: 0,
  24. selectedWidgetIndex: -1,
  25. node: null,
  26. bgm: '',
  27. muted: true
  28. }
  29. },
  30. computed: {
  31. transformStyles () {
  32. return {
  33. transform: `scale(${this.scale / 100})`,
  34. 'transform-origin': '0 0'
  35. }
  36. },
  37. styles () {
  38. if (this.node) {
  39. const { width, height, backgroundColor } = this.node
  40. return {
  41. width: `${width}px`,
  42. height: `${height}px`,
  43. color: backgroundColor
  44. }
  45. }
  46. return null
  47. },
  48. backgroundStyles () {
  49. if (this.node) {
  50. const { backgroundImage } = this.node
  51. return {
  52. 'background-image': backgroundImage[0] ? `url("${getThumbnailUrl(backgroundImage[0])}")` : 'none'
  53. }
  54. }
  55. return null
  56. },
  57. widgets () {
  58. return this.node?.widgets || []
  59. },
  60. widget () {
  61. return this.widgets[this.selectedWidgetIndex] || this.node
  62. },
  63. hasAudio () {
  64. if (this.node) {
  65. if (this.node.bgm.length) {
  66. return true
  67. }
  68. return this.node.widgets.some(widget => widget.mute === 0 && (widget.sources?.length || widget.url))
  69. }
  70. return false
  71. },
  72. bgmUrl () {
  73. return this.bgm ? getAssetUrl(this.bgm) : ''
  74. },
  75. hasNext () {
  76. return !this.muted && this.node?.bgm.length > 1
  77. }
  78. },
  79. watch: {
  80. 'node.bgm' () {
  81. this.setBgm()
  82. }
  83. },
  84. mounted () {
  85. this.initCanvas(this.program.detail)
  86. this.checkRatio()
  87. window.addEventListener('resize', this.checkRatio)
  88. },
  89. beforeDestroy () {
  90. window.removeEventListener('resize', this.checkRatio)
  91. },
  92. methods: {
  93. toggleMute () {
  94. this.muted = !this.muted
  95. },
  96. setBgm () {
  97. this.$bgmIndex = 0
  98. this.chooseBgm()
  99. },
  100. chooseBgm () {
  101. const { bgm, toggleType } = this.node
  102. const length = bgm.length
  103. if (length === 0) {
  104. this.bgm = ''
  105. return
  106. }
  107. if (length === 1) {
  108. this.bgm = bgm[0].keyName
  109. return
  110. }
  111. let index
  112. switch (toggleType) {
  113. case 'cycle':
  114. index = this.$bgmIndex
  115. this.$bgmIndex = (index + 1) % length
  116. break
  117. case 'random':
  118. index = Math.random() * length | 0
  119. if (bgm[index]?.keyName === this.bgm) {
  120. if (index === 0) {
  121. index += 1
  122. } else {
  123. index -= 1
  124. }
  125. }
  126. break
  127. default:
  128. return
  129. }
  130. this.bgm = bgm[index].keyName
  131. },
  132. onAudioEnded () {
  133. if (this.node.bgm.length > 1) {
  134. this.chooseBgm()
  135. }
  136. this.$refs.audio.play()
  137. },
  138. onAudioError (e) {
  139. console.warn('audio error', e)
  140. if (this.node?.bgm.length > 1) {
  141. this.chooseBgm()
  142. }
  143. },
  144. checkRatio () {
  145. const wrapper = this.$refs.wrapper
  146. if (wrapper && this.node) {
  147. const width = wrapper.offsetWidth - this.padding * 2
  148. const height = wrapper.offsetHeight - this.padding * 2
  149. const { width: cWidth, height: cHeight } = this.node
  150. const wScale = width / cWidth
  151. const hScale = height / cHeight
  152. if (cWidth > width || cHeight > height) {
  153. this.scale = Math.min(wScale, hScale) * 100 | 0
  154. this.maxScale = Math.max(1, wScale, hScale) * 100 | 0
  155. } else {
  156. this.scale = 100
  157. this.maxScale = Math.max(2, wScale, hScale) * 100 | 0
  158. }
  159. this.minScale = this.scale
  160. console.log('width: layout -> window', cWidth, '->', width, wScale)
  161. console.log('height: layout -> window', cHeight, '->', height, hScale)
  162. console.log(this.scale, this.maxScale)
  163. }
  164. },
  165. initCanvas (canvas) {
  166. this.node = create(canvas)
  167. console.log(this.node)
  168. }
  169. }
  170. }