其目的是
我想设置这样的大小为DataGrid (标准,从WPF),以便所有的单元格(文本)将是完全可见的。我有一个带有DockPanel的窗口,里面有DataGrid,所以当我调整窗口大小时,所有嵌套的小部件(DockPanel和DataGrid)都会相应地调整大小。
编辑示例(-1)
假设你有一个100像素宽的窗口,你有一个有一列的DataGrid,它的单元格是“敏捷的棕色狐狸...”(400像素宽)。因此,DataGrid应该调整到400像素(可能更多,因为需要填充),窗口也应该调整到400像素(也应该更多,因为需要填充)。
我没有找到任何标准的方法来做到这一点(AFAIK WPF提供了将内容裁剪到所需宽度的方法,我的问题正好相反),所以我想出了这样一个丑陋的变通办法,效果不是很好。
解决方法
中计算的差值增加窗口宽度
问题所在
我做了几次测试,在某些情况下计算的宽度太大(这是一个小问题),而在某些情况下计算的宽度太小。问题从它的核心过程开始--计算TextBox/TextBlock所需的宽度,计算出的宽度总是比它应该的宽度小1个单位(如果我将宽度设置为computed 1,文本中的1个像素总是被裁剪)。
那么,我在这里忽略了哪个因素?,或者更好的-- 是否已经有一些方法可以调整DataGrid的大小以适应其内容?
代码
计算文本所需的宽度(此处为TextBlock):
public static double TextWidth(this TextBlock widget, string text)
{
var formattedText = new FormattedText(text, // can use arbitrary text
System.Globalization.CultureInfo.CurrentCulture,
widget.FlowDirection,
widget.FontFamily.GetTypefaces().FirstOrDefault(),
widget.FontSize,
widget.Foreground);
return formattedText.Width+widget.Padding.Left+widget.Padding.Right;
}
调整窗口大小以适应DataGrid内容(ugly_factor是一个丑陋的变通方法;-)因为我不知道如何正确地修复它,所以我将其设置为1.3,这样我的窗口就“永远”不会太小:
public static void AdjustWidthToDataGrid(this Window window, DataGrid dataGrid, double ugly_factor)
{
var max_widths = dataGrid.Columns.Select(it => window.TextWidth(it.Header as string)
* ugly_factor).ToArray();
foreach (var row in Enumerable.Range(0, dataGrid.Items.Count))
foreach (var col in Enumerable.Range(0, dataGrid.Columns.Count))
{
var cell = dataGrid.GetCell(row, col);
double width = 0;
if (cell.Content is TextBlock)
width = (cell.Content as TextBlock).TextWidth();
else if (cell.Content is TextBox)
width = (cell.Content as TextBox).TextWidth();
if (cell.Content is FrameworkElement)
{
var widget = cell.Content as FrameworkElement;
width = width + widget.Margin.Left + widget.Margin.Right;
}
max_widths[col] = Math.Max(max_widths[col],
width*ugly_factor+cell.Padding.Left+cell.Padding.Right);
}
double width_diff = 0;
foreach (var col in Enumerable.Range(0, dataGrid.Columns.Count))
width_diff += Math.Max(0,max_widths[col] - dataGrid.Columns[col].ActualWidth);
if (width_diff > 0)
window.Width = window.ActualWidth+ width_diff;
}
发布于 2011-11-18 04:19:58
Marko's comment就是答案:
我对你的调整逻辑有点不知所措。首先,如果您设置了窗口的
SizeToContent="WidthAndHeight"
,那么窗口将显示为数据网格的完整大小。另一方面,如果您以某个预定义的大小显示窗口,并且希望在窗口显示后调整窗口的大小,那么此时调整到datagrid所需的大小是非常不直观的。因为调整大小会从100px跳到400px,但是如果我想只调整到250px怎么办…(通过拖动窗口的一角来调整大小)
发布于 2011-05-27 20:21:50
我刚刚从同样的问题中走出来,我必须在数据网格的列中给出选项,以便根据标题和单元格的内容来适应其宽度。我使用了以下代码:
private void FitToContent()
{
// where dg is my data grid's name...
foreach (DataGridColumn column in dg.Columns)
{
//if you want to size your column as per the cell content
column.Width = new DataGridLength(1.0, DataGridLengthUnitType.SizeToCells);
//if you want to size your column as per the column header
column.Width = new DataGridLength(1.0, DataGridLengthUnitType.SizeToHeader);
//if you want to size your column as per both header and cell content
column.Width = new DataGridLength(1.0, DataGridLengthUnitType.Auto);
}
}
此外,我还提供了一个列选项,以适合每个显示(datagrid的宽度)。为此,我使用了上面相同的代码,但做了以下细微的更改:
column.Width = new DataGridLength(1.0, DataGridLengthUnitType.Star);
对于所有列:确保将HorizontalScrollVisibility
设置为Auto
。
发布于 2011-01-02 18:56:43
如果我没理解错你的问题,你想:
这可以通过数据绑定来实现:
<DataGrid AutoGenerateColumns="False"
EnableRowVirtualization="True"
Height="111"
HorizontalAlignment="Left"
ItemsSource="{Binding}"
Margin="72,203,0,0"
Name="dataGrid"
RowDetailsVisibilityMode="VisibleWhenSelected"
VerticalAlignment="Top"
Width="{Binding Path=ActualWidth, ElementName=grid}">
<DataGrid.Columns>
<DataGridTextColumn x:Name="Column1"
Binding="{Binding Path=Something1}"
Header="Column1"
Width="Auto" />
<DataGridTextColumn x:Name="Column2"
Binding="{Binding Path=Something2}"
Header="Column2"
Width="*" />
</DataGrid.Columns>
</DataGrid>
在这里,第一列是所需的宽度,第二列是左侧的展开空间。然而,DataGrid的宽度与其周围的网格宽度相同,因此实现了所需的结果。
https://stackoverflow.com/questions/4577944
复制相似问题