绑定的形式组合框到数据表的DataContext [英] Binding forms ComboBox to DataTable DataContext

查看:128
本文介绍了绑定的形式组合框到数据表的DataContext的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我通常能够解决我的问题,约五分钟搜索,但是这一次采取了几天没有结果,所以我会尽力提出这个问题。

我的DataContext设置为一个DataTable中的一个表(将preFER LINQ到SQL,但我坚持瓦特/的Sybase缺少现代的实体框架很好的支持。)我有一个组合框源来自其他DataTable中要更新表格上的数据表中的列,但我似乎无法获得绑定的SelectedValue正常工作。

我在输出窗口,我不能确定如何解决获得绑定错误,但它指出了问题的原因:

System.Windows.Data错误:40:BindingEx pression路径错误:'颜色'属性不是'对象'''数据表(散列code = 1796783)'中。 BindingEx pression:路径=颜色; DataItem的=数据表(散列code = 1796783);目标元素是'组合框'(名称='cboColor');目标属性的SelectedValue(类型'对象')

我创建了一个示例应用程序,再现问题,并提供在此背后的XAML和code

在此先感谢您的帮助

 <窗​​口x:类=WPFTestBed.ComboTest
    的xmlns =htt​​p://schemas.microsoft.com/winfx/2006/xaml/$p$psentation
    的xmlns:X =htt​​p://schemas.microsoft.com/winfx/2006/xaml
    标题=ComboTest高度=300宽度=300
    加载=的OnLoad>
<电网>
    < Grid.ColumnDefinitions>
        < ColumnDefinition WIDTH =126 */>
        < ColumnDefinition WIDTH =152 */>
    < /Grid.ColumnDefinitions>
    <数据网格的AutoGenerateColumns =FALSE高度=243保证金=8,6,0,0NAME =dgListVerticalAlignment =热门CanUserAddRows =假的ItemsSource ={结合}的SelectionChanged =dgList_SelectionChanged >
        < D​​ataGrid.Columns>
            < D​​ataGridTextColumn标题=名称的IsReadOnly =真绑定={绑定路径=名}WIDTH =*/>
            < D​​ataGridTextColumn标题=颜色的IsReadOnly =真绑定={绑定路径=颜色}WIDTH =自动/>
        < /DataGrid.Columns>
    < /数据网格>
    <电网Grid.Column =1高度=207的Horizo​​ntalAlignment =左保证金=6,6,0,0NAME =grdSelectionVerticalAlignment =热门WIDTH =140的DataContext ={结合}>
        < TextBlock的高度=23的Horizo​​ntalAlignment =左保证金=6,6,0,0NAME =textBlock1文本={绑定路径=名}VerticalAlignment =热门/>
        < TextBlock的高度=23的Horizo​​ntalAlignment =左保证金=6,27,0,0NAME =textBlock2文本={绑定路径=颜色}VerticalAlignment =热门/>
        <组合框高度=23的Horizo​​ntalAlignment =左保证金=6,56,0,0NAME =cboColorVerticalAlignment =热门WIDTH =120
                  的ItemsSource ={结合}的DisplayMemberPath =colorNameSelectedValuePath =colorName的SelectedValue ={绑定路径=颜色}/>
    < /网格>
    <按钮内容=_保存Grid.Column =1高度=23的Horizo​​ntalAlignment =右保证金=0,0,6,12NAME =btnSaveVerticalAlignment =底部WIDTH =75 点击=btnSave_Click/>
< /网格>
 

$ C $后面ç

 使用系统;
使用System.Collections.Generic;
使用System.Linq的;
使用System.Text;
使用System.Windows;
使用System.Windows.Controls的;
使用System.Windows.Data;
使用System.Windows.Documents;
使用System.Windows.Input;
使用System.Windows.Media;
使用System.Windows.Media.Imaging;
使用System.Windows.Shapes;
使用System.Data这;

