示例#1
0
            /// <summary>
            /// Test whether the given location is a valid hit.
            /// </summary>
            /// <remarks>
            /// The hit is considered as valid if the location lies inside a node's top insets.
            /// </remarks>
            /// <param name="context">The current input mode context.</param>
            /// <param name="location">The location to test.</param>
            /// <returns></returns>
            public bool IsHit(IInputModeContext context, PointD location)
            {
                // Get the current hit tester from the input mode context
                IHitTester <IModelItem> enumerator = inputMode.InputModeContext.Lookup(typeof(IHitTester <IModelItem>)) as IHitTester <IModelItem>;

                if (enumerator != null)
                {
                    // get an enumerator over all elements at the given location
                    var hits = enumerator.EnumerateHits(inputMode.InputModeContext, location);
                    foreach (var item in hits)
                    {
                        // if the element is a node and its lookup returns an INodeInsetsProvider
                        var node = item as INode;
                        if (node != null)
                        {
                            var insetsProvider = node.Lookup <INodeInsetsProvider>();
                            if (insetsProvider != null)
                            {
                                // determine whether the given location lies inside the top insets
                                InsetsD insets = insetsProvider.GetInsets(node);
                                if (new RectD(node.Layout.X, node.Layout.Y, node.Layout.Width, insets.Top).Contains(location))
                                {
                                    // if so: return true
                                    return(true);
                                }
                                // else: continue iteration
                            }
                        }
                    }
                }
                // no hits found: return false
                return(false);
            }
        protected override VisualGroup CreateVisual(IRenderContext context, IStripe stripe)
        {
            IRectangle layout = stripe.Layout.ToRectD();
            InsetsD    stripeInsets;
            var        group = new VisualGroup();
            int        index;

            if (stripe is IColumn)
            {
                var col = (IColumn)stripe;
                stripeInsets = new InsetsD(0, col.GetActualInsets().Top, 0, col.GetActualInsets().Bottom);
                index        = col.ParentColumn.ChildColumns.ToList().FindIndex(curr => col == curr);
            }
            else
            {
                var row = (IRow)stripe;
                stripeInsets = new InsetsD(row.GetActualInsets().Left, 0, row.GetActualInsets().Right, 0);
                index        = row.ParentRow.ChildRows.ToList().FindIndex((curr) => row == curr);
            }
            StripeDescriptor descriptor = index % 2 == 0 ? EvenStripeDescriptor : OddStripeDescriptor;

            group.Add(new RectangleVisual(layout.X, layout.Y, layout.Width, layout.Height)
            {
                Brush = descriptor.BackgroundBrush, Pen = new Pen(descriptor.BorderBrush, descriptor.BorderThickness)
            });

            //Draw the insets
            if (stripeInsets.Left > 0)
            {
                group.Add(new RectangleVisual(layout.X, layout.Y, stripeInsets.Left, layout.Height)
                {
                    Brush = descriptor.InsetBrush
                });
            }
            if (stripeInsets.Top > 0)
            {
                group.Add(new RectangleVisual(layout.X, layout.Y, layout.Width, stripeInsets.Top)
                {
                    Brush = descriptor.InsetBrush
                });
            }
            if (stripeInsets.Right > 0)
            {
                group.Add(new RectangleVisual(layout.GetMaxX() - stripeInsets.Right, layout.Y, stripeInsets.Right, layout.Height)
                {
                    Brush = descriptor.InsetBrush
                });
            }
            if (stripeInsets.Bottom > 0)
            {
                group.Add(new RectangleVisual(layout.X, layout.GetMaxY() - stripeInsets.Bottom, layout.Width, stripeInsets.Bottom)
                {
                    Brush = descriptor.InsetBrush
                });
            }
            return(group);
        }
        public CollapsibleNodeStyleDecoratorExtension()
        {
            ButtonLocationParameter = InteriorLabelModel.NorthWest;
            Insets = new InsetsD(5, 16, 5, 5);
            var defaults = new CollapsibleNodeStyleDecorator();

            CollapsedIcon = defaults.CollapsedIcon;
            ExpandedIcon  = defaults.ExpandedIcon;
        }
 /// <summary>
 /// Creates a new instance using the default values.
 /// </summary>
 public ActivityNodeStyle()
 {
     MinimumSize                = new SizeD(40, 30);
     ActivityType               = ActivityType.Task;
     Insets                     = new InsetsD(15);
     SubState                   = SubState.None;
     LoopCharacteristic         = LoopCharacteristic.None;
     TaskType                   = TaskType.Abstract;
     TriggerEventType           = EventType.Message;
     TriggerEventCharacteristic = EventCharacteristic.SubProcessInterrupting;
 }
