Привязка данных Windows Forms DisplayMember дочернее свойство пользовательского класса - PullRequest
4 голосов
/ 13 января 2009

Я пытаюсь установить для свойства DisplayMember моего ListBox в проекте форм Windows значение свойства вложенного класса в общем списке, к которому привязан.

Вот простой пример:

 public class Security
{
    public int SecurityId { get; set;}
    public SecurityInfo Info { get; set;}
}
public class SecurityInfo
{        
    public string Description { get; set;}
}
//........//
public void DoIt()
{
    List<Security> securities = new List<Security>();
    //add securities to list
    lstSecurities.DataSource = securities;
    lstSecurities.DisplayMember = "Info.Description";
}

Возможно ли это с помощью простого ListBox или мне придется создать подклассный ListBox, чтобы справиться с этим?

редактирование:

Я пытаюсь не изменять эти классы, так как они генерируются через документ WSDL.

Ответы [ 6 ]

5 голосов
/ 14 января 2009

Нет, большинство привязок winforms не поддерживают дочерние свойства, подобные этой.

Вы можете сделать это напрямую с помощью пользовательских дескрипторов типов, но это лот работы и не стоит этого.

Проверьте сгенерированный код; он должен (с любой последней версией инструментов) быть partial class; это означает, что вы можете добавить дополнительные члены в второй файл класса, чтобы не нарушать сгенерированный wsdl-код - т.е.

namespace MyWsdlNamespace {
    partial class MyClass {
        public string InfoDescription {
            get { return Info.Description; }
            // and a set if you want
        }
    }
}

Теперь вы сможете довольно легко связываться с «Инфо-описанием».

2 голосов
/ 13 января 2009

Вы можете добавить новое свойство, которое отображается в Info.Description.

Примерно так:

public string InfoDescription
{
  get { return Info.Description; }
  set { Info.Description = value; }
}

Это будет работать. Но я подумал, что твой пример тоже должен работать

1 голос
/ 19 июля 2012

Я знаю, что несколько ответов, которые могут сработать для вас, уже опубликованы, и этому вопросу уже 3 года, но я хотел добавить еще один вариант, потому что столкнулся с этой проблемой при привязке данных к объектам в Entity Framework.

Я привязывался к ListBox, но хотел отобразить текст из дочернего объекта. Все, что я сделал, это обработал событие ListBox.Format и изменил ListControlConvertEventArgs.Value. Я мог получить свой дочерний объект, потому что DisplayMember, который я выбрал для ListBox, является самим родительским объектом, и к нему можно было получить доступ в событии с помощью ListControlConvertEventArgs.ListItem.

Например, ListBox связан с источником привязки со списком объектов objA. У objA есть свойство для дочернего объекта, objB. DisplayMember для ListBox (установлен во время разработки) является objB. Но, поскольку метод ToString() не возвращает того, что я хочу для objB, я обрабатываю событие Format в ListBox и устанавливаю e.Valuee, являющимся ListControlConvertEventArgs) для объекта, который я ищу :

CType(e.ListItem, objA).objB.DisplayText
0 голосов
/ 01 августа 2013

Да, привязка к вложенным свойствам может осуществляться через BindingSource. Комментарий Дэна от 25 января показал, как это можно сделать для «простого связывания», то есть связывания с вложенными свойствами одного объекта. Для «сложного связывания» с коллекциями это должно быть так:

public void DoIt()
{
    List<Security> securities = new List<Security>();

    var securitiesBindingSource = new BindingSource();
    securitiesBindingSource.DataSource = securities;

    //add securities to list
    lstSecurities.DataSource = securitiesBindingSource;
    lstSecurities.DisplayMember = "Info.Description";
}

Тонкое ПРЕДУПРЕЖДЕНИЕ. Объекты коллекции должны быть потомками одного типа, поэтому информация должна быть одного типа. Ковариация интерфейса не заставит его работать, когда свойство Info зависит от параметра типа, даже если оно ковариантно, так как это сделает Info ковариантным, но другого типа, например, когда Info имеет тип Information<out P>.

0 голосов
/ 09 июля 2009
0 голосов
/ 13 января 2009

Просто переопределите метод SecurityInfo ToString, чтобы вернуть Description и выполните:

lstSecurities.DisplayMember = "Info";

Если вы не можете изменить классы, лучшим вариантом будет использование ViewModel. Класс, который принимает Security и предоставляет свойства, которые вы хотите просмотреть.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...