viewxy - SeriesEventMarker not tracking correct axis

A forum dedicated to WinForms version of LightningChart Ultimate.

Moderator: Arction_LasseP

greggorob64
Posts: 183
Joined: Tue Mar 18, 2014 2:55 pm

viewxy - SeriesEventMarker not tracking correct axis

Post by greggorob64 » Fri Jan 29, 2016 4:18 pm

So, to preface this, i swear this used to work, and i don't know what happened!

I'm using a SeriesEventMarker in order to make a 'hovering tooltip' when my mouse gets close to a trace. On mouse move, i see how close I am to a trace, and if im close enough, i show a series event marker. Below is the code on how I create my series event marker

If i have exactly one series with one Y axis, everything works correctly (see screenshot 1). When i have multiple Y axis, and multiple series it's not working correctly.

Lets say that Series A is red, with Y axis set to visible (also red). Series B is blue (Y axis is not visible). When I hover over the red trace, the serieseventmarker is in the correct place.

If you hover over the blue trace, the Y placement of the marker is incorrect (see screenshot 2). I'm almost certain the serieseventmarker for the blue trace is having its value shown in reference to the red axis, and I want it in reference to the blue axis, which is where the series resides in the first place!

Please help!

screenshot 1:
Image

Image

Code: Select all

         // crerate the marker shape
         var markerShape = new PointShapeStyle()
         {
            Antialiasing = this.PreferenceTrackpointShapeAntiAlias,
            BorderColor = this.PreferenceTrackpointShapeColor,
            BorderWidth = this.PreferenceTrackpointShapeBorderWidth,
            // There is a current bug.  If you uncomment hiehgt or width you get MAD flickering
            Height = this.PreferenceTrackpointShapeSize,
            Width = this.PreferenceTrackpointShapeSize,
            Shape = this.PreferenceTrackpointShapeShape
         };


         AlignmentVertical Vertical = AlignmentVertical.Bottom;
         AlignmentHorizontal Horizontal = AlignmentHorizontal.Right;

         var markerTitle = new EventMarkerTitle()
         {
            Text = TooltipMouseOverStringGenerate(xUnits, yUnits, xValue, yValue, nearestSample, "     "),
            Color = sampleSeries.LineStyle.Color,
            VerticalAlign = Vertical,
            HorizontalAlign = Horizontal
            //, Distance = this.PreferenceTrackpointLabelOffset
         };

         SeriesEventMarker thisMarker = new SeriesEventMarker(
            sampleSeries,
            markerShape,
            SeriesEventMarkerVerticalPosition.AtYValue,
            xValue,
            yValue,
            markerTitle);

User avatar
ArctionPasi
Posts: 1366
Joined: Tue Mar 26, 2013 10:57 pm
Location: Finland

Re: viewxy - SeriesEventMarker not tracking correct axis

Post by ArctionPasi » Sun Jan 31, 2016 12:42 pm

Hi,

could you replace your initialization so that it won't use initializer lists? I think this is similar issue than discussed earlier here:http://forum.arction.com/viewtopic.php? ... 581&p=2207. The properties target the wrong scope.

Like this:

Code: Select all

var markerShape = new PointShapeStyle(); 
markerShape.Antialiasing = this.PreferenceTrackpointShapeAntiAlias; 
markerShape.BorderColor = this.PreferenceTrackpointShapeColor;
markerShape.BorderWidth = this.PreferenceTrackpointShapeBorderWidth;
markerShape.Height = this.PreferenceTrackpointShapeSize;
markerShape.Width = this.PreferenceTrackpointShapeSize;
markerShape.Shape = this.PreferenceTrackpointShapeShape; 
        
LightningChart Support Team, PT

greggorob64
Posts: 183
Joined: Tue Mar 18, 2014 2:55 pm

Re: viewxy - SeriesEventMarker not tracking correct axis

Post by greggorob64 » Wed Feb 03, 2016 2:43 pm

