• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1/*
2 * Copyright (c) 2023 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 *     http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15// @ts-nocheck
16import media from '@ohos.multimedia.media'
17import fs from '@ohos.file.fs'
18import Logger from './Logger'
19
20const TAG = 'qlw play'
21
22export class mediaPlay {
23    private avPlay: media.AVPlayer = undefined
24    private surfaceId: number = -1
25    public totalDuration: number
26    private handleVideoPlayback: (isVideoPlayback: boolean) => void = false
27
28    async getFileFd(name) {
29        let filesDir = globalThis.abilityContext.filesDir
30        let path = filesDir + '/' + name
31        let file = fs.openSync(path)
32        return file.fd
33    }
34
35    async getRawfileFd(name) {
36        let file = await globalThis.abilityContext.resourceManager.getRawFd(name)
37        return file.fd
38    }
39
40    getCurrentTime() {
41        return 0
42    }
43
44    seek() {
45
46    }
47
48    async init(surfaceId?) {
49        let fd
50        if (surfaceId) {
51            this.surfaceId = surfaceId
52            fd = await this.getFileFd('test.mp4')
53        } else {
54            fd = await this.getFileFd('test.wav')
55        }
56        Logger.info(TAG, ` fd success : ${fd}`)
57        this.avPlay = await media.createAVPlayer()
58        this.setCallBack(this.avPlay)
59        this.avPlay.url = 'fd://' + fd
60    }
61
62    async initVideo(surfaceId) {
63        this.surfaceId = surfaceId
64        let fd = await this.getRawfileFd('video.mp4')
65        Logger.info(TAG, ` fd success : ${fd}`)
66        this.avPlay = await media.createAVPlayer()
67        this.setCallBack(this.avPlay)
68        this.avPlay.url = 'fd://' + fd
69    }
70
71    async Play() {
72        await this.avPlay.play()
73    }
74
75    setCallBack(AVPlayer) {
76        AVPlayer.on('stateChange', async (state, reason) => {
77            switch (state) {
78                case 'idle':
79                    Logger.info(TAG, 'state idle start')
80                    break;
81                case 'initialized':
82                    Logger.info(TAG + 'state initialized start ')
83                    if (this.surfaceId != -1) {
84                        AVPlayer.surfaceId = String(this.surfaceId)
85                    }
86                    await AVPlayer.prepare()
87                    Logger.info(TAG, 'state initialized end')
88                    break;
89                case 'prepared':
90                    Logger.info(TAG, 'state prepared start')
91                    await AVPlayer.play()
92                    Logger.info(TAG, 'state prepared end')
93                    break;
94                case 'playing':
95                    Logger.info(TAG, 'state playing callback')
96                    break;
97                case 'paused':
98                    Logger.info(TAG, 'state paused callback')
99                    break;
100                case 'completed':
101					if (this.handleVideoPlayback) {
102                        this.handleVideoPlayback(true)
103                    }
104                    await AVPlayer.stop()
105                    await AVPlayer.release()
106                case 'error':
107                    Logger.info(TAG, 'state error callback')
108                    break;
109            }
110        })
111        AVPlayer.on('error', (err) => {
112            Logger.info(TAG, `state error callback err:${err},code:${err.code},message:${err.message}}`)
113        })
114    }
115
116    setVideoPlaybackCallback(callback) {
117        this.handleVideoPlayback = callback
118    }
119
120    async release(){
121        if (this.avPlay){
122            await this.avPlay.release()
123            Logger.info(TAG, 'avplay release success')
124        }
125    }
126
127    encodeWAV(sampleRateValue, sampleBitsValue, channelCountValue) {
128        let sampleRate = sampleRateValue;
129        let dataLen = sampleRate * 1000;
130        let sampleBits = sampleBitsValue * 8 + 8 // 采样格式
131        let channelCount = channelCountValue; // 单声道
132        let offset = 0;
133        let buffer = new ArrayBuffer(44);
134        let data = new DataView(buffer);
135        // 资源交换文件标识符
136        this.writeString(data, offset, 'RIFF');
137        offset += 4;
138        // 下个地址开始到文件尾总字节数,即文件大小-8
139        data.setUint32(offset, 36 + dataLen, true);
140        offset += 4;
141        // WAV文件标志
142        this.writeString(data, offset, 'WAVE');
143        offset += 4;
144        // 波形格式标志
145        this.writeString(data, offset, 'fmt ');
146        offset += 4;
147        // 过滤字节,一般为 0x10 = 16
148        data.setUint32(offset, 16, true);
149        offset += 4;
150        // 格式类别 (PCM形式采样数据)
151        data.setUint16(offset, 1, true);
152        offset += 2;
153        // 通道数
154        data.setUint16(offset, channelCount, true);
155        offset += 2;
156        // 采样率,每秒样本数,表示每个通道的播放速度
157        data.setUint32(offset, sampleRate, true);
158        offset += 4;
159        // 波形数据传输率 (每秒平均字节数) 单声道×每秒数据位数×每样本数据位/8
160        data.setUint32(offset, channelCount * sampleRate * (sampleBits / 8), true);
161        offset += 4;
162        // 快数据调整数 采样一次占用字节数 单声道×每样本的数据位数/8
163        data.setUint16(offset, channelCount * (sampleBits / 8), true);
164        offset += 2;
165        // 每样本数据位数
166        data.setUint16(offset, sampleBits, true);
167        offset += 2;
168        // 数据标识符
169        this.writeString(data, offset, 'data');
170        offset += 4;
171        // 采样数据总数,即数据总大小-44
172        data.setUint32(offset, dataLen, true);
173        offset += 4;
174        return data;
175    }
176
177    writeString(data, offset, str) {
178        for (let i = 0; i < str.length; i++) {
179            data.setUint8(offset + i, str.charCodeAt(i));
180        }
181    }
182}
183
184export default new mediaPlay()
185
186