/// <summary> /// Resizes the container to the specified size /// </summary> /// <param name="newSize">New size to which the container is to be resized</param> /// <param name="justify">Resize justification, which indicates the edge at which widgets are to /// remain in their current positions (i.e. right justification will make the left edge move left/right /// while right edge's location stays constant)</param> public void Resize(MatrixSize newSize, WidgetContainerResizeJustify justify) { if (newSize.RowCount > 256 || newSize.ColumnCount > 256) { throw new ApplicationException(string.Format("Attemp to allocate too much ({0} x {1})", newSize.RowCount, newSize.ColumnCount)); } else if (newSize == this.Bounds.Size) { return; } Validate(); MatrixSize currentSize = this.Size; MatrixSize originShift = currentSize - newSize; if (!justify.HasFlag(WidgetContainerResizeJustify.Bottom)) { originShift.RowCount = 0; } if (!justify.HasFlag(WidgetContainerResizeJustify.Right)) { originShift.ColumnCount = 0; } MatrixRect newContainerBounds = new MatrixRect( _containerBounds.Location + originShift, newSize); // Cells in the intersection of original bounding rectangle and the new bounding // rectangle are the ones that will survive the resize operation. Once we identify // the intersection of the two rectangles, we need to iterate through the original // array and copy those cells into the new array MatrixRect existingCellBounds = _containerBounds.Intersect(newContainerBounds); // normalize existing cell bounding box around 0-based arrays. existingCellBounds.Location = new MatrixLoc(originShift.RowCount > 0 ? originShift.RowCount : 0, originShift.ColumnCount > 0 ? originShift.ColumnCount : 0); Array2D <WidgetData> newArray = new Array2D <WidgetData>(newSize); foreach (var loc in existingCellBounds) { newArray[loc - originShift] = _widgetArray[loc]; } _widgetArray = newArray; _containerBounds = newContainerBounds; this.IsDirty = true; Validate(); OnContainerResized(); Validate(); }
private void SetWidget(MatrixLoc location, WidgetData widget) { WidgetData removedWidget = null; Validate(); // the same widget is being inserted at the same spot where it is already located, // let not do anything and just exit if (widget != null && widget.Parent == this && widget.Location == location) { return; } MatrixRect neededBounds = _containerBounds.GrowTo(location); // If the cell being modified within the bounds of the current array, let's make sure // the existing cell is empty. Otherwise, we need to reallocate the array before // we can assign the widget to it. if (neededBounds.Size == _containerBounds.Size) { removedWidget = ClearWidget(location); } else if (widget != null) { WidgetContainerResizeJustify resizeJustify = (_containerBounds.Row == neededBounds.Row ? WidgetContainerResizeJustify.Top : WidgetContainerResizeJustify.Bottom) | (_containerBounds.Column == neededBounds.Column ? WidgetContainerResizeJustify.Left : WidgetContainerResizeJustify.Right); Resize(neededBounds.Size, resizeJustify); } Validate(); if (widget != null) { if (widget.HasOwner) { widget.Parent.Remove(widget); } _widgetArray[_containerBounds.ToIndex(location)] = widget; widget.SetOwner(this, location); widget.IsDirtyChanged += OnChildIsDirtyChanged; if (removedWidget != null) { OnWidgetReplaced(location, removedWidget, widget); removedWidget = null; } else { OnWidgetAdded(location, widget); } } if (removedWidget != null) { OnWidgetRemoved(location, removedWidget); } Validate(); IsDirty = true; }
/// <summary> /// Resizes the container to the specified size /// </summary> /// <param name="newSize">New size to which the container is to be resized</param> /// <param name="justify">Resize justification, which indicates the edge at which widgets are to /// remain in their current positions (i.e. right justification will make the left edge move left/right /// while right edge's location stays constant)</param> public void Resize( MatrixSize newSize, WidgetContainerResizeJustify justify ) { if( newSize.RowCount > 256 || newSize.ColumnCount > 256 ) { throw new ApplicationException( string.Format( "Attemp to allocate too much ({0} x {1})", newSize.RowCount, newSize.ColumnCount ) ); } else if( newSize == this.Bounds.Size ) { return; } Validate(); MatrixSize currentSize = this.Size; MatrixSize originShift = currentSize - newSize; if( !justify.HasFlag( WidgetContainerResizeJustify.Bottom ) ) originShift.RowCount = 0; if( !justify.HasFlag( WidgetContainerResizeJustify.Right ) ) originShift.ColumnCount = 0; MatrixRect newContainerBounds = new MatrixRect( _containerBounds.Location + originShift, newSize ); // Cells in the intersection of original bounding rectangle and the new bounding // rectangle are the ones that will survive the resize operation. Once we identify // the intersection of the two rectangles, we need to iterate through the original // array and copy those cells into the new array MatrixRect existingCellBounds = _containerBounds.Intersect( newContainerBounds ); // normalize existing cell bounding box around 0-based arrays. existingCellBounds.Location = new MatrixLoc( originShift.RowCount > 0 ? originShift.RowCount : 0, originShift.ColumnCount > 0 ? originShift.ColumnCount : 0 ); Array2D< WidgetData > newArray = new Array2D<WidgetData>( newSize ); foreach( var loc in existingCellBounds ) { newArray[ loc - originShift ] = _widgetArray[ loc ]; } _widgetArray = newArray; _containerBounds = newContainerBounds; this.IsDirty = true; Validate(); OnContainerResized(); Validate(); }
/// <summary> /// Resizes the container to the specified size /// </summary> /// <param name="numRows">Number of rows to resize to</param> /// <param name="numColumns">Number of columns to resize to</param> /// <param name="justify">Resize justification, which indicates the edge at which widgets are to /// remain in their current positions (i.e. right justification will make the left edge move left/right /// while right edge's location stays constant)</param> public void Resize(int numRows, int numColumns, WidgetContainerResizeJustify justify) { Resize(new MatrixSize(numRows, numColumns), justify); }
/// <summary> /// Resizes the container to the specified size /// </summary> /// <param name="numRows">Number of rows to resize to</param> /// <param name="numColumns">Number of columns to resize to</param> /// <param name="justify">Resize justification, which indicates the edge at which widgets are to /// remain in their current positions (i.e. right justification will make the left edge move left/right /// while right edge's location stays constant)</param> public void Resize( int numRows, int numColumns, WidgetContainerResizeJustify justify ) { Resize( new MatrixSize( numRows, numColumns ), justify ); }