├── logo ├── icon.png ├── icon-nuget.png ├── verticalversion.png ├── horizontalversion.png └── audiorecorder-github-logo.png ├── Samples ├── Native │ ├── AudioRecord.UWP │ │ ├── Assets │ │ │ ├── StoreLogo.png │ │ │ ├── SplashScreen.scale-200.png │ │ │ ├── LockScreenLogo.scale-200.png │ │ │ ├── Square44x44Logo.scale-200.png │ │ │ ├── Wide310x150Logo.scale-200.png │ │ │ ├── Square150x150Logo.scale-200.png │ │ │ └── Square44x44Logo.targetsize-24_altform-unplated.png │ │ ├── App.xaml │ │ ├── Properties │ │ │ ├── AssemblyInfo.cs │ │ │ └── Default.rd.xml │ │ ├── MainPage.xaml │ │ ├── Package.appxmanifest │ │ ├── MainPage.xaml.cs │ │ └── App.xaml.cs │ ├── AudioRecord.Android │ │ ├── Resources │ │ │ ├── mipmap-hdpi │ │ │ │ ├── ic_launcher.png │ │ │ │ ├── ic_launcher_round.png │ │ │ │ └── ic_launcher_foreground.png │ │ │ ├── mipmap-mdpi │ │ │ │ ├── ic_launcher.png │ │ │ │ ├── ic_launcher_round.png │ │ │ │ └── ic_launcher_foreground.png │ │ │ ├── values │ │ │ │ ├── ic_launcher_background.xml │ │ │ │ ├── Strings.xml │ │ │ │ ├── colors.xml │ │ │ │ └── styles.xml │ │ │ ├── mipmap-xhdpi │ │ │ │ ├── ic_launcher.png │ │ │ │ ├── ic_launcher_round.png │ │ │ │ └── ic_launcher_foreground.png │ │ │ ├── mipmap-xxhdpi │ │ │ │ ├── ic_launcher.png │ │ │ │ ├── ic_launcher_round.png │ │ │ │ └── ic_launcher_foreground.png │ │ │ ├── mipmap-xxxhdpi │ │ │ │ ├── ic_launcher.png │ │ │ │ ├── ic_launcher_round.png │ │ │ │ └── ic_launcher_foreground.png │ │ │ ├── mipmap-anydpi-v26 │ │ │ │ ├── ic_launcher.xml │ │ │ │ └── ic_launcher_round.xml │ │ │ ├── layout │ │ │ │ └── activity_main.axml │ │ │ └── AboutResources.txt │ │ ├── Assets │ │ │ └── AboutAssets.txt │ │ ├── Properties │ │ │ ├── AndroidManifest.xml │ │ │ └── AssemblyInfo.cs │ │ ├── MainActivity.cs │ │ └── AudioRecord.Android.csproj │ └── AudioRecord.iOS │ │ ├── Assets.xcassets │ │ └── AppIcon.appiconset │ │ │ ├── Icon120.png │ │ │ ├── Icon152.png │ │ │ ├── Icon167.png │ │ │ ├── Icon180.png │ │ │ ├── Icon20.png │ │ │ ├── Icon29.png │ │ │ ├── Icon40.png │ │ │ ├── Icon58.png │ │ │ ├── Icon60.png │ │ │ ├── Icon76.png │ │ │ ├── Icon80.png │ │ │ ├── Icon87.png │ │ │ ├── Icon1024.png │ │ │ └── Contents.json │ │ ├── Entitlements.plist │ │ ├── Main.cs │ │ ├── Properties │ │ └── AssemblyInfo.cs │ │ ├── LaunchScreen.storyboard │ │ ├── Info.plist │ │ ├── ViewController.designer.cs │ │ ├── AppDelegate.cs │ │ ├── ViewController.cs │ │ ├── Resources │ │ └── LaunchScreen.xib │ │ ├── Main.storyboard │ │ └── AudioRecord.iOS.csproj └── Forms │ ├── AudioRecord.Forms.iOS │ ├── Resources │ │ ├── Default.png │ │ ├── Default@2x.png │ │ ├── Default-568h@2x.png │ │ ├── Default-Portrait.png │ │ ├── Default-Portrait@2x.png │ │ └── LaunchScreen.storyboard │ ├── Assets.xcassets │ │ └── AppIcon.appiconset │ │ │ ├── Icon120.png │ │ │ ├── Icon152.png │ │ │ ├── Icon167.png │ │ │ ├── Icon180.png │ │ │ ├── Icon20.png │ │ │ ├── Icon29.png │ │ │ ├── Icon40.png │ │ │ ├── Icon58.png │ │ │ ├── Icon60.png │ │ │ ├── Icon76.png │ │ │ ├── Icon80.png │ │ │ ├── Icon87.png │ │ │ ├── Icon1024.png │ │ │ └── Contents.json │ ├── Entitlements.plist │ ├── Main.cs │ ├── Info.plist │ ├── Properties │ │ └── AssemblyInfo.cs │ └── AppDelegate.cs │ ├── AudioRecord.Forms.UWP │ ├── Assets │ │ ├── StoreLogo.backup.png │ │ ├── LargeTile.scale-100.png │ │ ├── LargeTile.scale-200.png │ │ ├── LargeTile.scale-400.png │ │ ├── SmallTile.scale-100.png │ │ ├── SmallTile.scale-200.png │ │ ├── SmallTile.scale-400.png │ │ ├── StoreLogo.scale-100.png │ │ ├── StoreLogo.scale-200.png │ │ ├── StoreLogo.scale-400.png │ │ ├── SplashScreen.scale-100.png │ │ ├── SplashScreen.scale-200.png │ │ ├── SplashScreen.scale-400.png │ │ ├── Square44x44Logo.scale-100.png │ │ ├── Square44x44Logo.scale-200.png │ │ ├── Square44x44Logo.scale-400.png │ │ ├── Wide310x150Logo.scale-100.png │ │ ├── Wide310x150Logo.scale-200.png │ │ ├── Wide310x150Logo.scale-400.png │ │ ├── Square150x150Logo.scale-100.png │ │ ├── Square150x150Logo.scale-200.png │ │ ├── Square150x150Logo.scale-400.png │ │ ├── Square44x44Logo.targetsize-16.png │ │ ├── Square44x44Logo.targetsize-256.png │ │ ├── Square44x44Logo.targetsize-48.png │ │ ├── Square44x44Logo.altform-unplated_targetsize-16.png │ │ ├── Square44x44Logo.altform-unplated_targetsize-256.png │ │ └── Square44x44Logo.altform-unplated_targetsize-48.png │ ├── App.xaml │ ├── MainPage.xaml │ ├── MainPage.xaml.cs │ ├── Properties │ │ ├── AssemblyInfo.cs │ │ └── Default.rd.xml │ ├── Package.appxmanifest │ └── App.xaml.cs │ ├── AudioRecord.Forms.Android │ ├── Resources │ │ ├── mipmap-hdpi │ │ │ ├── Icon.png │ │ │ └── launcher_foreground.png │ │ ├── mipmap-mdpi │ │ │ ├── icon.png │ │ │ └── launcher_foreground.png │ │ ├── mipmap-xhdpi │ │ │ ├── Icon.png │ │ │ └── launcher_foreground.png │ │ ├── mipmap-xxhdpi │ │ │ ├── Icon.png │ │ │ └── launcher_foreground.png │ │ ├── mipmap-xxxhdpi │ │ │ ├── Icon.png │ │ │ └── launcher_foreground.png │ │ ├── mipmap-anydpi-v26 │ │ │ ├── icon.xml │ │ │ └── icon_round.xml │ │ ├── values │ │ │ ├── colors.xml │ │ │ └── styles.xml │ │ ├── layout │ │ │ ├── Toolbar.axml │ │ │ └── Tabbar.axml │ │ └── AboutResources.txt │ ├── Assets │ │ └── AboutAssets.txt │ ├── Properties │ │ ├── AndroidManifest.xml │ │ └── AssemblyInfo.cs │ ├── MainActivity.cs │ └── AudioRecord.Forms.Android.csproj │ └── AudioRecord.Forms │ ├── App.xaml │ ├── AudioRecord.Forms.csproj │ ├── App.xaml.cs │ ├── MainPage.xaml │ └── MainPage.xaml.cs ├── Plugin.AudioRecorder.Shared ├── AudioPlayer.cs ├── AudioStreamDetails.cs ├── Plugin.AudioRecorder.Shared.shproj ├── Plugin.AudioRecorder.Shared.projitems ├── IAudioStream.cs ├── WaveRecorder.cs └── AudioFunctions.cs ├── .editorconfig ├── Plugin.AudioRecorder.iOS ├── packages.config ├── Properties │ └── AssemblyInfo.cs ├── Plugin.AudioRecorder.iOS.csproj ├── AudioRecorderService.cs ├── AudioPlayer.cs └── AudioStream.cs ├── Plugin.AudioRecorder.Android ├── packages.config ├── Properties │ └── AssemblyInfo.cs ├── AudioPlayer.cs ├── AudioRecorderService.cs ├── Plugin.AudioRecorder.Android.csproj └── AudioStream.cs ├── Plugin.AudioRecorder ├── AudioPlayer.cs ├── Plugin.AudioRecorder.csproj ├── AudioRecorderService.cs └── AudioStream.cs ├── Plugin.AudioRecorder.UWP ├── AudioRecorderService.cs ├── Properties │ ├── AssemblyInfo.cs │ └── Plugin.AudioRecorder.UWP.rd.xml ├── AudioPlayer.cs └── Plugin.AudioRecorder.UWP.csproj ├── LICENSE ├── Plugin.AudioRecorder.NuGet └── Plugin.AudioRecorder.NuGet.nuproj └── .gitignore /logo/icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/logo/icon.png -------------------------------------------------------------------------------- /logo/icon-nuget.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/logo/icon-nuget.png -------------------------------------------------------------------------------- /logo/verticalversion.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/logo/verticalversion.png -------------------------------------------------------------------------------- /logo/horizontalversion.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/logo/horizontalversion.png -------------------------------------------------------------------------------- /logo/audiorecorder-github-logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/logo/audiorecorder-github-logo.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.UWP/Assets/StoreLogo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.UWP/Assets/StoreLogo.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Resources/Default.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Resources/Default.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Resources/Default@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Resources/Default@2x.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/StoreLogo.backup.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/StoreLogo.backup.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Resources/Default-568h@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Resources/Default-568h@2x.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.UWP/Assets/SplashScreen.scale-200.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.UWP/Assets/SplashScreen.scale-200.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/LargeTile.scale-100.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/LargeTile.scale-100.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/LargeTile.scale-200.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/LargeTile.scale-200.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/LargeTile.scale-400.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/LargeTile.scale-400.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/SmallTile.scale-100.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/SmallTile.scale-100.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/SmallTile.scale-200.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/SmallTile.scale-200.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/SmallTile.scale-400.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/SmallTile.scale-400.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/StoreLogo.scale-100.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/StoreLogo.scale-100.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/StoreLogo.scale-200.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/StoreLogo.scale-200.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/StoreLogo.scale-400.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/StoreLogo.scale-400.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Resources/Default-Portrait.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Resources/Default-Portrait.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.UWP/Assets/LockScreenLogo.scale-200.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.UWP/Assets/LockScreenLogo.scale-200.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.UWP/Assets/Square44x44Logo.scale-200.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.UWP/Assets/Square44x44Logo.scale-200.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.UWP/Assets/Wide310x150Logo.scale-200.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.UWP/Assets/Wide310x150Logo.scale-200.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-hdpi/Icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-hdpi/Icon.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-mdpi/icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-mdpi/icon.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/SplashScreen.scale-100.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/SplashScreen.scale-100.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/SplashScreen.scale-200.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/SplashScreen.scale-200.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/SplashScreen.scale-400.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/SplashScreen.scale-400.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Resources/Default-Portrait@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Resources/Default-Portrait@2x.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.UWP/Assets/Square150x150Logo.scale-200.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.UWP/Assets/Square150x150Logo.scale-200.png -------------------------------------------------------------------------------- /Plugin.AudioRecorder.Shared/AudioPlayer.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | 3 | namespace Plugin.AudioRecorder 4 | { 5 | public partial class AudioPlayer 6 | { 7 | public event EventHandler FinishedPlaying; 8 | } 9 | } -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-xhdpi/Icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-xhdpi/Icon.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-xxhdpi/Icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-xxhdpi/Icon.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.scale-100.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.scale-100.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.scale-200.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.scale-200.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.scale-400.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.scale-400.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Wide310x150Logo.scale-100.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Wide310x150Logo.scale-100.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Wide310x150Logo.scale-200.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Wide310x150Logo.scale-200.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Wide310x150Logo.scale-400.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Wide310x150Logo.scale-400.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-hdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-hdpi/ic_launcher.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-mdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-mdpi/ic_launcher.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/values/ic_launcher_background.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | #2C3E50 4 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-xxxhdpi/Icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-xxxhdpi/Icon.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Square150x150Logo.scale-100.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Square150x150Logo.scale-100.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Square150x150Logo.scale-200.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Square150x150Logo.scale-200.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Square150x150Logo.scale-400.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Square150x150Logo.scale-400.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-xhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-xhdpi/ic_launcher.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-xxhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-xxhdpi/ic_launcher.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-xxxhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-xxxhdpi/ic_launcher.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/values/Strings.xml: -------------------------------------------------------------------------------- 1 | 2 | AudioRecord.Android 3 | Settings 4 | 5 | -------------------------------------------------------------------------------- /.editorconfig: -------------------------------------------------------------------------------- 1 | # EditorConfig: http://EditorConfig.org 2 | root = true 3 | 4 | [*] 5 | end_of_line = crlf 6 | insert_final_newline = true 7 | charset = utf-8 8 | 9 | [*.cs] 10 | indent_style = tab 11 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.targetsize-16.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.targetsize-16.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.targetsize-256.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.targetsize-256.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.targetsize-48.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.targetsize-48.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon120.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon120.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon152.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon152.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon167.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon167.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon180.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon180.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon20.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon20.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon29.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon29.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon40.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon40.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon58.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon58.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon60.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon60.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon76.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon76.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon80.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon80.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon87.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon87.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-hdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-hdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-mdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-mdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-xhdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-xhdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-xxhdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-xxhdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon1024.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.iOS/Assets.xcassets/AppIcon.appiconset/Icon1024.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon120.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon120.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon152.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon152.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon167.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon167.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon180.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon180.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon20.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon20.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon29.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon29.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon40.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon40.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon58.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon58.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon60.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon60.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon76.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon76.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon80.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon80.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon87.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon87.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-xxxhdpi/ic_launcher_round.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-xxxhdpi/ic_launcher_round.png -------------------------------------------------------------------------------- /Plugin.AudioRecorder.iOS/packages.config: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-hdpi/launcher_foreground.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-hdpi/launcher_foreground.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-mdpi/launcher_foreground.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-mdpi/launcher_foreground.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon1024.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.iOS/Assets.xcassets/AppIcon.appiconset/Icon1024.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-hdpi/ic_launcher_foreground.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-hdpi/ic_launcher_foreground.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-mdpi/ic_launcher_foreground.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-mdpi/ic_launcher_foreground.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-xhdpi/ic_launcher_foreground.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-xhdpi/ic_launcher_foreground.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-xxhdpi/ic_launcher_foreground.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-xxhdpi/ic_launcher_foreground.png -------------------------------------------------------------------------------- /Plugin.AudioRecorder.Android/packages.config: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-xhdpi/launcher_foreground.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-xhdpi/launcher_foreground.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-xxhdpi/launcher_foreground.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-xxhdpi/launcher_foreground.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-xxxhdpi/ic_launcher_foreground.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.Android/Resources/mipmap-xxxhdpi/ic_launcher_foreground.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-xxxhdpi/launcher_foreground.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-xxxhdpi/launcher_foreground.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.UWP/Assets/Square44x44Logo.targetsize-24_altform-unplated.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Native/AudioRecord.UWP/Assets/Square44x44Logo.targetsize-24_altform-unplated.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.altform-unplated_targetsize-16.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.altform-unplated_targetsize-16.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.altform-unplated_targetsize-256.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.altform-unplated_targetsize-256.png -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.altform-unplated_targetsize-48.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NateRickard/Plugin.AudioRecorder/HEAD/Samples/Forms/AudioRecord.Forms.UWP/Assets/Square44x44Logo.altform-unplated_targetsize-48.png -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Entitlements.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Entitlements.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/values/colors.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | #2c3e50 4 | #1B3147 5 | #3498db 6 | 7 | -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.UWP/App.xaml: -------------------------------------------------------------------------------- 1 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/App.xaml: -------------------------------------------------------------------------------- 1 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-anydpi-v26/icon.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms/App.xaml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/values/colors.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | #FFFFFF 4 | #3F51B5 5 | #303F9F 6 | #FF4081 7 | 8 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/mipmap-anydpi-v26/icon_round.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-anydpi-v26/ic_launcher.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/mipmap-anydpi-v26/ic_launcher_round.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /Plugin.AudioRecorder/AudioPlayer.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | 3 | namespace Plugin.AudioRecorder 4 | { 5 | public partial class AudioPlayer 6 | { 7 | public void Play (string pathToAudioFile) => throw new NotImplementedException (); 8 | 9 | public void Pause () => throw new NotImplementedException (); 10 | 11 | public void Play () => throw new NotImplementedException (); 12 | } 13 | } -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms/AudioRecord.Forms.csproj: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | netstandard2.0 5 | 6 | 7 | 8 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/Main.cs: -------------------------------------------------------------------------------- 1 | using UIKit; 2 | 3 | namespace AudioRecord.iOS 4 | { 5 | public class Application 6 | { 7 | // This is the main entry point of the application. 8 | static void Main(string[] args) 9 | { 10 | // if you want to use a different Application Delegate class from "AppDelegate" 11 | // you can specify it here. 12 | UIApplication.Main(args, null, "AppDelegate"); 13 | } 14 | } 15 | } -------------------------------------------------------------------------------- /Plugin.AudioRecorder/Plugin.AudioRecorder.csproj: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | netstandard2.0 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /Plugin.AudioRecorder/AudioRecorderService.cs: -------------------------------------------------------------------------------- 1 | using System.IO; 2 | using System.Threading.Tasks; 3 | 4 | namespace Plugin.AudioRecorder 5 | { 6 | public partial class AudioRecorderService 7 | { 8 | Task GetDefaultFilePath () 9 | { 10 | return Task.FromResult (Path.Combine (Path.GetTempPath (), DefaultFileName)); 11 | } 12 | 13 | void OnRecordingStarting () 14 | { 15 | } 16 | 17 | void OnRecordingStopped () 18 | { 19 | } 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/layout/Toolbar.axml: -------------------------------------------------------------------------------- 1 | 9 | 10 | -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Resources/values/styles.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 10 | 11 | 12 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.iOS/Main.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.Linq; 4 | 5 | using Foundation; 6 | using UIKit; 7 | 8 | namespace AudioRecord.Forms.iOS 9 | { 10 | public class Application 11 | { 12 | // This is the main entry point of the application. 13 | static void Main(string[] args) 14 | { 15 | // if you want to use a different Application Delegate class from "AppDelegate" 16 | // you can specify it here. 17 | UIApplication.Main(args, null, "AppDelegate"); 18 | } 19 | } 20 | } 21 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Resources/layout/Tabbar.axml: -------------------------------------------------------------------------------- 1 | 2 | 12 | -------------------------------------------------------------------------------- /Plugin.AudioRecorder.UWP/AudioRecorderService.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Threading.Tasks; 3 | using Windows.Storage; 4 | 5 | namespace Plugin.AudioRecorder 6 | { 7 | public partial class AudioRecorderService 8 | { 9 | partial void Init () { } 10 | 11 | async Task GetDefaultFilePath () 12 | { 13 | var temporaryFolder = ApplicationData.Current.TemporaryFolder; 14 | var tempFile = await temporaryFolder.CreateFileAsync (DefaultFileName, CreationCollisionOption.ReplaceExisting); 15 | 16 | return tempFile.Path; 17 | } 18 | 19 | void OnRecordingStarting () 20 | { 21 | } 22 | 23 | void OnRecordingStopped () 24 | { 25 | } 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms/App.xaml.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using Xamarin.Forms; 3 | using Xamarin.Forms.Xaml; 4 | 5 | [assembly: XamlCompilation (XamlCompilationOptions.Compile)] 6 | namespace AudioRecord.Forms 7 | { 8 | public partial class App : Application 9 | { 10 | public App () 11 | { 12 | InitializeComponent(); 13 | 14 | MainPage = new MainPage(); 15 | } 16 | 17 | protected override void OnStart () 18 | { 19 | // Handle when your app starts 20 | } 21 | 22 | protected override void OnSleep () 23 | { 24 | // Handle when your app sleeps 25 | } 26 | 27 | protected override void OnResume () 28 | { 29 | // Handle when your app resumes 30 | } 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/MainPage.xaml: -------------------------------------------------------------------------------- 1 | 11 | 12 | 13 | 14 | 15 | -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Assets/AboutAssets.txt: -------------------------------------------------------------------------------- 1 | Any raw assets you want to be deployed with your application can be placed in 2 | this directory (and child directories) and given a Build Action of "AndroidAsset". 3 | 4 | These files will be deployed with you package and will be accessible using Android's 5 | AssetManager, like this: 6 | 7 | public class ReadAsset : Activity 8 | { 9 | protected override void OnCreate (Bundle bundle) 10 | { 11 | base.OnCreate (bundle); 12 | 13 | InputStream input = Assets.Open ("my_asset.txt"); 14 | } 15 | } 16 | 17 | Additionally, some Android functions will automatically load asset files: 18 | 19 | Typeface tf = Typeface.CreateFromAsset (Context.Assets, "fonts/samplefont.ttf"); -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Assets/AboutAssets.txt: -------------------------------------------------------------------------------- 1 | Any raw assets you want to be deployed with your application can be placed in 2 | this directory (and child directories) and given a Build Action of "AndroidAsset". 3 | 4 | These files will be deployed with you package and will be accessible using Android's 5 | AssetManager, like this: 6 | 7 | public class ReadAsset : Activity 8 | { 9 | protected override void OnCreate (Bundle bundle) 10 | { 11 | base.OnCreate (bundle); 12 | 13 | InputStream input = Assets.Open ("my_asset.txt"); 14 | } 15 | } 16 | 17 | Additionally, some Android functions will automatically load asset files: 18 | 19 | Typeface tf = Typeface.CreateFromAsset (Context.Assets, "fonts/samplefont.ttf"); 20 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/Properties/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /Plugin.AudioRecorder.Shared/AudioStreamDetails.cs: -------------------------------------------------------------------------------- 1 | namespace Plugin.AudioRecorder 2 | { 3 | /// 4 | /// Represents the details of an , including channel count, sample rate, and bits per sample. 5 | /// 6 | public class AudioStreamDetails 7 | { 8 | /// 9 | /// Gets the sample rate of the underlying audio stream. 10 | /// 11 | public int SampleRate { get; set; } 12 | 13 | /// 14 | /// Gets the channel count of the underlying audio stream. 15 | /// 16 | public int ChannelCount { get; set; } 17 | 18 | /// 19 | /// Gets the bits per sample of the underlying audio stream. 20 | /// 21 | public int BitsPerSample { get; set; } 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.UWP/MainPage.xaml.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.IO; 4 | using System.Linq; 5 | using System.Runtime.InteropServices.WindowsRuntime; 6 | using Windows.Foundation; 7 | using Windows.Foundation.Collections; 8 | using Windows.UI.Xaml; 9 | using Windows.UI.Xaml.Controls; 10 | using Windows.UI.Xaml.Controls.Primitives; 11 | using Windows.UI.Xaml.Data; 12 | using Windows.UI.Xaml.Input; 13 | using Windows.UI.Xaml.Media; 14 | using Windows.UI.Xaml.Navigation; 15 | 16 | namespace AudioRecord.Forms.UWP 17 | { 18 | public sealed partial class MainPage 19 | { 20 | public MainPage() 21 | { 22 | this.InitializeComponent(); 23 | 24 | LoadApplication(new AudioRecord.Forms.App()); 25 | } 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.Android/Properties/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms/MainPage.xaml: -------------------------------------------------------------------------------- 1 | 2 | 6 | 7 | 8 | 9 | 10 | 12 | 46 | 56 | 57 | 58 | 59 | 60 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | -------------------------------------------------------------------------------- /Samples/Forms/AudioRecord.Forms.Android/AudioRecord.Forms.Android.csproj: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Debug 5 | AnyCPU 6 | {CB59A887-9999-4656-BDF0-CD47F3E1B1AA} 7 | {EFBA0AD7-5A72-4C68-AF49-83D382785DCF};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} 8 | {c9e5eea5-ca05-42a1-839b-61506e0a37df} 9 | Library 10 | AudioRecord.Forms.Droid 11 | AudioRecord.Forms.Android 12 | True 13 | Resources\Resource.designer.cs 14 | Resource 15 | Properties\AndroidManifest.xml 16 | Resources 17 | Assets 18 | false 19 | v8.1 20 | 21 | 22 | 23 | 24 | true 25 | full 26 | false 27 | bin\Debug 28 | DEBUG; 29 | prompt 30 | 4 31 | None 32 | 33 | 34 | true 35 | pdbonly 36 | true 37 | bin\Release 38 | prompt 39 | 4 40 | true 41 | false 42 | 43 | 44 | true 45 | bin\x86\Debug\ 46 | DEBUG; 47 | full 48 | x86 49 | Off 50 | prompt 51 | MinimumRecommendedRules.ruleset 52 | 53 | 54 | true 55 | bin\x86\Release\ 56 | true 57 | pdbonly 58 | x86 59 | Off 60 | prompt 61 | MinimumRecommendedRules.ruleset 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 1.1.0 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | Designer 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 | {64696B44-CFA0-4320-B53F-CD539D3BA5AE} 121 | AudioRecord.Forms 122 | 123 | 124 | 125 | -------------------------------------------------------------------------------- /Samples/Native/AudioRecord.iOS/AudioRecord.iOS.csproj: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Debug 5 | iPhoneSimulator 6 | {80A96B52-6758-4BDB-B0B4-CEA4CA155C60} 7 | {FEACFBD2-3405-455C-9665-78FE426C6842};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} 8 | {440aa056-593a-4519-8708-27081dee632f} 9 | Exe 10 | AudioRecord.iOS 11 | Resources 12 | AudioRecord.iOS 13 | 14 | 15 | true 16 | full 17 | false 18 | bin\iPhoneSimulator\Debug 19 | DEBUG 20 | prompt 21 | 4 22 | false 23 | x86_64 24 | None 25 | true 26 | 27 | 28 | none 29 | true 30 | bin\iPhoneSimulator\Release 31 | prompt 32 | 4 33 | None 34 | x86_64 35 | false 36 | 37 | 38 | true 39 | full 40 | false 41 | bin\iPhone\Debug 42 | DEBUG 43 | prompt 44 | 4 45 | false 46 | ARM64 47 | 48 | 49 | iPhone Developer: Nate Rickard (BK3AN56E7X) 50 | true 51 | VS: com.companyname.AudioRecord.iOS Development 52 | 53 | 54 | 55 | 56 | none 57 | true 58 | bin\iPhone\Release 59 | prompt 60 | 4 61 | 62 | 63 | ARM64 64 | false 65 | iPhone Developer: Nate Rickard (BK3AN56E7X) 66 | VS: com.companyname.AudioRecord.iOS Development 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | AudioRecord.iOS.Application 75 | 76 | 77 | 78 | 79 | 80 | 81 | ViewController.cs 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | 97 | false 98 | 99 | 100 | false 101 | 102 | 103 | false 104 | 105 | 106 | false 107 | 108 | 109 | false 110 | 111 | 112 | false 113 | 114 | 115 | false 116 | 117 | 118 | false 119 | 120 | 121 | false 122 | 123 | 124 | false 125 | 126 | 127 | false 128 | 129 | 130 | false 131 | 132 | 133 | false 134 | 135 | 136 | false 137 | 138 | 139 | 140 | 141 | 142 | 143 | 144 | 1.1.0 145 | 146 | 147 | 148 | -------------------------------------------------------------------------------- /Plugin.AudioRecorder.Android/AudioStream.cs: -------------------------------------------------------------------------------- 1 | using Android.Media; 2 | using System; 3 | using System.Diagnostics; 4 | using System.Threading.Tasks; 5 | 6 | namespace Plugin.AudioRecorder 7 | { 8 | internal class AudioStream : IAudioStream 9 | { 10 | readonly int bufferSize; 11 | readonly ChannelIn channels = ChannelIn.Mono; 12 | readonly Encoding audioFormat = Encoding.Pcm16bit; 13 | 14 | /// 15 | /// The audio source. 16 | /// 17 | AudioRecord audioSource; 18 | 19 | /// 20 | /// Occurs when new audio has been streamed. 21 | /// 22 | public event EventHandler OnBroadcast; 23 | 24 | /// 25 | /// Occurs when the audio stream active status changes. 26 | /// 27 | public event EventHandler OnActiveChanged; 28 | 29 | /// 30 | /// Occurs when there's an error while capturing audio. 31 | /// 32 | public event EventHandler OnException; 33 | 34 | /// 35 | /// The default device. 36 | /// 37 | public static readonly AudioSource DefaultDevice = AudioSource.Mic; 38 | 39 | /// 40 | /// Gets the sample rate. 41 | /// 42 | /// 43 | /// The sample rate. 44 | /// 45 | public int SampleRate { get; private set; } = 44100; 46 | 47 | /// 48 | /// Gets bits per sample. 49 | /// 50 | public int BitsPerSample => (audioSource.AudioFormat == Encoding.Pcm16bit) ? 16 : 8; 51 | 52 | /// 53 | /// Gets the channel count. 54 | /// 55 | /// 56 | /// The channel count. 57 | /// 58 | public int ChannelCount => audioSource.ChannelCount; 59 | 60 | /// 61 | /// Gets the average data transfer rate 62 | /// 63 | /// The average data transfer rate in bytes per second. 64 | public int AverageBytesPerSecond => SampleRate * BitsPerSample / 8 * ChannelCount; 65 | 66 | /// 67 | /// Gets a value indicating if the audio stream is active. 68 | /// 69 | public bool Active => audioSource?.RecordingState == RecordState.Recording; 70 | 71 | void Init () 72 | { 73 | Stop (); // just in case 74 | 75 | audioSource = new AudioRecord ( 76 | DefaultDevice, 77 | SampleRate, 78 | channels, 79 | audioFormat, 80 | bufferSize); 81 | 82 | if (audioSource.State == State.Uninitialized) 83 | { 84 | throw new Exception ("Unable to successfully initialize AudioStream; reporting State.Uninitialized. If using an emulator, make sure it has access to the system microphone."); 85 | } 86 | } 87 | 88 | /// 89 | /// Starts the audio stream. 90 | /// 91 | public Task Start () 92 | { 93 | try 94 | { 95 | if (!Active) 96 | { 97 | // not sure this does anything or if should be here... inherited via copied code ¯\_(ツ)_/¯ 98 | Android.OS.Process.SetThreadPriority (Android.OS.ThreadPriority.UrgentAudio); 99 | 100 | Init (); 101 | 102 | audioSource.StartRecording (); 103 | 104 | OnActiveChanged?.Invoke (this, true); 105 | 106 | Task.Run (() => Record ()); 107 | } 108 | 109 | return Task.FromResult (true); 110 | } 111 | catch (Exception ex) 112 | { 113 | Debug.WriteLine ("Error in AudioStream.Start(): {0}", ex.Message); 114 | 115 | Stop (); 116 | throw; 117 | } 118 | } 119 | 120 | /// 121 | /// Stops the audio stream. 122 | /// 123 | public Task Stop () 124 | { 125 | if (Active) 126 | { 127 | audioSource.Stop (); 128 | audioSource.Release (); 129 | 130 | OnActiveChanged?.Invoke (this, false); 131 | } 132 | else // just in case 133 | { 134 | audioSource?.Release (); 135 | } 136 | 137 | return Task.FromResult (true); 138 | } 139 | 140 | /// 141 | /// Initializes a new instance of the class. 142 | /// 143 | /// Sample rate. 144 | /// The value representing the number of channels to record. 145 | /// The format of the recorded audio. 146 | public AudioStream (int sampleRate = 44100, ChannelIn channels = ChannelIn.Mono, Encoding audioFormat = Encoding.Pcm16bit) 147 | { 148 | bufferSize = AudioRecord.GetMinBufferSize (sampleRate, channels, audioFormat); 149 | 150 | if (bufferSize < 0) 151 | { 152 | throw new Exception ("Invalid buffer size calculated; audio settings used may not be supported on this device"); 153 | } 154 | 155 | SampleRate = sampleRate; 156 | this.channels = channels; 157 | this.audioFormat = audioFormat; 158 | } 159 | 160 | /// 161 | /// Record from the microphone and broadcast the buffer. 162 | /// 163 | async Task Record () 164 | { 165 | byte [] data = new byte [bufferSize]; 166 | int readFailureCount = 0; 167 | int readResult = 0; 168 | 169 | Debug.WriteLine ("AudioStream.Record(): Starting background loop to read audio stream"); 170 | 171 | while (Active) 172 | { 173 | try 174 | { 175 | // not sure if this is even a good idea, but we'll try to allow a single bad read, and past that shut it down 176 | if (readFailureCount > 1) 177 | { 178 | Debug.WriteLine ("AudioStream.Record(): Multiple read failures detected, stopping stream"); 179 | await Stop (); 180 | break; 181 | } 182 | 183 | readResult = audioSource.Read (data, 0, bufferSize); // this can block if there are no bytes to read 184 | 185 | // readResult should == the # bytes read, except a few special cases 186 | if (readResult > 0) 187 | { 188 | readFailureCount = 0; 189 | OnBroadcast?.Invoke (this, data); 190 | } 191 | else 192 | { 193 | switch (readResult) 194 | { 195 | case (int) TrackStatus.ErrorInvalidOperation: 196 | case (int) TrackStatus.ErrorBadValue: 197 | case (int) TrackStatus.ErrorDeadObject: 198 | Debug.WriteLine ("AudioStream.Record(): readResult returned error code: {0}", readResult); 199 | await Stop (); 200 | break; 201 | //case (int)TrackStatus.Error: 202 | default: 203 | readFailureCount++; 204 | Debug.WriteLine ("AudioStream.Record(): readResult returned error code: {0}", readResult); 205 | break; 206 | } 207 | } 208 | } 209 | catch (Exception ex) 210 | { 211 | readFailureCount++; 212 | 213 | Debug.WriteLine ("Error in Android AudioStream.Record(): {0}", ex.Message); 214 | 215 | OnException?.Invoke (this, ex); 216 | } 217 | } 218 | } 219 | 220 | /// 221 | /// Flushes any audio bytes in memory but not yet broadcast out to any listeners. 222 | /// 223 | public void Flush () 224 | { 225 | // not needed for this implementation 226 | } 227 | } 228 | } 229 | -------------------------------------------------------------------------------- /Plugin.AudioRecorder.UWP/Plugin.AudioRecorder.UWP.csproj: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | Debug 6 | AnyCPU 7 | {8803A551-21D1-43AC-866C-39DDA703C237} 8 | Library 9 | Properties 10 | Plugin.AudioRecorder 11 | Plugin.AudioRecorder 12 | en-US 13 | UAP 14 | 10.0.17134.0 15 | 10.0.15063.0 16 | 14 17 | 512 18 | {A5A43C5B-DE2A-4C0C-9213-0A381AF9435A};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} 19 | 20 | 21 | AnyCPU 22 | true 23 | full 24 | false 25 | bin\Debug\ 26 | DEBUG;TRACE;NETFX_CORE;WINDOWS_UWP 27 | prompt 28 | 4 29 | 30 | 31 | AnyCPU 32 | pdbonly 33 | true 34 | bin\Release\ 35 | TRACE;NETFX_CORE;WINDOWS_UWP 36 | prompt 37 | 4 38 | true 39 | 40 | 41 | x86 42 | true 43 | bin\x86\Debug\ 44 | DEBUG;TRACE;NETFX_CORE;WINDOWS_UWP 45 | ;2008 46 | full 47 | x86 48 | false 49 | prompt 50 | true 51 | 52 | 53 | x86 54 | bin\x86\Release\ 55 | TRACE;NETFX_CORE;WINDOWS_UWP 56 | true 57 | ;2008 58 | pdbonly 59 | x86 60 | false 61 | prompt 62 | true 63 | 64 | 65 | ARM 66 | true 67 | bin\ARM\Debug\ 68 | DEBUG;TRACE;NETFX_CORE;WINDOWS_UWP 69 | ;2008 70 | full 71 | ARM 72 | false 73 | prompt 74 | 75 | 76 | ARM 77 | bin\ARM\Release\ 78 | TRACE;NETFX_CORE;WINDOWS_UWP 79 | true 80 | ;2008 81 | pdbonly 82 | ARM 83 | false 84 | prompt 85 | 86 | 87 | x64 88 | true 89 | bin\x64\Debug\ 90 | DEBUG;TRACE;NETFX_CORE;WINDOWS_UWP 91 | ;2008 92 | full 93 | x64 94 | false 95 | prompt 96 | 97 | 98 | x64 99 | bin\x64\Release\ 100 | TRACE;NETFX_CORE;WINDOWS_UWP 101 | true 102 | ;2008 103 | pdbonly 104 | x64 105 | false 106 | prompt 107 | 108 | 109 | PackageReference 110 | 111 | 112 | 113 | 114 | 115 | 116 | 117 | 118 | 119 | 120 | 6.1.7 121 | 122 | 123 | 0.2.5-dev.1 124 | 125 | 126 | 127 | 128 | 14.0 129 | 130 | 131 | 138 | -------------------------------------------------------------------------------- /Plugin.AudioRecorder.iOS/AudioStream.cs: -------------------------------------------------------------------------------- 1 | using AudioToolbox; 2 | using System; 3 | using System.Diagnostics; 4 | using System.Runtime.InteropServices; 5 | using System.Threading.Tasks; 6 | 7 | namespace Plugin.AudioRecorder 8 | { 9 | internal class AudioStream : IAudioStream 10 | { 11 | const int CountAudioBuffers = 3; 12 | const int MaxBufferSize = 0x50000; // 320 KB 13 | const float TargetMeasurementTime = 100F; // milliseconds 14 | 15 | InputAudioQueue audioQueue; 16 | 17 | /// 18 | /// Occurs when new audio has been streamed. 19 | /// 20 | public event EventHandler OnBroadcast; 21 | 22 | /// 23 | /// Occurs when the audio stream active status changes. 24 | /// 25 | public event EventHandler OnActiveChanged; 26 | 27 | /// 28 | /// Occurs when there's an error while capturing audio. 29 | /// 30 | public event EventHandler OnException; 31 | 32 | /// 33 | /// Gets the sample rate. 34 | /// 35 | /// 36 | /// The sample rate. 37 | /// 38 | public int SampleRate 39 | { 40 | get; 41 | private set; 42 | } 43 | 44 | /// 45 | /// Gets the channel count. Currently always 1 (Mono). 46 | /// 47 | /// 48 | /// The channel count. 49 | /// 50 | public int ChannelCount => 1; 51 | 52 | /// 53 | /// Gets bits per sample. Currently always 16 (bits). 54 | /// 55 | public int BitsPerSample => 16; 56 | 57 | /// 58 | /// Gets a value indicating if the audio stream is active. 59 | /// 60 | public bool Active => audioQueue?.IsRunning ?? false; 61 | 62 | /// 63 | /// Wrapper function to run success/failure callbacks from an operation that returns an AudioQueueStatus. 64 | /// 65 | /// The function that returns AudioQueueStatus. 66 | /// The Action to run if the result is AudioQueueStatus.Ok. 67 | /// The Action to run if the result is anything other than AudioQueueStatus.Ok. 68 | void BufferOperation (Func bufferFn, Action successAction = null, Action failAction = null) 69 | { 70 | var status = bufferFn (); 71 | 72 | if (status == AudioQueueStatus.Ok) 73 | { 74 | successAction?.Invoke (); 75 | } 76 | else 77 | { 78 | if (failAction != null) 79 | { 80 | failAction (status); 81 | } 82 | else 83 | { 84 | throw new Exception ($"AudioStream buffer error :: buffer operation returned non - Ok status:: {status}"); 85 | } 86 | } 87 | } 88 | 89 | /// 90 | /// Starts the audio stream. 91 | /// 92 | public Task Start () 93 | { 94 | try 95 | { 96 | if (!Active) 97 | { 98 | InitAudioQueue (); 99 | 100 | BufferOperation (() => audioQueue.Start (), 101 | () => OnActiveChanged?.Invoke (this, true), 102 | status => throw new Exception ($"audioQueue.Start() returned non-OK status: {status}")); 103 | } 104 | 105 | return Task.FromResult (true); 106 | } 107 | catch (Exception ex) 108 | { 109 | Debug.WriteLine ("Error in AudioStream.Start(): {0}", ex.Message); 110 | 111 | Stop (); 112 | throw; 113 | } 114 | } 115 | 116 | /// 117 | /// Stops the audio stream. 118 | /// 119 | public Task Stop () 120 | { 121 | if (audioQueue != null) 122 | { 123 | audioQueue.InputCompleted -= QueueInputCompleted; 124 | 125 | if (audioQueue.IsRunning) 126 | { 127 | BufferOperation (() => audioQueue.Stop (true), 128 | () => OnActiveChanged?.Invoke (this, false), 129 | status => Debug.WriteLine ("AudioStream.Stop() :: audioQueue.Stop returned non OK result: {0}", status)); 130 | } 131 | 132 | audioQueue.Dispose (); 133 | audioQueue = null; 134 | } 135 | 136 | return Task.FromResult (true); 137 | } 138 | 139 | /// 140 | /// Initializes a new instance of the class. 141 | /// 142 | /// Sample rate. 143 | public AudioStream (int sampleRate) 144 | { 145 | SampleRate = sampleRate; 146 | } 147 | 148 | void InitAudioQueue () 149 | { 150 | // create our audio queue & configure buffers 151 | var audioFormat = AudioStreamBasicDescription.CreateLinearPCM (SampleRate, (uint) ChannelCount, (uint) BitsPerSample); 152 | 153 | audioQueue = new InputAudioQueue (audioFormat); 154 | audioQueue.InputCompleted += QueueInputCompleted; 155 | 156 | // calculate our buffer size and make sure it's not too big 157 | var bufferByteSize = (int) (TargetMeasurementTime / 1000F/*ms to sec*/ * SampleRate * audioFormat.BytesPerPacket); 158 | bufferByteSize = bufferByteSize < MaxBufferSize ? bufferByteSize : MaxBufferSize; 159 | 160 | for (var index = 0; index < CountAudioBuffers; index++) 161 | { 162 | var bufferPtr = IntPtr.Zero; 163 | 164 | BufferOperation (() => audioQueue.AllocateBuffer (bufferByteSize, out bufferPtr), () => 165 | { 166 | BufferOperation (() => audioQueue.EnqueueBuffer (bufferPtr, bufferByteSize, null), () => Debug.WriteLine ("AudioQueue buffer enqueued :: {0} of {1}", index + 1, CountAudioBuffers)); 167 | }); 168 | } 169 | } 170 | 171 | /// 172 | /// Handles iOS audio buffer queue completed message. 173 | /// 174 | /// Sender object 175 | /// Input completed parameters. 176 | void QueueInputCompleted (object sender, InputCompletedEventArgs e) 177 | { 178 | try 179 | { 180 | // we'll only broadcast if we're actively monitoring audio packets 181 | if (!Active) 182 | { 183 | return; 184 | } 185 | 186 | if (e.Buffer.AudioDataByteSize > 0) 187 | { 188 | var audioBytes = new byte [e.Buffer.AudioDataByteSize]; 189 | Marshal.Copy (e.Buffer.AudioData, audioBytes, 0, (int) e.Buffer.AudioDataByteSize); 190 | 191 | // broadcast the audio data to any listeners 192 | OnBroadcast?.Invoke (this, audioBytes); 193 | 194 | // check if active again, because the auto stop logic may stop the audio queue from within this handler! 195 | if (Active) 196 | { 197 | BufferOperation (() => audioQueue.EnqueueBuffer (e.IntPtrBuffer, null), null, status => 198 | { 199 | Debug.WriteLine ("AudioStream.QueueInputCompleted() :: audioQueue.EnqueueBuffer returned non-Ok status :: {0}", status); 200 | OnException?.Invoke (this, new Exception ($"audioQueue.EnqueueBuffer returned non-Ok status :: {status}")); 201 | }); 202 | } 203 | } 204 | } 205 | catch (Exception ex) 206 | { 207 | Debug.WriteLine ("AudioStream.QueueInputCompleted() :: Error: {0}", ex.Message); 208 | 209 | OnException?.Invoke (this, new Exception ($"AudioStream.QueueInputCompleted() :: Error: {ex.Message}")); 210 | } 211 | } 212 | 213 | /// 214 | /// Flushes any audio bytes in memory but not yet broadcast out to any listeners. 215 | /// 216 | public void Flush () 217 | { 218 | // not needed for this implementation 219 | } 220 | } 221 | } 222 | --------------------------------------------------------------------------------