c# – Send and receive stream. Socket

Question:

I write the picture from the camera to the stream:

var stream = new InMemoryRandomAccessStream();
await _mediaCapture.StartRecordToStreamAsync(encodingProfile,stream);

The task: to somehow break this one into bytes and transmit it over a socket, and create a stream again at the reception? It turns out to be a kind of broadcast.

The stream needs to be encrypted and decrypted with aes. Encryption method implemented, takes an array of bytes. How do I send a stream there?

Answer:

Here's the code:

private async Task<IDisposable> SendStreamAsync(MediaEncodingProfile encodingProfile, MediaCapture mediaCapture)
{
    var socket = new DatagramSocket();

    var outputStream = await socket.GetOutputStreamAsync(new HostName("example.com"), "12345");

    var writeOnlyStream = new WriteOnlyStreamStream(outputStream);

    await mediaCapture.StartRecordToStreamAsync(encodingProfile, writeOnlyStream);

    return new CompositeDisposable {writeOnlyStream, outputStream, socket};
}

private sealed class WriteOnlyStreamStream : IRandomAccessStream
{
    readonly IOutputStream _outputStream;

    public WriteOnlyStreamStream(IOutputStream outputStream)
    {
        _outputStream = outputStream;
    }

    public IInputStream GetInputStreamAt(ulong position)
    {
        throw new NotSupportedException(); //or we can return empty stream
    }

    public IOutputStream GetOutputStreamAt(ulong position)
    {
        return _outputStream;
    }

    public ulong Size
    {
        get { return 0; }
        set { }
    }

    public bool CanRead => false;

    public bool CanWrite => true;

    public IRandomAccessStream CloneStream()
    {
        throw new NotSupportedException();
    }

    public ulong Position => 0;

    public void Seek(ulong position)
    {
    }

    public void Dispose()
    {
        this._outputStream.Dispose();
    }

    public IAsyncOperationWithProgress<IBuffer, uint> ReadAsync(IBuffer buffer, uint count, InputStreamOptions options)
    {
        throw new NotSupportedException();
    }

    public IAsyncOperationWithProgress<uint, uint> WriteAsync(IBuffer buffer)
    {
        return _outputStream.WriteAsync(buffer);
    }

    public IAsyncOperation<bool> FlushAsync()
    {
        return _outputStream.FlushAsync();
    }
}

What's going on here:

  1. Created an Udp socket (packets will be lost, broken, no integrity in it)
  2. We created a special wrapper class to push the IOutputStream inside the MediaCapture. There are options here, you can return an empty IInputStream instead of exceptions
  3. We created an IDisposable that needs to be closed after all operations (we use Reactive Extensions).

As more correctly advised in the questions, it is better to use TCP sockets here. For the client side, everything will be 1-in-1, only the classes will change a little. For the server side, you need to use the StreamSocketListener class (it is in uwp), from which you already listen to some port.

Scroll to Top