2016-03-26 13:51:42 +11:00
|
|
|
|
// ClassicalSharp copyright 2014-2016 UnknownShadow200 | Licensed under MIT
|
|
|
|
|
using System;
|
2015-05-09 18:37:20 +10:00
|
|
|
|
using System.Drawing;
|
2016-03-27 09:33:51 +11:00
|
|
|
|
using ClassicalSharp.Entities;
|
2015-10-08 19:39:27 +11:00
|
|
|
|
using ClassicalSharp.GraphicsAPI;
|
2014-12-17 14:47:17 +11:00
|
|
|
|
|
2016-03-27 09:33:51 +11:00
|
|
|
|
namespace ClassicalSharp.Gui {
|
2014-12-17 14:47:17 +11:00
|
|
|
|
|
|
|
|
|
public class FpsScreen : Screen {
|
|
|
|
|
|
2015-10-28 07:20:15 +11:00
|
|
|
|
Font font, posFont;
|
2015-09-02 19:44:24 +10:00
|
|
|
|
StringBuffer text;
|
2015-10-08 19:39:27 +11:00
|
|
|
|
|
2015-09-23 19:53:12 +10:00
|
|
|
|
public FpsScreen( Game game ) : base( game ) {
|
2015-12-30 21:03:32 +11:00
|
|
|
|
text = new StringBuffer( 128 );
|
2014-12-17 14:47:17 +11:00
|
|
|
|
}
|
2015-10-28 07:20:15 +11:00
|
|
|
|
|
2015-10-08 19:39:27 +11:00
|
|
|
|
TextWidget fpsTextWidget, hackStatesWidget;
|
|
|
|
|
Texture posTexture;
|
2015-10-03 09:36:29 +10:00
|
|
|
|
public override void Render( double delta ) {
|
2014-12-17 14:47:17 +11:00
|
|
|
|
UpdateFPS( delta );
|
2015-10-08 19:39:27 +11:00
|
|
|
|
if( game.HideGui || !game.ShowFPS ) return;
|
2015-09-11 19:39:48 +10:00
|
|
|
|
|
2016-03-30 22:43:08 +11:00
|
|
|
|
api.Texturing = true;
|
2014-12-17 14:47:17 +11:00
|
|
|
|
fpsTextWidget.Render( delta );
|
2016-03-26 17:45:52 +11:00
|
|
|
|
if( !game.ClassicMode && game.activeScreen == null ) {
|
2015-10-21 06:15:49 +11:00
|
|
|
|
UpdateHackState( false );
|
2015-10-11 20:22:20 +11:00
|
|
|
|
DrawPosition();
|
|
|
|
|
hackStatesWidget.Render( delta );
|
|
|
|
|
}
|
2016-03-30 22:43:08 +11:00
|
|
|
|
api.Texturing = false;
|
2014-12-17 14:47:17 +11:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
double accumulator, maxDelta;
|
2016-02-05 18:51:06 +11:00
|
|
|
|
int fpsCount, totalSeconds;
|
|
|
|
|
int oldMinutes = -1;
|
|
|
|
|
|
2015-10-03 09:36:29 +10:00
|
|
|
|
void UpdateFPS( double delta ) {
|
2014-12-17 14:47:17 +11:00
|
|
|
|
fpsCount++;
|
|
|
|
|
maxDelta = Math.Max( maxDelta, delta );
|
|
|
|
|
accumulator += delta;
|
|
|
|
|
|
2015-10-03 09:36:29 +10:00
|
|
|
|
if( accumulator >= 1 ) {
|
|
|
|
|
int index = 0;
|
2016-02-05 18:51:06 +11:00
|
|
|
|
totalSeconds++;
|
2016-03-26 17:45:52 +11:00
|
|
|
|
if( game.ClassicMode ) {
|
2016-01-31 00:27:29 +11:00
|
|
|
|
text.Clear()
|
|
|
|
|
.AppendNum( ref index, (int)(fpsCount / accumulator) ).Append( ref index, " fps, " )
|
|
|
|
|
.AppendNum( ref index, game.ChunkUpdates ).Append( ref index, " chunk updates" );
|
|
|
|
|
} else {
|
|
|
|
|
text.Clear()
|
2015-10-03 09:36:29 +10:00
|
|
|
|
.Append( ref index, "FPS: " ).AppendNum( ref index, (int)(fpsCount / accumulator) )
|
|
|
|
|
.Append( ref index, " (min " ).AppendNum( ref index, (int)(1f / maxDelta) )
|
|
|
|
|
.Append( ref index, "), chunks/s: " ).AppendNum( ref index, game.ChunkUpdates )
|
|
|
|
|
.Append( ref index, ", vertices: " ).AppendNum( ref index, game.Vertices );
|
2016-01-31 00:27:29 +11:00
|
|
|
|
}
|
2016-02-05 18:51:06 +11:00
|
|
|
|
int minutes = totalSeconds / 60;
|
|
|
|
|
if( minutes != oldMinutes && game.ShowClock ) {
|
|
|
|
|
oldMinutes = minutes;
|
|
|
|
|
TimeSpan span = TimeSpan.FromMinutes( minutes );
|
|
|
|
|
string format = null;
|
|
|
|
|
|
|
|
|
|
if( span.TotalDays > 1 )
|
|
|
|
|
format = "&eBeen playing for {2} day" + Q( span.Days ) + ", {1} hour" + Q( span.Hours ) + ", {0} min" + Q( span.Minutes );
|
|
|
|
|
else if( span.TotalHours > 1 )
|
2016-04-11 18:54:11 +10:00
|
|
|
|
format = "&eBeen playing for {1} hour" + Q( span.Hours ) + ", {0} min" + Q( span.Minutes );
|
2016-02-05 18:51:06 +11:00
|
|
|
|
else
|
|
|
|
|
format = "&eBeen playing for {0} min" + Q( span.Minutes );
|
|
|
|
|
string spanText = String.Format( format, span.Minutes, span.Hours, span.Days );
|
|
|
|
|
game.Chat.Add( spanText, MessageType.ClientClock );
|
|
|
|
|
}
|
2015-05-21 16:22:48 +10:00
|
|
|
|
|
2015-09-05 07:36:51 +10:00
|
|
|
|
string textString = text.GetString();
|
2015-05-21 16:22:48 +10:00
|
|
|
|
fpsTextWidget.SetText( textString );
|
2014-12-17 14:47:17 +11:00
|
|
|
|
maxDelta = 0;
|
|
|
|
|
accumulator = 0;
|
|
|
|
|
fpsCount = 0;
|
2015-09-01 18:03:36 +10:00
|
|
|
|
game.ChunkUpdates = 0;
|
2014-12-17 14:47:17 +11:00
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2016-02-05 18:51:06 +11:00
|
|
|
|
string Q( int value ) { return value == 1 ? "" : "s"; }
|
|
|
|
|
|
2014-12-17 14:47:17 +11:00
|
|
|
|
public override void Init() {
|
2016-02-01 18:11:06 +11:00
|
|
|
|
font = new Font( game.FontName, 13 );
|
|
|
|
|
posFont = new Font( game.FontName, 12, FontStyle.Italic );
|
2015-10-28 07:20:15 +11:00
|
|
|
|
game.Events.ChatFontChanged += ChatFontChanged;
|
|
|
|
|
|
|
|
|
|
fpsTextWidget = new ChatTextWidget( game, font );
|
2015-10-27 19:46:22 +11:00
|
|
|
|
fpsTextWidget.XOffset = 2;
|
|
|
|
|
fpsTextWidget.YOffset = 2;
|
2014-12-17 14:47:17 +11:00
|
|
|
|
fpsTextWidget.Init();
|
2015-10-28 16:40:36 +11:00
|
|
|
|
string fpsText = text.Length > 0 ? text.GetString() :
|
|
|
|
|
"FPS: no data yet";
|
|
|
|
|
fpsTextWidget.SetText( fpsText );
|
2015-10-08 19:39:27 +11:00
|
|
|
|
MakePosTextWidget();
|
|
|
|
|
|
2015-10-28 07:20:15 +11:00
|
|
|
|
hackStatesWidget = new ChatTextWidget( game, posFont );
|
2015-10-27 19:46:22 +11:00
|
|
|
|
hackStatesWidget.XOffset = 2;
|
|
|
|
|
hackStatesWidget.YOffset = fpsTextWidget.Height + posHeight + 2;
|
2015-10-08 19:39:27 +11:00
|
|
|
|
hackStatesWidget.Init();
|
2015-10-28 07:20:15 +11:00
|
|
|
|
UpdateHackState( true );
|
2014-12-17 14:47:17 +11:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public override void Dispose() {
|
2015-05-09 18:37:20 +10:00
|
|
|
|
font.Dispose();
|
2015-10-08 19:39:27 +11:00
|
|
|
|
posFont.Dispose();
|
2014-12-17 14:47:17 +11:00
|
|
|
|
fpsTextWidget.Dispose();
|
2016-03-30 22:43:08 +11:00
|
|
|
|
api.DeleteTexture( ref posTexture );
|
2015-10-28 07:20:15 +11:00
|
|
|
|
game.Events.ChatFontChanged -= ChatFontChanged;
|
|
|
|
|
}
|
|
|
|
|
|
2015-11-30 14:16:48 +11:00
|
|
|
|
void ChatFontChanged( object sender, EventArgs e ) { Recreate(); }
|
2015-10-08 19:39:27 +11:00
|
|
|
|
|
2015-10-27 19:46:22 +11:00
|
|
|
|
public override void OnResize( int oldWidth, int oldHeight, int width, int height ) {
|
2015-10-09 16:47:39 +11:00
|
|
|
|
}
|
|
|
|
|
|
2015-10-08 19:39:27 +11:00
|
|
|
|
void DrawPosition() {
|
|
|
|
|
int index = 0;
|
2015-10-27 19:46:22 +11:00
|
|
|
|
TextureRec xy = new TextureRec( 2, posTexture.Y1, baseWidth, posTexture.Height );
|
2015-10-08 19:39:27 +11:00
|
|
|
|
TextureRec uv = new TextureRec( 0, 0, posTexture.U2, posTexture.V2 );
|
2015-10-21 18:30:18 +11:00
|
|
|
|
IGraphicsApi.Make2DQuad( xy, uv, game.ModelCache.vertices, ref index );
|
2015-10-08 19:39:27 +11:00
|
|
|
|
|
|
|
|
|
Vector3I pos = Vector3I.Floor( game.LocalPlayer.Position );
|
2015-10-27 19:46:22 +11:00
|
|
|
|
curX = baseWidth + 2;
|
2015-10-08 19:39:27 +11:00
|
|
|
|
AddChar( 13, ref index );
|
|
|
|
|
AddInt( pos.X, ref index, true );
|
|
|
|
|
AddInt( pos.Y, ref index, true );
|
|
|
|
|
AddInt( pos.Z, ref index, false );
|
|
|
|
|
AddChar( 14, ref index );
|
|
|
|
|
|
2016-03-30 22:43:08 +11:00
|
|
|
|
api.BindTexture( posTexture.ID );
|
|
|
|
|
api.UpdateDynamicIndexedVb( DrawMode.Triangles,
|
2015-10-08 19:39:27 +11:00
|
|
|
|
game.ModelCache.vb, game.ModelCache.vertices, index, index * 6 / 4 );
|
|
|
|
|
}
|
|
|
|
|
|
2016-01-08 17:52:58 +11:00
|
|
|
|
bool speeding, halfSpeeding, noclip, fly;
|
2015-12-31 12:33:55 +11:00
|
|
|
|
int lastZoomFov;
|
2015-10-08 19:39:27 +11:00
|
|
|
|
void UpdateHackState( bool force ) {
|
2016-03-31 21:25:25 +11:00
|
|
|
|
HacksComponent hacks = game.LocalPlayer.Hacks;
|
|
|
|
|
if( force || hacks.Speeding != speeding || hacks.HalfSpeeding != halfSpeeding || hacks.Noclip != noclip ||
|
|
|
|
|
hacks.Flying != fly || game.ZoomFieldOfView != lastZoomFov ) {
|
|
|
|
|
speeding = hacks.Speeding; halfSpeeding = hacks.HalfSpeeding; noclip = hacks.Noclip; fly = hacks.Flying;
|
2015-12-31 12:33:55 +11:00
|
|
|
|
lastZoomFov = game.ZoomFieldOfView;
|
2015-10-08 19:39:27 +11:00
|
|
|
|
int index = 0;
|
|
|
|
|
text.Clear();
|
2016-01-02 22:51:38 +11:00
|
|
|
|
int defFov = Options.GetInt( OptionsKey.FieldOfView, 1, 150, 70 );
|
2015-10-08 19:39:27 +11:00
|
|
|
|
|
2015-12-31 13:52:58 +11:00
|
|
|
|
if( lastZoomFov != defFov ) text.Append( ref index, "Zoom fov " )
|
2015-12-31 12:33:55 +11:00
|
|
|
|
.AppendNum( ref index, lastZoomFov ).Append( ref index, " " );
|
2015-10-08 19:39:27 +11:00
|
|
|
|
if( fly ) text.Append( ref index, "Fly ON " );
|
2016-01-08 17:52:58 +11:00
|
|
|
|
if( speeding || halfSpeeding ) text.Append( ref index, "Speed ON " );
|
2015-10-08 19:39:27 +11:00
|
|
|
|
if( noclip ) text.Append( ref index, "Noclip ON " );
|
|
|
|
|
hackStatesWidget.SetText( text.GetString() );
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const string possibleChars = "0123456789-, ()";
|
|
|
|
|
int[] widths = new int[possibleChars.Length];
|
|
|
|
|
int baseWidth, curX, posHeight;
|
|
|
|
|
float texWidth;
|
|
|
|
|
void MakePosTextWidget() {
|
2015-10-19 18:19:05 +11:00
|
|
|
|
DrawTextArgs args = new DrawTextArgs( "", posFont, true );
|
2015-10-08 19:39:27 +11:00
|
|
|
|
for( int i = 0; i < possibleChars.Length; i++ ) {
|
2015-10-19 18:19:05 +11:00
|
|
|
|
args.Text = new String( possibleChars[i], 1 );
|
2015-10-28 16:40:36 +11:00
|
|
|
|
widths[i] = game.Drawer2D.MeasureChatSize( ref args ).Width;
|
2015-10-08 19:39:27 +11:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
using( IDrawer2D drawer = game.Drawer2D ) {
|
2015-10-19 18:19:05 +11:00
|
|
|
|
args.Text = "Feet pos: ";
|
2015-10-28 16:40:36 +11:00
|
|
|
|
Size size = game.Drawer2D.MeasureChatSize( ref args );
|
2015-10-08 19:39:27 +11:00
|
|
|
|
baseWidth = size.Width;
|
|
|
|
|
size.Width += 16 * possibleChars.Length;
|
|
|
|
|
posHeight = size.Height;
|
|
|
|
|
|
|
|
|
|
using( Bitmap bmp = IDrawer2D.CreatePow2Bitmap( size ) ) {
|
|
|
|
|
drawer.SetBitmap( bmp );
|
2015-10-28 16:40:36 +11:00
|
|
|
|
drawer.DrawChatText( ref args, 0, 0 );
|
2015-10-08 19:39:27 +11:00
|
|
|
|
|
|
|
|
|
for( int i = 0; i < possibleChars.Length; i++ ) {
|
|
|
|
|
args.Text = new String( possibleChars[i], 1 );
|
2015-10-28 16:40:36 +11:00
|
|
|
|
drawer.DrawChatText( ref args, baseWidth + 16 * i, 0 );
|
2015-10-08 19:39:27 +11:00
|
|
|
|
}
|
|
|
|
|
|
2015-10-27 19:46:22 +11:00
|
|
|
|
int y = fpsTextWidget.Height + 2;
|
2015-10-08 19:39:27 +11:00
|
|
|
|
posTexture = drawer.Make2DTexture( bmp, size, 0, y );
|
|
|
|
|
posTexture.U2 = (float)baseWidth / bmp.Width;
|
|
|
|
|
posTexture.Width = baseWidth;
|
|
|
|
|
texWidth = bmp.Width;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void AddChar( int charIndex, ref int index ) {
|
|
|
|
|
int width = widths[charIndex];
|
|
|
|
|
TextureRec xy = new TextureRec( curX, posTexture.Y1, width, posTexture.Height );
|
|
|
|
|
TextureRec uv = new TextureRec( (baseWidth + charIndex * 16) / texWidth, 0, width / texWidth, posTexture.V2 );
|
|
|
|
|
|
|
|
|
|
curX += width;
|
2015-10-21 18:30:18 +11:00
|
|
|
|
IGraphicsApi.Make2DQuad( xy, uv, game.ModelCache.vertices, ref index );
|
2015-10-08 19:39:27 +11:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void AddInt( int value, ref int index, bool more ) {
|
|
|
|
|
if( value < 0 )
|
|
|
|
|
AddChar( 10, ref index );
|
|
|
|
|
|
|
|
|
|
int count = 0;
|
|
|
|
|
value = Reverse( Math.Abs( value ), out count );
|
|
|
|
|
for( int i = 0; i < count; i++ ) {
|
|
|
|
|
AddChar( value % 10, ref index ); value /= 10;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if( more )
|
|
|
|
|
AddChar( 11, ref index );
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static int Reverse( int value, out int count ) {
|
|
|
|
|
int orig = value, reversed = 0;
|
|
|
|
|
count = 1; value /= 10;
|
|
|
|
|
while( value > 0 ) {
|
|
|
|
|
count++; value /= 10;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
for( int i = 0; i < count; i++ ) {
|
|
|
|
|
reversed *= 10;
|
|
|
|
|
reversed += orig % 10;
|
|
|
|
|
orig /= 10;
|
|
|
|
|
}
|
|
|
|
|
return reversed;
|
2014-12-17 14:47:17 +11:00
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|