Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Directing microphone input to speakers and writing a custom DSP function. #34

Closed
postacik opened this issue Jan 5, 2016 · 10 comments
Closed
Assignees
Labels

Comments

@postacik
Copy link

postacik commented Jan 5, 2016

I'm trying to capture microphone input from WasapiCapture device and output the recorded data to WasapiOut device but I could not succeed it.

What I am trying to do is write an application like this one:
http://www.pitchtech.ch/PitchBox/

I also have tested DSP functions which I want to apply to recorded data.

Can you provide examples of directing WasapiCapture to WasapiOut and writing a custom DSP.

@filoe
Copy link
Owner

filoe commented Jan 8, 2016

Take a look at the following snippet: https://github.com/filoe/cscore/blob/master/CSCore.Test/RecentIssueTests/SoundInToSoundOutTests.cs
The dsp function can be created by implementing the IWaveSource or ISampleSource interface. The instance of the dsp function can be applied to the waveInToSource object.
For example: soundOut.Initialize(new DmoEchoEffect(waveInToSource));

@postacik
Copy link
Author

postacik commented Jan 8, 2016

Thank you very much. It works like a charm.

I've been trying to do the same think with the Bass.Net and the Bass library and I succeeded but CSCore way of doing it is just easier and requires only one native DLL.

It would be great if you could extend the sample applications with some common tasks like this one because it is hard to dig into the test codes.

I will try implementing the IWaveSource or ISampleSource interfaces and maybe return with new questions.

@filoe
Copy link
Owner

filoe commented Jan 8, 2016

Glad to hear that.

@postacik
Copy link
Author

postacik commented Jan 9, 2016

I wrote a sample ISampleSource to amplify captured sound. Is this the right way of doing it?

using System;
using CSCore;

namespace MyTests
{
    class DSPGain: ISampleSource
    {
        ISampleSource _source;
        public DSPGain(ISampleSource source)
        {
            if (source == null)
                throw new ArgumentNullException("source");
            _source = source;
        }
        public int Read(float[] buffer, int offset, int count)
        {
            float gainAmplification = (float)(Math.Pow(10.0, GainDB / 20.0));
            int samples = _source.Read(buffer, offset, count);
            for (int i = offset; i < offset + samples; i++)
            {
                buffer[i] = Math.Max(Math.Min(buffer[i] * gainAmplification, 1), -1);
            }
            return samples;
        }

        public float GainDB { get; set; }

        public bool CanSeek
        {
            get { return _source.CanSeek; }
        }

        public WaveFormat WaveFormat
        {
            get { return _source.WaveFormat; }
        }

        public long Position
        {
            get
            {
                return _source.Position;
            }
            set
            {
                _source.Position = value;
            }
        }

        public long Length
        {
            get { return _source.Length; }
        }

        public void Dispose()
        {
        }
    }
}

@filoe
Copy link
Owner

filoe commented Jan 9, 2016

It is, but do not forget to dispose the _source inside of the dispose method.

@postacik
Copy link
Author

postacik commented Jan 9, 2016

Thanks. I also added pitch shifting option to the class and it works fine.

However, I tested my application with a user with Admin rights and with a user without Admin rights. (Windows 8)

The application works with minimum latency with the Admin user but it starts to lag and voice quality decreases when I run the application with the other user.

My application also uses the Bass library to achieve the same task as an alternative and it does not have this kind of problem.

CSCore and Bass versions both initialize Wasapi capture and playback in exclusive mode with 5 ms latency.

Do you have any idea why this might happen?

@postacik
Copy link
Author

postacik commented Jan 9, 2016

Here is a link to the related stackoverflow question which includes the code I am using.

http://stackoverflow.com/q/34634726/5413816

@filoe filoe self-assigned this Jan 11, 2016
@filoe
Copy link
Owner

filoe commented Jan 16, 2016

Well, if you compare CSCore with Bass you will always have a slightly worse performance. Bass is written in some native languages (I would guess C++?) and CSCore is written in C#. CSCore got a quite nice performance but I am not sure whether it can handle such a low latency. Have you tried to adjust the latency to lets say 20 or 30ms?

@postacik
Copy link
Author

Well, CSCore and Bass have similar latency when I run the application under an admin user.

My son has a limited user account on my laptop and when I run the application under his account it lags severely with CSCore but has no problems with Bass. In my opinion, it may be related to the AudioClientShareMode.Exclusive option.

I can provide a sample application if you have time to test.

@filoe
Copy link
Owner

filoe commented Jan 21, 2016

A sample application would be great. But as I already said, its hard to compare C# with native languages on such a low latency.

@filoe filoe closed this as completed Apr 10, 2016
@filoe filoe added question and removed help wanted labels Jan 1, 2017
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

2 participants