I don't know if i'm happy or sad, but the initializer lists wasn't the problem. The marker is showing itself in reference to the wrong axis.

Code: Select all

   var markerShape = new PointShapeStyle();
         markerShape.Antialiasing = this.PreferenceTrackpointShapeAntiAlias;
         markerShape.BorderColor = this.PreferenceTrackpointShapeColor;
         markerShape.BorderWidth = this.PreferenceTrackpointShapeBorderWidth;
         // There is a current bug.  If you uncomment hiehgt or width you get MAD flickering
         markerShape.Height = this.PreferenceTrackpointShapeSize;
         markerShape.Width = this.PreferenceTrackpointShapeSize;
         markerShape.Shape = this.PreferenceTrackpointShapeShape;


         AlignmentVertical Vertical = AlignmentVertical.Bottom;
         AlignmentHorizontal Horizontal = AlignmentHorizontal.Right;

         var markerTitle = new EventMarkerTitle();
         markerTitle.Text = TooltipMouseOverStringGenerate(xUnits, yUnits, xValue, yValue, nearestSample, "     ");
         markerTitle.Color = sampleSeries.LineStyle.Color;
         markerTitle.VerticalAlign = Vertical;
         markerTitle.HorizontalAlign = Horizontal;

         SeriesEventMarker thisMarker = new SeriesEventMarker(
            sampleSeries,
            markerShape,
            SeriesEventMarkerVerticalPosition.AtYValue,
            xValue,
            yValue,
            markerTitle);

User avatar
ArctionPasi
Posts: 1366
Joined: Tue Mar 26, 2013 10:57 pm
Location: Finland

Re: viewxy - SeriesEventMarker not tracking correct axis

Post by ArctionPasi » Wed Feb 03, 2016 4:43 pm

Flickering disappeared with my tip?

Could you attach a small project to reproduce the issue?
LightningChart Support Team, PT

greggorob64
Posts: 183
Joined: Tue Mar 18, 2014 2:55 pm

Re: viewxy - SeriesEventMarker not tracking correct axis

Post by greggorob64 » Wed Feb 03, 2016 7:55 pm

The flickering was not an issue i meant to address with this post. The code snippet i sent you had that old comment which i accidentally forgot to delete. That bug was from the initializer list and you helped me fix it a few months ago. I am not having any flickering issues currently.

The problem i'm having is this: When i create a series marker and attach it to a series, the XY location of the marker is not correct, it is in reference to a different axis.

Do you know offhand what might be causing it based off the information above? If not, i'll take the time to make the sample

greggorob64
Posts: 183
Joined: Tue Mar 18, 2014 2:55 pm

Re: viewxy - SeriesEventMarker not tracking correct axis

Post by greggorob64 » Wed Feb 03, 2016 8:36 pm

Alright, i put together a sample. You should just be able to paste this into a program.cs and run

All markers are getting display in reference to the first yaxis, as opposed to the axis that thier host series is a part of. In this example, hover your mouse over the red line, and then the blue line. In the code sample, if you swtch the creation of the two axis, the effect is reversed

Code: Select all

