enhanced ping graph
This commit is contained in:
parent
ccd5faf8a9
commit
e09c84a027
5 changed files with 167 additions and 115 deletions
|
@ -72,6 +72,7 @@
|
|||
<Compile Include="DcControl.Designer.cs">
|
||||
<DependentUpon>DcControl.cs</DependentUpon>
|
||||
</Compile>
|
||||
<Compile Include="Libre\PingGrapher.cs" />
|
||||
<Compile Include="Tab\ConfigForm.cs">
|
||||
<SubType>Form</SubType>
|
||||
</Compile>
|
||||
|
@ -95,7 +96,6 @@
|
|||
<DependentUpon>DutyOvForm.cs</DependentUpon>
|
||||
</Compile>
|
||||
<Compile Include="ThirdParty\Converter.cs" />
|
||||
<Compile Include="ThirdParty\FastGraphLine.cs" />
|
||||
<Compile Include="ThirdParty\LineDb.cs" />
|
||||
<Compile Include="ThirdParty\NativeMethods.cs" />
|
||||
<Compile Include="ThirdParty\ThreadWorker.cs" />
|
||||
|
|
148
Libre/PingGrapher.cs
Normal file
148
Libre/PingGrapher.cs
Normal file
|
@ -0,0 +1,148 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using System.Windows.Forms;
|
||||
using System.Drawing;
|
||||
|
||||
namespace DutyContent.Libre
|
||||
{
|
||||
class PingGrapher
|
||||
{
|
||||
private PictureBox _pbx;
|
||||
private Bitmap _bmp;
|
||||
private Font _fnt;
|
||||
|
||||
private int _count_per_line;
|
||||
|
||||
public int Width { get; private set; } = -1;
|
||||
public int Height { get; private set; } = -1;
|
||||
|
||||
public int Step { get; set; } = 20;
|
||||
|
||||
//
|
||||
public PingGrapher(PictureBox container_pbx)
|
||||
{
|
||||
_pbx = container_pbx;
|
||||
|
||||
_fnt = new Font(FontFamily.GenericSansSerif, 7.0f, FontStyle.Regular, GraphicsUnit.Pixel);
|
||||
}
|
||||
|
||||
//
|
||||
public void Enter()
|
||||
{
|
||||
if (_pbx == null)
|
||||
return;
|
||||
|
||||
if (Width != _pbx.ClientSize.Width || Height != _pbx.ClientSize.Height)
|
||||
{
|
||||
Width = _pbx.ClientSize.Width;
|
||||
Height = _pbx.ClientSize.Height;
|
||||
|
||||
_count_per_line = (Width - Step + Step) / Step + 1;
|
||||
|
||||
_bmp = new Bitmap(Width, Height);
|
||||
}
|
||||
|
||||
if (_bmp != null)
|
||||
{
|
||||
using (var g = Graphics.FromImage(_bmp))
|
||||
g.Clear(Color.Black);
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
class CalcData
|
||||
{
|
||||
public int[] Values { get; set; }
|
||||
public int Count { get; set; }
|
||||
|
||||
public int Min { get; set; } = int.MaxValue;
|
||||
public int Max { get; set; } = int.MinValue;
|
||||
|
||||
public int RangeMax { get; set; }
|
||||
public int RangeStep { get; set; }
|
||||
|
||||
public CalcData(List<int> lst, int count_per_line, int range_delta)
|
||||
{
|
||||
var at = Math.Max(lst.Count - count_per_line, 0);
|
||||
|
||||
Count = lst.Count - at;
|
||||
Values = new int[Count];
|
||||
|
||||
for (int j = 0, i = lst.Count - 1; i >= at; i--)
|
||||
{
|
||||
if (Min > lst[i]) Min = lst[i];
|
||||
if (Max < lst[i]) Max = lst[i];
|
||||
|
||||
Values[j++] = lst[i];
|
||||
}
|
||||
|
||||
var rf = (float)(Max + range_delta) / 10.0f;
|
||||
RangeMax = ((int)Math.Round(rf) + 1) * 10;
|
||||
|
||||
RangeStep =
|
||||
RangeMax < 100 ? 20 :
|
||||
RangeMax < 300 ? 40 :
|
||||
RangeMax < 1000 ? 100 : 200;
|
||||
}
|
||||
}
|
||||
|
||||
public void DrawValues(List<int> values)
|
||||
{
|
||||
if (_bmp == null || values.Count < 2)
|
||||
return;
|
||||
|
||||
var cd = new CalcData(values, _count_per_line, 5);
|
||||
var height = (float)Height;
|
||||
var scale = height / cd.RangeMax;
|
||||
|
||||
using (var g = Graphics.FromImage(_bmp))
|
||||
{
|
||||
float f;
|
||||
int u;
|
||||
|
||||
for (var i = cd.RangeStep; i < cd.RangeMax; i += cd.RangeStep)
|
||||
{
|
||||
f = height - i * scale;
|
||||
u = (int)f;
|
||||
|
||||
g.DrawLine(Pens.DarkBlue, 0, u, Width - 1, u);
|
||||
g.DrawString(i.ToString(), _fnt, Brushes.DarkGray, 0.0f, f);
|
||||
}
|
||||
|
||||
var pen = new Pen(Color.White, 2.0f);
|
||||
|
||||
#if false
|
||||
u = 0;
|
||||
|
||||
// linear
|
||||
for (var i = 0; i < cd.Count - 1; i++)
|
||||
{
|
||||
var y1 = height - cd.Values[i] * scale;
|
||||
var y2 = height - cd.Values[i + 1] * scale;
|
||||
|
||||
g.DrawLine(pen, u, y1, u + Step, y2);
|
||||
|
||||
u += Step;
|
||||
}
|
||||
#else
|
||||
// curved
|
||||
u = 10;
|
||||
var pts = new PointF[cd.Count - 1];
|
||||
for (var i = 0; i < cd.Count - 1; i++, u += Step)
|
||||
pts[i] = new PointF(u, height - cd.Values[i] * scale);
|
||||
g.DrawCurve(pen, pts, 0.6f);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
public void Leave()
|
||||
{
|
||||
_pbx.Image = _bmp;
|
||||
_pbx.Refresh();
|
||||
}
|
||||
}
|
||||
}
|
|
@ -123,5 +123,12 @@ namespace DutyContent
|
|||
string msg = ExceptionPattern.Replace(ex.Message, "{{$1}}");
|
||||
Write(Color.Red, $"{text}: {msg}");
|
||||
}
|
||||
|
||||
// exception
|
||||
public static void Ex(Exception ex)
|
||||
{
|
||||
string msg = ExceptionPattern.Replace(ex.Message, "{{$1}}");
|
||||
Write(Color.Red, $"EX: {msg}");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -31,7 +31,7 @@ namespace DutyContent.Tab
|
|||
private System.Timers.Timer _ping_timer;
|
||||
private long _ping_last;
|
||||
private Color _ping_color = Color.Transparent;
|
||||
private ThirdParty.FastGraphLine _ping_graph;
|
||||
private Libre.PingGrapher _ping_grpr;
|
||||
private List<int> _ping_keeps = new List<int>();
|
||||
|
||||
public DutyForm()
|
||||
|
@ -41,7 +41,8 @@ namespace DutyContent.Tab
|
|||
InitializeComponent();
|
||||
|
||||
_overlay = new Overlay.DutyOvForm();
|
||||
_ping_graph = new ThirdParty.FastGraphLine(pbxPingGraph);
|
||||
_ping_grpr = new Libre.PingGrapher(pbxPingGraph);
|
||||
_ping_keeps.Add(0);
|
||||
}
|
||||
|
||||
private void DutyTabForm_FormClosing(object sender, FormClosingEventArgs e)
|
||||
|
@ -135,7 +136,10 @@ namespace DutyContent.Tab
|
|||
_ping_timer.Elapsed += (sender, e) => PingOnce();
|
||||
|
||||
if (DcConfig.Duty.UsePing)
|
||||
{
|
||||
PingOnce();
|
||||
_ping_timer.Start();
|
||||
}
|
||||
}
|
||||
|
||||
public void PluginDeinitialize()
|
||||
|
@ -1442,12 +1446,12 @@ namespace DutyContent.Tab
|
|||
if (DcConfig.Duty.PingGraph)
|
||||
{
|
||||
_ping_keeps.Add((int)rtt);
|
||||
if (_ping_keeps.Count > 100)
|
||||
_ping_keeps.Remove(0);
|
||||
if (_ping_keeps.Count > 120)
|
||||
_ping_keeps.RemoveAt(0);
|
||||
|
||||
_ping_graph.Enter();
|
||||
_ping_graph.SetValues(_ping_keeps);
|
||||
WorkerAct.Invoker(() => _ping_graph.Leave());
|
||||
_ping_grpr.Enter();
|
||||
_ping_grpr.DrawValues(_ping_keeps);
|
||||
WorkerAct.Invoker(() => _ping_grpr.Leave());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
107
ThirdParty/FastGraphLine.cs
vendored
107
ThirdParty/FastGraphLine.cs
vendored
|
@ -1,107 +0,0 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Drawing;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using System.Windows.Forms;
|
||||
|
||||
namespace DutyContent.ThirdParty
|
||||
{
|
||||
class FastGraphLine
|
||||
{
|
||||
private PictureBox _pbx;
|
||||
private Bitmap _bmp;
|
||||
|
||||
private int _midv;
|
||||
private int _dcnt;
|
||||
|
||||
public int Width { get; private set; } = -1;
|
||||
public int Height { get; private set; } = -1;
|
||||
|
||||
//
|
||||
public FastGraphLine(PictureBox pbx)
|
||||
{
|
||||
_pbx = pbx;
|
||||
}
|
||||
|
||||
//
|
||||
public void Enter()
|
||||
{
|
||||
if (_pbx == null)
|
||||
return;
|
||||
|
||||
if (Width != _pbx.ClientSize.Width || Height != _pbx.ClientSize.Height)
|
||||
{
|
||||
Width = _pbx.ClientSize.Width;
|
||||
Height = _pbx.ClientSize.Height;
|
||||
|
||||
_midv = Height / 2;
|
||||
_dcnt = (Width - 40) / 20;
|
||||
|
||||
_bmp = new Bitmap(Width, Height);
|
||||
}
|
||||
|
||||
if (_bmp != null)
|
||||
{
|
||||
using (var g = Graphics.FromImage(_bmp))
|
||||
{
|
||||
g.Clear(Color.Black);
|
||||
g.DrawLine(Pens.DarkBlue, 0, _midv, Width - 1, _midv);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
public void SetValues(List<int> vs, int mindelta = 5, int maxdelta = 5)
|
||||
{
|
||||
if (_bmp == null && vs.Count >= 2)
|
||||
return;
|
||||
|
||||
int min = int.MaxValue, max = int.MinValue;
|
||||
int cnt = vs.Count - _dcnt;
|
||||
|
||||
if (cnt < 0)
|
||||
cnt = 0;
|
||||
|
||||
for (var i = vs.Count - 1; i >= cnt; i--)
|
||||
{
|
||||
if (min > vs[i])
|
||||
min = vs[i];
|
||||
if (max < vs[i])
|
||||
max = vs[i];
|
||||
}
|
||||
|
||||
min -= mindelta;
|
||||
max += maxdelta;
|
||||
|
||||
//
|
||||
MesgLog.L("Count: {0}, MM: {1}/{2}", vs.Count, min, max);
|
||||
|
||||
float scale = (float)Height / (float)(max - min);
|
||||
int xx = 10;
|
||||
|
||||
using (var g = Graphics.FromImage(_bmp))
|
||||
{
|
||||
Pen pen = new Pen(Color.White, 2.0f);
|
||||
|
||||
for (var i = vs.Count - 2; i >= cnt; i--)
|
||||
{
|
||||
var y1 = (int)((vs[i + 1] - min) * scale);
|
||||
var y2 = (int)((vs[i] - min) * scale);
|
||||
|
||||
g.DrawLine(pen, xx, y1, xx + 10, y2);
|
||||
|
||||
xx += 10;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
public void Leave()
|
||||
{
|
||||
_pbx.Image = _bmp;
|
||||
_pbx.Refresh();
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue