/// <summary>
        /// Stretches the component horizontally to the containerWidth, if the component's width is smaller.
        /// </summary>
        /// <param name="component"></param>
        /// <param name="containerWidth"></param>
        private static void StretchComponentIfNeeded(VisioShape component, double containerWidth)
        {
            double marginIncludedWidth = component.MarginLeft + component.Width + component.MarginRight;

            if (marginIncludedWidth < containerWidth)
            {
                component.Width = containerWidth - (component.MarginLeft + component.MarginRight) - Constants.Epsilon;
            }
        }
        private void Draw(double x, double y, double currentLineHeight, double contentXEnd, double contentYEnd, Queue <VisioShape> components)
        {
            while (components.Count > 0)
            {
                VisioShape toDraw       = components.Dequeue();
                double     toDrawWidth  = toDraw.MarginLeft + toDraw.Width + toDraw.MarginRight;  //expected increase in x
                double     toDrawHeight = toDraw.MarginTop + toDraw.Height + toDraw.MarginBottom; //expected height in y

                PrepareContainerExpansion(x, y, toDrawWidth, 0);                                  //if the container streches to support the drawing, the container height does not need to change
                if ((toManage.CenterX + (toManage.Width / 2.0)) < (x + toDrawWidth))              //the new component does not fit next to the last component on the same line in the container
                {
                    x  = toManage.CenterX - (toManage.Width / 2.0);                               //go to a new line
                    y -= currentLineHeight;                                                       //the new line of components should not overlap with the one above
                    PrepareContainerExpansion(x, y, 0, toDrawHeight);
                }

                double dropX  = x + toDraw.MarginLeft + (toDraw.Width / 2.0);
                double dropY  = y - toDraw.MarginTop - (toDraw.Height / 2.0);
                double deltaX = dropX - toDraw.CenterX;
                double deltaY = dropY - toDraw.CenterY;
                toDraw.CenterX = dropX;
                toDraw.CenterY = dropY;

                if (toDraw is RationallyContainer)
                {
                    foreach (VisioShape c in ((RationallyContainer)toDraw).Children)
                    {
                        c.CenterX += deltaX;
                        c.CenterY += deltaY;
                        c.MoveChildren(deltaX, deltaY);
                    }
                }
                else
                {
                    toDraw.MoveChildren(deltaX, deltaY);
                }

                x = x + toDrawWidth;
                currentLineHeight = Math.Max(currentLineHeight, toDrawHeight);
                contentXEnd       = Math.Max(contentXEnd, dropX + (toDrawWidth / 2.0));
                contentYEnd       = Math.Min(contentYEnd, y - toDrawHeight);
            }

            //the container might still be not high enough, if the initial height is very small and expandX is true
            if (((toManage.UsedSizingPolicy & SizingPolicy.ExpandYIfNeeded) > 0) && (currentLineHeight > toManage.Height))
            {
                double topLeftY = toManage.CenterY + (toManage.Height / 2.0);
                toManage.Height  = currentLineHeight;
                toManage.CenterY = topLeftY - (toManage.Height / 2.0);
            }
            ShrinkContainer(contentXEnd, contentYEnd);
        }
        /// <summary>
        /// Places the component first in line in the container, at (x,y)
        /// </summary>
        /// <param name="x">top left x-coordinate to start drawing the component.</param>
        /// <param name="y">top left y-coordinate to start drawing the component.</param>
        /// <param name="components">Queue of components to draw.</param>
        private void Draw(double x, double y, Queue <VisioShape> components)
        {
            while (components.Count > 0)
            {
                VisioShape toDraw            = components.Dequeue();
                double     totalWidthToDraw  = toDraw.MarginLeft + toDraw.Width + toDraw.MarginRight;
                double     totalHeightToDraw = toDraw.MarginTop + toDraw.Height + toDraw.MarginBottom;

                //allow container to stretch horizontally and/or vertically if the content component overflows in those directions
                PrepareContainerExpansion(x, y, totalWidthToDraw, totalHeightToDraw);

                //this layout stacks components vertically and stretches them horizontally to the width of the container
                StretchComponentIfNeeded(toDraw, toManage.Width);

                //calculate position to draw this component
                double drawX  = x + (toDraw.Width / 2.0) + toDraw.MarginLeft;
                double drawY  = y - (toDraw.Height / 2.0) - toDraw.MarginTop;
                double deltaX = drawX - toDraw.CenterX;
                double deltaY = drawY - toDraw.CenterY;

                if (toDraw is RationallyContainer)
                {
                    foreach (VisioShape c in ((RationallyContainer)toDraw).Children)
                    {
                        if (c.Shape.ContainerProperties != null)
                        {
                            //moving children will disband the composite pattern between the shapes => remember children and later rebuild the pattern
                            c.StoreChildren();
                            c.MoveChildren(deltaX, deltaY);
                        }
                        c.CenterX += deltaX;
                        c.CenterY += deltaY;

                        if (c.Shape.ContainerProperties != null)
                        {
                            c.RestoreChildren();
                        }
                    }
                }
                else
                {
                    toDraw.MoveChildren(deltaX, deltaY);
                }
                toDraw.CenterX = drawX;
                toDraw.CenterY = drawY;

                //update x and y for the next component
                //x remains the same
                y = y - (toDraw.MarginTop + toDraw.Height + toDraw.MarginBottom);
            }
            ShrinkContainer(y); //y points below the last added component
        }
        public override void AddToTree(Shape s, bool allowAddOfSubpart)
        {
            //make s into an rcomponent for access to wrapper
            VisioShape shapeComponent = new VisioShape(Page)
            {
                Shape = s
            };

            if (CheckBoxStateComponent.IsCheckBoxStateComponent(shapeComponent.Name))
            {
                Children.Add(new CheckBoxStateComponent(Page, s));
            }//TODO validate whether it's the right one
        }