Beispiel #1
0
        /// <summary>
        /// Divide a grid by a pattern of lengths. Type names will be automatically generated, repetition will be governed by PatternMode,
        /// and remainder handling will be governed by DivisionMode.
        /// </summary>
        /// <param name="lengthPattern">A pattern of lengths to apply to the grid</param>
        /// <param name="patternMode">How to apply/repeat the pattern</param>
        /// <param name="divisionMode">How to handle leftover/remainder length</param>
        public void DivideByPattern(IList <double> lengthPattern, PatternMode patternMode = PatternMode.Cycle, FixedDivisionMode divisionMode = FixedDivisionMode.RemainderAtEnd)
        {
            var patternwithNames = new List <(string typeName, double length)>();

            for (int i = 0; i < lengthPattern.Count; i++)
            {
                patternwithNames.Add((StringExtensions.NumberToString(i), lengthPattern[i]));
            }
            DivideByPattern(patternwithNames, patternMode, divisionMode);
        }
Beispiel #2
0
        /// <summary>
        /// Divide a grid by constant length subdivisions, with a variable division mode to control how leftover
        /// space is handled.
        /// </summary>
        /// <param name="length">The division length</param>
        /// <param name="divisionMode">How to handle leftover / partial remainder panels </param>
        /// <param name="sacrificialPanels">How many full length panels to sacrifice to make remainder panels longer.</param>
        public void DivideByFixedLength(double length, FixedDivisionMode divisionMode = FixedDivisionMode.RemainderAtEnd, int sacrificialPanels = 0)
        {
            if (length <= Vector3.EPSILON)
            {
                throw new ArgumentException($"Unable to divide by length {length}: smaller than tolerance.");
            }
            var lengthToFill  = Domain.Length;
            var maxPanelCount = (int)Math.Floor(lengthToFill / length) - sacrificialPanels;

            if (maxPanelCount < 1)
            {
                return;
            }


            var remainderSize = lengthToFill - maxPanelCount * length;

            if (remainderSize < 0.01)
            {
                DivideByCount(maxPanelCount);
                return;
            }
            switch (divisionMode)
            {
            case FixedDivisionMode.RemainderAtBothEnds:
                for (double i = remainderSize / 2.0; i < lengthToFill; i += length)
                {
                    SplitAtOffset(i);
                }
                break;

            case FixedDivisionMode.RemainderAtStart:
                for (double i = remainderSize; i < lengthToFill; i += length)
                {
                    SplitAtOffset(i);
                }
                break;

            case FixedDivisionMode.RemainderAtEnd:
                for (int i = 1; i < maxPanelCount + 1; i++)
                {
                    SplitAtOffset(i * length);
                }
                break;

            case FixedDivisionMode.RemainderNearMiddle:
                // assumes we must have at least 2 full-size panels
                int panelsOnLeft = maxPanelCount / 2;     //integer division, on purpose
                //make left panels
                for (int i = 1; i <= panelsOnLeft; i++)
                {
                    SplitAtOffset(i * length);
                }
                //make middle + right panels
                for (double i = panelsOnLeft * length + remainderSize; i < lengthToFill; i += length)
                {
                    SplitAtOffset(i);
                }

                break;
            }
        }