private unsafe void CalculateLuminance(SoftwareBitmap bitmap)
        {
            // Effect is hard-coded to operate on BGRA8 format only
            if (bitmap.BitmapPixelFormat == BitmapPixelFormat.Bgra8)
            {
                // In BGRA8 format, each pixel is defined by 4 bytes
                const int BYTES_PER_PIXEL = 4;

                using (var buffer = bitmap.LockBuffer(BitmapBufferAccessMode.Read))
                using (var reference = buffer.CreateReference())
                {

                    if (reference is IMemoryBufferByteAccess)
                    {


                        try
                        {
                            // Get a pointer to the pixel buffer
                            byte* data;
                            uint capacity;
                            ((IMemoryBufferByteAccess)reference).GetBuffer(out data, out capacity);

                            // Get information about the BitmapBuffer
                            var desc = buffer.GetPlaneDescription(0);
                            var luminanceIndex = 0;

                            // Iterate over all pixels
                            for (uint row = 0; row < desc.Height; row++)
                            {
                                for (uint col = 0; col < desc.Width; col++)
                                {
                                    // Index of the current pixel in the buffer (defined by the next 4 bytes, BGRA8)
                                    var currPixel = desc.StartIndex + desc.Stride * row + BYTES_PER_PIXEL * col;

                                    // Read the current pixel information into b,g,r channels (leave out alpha channel)
                                    var b = data[currPixel + 0]; // Blue
                                    var g = data[currPixel + 1]; // Green
                                    var r = data[currPixel + 2]; // Red

                                    var luminance = (byte)((RChannelWeight * r + GChannelWeight * g + BChannelWeight * b) >> ChannelWeight);
                                    var alpha = data[currPixel + 3];
                                    luminance = (byte)(((luminance * alpha) >> 8) + (255 * (255 - alpha) >> 8));
                                    luminances[luminanceIndex] = luminance;
                                    luminanceIndex++;
                                }
                            }
                        }
                        catch (Exception ex)
                        {
                            System.Diagnostics.Debug.WriteLine("Luminance Source Failed: {0}", ex);
                        }
                    }
                }
            }
        }
        /// <summary>
        /// Transform image into Bgra8 image using given transform method.
        /// </summary>
        /// <param name="softwareBitmap">Input image to transform.</param>
        /// <param name="transformScanline">Method to map pixels in a scanline.</param>
        private static unsafe SoftwareBitmap TransformBitmap(SoftwareBitmap softwareBitmap, TransformScanline transformScanline)
        {
            // XAML Image control only supports premultiplied Bgra8 format.
            var outputBitmap = new SoftwareBitmap(BitmapPixelFormat.Bgra8,
                softwareBitmap.PixelWidth, softwareBitmap.PixelHeight, BitmapAlphaMode.Premultiplied);

            using (var input = softwareBitmap.LockBuffer(BitmapBufferAccessMode.Read))
            using (var output = outputBitmap.LockBuffer(BitmapBufferAccessMode.Write))
            {
                // Get stride values to calculate buffer position for a given pixel x and y position.
                int inputStride = input.GetPlaneDescription(0).Stride;
                int outputStride = output.GetPlaneDescription(0).Stride;
                int pixelWidth = softwareBitmap.PixelWidth;
                int pixelHeight = softwareBitmap.PixelHeight;

                using (var outputReference = output.CreateReference())
                using (var inputReference = input.CreateReference())
                {
                    // Get input and output byte access buffers.
                    byte* inputBytes;
                    uint inputCapacity;
                    ((IMemoryBufferByteAccess)inputReference).GetBuffer(out inputBytes, out inputCapacity);
                    byte* outputBytes;
                    uint outputCapacity;
                    ((IMemoryBufferByteAccess)outputReference).GetBuffer(out outputBytes, out outputCapacity);

                    // Iterate over all pixels and store converted value.
                    for (int y = 0; y < pixelHeight; y++)
                    {
                        byte* inputRowBytes = inputBytes + y * inputStride;
                        byte* outputRowBytes = outputBytes + y * outputStride;

                        transformScanline(pixelWidth, inputRowBytes, outputRowBytes);
                    }
                }
            }
            return outputBitmap;
        }
        /// <summary>
        /// Applies a basic effect to a Bgra8 SoftwareBitmap in-place
        /// </summary>
        /// <param name="bitmap">SoftwareBitmap that will receive the effect</param>
        private unsafe void ApplyGreenFilter(SoftwareBitmap bitmap)
        {
            // Effect is hard-coded to operate on BGRA8 format only
            if (bitmap.BitmapPixelFormat == BitmapPixelFormat.Bgra8)
            {
                // In BGRA8 format, each pixel is defined by 4 bytes
                const int BYTES_PER_PIXEL = 4;

                using (var buffer = bitmap.LockBuffer(BitmapBufferAccessMode.ReadWrite))
                using (var reference = buffer.CreateReference())
                {
                    if (reference is IMemoryBufferByteAccess)
                    {
                        // Get a pointer to the pixel buffer
                        byte* data;
                        uint capacity;
                        ((IMemoryBufferByteAccess)reference).GetBuffer(out data, out capacity);

                        // Get information about the BitmapBuffer
                        var desc = buffer.GetPlaneDescription(0);

                        // Iterate over all pixels
                        for (uint row = 0; row < desc.Height; row++)
                        {
                            for (uint col = 0; col < desc.Width; col++)
                            {
                                // Index of the current pixel in the buffer (defined by the next 4 bytes, BGRA8)
                                var currPixel = desc.StartIndex + desc.Stride * row + BYTES_PER_PIXEL * col;

                                // Read the current pixel information into b,g,r channels (leave out alpha channel)
                                var b = data[currPixel + 0]; // Blue
                                var g = data[currPixel + 1]; // Green
                                var r = data[currPixel + 2]; // Red

                                // Boost the green channel, leave the other two untouched
                                data[currPixel + 0] = b;
                                data[currPixel + 1] = (byte)Math.Min(g + 80, 255);
                                data[currPixel + 2] = r;
                            }
                        }
                    }
                }
            }
        }
        /// <summary>
        /// 
        /// </summary>
        /// <param name="bitmap"></param>
        private unsafe void EncodeStream(SoftwareBitmap bitmap)
        {
            using (BitmapBuffer buffer = bitmap.LockBuffer(BitmapBufferAccessMode.ReadWrite))
            using (var bufferReference = buffer.CreateReference())
            {

                if (bufferReference is IMemoryBufferByteAccess)
                {
                    byte* frameByte;
                    uint capacity;

                    ((IMemoryBufferByteAccess)bufferReference).GetBuffer(out frameByte, out capacity);

                    var bufferDescription = buffer.GetPlaneDescription(0);
                    byte[] frameData = new byte[bufferDescription.Height * bufferDescription.Width];
                    Marshal.Copy((IntPtr)frameByte, frameData, 0, frameData.Length);

                    encoder.Ffmpeg_encodeVideoFrame(frameData);
                }
            }
        }