awacke1 commited on
Commit
0145c6e
·
verified ·
1 Parent(s): 17b0e6f

Update index.html

Browse files
Files changed (1) hide show
  1. index.html +131 -21
index.html CHANGED
@@ -1,29 +1,139 @@
1
  <!DOCTYPE html>
2
  <html lang="en">
3
-
4
  <head>
5
- <meta charset="UTF-8" />
6
- <link rel="stylesheet" href="style.css" />
7
-
8
- <meta name="viewport" content="width=device-width, initial-scale=1.0" />
9
- <title>Transformers.js - Object Detection</title>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
10
  </head>
11
-
12
  <body>
13
- <h1>Object Detection w/ 🤗 Transformers.js</h1>
14
- <label id="container" for="upload">
15
- <svg width="25" height="25" viewBox="0 0 25 25" fill="none" xmlns="http://www.w3.org/2000/svg">
16
- <path fill="#000"
17
- d="M3.5 24.3a3 3 0 0 1-1.9-.8c-.5-.5-.8-1.2-.8-1.9V2.9c0-.7.3-1.3.8-1.9.6-.5 1.2-.7 2-.7h18.6c.7 0 1.3.2 1.9.7.5.6.7 1.2.7 2v18.6c0 .7-.2 1.4-.7 1.9a3 3 0 0 1-2 .8H3.6Zm0-2.7h18.7V2.9H3.5v18.7Zm2.7-2.7h13.3c.3 0 .5 0 .6-.3v-.7l-3.7-5a.6.6 0 0 0-.6-.2c-.2 0-.4 0-.5.3l-3.5 4.6-2.4-3.3a.6.6 0 0 0-.6-.3c-.2 0-.4.1-.5.3l-2.7 3.6c-.1.2-.2.4 0 .7.1.2.3.3.6.3Z">
18
- </path>
19
- </svg>
20
- Click to upload image
21
- <label id="example">(or try example)</label>
22
- </label>
23
- <label id="status">Loading model...</label>
24
- <input id="upload" type="file" accept="image/*" />
25
 
26
- <script src="index.js" type="module"></script>
27
- </body>
 
 
 
 
 
 
28
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
29
  </html>
 
1
  <!DOCTYPE html>
2
  <html lang="en">
 
3
  <head>
4
+ <meta charset="UTF-8">
5
+ <meta name="viewport" content="width=device-width, initial-scale=1.0">
6
+ <title>ASR Client</title>
7
+ <script src="https://cdnjs.cloudflare.com/ajax/libs/transformers/1.4.1/transformers.min.js"></script>
8
+ <style>
9
+ body {
10
+ font-family: system-ui, -apple-system, sans-serif;
11
+ max-width: 800px;
12
+ margin: 2rem auto;
13
+ padding: 0 1rem;
14
+ }
15
+ .container {
16
+ display: flex;
17
+ flex-direction: column;
18
+ gap: 1rem;
19
+ align-items: center;
20
+ }
21
+ #status {
22
+ margin: 1rem 0;
23
+ padding: 0.5rem;
24
+ border-radius: 4px;
25
+ }
26
+ #transcription {
27
+ width: 100%;
28
+ min-height: 200px;
29
+ padding: 1rem;
30
+ border: 1px solid #ccc;
31
+ border-radius: 4px;
32
+ margin: 1rem 0;
33
+ }
34
+ button {
35
+ padding: 0.5rem 1rem;
36
+ font-size: 1rem;
37
+ cursor: pointer;
38
+ background: #0066ff;
39
+ color: white;
40
+ border: none;
41
+ border-radius: 4px;
42
+ }
43
+ button:disabled {
44
+ background: #cccccc;
45
+ cursor: not-allowed;
46
+ }
47
+ .status-loading {
48
+ background: #fff3cd;
49
+ }
50
+ .status-ready {
51
+ background: #d4edda;
52
+ }
53
+ .status-error {
54
+ background: #f8d7da;
55
+ }
56
+ </style>
57
  </head>
 
58
  <body>
59
+ <div class="container">
60
+ <h1>Speech Recognition Client</h1>
61
+ <div id="status">Loading model...</div>
62
+ <button id="startButton" disabled>Start Recording</button>
63
+ <div id="transcription"></div>
64
+ </div>
 
 
 
 
 
 
65
 
66
+ <script type="module">
67
+ import { pipeline } from 'https://cdn.jsdelivr.net/npm/@xenova/[email protected]/+esm';
68
+
69
+ let isRecording = false;
70
+ let model = null;
71
+ const startButton = document.getElementById('startButton');
72
+ const statusDiv = document.getElementById('status');
73
+ const transcriptionDiv = document.getElementById('transcription');
74
 
75
+ // Initialize the model
76
+ async function initializeModel() {
77
+ try {
78
+ statusDiv.textContent = 'Loading model...';
79
+ statusDiv.className = 'status-loading';
80
+
81
+ model = await pipeline('automatic-speech-recognition', 'Xenova/whisper-tiny');
82
+
83
+ statusDiv.textContent = 'Model ready! Click Start Recording to begin.';
84
+ statusDiv.className = 'status-ready';
85
+ startButton.disabled = false;
86
+ } catch (error) {
87
+ statusDiv.textContent = 'Error loading model: ' + error.message;
88
+ statusDiv.className = 'status-error';
89
+ }
90
+ }
91
+
92
+ // Handle recording
93
+ async function toggleRecording() {
94
+ if (!isRecording) {
95
+ try {
96
+ const stream = await navigator.mediaDevices.getUserMedia({ audio: true });
97
+ isRecording = true;
98
+ startButton.textContent = 'Stop Recording';
99
+ statusDiv.textContent = 'Recording...';
100
+ statusDiv.className = 'status-loading';
101
+
102
+ // Create processor and start processing audio
103
+ const audioTrack = stream.getAudioTracks()[0];
104
+ const processor = new MediaStreamTrackProcessor({ track: audioTrack });
105
+
106
+ const transformer = new TransformStream({
107
+ async transform(chunk, controller) {
108
+ try {
109
+ const result = await model(chunk.data);
110
+ if (result && result.text) {
111
+ transcriptionDiv.textContent += ' ' + result.text;
112
+ }
113
+ } catch (error) {
114
+ console.error('Error processing audio:', error);
115
+ }
116
+ }
117
+ });
118
+
119
+ await processor.readable.pipeTo(transformer.writable);
120
+ } catch (error) {
121
+ statusDiv.textContent = 'Error accessing microphone: ' + error.message;
122
+ statusDiv.className = 'status-error';
123
+ isRecording = false;
124
+ }
125
+ } else {
126
+ // Stop recording
127
+ isRecording = false;
128
+ startButton.textContent = 'Start Recording';
129
+ statusDiv.textContent = 'Recording stopped. Click Start Recording to begin again.';
130
+ statusDiv.className = 'status-ready';
131
+ }
132
+ }
133
+
134
+ // Initialize the app
135
+ startButton.addEventListener('click', toggleRecording);
136
+ initializeModel();
137
+ </script>
138
+ </body>
139
  </html>