在尝试设置组合框的选择时,未将对象引用设置为对象的实例

本文关键字:设置 对象引用 实例 对象 选择 组合 | 更新日期: 2023-09-27 18:02:13

我有一个text boxRadComboBox像这样:

<asp:TextBox ID="txt_inner_emp_num" runat="server" Width="60px" 
ontextchanged="txt_inner_emp_num_TextChanged" AutoPostBack="true"></asp:TextBox>
<telerik:RadComboBox ID="rad_ddl_inner_emp_name" runat="server" CausesValidation="False"
CollapseDelay="0" Culture="ar-EG" ExpandDelay="0" Filter="Contains" ItemsPerRequest="100"
MarkFirstMatch="true" Width="380px" EnableAutomaticLoadOnDemand="True" EmptyMessage="-emp name-" ShowMoreResultsBox="True" AutoPostBack="True">
</telerik:RadComboBox>

根据Telerik Documentation

为RadComboBox设置数据源。使用DataSourceID或属性来执行此操作,并设置DataTextField和datavalufield属性到数据源中的相应字段。(注意,当使用DataSource时,必须在每个数据源上设置属性回发,最方便的是在Page_Init中。)集EnableAutomaticLoadOnDemand为true


 protected void BindEmployees()
        {
            rad_ddl_inner_emp_name.Items.Clear();
            rad_ddl_inner_emp_name.DataSource = Utilities.GetAllEmployees();
            rad_ddl_inner_emp_name.DataTextField = "name";
            rad_ddl_inner_emp_name.DataValueField = "emp_num";
            rad_ddl_inner_emp_name.DataBind();
        }

 protected void Page_Init(object sender, EventArgs e)
        {
            BindEmployees();
        }

 protected void txt_inner_emp_num_TextChanged(object sender, EventArgs e)
        {
            rad_ddl_inner_emp_name.ClearSelection();
            rad_ddl_inner_emp_name.Items.FindItemByValue(txt_inner_emp_num.Text.TrimEnd()).Selected = true;//Get exception here Object reference not set to an instance of an object.
        }

我找到了rad_ddl_inner_emp_name.Items.Count = 0 !!在设置选区之前!如何解决这个问题?

在尝试设置组合框的选择时,未将对象引用设置为对象的实例

我相信你现在已经意识到,radcombox typeahead功能通过客户端交互而不是通过值搜索文本,这就是为什么你找不到值的原因。

我的建议是有一个次要对象来搜索emp_num(假设这是将始终输入到文本框中的值)。

例如,创建一个全局变量:
private Dictionary<string, string> Emp_Dict = new Dictionary<string, string>(); 

然后在绑定时填充这个字典。下面的代码假设返回的是一个ienumerable类型。如果不是,您可能需要以不同的方式填充字典。此外,为了使其工作,您必须包含(System.Linq)。

    var dataSource = Utilities.GetAllEmployees();
    Emp_Dict = dataSource.ToDictionary(ex => ex.emp_num, ex => ex.name);
    rad_ddl_inner_emp_name.Items.Clear();
    rad_ddl_inner_emp_name.DataSource = dataSource;
    rad_ddl_inner_emp_name.DataTextField = "name";
    rad_ddl_inner_emp_name.DataValueField = "emp_num";
    rad_ddl_inner_emp_name.DataBind();

现在我们需要在text changed事件中使用字典

protected void txt_inner_emp_num_TextChanged(object sender, EventArgs e)
{
    rad_ddl_inner_emp_name.ClearSelection();
    if (Emp_Dict.ContainsKey(txt_inner_emp_num.Text.TrimEnd()))
    {
        rad_ddl_inner_emp_name.SelectedValue = txt_inner_emp_num.Text.TrimEnd();
        rad_ddl_inner_emp_name.Text = Emp_Dict[txt_inner_emp_num.Text.TrimEnd()];
    }
}

现在,当文本框中的文本发生变化时,当在文本框中输入有效的emp_num时,radcombobox将更新

问题是项目只有在您请求时才会加载!

EnableAutomaticLoadOnDemand="False"

,它会工作!

更新:

如果你想使用LoadOnDemand设置这两个属性并删除EnableAutomicLoadOnDemand!

EnableLoadOnDemand="True"
EnableItemCaching="True"

更新2:启用ItemCaching并不是必须的,但也无妨!

你不需要在每次回发时绑定数据到RadComboBox,除非你禁用视图状态。

Filter, MarkFirstMatch和EnableAutomaticLoadOnDemand在您的情况下是没有用的,因为您正在自己加载所有员工。

LoadOnDemand基本上是当用户开始在ComboBox中输入时,ComboBox触发ItemsRequested事件并通过ajax检索数据。

<asp:TextBox ID="txt_inner_emp_num" runat="server" Width="60px" 
ontextchanged="txt_inner_emp_num_TextChanged" AutoPostBack="true" />
<telerik:RadComboBox ID="rad_ddl_inner_emp_name" runat="server" 
   CausesValidation="False" Culture="ar-EG">
</telerik:RadComboBox>
protected void Page_Init(object sender, EventArgs e)
{
    if (!IsPostBack)
    {
        rad_ddl_inner_emp_name.DataSource = Utilities.GetAllEmployees();
        rad_ddl_inner_emp_name.DataTextField = "name";
        rad_ddl_inner_emp_name.DataValueField = "emp_num";
        rad_ddl_inner_emp_name.DataBind();
    }
}
protected void txt_inner_emp_num_TextChanged(object sender, EventArgs e)
{
    string value = txt_inner_emp_num.Text;
    if(!string.IsNullOrWhiteSpace(value))
    {
        value = value.Trim();
        if (rad_ddl_inner_emp_name.Items
            .FindItemByValue(txt_inner_emp_num.Text.Trim()) != null)
            rad_ddl_inner_emp_name.SelectedValue = value;
    }
}

由于rad_ddl_inner_emp_name.Items中没有任何项目,您可以将txt_inner_emp_num.Text设置为ddl中的选择。

首先检查rad_ddl_inner_emp_name.Items count > 0,然后设置所需的文本选中。或者您可以检查rad_ddl_inner_emp_name.Items.FindItemByValue(txt_inner_emp_num.Text.TrimEnd())是否为空