Wpf XAML中的VisualCollection和ContentPropertyAttribute
我想写一个自定义的框架元素来承载视觉效果。我的第一次尝试是创建一个ContainerVisual实例,并为ContainerVisual.Children编写一个包装器属性,然后将其设置为ContentProperty,这样我就可以通过XAML查看和显示。但VisualCollection只实现ICollection,而不实现IList或任何支持的接口,VisualCollection是selead,因此我无法单独实现IListWpf XAML中的VisualCollection和ContentPropertyAttribute,wpf,xaml,Wpf,Xaml,我想写一个自定义的框架元素来承载视觉效果。我的第一次尝试是创建一个ContainerVisual实例,并为ContainerVisual.Children编写一个包装器属性,然后将其设置为ContentProperty,这样我就可以通过XAML查看和显示。但VisualCollection只实现ICollection,而不实现IList或任何支持的接口,VisualCollection是selead,因此我无法单独实现IList 我怎样才能承载视觉效果并让它们使用XAML以声明方式添加?好的,很
我怎样才能承载视觉效果并让它们使用XAML以声明方式添加?好的,很久以前,但这是我以前找到的解决方案 收藏: 注意黑客的评论
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Media;
using System.Collections.ObjectModel;
using WPF.Controls.Primitives;
namespace WPF.Controls.Core
{
public class PrimitiveCollection : ObservableCollection<Primitive>
{
protected PrimitiveContainerVisual _owner;
public PrimitiveCollection(PrimitiveContainerVisual owner)
: base()
{
if (owner == null)
throw new ArgumentNullException("owner");
_owner = owner;
}
protected override void ClearItems()
{
foreach (var item in this)
{
item.IsDirtyChanged -= new IsDirtyChangedHandler(item_IsDirtyChanged);
_owner.InternalRemoveVisualChild(item);
}
base.ClearItems();
}
protected override void InsertItem(int index, Primitive item)
{
if (item != null && item.Parent != null)
throw new ArgumentNullException("Visual has parent");
item.IsDirtyChanged += new IsDirtyChangedHandler(item_IsDirtyChanged);
_owner.InternalAddVisualChild(item);
base.InsertItem(index, item);
}
protected override void RemoveItem(int index)
{
Primitive item = this[index];
item.IsDirtyChanged -= new IsDirtyChangedHandler(item_IsDirtyChanged);
_owner.InternalRemoveVisualChild(item);
base.RemoveItem(index);
}
protected override void OnPropertyChanged(System.ComponentModel.PropertyChangedEventArgs e)
{
base.OnPropertyChanged(e);
}
void item_IsDirtyChanged(object sender, PrimitiveChangedEventArgs e)
{
if(e.IsDirty)
_owner.RequestRedraw();
}
}
}
你能解释一下吗?请问一个具体的问题。这个问题很老了。最好创建一个新的,并在评论中发布链接。然后我会看看我是否能帮上忙:)
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Media;
using WPF.Controls.Primitives;
using System.Windows;
using System.Reflection;
namespace WPF.Controls.Core
{
public class PrimitiveContainerVisual : Visual
{
private PrimitiveCollection _primitives;
private PropertyInfo _contentBoundsPropInfo;
private PropertyInfo _descendantBoundsPropInfo;
public PrimitiveCollection Children
{
get { return _primitives; }
set { _primitives = value; }
}
public Rect ContentBounds
{
// HACK access internal property of Visual
get { return (Rect)_contentBoundsPropInfo.GetValue(this, null); }
}
public Rect DescendantBounds
{
// HACK access internal property of Visual
get { return (Rect)_descendantBoundsPropInfo.GetValue(this, null); }
}
public PrimitiveContainerVisual()
{
_primitives = new PrimitiveCollection(this);
Type thisType = this.GetType();
BindingFlags flags = BindingFlags.NonPublic | BindingFlags.Instance;
_contentBoundsPropInfo = thisType.GetProperty("VisualContentBounds", flags);
_descendantBoundsPropInfo = thisType.GetProperty("VisualDescendantBounds", flags);
}
internal void InternalAddVisualChild(Primitive prim)
{
this.AddVisualChild(prim);
}
internal void InternalRemoveVisualChild(Primitive prim)
{
this.RemoveVisualChild(prim);
}
public bool RequestRedraw()
{
UIElement uiParent = VisualParent as UIElement;
if (uiParent != null)
{
uiParent.InvalidateVisual();
return true;
}
else
return false;
}
}
}