命名空间WPFTestBed
{
    ///<总结>
    ///为ComboTest.xaml交互逻辑
    ///< /总结>
    公共部分类ComboTest:窗口
    {
        公共ComboTest()
        {
            的InitializeComponent();
        }


        私人数据表的GetList()
        {
            数据表DT =新的DataTable();
            DataRow的列;

            dt.Columns.Add(新的DataColumn(名字));
            dt.Columns.Add(新的DataColumn(颜色));

            行= dt.NewRow();行[名称] =安倍;行[颜色] =红; dt.Rows.Add(行);
            行= dt.NewRow();行[名称] =鲍勃;行[颜色] =黄色; dt.Rows.Add(行);
            行= dt.NewRow();行[名称] =夹头;行[颜色] =蓝; dt.Rows.Add(行);
            行= dt.NewRow();行[名称] =道;行[颜色] =红; dt.Rows.Add(行);
            行= dt.NewRow();行[名称] =埃迪;行[颜色] =黄色; dt.Rows.Add(行);
            行= dt.NewRow();行[名称] =弗雷德;行[颜色] =蓝; dt.Rows.Add(行);
            返回DT;
        }

        私人数据表getColors()
        {
            数据表DT =新的DataTable();
            DataRow的列;
            dt.Columns.Add(新的DataColumn(colorName));
            行= dt.NewRow();行[colorName] =红; dt.Rows.Add(行);
            行= dt.NewRow();行[colorName] =黄色; dt.Rows.Add(行);
            行= dt.NewRow();行[colorName] =蓝; dt.Rows.Add(行);
            返回DT;
        }

        私人无效的OnLoad(对象发件人,RoutedEventArgs E)
        {
            dgList.DataContext =的GetList();
            cboColor.DataContext = getColors();
        }

        私人无效dgList_SelectionChanged(对象发件人,SelectionChangedEventArgs E)
        {
            //获取所选择的项目
            DataRowView的selectedRow =(DataRowView的)dgList.SelectedCells [0] .Item;

            //对于说明性的目的 - 在现实生活用于在DataContext的数据表将来自数据库
            数据表DT =新的DataTable();
            dt.Columns.Add(新的DataColumn(名字));
            dt.Columns.Add(新的DataColumn(颜色));
            DataRow的行= dt.NewRow(); 。行[名称] = selectedRow [名称]的ToString();行[颜色] = selectedRow [颜色]; dt.Rows.Add(行);

            //设置数据上下文的形式
            grdSelection.DataContext = DT;
        }

        私人无效btnSave_Click(对象发件人,RoutedEventArgs E)
        {
            数据表DT =(数据表)grdSelection.DataContext;
            // DT没有被更新的组合框结合预期
        }
    }
}
 

解决方案

现在的问题是,当你绑定列表中的颜色,数据上下文被搞砸了:

  cboColor.DataContext = getColors();
 

需要保持绑定到数据表的组合框的数据上下文。在这个例子中的应用程序,你可以做直接设置项目源独自离开其数据方面:

  cboColor.ItemsSource = getColors()AsDataView();
 

I'm usually able to solve my problems with about five minutes of searching but this one has taken several days with no results, so I'll try posing the question.

I have a Form whose DataContext is set to a datatable (would prefer LINQ to SQL but I am stuck w/ Sybase which lacks good support for modern entity frameworks.) I have a combo box sourced by another datatable that should update a column on the forms data table but I can't seem to get the binding for SelectedValue to work correctly.

I get a binding error in my Output window which I am unsure how to resolve but it points to the cause of the problem:

System.Windows.Data Error: 40 : BindingExpression path error: 'color' property not found on 'object' ''DataTable' (HashCode=1796783)'. BindingExpression:Path=color; DataItem='DataTable' (HashCode=1796783); target element is 'ComboBox' (Name='cboColor'); target property is 'SelectedValue' (type 'Object')

I've created a sample app that recreates the problem and provide the Xaml and code behind here

Thanks in advance for your help

<Window x:Class="WPFTestBed.ComboTest"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="ComboTest" Height="300" Width="300"
    Loaded="OnLoad">
