Привязка IList <IMyInterfaceType>не отображает членов интерфейсов, которые наследует IMyInterface - PullRequest
14 голосов
/ 12 февраля 2009

Я связываю IList с GridView. IMyInterface выглядит как

public interface IMyInterface: IHasTotalHours, IHasLines
{
    DateTime GoalStartDate { get; set; }
    DateTime GoalEndDate { get; set; }
}

Я привязываю экземпляр к Grid следующим образом:

IList<IMyInterface> instance= GetMyData();

myGrid.DataSource = instance;
myGrid.DataBind();

При привязке этого к сетке единственными элементами, которые отображаются в сетке, являются прямые члены IMyInterface: GoalStartDate и GoalEndDate.

Почему это? Как получить сетку для отображения элементов других интерфейсов, которые она наследует?

Обновление Унаследованные интерфейсы определяют простые свойства данных, такие как

public interface IHasTotalHours
{
    string Description { get; set; }
    int Hours{ get; set; }
}
public interface IHasLines
{
    double TotalLines { get; set; }
    double LinesPerHour { get; set; }
}

Существует класс, который реализует IMyInterface:

public class MyClass : IMyInterface
{
    public string Description { get; set; }
    public int Hours { get; set; }
    public double TotalLines { get; set; }
    public double LinesPerHour { get; set; }
    public DateTime GoalStartDate { get; set; }
    public DateTime GoalEndDate { get; set; }

}

Они приводятся как IMyInterface и возвращаются в списке, который я привязываю к GridView.

Ответы [ 2 ]

7 голосов
/ 24 февраля 2009

Элементы управления с привязкой к данным используют не отражение, а TypeDescriptor для получения свойств из источника данных. В методе TypeDescriptor.GetProperties вы можете прочитать следующее:

Свойства компонента могут отличаются от свойств класса, потому что сайт может добавлять или удалять свойства, если компонент размещен.

Очевидно, реализация по умолчанию будет возвращать только прямые свойства интерфейса, а не унаследованные.

К счастью, этот механизм является расширяемым, и вы можете написать TypeConverter класс с реализацией информации о пользовательских свойствах. Пожалуйста, обратитесь к замечаниям в документации TypeConverter для реализации логики свойств.

Реализация GetProperties вашего пользовательского класса TypeConverter может вызывать TypeDescriptor.GetProperties (Type) для вашего интерфейса и всех его унаследованных интерфейсов. Но, возможно, вы могли бы даже написать универсальный TypeConverter, который бы нашел все унаследованные свойства, используя отражение.

Затем вы присоединяете этот пользовательский TypeConverter к своему интерфейсу с атрибутом TypeConverterAttribute.

И тогда, как по волшебству, источник данных найдет все свойства. ; -)

0 голосов
/ 12 февраля 2009

Это потому, что интерфейс - это контракт, и это единственный способ взаимодействия с объектом - через этот конкретный контракт. Другие интерфейсы не могут быть приняты и не могут быть использованы, пока не будет произведено приведение.

Поэтому, когда вы связываете список T с чем-то, сетка данных не знает об этих других интерфейсах. И сетка данных не собирается использовать отражение, чтобы выяснить, какие другие классы или интерфейсы могут быть унаследованы. Единственные свойства объекта, которые будут доступны для сетки данных, - это свойства, предоставляемые интерфейсом T.

Вам необходимо связать List, если вы хотите, чтобы сетка данных имела доступ ко всем свойствам.

...