示例#5
0
 public ChoreographyNodeStyleExtension()
 {
     Type = ChoreographyType.Task;
     LoopCharacteristic = LoopCharacteristic.None;
     SubState           = SubState.None;
     InitiatingMessage  = false;
     ResponseMessage    = false;
     InitiatingAtTop    = true;
     Insets             = new InsetsD(5);
     MinimumSize        = SizeD.Empty;
 }
        /// <summary>
        /// Paint the style representation.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private static void styleListBox_DrawItem(object sender, DrawItemEventArgs e)
        {
            ListBox listBox = (ListBox)sender;
            int     i       = e.Index;

            e.DrawBackground();
            INode node = listBox.Items[i] as INode;

            var     bounds = e.Bounds;
            InsetsD insets = new InsetsD(2);

            var canvasControl = new GraphControl();

            canvasControl.Size = new Size(bounds.Width - (int)insets.HorizontalInsets,
                                          bounds.Height - (int)insets.VerticalInsets);
            Bitmap   bm = new Bitmap(canvasControl.Size.Width, canvasControl.Size.Height);
            Graphics g  = Graphics.FromImage(bm);

            canvasControl.HorizontalScrollBarPolicy = ScrollBarVisibility.Never;
            canvasControl.VerticalScrollBarPolicy   = ScrollBarVisibility.Never;
            var dummyNode = canvasControl.Graph.CreateNode(node.Layout.ToRectD(), node.Style, node.Tag);

            foreach (var label in node.Labels)
            {
                canvasControl.Graph.AddLabel(dummyNode, label.Text, label.LayoutParameter, label.Style, label.PreferredSize, label.Tag);
            }
            foreach (var port in node.Ports)
            {
                canvasControl.Graph.AddPort(dummyNode, port.LocationParameter, port.Style, port.Tag);
            }
            canvasControl.ContentRect = new RectD(0, 0, 70, 70);
            canvasControl.FitContent();
            e.DrawBackground();
            g.SmoothingMode = SmoothingMode.HighQuality;
            g.Clear(Color.White);

            ContextConfigurator cc = new ContextConfigurator(canvasControl.ContentRect);
            var renderContext      = cc.CreateRenderContext(canvasControl, g);

            canvasControl.RenderContent(renderContext, g);
            var listGraphics = e.Graphics;
            var oldClip      = listGraphics.Clip;

            listGraphics.IntersectClip(bounds);
            listGraphics.Clear(listBox.BackColor);
            listGraphics.DrawImage(bm, bounds.X + (int)insets.Left, bounds.Y + (int)insets.Top, bm.Width, bm.Height);
            listGraphics.Clip = oldClip;
            e.DrawFocusRectangle();

            canvasControl.Dispose();
            g.Dispose();
            bm.Dispose();
        }
示例#7
0
 public ActivityNodeStyleExtension()
 {
     ActivityType               = ActivityType.Task;
     TaskType                   = TaskType.Abstract;
     TriggerEventType           = EventType.Message;
     TriggerEventCharacteristic = EventCharacteristic.SubProcessInterrupting;
     LoopCharacteristic         = LoopCharacteristic.None;
     SubState                   = SubState.None;
     AdHoc        = false;
     Compensation = false;
     Insets       = new InsetsD(15);
     MinimumSize  = SizeD.Empty;
 }
示例#8
0
        public InsetsD GetInsets(INode node)
        {
            InsetsD result = InsetsD.Empty;

            foreach (ILabel label in node.Labels)
            {
                INodeInsetsProvider provider =
                    label.LayoutParameter.Model.Lookup <INodeInsetsProvider>();
                if (provider != null)
                {
                    InsetsD insets = provider.GetInsets(node);
                    result = result.CreateUnion(insets);
                }
            }
            return(result.CreateUnion(outerInsets));
        }
            public NodeGroupHandle(IInputModeContext context, HandlePositions position, IReshapeHandler reshapeHandler, InsetsD margins)
                : base(position, reshapeHandler)
            {
                this.margins = margins;
                this.context = context;

                if ((position & HandlePositions.Vertical) != 0)
                {
                    ReshapePolicy = ReshapePolicy.Vertical;
                }
                else if ((position & HandlePositions.Horizontal) != 0)
                {
                    ReshapePolicy = ReshapePolicy.Horizontal;
                }
                else
                {
                    ReshapePolicy = ReshapePolicy.Projection;
                }
            }
        public IOrientedRectangle GetGeometry(ILabel label, ILabelModelParameter parameter)
        {
            var   php   = parameter as PoolHeaderParameter;
            INode owner = (INode)label.Owner;

            if (php == null || owner == null)
            {
                return(null);
            }

            ITable  table  = owner.Lookup <ITable>();
            InsetsD insets = table != null && table.Insets != InsetsD.Empty ? table.Insets : new InsetsD(0);

            var orientedRectangle = new OrientedRectangle();

            orientedRectangle.Resize(label.PreferredSize);
            switch (php.Side)
            {
            case 0: // North
                orientedRectangle.SetUpVector(0, -1);
                orientedRectangle.SetCenter(new PointD(owner.Layout.X + owner.Layout.Width / 2, owner.Layout.Y + insets.Top / 2));
                break;

            case 1: // East
                orientedRectangle.SetUpVector(1, 0);
                orientedRectangle.SetCenter(new PointD(owner.Layout.GetMaxX() - insets.Right / 2, owner.Layout.Y + owner.Layout.Height / 2));
                break;

            case 2: // South
                orientedRectangle.SetUpVector(0, -1);
                orientedRectangle.SetCenter(new PointD(owner.Layout.X + owner.Layout.Width / 2, owner.Layout.GetMaxY() - insets.Bottom / 2));
                break;

            case 3: // West
            default:
                orientedRectangle.SetUpVector(-1, 0);
                orientedRectangle.SetCenter(new PointD(owner.Layout.X + insets.Left / 2, owner.Layout.Y + owner.Layout.Height / 2));
                break;
            }

            return(orientedRectangle);
        }
示例#11
0
        /// <summary>
        /// Paint <see cref="IGraph">component</see> as elements of the palette.
        /// </summary>
        private static void OnDrawItem(object sender, DrawItemEventArgs e)
        {
            if (sender is ListBox listBox && listBox.Items[e.Index] is IGraph component)
            {
                var     bounds = e.Bounds;
                InsetsD insets = new InsetsD(10);

                // create a GraphControl that shows the component
                var componentControl = new GraphControl {
                    Size = new Size(bounds.Width - (int)insets.HorizontalInsets, bounds.Height - (int)insets.VerticalInsets),
                    HorizontalScrollBarPolicy = ScrollBarVisibility.Never,
                    VerticalScrollBarPolicy   = ScrollBarVisibility.Never,
                    Graph = component
                };
                componentControl.FitGraphBounds();

                // create a bitmap with the same size as the GraphControl
                Bitmap   bm = new Bitmap(componentControl.Size.Width, componentControl.Size.Height);
                Graphics g  = Graphics.FromImage(bm);
                e.DrawBackground();
                g.SmoothingMode = SmoothingMode.HighQuality;
                g.Clear(Color.White);

                // render the content of the GraphControl into the bitmap
                ContextConfigurator cc = new ContextConfigurator(componentControl.ContentRect);
                var renderContext      = cc.CreateRenderContext(componentControl, g);
                componentControl.RenderContent(renderContext, g);

                // render the image as an element of the palette
                var listGraphics = e.Graphics;
                var oldClip      = listGraphics.Clip;
                listGraphics.IntersectClip(bounds);
                listGraphics.Clear(listBox.BackColor);
                listGraphics.DrawImage(bm, bounds.X + (int)insets.Left, bounds.Y + (int)insets.Top, bm.Width, bm.Height);
                listGraphics.Clip = oldClip;
                e.DrawFocusRectangle();

                componentControl.Dispose();
                g.Dispose();
                bm.Dispose();
            }
        }
