-
Notifications
You must be signed in to change notification settings - Fork 1
Expand file tree
/
Copy pathindex.html
More file actions
155 lines (138 loc) · 4.5 KB
/
Copy pathindex.html
File metadata and controls
155 lines (138 loc) · 4.5 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<title>Audio Visulizer</title>
<style type="text/css">
html, body {
margin: 0;
font-family: arial, "Microsoft YaHei";
background-color: #272822;
color: #FEFEFE;
}
#fileWrapper{
transition:all 0.5s ease;
}
#fileWrapper:hover{
opacity: 1!important;
}
#visualizer_wrapper{
text-align: center;
}
footer{
position: fixed;
bottom: 2px;
color:#aaa;
}
</style>
</head>
<body onload='init()'>
<div id="main-content-container" >
<button onclick="start()">start</button>
<button onclick="stop()">stop</button>
<div id="info"></div>
<div id="visualizer_wrapper">
<canvas id='canvas' width="800" height="350"></canvas>
</div>
</div>
<script src="animation.js"></script>
<script type="script/worker" id="workerCode">
</script>
<script>
const url = 'ws://109.123.120.200:5000';
let ws, player;
const init = () => {
console.log(`[${new Date()}] AudioCapture App Start...`);
ws = new WebSocket(url);
// 接收二进制数据,需要配置binaryType
ws.binaryType = 'arraybuffer';
player = new StreamAnalyser();
// 绑定链接open & close 事件
ws.addEventListener('open', event => (console.log(`[${new Date()}] ws server open sucess!`)));
ws.addEventListener('close', event => (console.log(`[${new Date()}] ws server closed!`)));
ws.addEventListener('message', event => {
let raw = new Uint8Array(event.data);
player.feed(raw);
});
}
let _status;
const start = () => {
ws.send('start');
_status = 1;
setTimeout(() => {
const {channels, sampleRate} = player.getAudioInfo();
document.getElementById('info').innerHTML = `<div>Num of Channels: ${channels}</div>
<div>Sample Rate: ${sampleRate}</div>`;
}, 1000);
// draw canvas animation
drawSpectrum();
}
const stop = () => {
_status = 0;
player.stop();
}
let animationId,
allCapsReachBottom = false,
canvas = document.getElementById('canvas'),
cwidth = canvas.width,
cheight = canvas.height - 2,
meterWidth = 10, //width of the meters in the spectrum
gap = 2, //gap between meters
capHeight = 2,
capStyle = '#fff',
meterNum = 800 / (10 + 2), //count of the meters
capYPositionArray = []; ////store the vertical position of hte caps for the preivous frame
ctx = canvas.getContext('2d'),
gradient = ctx.createLinearGradient(0, 0, 0, 300);
gradient.addColorStop(1, '#0f0');
gradient.addColorStop(0.5, '#ff0');
gradient.addColorStop(0, '#f00');
const drawSpectrum = () => {
let analyser = player.getAnalyzser();
let array = new Uint8Array(analyser.frequencyBinCount);
analyser.getByteFrequencyData(array);
if (_status === 0) {
// fix when sounds end the value still not back to zero
for (let i = array.length - 1; i >= 0; i--) {
array[i] = 0;
}
allCapsReachBottom = true;
for (let i = capYPositionArray.length - 1; i >= 0; i--) {
allCapsReachBottom = allCapsReachBottom && (capYPositionArray[i] === 0);
}
if (allCapsReachBottom) {
cancelAnimationFrame(animationId);
return;
}
}
let step = Math.round(array.length / meterNum);//sample limited data from the total array
ctx.clearRect(0, 0, cwidth, cheight);
for (let i = 0; i < meterNum; i++) {
let value = array[i * step];
if (capYPositionArray.length < Math.round(meterNum)) {
capYPositionArray.push(value);
}
ctx.fillStyle = capStyle;
//draw the cap, with transition effect
if (value < capYPositionArray[i]) {
ctx.fillRect(i * 12, cheight - (--capYPositionArray[i]), meterWidth, capHeight);
} else {
ctx.fillRect(i * 12, cheight - value, meterWidth, capHeight);
capYPositionArray[i] = value;
}
ctx.fillStyle = gradient; // set the fillstyle to gradient for a better look
ctx.fillRect(i * 12 /*meterWidth+gap*/, cheight - value + capHeight, meterWidth, cheight); // the meter
}
animationId = requestAnimationFrame(drawSpectrum);
}
</script>
<script>
(async () => {
// new feature detect.
document.querySelector('main').classList.toggle(
'supported', ('OffscreenCanvas' in window));
})();
</script>
<script type="text/javascript" src="./dist/wav-stream-analyser.min.js"></script>
</body>
</html>