从 UI 自动化中只能看到 UIElement(就像您所看到的,OnCreateAutomationPeer 从此类开始,而不是从 Visual 类开始)。
因此,如果您希望 UIAutomation 可以使用它,则需要将 UIElement(或类似 FrameworkElement 的派生对象)添加到画布。
您可以创建自己的类,如下所述:Using DrawingVisual Objects or with a custom UserControl 或使用适合您需要的现有类,但它必须以某种方式从 UIElement 派生。
一旦你有了一个好的类,你就可以使用默认的 AutomationPeer 或重写该方法并更紧密地适应。
如果要保留 Visual 对象,一种解决方案是修改包含对象(但它仍然需要从 UIElement 派生)。例如,如果我按照链接中的文章进行操作,我可以编写一个自定义的包含对象(而不是您的示例代码的画布,因此您可能需要稍作调整),如下所示:
public class MyVisualHost : UIElement
{
public MyVisualHost()
{
Children = new VisualCollection(this);
}
public VisualCollection Children { get; private set; }
public void AddChild(Visual visual)
{
Children.Add(visual);
}
protected override int VisualChildrenCount
{
get { return Children.Count; }
}
protected override Visual GetVisualChild(int index)
{
return Children[index];
}
protected override AutomationPeer OnCreateAutomationPeer()
{
return new MyVisualHostPeer(this);
}
// create a custom AutomationPeer for the container
private class MyVisualHostPeer : UIElementAutomationPeer
{
public MyVisualHostPeer(MyVisualHost owner)
: base(owner)
{
}
public new MyVisualHost Owner
{
get
{
return (MyVisualHost)base.Owner;
}
}
// a listening client (like UISpy is requesting a list of children)
protected override List<AutomationPeer> GetChildrenCore()
{
List<AutomationPeer> list = new List<AutomationPeer>();
foreach (Visual visual in Owner.Children)
{
list.Add(new MyVisualPeer(visual));
}
return list;
}
}
// create a custom AutomationPeer for the visuals
private class MyVisualPeer : AutomationPeer
{
public MyVisualPeer(Visual visual)
{
}
// here you'll need to implement the abstrat class the way you want
}
}