自定义 Tick 格式化程序
用户可以自定义用于从刻度位置创建刻度标签的逻辑。旧版本的 ScottPlot 使用 ManualTickPositions 方法实现了这一点。
double[] xs = Generate.Consecutive(100, 1, -50);
WpfPlot1.Plot.Add.Scatter(xs, Generate.Sin(100));
WpfPlot1.Plot.Add.Scatter(xs, Generate.Cos(100));
// create a static function containing the string formatting logic
static string CustomFormatter(double position)
{
if (position == 0)
return "0";
else if (position > 0)
return $"+{position}";
else
return $"({-position})";
}
// create a custom tick generator using your custom label formatter
ScottPlot.TickGenerators.NumericAutomatic myTickGenerator = new()
{
LabelFormatter = CustomFormatter
};
// tell an axis to use the custom tick generator
WpfPlot1.Plot.Axes.Bottom.TickGenerator = myTickGenerator;
WpfPlot1.Refresh();
DateTimeAutomatic Tick 格式化程序
用户可以自定义用于从刻度位置创建日期时间刻度标签的逻辑。
// plot data using DateTime values on the horizontal axis
DateTime[] xs = Generate.ConsecutiveHours(100);
double[] ys = Generate.RandomWalk(100);
WpfPlot1.Plot.Add.Scatter(xs, ys);
// setup the bottom axis to use DateTime ticks
var axis = WpfPlot1.Plot.Axes.DateTimeTicksBottom();
// create a custom formatter to return a string with
// date only when zoomed out and time only when zoomed in
static string CustomFormatter(DateTime dt)
{
bool isMidnight = dt is { Hour: 0, Minute: 0, Second: 0 };
return isMidnight
? DateOnly.FromDateTime(dt).ToString()
: TimeOnly.FromDateTime(dt).ToString();
}
// apply our custom tick formatter
var tickGen = (ScottPlot.TickGenerators.DateTimeAutomatic)axis.TickGenerator;
tickGen.LabelFormatter = CustomFormatter;
WpfPlot1.Refresh();
自定义 Tick 生成器
Tick 生成器确定 tick 的放置位置,并且还包含从 tick 位置生成 tick 标签的逻辑。可以创建替代 tick 生成器并将其分配给轴。ScottPlot 提供了一些常见的即时报价生成器,用户还可以选择创建自己的。
WpfPlot1.Plot.Add.Signal(Generate.Sin(51));
WpfPlot1.Plot.Add.Signal(Generate.Cos(51));
WpfPlot1.Plot.Axes.Bottom.TickGenerator = new ScottPlot.TickGenerators.NumericFixedInterval(11);
WpfPlot1.Refresh();
SetTicks 快捷方式
默认坐标区有一个 SetTicks() 辅助方法,该方法将默认的更新生成器替换为预先加载了提供的更新中的手动更新生成器。
// display sample data
WpfPlot1.Plot.Add.Signal(Generate.Sin());
WpfPlot1.Plot.Add.Signal(Generate.Cos());
// use manually defined ticks
double[] tickPositions = { 10, 25, 40 };
string[] tickLabels = { "Alpha", "Beta", "Gamma" };
WpfPlot1.Plot.Axes.Bottom.SetTicks(tickPositions, tickLabels);
WpfPlot1.Refresh();
自定义即时报价位置
希望对主要和次要刻度位置和标签进行更多控制的用户可以实例化手动刻度生成器,根据需要进行设置,然后将其分配给正在自定义的轴
// display sample data
WpfPlot1.Plot.Add.Signal(Generate.Sin());
WpfPlot1.Plot.Add.Signal(Generate.Cos());
// create a manual tick generator and add ticks
ScottPlot.TickGenerators.NumericManual ticks = new();
// add major ticks with their labels
ticks.AddMajor(0, "zero");
ticks.AddMajor(20, "twenty");
ticks.AddMajor(50, "fifty");
// add minor ticks
ticks.AddMinor(22);
ticks.AddMinor(25);
ticks.AddMinor(32);
ticks.AddMinor(35);
ticks.AddMinor(42);
ticks.AddMinor(45);
// tell the horizontal axis to use the custom tick generator
WpfPlot1.Plot.Axes.Bottom.TickGenerator = ticks;
WpfPlot1.Refresh();
自定义刻度日期时间
用户可以使用 DateTime 单位定义自定义刻度
DateTime[] dates = Generate.ConsecutiveDays(100);
double[] values = Generate.RandomWalk(100);
WpfPlot1.Plot.Add.Scatter(dates, values);
// create a manual DateTime tick generator and add ticks
ScottPlot.TickGenerators.DateTimeManual ticks = new();
// add ticks for Mondays only
foreach (DateTime date in dates)
{
if (date.DayOfWeek == DayOfWeek.Monday)
{
string label = date.DayOfYear.ToString();
ticks.AddMajor(date, label);
}
}
// tell the horizontal axis to use the custom tick generator
WpfPlot1.Plot.Axes.Bottom.TickGenerator = ticks;
// style the plot
WpfPlot1.Plot.Title("Monday Ticks");
WpfPlot1.Plot.XLabel("Day of the Year");
WpfPlot1.Refresh();
旋转的刻度标签
用户可以自定义刻度标签旋转。
WpfPlot1.Plot.Add.Signal(Generate.Sin());
WpfPlot1.Plot.Add.Signal(Generate.Cos());
WpfPlot1.Plot.Axes.Bottom.TickLabelStyle.Rotation = -45;
WpfPlot1.Plot.Axes.Bottom.TickLabelStyle.Alignment = Alignment.MiddleRight;
WpfPlot1.Refresh();
带有长标签的旋转刻度
可以增加轴大小以适应旋转或长刻度标签。
// create a bar plot
double[] values = { 5, 10, 7, 13, 25, 60 };
WpfPlot1.Plot.Add.Bars(values);
WpfPlot1.Plot.Axes.Margins(bottom: 0);
// create a tick for each bar
Tick[] ticks =
{
new(0, "First Long Title"),
new(1, "Second Long Title"),
new(2, "Third Long Title"),
new(3, "Fourth Long Title"),
new(4, "Fifth Long Title"),
new(5, "Sixth Long Title")
};
WpfPlot1.Plot.Axes.Bottom.TickGenerator = new ScottPlot.TickGenerators.NumericManual(ticks);
WpfPlot1.Plot.Axes.Bottom.TickLabelStyle.Rotation = 45;
WpfPlot1.Plot.Axes.Bottom.TickLabelStyle.Alignment = Alignment.MiddleLeft;
// determine the width of the largest tick label
float largestLabelWidth = 0;
using SKPaint paint = new();
foreach (Tick tick in ticks)
{
PixelSize size = WpfPlot1.Plot.Axes.Bottom.TickLabelStyle.Measure(tick.Label, paint).Size;
largestLabelWidth = Math.Max(largestLabelWidth, size.Width);
}
// ensure axis panels do not get smaller than the largest label
WpfPlot1.Plot.Axes.Bottom.MinimumSize = largestLabelWidth;
WpfPlot1.Plot.Axes.Right.MinimumSize = largestLabelWidth;
WpfPlot1.Refresh();
禁用网格线
用户可以禁用特定轴的网格线。
WpfPlot1.Plot.Add.Signal(Generate.Sin());
WpfPlot1.Plot.Add.Signal(Generate.Cos());
WpfPlot1.Plot.Grid.XAxisStyle.IsVisible = true;
WpfPlot1.Plot.Grid.YAxisStyle.IsVisible = false;
WpfPlot1.Refresh();
最小刻度间距
通过设置一个值来指示刻度标签之间的最小距离(以像素为单位),可以增加刻度之间的间距。
WpfPlot1.Plot.Add.Signal(Generate.Sin(51));
WpfPlot1.Plot.Add.Signal(Generate.Cos(51));
ScottPlot.TickGenerators.NumericAutomatic tickGenX = new();
tickGenX.MinimumTickSpacing = 50;
WpfPlot1.Plot.Axes.Bottom.TickGenerator = tickGenX;
ScottPlot.TickGenerators.NumericAutomatic tickGenY = new();
tickGenY.MinimumTickSpacing = 25;
WpfPlot1.Plot.Axes.Left.TickGenerator = tickGenY;
WpfPlot1.Refresh();
刻度密度
Tick density (刻度密度) 可以调整为默认值的分数。与 MinimumTickSpacing 不同,此策略知道刻度标签的大小并相应地进行调整。
WpfPlot1.Plot.Add.Signal(Generate.Sin(51));
WpfPlot1.Plot.Add.Signal(Generate.Cos(51));
ScottPlot.TickGenerators.NumericAutomatic tickGenX = new();
tickGenX.TickDensity = 0.2;
WpfPlot1.Plot.Axes.Bottom.TickGenerator = tickGenX;
ScottPlot.TickGenerators.NumericAutomatic tickGenY = new();
tickGenY.TickDensity = 0.2;
WpfPlot1.Plot.Axes.Left.TickGenerator = tickGenY;
WpfPlot1.Refresh();
Tick Count
可以提供目标数量的报价,自动报价生成器将尝试放置该数量的报价。此策略允许刻度密度随着图像大小的增加而减小。
WpfPlot1.Plot.Add.Signal(Generate.Sin(51));
WpfPlot1.Plot.Add.Signal(Generate.Cos(51));
ScottPlot.TickGenerators.NumericAutomatic tickGenX = new();
tickGenX.TargetTickCount = 3;
WpfPlot1.Plot.Axes.Bottom.TickGenerator = tickGenX;
ScottPlot.TickGenerators.NumericAutomatic tickGenY = new();
tickGenY.TargetTickCount = 3;
WpfPlot1.Plot.Axes.Left.TickGenerator = tickGenY;
WpfPlot1.Refresh();
次刻度密度
次要刻度线是在主要刻度线之间的间隔自动生成的。默认情况下,它们的间距是均匀的,但可以自定义它们的密度。
// plot sample data
double[] xs = Generate.Consecutive(100);
double[] ys = Generate.NoisyExponential(100);
var sp = WpfPlot1.Plot.Add.Scatter(xs, ys);
sp.LineWidth = 0;
// create a minor tick generator with 10 minor ticks per major tick
ScottPlot.TickGenerators.EvenlySpacedMinorTickGenerator minorTickGen = new(10);
// create a numeric tick generator that uses our custom minor tick generator
ScottPlot.TickGenerators.NumericAutomatic tickGen = new();
tickGen.MinorTickGenerator = minorTickGen;
// tell the left axis to use our custom tick generator
WpfPlot1.Plot.Axes.Left.TickGenerator = tickGen;
WpfPlot1.Refresh();
对数刻度刻度线
可以通过对要显示的数据进行对数缩放,然后自定义次要刻度和网格来实现对数缩放的外观。
// start with original data
double[] xs = Generate.Consecutive(100);
double[] ys = Generate.NoisyExponential(100);
// log-scale the data and account for negative values
double[] logYs = ys.Select(Math.Log10).ToArray();
// add log-scaled data to the plot
var sp = WpfPlot1.Plot.Add.Scatter(xs, logYs);
sp.LineWidth = 0;
// create a minor tick generator that places log-distributed minor ticks
ScottPlot.TickGenerators.LogMinorTickGenerator minorTickGen = new();
// create a numeric tick generator that uses our custom minor tick generator
ScottPlot.TickGenerators.NumericAutomatic tickGen = new();
tickGen.MinorTickGenerator = minorTickGen;
// create a custom tick formatter to set the label text for each tick
static string LogTickLabelFormatter(double y) => $"{Math.Pow(10, y):N0}";
// tell our major tick generator to only show major ticks that are whole integers
tickGen.IntegerTicksOnly = true;
// tell our custom tick generator to use our new label formatter
tickGen.LabelFormatter = LogTickLabelFormatter;
// tell the left axis to use our custom tick generator
WpfPlot1.Plot.Axes.Left.TickGenerator = tickGen;
// show grid lines for minor ticks
WpfPlot1.Plot.Grid.MajorLineColor = Colors.Black.WithOpacity(.15);
WpfPlot1.Plot.Grid.MinorLineColor = Colors.Black.WithOpacity(.05);
WpfPlot1.Plot.Grid.MinorLineWidth = 1;
WpfPlot1.Refresh();