示例#12
0
        public InsetsD GetInsets(INode item)
        {
            InsetsD result = InsetsD.Empty;

            if (innnerProvider != null)
            {
                result = innnerProvider.GetInsets(item);
            }
            foreach (ILabel label in item.Labels)
            {
                var provider =
                    label.LayoutParameter.Model.Lookup <INodeInsetsProvider>();
                if (provider != null)
                {
                    InsetsD insets = provider.GetInsets(item);
                    result = result.CreateUnion(insets);
                }
            }
            return(result);
        }
示例#13
0
        /// <summary>
        /// Initializes the graph instance, setting default styles
        /// and creating a small sample graph.
        /// </summary>
        protected virtual void InitializeGraph()
        {
            // create the manager for the folding operations
            FoldingManager foldingManager = new FoldingManager();

            // create a view
            foldingView = foldingManager.CreateFoldingView();

            // and set it to the GraphControl
            graphControl.Graph = foldingView.Graph;

            // decorate the behavior of nodes
            NodeDecorator nodeDecorator = graphControl.Graph.GetDecorator().NodeDecorator;

            // adjust the insets so that labels are considered
            nodeDecorator.InsetsProviderDecorator.SetImplementationWrapper(
                delegate(INode node, INodeInsetsProvider insetsProvider) {
                if (insetsProvider != null)
                {
                    InsetsD insets = insetsProvider.GetInsets(node);
                    return(new LabelInsetsProvider(insets));
                }
                else
                {
                    return(new LabelInsetsProvider());
                }
            });

            //Constrain group nodes to at least the size of their labels
            nodeDecorator.SizeConstraintProviderDecorator.SetImplementationWrapper(
                (node, oldImpl) => new LabelSizeConstraintProvider(oldImpl));

            fixedGroupNodeLayout = graphControl.Graph.MapperRegistry.CreateMapper <INode, RectD?>("NodeLayouts");
            ReadSampleGraph();
            incrementalNodes.UnionWith(graphControl.Graph.Nodes);
        }
示例#14
0
        protected override VisualGroup CreateVisual(IRenderContext context, IStripe stripe)
        {
            var     layout = stripe.Layout.ToRectD();
            var     cc     = new VisualGroup();
            InsetsD stripeInsets;

            StripeDescriptor descriptor;

            //Depending on the stripe type, we need to consider horizontal or vertical insets
            if (stripe is IColumn)
            {
                var col          = (IColumn)stripe;
                var actualInsets = col.GetActualInsets();
                stripeInsets = new InsetsD(0, actualInsets.Top, 0, actualInsets.Bottom);
            }
            else
            {
                var row          = (IRow)stripe;
                var actualInsets = row.GetActualInsets();
                stripeInsets = new InsetsD(actualInsets.Left, 0, actualInsets.Right, 0);
            }

            if (stripe.GetChildStripes().Any())
            {
                //Parent stripe - use the parent descriptor
                descriptor = ParentDescriptor;
            }
            else
            {
                int index;
                if (stripe is IColumn)
                {
                    var col = (IColumn)stripe;
                    //Get all leaf columns
                    var leafs = col.Table.RootColumn.GetLeaves().ToList();
                    //Determine the index
                    index = leafs.FindIndex(curr => col == curr);
                    //Use the correct descriptor
                    descriptor = index % 2 == 0 ? EvenLeafDescriptor : OddLeafDescriptor;
                }
                else
                {
                    var row   = (IRow)stripe;
                    var leafs = row.Table.RootRow.GetLeaves().ToList();
                    index      = leafs.FindIndex((curr) => row == curr);
                    descriptor = index % 2 == 0 ? EvenLeafDescriptor : OddLeafDescriptor;
                }
            }
            cc.Add(new RectangleVisual(layout)
            {
                Brush = descriptor.BackgroundBrush
            });
            //Draw the insets
            if (stripeInsets.Left > 0)
            {
                cc.Add(new RectangleVisual(layout.X, layout.Y, stripeInsets.Left, layout.Height)
                {
                    Brush = descriptor.InsetBrush
                });
            }
            if (stripeInsets.Top > 0)
            {
                cc.Add(new RectangleVisual(layout.X, layout.Y, layout.Width, stripeInsets.Top)
                {
                    Brush = descriptor.InsetBrush
                });
            }
            if (stripeInsets.Right > 0)
            {
                cc.Add(new RectangleVisual(layout.MaxX - stripeInsets.Right, layout.Y, stripeInsets.Right, layout.Height)
                {
                    Brush = descriptor.InsetBrush
                });
            }
            if (stripeInsets.Bottom > 0)
            {
                cc.Add(new RectangleVisual(layout.X, layout.MaxY - stripeInsets.Bottom, layout.Width, stripeInsets.Bottom)
                {
                    Brush = descriptor.InsetBrush
                });
            }
            cc.Add(new RectangleVisual(layout)
            {
                Pen = new Pen(descriptor.BorderBrush, descriptor.BorderThickness)
            });
            return(cc);
        }
 public NodeControlNodeStyleExtension()
 {
     Insets        = new InsetsD(5);
     MinimumSize   = SizeD.Empty;
     ContextLookup = Lookups.EmptyContextLookup;
 }
示例#16
0
 public IconLabelStyleExtension()
 {
     AutoFlip         = true;
     InnerStyleInsets = new InsetsD(0);
 }
 public CollapsibleNodeStyleDecoratorExtension()
 {
     ButtonLocationParameter = InteriorLabelModel.NorthWest;
     Insets = new InsetsD(5, 16, 5, 5);
 }
        protected override VisualGroup UpdateVisual(IRenderContext context, VisualGroup group, IStripe stripe)
        {
            IRectangle layout = stripe.Layout.ToRectD();
            InsetsD    stripeInsets;
            int        index;

            if (stripe is IColumn)
            {
                var col = (IColumn)stripe;
                stripeInsets = new InsetsD(0, col.GetActualInsets().Top, 0, col.GetActualInsets().Bottom);
                index        = col.ParentColumn.ChildColumns.ToList().FindIndex((curr) => col == curr);
            }
            else
            {
                var row = (IRow)stripe;
                stripeInsets = new InsetsD(row.GetActualInsets().Left, 0, row.GetActualInsets().Right, 0);
                index        = row.ParentRow.ChildRows.ToList().FindIndex((curr) => row == curr);
            }
            StripeDescriptor descriptor = index % 2 == 0 ? EvenStripeDescriptor : OddStripeDescriptor;
            var rect = (RectangleVisual)group.Children[0];

            rect.Rectangle = layout;
            rect.Brush     = descriptor.BackgroundBrush;
            if (rect.Pen.Brush != descriptor.BorderBrush)
            {
                rect.Pen = new Pen(descriptor.BorderBrush, descriptor.BorderThickness);
            }

            int count = 1;

            //Draw the insets
            if (stripeInsets.Left > 0)
            {
                if (count >= group.Children.Count)
                {
                    group.Add(new RectangleVisual(layout.X, layout.Y, stripeInsets.Left, layout.Height)
                    {
                        Brush = descriptor.InsetBrush
                    });
                }
                else
                {
                    rect           = (RectangleVisual)group.Children[count];
                    rect.Rectangle = new RectD(layout.X, layout.Y, stripeInsets.Left, layout.Height);
                }
                count++;
            }
            if (stripeInsets.Top > 0)
            {
                if (count >= group.Children.Count)
                {
                    group.Add(new RectangleVisual(layout.X, layout.Y, layout.Width, stripeInsets.Top)
                    {
                        Brush = descriptor.InsetBrush
                    });
                }
                else
                {
                    rect           = (RectangleVisual)group.Children[count];
                    rect.Rectangle = new RectD(layout.X, layout.Y, layout.Width, stripeInsets.Top);
                }
                count++;
            }
            if (stripeInsets.Right > 0)
            {
                if (count >= group.Children.Count)
                {
                    group.Add(new RectangleVisual(layout.GetMaxX() - stripeInsets.Right, layout.Y, stripeInsets.Right, layout.Height)
                    {
                        Brush = descriptor.InsetBrush
                    });
                }
                else
                {
                    rect           = (RectangleVisual)group.Children[count];
                    rect.Rectangle = new RectD(layout.GetMaxX() - stripeInsets.Right, layout.Y, stripeInsets.Right, layout.Height);
                }
                count++;
            }
            if (stripeInsets.Bottom > 0)
            {
                if (count >= group.Children.Count)
                {
                    group.Add(new RectangleVisual(layout.X, layout.GetMaxY() - stripeInsets.Bottom, layout.Width, stripeInsets.Bottom)
                    {
                        Brush = descriptor.InsetBrush
                    });
                }
                else
                {
                    rect           = (RectangleVisual)group.Children[count];
                    rect.Rectangle = new RectD(layout.X, layout.GetMaxY() - stripeInsets.Bottom, layout.Width, stripeInsets.Bottom);
                }
                count++;
            }
            while (group.Children.Count > count)
            {
                group.Children.RemoveAt(group.Children.Count - 1);
            }
            return(group);
        }
