+2008-05-29 Ivan N. Zlatev <contact@i-nz.net>
+
+ * TypeDescriptor.cs: GetAttributes must retrieve the attributes of
+ the type, the base types and the interfaces the type implements.
+ [Fix part of bug #394310]
+
2008-05-21 Atsushi Enomoto <atsushi@ximian.com>
* INotifyPropertyChanging.cs, PropertyChangingEventArgs.cs,
return _attributes;
bool cache = true;
- object[] ats = _infoType.GetCustomAttributes (true);
- Hashtable t = new Hashtable ();
+ ArrayList attributesList = new ArrayList ();
+
+ // 1) Attributes of the type
+ foreach (Attribute attribute in _infoType.GetCustomAttributes (false))
+ attributesList.Add (attribute);
+
+ // 2) Attributes of the type's implemented interfaces and their interfaces as well
+ foreach (Type inface in _infoType.GetInterfaces ())
+ foreach (Attribute attribute in TypeDescriptor.GetAttributes (inface))
+ attributesList.Add (attribute);
+
+ // 3) Attributes of the base types
+ Type baseType = _infoType.BaseType;
+ while (baseType != null && baseType != typeof (object)) {
+ foreach (Attribute attribute in baseType.GetCustomAttributes (false))
+ attributesList.Add (attribute);
+ baseType = baseType.BaseType;
+ }
+
+ // Filter out duplicate attributes, so that the type and its interfaces
+ // have higher precedence than the base types.
+ Hashtable attributesTable = new Hashtable ();
+ for (int i = attributesList.Count - 1; i >= 0; i--) {
+ Attribute attribute = (Attribute)attributesList[i];
+ attributesTable[attribute.TypeId] = attribute;
+ }
- for (int i = ats.Length -1; i >= 0; i--)
- t [((Attribute) ats[i]).TypeId] = ats[i];
-
if (comp != null && comp.Site != null)
{
ITypeDescriptorFilterService filter = (ITypeDescriptorFilterService) comp.Site.GetService (typeof(ITypeDescriptorFilterService));
if (filter != null)
- cache = filter.FilterAttributes (comp, t);
+ cache = filter.FilterAttributes (comp, attributesTable);
}
-
- ArrayList atts = new ArrayList ();
- atts.AddRange (t.Values);
- AttributeCollection attCol = new AttributeCollection (atts);
+
+ Attribute[] attributes = new Attribute[attributesTable.Values.Count];
+ attributesTable.Values.CopyTo (attributes, 0);
+ AttributeCollection attCol = new AttributeCollection (attributes);
if (cache)
_attributes = attCol;
return attCol;
+2008-05-29 Ivan N. Zlatev <contact@i-nz.net>
+
+ * TypeDescriptorTests.cs: Add test that verifies that GetAttributes
+ retrieves the attributes of the type, the base types and the
+ interfaces the type implements.
+
2008-05-05 Ivan N. Zlatev <contact@i-nz.net>
* TypeDescriptorTests.cs: Add test for handling write-only properties.
set { prop = value; }
}
+ [Browsable (false)]
public string YetAnotherProperty
{
get { return null; }
}
}
+ [Browsable (false)]
public interface ITestInterface
{
void TestFunction ();
}
-
+
+ [Serializable]
public class TestClass
{
public TestClass()
void TestFunction ()
{}
}
+
+ [DescriptionAttribute ("bla")]
+ public class TestDerivedClass : TestClass, ITestInterface
+ {
+ public void TestFunction ()
+ {}
+ }
public struct TestStruct
{
}
}
Assert.IsTrue (found, "#E4");
+
+ // Shows that attributes are retrieved from the current type, the base types
+ // and the implemented by the type interfaces.
+ Assert.AreEqual (3, TypeDescriptor.GetAttributes (typeof (TestDerivedClass)).Count, "#F1");
}
[Test]
yetAnotherPropsFound++;
}
- Assert.AreEqual (1, anotherPropsFound, "#G2");
-
// GetProperties does not return the base type property in the case
// where both the "new" keyword is used and also the Property type is different
// (Type.GetProperties does return both properties)
//
- Assert.AreEqual (1, yetAnotherPropsFound, "#G3");
+ Assert.AreEqual (1, anotherPropsFound, "#G2");
+ Assert.IsNotNull (derivedCol["AnotherProperty"].Attributes[typeof (DescriptionAttribute)], "#G3");
+ Assert.AreEqual (1, yetAnotherPropsFound, "#G4");
+
+ // Verify that we return the derived "new" property when
+ // filters are applied that match the parent property
+ //
+ PropertyDescriptorCollection filteredCol = TypeDescriptor.GetProperties (typeof(MyDerivedComponent),
+ new Attribute[] { BrowsableAttribute.Yes });
+ Assert.IsNotNull (filteredCol["YetAnotherProperty"], "#G5");
// GetProperties does not return write-only properties (ones without a getter)
//