GetAdornerLayer returns 对于 WPF 用户控件始终为 null

GetAdornerLayer returns null always for WPF usercontrol

我对

总是空的
_AdornerLayer = AdornerLayer.GetAdornerLayer(InteractiveCanvas);

可能是什么原因。我想得到 AdornerLayer 并且需要在同一个

上添加一个 _AdornerCursor

我看到了一些可能的答案,但它对我不起作用

根据 documentation,您的 InteractiveCanvas 上方的 VisualTree 中没有任何 AdornerLayer。这可能有很多原因。

例如,可能是您的 InteractiveCanvas 尚未在 VisualTree 中。 (至少不是像 WindowPopup 这样可见的。)如果你有这样的东西就是这种情况:

var adornerLayer = AdornerLayer.GetAdornerLayer(new Button());
// adornerLayer will be null every time.

AdornerLayer.GetAdornerLayer(visual)背后的逻辑很简单。它只是使用 VisualTreeHelper.GetParent(visual) 在 VisualTree 中向上移动。如果该父级是 AdornerDecoratorScrollContentPresenter 那么它 returns 该父级的 属性 .AdornerLayer (或多或少保证不为空) .如果它到达 VisualTree 的根目录并且没有找到这两种类型的视觉对象中的任何一种,它会像您的情况一样 returns null

因此,请使用 WPF Tree Visualizer in Visual Studio, Mole or Snoop 检查 InteractiveCanvas 的 VisualTree,并在父元素中查找任何 AdornerDecoratorScrollContentPresenter。如果您找不到其中任何一个,那么这正是您遇到问题的原因。

如果您还不能将 InteractiveCanvas 放入 VisualTree 中,也可以手动将 <AdornerDecorator> 元素放置在 XAML 上方的某个位置 InteractiveCanvas.此元素将创建一个单独的 AdornerLayer,您的代码将找到该元素。这当然可以在 C# 中完成,也可以像这样做:

var btn = new Button();
var ad = new AdornerDecorator();
ad.Child = btn;
var adornerLayer = AdornerLayer.GetAdornerLayer(btn);
// adornerLayer will now be NOT null every time.

底线:检查您 InteractiveCanvas 的 VisualTree 中的父项,您会找到答案。