void AttachColumn(int column) { for (int y = 0; y < controls.GetLength(0); y++) { Attach(controls[y, column], column, y); } }
public void Move(Control child, int x, int y) { var current = views[y, x]; if (current != null) { var currentView = current.GetContainerView(); if (currentView != null) { currentView.RemoveFromSuperview(); } } for (int yy = 0; yy < views.GetLength(0); yy++) { for (int xx = 0; xx < views.GetLength(1); xx++) { if (object.ReferenceEquals(views[yy, xx], child)) { views[yy, xx] = null; } } } views[y, x] = child; if (Widget.Loaded) { LayoutParent(); } }
private Table BuildLayout() { Table table = new Table(); for (int i = 0; i < cells.GetLength(0); i++) { TableRow row = new TableRow(); for (int j = 0; j < cells.GetLength(1); j++) { TableCell cell = new TableCell(); Control c = cells[i, j]; if (c != null) { cell.Controls.Add(c); } row.Cells.Add(cell); } table.Rows.Add(row); } return(table); }
swf.Padding GetPadding(int x, int y) { return(new swf.Padding( x == 0 ? 0 : spacing.Width / 2, y == 0 ? 0 : spacing.Height / 2, x == views.GetLength(0) - 1 ? 0 : (spacing.Width + 1) / 2, y == views.GetLength(1) - 1 ? 0 : (spacing.Height + 1) / 2)); }
//удаление контролов ячеек с формы private void RemoveControl() { for (int i = 0; i < board.GetLength(0); i++) { for (int j = 0; j < board.GetLength(1); j++) { Controls.Remove(board[i, j]); } } btnFace.Image = null; }
void FillEmptyCells() { for (int x = 1; x < views.GetLength(0); x++) { if (Control.GetControlFromPosition(x, 0) == null && views[x, 0] == null) { Control.Controls.Add(CreateEmptyCell(x, 0), x, 0); } } for (int y = 0; y < views.GetLength(1); y++) { if (Control.GetControlFromPosition(0, y) == null && views[0, y] == null) { Control.Controls.Add(CreateEmptyCell(0, y), 0, y); } } }
/// <summary> /// Calculate the widths of the columns and the heights of the rows. /// </summary> /// <param name="parent">The parent control.</param> /// <param name="settings">The layout settings.</param> /// <param name="grid">The matrix with the controls in their corresponding positions.</param> /// <param name="columnWidths">The list of widths for the columns.</param> /// <param name="rowHeights">The list of heights for the rows.</param> private static void CalculateCellSizes(Control parent, TableLayoutSettings settings, Control[,] grid, out int[] columnWidths, out int[] rowHeights) { int columns = grid.GetLength(0); int rows = grid.GetLength(1); var rect = new Rectangle(Point.Empty, parent.DisplayRectangle.Size); // Column widths Func <int, int> findWidestControl = index => FindBiggestControl(rows, i => grid[index, i], s => s.Width, margin => margin.Horizontal); columnWidths = GetDimensionSize(columns, settings.ColumnStyles, rect.Width, findWidestControl); // Row heights Func <int, int> findTallestControl = index => FindBiggestControl(columns, i => grid[i, index], s => s.Height, margin => margin.Vertical); rowHeights = GetDimensionSize(rows, settings.RowStyles, rect.Height, findTallestControl); }
public void Remove(Control child) { swf.Control childControl = child.GetContainerControl(); if (childControl.Parent == Control) { childControl.Parent = null; for (int y = 0; y < views.GetLength(0); y++) { for (int x = 0; x < views.GetLength(1); x++) { if (object.ReferenceEquals(views[y, x], child)) { views[y, x] = null; } } } } }
public void Remove(Control child) { SWF.Control childControl = child.GetContainerControl(); if (childControl.Parent != null) { childControl.Parent.Controls.Remove(childControl); } for (int y = 0; y < views.GetLength(0); y++) { for (int x = 0; x < views.GetLength(1); x++) { if (views[y, x] == child) { views[y, x] = null; } } } }
void SetScale(bool force = false) { if (Control == null || (!Widget.Loaded && !force)) { return; } for (int y = 0; y < controls.GetLength(1); y++) { for (int x = 0; x < controls.GetLength(0); x++) { var handler = controls[x, y].GetWpfFrameworkElement(); if (handler != null) { SetScale(handler, x, y); } } } }
void FillEmptyCells() { for (int x = 1; x < views.GetLength(0); x++) { var ctl = Control.GetControlFromPosition(x, 0); if (ctl == null) { Control.Controls.Add(CreateEmptyCell(x, 0), x, 0); } } for (int y = 0; y < views.GetLength(1); y++) { var ctl = Control.GetControlFromPosition(0, y); if (ctl == null) { Control.Controls.Add(CreateEmptyCell(0, y), 0, y); } } }
/// <summary> /// Resets the controls specific to each hand which might not otherwise be reset /// </summary> public void resetAllTableElements() { potValue.Text = ""; clearCard(tableCard1); clearCard(tableCard2); clearCard(tableCard3); clearCard(tableCard4); clearCard(tableCard5); for (int i = 0; i < playerControls.GetLength(0); i++) { clearCard((PictureBox)playerControls[i, 2]); clearCard((PictureBox)playerControls[i, 3]); //clearCard((PictureBox)playerControls[i, 4]); playerControls[i, 0].Text = ""; playerControls[i, 1].Text = ""; playerControls[i, 4].Text = ""; sitInOutPlayer((byte)i, true); } }
public override Size GetPreferredSize(Size availableSize) { var baseSize = base.GetPreferredSize(availableSize); if (views == null) { return(baseSize); } var heights = new float[views.GetLength(0)]; var widths = new float[views.GetLength(1)]; float totalxpadding = Padding.Horizontal + Spacing.Width * (widths.Length - 1); float totalypadding = Padding.Vertical + Spacing.Height * (heights.Length - 1); var requiredx = totalxpadding; var requiredy = totalypadding; for (int y = 0; y < heights.Length; y++) { heights[y] = 0; } for (int x = 0; x < widths.Length; x++) { widths[x] = 0; } for (int y = 0; y < heights.Length; y++) { for (int x = 0; x < widths.Length; x++) { var view = views[y, x]; if (view != null && view.Visible) { var size = view.GetPreferredSize(availableSize); if (size.Width > widths[x]) { requiredx += size.Width - widths[x]; widths[x] = size.Width; } if (size.Height > heights[y]) { requiredy += size.Height - heights[y]; heights[y] = size.Height; } } } } return(Size.Max(baseSize, new Size((int)requiredx, (int)requiredy))); }
private void OutputControlGrid(Control[,] grid, TableLayoutPanel panel) { Console.WriteLine(" Size: {0}x{1}", grid.GetLength(0), grid.GetLength(1)); Console.Write(" "); foreach (int i in panel.column_widths) { Console.Write(" {0}px ", i.ToString().PadLeft(3)); } Console.WriteLine(); for (int y = 0; y < grid.GetLength(1); y++) { Console.Write(" {0}px |", panel.row_heights[y].ToString().PadLeft(3)); for (int x = 0; x < grid.GetLength(0); x++) { if (grid[x, y] == null) { Console.Write(" --- |"); } else if (string.IsNullOrEmpty(grid[x, y].Name)) { Console.Write(" ??? |"); } else { Console.Write(" {0} |", grid[x, y].Name.PadRight(5).Substring(0, 5)); } } Console.WriteLine(); } }
internal override Size GetPreferredSizeCore (Size proposedSize) { // If the tablelayoutowner is autosize, we have to make sure it is big enough // to hold every non-autosize control actual_positions = (LayoutEngine as TableLayout).CalculateControlPositions (this, Math.Max (ColumnCount, 1), Math.Max (RowCount, 1)); // Use actual row/column counts, not user set ones int actual_cols = actual_positions.GetLength (0); int actual_rows = actual_positions.GetLength (1); // Figure out how wide the owner needs to be int[] column_widths = new int[actual_cols]; float total_column_percentage = 0f; // Figure out how tall each column wants to be for (int i = 0; i < actual_cols; i++) { if (i < ColumnStyles.Count && ColumnStyles[i].SizeType == SizeType.Percent) total_column_percentage += ColumnStyles[i].Width; int biggest = 0; for (int j = 0; j < actual_rows; j++) { Control c = actual_positions[i, j]; if (c != null) { if (!c.AutoSize) biggest = Math.Max (biggest, c.ExplicitBounds.Width + c.Margin.Horizontal + Padding.Horizontal); else biggest = Math.Max (biggest, c.PreferredSize.Width + c.Margin.Horizontal + Padding.Horizontal); } } column_widths[i] = biggest; } // Because percentage based rows divy up the remaining space, // we have to make the owner big enough so that all the rows // get bigger, even if we only need one to be bigger. int non_percent_total_width = 0; int percent_total_width = 0; for (int i = 0; i < actual_cols; i++) { if (i < ColumnStyles.Count && ColumnStyles[i].SizeType == SizeType.Percent) percent_total_width = Math.Max (percent_total_width, (int)(column_widths[i] / ((ColumnStyles[i].Width) / total_column_percentage))); else non_percent_total_width += column_widths[i]; } // Figure out how tall the owner needs to be int[] row_heights = new int[actual_rows]; float total_row_percentage = 0f; // Figure out how tall each row wants to be for (int j = 0; j < actual_rows; j++) { if (j < RowStyles.Count && RowStyles[j].SizeType == SizeType.Percent) total_row_percentage += RowStyles[j].Height; int biggest = 0; for (int i = 0; i < actual_cols; i++) { Control c = actual_positions[i, j]; if (c != null) { if (!c.AutoSize) biggest = Math.Max (biggest, c.ExplicitBounds.Height + c.Margin.Vertical + Padding.Vertical); else biggest = Math.Max (biggest, c.PreferredSize.Height + c.Margin.Vertical + Padding.Vertical); } } row_heights[j] = biggest; } // Because percentage based rows divy up the remaining space, // we have to make the owner big enough so that all the rows // get bigger, even if we only need one to be bigger. int non_percent_total_height = 0; int percent_total_height = 0; for (int j = 0; j < actual_rows; j++) { if (j < RowStyles.Count && RowStyles[j].SizeType == SizeType.Percent) percent_total_height = Math.Max (percent_total_height, (int)(row_heights[j] / ((RowStyles[j].Height) / total_row_percentage))); else non_percent_total_height += row_heights[j]; } int border_width = GetCellBorderWidth (CellBorderStyle); return new Size (non_percent_total_width + percent_total_width + (border_width * (actual_cols + 1)), non_percent_total_height + percent_total_height + (border_width * (actual_rows + 1))); }
internal override Size GetPreferredSizeCore (Size proposedSize) { // If the tablelayoutowner is autosize, we have to make sure it is big enough // to hold every non-autosize control actual_positions = (LayoutEngine as TableLayout).CalculateControlPositions (this, Math.Max (ColumnCount, 1), Math.Max (RowCount, 1)); // Use actual row/column counts, not user set ones int actual_cols = actual_positions.GetLength (0); int actual_rows = actual_positions.GetLength (1); // Find the largest column-span/row-span values. A table entry that spans more than one // column (row) should not be treated as though it's width (height) all belongs to the // first column (row), but should be spread out across all the columns (rows) that are // spanned. So we need to keep track of the widths (heights) of spans as well as // individual columns (rows). int max_colspan = 1, max_rowspan = 1; foreach (Control c in Controls) { max_colspan = Math.Max(max_colspan, GetColumnSpan(c)); max_rowspan = Math.Max(max_rowspan, GetRowSpan(c)); } // Figure out how wide the owner needs to be int[] column_widths = new int[actual_cols]; // Keep track of widths for spans as well as columns. column_span_widths[i,j] stores // the maximum width for items column i than have a span of j+1 (ie, covers columns // i through i+j). int[,] column_span_widths = new int[actual_cols, max_colspan]; int[] biggest = new int[max_colspan]; float total_column_percentage = 0f; // Figure out how wide each column wants to be for (int i = 0; i < actual_cols; i++) { if (i < ColumnStyles.Count && ColumnStyles[i].SizeType == SizeType.Percent) total_column_percentage += ColumnStyles[i].Width; int absolute_width = -1; if (i < ColumnStyles.Count && ColumnStyles[i].SizeType == SizeType.Absolute) absolute_width = (int)ColumnStyles[i].Width; // use the absolute width if it's absolute! for (int s = 0; s < max_colspan; ++s) biggest[s] = 0; for (int j = 0; j < actual_rows; j++) { Control c = actual_positions[i, j]; if (c != null) { int colspan = GetColumnSpan (c); if (colspan == 0) continue; if (colspan == 1 && absolute_width > -1) biggest[0] = absolute_width; // use the absolute width if the column has absolute width assigned! else if (!c.AutoSize) biggest[colspan-1] = Math.Max (biggest[colspan-1], c.ExplicitBounds.Width + c.Margin.Horizontal + Padding.Horizontal); else biggest[colspan-1] = Math.Max (biggest[colspan-1], c.PreferredSize.Width + c.Margin.Horizontal + Padding.Horizontal); } else if (absolute_width > -1) { biggest[0] = absolute_width; } } for (int s = 0; s < max_colspan; ++s) column_span_widths[i,s] = biggest[s]; } for (int i = 0; i < actual_cols; ++i) { for (int s = 1; s < max_colspan; ++s) { if (column_span_widths[i,s] > 0) AdjustWidthsForSpans (column_span_widths, i, s); } column_widths[i] = column_span_widths[i,0]; } // Because percentage based rows divy up the remaining space, // we have to make the owner big enough so that all the rows // get bigger, even if we only need one to be bigger. int non_percent_total_width = 0; int percent_total_width = 0; for (int i = 0; i < actual_cols; i++) { if (i < ColumnStyles.Count && ColumnStyles[i].SizeType == SizeType.Percent) percent_total_width = Math.Max (percent_total_width, (int)(column_widths[i] / ((ColumnStyles[i].Width) / total_column_percentage))); else non_percent_total_width += column_widths[i]; } int border_width = GetCellBorderWidth (CellBorderStyle); int needed_width = non_percent_total_width + percent_total_width + (border_width * (actual_cols + 1)); // Figure out how tall the owner needs to be int[] row_heights = new int[actual_rows]; int[,] row_span_heights = new int[actual_rows, max_rowspan]; biggest = new int[max_rowspan]; float total_row_percentage = 0f; // Figure out how tall each row wants to be for (int j = 0; j < actual_rows; j++) { if (j < RowStyles.Count && RowStyles[j].SizeType == SizeType.Percent) total_row_percentage += RowStyles[j].Height; int absolute_height = -1; if (j < RowStyles.Count && RowStyles[j].SizeType == SizeType.Absolute) absolute_height = (int)RowStyles[j].Height; // use the absolute height if it's absolute! for (int s = 0; s < max_rowspan; ++s) biggest[s] = 0; for (int i = 0; i < actual_cols; i++) { Control c = actual_positions[i, j]; if (c != null) { int rowspan = GetRowSpan (c); if (rowspan == 0) continue; if (rowspan == 1 && absolute_height > -1) biggest[0] = absolute_height; // use the absolute height if the row has absolute height assigned! else if (!c.AutoSize) biggest[rowspan-1] = Math.Max (biggest[rowspan-1], c.ExplicitBounds.Height + c.Margin.Vertical + Padding.Vertical); else biggest[rowspan-1] = Math.Max (biggest[rowspan-1], c.PreferredSize.Height + c.Margin.Vertical + Padding.Vertical); } else if (absolute_height > -1) { biggest[0] = absolute_height; } } for (int s = 0; s < max_rowspan; ++s) row_span_heights[j,s] = biggest[s]; } for (int j = 0; j < actual_rows; ++j) { for (int s = 1; s < max_rowspan; ++s) { if (row_span_heights[j,s] > 0) AdjustHeightsForSpans (row_span_heights, j, s); } row_heights[j] = row_span_heights[j,0]; } // Because percentage based rows divy up the remaining space, // we have to make the owner big enough so that all the rows // get bigger, even if we only need one to be bigger. int non_percent_total_height = 0; int percent_total_height = 0; for (int j = 0; j < actual_rows; j++) { if (j < RowStyles.Count && RowStyles[j].SizeType == SizeType.Percent) percent_total_height = Math.Max (percent_total_height, (int)(row_heights[j] / ((RowStyles[j].Height) / total_row_percentage))); else non_percent_total_height += row_heights[j]; } int needed_height = non_percent_total_height + percent_total_height + (border_width * (actual_rows + 1)); return new Size (needed_width, needed_height); }
private void CalculateColumnRowSizes(TableLayoutPanel panel, Control[,] actual_positions, out int[] column_widths, out int[] row_heights, Size size, bool measureOnly) { TableLayoutSettings settings = panel.LayoutSettings; int columns = actual_positions.GetLength(0); int rows = actual_positions.GetLength(1); bool auto_size = panel.AutoSizeInternal && measureOnly; bool boundBySize = !measureOnly; column_widths = new int[actual_positions.GetLength(0)]; row_heights = new int[actual_positions.GetLength(1)]; // Calculate the bounded size only if we are in default layout and docked, otherwise calculate unbounded. if (measureOnly && size.Width > 0) { if (panel.Parent != null && panel.Parent.LayoutEngine is DefaultLayout) { boundBySize |= panel.Dock == DockStyle.Top || panel.Dock == DockStyle.Bottom || panel.Dock == DockStyle.Fill; boundBySize |= (panel.Anchor & (AnchorStyles.Left | AnchorStyles.Right)) == (AnchorStyles.Left | AnchorStyles.Right); } } int border_width = TableLayoutPanel.GetCellBorderWidth(panel.CellBorderStyle); // Find the largest column-span/row-span values. int max_colspan = 0, max_rowspan = 0; foreach (Control c in panel.Controls) { if (c.VisibleInternal && c != dummy_control) { max_colspan = Math.Max(max_colspan, settings.GetColumnSpan(c)); max_rowspan = Math.Max(max_rowspan, settings.GetRowSpan(c)); } } // Figure up all the column widths CalculateColumnWidths(settings, actual_positions, max_colspan, settings.ColumnStyles, auto_size, column_widths, false); // Calculate available width int available_width = size.Width - (border_width * (columns + 1)); foreach (int width in column_widths) { available_width -= width; } // Shrink the table horizontally by shrinking it's columns, if necessary if (boundBySize && size.Width > 0 && available_width < 0) { // Calculate the minimum widths for each column int[] col_min_widths = new int[column_widths.Length]; CalculateColumnWidths(settings, actual_positions, max_colspan, settings.ColumnStyles, auto_size, col_min_widths, true); available_width += Shrink(column_widths, col_min_widths, -available_width, max_colspan); } // Finally, assign the remaining space to Percent columns, if any. if (available_width > 0) { available_width -= RedistributePercents(available_width, settings.ColumnStyles, column_widths); } if (available_width > 0 && column_widths.Length > 0) { // Find the last column that isn't an Absolute SizeType, and give it // all this free space. (Absolute sized columns need to retain their // absolute width if at all possible!) int col = Math.Min(settings.ColumnStyles.Count, column_widths.Length) - 1; for (; col >= 0; --col) { if (settings.ColumnStyles[col].SizeType != SizeType.Absolute) { break; } } if (col < 0) { col = column_widths.Length - 1; } column_widths[col] += available_width; } // Figure up all the row heights CalculateRowHeights(settings, actual_positions, max_rowspan, settings.RowStyles, auto_size, column_widths, row_heights); // Calculate available height int available_height = size.Height - (border_width * (rows + 1)); foreach (int height in row_heights) { available_height -= height; } // NOTE: We don't do shrinking here, since there's no space to save. // Finally, assign the remaining space to Percent rows, if any. if (available_height > 0) { available_height -= RedistributePercents(available_height, settings.RowStyles, row_heights); } if (available_height > 0 && row_heights.Length > 0 && !measureOnly) { // Find the last row that isn't an Absolute SizeType, and give it // all this free space. (Absolute sized rows need to retain their // absolute height if at all possible!) int row = Math.Min(settings.RowStyles.Count, row_heights.Length) - 1; for (; row >= 0; --row) { if (settings.RowStyles[row].SizeType != SizeType.Absolute) { break; } } if (row < 0) { row = row_heights.Length - 1; } row_heights[row] += available_height; } }
private static void CalculateRowHeights(TableLayoutSettings settings, Control[,] actual_positions, int max_rowspan, TableLayoutRowStyleCollection row_styles, bool auto_size, int[] column_widths, int[] row_heights) { int columns = actual_positions.GetLength(0); float max_percent_size = 0; // First assign all the Absolute sized rows.. int index = 0; foreach (RowStyle rs in row_styles) { if (index >= row_heights.Length) { break; } if (rs.SizeType == SizeType.Absolute) { row_heights[index] = (int)rs.Height; } index++; } while (index < row_heights.Length) { row_heights[index] = 0; index++; } // Next, assign all the AutoSize rows to the height of their tallest // control. If the table-layout is auto-sized, then make sure that // no row with Percent styling clips its contents. // (per http://msdn.microsoft.com/en-us/library/ms171690.aspx) for (int rowspan = 0; rowspan < max_rowspan; ++rowspan) { for (index = rowspan; index < row_heights.Length - rowspan; ++index) { RowStyle rs = index < row_styles.Count ? row_styles[index] : default_row_style; if (rs.SizeType == SizeType.AutoSize || (auto_size && rs.SizeType == SizeType.Percent)) { int max_height = row_heights[index]; // Find the tallest control in the row for (int i = 0; i < columns; i++) { Control c = actual_positions[i, index - rowspan]; if (c != null && c != dummy_control && c.VisibleInternal) { // Skip any controls not being sized in this pass. if (settings.GetRowSpan(c) != rowspan + 1) { continue; } int current_width = 0; int column_span = settings.GetColumnSpan(c); for (int j = i; j < i + column_span && j < column_widths.Length; j++) { current_width += column_widths[j]; } // Calculate the maximum control height. max_height = Math.Max(max_height, GetControlSize(c, new Size(current_width - c.Margin.Horizontal, 0)).Height + c.Margin.Vertical); } } if (rs.SizeType == SizeType.Percent) { max_percent_size = Math.Max(max_percent_size, max_height / rs.Height); } // Subtract the height of prior rows, if any. for (int i = Math.Max(index - rowspan, 0); i < index; ++i) { max_height -= row_heights[i]; } // If necessary, increase this row's height. if (max_height > row_heights[index]) { row_heights[index] = max_height; } } } } // Resize the percent columns to match other percent columns relatively. for (index = 0; index < row_styles.Count && index < row_heights.Length; ++index) { RowStyle rs = row_styles[index]; if (rs.SizeType == SizeType.Percent) { row_heights[index] = Math.Max(row_heights[index], (int)Math.Ceiling(max_percent_size * rs.Height)); } } }
private void update() { { int old_Ro_size = Ro.Length; int old_C_size = C.Length; int old_B_size = B.Length; System.Array.Resize(ref Ro, ProductsCount); System.Array.Resize(ref C, CentersCount); System.Array.Resize(ref B, CentersCount); for (int i = old_Ro_size; i < Ro.Length; i++) { Ro[i] = createRo(i); } for (int i = old_C_size; i < C.Length; i++) { C[i] = createC(i); } for (int i = old_B_size; i < B.Length; i++) { B[i] = createB(i); } } { int old_D_width = D.GetLength(1); int old_D_height = D.GetLength(0); Control[,] new_D = new Control[CentersCount, ProductsCount]; for (int i = 0; i < CentersCount; i++) { for (int j = 0; j < ProductsCount; j++) { if (i < old_D_height && j < old_D_width) { new_D[i, j] = D[i, j]; } else { new_D[i, j] = createD(i, j); } } } D = new_D; } RoParent.Controls.Clear(); RoParent.Size = new Size(box_area_size.Width * ProductsCount, box_area_size.Height); CParent.Controls.Clear(); CParent.Size = new Size(box_area_size.Width, box_area_size.Height * CentersCount); BParent.Controls.Clear(); BParent.Size = new Size(box_area_size.Width, box_area_size.Height * CentersCount); DParent.Controls.Clear(); DParent.Size = new Size(box_area_size.Width * ProductsCount, box_area_size.Height * CentersCount); for (int i = 0; i < Ro.Length; i++) { RoParent.Controls.Add(Ro[i]); } for (int i = 0; i < C.Length; i++) { CParent.Controls.Add(C[i]); } for (int i = 0; i < B.Length; i++) { BParent.Controls.Add(B[i]); } for (int i = 0; i < D.GetLength(0); i++) { for (int j = 0; j < D.GetLength(1); j++) { DParent.Controls.Add(D[i, j]); } } }
internal override Size GetPreferredSizeCore(Size proposedSize) { // If the tablelayoutowner is autosize, we have to make sure it is big enough // to hold every non-autosize control actual_positions = (LayoutEngine as TableLayout).CalculateControlPositions(this, Math.Max(ColumnCount, 1), Math.Max(RowCount, 1)); // Use actual row/column counts, not user set ones int actual_cols = actual_positions.GetLength(0); int actual_rows = actual_positions.GetLength(1); // Find the largest column-span/row-span values. A table entry that spans more than one // column (row) should not be treated as though it's width (height) all belongs to the // first column (row), but should be spread out across all the columns (rows) that are // spanned. So we need to keep track of the widths (heights) of spans as well as // individual columns (rows). int max_colspan = 1, max_rowspan = 1; foreach (Control c in Controls) { max_colspan = Math.Max(max_colspan, GetColumnSpan(c)); max_rowspan = Math.Max(max_rowspan, GetRowSpan(c)); } // Figure out how wide the owner needs to be int[] column_widths = new int[actual_cols]; // Keep track of widths for spans as well as columns. column_span_widths[i,j] stores // the maximum width for items column i than have a span of j+1 (ie, covers columns // i through i+j). int[,] column_span_widths = new int[actual_cols, max_colspan]; int[] biggest = new int[max_colspan]; float total_column_percentage = 0f; // Figure out how wide each column wants to be for (int i = 0; i < actual_cols; i++) { if (i < ColumnStyles.Count && ColumnStyles[i].SizeType == SizeType.Percent) { total_column_percentage += ColumnStyles[i].Width; } int absolute_width = -1; if (i < ColumnStyles.Count && ColumnStyles[i].SizeType == SizeType.Absolute) { absolute_width = (int)ColumnStyles[i].Width; // use the absolute width if it's absolute! } for (int s = 0; s < max_colspan; ++s) { biggest[s] = 0; } for (int j = 0; j < actual_rows; j++) { Control c = actual_positions[i, j]; if (c != null) { int colspan = GetColumnSpan(c); if (colspan == 0) { continue; } if (colspan == 1 && absolute_width > -1) { biggest[0] = absolute_width; // use the absolute width if the column has absolute width assigned! } else if (!c.AutoSize) { biggest[colspan - 1] = Math.Max(biggest[colspan - 1], c.ExplicitBounds.Width + c.Margin.Horizontal + Padding.Horizontal); } else { biggest[colspan - 1] = Math.Max(biggest[colspan - 1], c.PreferredSize.Width + c.Margin.Horizontal + Padding.Horizontal); } } else if (absolute_width > -1) { biggest[0] = absolute_width; } } for (int s = 0; s < max_colspan; ++s) { column_span_widths[i, s] = biggest[s]; } } for (int i = 0; i < actual_cols; ++i) { for (int s = 1; s < max_colspan; ++s) { if (column_span_widths[i, s] > 0) { AdjustWidthsForSpans(column_span_widths, i, s); } } column_widths[i] = column_span_widths[i, 0]; } // Because percentage based rows divy up the remaining space, // we have to make the owner big enough so that all the rows // get bigger, even if we only need one to be bigger. int non_percent_total_width = 0; int percent_total_width = 0; for (int i = 0; i < actual_cols; i++) { if (i < ColumnStyles.Count && ColumnStyles[i].SizeType == SizeType.Percent) { percent_total_width = Math.Max(percent_total_width, (int)(column_widths[i] / ((ColumnStyles[i].Width) / total_column_percentage))); } else { non_percent_total_width += column_widths[i]; } } int border_width = GetCellBorderWidth(CellBorderStyle); int needed_width = non_percent_total_width + percent_total_width + (border_width * (actual_cols + 1)); // Figure out how tall the owner needs to be int[] row_heights = new int[actual_rows]; int[,] row_span_heights = new int[actual_rows, max_rowspan]; biggest = new int[max_rowspan]; float total_row_percentage = 0f; // Figure out how tall each row wants to be for (int j = 0; j < actual_rows; j++) { if (j < RowStyles.Count && RowStyles[j].SizeType == SizeType.Percent) { total_row_percentage += RowStyles[j].Height; } int absolute_height = -1; if (j < RowStyles.Count && RowStyles[j].SizeType == SizeType.Absolute) { absolute_height = (int)RowStyles[j].Height; // use the absolute height if it's absolute! } for (int s = 0; s < max_rowspan; ++s) { biggest[s] = 0; } for (int i = 0; i < actual_cols; i++) { Control c = actual_positions[i, j]; if (c != null) { int rowspan = GetRowSpan(c); if (rowspan == 0) { continue; } if (rowspan == 1 && absolute_height > -1) { biggest[0] = absolute_height; // use the absolute height if the row has absolute height assigned! } else if (!c.AutoSize) { biggest[rowspan - 1] = Math.Max(biggest[rowspan - 1], c.ExplicitBounds.Height + c.Margin.Vertical + Padding.Vertical); } else { biggest[rowspan - 1] = Math.Max(biggest[rowspan - 1], c.PreferredSize.Height + c.Margin.Vertical + Padding.Vertical); } } else if (absolute_height > -1) { biggest[0] = absolute_height; } } for (int s = 0; s < max_rowspan; ++s) { row_span_heights[j, s] = biggest[s]; } } for (int j = 0; j < actual_rows; ++j) { for (int s = 1; s < max_rowspan; ++s) { if (row_span_heights[j, s] > 0) { AdjustHeightsForSpans(row_span_heights, j, s); } } row_heights[j] = row_span_heights[j, 0]; } // Because percentage based rows divy up the remaining space, // we have to make the owner big enough so that all the rows // get bigger, even if we only need one to be bigger. int non_percent_total_height = 0; int percent_total_height = 0; for (int j = 0; j < actual_rows; j++) { if (j < RowStyles.Count && RowStyles[j].SizeType == SizeType.Percent) { percent_total_height = Math.Max(percent_total_height, (int)(row_heights[j] / ((RowStyles[j].Height) / total_row_percentage))); } else { non_percent_total_height += row_heights[j]; } } int needed_height = non_percent_total_height + percent_total_height + (border_width * (actual_rows + 1)); return(new Size(needed_width, needed_height)); }
// ignore border width, dummy controls, spans private static void LayoutControls(Control parent, Control[,] grid, IList <int> columnWidths, IList <int> rowHeights) { int columns = grid.GetLength(0); int rows = grid.GetLength(1); var position = Point.Empty; for (int row = 0; row < rows; row++) { for (int col = 0; col < columns; col++) { Control child = grid[col, row]; if (child != null) { Size preferredSize = child.AutoSize ? child.PreferredSize : child.Size; int x, y, width, height; // Ignore 0 sizes or the dimensions of some children could get corrupted if (columnWidths[col] == 0 || rowHeights[row] == 0) { continue; } // Figure out the width of the control int columnWidth = columnWidths[col]; if (child.Dock == DockStyle.Fill || child.Dock == DockStyle.Top || child.Dock == DockStyle.Bottom || (child.Anchor & AnchorStyles.Horizontal) == AnchorStyles.Horizontal) { width = columnWidth - child.Margin.Horizontal; } else { width = Math.Min(preferredSize.Width, columnWidth - child.Margin.Horizontal); } // Figure out the height of the control int columnHeight = rowHeights[row]; if (child.Dock == DockStyle.Fill || child.Dock == DockStyle.Left || child.Dock == DockStyle.Right || (child.Anchor & AnchorStyles.Vertical) == AnchorStyles.Vertical) { height = columnHeight - child.Margin.Vertical; } else { height = Math.Min(preferredSize.Height, columnHeight - child.Margin.Vertical); } // Figure out the left location of the control int right = position.X + columnWidth; if (child.Dock == DockStyle.Left || child.Dock == DockStyle.Fill || (child.Anchor & AnchorStyles.Left) == AnchorStyles.Left) { x = position.X + child.Margin.Left; } else if (child.Dock == DockStyle.Right || (child.Anchor & AnchorStyles.Right) == AnchorStyles.Right) { x = right - width - child.Margin.Right; } else { x = (position.X + ((columnWidth - child.Margin.Horizontal) / 2)) + child.Margin.Left - (width / 2); } // Figure out the top location of the control int bottom = position.Y + columnHeight; if (child.Dock == DockStyle.Top || child.Dock == DockStyle.Fill || (child.Anchor & AnchorStyles.Top) == AnchorStyles.Top) { y = position.Y + child.Margin.Top; } else if (child.Dock == DockStyle.Bottom || (child.Anchor & AnchorStyles.Bottom) == AnchorStyles.Bottom) { y = bottom - height - child.Margin.Bottom; } else { y = (position.Y + ((columnHeight - child.Margin.Vertical) / 2)) + child.Margin.Top - (height / 2); } child.SetBounds(x, y, width, height, BoundsSpecified.None); } position = Point.Add(position, columnWidths[col], 0); } position = Point.Add(position, (-1 * position.X), rowHeights[row]); } }
internal override Size GetPreferredSizeCore(Size proposedSize) { // If the tablelayoutowner is autosize, we have to make sure it is big enough // to hold every non-autosize control actual_positions = (LayoutEngine as TableLayout).CalculateControlPositions(this, Math.Max(ColumnCount, 1), Math.Max(RowCount, 1)); // Use actual row/column counts, not user set ones int actual_cols = actual_positions.GetLength(0); int actual_rows = actual_positions.GetLength(1); // Figure out how wide the owner needs to be int[] column_widths = new int[actual_cols]; float total_column_percentage = 0f; // Figure out how tall each column wants to be for (int i = 0; i < actual_cols; i++) { if (i < ColumnStyles.Count && ColumnStyles[i].SizeType == SizeType.Percent) { total_column_percentage += ColumnStyles[i].Width; } int biggest = 0; for (int j = 0; j < actual_rows; j++) { Control c = actual_positions[i, j]; if (c != null) { if (!c.AutoSize) { biggest = Math.Max(biggest, c.ExplicitBounds.Width + c.Margin.Horizontal + Padding.Horizontal); } else { biggest = Math.Max(biggest, c.PreferredSize.Width + c.Margin.Horizontal + Padding.Horizontal); } } } column_widths[i] = biggest; } // Because percentage based rows divy up the remaining space, // we have to make the owner big enough so that all the rows // get bigger, even if we only need one to be bigger. int non_percent_total_width = 0; int percent_total_width = 0; for (int i = 0; i < actual_cols; i++) { if (i < ColumnStyles.Count && ColumnStyles[i].SizeType == SizeType.Percent) { percent_total_width = Math.Max(percent_total_width, (int)(column_widths[i] / ((ColumnStyles[i].Width) / total_column_percentage))); } else { non_percent_total_width += column_widths[i]; } } // Figure out how tall the owner needs to be int[] row_heights = new int[actual_rows]; float total_row_percentage = 0f; // Figure out how tall each row wants to be for (int j = 0; j < actual_rows; j++) { if (j < RowStyles.Count && RowStyles[j].SizeType == SizeType.Percent) { total_row_percentage += RowStyles[j].Height; } int biggest = 0; for (int i = 0; i < actual_cols; i++) { Control c = actual_positions[i, j]; if (c != null) { if (!c.AutoSize) { biggest = Math.Max(biggest, c.ExplicitBounds.Height + c.Margin.Vertical + Padding.Vertical); } else { biggest = Math.Max(biggest, c.PreferredSize.Height + c.Margin.Vertical + Padding.Vertical); } } } row_heights[j] = biggest; } // Because percentage based rows divy up the remaining space, // we have to make the owner big enough so that all the rows // get bigger, even if we only need one to be bigger. int non_percent_total_height = 0; int percent_total_height = 0; for (int j = 0; j < actual_rows; j++) { if (j < RowStyles.Count && RowStyles[j].SizeType == SizeType.Percent) { percent_total_height = Math.Max(percent_total_height, (int)(row_heights[j] / ((RowStyles[j].Height) / total_row_percentage))); } else { non_percent_total_height += row_heights[j]; } } int border_width = GetCellBorderWidth(CellBorderStyle); return(new Size(non_percent_total_width + percent_total_width + (border_width * (actual_cols + 1)), non_percent_total_height + percent_total_height + (border_width * (actual_rows + 1)))); }
private static void CalculateColumnWidths(TableLayoutSettings settings, Control[,] actual_positions, int max_colspan, TableLayoutColumnStyleCollection col_styles, bool auto_size, int[] column_widths, bool minimum_sizes) { Size proposed_size = minimum_sizes ? new Size(1, 0) : Size.Empty; int rows = actual_positions.GetLength(1); float max_percent_size = 0; // First assign all the Absolute sized columns int index = 0; foreach (ColumnStyle cs in col_styles) { if (index >= column_widths.Length) { break; } if (cs.SizeType == SizeType.Absolute) { column_widths[index] = (int)cs.Width; } index++; } while (index < column_widths.Length) { column_widths[index] = 0; index++; } // Next, assign all the AutoSize columns to the width of their widest // control. If the table-layout is auto-sized, then make sure that // no column with Percent styling clips its contents. // (per http://msdn.microsoft.com/en-us/library/ms171690.aspx) for (int colspan = 0; colspan < max_colspan; ++colspan) { for (index = colspan; index < column_widths.Length - colspan; ++index) { ColumnStyle cs = index < col_styles.Count ? col_styles[index] : default_column_style; if (cs.SizeType == SizeType.AutoSize || (auto_size && cs.SizeType == SizeType.Percent)) { int max_width = column_widths[index]; // Find the widest control in the column for (int i = 0; i < rows; i++) { Control c = actual_positions[index - colspan, i]; if (c != null && c != dummy_control && c.VisibleInternal) { // Skip any controls not being sized in this pass. if (settings.GetColumnSpan(c) != colspan + 1) { continue; } // Calculate the maximum control width. max_width = Math.Max(max_width, GetControlSize(c, proposed_size).Width + c.Margin.Horizontal); } } if (cs.SizeType == SizeType.Percent) { max_percent_size = Math.Max(max_percent_size, max_width / cs.Width); } // Subtract the width of prior columns, if any. for (int i = Math.Max(index - colspan, 0); i < index; ++i) { max_width -= column_widths[i]; } // If necessary, increase this column's width. if (max_width > column_widths[index]) { column_widths[index] = max_width; } } } } for (index = 0; index < col_styles.Count && index < column_widths.Length; ++index) { ColumnStyle cs = col_styles[index]; if (cs.SizeType == SizeType.Percent) { column_widths[index] = Math.Max(column_widths[index], (int)Math.Ceiling(max_percent_size * cs.Width)); } } }