using SkiaSharp; namespace MarketData.CNNProcessing { /// /// This class provides functionality to both scale and map data points from an upper left coordinate system to a lower left coordinate system /// public class PointMapping { public PointMapping(double width, double height, double xDataExtent, double xDataExtentMin, double yDataExtent, double yDataExtentMin, double xMarginExtent = 0.00, double yMarginExtent = 0.00) { Width = width; Height = height; XMargin = xMarginExtent; YMargin = yMarginExtent; XDataExtent = xDataExtent; XDataExtentMin = xDataExtentMin; YDataExtent = yDataExtent; YDataExtentMin = yDataExtentMin; XScalingFactor = (Width - (XMargin * 2.00)) / (XDataExtent - XDataExtentMin); YScalingFactor = (Height - (YMargin * 2.00)) / (YDataExtent - YDataExtentMin); } public PointMapping(PointMapping pointMapping) { Width = pointMapping.Width; Height = pointMapping.Height; XMargin = pointMapping.XMargin; YMargin = pointMapping.YMargin; XDataExtent = pointMapping.XDataExtent; YDataExtent = pointMapping.YDataExtent; XScalingFactor = pointMapping.XScalingFactor; YScalingFactor = pointMapping.YScalingFactor; } /// /// MapPoint will both scale the given point and translate the given point from an upper left origin system to a bottom left origin system /// Because of the scaling factor (XScalingFactor and YScalingFactor) it is possible for the resulting X,Y values to be rounded out of range. /// To remedy this we perform a boundary check of the X,Y points against the extents and set them to those extents if they are out of range. /// /// /// public SKPoint MapPoint(SKPoint sourcePoint) { SKPoint mappedPoint = new SKPoint((int)((sourcePoint.X - XDataExtentMin) * XScalingFactor), (int)((Height - 1) - ((sourcePoint.Y - YDataExtentMin) * YScalingFactor))); mappedPoint.X += (int)XMargin; // offset by the xMargin mappedPoint.Y -= (int)YMargin; // offset by the yMargin if (mappedPoint.X > XDataExtent) mappedPoint.X = (int)XDataExtent; // constrain X to XDataExtent if (mappedPoint.Y > YDataExtent) mappedPoint.Y = (int)YDataExtent; // constrain Y to YDataExtent if (mappedPoint.X < XDataExtentMin) mappedPoint.X = (int)XDataExtentMin; // constrain X to XDataExtentMin if (mappedPoint.Y < YDataExtentMin) mappedPoint.Y = (int)YDataExtentMin; // constrain Y to YDataExtentMin return mappedPoint; } // TranslatePoint will only translate the given point from an upper left origin system to a bottom left origin system public SKPoint TranslatePoint(SKPoint sourcePoint) { SKPoint mappedPoint=new SKPoint((int)sourcePoint.X,(int)(Height-sourcePoint.Y-1)); return mappedPoint; } public double Width { get; private set; } public double Height{get;private set;} public double XDataExtent{get;private set;} public double XDataExtentMin{get;private set;} public double XRange{get{return XDataExtent-XDataExtentMin;}} public double YDataExtent{get;private set;} public double YDataExtentMin{get;private set;} public double YRange{get{return YDataExtent-YDataExtentMin;}} public double XMargin{get;private set;} public double YMargin{get;private set;} public double XScalingFactor{get;private set;} public double YScalingFactor{get;private set;} } }