Esempio n. 1
0
        public void FullTest( )
        {
            var          array   = 0;
            var          element = 0;
            IBufferStack stack   = new BufferStack(source);

            while (stack.NextBuffer())
            {
                Assert.AreEqual(array, stack.Index, $"failed Index [{array}]:[{stack.Index}]");
                Assert.AreEqual(-1, stack.Element,
                                $"failed Element [{array},{element}]:[{stack.Index},{stack.Element}]");

                var expectedArray = source[array];
                CollectionAssert.AreEqual(expectedArray, stack.Current, $"failed collection [{array}]");

                while (stack.MoveNext())
                {
                    Assert.AreEqual(expectedArray[element], ((IByteStack)stack).Current,
                                    $"failed Current [{expectedArray[element]}]:[{((IByteStack)stack).Current}]");

                    ++element;
                }

                ++array;
                element = 0;
            }
        }
Esempio n. 2
0
        public void ExecuteNextBuffer( )
        {
            IBufferStack stack = new BufferStack(source);

            //  NextBuffer will position the stack at the first array, first element
            Assert.IsTrue(stack.NextBuffer(), "failed first NextBuffer");
            Assert.AreEqual(0, stack.Index, $"failed first Index [0]:[{stack.Index}]");
            Assert.AreEqual(-1, stack.Element, $"failed first Element [-1]:[{stack.Element}]");

            //  second array, 2nd element
            Assert.IsTrue(stack.NextBuffer(), "failed second NextBuffer");
            Assert.AreEqual(1, stack.Index, $"failed second Index [0]:[{stack.Index}]");
            Assert.AreEqual(-1, stack.Element, $"failed second Element [-1]:[{stack.Element}]");
        }
Esempio n. 3
0
        public void ExecuteMoveNext( )
        {
            IBufferStack stack = new BufferStack(source);

            //  MoveNext will position the stack at first array, first element
            Assert.IsTrue(stack.MoveNext(), "failed first MoveNext");
            Assert.AreEqual(0, stack.Index, $"failed first Index [0]:[{stack.Index}]");
            Assert.AreEqual(0, stack.Element, $"failed first Element [0]:[{stack.Element}]");

            //  first array, 2nd element
            Assert.IsTrue(stack.MoveNext(), "failed second MoveNext");
            Assert.AreEqual(0, stack.Index, $"failed second Index [0]:[{stack.Index}]");
            Assert.AreEqual(1, stack.Element, $"failed second Element [1]:[{stack.Element}]");
        }
Esempio n. 4
0
        /// <summary>
        /// Create an empty raw texture with an optional <see cref="BufferStack{T}"/>. backing.
        /// </summary>
        /// <param name="width">The width of the texture.</param>
        /// <param name="height">The height of the texture.</param>
        /// <param name="bufferStack">The buffer stack to retrieve the byte[] from.</param>
        public RawTexture(int width, int height, BufferStack <byte> bufferStack = null)
        {
            int size = width * height * 4;

            Width  = width;
            Height = height;

            if (bufferStack != null)
            {
                this.bufferStack = bufferStack;
                Data             = this.bufferStack.ReserveBuffer(size);
            }
            else
            {
                Data = new byte[size];
            }
        }
Esempio n. 5
0
        private void decodingLoop(CancellationToken cancellationToken)
        {
            var packet = ffmpeg.av_packet_alloc();

            const int max_pending_frames = 3;

            var bufferStack = new BufferStack <Rgba32>(max_pending_frames * 2);

            try
            {
                while (true)
                {
                    if (cancellationToken.IsCancellationRequested)
                    {
                        return;
                    }

                    if (decodedFrames.Count < max_pending_frames && bufferStack.BuffersInUse < max_pending_frames * 2)
                    {
                        int readFrameResult = ffmpeg.av_read_frame(formatContext, packet);

                        if (readFrameResult >= 0)
                        {
                            state = DecoderState.Running;
                            if (packet->stream_index == stream->index)
                            {
                                if (ffmpeg.avcodec_send_packet(stream->codec, packet) < 0)
                                {
                                    throw new Exception("Error sending packet.");
                                }

                                var result = ffmpeg.avcodec_receive_frame(stream->codec, frame);
                                if (result == 0)
                                {
                                    var frameTime = (frame->best_effort_timestamp - stream->start_time) * timeBaseInSeconds * 1000;
                                    if (!skipOutputUntilTime.HasValue || skipOutputUntilTime.Value < frameTime)
                                    {
                                        skipOutputUntilTime = null;

                                        SwsContext *swsCtx = null;
                                        try
                                        {
                                            swsCtx = ffmpeg.sws_getContext(codecParams.width, codecParams.height, (AVPixelFormat)frame->format, codecParams.width, codecParams.height, AVPixelFormat.AV_PIX_FMT_RGBA, 0, null, null, null);
                                            ffmpeg.sws_scale(swsCtx, frame->data, frame->linesize, 0, frame->height, frameRgb->data, frameRgb->linesize);
                                        }
                                        finally
                                        {
                                            ffmpeg.sws_freeContext(swsCtx);
                                        }

                                        if (!availableTextures.TryDequeue(out var tex))
                                        {
                                            tex = new Texture(codecParams.width, codecParams.height, true);
                                        }

                                        var rawTex = new BufferStackTextureUpload(tex.Width, tex.Height, bufferStack);

                                        // todo: can likely make this more efficient
                                        var videoText = new Span <Rgba32>(frameRgb->data[0], uncompressedFrameSize / 4);
                                        videoText.CopyTo(rawTex.RawData);

                                        tex.SetData(rawTex);
                                        decodedFrames.Enqueue(new DecodedFrame {
                                            Time = frameTime, Texture = tex
                                        });
                                    }

                                    lastDecodedFrameTime = (float)frameTime;
                                }
                            }
                        }
                        else if (readFrameResult == ffmpeg.AVERROR_EOF)
                        {
                            if (Looping)
                            {
                                Seek(0);
                            }
                            else
                            {
                                state = DecoderState.EndOfStream;
                            }
                        }
                        else
                        {
                            state = DecoderState.Ready;
                            Thread.Sleep(1);
                        }
                    }
                    else
                    {
                        // wait until existing buffers are consumed.
                        state = DecoderState.Ready;
                        Thread.Sleep(1);
                    }

                    while (!decoderCommands.IsEmpty)
                    {
                        if (cancellationToken.IsCancellationRequested)
                        {
                            return;
                        }
                        if (decoderCommands.TryDequeue(out var cmd))
                        {
                            cmd();
                        }
                    }
                }
            }
            catch (Exception)
            {
                state = DecoderState.Faulted;
            }
            finally
            {
                ffmpeg.av_packet_free(&packet);

                if (state != DecoderState.Faulted)
                {
                    state = DecoderState.Stopped;
                }
            }
        }
        public FrameStatisticsDisplay(GameThread thread, TextureAtlas atlas)
        {
            Name    = thread.Thread.Name;
            monitor = thread.Monitor;

            Origin       = Anchor.TopRight;
            AutoSizeAxes = Axes.Both;
            Alpha        = alpha_when_active;

            bool hasCounters = monitor.ActiveCounters.Any(b => b);

            Child = new Container
            {
                AutoSizeAxes = Axes.Both,
                Children     = new[]
                {
                    new Container
                    {
                        Origin           = Anchor.TopRight,
                        AutoSizeAxes     = Axes.X,
                        RelativeSizeAxes = Axes.Y,
                        Children         = new[]
                        {
                            labelText = new SpriteText
                            {
                                Text     = Name,
                                Origin   = Anchor.BottomCentre,
                                Anchor   = Anchor.CentreLeft,
                                Rotation = -90,
                            },
                            !hasCounters
                                ? new Container {
                                Width = 2
                            }
                                : new Container
                            {
                                Masking          = true,
                                CornerRadius     = 5,
                                AutoSizeAxes     = Axes.X,
                                RelativeSizeAxes = Axes.Y,
                                Margin           = new MarginPadding {
                                    Right = 2, Left = 2
                                },
                                Children = new Drawable[]
                                {
                                    counterBarBackground = new Sprite
                                    {
                                        Texture          = atlas.Add(1, HEIGHT),
                                        RelativeSizeAxes = Axes.Both,
                                        Size             = new Vector2(1, 1),
                                    },
                                    new FillFlowContainer
                                    {
                                        Direction          = FillDirection.Horizontal,
                                        AutoSizeAxes       = Axes.X,
                                        RelativeSizeAxes   = Axes.Y,
                                        ChildrenEnumerable =
                                            from StatisticsCounterType t in Enum.GetValues(typeof(StatisticsCounterType))
                                            where monitor.ActiveCounters[(int)t]
                                            select counterBars[t] = new CounterBar
                                        {
                                            Colour = getColour(t),
                                            Label  = t.ToString(),
                                        },
                                    },
                                }
                            }
                        }
                    },
                    mainContainer = new Container
                    {
                        Size     = new Vector2(WIDTH, HEIGHT),
                        Children = new[]
                        {
                            timeBarsContainer = new Container
                            {
                                Masking          = true,
                                CornerRadius     = 5,
                                RelativeSizeAxes = Axes.Both,
                                Children         = timeBars = new[]
                                {
                                    new TimeBar(atlas),
                                    new TimeBar(atlas),
                                },
                            },
                            fpsDisplay = new FpsDisplay(monitor.Clock)
                            {
                                Anchor = Anchor.BottomRight,
                                Origin = Anchor.BottomRight,
                            },
                            overlayContainer = new Container
                            {
                                RelativeSizeAxes = Axes.Both,
                                Alpha            = 0,
                                Children         = new[]
                                {
                                    new FillFlowContainer
                                    {
                                        Anchor       = Anchor.TopRight,
                                        Origin       = Anchor.TopRight,
                                        AutoSizeAxes = Axes.Both,
                                        Spacing      = new Vector2(5, 1),
                                        Padding      = new MarginPadding {
                                            Right = 5
                                        },
                                        ChildrenEnumerable =
                                            from PerformanceCollectionType t in Enum.GetValues(typeof(PerformanceCollectionType))
                                            select legendMapping[(int)t] = new SpriteText
                                        {
                                            Colour = getColour(t),
                                            Text   = t.ToString(),
                                            Alpha  = 0
                                        },
                                    },
                                    new SpriteText
                                    {
                                        Padding = new MarginPadding {
                                            Left = 4
                                        },
                                        Text = $@"{visible_ms_range}ms"
                                    },
                                    new SpriteText
                                    {
                                        Padding = new MarginPadding {
                                            Left = 4
                                        },
                                        Text   = @"0ms",
                                        Anchor = Anchor.BottomLeft,
                                        Origin = Anchor.BottomLeft
                                    }
                                }
                            }
                        }
                    }
                }
            };

            textureBufferStack = new BufferStack <byte>(timeBars.Length * WIDTH);
        }
Esempio n. 7
0
 public TextureUpload(int size, BufferStack <byte> bufferStack = null)
 {
     this.bufferStack = bufferStack ?? global_buffer_stack;
     Data             = this.bufferStack.ReserveBuffer(size);
 }
Esempio n. 8
0
 /// <summary>
 /// Create an empty raw texture with an optional <see cref="BufferStack{T}"/>. backing.
 /// </summary>
 /// <param name="width">The width of the texture.</param>
 /// <param name="height">The height of the texture.</param>
 /// <param name="bufferStack">The buffer stack to retrieve the Rgba32[] from.</param>
 public BufferStackTextureUpload(int width, int height, BufferStack <Rgba32> bufferStack)
 {
     this.bufferStack = bufferStack;
     RawData          = bufferStack.ReserveBuffer(width * height);
 }
Esempio n. 9
0
 public FrameTimeDisplay(string name, PerformanceMonitor monitor)
 {
     Name               = name;
     this.monitor       = monitor;
     textureBufferStack = new BufferStack <byte>(timeBars.Length * WIDTH);
 }
Esempio n. 10
0
        public FrameStatisticsDisplay(string name, PerformanceMonitor monitor, TextureAtlas atlas)
        {
            Name         = name;
            this.monitor = monitor;

            Origin       = Anchor.TopRight;
            AutoSizeAxes = Axes.Both;
            Alpha        = alpha_when_inactive;

            bool hasCounters = false;

            for (int i = 0; i < (int)StatisticsCounterType.AmountTypes; ++i)
            {
                if (monitor.Counters[i] != null)
                {
                    hasCounters = true;
                }
            }

            Children = new Drawable[]
            {
                new Container
                {
                    AutoSizeAxes = Axes.Both,
                    Children     = new[]
                    {
                        new Container
                        {
                            Origin           = Anchor.TopRight,
                            AutoSizeAxes     = Axes.X,
                            RelativeSizeAxes = Axes.Y,
                            Position         = new Vector2(-2, 0),
                            Children         = new[]
                            {
                                labelText = new SpriteText
                                {
                                    Text     = Name,
                                    Origin   = Anchor.BottomCentre,
                                    Anchor   = Anchor.CentreLeft,
                                    Rotation = -90,
                                    Position = new Vector2(-2, 0),
                                },
                                !hasCounters ? new Container() : new Container
                                {
                                    Masking          = true,
                                    CornerRadius     = 5,
                                    AutoSizeAxes     = Axes.X,
                                    RelativeSizeAxes = Axes.Y,
                                    Children         = new Drawable[]
                                    {
                                        counterBarBackground = new Sprite
                                        {
                                            Texture          = atlas.Add(1, HEIGHT),
                                            RelativeSizeAxes = Axes.Both,
                                            Size             = new Vector2(1, 1),
                                        },
                                        new FlowContainer
                                        {
                                            Direction        = FlowDirection.HorizontalOnly,
                                            AutoSizeAxes     = Axes.X,
                                            RelativeSizeAxes = Axes.Y,
                                            Children         = from StatisticsCounterType t in Enum.GetValues(typeof(StatisticsCounterType))
                                                               where t < StatisticsCounterType.AmountTypes && monitor.Counters[(int)t] != null
                                                               select counterBars[t] = new CounterBar
                                            {
                                                Colour = getColour(t),
                                                Label  = t.ToString(),
                                            },
                                        },
                                    }
                                }
                            }
                        },
                        mainContainer = new Container
                        {
                            Size     = new Vector2(WIDTH, HEIGHT),
                            Children = new[]
                            {
                                timeBarsContainer = new Container
                                {
                                    Masking          = true,
                                    CornerRadius     = 5,
                                    RelativeSizeAxes = Axes.Both,
                                    Children         = timeBars = new[]
                                    {
                                        new TimeBar(atlas),
                                        new TimeBar(atlas),
                                    },
                                },
                                fpsDisplay = new FpsDisplay(monitor.Clock)
                                {
                                    Anchor = Anchor.BottomRight,
                                    Origin = Anchor.BottomRight,
                                },
                                overlayContainer = new Container
                                {
                                    RelativeSizeAxes = Axes.Both,
                                    Alpha            = 0,
                                    Children         = new []
                                    {
                                        new FlowContainer
                                        {
                                            Anchor       = Anchor.TopRight,
                                            Origin       = Anchor.TopRight,
                                            AutoSizeAxes = Axes.Both,
                                            Spacing      = new Vector2(5, 1),
                                            Padding      = new MarginPadding {
                                                Right = 5
                                            },
                                            Children = from PerformanceCollectionType t in Enum.GetValues(typeof(PerformanceCollectionType))
                                                       where t < PerformanceCollectionType.Empty
                                                       select legendMapping[(int)t] = new SpriteText
                                            {
                                                Colour = getColour(t),
                                                Text   = t.ToString(),
                                                Alpha  = 0
                                            },
                                        },
                                        new SpriteText
                                        {
                                            Padding = new MarginPadding {
                                                Left = 4
                                            },
                                            Text = $@"{VISIBLE_MS_RANGE}ms"
                                        },
                                        new SpriteText
                                        {
                                            Padding = new MarginPadding {
                                                Left = 4
                                            },
                                            Text   = @"0ms",
                                            Anchor = Anchor.BottomLeft,
                                            Origin = Anchor.BottomLeft
                                        }
                                    }
                                }
                            }
                        }
                    }
                },
            };

            textureBufferStack = new BufferStack <byte>(timeBars.Length * WIDTH);
        }