Отображение координат оси мыши на элементе управления диаграммы - PullRequest
12 голосов
/ 24 марта 2011

Есть ли простой способ получить координаты X / Y ЛЮБОЙ точки в Области карты (конечно, относительно этой оси Оси)?

На данный момент мне только удалось получить координаты, когдамышь находится в серии (не снаружи)

private void chart_GetToolTipText(object sender, ToolTipEventArgs e)
{
    if (e.HitTestResult.Series != null)
    {
        e.Text = e.HitTestResult.Series.Points[e.HitTestResult.PointIndex].YValues[0] + " \n " + DateTime.FromOADate(e.HitTestResult.Series.Points[e.HitTestResult.PointIndex].XValue);
    }
}

Ответы [ 6 ]

10 голосов
/ 25 марта 2011

В любом случае, как всегда с MS Chart Controls, не существует простого способа сделать что-либо,
, но есть обходной путь для достижения цели. Я, к сожалению, привыкаю к ​​этому ...

private void chart1_MouseWhatever(object sender, MouseEventArgs e)
{
    chartArea1.CursorX.SetCursorPixelPosition(new Point(e.X, e.Y), true);
    chartArea1.CursorY.SetCursorPixelPosition(new Point(e.X, e.Y), true);

    double pX = chartArea1.CursorX.Position; //X Axis Coordinate of your mouse cursor
    double pY = chartArea1.CursorY.Position; //Y Axis Coordinate of your mouse cursor
}
9 голосов
/ 21 марта 2012

Это работает для моих целей и не оказывает побочного влияния на курсор.

private Tuple<double,double> GetAxisValuesFromMouse(int x, int y)
{
    var chartArea = _chart.ChartAreas[0];
    var xValue = chartArea.AxisX.PixelPositionToValue(x);
    var yValue = chartArea.AxisY.PixelPositionToValue(y);
    return new Tuple<double, double>(xValue, yValue);
}
6 голосов
/ 28 декабря 2011

Я попробовал ваш ответ, но у меня не получилось. В итоге курсор оказался в одном месте и никогда не двигался. Я полагаю, что это потому, что я использую десятичные / двойные значения вдоль обеих осей, а курсор округляется до ближайшего целого числа.

После нескольких попыток я смог разработать метод определения, где находится курсор внутри графика. Сложнее всего было выяснить, что все «позиции» для элементов диаграммы на самом деле являются процентными значениями (от 0 до 100).

Согласно
http://msdn.microsoft.com/en-us/library/system.windows.forms.datavisualization.charting.elementposition.aspx:
"Определяет положение элемента диаграммы в относительных координатах в диапазоне от (0,0) до (100,100)."

Надеюсь, вы не возражаете, я публикую здесь этот ответ только для потомков, на случай, если кто-нибудь еще столкнется с этой проблемой, и ваш метод также не работает для них. Это не красиво и не элегантно, но пока у меня работает.

private struct PointD
{
  public double X;
  public double Y;
  public PointD(double X, double Y)
  {
    this.X = X;
    this.Y = Y;
  }
}

private void chart1_MouseMove(object sender, MouseEventArgs e)
{
  var pos = LocationInChart(e.X, e.Y);
  lblCoords.Text = string.Format("({0}, {1}) ... ({2}, {3})", e.X, e.Y, pos.X, pos.Y);
}

