如何将最近的未来日期设置为今天的默认下拉列表值?

时间:2014-08-05 16:25:28

标签: sql asp.net vb.net

我们使用数据库中的几个事件日期动态填充我们的下拉列表。

目前,所有低于今天的日期都已停用,我们的用户无法查看。

下一个可用日期大于今天的日期将成为默认的下拉列表值,所有未来日期都可以在下拉列表中显示。

例如,如果我们的日期基准上有以下日期:

2013年2月12日

12/20/203

2014年5月21日

2014年8月8日

2014年10月22日

由于其中三个日期( 2/12 / 2013,12 / 20 / 203,5 / 21/2014 )低于今天的日期,因此这些日期已被禁用,可见。

最接近的可用日期大于今天的日期是8/8/2014,这将成为默认的下拉列表值。

最后,所有未来的日期,例如10/22/2014,也可以在下拉列表中找到。

以下是实现此目的的代码剪辑:

//标记

  <asp:DropDownList id="txtEventDate" runat="server">
    </asp:DropDownList>

//动态填充下拉列表的代码

 Dim cmd As New SqlCommand("Select convert(datetime, dates, 103) dates, CONVERT(VARCHAR(12), dates, 107) as datelist from events", New SqlConnection(ConfigurationManager.ConnectionStrings("Events").ConnectionString))
          cmd.Connection.Open()

          Dim ddlValues As SqlDataReader
          ddlValues = cmd.ExecuteReader()

          txtEventDate.DataSource = ddlValues
          txtEventDate.DataValueField = "dates"
          txtEventDate.DataTextField = "datelist"
          txtEventDate.DataBind()

          cmd.Connection.Close()
              cmd.Connection.Dispose()

//仅显示未来日期和下一个可用未来日期的代码作为默认下拉列表值

For Each items As ListItem In txtEventDate.Items
    If (DateTime.Parse(items.Value).CompareTo(DateTime.Today)) < 0 Then
        items.Enabled = False
    End If
Next

我们的用户希望更改流程,以便他们可以返回更早的日期,并在需要时进行一些更改。

有任何想法如何解决这个问题?

Public Sub PopulateDates()
    Dim cmd As New SqlCommand("Select convert(datetime, dates, 103) dates, CONVERT(VARCHAR(12), dates, 107) as datelist from events", New SqlConnection(ConfigurationManager.ConnectionStrings("events").ConnectionString))
    cmd.Connection.Open()


    Dim lstDates As New List(Of DateTime)()

    Using rdr As SqlDataReader = cmd.ExecuteReader()
        If rdr.Read() Then
            lstDates.Add(DirectCast(rdr("dates"), DateTime))
        End If
    End Using

    lstDates = lstDates.OrderBy(Function(x) x.[Date]).ToList()
    Dim nearestDate = lstDates.OrderBy(Function(t) Math.Abs((t - DateTime.Now).Ticks)).First()
    txtEventDate.DataSource = lstDates
    txtEventDate.DataBind()
    txtEventDate.SelectedIndex = txtEventDate.Items.IndexOf(txtEventDate.Items.FindByValue(nearestDate.ToString()))

    cmd.Connection.Close()
    cmd.Connection.Dispose()
End Sub

2 个答案:

答案 0 :(得分:3)

根据您的评论,您似乎想让用户更改旧日期。因此,请删除禁用旧日期的For Each

首先,您需要找到与当前日期相同或更接近的最近日期,如下所示

Dim nearestDate = ddlValues.OrderBy(Function(t) Math.Abs((t.dates - DateTime.Now).Ticks)).First()

然后,在执行数据绑定后,使用FindByValueFindByText

保持选择最近的默认日期
txtEventDate.SelectedIndex = txtEventDate.Items.IndexOf(txtEventDate.Items.FindByValue(nearestDate.ToString()))

旁注: 总是尝试使用using语句作为SqlConnectionSqlCommad等数据库连接对象,以便资源这些对象使用后会在使用后释放。

更新1:根据您在评论中报告的内容,我对日期格式进行了一些更改(它不是您初始问题的一部分)等等,这里是{的完整代码{1}}。另外,请确保您不必运行之前必须设置最近日期的PopulateDates(),因为它可能会设置错误的值。如果您得到错误的值,那么最好放置断点并查看哪个对象返回意外数据。

foreach

以下是指向 DEMO 的链接(不幸的是它在C#中)我设置为显示它如何返回正确的数据。

更新2:这是您完整的工作版本(希望它能正常运行)。我在本地尝试从数据库加载数据并通过Public Sub PopulateDates() Dim cmd As New SqlCommand("Select dates from events", New SqlConnection(ConfigurationManager.ConnectionStrings("events").ConnectionString)) cmd.Connection.Open() Dim lstDates As New List(Of DateTime)() Using rdr As SqlDataReader = cmd.ExecuteReader() If rdr.Read() Then lstDates.Add(DirectCast(rdr("dates"), DateTime)) End If End Using Dim stDates As List(Of [String]) = lstDates.OrderBy(Function(o) o.[Date]).[Select](Function(x) x.[Date].ToString("MMM dd, yyyy")).ToList() Dim nearestDate = lstDates.OrderBy(Function(t) Math.Abs((t - DateTime.Now).Ticks)).First() // Dim nearestDate = lstDates.First(Function(x) x >= DateTime.Now.[Date]) // this does the trick too txtEventDate.DataSource = stDates txtEventDate.DataBind() txtEventDate.SelectedIndex = txtEventDate.Items.IndexOf(txtEventDate.Items.FindByValue(nearestDate.ToString("MMM dd, yyyy"))) cmd.Connection.Close() cmd.Connection.Dispose() End Sub 检索,一切都按照你想要的方式工作。

您在评论中报告说,从DataReader访问时只返回了一个项目,因为您的原始代码DataReader将在第一条记录之后退出,但我们需要使用{{ 1}}迭代完整列表。

关于持有不同日期格式的下拉列表的If rdr.Read() Then字段和while,我已创建了Value集合来实现此目的。以下是Text的完整代码。

Dictionary

HTML标记看起来像你想要的格式。

enter image description here

答案 1 :(得分:0)

完全没有经过测试,但是会像以下那样做你想要的吗?您的项目列表需要进行排序(如果尚未排序),但这应该找到今天或更晚的第一个项目,并将其设置为下拉列表中的所选项目。

更新 - 请尝试SelectedValue

For Each items As ListItem In txtEventDate.Items
    If (DateTime.Parse(items.Value).CompareTo(DateTime.Today)) >= 0 Then
        txtEventDate.SelectedValue = items.Value
        Exit For
    End If
Next