Пример #1
0
        public void SetGlyphDrawer(GlyphDrawer glyphDrawer, double fontSize)
        {
            if (this.glyphDrawer == glyphDrawer && this.fontSize == fontSize)
            {
                return;
            }

            this.glyphDrawer = glyphDrawer;
            this.fontSize    = fontSize;

            if (timeSpanUnitConfigs == null)
            {
                timeSpanUnitConfigs = new TimeSpanUnitConfig[(int)TimeSpanUnitEnum.max + 1];
            }

            maxFollowLabelWidth = double.MinValue;
            for (TimeSpanUnitEnum timeSpanUnitIndex = TimeSpanUnitEnum.none + 1; timeSpanUnitIndex <= TimeSpanUnitEnum.max; timeSpanUnitIndex++)
            {
                TimeSpanUnitMask mask             = timeSpanUnitIndex.GetMask();
                double           firstLabelWidth  = glyphDrawer.GetLength(mask.FirstLabelMask !, fontSize);
                double           followLabelWidth = glyphDrawer.GetLength(mask.FollowLabelMask !, fontSize);
                maxFollowLabelWidth = Math.Max(followLabelWidth, maxFollowLabelWidth);
                timeSpanUnitConfigs[(int)timeSpanUnitIndex] = new TimeSpanUnitConfig(timeSpanUnitIndex, firstLabelWidth, followLabelWidth);
            }
        }
Пример #2
0
        protected override void OnRecalculate(ref double[]?labelValues, ref string?[]?labelStrings, ref Point[]?labelPoints)
        {
            //choose time unit (seconds to years)
            TimeSpanUnitEnum newTimeSpanUnit = timeSpanUnitFormatter.GetDefaultTimeSpanUnit(DisplayDateRange, RenderWidthTracked);

            //check if even more labels can be displayed
            TimeSpan step               = TimeSpan.MinValue;
            DateTime firstLabelDate     = DateTime.MinValue;
            int      labelsCount        = int.MinValue;
            double   spaceBetweenLabels = LegendGlyphDrawer.GetLength("    ", FontSize);

            while (true)
            {
                calculate(newTimeSpanUnit, out var newStep, out var newFirstLabelDate, out var newLabelsCount);
                TimeSpanUnitConfig timeSpanUnitConfig = timeSpanUnitFormatter.GetWidths(newTimeSpanUnit);
                double             totalWidth         = timeSpanUnitConfig.FirstLabelWidth;
                if (newLabelsCount > 1)
                {
                    totalWidth += (newLabelsCount - 1) * (timeSpanUnitConfig.FollowLabelWidth + spaceBetweenLabels) * 1.1;
                }
                if (totalWidth > RenderWidthTracked || newTimeSpanUnit < 0)
                {
                    if (labelsCount == int.MinValue)
                    {
                        //seems even the first estimated step is already too big. Just use the values
                        step           = newStep;
                        firstLabelDate = newFirstLabelDate;
                        labelsCount    = newLabelsCount;
                    }
                    else
                    {
                        //take previous TimeSpanUnit
                        newTimeSpanUnit += 1;
                    }
                    break;
                }
                step             = newStep;
                firstLabelDate   = newFirstLabelDate;
                labelsCount      = newLabelsCount;
                newTimeSpanUnit -= 1;
            }
            TimeSpanUnit = newTimeSpanUnit;

            if (labelValues == null || labelValues.Length != labelsCount)
            {
                labelValues  = new double[labelsCount];
                labelStrings = new string[labelsCount];
                labelPoints  = new Point[labelsCount];
            }

            //calculate labels
            double           pixelPerValue   = RenderWidthTracked / DisplayValueRange;
            TimeSpanUnitMask mask            = newTimeSpanUnit.GetMask();
            double           firstLabelWidth = double.MinValue;
            DateTime         labelDate       = firstLabelDate;

            for (int labelIndex = 0; labelIndex < labelsCount; labelIndex++)
            {
                //write label value
                labelValues[labelIndex] = labelDate.ToDouble();

                //calculate position
                double xPosition = (labelValues[labelIndex] - DisplayValue) * pixelPerValue;
#if DEBUG
                if (xPosition > RenderWidthTracked && labelsCount > 1)
                {
                    if (xPosition - RenderWidthTracked > 0.0001)//filter rounding problems
                    //should not happen
                    {
                        System.Diagnostics.Debugger.Break();
                        throw new Exception();
                    }
                }
#endif
                labelPoints ![labelIndex] = new Point(xPosition, 0);