Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

SignalXY: last point sometimes does not get rendered #3812

Closed
swharden opened this issue May 8, 2024 · 5 comments · Fixed by #3918
Closed

SignalXY: last point sometimes does not get rendered #3812

swharden opened this issue May 8, 2024 · 5 comments · Fixed by #3918

Comments

@swharden
Copy link
Member

swharden commented May 8, 2024

Perhaps because a binning issue?
sigxylast

@swharden
Copy link
Member Author

swharden commented Jun 7, 2024

This is reproducible and only affects "high density mode"

using ScottPlot;

namespace Sandbox.WinForms;

public partial class Form1 : Form
{
    public Form1()
    {
        InitializeComponent();

        int count = 1000;
        double[] xs = Generate.Consecutive(count);
        double[] ys = Generate.RandomWalk(count);
        ys[^1] = -100;

        formsPlot1.Plot.Add.SignalXY(xs, ys);
    }
}

@swharden
Copy link
Member Author

swharden commented Jun 7, 2024

Interestingly, it's only the very last point, and only about half the frames. It "flickers" as you zoom horizontally.

image

using ScottPlot;

namespace Sandbox.WinForms;

public partial class Form1 : Form
{
    public Form1()
    {
        InitializeComponent();

        int count = 1000;
        double[] xs = Generate.Consecutive(count);
        double[] ys = Generate.RandomWalk(count);
        ys[0] = -100;
        ys[499] = -100;
        ys[999] = -100;

        var sig = formsPlot1.Plot.Add.SignalXY(xs, ys);
        sig.MarkerShape = MarkerShape.OpenCircle;
        sig.MarkerColor = Colors.Black;
        sig.MarkerSize = 10;
    }
}

@swharden
Copy link
Member Author

swharden commented Jun 7, 2024

I'm pretty sure the issue is in here

private IEnumerable<Pixel> GetColumnPixelsX(int pixelColumnIndex, IndexRange rng, RenderPack rp, IAxes axes)
{
float xPixel = pixelColumnIndex + rp.DataRect.Left;
double unitsPerPixelX = axes.XAxis.Width / rp.DataRect.Width;
double start = axes.XAxis.Min + unitsPerPixelX * pixelColumnIndex;
double end = start + unitsPerPixelX;
// add slight overlap to prevent floating point errors from missing points
// https://github.com/ScottPlot/ScottPlot/issues/3665
double overlap = unitsPerPixelX * .01;
end += overlap;
var (startPosition, startIndex) = SearchIndex(start, rng);
var (endPosition, endIndex) = SearchIndex(end, rng);
int pointsInRange = Math.Abs(endPosition - startPosition);
if (pointsInRange == 0)
{
yield break;
}
yield return new Pixel(xPixel, axes.GetPixelY(Ys[startIndex] * YScale + YOffset)); // enter
if (pointsInRange > 1)
{
int lastIndex = startIndex < endIndex ? endIndex - 1 : endIndex + 1;
CoordinateRange yRange = GetRangeY(startIndex, lastIndex); //YOffset is added in GetRangeY
yield return new Pixel(xPixel, axes.GetPixelY(yRange.Min)); // min
yield return new Pixel(xPixel, axes.GetPixelY(yRange.Max)); // max
yield return new Pixel(xPixel, axes.GetPixelY(Ys[lastIndex] * YScale + YOffset)); // exit
}
}

@swharden
Copy link
Member Author

swharden commented Jun 7, 2024

I'm thinking the issue is here:

int pointsInRange = Math.Abs(endPosition - startPosition);
if (pointsInRange == 0)
{
yield break;
}

For the last point, it's possible where the last pixel column contains a single value, so start and stop index positions will be the same

@BrianAtZetica
Copy link
Contributor

This fix introduced a bug with rotated SignalXY plots that can be demonstrated with the following code (I'm using the WPF Sandbox here):

'''

    InitializeComponent();

    var amplitude = Generate.Sin();
    double[] time = new double[51];
    for (int i = 0; i < time.Length; i++)
        time[i] = i;

    var signal = WpfPlot1.Plot.Add.SignalXY(time, amplitude, color: ScottPlot.Colors.Black);
    signal.Data.Rotated = true;

'''

It looks like the last point (which should be at X = 0, Y = 51, is being plotted without cooridnate rotation (i.e. at X = 51 and Y = 0).

image

BrianAtZetica added a commit to BrianAtZetica/ScottPlot that referenced this issue Jun 9, 2024
swharden added a commit that referenced this issue Jun 10, 2024
* Bugfix in end-point interpolation for rotated SignalXY

* Bugfix for lastpoint coordinates in rotated SignalXY plottables
(resolves issue discussed in #3812

* Bug fix for inverted Axes when finding last pixel for SignalXY plots

* Update CHANGELOG.md

---------

Co-authored-by: Scott W Harden <swharden@gmail.com>
swharden added a commit that referenced this issue Jun 10, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants