@siteed/expo-audio-stream 1.0.1 → 1.0.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (142) hide show
  1. package/.size-limit.json +6 -0
  2. package/README.md +6 -6
  3. package/android/build.gradle +5 -0
  4. package/android/src/main/java/net/siteed/audiostream/AudioAnalysisData.kt +120 -0
  5. package/android/src/main/java/net/siteed/audiostream/AudioFileHandler.kt +34 -4
  6. package/android/src/main/java/net/siteed/audiostream/AudioProcessor.kt +635 -0
  7. package/android/src/main/java/net/siteed/audiostream/AudioRecorderManager.kt +194 -79
  8. package/android/src/main/java/net/siteed/audiostream/Constants.kt +1 -0
  9. package/android/src/main/java/net/siteed/audiostream/ExpoAudioStreamModule.kt +48 -2
  10. package/android/src/main/java/net/siteed/audiostream/FFT.kt +44 -0
  11. package/android/src/main/java/net/siteed/audiostream/Features.kt +56 -0
  12. package/android/src/main/java/net/siteed/audiostream/RecordingConfig.kt +12 -0
  13. package/android/src/main/test/java/net/siteed/audiostream/AudioProcessorTest.kt +56 -0
  14. package/app.plugin.js +1 -1
  15. package/build/AudioAnalysis/AudioAnalysis.types.d.ts +76 -0
  16. package/build/AudioAnalysis/AudioAnalysis.types.d.ts.map +1 -0
  17. package/build/AudioAnalysis/AudioAnalysis.types.js +3 -0
  18. package/build/AudioAnalysis/AudioAnalysis.types.js.map +1 -0
  19. package/build/AudioAnalysis/extractAudioAnalysis.d.ts +4 -0
  20. package/build/AudioAnalysis/extractAudioAnalysis.d.ts.map +1 -0
  21. package/build/AudioAnalysis/extractAudioAnalysis.js +101 -0
  22. package/build/AudioAnalysis/extractAudioAnalysis.js.map +1 -0
  23. package/build/AudioAnalysis/extractWaveform.d.ts +8 -0
  24. package/build/AudioAnalysis/extractWaveform.d.ts.map +1 -0
  25. package/build/AudioAnalysis/extractWaveform.js +14 -0
  26. package/build/AudioAnalysis/extractWaveform.js.map +1 -0
  27. package/build/AudioRecorder.provider.d.ts +14 -1
  28. package/build/AudioRecorder.provider.d.ts.map +1 -1
  29. package/build/AudioRecorder.provider.js +18 -5
  30. package/build/AudioRecorder.provider.js.map +1 -1
  31. package/build/ExpoAudioStream.native.d.ts +3 -0
  32. package/build/ExpoAudioStream.native.d.ts.map +1 -0
  33. package/build/ExpoAudioStream.native.js +6 -0
  34. package/build/ExpoAudioStream.native.js.map +1 -0
  35. package/build/ExpoAudioStream.types.d.ts +35 -20
  36. package/build/ExpoAudioStream.types.d.ts.map +1 -1
  37. package/build/ExpoAudioStream.types.js.map +1 -1
  38. package/build/ExpoAudioStream.web.d.ts +42 -0
  39. package/build/ExpoAudioStream.web.d.ts.map +1 -0
  40. package/build/ExpoAudioStream.web.js +185 -0
  41. package/build/ExpoAudioStream.web.js.map +1 -0
  42. package/build/ExpoAudioStreamModule.d.ts +2 -2
  43. package/build/ExpoAudioStreamModule.d.ts.map +1 -1
  44. package/build/ExpoAudioStreamModule.js +16 -3
  45. package/build/ExpoAudioStreamModule.js.map +1 -1
  46. package/build/WebRecorder.web.d.ts +51 -0
  47. package/build/WebRecorder.web.d.ts.map +1 -0
  48. package/build/WebRecorder.web.js +288 -0
  49. package/build/WebRecorder.web.js.map +1 -0
  50. package/build/constants.d.ts +11 -0
  51. package/build/constants.d.ts.map +1 -0
  52. package/build/constants.js +14 -0
  53. package/build/constants.js.map +1 -0
  54. package/build/events.d.ts +6 -0
  55. package/build/events.d.ts.map +1 -0
  56. package/build/events.js +15 -0
  57. package/build/events.js.map +1 -0
  58. package/build/index.d.ts +8 -7
  59. package/build/index.d.ts.map +1 -1
  60. package/build/index.js +7 -14
  61. package/build/index.js.map +1 -1
  62. package/build/logger.d.ts +9 -0
  63. package/build/logger.d.ts.map +1 -0
  64. package/build/logger.js +17 -0
  65. package/build/logger.js.map +1 -0
  66. package/build/useAudioRecorder.d.ts +37 -0
  67. package/build/useAudioRecorder.d.ts.map +1 -0
  68. package/build/useAudioRecorder.js +271 -0
  69. package/build/useAudioRecorder.js.map +1 -0
  70. package/build/utils/convertPCMToFloat32.d.ts +11 -0
  71. package/build/utils/convertPCMToFloat32.d.ts.map +1 -0
  72. package/build/utils/convertPCMToFloat32.js +41 -0
  73. package/build/utils/convertPCMToFloat32.js.map +1 -0
  74. package/build/utils/encodingToBitDepth.d.ts +5 -0
  75. package/build/utils/encodingToBitDepth.d.ts.map +1 -0
  76. package/build/utils/encodingToBitDepth.js +13 -0
  77. package/build/utils/encodingToBitDepth.js.map +1 -0
  78. package/build/utils/getWavFileInfo.d.ts +25 -0
  79. package/build/utils/getWavFileInfo.d.ts.map +1 -0
  80. package/build/utils/getWavFileInfo.js +89 -0
  81. package/build/utils/getWavFileInfo.js.map +1 -0
  82. package/build/utils/writeWavHeader.d.ts +9 -0
  83. package/build/utils/writeWavHeader.d.ts.map +1 -0
  84. package/build/utils/writeWavHeader.js +41 -0
  85. package/build/utils/writeWavHeader.js.map +1 -0
  86. package/build/workers/InlineFeaturesExtractor.web.d.ts +2 -0
  87. package/build/workers/InlineFeaturesExtractor.web.d.ts.map +1 -0
  88. package/build/workers/InlineFeaturesExtractor.web.js +303 -0
  89. package/build/workers/InlineFeaturesExtractor.web.js.map +1 -0
  90. package/build/workers/inlineAudioWebWorker.web.d.ts +2 -0
  91. package/build/workers/inlineAudioWebWorker.web.d.ts.map +1 -0
  92. package/build/workers/inlineAudioWebWorker.web.js +243 -0
  93. package/build/workers/inlineAudioWebWorker.web.js.map +1 -0
  94. package/expo-module.config.json +13 -4
  95. package/ios/AudioAnalysisData.swift +39 -0
  96. package/ios/AudioProcessingHelpers.swift +59 -0
  97. package/ios/AudioProcessor.swift +317 -0
  98. package/ios/AudioStreamError.swift +7 -0
  99. package/ios/AudioStreamManager.swift +243 -54
  100. package/ios/AudioStreamManagerDelegate.swift +4 -0
  101. package/ios/DataPoint.swift +41 -0
  102. package/ios/ExpoAudioStreamModule.swift +198 -6
  103. package/ios/Features.swift +44 -0
  104. package/ios/RecordingResult.swift +19 -0
  105. package/ios/RecordingSettings.swift +13 -0
  106. package/ios/WaveformExtractor.swift +105 -0
  107. package/package.json +13 -12
  108. package/plugin/tsconfig.json +13 -8
  109. package/publish.sh +8 -0
  110. package/src/AudioAnalysis/AudioAnalysis.types.ts +85 -0
  111. package/src/AudioAnalysis/extractAudioAnalysis.ts +136 -0
  112. package/src/AudioAnalysis/extractWaveform.ts +25 -0
  113. package/src/AudioRecorder.provider.tsx +36 -8
  114. package/src/ExpoAudioStream.native.ts +6 -0
  115. package/src/ExpoAudioStream.types.ts +50 -25
  116. package/src/ExpoAudioStream.web.ts +229 -0
  117. package/src/ExpoAudioStreamModule.ts +22 -3
  118. package/src/WebRecorder.web.ts +416 -0
  119. package/src/constants.ts +18 -0
  120. package/src/events.ts +25 -0
  121. package/src/index.ts +14 -29
  122. package/src/logger.ts +26 -0
  123. package/src/useAudioRecorder.tsx +415 -0
  124. package/src/utils/convertPCMToFloat32.ts +48 -0
  125. package/src/utils/encodingToBitDepth.ts +18 -0
  126. package/src/utils/getWavFileInfo.ts +125 -0
  127. package/src/utils/writeWavHeader.ts +56 -0
  128. package/src/workers/InlineFeaturesExtractor.web.tsx +302 -0
  129. package/src/workers/inlineAudioWebWorker.web.tsx +242 -0
  130. package/build/ExpoAudioStreamModule.web.d.ts +0 -37
  131. package/build/ExpoAudioStreamModule.web.d.ts.map +0 -1
  132. package/build/ExpoAudioStreamModule.web.js +0 -156
  133. package/build/ExpoAudioStreamModule.web.js.map +0 -1
  134. package/build/useAudioRecording.d.ts +0 -23
  135. package/build/useAudioRecording.d.ts.map +0 -1
  136. package/build/useAudioRecording.js +0 -189
  137. package/build/useAudioRecording.js.map +0 -1
  138. package/docs/demo.gif +0 -0
  139. package/release-it.js +0 -18
  140. package/src/ExpoAudioStreamModule.web.ts +0 -181
  141. package/src/useAudioRecording.ts +0 -268
  142. package/yarn-error.log +0 -7793
@@ -0,0 +1,6 @@
1
+ [
2
+ {
3
+ "path": "./build/index.js",
4
+ "limit": "100000 ms"
5
+ }
6
+ ]
package/README.md CHANGED
@@ -1,6 +1,6 @@
1
1
  # @siteed/expo-audio-stream
2
2
 
3
- `@siteed/expo-audio-stream` is a comprehensive library designed to facilitate real-time audio processing and streaming across iOS, Android, and web platforms. This library leverages Expo's robust ecosystem to simplify the implementation of audio recording and streaming functionalities within React Native applications.
3
+ `@siteed/expo-audio-stream` is a comprehensive library designed to facilitate real-time audio processing and streaming across iOS, Android, and web platforms.
4
4
 
5
5
  ## Features
6
6
 
@@ -11,7 +11,7 @@
11
11
  - Listeners for audio data events with detailed event payloads.
12
12
  - Utility functions for recording control and file management.
13
13
 
14
- ## Example Application
14
+ ## Playground Example Application
15
15
 
16
16
  The project comes with a fully functional example application that demonstrates how to use the library in a real-world scenario.
17
17
 
@@ -23,9 +23,9 @@ To try it:
23
23
  git clone https://github.com/deeeed/expo-audio-stream.git
24
24
  cd expo-audio-stream