using Arction.LightningChartUltimate;
using Arction.LightningChartUltimate.Axes;
using Arction.LightningChartUltimate.EventMarkers;
using Arction.LightningChartUltimate.SeriesXY;
using Arction.LightningChartUltimate.Titles;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace WindowsFormsApplication2
{
   static class Program
   {
      /// <summary>
      /// The main entry point for the application.
      /// </summary>
      [STAThread]
      static void Main()
      {
         Application.EnableVisualStyles();
         Application.SetCompatibleTextRenderingDefault(false);
         Application.Run(new Form1());
      }
   }
   public partial class Form1 : Form
   {
      public Form1()
      {
         this.Size = new System.Drawing.Size(800, 600);

         chart = new LightningChartUltimate("liscense key here");
         chart.Dock = DockStyle.Fill;
         this.Controls.Add(chart);

         chart.ViewXY.YAxes.Clear();
         chart.ViewXY.XAxes.Clear();

         this.SampleMarkersSeries = new SampleDataSeries();
         this.chart.ViewXY.SampleDataSeries.Add(this.SampleMarkersSeries);

         chart.MouseMove += chart_MouseMove;

         var x = new AxisX(chart.ViewXY);
         chart.ViewXY.XAxes.Add(x);
         x.ValueType = AxisValueType.Number;

         List<double> redPoints = new List<double>();
         List<double> bluePoints = new List<double>();

         for (int i = 0; i < 100; i++)
         {
            redPoints.Add(100d - (double)i);
            bluePoints.Add(25 + (double)i / 4.0);
         }

         {
            var red = new AxisY(chart.ViewXY, true);
            red.AxisColor = Color.Red;
            red.Minimum = 0;
            red.Maximum = 100;
            var redSeries = new SampleDataSeries(chart.ViewXY, chart.ViewXY.XAxes[0], red);
            redSeries.LineStyle.Color = Color.Red;
            redSeries.PointStyle.Color1 = Color.Red;
            chart.ViewXY.SampleDataSeries.Add(redSeries);
            redSeries.SampleFormat = SampleFormat.DoubleFloat;
            redSeries.SamplesDouble = redPoints.ToArray();
         }


         {
            var blue = new AxisY(chart.ViewXY, true);
            blue.AxisColor = Color.Blue;
            blue.Minimum = -10;
            blue.Maximum = 50;
            var blueSeries = new SampleDataSeries(chart.ViewXY, chart.ViewXY.XAxes[0], blue);
            blueSeries.LineStyle.Color = Color.Blue;
            blueSeries.PointStyle.Color1 = Color.Blue;
            chart.ViewXY.SampleDataSeries.Add(blueSeries);
            blueSeries.SampleFormat = SampleFormat.DoubleFloat;
            blueSeries.SamplesDouble = bluePoints.ToArray();
         }

      }

      LightningChartUltimate chart;
      public SampleDataSeries SampleMarkersSeries
      {
         get;
         protected set;
      }
      List<SeriesEventMarker> SeriesEventMarkers = new List<SeriesEventMarker>();

      public static double CalculateDistance(double X1, double Y1, double X2, double Y2)
      {
         double dX = X1 - X2;
         double dY = Y1 - Y2;
         return Math.Sqrt(dX * dX + dY * dY);

      }

      void chart_MouseMove(object sender, MouseEventArgs e)
      {
         // We want to keep track of the visible markers so we can properly align the boxes so there isn't any overlap
         int MarkersVisible = 0;
         List<SeriesEventMarker> markersToAdd = null;

         this.SampleMarkersSeries.Clear();

         foreach (var sampleSeries in this.chart.ViewXY.SampleDataSeries)
         {
            if (sampleSeries.Visible)
            {
               double xValue, yValue;
               int nearestSample;
               sampleSeries.SolveNearestSampleByCoord(e.X, e.Y, out xValue, out yValue, out nearestSample);

               var xAxis = this.chart.ViewXY.XAxes[sampleSeries.AssignXAxisIndex];
               var yAxis = this.chart.ViewXY.YAxes[sampleSeries.AssignYAxisIndex];
               var xCoordOfPoint = xAxis.ValueToCoord(xValue);
               var yCoordOfPoint = yAxis.ValueToCoord(yValue);

               var distanceOfMouseToPoint = CalculateDistance(xCoordOfPoint, yCoordOfPoint, e.X, e.Y);

               sampleSeries.SeriesEventMarkers.Clear();

               if (distanceOfMouseToPoint < 25)
               {
                  //this.OnUpdateStatusEvent(
                  //   string.Format("Xloc: {0}, Yloc: {1}, xValue: {2}, yValue: {3}, Sample: {4}",
                  //      e.X, e.Y, xValue, yValue, nearestSample));

                  SeriesEventMarker thisMarker = CreateSeriesEventMarker(
                     e.X,
                     e.Y,
                     MarkersVisible,
                     xValue,
                     yValue,
                     nearestSample,
                     sampleSeries,
                     xAxis.Units.Text,
                     yAxis.Units.Text);

                  if (markersToAdd == null)
                  {
                     markersToAdd = new List<SeriesEventMarker>();
                  }
                  markersToAdd.Add(thisMarker);
                  MarkersVisible++;
               }
            }
         }


         if (markersToAdd != null && markersToAdd.Any())
         {
            this.chart.BeginUpdate();
            this.SampleMarkersSeries.SeriesEventMarkers.AddRange(markersToAdd);
            this.SeriesEventMarkers.AddRange(markersToAdd);

            this.chart.EndUpdate();
         }
      }


      /// <summary>
      /// Produce a marker for when you hover the cursor over a the chart, it will find the nearest point to show
      /// </summary>
      /// <param name="mouseX">X-Coordinate</param>
      /// <param name="mouseY">Y-Coordinate</param>
      /// <param name="Index">How many we are adding</param>
      /// <param name="xValue"></param>
      /// <param name="yValue"></param>
      /// <param name="nearestSample"></param>
      /// <param name="sampleSeries"></param>
      /// <returns>Marker</returns>
      private SeriesEventMarker CreateSeriesEventMarker(
         int mouseX, int mouseY,
         int Index,
         double xValue,
         double yValue,
         int nearestSample,
         SampleDataSeries sampleSeries,
         string xUnits,
         string yUnits)
      {
         // crerate the marker shape
         var markerShape = new PointShapeStyle();
         markerShape.Antialiasing = this.PreferenceTrackpointShapeAntiAlias;
         markerShape.BorderColor = this.PreferenceTrackpointShapeColor;
         markerShape.BorderWidth = this.PreferenceTrackpointShapeBorderWidth;
         // There is a current bug.  If you uncomment hiehgt or width you get MAD flickering
         markerShape.Height = this.PreferenceTrackpointShapeSize;
         markerShape.Width = this.PreferenceTrackpointShapeSize;
         markerShape.Shape = this.PreferenceTrackpointShapeShape;


         AlignmentVertical Vertical = AlignmentVertical.Bottom;
         AlignmentHorizontal Horizontal = AlignmentHorizontal.Right;

         var markerTitle = new EventMarkerTitle();
         markerTitle.Text = TooltipMouseOverStringGenerate(xUnits, yUnits, xValue, yValue, nearestSample, "     ");
         markerTitle.Color = sampleSeries.LineStyle.Color;
         markerTitle.VerticalAlign = Vertical;
         markerTitle.HorizontalAlign = Horizontal;

         SeriesEventMarker thisMarker = new SeriesEventMarker(
            sampleSeries,
            markerShape,
            SeriesEventMarkerVerticalPosition.AtYValue,
            xValue,
            yValue,
            markerTitle);


        

         return thisMarker;
      }
      private Font PreferneceTrackpointFont = new Font("Arial", 10, FontStyle.Underline);

      //private int PreferenceTrackpointLabelOffset = 15;

      /// <summary>
      /// The distance the mouse has to be to a trace to highlight the nearest value
      /// </summary>
      private double PreferenceTrackpointMouseDistanceThreshold = 10f;
      /// <summary>
      /// Whether or not to antialias the shape that shows when your cursor hovers over a point
      /// </summary>
      private bool PreferenceTrackpointShapeAntiAlias = false;
      /// <summary>
      /// Color to show as the shape in the tracking cursor
      /// </summary>
      private Color PreferenceTrackpointShapeColor = Color.Black;
      /// <summary>
      /// Width of the shape of the tracking cursor
      /// </summary>
      private int PreferenceTrackpointShapeBorderWidth = 2;
      ///<summary>
      ///Size of the shape of the tracking cursor (currently bugged)
      ///</summary>
      private int PreferenceTrackpointShapeSize = 5;
      /// <summary>
      /// Shape of the tracking cursor
      /// </summary>
      private Shape PreferenceTrackpointShapeShape = Shape.Circle;
      /// <summary>
      /// If tracking cursor border is enabled, the inside fill
      /// </summary>
      private Color PreferenceTrackpointBorderFill1 = Color.White;
      /// <summary>
      /// If tracking cursor border is enabled, the inside fill
      /// </summary>
      private Color PreferenceTrackpointBorderFill2 = Color.LightGray;
      ///// <summary>
      ///// Whether to draw a box aroudn the tracking cursor text
      ///// </summary>
      //private bool PreferenceTrackpointBorderShow = true;
      /// <summary>
      /// Tracking cursor border color
      /// </summary>
      private Color PreferenceTrackpointBorderColor = Color.DarkGray;
      ///// <summary>
      ///// Tracking cursor border width
      ///// </summary>
      //private int PreferenceTrackpointBorderWidth = 1;

      private static string TooltipMouseOverStringGenerate(string xUnitsText, string yUnitsText, double nearestX, double nearestY, int nearestIndex, string seperator = "\t")
      {
         string Text = string.Format("Sample:{5}{0}\n\nX Value:{5}{1:0.##}{5}{2}\nY Value:{5}{3:0.##}{5}{4}",
            nearestIndex,
            nearestX,
            xUnitsText,
            nearestY,
            yUnitsText,
            seperator
            );
         return Text;
      }

   }

}