示例#19
0
 public static void SetInsets(this ITable table, IStripe stripe, InsetsD insets)
 {
     table.SetStripeInsets(stripe, insets);
 }
示例#20
0
 public GroupNodeStyleExtension()
 {
     Insets = new InsetsD(15);
 }
 public EncompassingRectangle(IEnumerable <INode> nodes, InsetsD margins)
 {
     this.nodes   = nodes;
     this.margins = margins;
     this.invalid = true;
 }
示例#22
0
 public LabelInsetsProvider(InsetsD outerInsets)
 {
     this.outerInsets = outerInsets;
 }
            public void Paint(IRenderContext context, Graphics graphics)
            {
                var        node   = Stripe;
                var        stripe = node.Lookup <IStripe>();
                IRectangle layout = node.Layout.ToRectD();

                if (stripe != null)
                {
                    InsetsD stripeInsets;

                    if (stripe is IColumn)
                    {
                        var col = (IColumn)stripe;
                        stripeInsets = new InsetsD(0, col.GetActualInsets().Top, 0, col.GetActualInsets().Bottom);
                    }
                    else
                    {
                        var row = (IRow)stripe;
                        stripeInsets = new InsetsD(row.GetActualInsets().Left, 0, row.GetActualInsets().Right, 0);
                    }

                    StripeDescriptor descriptor;

                    if (stripe.GetChildStripes().Any())
                    {
                        //Parent stripe - use the parent descriptor
                        descriptor = ParentDescriptor;
                    }
                    else
                    {
                        int index;
                        if (stripe is IColumn)
                        {
                            var col = (IColumn)stripe;
                            //Get all leaf columns
                            var leafs = col.Table.RootColumn.GetLeaves().ToList();
                            //Determine the index
                            index = leafs.FindIndex((curr) => col == curr);
                            //Use the correct descriptor
                            descriptor = index % 2 == 0 ? EvenLeafDescriptor : OddLeafDescriptor;
                        }
                        else
                        {
                            var row   = (IRow)stripe;
                            var leafs = row.Table.RootRow.GetLeaves().ToList();
                            index      = leafs.FindIndex((curr) => row == curr);
                            descriptor = index % 2 == 0 ? EvenLeafDescriptor : OddLeafDescriptor;
                        }
                    }

                    graphics.FillRectangle(descriptor.BackgroundBrush,
                                           new RectangleF((float)layout.X, (float)node.Layout.Y, (float)layout.Width, (float)layout.Height));
                    //Draw the insets
                    if (stripeInsets.Left > 0)
                    {
                        graphics.FillRectangle(descriptor.InsetBrush,
                                               new RectangleF((float)layout.X, (float)node.Layout.Y, (float)stripeInsets.Left, (float)layout.Height));
                    }
                    if (stripeInsets.Top > 0)
                    {
                        graphics.FillRectangle(descriptor.InsetBrush,
                                               new RectangleF((float)layout.X, (float)layout.Y, (float)layout.Width, (float)stripeInsets.Top));
                    }
                    if (stripeInsets.Right > 0)
                    {
                        graphics.FillRectangle(descriptor.InsetBrush,
                                               new RectangleF((float)(layout.GetMaxX() - stripeInsets.Right), (float)layout.Y,
                                                              (float)stripeInsets.Right, (float)layout.Height));
                    }
                    if (stripeInsets.Bottom > 0)
                    {
                        graphics.FillRectangle(descriptor.InsetBrush,
                                               new RectangleF((float)layout.X, (float)(layout.GetMaxY() - stripeInsets.Bottom), (float)layout.Width,
                                                              (float)stripeInsets.Bottom));
                    }
                    graphics.DrawRectangle(new Pen(descriptor.BorderBrush, descriptor.BorderThickness),
                                           new Rectangle((int)layout.X, (int)layout.Y, (int)layout.Width, (int)layout.Height));
                }
            }