<Grid>
    <Grid.ColumnDefinitions>
        <ColumnDefinition Width="126*" />
        <ColumnDefinition Width="152*" />
    </Grid.ColumnDefinitions>
    <DataGrid AutoGenerateColumns="False" Height="243" Margin="8,6,0,0" Name="dgList" VerticalAlignment="Top" CanUserAddRows="False" ItemsSource="{Binding}" SelectionChanged="dgList_SelectionChanged"> 
        <DataGrid.Columns>
            <DataGridTextColumn Header="Name" IsReadOnly="True" Binding="{Binding Path=name}" Width="*"/>
            <DataGridTextColumn Header="Color" IsReadOnly="True" Binding="{Binding Path=color}" Width="Auto"/>
        </DataGrid.Columns>
    </DataGrid>
    <Grid Grid.Column="1" Height="207" HorizontalAlignment="Left" Margin="6,6,0,0" Name="grdSelection" VerticalAlignment="Top" Width="140" DataContext="{Binding}">
        <TextBlock Height="23" HorizontalAlignment="Left" Margin="6,6,0,0" Name="textBlock1" Text="{Binding Path=name}" VerticalAlignment="Top" />
        <TextBlock Height="23" HorizontalAlignment="Left" Margin="6,27,0,0" Name="textBlock2" Text="{Binding Path=color}" VerticalAlignment="Top" />
        <ComboBox Height="23" HorizontalAlignment="Left" Margin="6,56,0,0" Name="cboColor" VerticalAlignment="Top" Width="120" 
                  ItemsSource="{Binding}" DisplayMemberPath="colorName" SelectedValuePath="colorName" SelectedValue="{Binding Path=color}" />
    </Grid>
    <Button Content="_Save" Grid.Column="1" Height="23" HorizontalAlignment="Right" Margin="0,0,6,12" Name="btnSave" VerticalAlignment="Bottom" Width="75" Click="btnSave_Click" />
</Grid>

Code behind

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Shapes;
using System.Data;

namespace WPFTestBed
{
    /// <summary>
    /// Interaction logic for ComboTest.xaml
    /// </summary>
    public partial class ComboTest : Window
    {
        public ComboTest()
        {
            InitializeComponent();
        }


        private DataTable getList()
        {
            DataTable dt = new DataTable();
            DataRow row;

            dt.Columns.Add(new DataColumn("name"));
            dt.Columns.Add(new DataColumn("color"));

            row = dt.NewRow(); row["name"] = "abe";  row["color"] = "Red"; dt.Rows.Add(row);
            row = dt.NewRow(); row["name"] = "bob"; row["color"] = "Yellow"; dt.Rows.Add(row);
            row = dt.NewRow(); row["name"] = "chuck"; row["color"] = "Blue"; dt.Rows.Add(row);
            row = dt.NewRow(); row["name"] = "doug"; row["color"] = "Red"; dt.Rows.Add(row);
            row = dt.NewRow(); row["name"] = "eddie"; row["color"] = "Yellow"; dt.Rows.Add(row);
            row = dt.NewRow(); row["name"] = "fred"; row["color"] = "Blue"; dt.Rows.Add(row);
            return dt;
        }

        private DataTable getColors()
        {
            DataTable dt = new DataTable();
            DataRow row;
            dt.Columns.Add(new DataColumn("colorName"));
            row = dt.NewRow(); row["colorName"] = "Red"; dt.Rows.Add(row);
            row = dt.NewRow(); row["colorName"] = "Yellow"; dt.Rows.Add(row);
            row = dt.NewRow(); row["colorName"] = "Blue"; dt.Rows.Add(row);
            return dt;
        }

        private void OnLoad(object sender, RoutedEventArgs e)
        {
            dgList.DataContext = getList();
            cboColor.DataContext = getColors();
        }

        private void dgList_SelectionChanged(object sender, SelectionChangedEventArgs e)
        {
            // Get the selected Item
            DataRowView selectedRow = (DataRowView)dgList.SelectedCells[0].Item;

            //For Illustrative purposes - in "real life" the data table used for the DataContext would come from the database
            DataTable dt = new DataTable();
            dt.Columns.Add(new DataColumn("name"));
            dt.Columns.Add(new DataColumn("color"));
            DataRow row = dt.NewRow(); row["name"] = selectedRow["name"].ToString();  row["color"] = selectedRow["color"]; dt.Rows.Add(row);

            // Set the data context for the form
            grdSelection.DataContext = dt;
        }

        private void btnSave_Click(object sender, RoutedEventArgs e)
        {
            DataTable dt = (DataTable)grdSelection.DataContext;
            // dt is not updated by combobox binding as expected
        }            
    }
}

解决方案

The problem is that when you bind the list to the colors, the data context gets screwed up:

 cboColor.DataContext = getColors();

Need to keep the ComboBox's data context bound to the DataTable. In the example app, you could do by setting the items source directly and leaving its data context alone:

cboColor.ItemsSource = getColors().AsDataView();

这篇关于绑定的形式组合框到数据表的DataContext的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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