/// <summary> /// This will create a point list out of the data, which can be used to plot the data. In order to create this list, /// the function must have knowledge how to calculate the points out of the data. This will be done /// by a function provided by the calling function. /// </summary> /// <param name="layer">The plot layer.</param> /// <returns>An array of plot points in layer coordinates.</returns> public Processed3DPlotData GetRangesAndPoints( IPlotArea layer) { const double MaxRelativeValue = 1E2; Altaxo.Data.IReadableColumn xColumn = XColumn; Altaxo.Data.IReadableColumn yColumn = YColumn; Altaxo.Data.IReadableColumn zColumn = ZColumn; if (null == xColumn || null == yColumn || null == zColumn) { return(null); // this plotitem is only for x and y double columns } var result = new Processed3DPlotData(); var myPlotData = new MyPlotData(xColumn, yColumn, zColumn); result.XPhysicalAccessor = new IndexedPhysicalValueAccessor(myPlotData.GetXPhysical); result.YPhysicalAccessor = new IndexedPhysicalValueAccessor(myPlotData.GetYPhysical); result.ZPhysicalAccessor = new IndexedPhysicalValueAccessor(myPlotData.GetZPhysical); PlotRangeList rangeList = null; // allocate an array PointF to hold the line points // _tlsBufferedPlotData is a static buffer that is allocated per thread // and thus is only used temporary here in this routine if (null == _tlsBufferedPlotData) { _tlsBufferedPlotData = new List <PointD3D>(); } else { _tlsBufferedPlotData.Clear(); } // Fill the array with values // only the points where x and y are not NaNs are plotted! bool weAreInsideSegment = false; int rangeStart = 0; int rangeOffset = 0; rangeList = new PlotRangeList(); result.RangeList = rangeList; Scale xAxis = layer.XAxis; Scale yAxis = layer.YAxis; Scale zAxis = layer.ZAxis; G3DCoordinateSystem coordsys = layer.CoordinateSystem; int maxRowIndex = GetMaximumRowIndexFromDataColumns(); int plotArrayIdx = 0; foreach ((int start, int endExclusive) in _dataRowSelection.GetSelectedRowIndexSegmentsFromTo(0, maxRowIndex, _dataTable?.Document?.DataColumns, maxRowIndex)) { for (int dataRowIdx = start; dataRowIdx < endExclusive; ++dataRowIdx) { if (xColumn.IsElementEmpty(dataRowIdx) || yColumn.IsElementEmpty(dataRowIdx) || zColumn.IsElementEmpty(dataRowIdx)) { if (weAreInsideSegment) { weAreInsideSegment = false; rangeList.Add(new PlotRange(rangeStart, plotArrayIdx, rangeOffset)); } continue; } double x_rel, y_rel, z_rel; x_rel = xAxis.PhysicalVariantToNormal(xColumn[dataRowIdx]); y_rel = yAxis.PhysicalVariantToNormal(yColumn[dataRowIdx]); z_rel = zAxis.PhysicalVariantToNormal(zColumn[dataRowIdx]); // chop relative values to an range of about -+ 10^6 if (x_rel > MaxRelativeValue) { x_rel = MaxRelativeValue; } if (x_rel < -MaxRelativeValue) { x_rel = -MaxRelativeValue; } if (y_rel > MaxRelativeValue) { y_rel = MaxRelativeValue; } if (y_rel < -MaxRelativeValue) { y_rel = -MaxRelativeValue; } if (z_rel > MaxRelativeValue) { z_rel = MaxRelativeValue; } if (z_rel < -MaxRelativeValue) { z_rel = -MaxRelativeValue; } // after the conversion to relative coordinates it is possible // that with the choosen axis the point is undefined // (for instance negative values on a logarithmic axis) // in this case the returned value is NaN if (coordsys.LogicalToLayerCoordinates(new Logical3D(x_rel, y_rel, z_rel), out var coord)) { if (!weAreInsideSegment) { weAreInsideSegment = true; rangeStart = plotArrayIdx; rangeOffset = dataRowIdx - plotArrayIdx; } _tlsBufferedPlotData.Add(coord); plotArrayIdx++; } else { if (weAreInsideSegment) { weAreInsideSegment = false; rangeList.Add(new PlotRange(rangeStart, plotArrayIdx, rangeOffset)); } } } // end for if (weAreInsideSegment) { weAreInsideSegment = false; rangeList.Add(new PlotRange(rangeStart, plotArrayIdx, rangeOffset)); // add the last range } } // end foreach result.PlotPointsInAbsoluteLayerCoordinates = _tlsBufferedPlotData.ToArray(); return(result); }
/// <summary> /// This will create a point list out of the data, which can be used to plot the data. In order to create this list, /// the function must have knowledge how to calculate the points out of the data. This will be done /// by a function provided by the calling function. /// </summary> /// <param name="layer">The plot layer.</param> /// <returns>An array of plot points in layer coordinates.</returns> public Processed2DPlotData GetRangesAndPoints( Gdi.IPlotArea layer) { const double MaxRelativeValue = 1E2; Altaxo.Data.IReadableColumn xColumn = this.XColumn; Altaxo.Data.IReadableColumn yColumn = this.YColumn; if (null == xColumn || null == yColumn) { return(null); // this plotitem is only for x and y double columns } if (this.PlottablePoints <= 0) { return(null); } Processed2DPlotData result = new Processed2DPlotData(); MyPlotData myPlotData = new MyPlotData(xColumn, yColumn); result.XPhysicalAccessor = new IndexedPhysicalValueAccessor(myPlotData.GetXPhysical); result.YPhysicalAccessor = new IndexedPhysicalValueAccessor(myPlotData.GetYPhysical); PlotRangeList rangeList = null; PointF[] ptArray = null; // allocate an array PointF to hold the line points ptArray = new PointF[this.PlottablePoints]; result.PlotPointsInAbsoluteLayerCoordinates = ptArray; // Fill the array with values // only the points where x and y are not NaNs are plotted! int i, j; bool bInPlotSpace = true; int rangeStart = 0; int rangeOffset = 0; rangeList = new PlotRangeList(); result.RangeList = rangeList; Scale xAxis = layer.XAxis; Scale yAxis = layer.YAxis; Gdi.G2DCoordinateSystem coordsys = layer.CoordinateSystem; int len = this.PlotRangeEnd; for (i = this.PlotRangeStart, j = 0; i < len; i++) { if (xColumn.IsElementEmpty(i) || yColumn.IsElementEmpty(i)) { if (!bInPlotSpace) { bInPlotSpace = true; rangeList.Add(new PlotRange(rangeStart, j, rangeOffset)); } continue; } double x_rel, y_rel; double xcoord, ycoord; x_rel = xAxis.PhysicalVariantToNormal(xColumn[i]); y_rel = yAxis.PhysicalVariantToNormal(yColumn[i]); // chop relative values to an range of about -+ 10^6 if (x_rel > MaxRelativeValue) { x_rel = MaxRelativeValue; } if (x_rel < -MaxRelativeValue) { x_rel = -MaxRelativeValue; } if (y_rel > MaxRelativeValue) { y_rel = MaxRelativeValue; } if (y_rel < -MaxRelativeValue) { y_rel = -MaxRelativeValue; } // after the conversion to relative coordinates it is possible // that with the choosen axis the point is undefined // (for instance negative values on a logarithmic axis) // in this case the returned value is NaN if (coordsys.LogicalToLayerCoordinates(new Logical3D(x_rel, y_rel), out xcoord, out ycoord)) { if (bInPlotSpace) { bInPlotSpace = false; rangeStart = j; rangeOffset = i - j; } ptArray[j].X = (float)xcoord; ptArray[j].Y = (float)ycoord; j++; } else { if (!bInPlotSpace) { bInPlotSpace = true; rangeList.Add(new PlotRange(rangeStart, j, rangeOffset)); } } } // end for if (!bInPlotSpace) { bInPlotSpace = true; rangeList.Add(new PlotRange(rangeStart, j, rangeOffset)); // add the last range } return(result); }