智能标签(又名ActionList)在visual studio中崩溃

时间:2010-06-30 22:02:16

标签: c# visual-studio-2008 visual-studio-2010 crash-reports smart-tags

将VS2010(或VS2008)中的智能标签添加到我的控件中会导致VS崩溃。

以下设计器用于操作列表:

internal class DataEditorDesigner : ComponentDesigner {
[...]
    public override DesignerActionListCollection ActionLists {
        get {
            var lists = new DesignerActionListCollection();
            lists.AddRange(base.ActionLists);
            lists.Add(new DataEditorActionList(Component));
            return lists;
        }
    }
}

internal class DataEditorActionList : DesignerActionList {
    public DataEditorActionList(IComponent component) : base(component) {}
    public override DesignerActionItemCollection GetSortedActionItems() {
        var items = new DesignerActionItemCollection();
        items.Add(new DesignerActionPropertyItem("DataSource", "Data Source:", "Data"));
        items.Add(new DesignerActionMethodItem(this, "AddControl", "Add column..."));
        return items;
    }
    private void AddControl() {
        System.Windows.Forms.MessageBox.Show("dpa");
    }
}

DataSource属性声明为:

    [AttributeProvider(typeof (IListSource))]
    [DefaultValue(null)]
    public object DataSource {
[...]

有关如何调试它的任何想法?

1 个答案:

答案 0 :(得分:0)

我找到了解决方案。有必要向DesignerActionList类添加包装器属性,这是它们的读取位置,而不是实际组件。此外,有必要编写这样的代码:

internal static PropertyDescriptor GetPropertyDescriptor(IComponent component, string propertyName) {
    return TypeDescriptor.GetProperties(component)[propertyName];
}

internal static IDesignerHost GetDesignerHost(IComponent component) {
    return (IDesignerHost) component.Site.GetService(typeof (IDesignerHost));
}

internal static IComponentChangeService GetChangeService(IComponent component) {
    return (IComponentChangeService) component.Site.GetService(typeof (IComponentChangeService));
}

internal static void SetValue(IComponent component, string propertyName, object value) {
    PropertyDescriptor propertyDescriptor = GetPropertyDescriptor(component, propertyName);
    IComponentChangeService svc = GetChangeService(component);
    IDesignerHost host = GetDesignerHost(component);
    DesignerTransaction txn = host.CreateTransaction();
    try {
        svc.OnComponentChanging(component, propertyDescriptor);
        propertyDescriptor.SetValue(component, value);
        svc.OnComponentChanged(component, propertyDescriptor, null, null);
        txn.Commit();
        txn = null;
    } finally {
        if (txn != null)
            txn.Cancel();
    }
}

然后使用它:

[AttributeProvider(typeof (IListSource))]
public object DataSource {
    get { return Editor.DataSource; }
    set { DesignerUtil.SetValue(Component, "DataSource", value); }
}

以及其他属性。