我一直在尝试通过AppDomain边界传递UserControl,并注意到FrameworkElementAdapters.ViewToContractAdapter()
和ContractToViewAdapter()
的行为很奇怪。使用INativeHandleContract
使用FrameworkElementAdapters.ContractToViewAdapters()
转换回FrameworkElement
后,包裹的UserControl不会再改变其大小,如果其中一个孩子成长。
可以使用简单的,空的WPF窗口轻松证明此行为:
public partial class MainWindow : Window
{
private ListBox listBox;
private Button myButton;
public MainWindow()
{
InitializeComponent();
listBox = new ListBox();
Content = listBox;
myButton = new Button { Content = "Click me" };
myButton.Click += (sender, args) => myButton.Content = "Lorem ipsum dolor sit amet.";
myButton.SizeChanged += (sender, args) => Debug.WriteLine($"{myButton.DesiredSize}");
//listBox.Items.Add(myButton);
var frameworkElement = FrameworkElementAdapters.ContractToViewAdapter(FrameworkElementAdapters.ViewToContractAdapter(myButton));
listBox.Items.Add(frameworkElement);
}
}
如果单击按钮,则文本会按预期更改。但是,该按钮不会调整大小,这会给您带来截短的文本。如果您评论最后两行,然后添加按钮,则可以按预期工作。
我认为它基本上与这种情况相同,但似乎没有解决方案。有人知道如何摆脱这一点吗?
预先感谢!
正如我的评论中所述,将Grid
中的所有内容包装在其他方面,或者至少允许您接收SizeChanged
事件,然后您可以使用该事件来调整结果FrameworkElement
。
public partial class MainWindow : Window
{
private ListBox listBox;
private Button myButton;
private Grid dummyGrid;
public MainWindow()
{
InitializeComponent();
listBox = new ListBox();
Content = listBox;
myButton = new Button { Content = "Click me" };
myButton.Click += (sender, args) =>
{
myButton.Content = "Lorem ipsum dolor sit amet.";
myButton.FontSize = 24;
};
dummyGrid = new Grid();
dummyGrid.ColumnDefinitions.Add(new ColumnDefinition() { Width = GridLength.Auto });
dummyGrid.RowDefinitions.Add(new RowDefinition() { Height = GridLength.Auto });
dummyGrid.Children.Add(myButton);
var frameworkElement =
FrameworkElementAdapters.ContractToViewAdapter(
FrameworkElementAdapters.ViewToContractAdapter(dummyGrid));
listBox.Items.Add(frameworkElement);
// Automatically adjust HwndHost's size when the grid changes
dummyGrid.SizeChanged += (sender, args) =>
{
frameworkElement.Width = args.NewSize.Width;
frameworkElement.Height = args.NewSize.Height;
};
}
}
在我的情况下,我必须做一些魔术才能使事件通过AppDomain边界(例如SizeChangedEventArgs
不可行序列化等(。