private PointD LocationInChart(double xMouse, double yMouse)
{
  var ca = chart1.ChartAreas[0];

  //Position inside the control, from 0 to 100
  var relPosInControl = new PointD
  (
    ((double)xMouse / (double)execDetailsChart.Width) * 100,
    ((double)yMouse / (double)execDetailsChart.Height) * 100
  );

  //Verify we are inside the Chart Area
  if (relPosInControl.X < ca.Position.X || relPosInControl.X > ca.Position.Right
  || relPosInControl.Y < ca.Position.Y || relPosInControl.Y > ca.Position.Bottom) return new PointD(double.NaN, double.NaN);

  //Position inside the Chart Area, from 0 to 100
  var relPosInChartArea = new PointD
  (
    ((relPosInControl.X - ca.Position.X) / ca.Position.Width) * 100,
    ((relPosInControl.Y - ca.Position.Y) / ca.Position.Height) * 100
  );

  //Verify we are inside the Plot Area
  if (relPosInChartArea.X < ca.InnerPlotPosition.X || relPosInChartArea.X > ca.InnerPlotPosition.Right
  || relPosInChartArea.Y < ca.InnerPlotPosition.Y || relPosInChartArea.Y > ca.InnerPlotPosition.Bottom) return new PointD(double.NaN, double.NaN);

  //Position inside the Plot Area, 0 to 1
  var relPosInPlotArea = new PointD
  (
    ((relPosInChartArea.X - ca.InnerPlotPosition.X) / ca.InnerPlotPosition.Width),
    ((relPosInChartArea.Y - ca.InnerPlotPosition.Y) / ca.InnerPlotPosition.Height)
  );

  var X = relPosInPlotArea.X * (ca.AxisX.Maximum - ca.AxisX.Minimum) + ca.AxisX.Minimum;
  var Y = (1 - relPosInPlotArea.Y) * (ca.AxisY.Maximum - ca.AxisY.Minimum) + ca.AxisY.Minimum;

  return new PointD(X, Y);
}
2 голосов
/ 03 июня 2013
private void OnChartMouseMove(object sender, MouseEventArgs e)
{
    var sourceChart = sender as Chart;
    HitTestResult result = sourceChart.HitTest(e.X, e.Y);
    ChartArea chartAreas = sourceChart.ChartAreas[0];

    if (result.ChartElementType == ChartElementType.DataPoint)  
    {
        chartAreas.CursorX.Position = chartAreas.AxisX.PixelPositionToValue(e.X);
        chartAreas.CursorY.Position = chartAreas.AxisY.PixelPositionToValue(e.Y);
    }
}
1 голос
/ 05 мая 2012

Это работает

private void chart1_MouseWhatever(object sender, MouseEventArgs e)
{   
    Point chartLocationOnForm = chart1.FindForm().PointToClient(chart1.Parent.PointToScreen(chart1.Location));     

    double x = chart1.ChartAreas[0].AxisX.PixelPositionToValue(e.X - chartLocationOnForm.X);    
    double y = chart1.ChartAreas[0].AxisY.PixelPositionToValue(e.Y - chartLocationOnForm.Y);
}

И это работает

private void chart1_MouseWhatever(object sender, MouseEventArgs e)
{ 
    Point chartLocationOnForm = chart1.FindForm().PointToClient(chart1.Parent.PointToScreen(chart1.Location));                

    chart1.ChartAreas[0].CursorX.SetCursorPixelPosition(new PointF(e.X - chartLocationOnForm.X, e.Y - chartLocationOnForm.Y), true);
    chart1.ChartAreas[0].CursorY.SetCursorPixelPosition(new PointF(e.X - chartLocationOnForm.X, e.Y - chartLocationOnForm.Y), true);

    double x = chart1.ChartAreas[0].CursorX.Position;
    double y = chart1.ChartAreas[0].CursorY.Position;
}
0 голосов
/ 08 ноября 2017

Это то, что я получил, я думаю, что многие из нас придерживаются той же линии, но с разными интерпретациями того, что вы ищете.

Это даст вам координаты в любом месте области печати. Я обнаружил, что HitTest дает чистое и простое решение, но нужно сделать несколько проверок, находится ли курсор на точке данных, на линии сетки или в области построения графика (которые, кажется, имеют приоритет в этом порядке). Я предполагаю, что вам будет интересна координата независимо от того, над каким объектом мыши находится курсор.

private void chart_GetToolTipText(object sender, ToolTipEventArgs e)
{
    // If the mouse isn't on the plotting area, a datapoint, or gridline then exit
    HitTestResult htr = chart.HitTest(e.X, e.Y);
    if (htr.ChartElementType != ChartElementType.PlottingArea && htr.ChartElementType != ChartElementType.DataPoint && htr.ChartElementType != ChartElementType.Gridlines)
        return;

    ChartArea ca = chart.ChartAreas[0]; // Assuming you only have 1 chart area on the chart

    double xCoord = ca.AxisX.PixelPositionToValue(e.X);
    double yCoord = ca.AxisY.PixelPositionToValue(e.Y);

    e.Text = "X = " + Math.Round(xCoord, 2).ToString() + "\nY = " + Math.Round(yCoord, 2).ToString();
}
...