如何声明性地将"SelectedValue"绑定到数据源字段? [英] How do I declaratively bind 'SelectedValue' to datasource field?

查看:53
本文介绍了如何声明性地将"SelectedValue"绑定到数据源字段?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想从数据源中的属性驱动 RadioButtonList SelectedValue 属性,但是我无法使其正常工作.

I want to drive a RadioButtonLists SelectedValue property from a property in my datasource, but I'm not managing to make it work.

我的页面上有一个< asp:RadioButtonList 绑定到< asp:ObjectDataSource .该数据源又提供了以下模型类:

I have a <asp:RadioButtonList on my page bound to an <asp:ObjectDataSource. This datasource in turn provides the following model class:

public class CollectionWithDefault : Collection<string>
{
    CollectionWithDefault(IEnumerable<string> items, string defaultItem)
    {
        foreach (var item in items)
            Add(item);

        DefaultItem = defaultItem;
    }

    public string DefaultItem { get; }
}

请注意,此类是标准的字符串集合,该字符串还公开了默认选项之一.

Notice that this class is a standard collection of strings that also exposes which one of them is the default option.

请考虑我对于值提供者具有以下实现.这是一个简单的内存实现,但是请记住,这可能来自数据库或任何其他来源:

Consider that I have the following implementation for a value provider. This is a simple in-memory implementation, but keep in mind that this could be coming from a database or any other source:

public static class ItemProvider
{
    public static CollectionWithDefault GetAvailableItems()
    {
        var items = new [] { "option1", "option2", "option3" };

        return new CollectionWithDefault(items, items[1]);
    }
}

我尝试了以下操作:

<asp:ObjectDataSource runat="server"
    ID="ItemSource"
    TypeName="MyNamespace.ItemProvider"
    SelectMethod="GetAvailableItems" />
<asp:RadioButtonList runat="server" 
    DataSourceID="ItemSource"
    SelectedValue='<%# Eval("DefaultItem") #>' />

Eval 调用中出现以下异常:

I'm getting the following exception in the Eval call:

System.InvalidOperationException:'诸如Eval(),XPath()和Bind()之类的数据绑定方法只能在数据绑定控件的上下文中使用.'

System.InvalidOperationException: 'Databinding methods such as Eval(), XPath(), and Bind() can only be used in the context of a databound control.'

如何确保根据来自数据源的字段预先选择了正确的无线电?

How can I ensure that the correct radio is preselected based on the field coming from my datasource?

更改收集模型本身以使其正常工作是可以接受的,但是我无法从代码隐藏中设置 SelectedValue .我想依靠数据源控件来完成繁重的工作.

Changing the collection model itself to make it work is acceptable, but I can't set the SelectedValue from codebehind. I wanted to rely on the datasource control to do the heavy lifting.

推荐答案

通过扩展原始的 RadioButtonList 控件并将核心数据绑定方法修改为荣誉 ListItem 对象.

I managed to make this work seamlessly without requiring manual assignments in codebehind by extending the original RadioButtonList control and modifying the core databinding method to honor ListItem objects.

它是这样的:

public class MyRadioButtonList : RadioButtonList
{
    protected override void PerformDataBinding(IEnumerable dataSource)
    {
        if (dataSource is IEnumerable<ListItem> listItems)
        {
            ...

            foreach (var listItem in listItems)
                Items.Add(listItem);

            ...
        }
        else
        {
            base.PerformDataBinding(dataSource);
        }
    }    
}

有了这个,只需要将我的源模型转换为表示层上的 IEnumerable< ListItem> (使用适配器/代理实现即可轻松完成),然后将其输入 ListItem s到控件.

With this in place, it was just a matter of converting my source model into a IEnumerable<ListItem> on the presentation layer (easy to accomplish with an adapter/proxy implementation) and then feed these ListItems to the control.

一旦完成此操作,就可以基于数据源字段看到所选的项目正确反映在UI中.考虑到扩展的琐碎性,我觉得很值得:)

Once I got this in place, I could see my selected items reflected correctly in the UI based on the datasource field. Considering how trivial the extension is, I feel it was quite worth it :)

相同的继承方法可能会用于类似的控件,例如 CheckBoxList ,该控件也受相同的限制.

The same inheritance approach can probably be used for similar controls like CheckBoxList, which suffers from the very same limitation.

对于喜欢冒险的人来说,也可以通过在控件中引入额外的 DataSelectedField DataEnabledField 属性并在其上使用 Eval 来完成这项工作.它们的顶部作为原始数据绑定算法的一部分(已经使用 DataTextField DataValueField 进行了此操作).我觉得这对我的用例来说会涉及更多点,因此决定采用一个更简单的替代方法,但这绝对是一种有效的方法,甚至可以与我提出的解决方案一起使用,以实现更强大的 RadioButtonList .

For the more adventurous folks, one could also make this work by introducing extra DataSelectedField and DataEnabledField properties in the control and using Eval on top of them as part of the original databinding algorithm (which already does this with DataTextField and DataValueField). I felt this would be a little bit more involved for my use case and decided to go with a simpler override, but it is definitely a valid approach that could even live along my proposed solution for an even more robust RadioButtonList.

这篇关于如何声明性地将"SelectedValue"绑定到数据源字段?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