25
25
  yarn
26
- yarn example ios
27
- yarn example android
28
- yarn example web
26
+ yarn playground ios
27
+ yarn playground android
28
+ yarn playground web
29
29
  ```
30
30
 
31
31
  ## Installation
@@ -60,7 +60,7 @@ This library provides two hooks: `useAudioRecorder` for standalone use and `useS
60
60
 
61
61
  ### Standalone Recording
62
62
 
63
- The `example/` folder contains a fully functional React Native application demonstrating how to integrate and use `useAudioRecorder` from `@siteed/expo-audio-stream`. This includes starting and stopping recordings, handling permissions, and processing live audio data.
63
+ The `playground/` folder contains a fully functional React Native application demonstrating how to integrate and use `useAudioRecorder` from `@siteed/expo-audio-stream`. This includes starting and stopping recordings, handling permissions, and processing live audio data.
64
64
 
65
65
 
66
66
  #### Standalone Usage
@@ -89,4 +89,9 @@ repositories {
89
89
  dependencies {
90
90
  implementation project(':expo-modules-core')
91
91
  implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:${getKotlinVersion()}"
92
+
93
+ // Add testing dependencies
94
+ testImplementation 'junit:junit:4.13.2'
95
+ testImplementation 'org.jetbrains.kotlin:kotlin-test:1.8.10'
96
+ testImplementation 'org.jetbrains.kotlin:kotlin-test-junit:1.8.10'
92
97
  }
@@ -0,0 +1,120 @@
1
+ // net/siteed/audiostream/AudioAnalysisData.kt
2
+ package net.siteed.audiostream
3
+
4
+ import android.os.Bundle
5
+ import androidx.core.os.bundleOf
6
+
7
+ data class DataPoint(
8
+ val id: Long,
9
+ val amplitude: Float,
10
+ val activeSpeech: Boolean? = null,
11
+ val dB: Float? = null,
12
+ val silent: Boolean? = null,
13
+ val features: Features? = null,
14
+ val startTime: Float? = null,
15
+ val endTime: Float? = null,
16
+ val startPosition: Int? = null,
17
+ val endPosition: Int? = null,
18
+ val samples: Int = 0,
19
+ val speaker: Int? = null
20
+ ) {
21
+ fun toDictionary(): Map<String, Any?> {
22
+ return mapOf(
23
+ "id" to id,
24
+ "amplitude" to amplitude,
25
+ "activeSpeech" to activeSpeech,
26
+ "dB" to dB,
27
+ "silent" to silent,
28
+ "features" to features?.toDictionary(),
29
+ "startTime" to startTime,
30
+ "endTime" to endTime,
31
+ "startPosition" to startPosition,
32
+ "endPosition" to endPosition,
33
+ "samples" to samples,
34
+ "speaker" to speaker
35
+ )
36
+ }
37
+
38
+ fun toBundle(): Bundle {
39
+ return bundleOf(
40
+ "id" to id,
41
+ "amplitude" to amplitude,
42
+ "activeSpeech" to activeSpeech,
43
+ "dB" to dB,
44
+ "silent" to silent,
45
+ "features" to features?.toBundle(),
46
+ "startTime" to startTime,
47
+ "endTime" to endTime,
48
+ "startPosition" to startPosition,
49
+ "endPosition" to endPosition,
50
+ "samples" to samples,
51
+ "speaker" to speaker
52
+ )
53
+ }
54
+ }
55
+
56
+ data class AudioAnalysisData(
57
+ val pointsPerSecond: Double,
58
+ val durationMs: Int,
59
+ val bitDepth: Int,
60
+ val numberOfChannels: Int,
61
+ val sampleRate: Int,
62
+ val samples: Int,
63
+ val dataPoints: List<DataPoint>,
64
+ val amplitudeRange: AmplitudeRange,
65
+ val speakerChanges: List<SpeakerChange>,
66
+ val extractionTimeMs: Float
67
+ ) {
68
+ data class AmplitudeRange(val min: Float, val max: Float) {
69
+ fun toDictionary(): Map<String, Float> {
70
+ return mapOf("min" to min, "max" to max)
71
+ }
72
+
73
+ fun toBundle(): Bundle {
74
+ return bundleOf("min" to min, "max" to max)
75
+ }
76
+ }
77
+
78
+ data class SpeakerChange(val timestamp: Float, val speaker: Int) {
79
+ fun toDictionary(): Map<String, Any> {
80
+ return mapOf("timestamp" to timestamp, "speaker" to speaker)
81
+ }
82
+
83
+ fun toBundle(): Bundle {
84
+ return bundleOf("timestamp" to timestamp, "speaker" to speaker)
85
+ }
86
+ }
87
+
88
+ fun toDictionary(): Map<String, Any> {
89
+ return mapOf(
90
+ "pointsPerSecond" to pointsPerSecond,
91
+ "durationMs" to durationMs,
92
+ "bitDepth" to bitDepth,
93
+ "numberOfChannels" to numberOfChannels,
94
+ "sampleRate" to sampleRate,
95
+ "samples" to samples,
96
+ "dataPoints" to dataPoints.map { it.toDictionary() },
97
+ "amplitudeRange" to amplitudeRange.toDictionary(),
98
+ "speakerChanges" to speakerChanges.map { it.toDictionary() },
99
+ "extractionTimeMs" to extractionTimeMs
100
+ )
101
+ }
102
+
103
+ fun toBundle(): Bundle {
104
+ val dataPointsBundleArray = dataPoints.map { it.toBundle() }.toTypedArray()
105
+ val speakerChangesBundleArray = speakerChanges.map { it.toBundle() }.toTypedArray()
106
+
107
+ return bundleOf(
108
+ "pointsPerSecond" to pointsPerSecond,
109
+ "durationMs" to durationMs,
110
+ "bitDepth" to bitDepth,
111
+ "numberOfChannels" to numberOfChannels,
112
+ "sampleRate" to sampleRate,
113
+ "samples" to samples,
114
+ "dataPoints" to dataPointsBundleArray,
115
+ "amplitudeRange" to amplitudeRange.toBundle(),
116
+ "speakerChanges" to speakerChangesBundleArray,
117
+ "extractionTimeMs" to extractionTimeMs
118
+ )
119
+ }
120
+ }
@@ -14,25 +14,55 @@ class AudioFileHandler(private val filesDir: File) {
14
14
 
15
15
  // RIFF/WAVE header
16
16
  "RIFF".toByteArray().copyInto(header, 0)
17
- header[4] = 0 // Size will be updated later
17
+ // (file size - 8) to be updated later
18
+ header[4] = 0 // Placeholder
19
+ header[5] = 0 // Placeholder
20
+ header[6] = 0 // Placeholder
21
+ header[7] = 0 // Placeholder
18
22
  "WAVE".toByteArray().copyInto(header, 8)
19
23
  "fmt ".toByteArray().copyInto(header, 12)
20
24
 
21
25
  // 16 for PCM
22
26
  header[16] = 16
27
+ header[17] = 0
28
+ header[18] = 0
29
+ header[19] = 0
30
+
31
+ // PCM format ID
23
32
  header[20] = 1 // Audio format 1 for PCM (not compressed)
24
- header[22] = channels.toByte()
33
+ header[21] = 0
34
+
35
+ // Number of channels
36
+ header[22] = (channels and 0xff).toByte()
37
+ header[23] = (channels shr 8 and 0xff).toByte()
38
+
39
+ // Sample rate
25
40
  header[24] = (sampleRateInHz and 0xff).toByte()
26
41
  header[25] = (sampleRateInHz shr 8 and 0xff).toByte()
27
42
  header[26] = (sampleRateInHz shr 16 and 0xff).toByte()
28
43
  header[27] = (sampleRateInHz shr 24 and 0xff).toByte()
44
+
45
+ // Byte rate
29
46
  header[28] = (byteRate and 0xff).toByte()
30
47
  header[29] = (byteRate shr 8 and 0xff).toByte()
31
48
  header[30] = (byteRate shr 16 and 0xff).toByte()
32
49
  header[31] = (byteRate shr 24 and 0xff).toByte()
33
- header[32] = blockAlign.toByte()
34
- header[34] = bitDepth.toByte()
50
+
51
+ // Block align
52
+ header[32] = (blockAlign and 0xff).toByte()
53
+ header[33] = (blockAlign shr 8 and 0xff).toByte()
54
+
55
+ // Bits per sample
56
+ header[34] = (bitDepth and 0xff).toByte()
57
+ header[35] = (bitDepth shr 8 and 0xff).toByte()
58
+
59
+ // Data chunk
35
60
  "data".toByteArray().copyInto(header, 36)
61
+ // Data size to be updated later
62
+ header[40] = 0 // Placeholder
63
+ header[41] = 0 // Placeholder
64
+ header[42] = 0 // Placeholder
65
+ header[43] = 0 // Placeholder
36
66
 
37
67
  out.write(header, 0, 44)
38
68
  }