Выпадающий список AppendDataBoundItems (первый элемент должен быть пустым и без дубликатов)
-
06-09-2019 - |
Вопрос
У меня есть DropDownList
внутри UpdatePanel
который заполняется при обратной передаче из SqlDataSource
.У него есть параметр, который является другим элементом управления.Иногда мне требуется несколько обратных отправлений, но что происходит, так это то, что каждый раз, когда обновляется панель обновления, элементы добавляются в DropDownList
.Таким образом , DropDownList
в конечном итоге получаются неверные или повторяющиеся данные.
У меня есть AppendDataBoundItems
свойство, установленное в true
потому что мне нужно, чтобы первый элемент был пустым.
Как я могу преодолеть эту проблему?Есть ли другой способ получить пустой первый элемент?
(Это DropDownList
находится в веб-приложении ASP.NET 2.0, а codebehind находится на C #)
Решение
Вместо того, чтобы использовать AppendDataboundItems='true'
(что вызовет проблему, о которой вы говорите), ответьте на DataBound
мероприятие для DropDownList
а затем добавьте свой "пустой" элемент в начало списка.
<asp:DropDownList runat="server" ID="MyList"
ondatabound="MyListDataBound"></asp:DropDownList>
Затем в вашем коде за:
protected void MyListDataBound(object sender, EventArgs e)
{
MyList.Items.Insert(0, new ListItem("- Select -", ""));
}
Другие советы
Здесь есть хорошие ответы, но я почувствовал необходимость включить больше информации, потому что есть несколько вариантов, которые работают, и нам нужно решить, какой из них использовать.
Во-первых, мы должны понять AppendDataBoundItems
.Если AppendDataBoundItems = "true"
, ListItems
добавляются к DropDownList
не убирая старые.В противном случае, DropDownList
очищается примерно перед следующим DataBind
. MSDN AppendDataBoundItems документ
В основном есть 2 варианта, рассмотренные в большинстве ответов:
1.Определите пустой параметр в html и добавьте элементы списка из базы данных в выпадающий список только один раз.
Обратите внимание на 3 вещи здесь:
- Пустой
ListItem
определяется в html AppendDataBoundItems="true"
DataBind
не вызывается при обратной передаче или когдаDropDownList
пункт количество равно > 1
Источник:
<asp:DropDownList ID="MyList" runat="server" AppendDataBoundItems="true" DataValueField="Id" DataTextField="Name" >
<asp:ListItem Text="- Select One -" Value="" />
</asp:DropDownList>
Код, стоящий за:
protected void Page_Load(object sender, System.EventArgs e)
{
if (MyList.Items.Count <= 1 ) {
MyList.DataSource = MyDataSource;
MyList.DataBind();
}
}
Примечание:Мне нравится логика проверки количества по сравнению с проверкой IsPostBack
.Хотя обратная передача часто является причиной дублирующейся привязки к данным, это можно вызвать другими способами.Проверка количества элементов - это, по сути, просто проверка того, было ли оно уже загружено.
ИЛИ (возможность использовать IsPostBack
вместо этого)
protected void Page_Load(object sender, System.EventArgs e)
{
if (!IsPostBack) {
MyList.DataSource = MyDataSource;
MyList.DataBind();
}
}
2.Очищайте и перезагружайте выпадающий список при каждом обновлении страницы.
Обратите внимание на 3 отличия от первого варианта:
AppendDataBoundItems="false"
(если это не определено , тоfalse
является ли это значением по умолчанию)- Пустой
ListItem
это добавлено в код позади.Мы не можем определить это в html потому что сAppendDataBoundItems="false"
, это было бы вычищено. DataBind
вызывается на каждомPage_Load
Источник:
<asp:DropDownList ID="MyList" runat="server" DataValueField="Id" DataTextField="Name"
OnDataBound="MyList_DataBound" >
</asp:DropDownList>
Код, стоящий за:
protected void Page_Load(object sender, System.EventArgs e)
{
MyList.DataSource = MyDataSource;
MyList.DataBind();
}
protected void MyList_DataBound(object sender, EventArgs e)
{
MyList.Items.Insert(0, new ListItem("- Select One -", ""));
}
Вероятно, вы привязываете этот выпадающий список к стоящему за ним коду.Поэтому вам не следует делать это после повторной отправки:
// probably in Page_Load method
if (!Page.IsPostBack)
{
// do data binding here
};
Вот идея, мы можем использовать 2 события: Привязка к базе данных и Привязка к данным:
protected void MyListDataBound(object sender, EventArgs e)
{
MyList.Items.Insert(0, new ListItem("- Select -", ""));
}
protected void MyListDataBinding(object sender, EventArgs e)
{
MyList.Items.Items.Clear();
}
<asp:DropDownList ID="DropDownList1" AppendDataBoundItems="true" runat="server"
DataSourceID="SqlDataSource1" DataTextField="state" DataValueField="state">
<asp:ListItem Text="(Select a State)" Value="" />
</asp:DropDownList>
<asp:SqlDataSource ID="SqlDataSource1" runat="server"
ConnectionString="<%$ ConnectionStrings:pubsConnectionString %>"
SelectCommand="SELECT DISTINCT [state] FROM [authors]">
</asp:SqlDataSource>
Вот такая идея.
В выпадающем списке есть свойство, которое называется AutoPostBack
установите для него значение true, а затем в коде позади вас поместите весь метод привязки внутрь if(!Page.IsPostBack)
.У меня это сработало.
с уважением.
Просто добавьте EnableViewState="ложь" к выпадающему тегу
<asp:DropDownList runat="server" ID="DropDownList1" DataSourceID="SqlDataSource"
DataTextField="Name" DataValueField="ID" EnableViewState="false"
AppendDataBoundItems="true">
<asp:ListItem Value="">Select</asp:ListItem>
</asp:DropDownList>