Мне удалось переопределить Boundfield для отображения раскрывающегося списка, если я поместил его в Gridview.
protected override void InitializeDataCell(DataControlFieldCell cell, DataControlRowState rowState)
{
Control child = null;
Control cellControl = null;
if ((((rowState & DataControlRowState.Edit) != DataControlRowState.Normal) && !this.ReadOnly)
|| ((rowState & DataControlRowState.Insert) != DataControlRowState.Normal))
{
// If data cell is in edit mode, create DropDownList editor for this cell
// and set data properties.
DropDownList box = new DropDownList();
box.Items.Add(DefaultValueText);
box.DataSource = this.GetDataSource();
box.DataMember = this.BusinessObjectName;
box.DataTextField = this.DataTextField;
box.DataValueField = this.DataValueField;
box.AppendDataBoundItems = true;
box.ToolTip = this.HeaderText;
cell.Controls.Add(box);
box.DataBind();
// if in edit mode, prepare dropdown for binding
if ((this.DataField.Length != 0) && ((rowState & DataControlRowState.Edit) != DataControlRowState.Normal))
{
cellControl = box;
}
}
else if (this.DataField.Length != 0) // if in read only mode, prepare cell for binding
{
cellControl = cell;
}
if ((cellControl != null) && base.Visible)
{
cellControl.DataBinding += new EventHandler(this.OnDataBindField);
}
}
protected override void OnDataBindField(object sender, EventArgs e)
{
Control control = (Control)sender;
Control namingContainer = control.NamingContainer;
object dataValue = this.GetValue(namingContainer);
bool encode = (this.SupportsHtmlEncode && this.HtmlEncode) && (control is TableCell);
string str = this.FormatDataValue(dataValue, encode);
if (control is TableCell)
{
if (str.Length == 0)
{
str = " ";
}
((TableCell)control).Text = str;
}
else
{
//If data cell is in edit mode, set selected value of DropDownList
if (dataValue != null)
{
DropDownList dropDownList = (DropDownList) control;
ListItem itm = dropDownList.Items.FindByText(dataValue.ToString());
if (itm != null)
{
dropDownList.Text = itm.Value;
}
else
((DropDownList)control).Text = DefaultValueText;
}
}
}
Последняя функция, которую я добавил, - это значение по умолчанию / дополнительный элемент, отображаемый, если ничего не было выбрано, например, выберите, например. Я могу установить это с помощью свойства DefaultValueText в событии OnDataBind.
Вот проблема, с которой я столкнулся:
В InitializeDataCell, если я установил
box.AppendDataBoundItems = true;
и позвони
box.DataBind();
В раскрывающемся списке есть все элементы плюс дополнительный элемент по умолчанию. Он также прекрасно работает в событии OnDataBind, где теперь я могу выбрать значение по умолчанию, если элемент привязки данных не содержит значения.
Но когда раскрывающийся список отображается в представлении сетки, он содержит значение по умолчанию плюс все из источника данных ДВАЖДЫ, потому что я установил AppendDataBoundItems = true, что приводит к тому, что раскрывающийся список НЕ очищает его элементы при добавлении элементов gridview должен вызывать привязку данных дважды, но только один раз регистрируется в методе события OnDataBind. Я вижу там только один вызов, и в этот момент все в порядке, раскрывающийся список содержит элемент по умолчанию плюс один из каждого элемента из источника данных.
Любые предложения, где и как я могу обрабатывать привязку данных, чтобы иметь полный контроль над привязкой данных?