User avatar
ArctionPasi
Posts: 1366
Joined: Tue Mar 26, 2013 10:57 pm
Location: Finland

Re: viewxy - SeriesEventMarker not tracking correct axis

Post by ArctionPasi » Wed Feb 03, 2016 10:56 pm

I checked the code. I suppose you are using a common marker container series because your data will actually have many data segments per Y axis.

The markers get wrong values because they are eventually assigned to wrong Y axis.

This assigns the SampleMarkerSeries for the first Y axis:

Code: Select all

this.SampleMarkersSeries = new SampleDataSeries();
this.chart.ViewXY.SampleDataSeries.Add(this.SampleMarkersSeries);
When you add markers for this series' SeriesEventMarkersCollection:

Code: Select all

 if (markersToAdd != null && markersToAdd.Any())
            {
                this.chart.BeginUpdate();
                this.SampleMarkersSeries.SeriesEventMarkers.AddRange(markersToAdd);
                this.SeriesEventMarkers.AddRange(markersToAdd);

                this.chart.EndUpdate();
            }
, they all start to follow this first Y axis scale.


Please create marker container series for every Y axis separately, and not use a common one. When you create the marker, ensure you are giving the series as parameter that will be the owner of the marker

Code: Select all

SeriesEventMarker thisMarker = new SeriesEventMarker(
               MarkerContainerSeriesForThisYAxis, //the marker container series here
               markerShape,
               SeriesEventMarkerVerticalPosition.AtYValue,
               xValue,
               yValue,
               markerTitle);
Then the object tree is correct :) . Please let me know if it still doesn't work correctly
LightningChart Support Team, PT

greggorob64
Posts: 183
Joined: Tue Mar 18, 2014 2:55 pm

Re: viewxy - SeriesEventMarker not tracking correct axis

Post by greggorob64 » Thu Feb 04, 2016 1:42 pm

Thanks Pasi, that was definately the solution. I couldn't figure out why the heck I held that series there either (at first). Then i figured out why! I made a seperate post about not liking the fact that my series event markers where showing underneath other series (link: http://forum.arction.com/viewtopic.php?f=15&t=582).

The solution there was to move all of the serieseventmarkers into a different series, and voila, the markers are always on top now. This tracking issue is a fallout from that. My initial post was 'i swear this used to work' statement is referring to the fact that this worked before my 'always on top' fix.

So, a followup question, how do i have my cake and eat it too (get tracking pointers on top, and also have them tracked correctly)?