Debugging/ScoreBoard.razor
@using Sandbox;
@using Sandbox.UI;
@inherits Panel
@namespace Sandbox

@*
    A simple leaderboard. It reads the whole chat roster from Streamer.Viewers and pulls each viewer's
    "poops" score off their Data bag - the same bag StreamPlayer.Poop() writes to. Because the score lives
    on the viewer, this UI never needs to know anything about avatars or StreamPlayer.
*@

<root>
    <h1>💩 Most Poops</h1>

    @foreach ( var entry in Scores.OrderByDescending( x => x.Poops ).Take( 10 ) )
    {
        <div>
            <div class="name">@entry.Viewer.DisplayName</div>
            <div class="score">@entry.Poops</div>
        </div>
    }
</root>

@code
{
    /// <summary>
    /// Every viewer in chat paired with their current poop score (0 if they haven't pooped yet).
    /// </summary>
    IEnumerable<(int Poops, Streamer.Viewer Viewer)> Scores =>
        Streamer.Viewers.Select( v => (v.Data.Get( "poops", 0 ), v) );

    /// <summary>
    /// Rebuild whenever the total score changes - i.e. whenever anyone poops.
    /// </summary>
    protected override int BuildHash() => System.HashCode.Combine( Scores.Sum( x => x.Poops ) );
}