0

经过多年的 WinForms,我正在涉足 WPF,并且我正在努力处理数据绑定/过滤。

编辑:这是我的代码;网格 1 (companiesDataGrid) SelectionChanged 事件是对网格 2 (sitesDataGrid) 进行过滤的地方。简而言之,当 vs_Companies 改变位置时,需要过滤 vs_Sites;vs_Sites 有一个名为 Company_ID 的字段,它将过滤该字段以匹配当前选定的 vs_Companies 行的 ID 字段。

这是我在 WPF 的第一次尝试——如果有任何指针作为在多用户环境中连接到 SQL 服务器方面的最佳实践,我将不胜感激,当前的代码非常基本,CollectionViewSource 数据直接提供给两个没有中间对象的数据网格。

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
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.Navigation;
using System.Windows.Shapes;

namespace RevDB
{
    public partial class MainWindow : Window
    {
        public RevDB.TSDBDataSet ds_Rev;

        public RevDB.TSDBDataSetTableAdapters.CompaniesTableAdapter ta_Companies;
        public RevDB.TSDBDataSetTableAdapters.SitesTableAdapter ta_Sites;

        public System.Windows.Data.CollectionViewSource vs_Sites;
        public System.Windows.Data.CollectionViewSource vs_Companies;

        public MainWindow()
        {
            InitializeComponent();
        }

        private void Window_Loaded_1(object sender, RoutedEventArgs e)
        {

            ds_Rev = ((RevDB.TSDBDataSet)(this.FindResource("tsDBDataSet")));

            //Sites
            ta_Sites = new RevDB.TSDBDataSetTableAdapters.SitesTableAdapter();
            ta_Sites.Fill(ds_Rev.Sites);

            vs_Sites = ((System.Windows.Data.CollectionViewSource)(this.FindResource("sitesViewSource")));
            vs_Sites.View.MoveCurrentToFirst();

            //Companies
            ta_Companies = new RevDB.TSDBDataSetTableAdapters.CompaniesTableAdapter();
            ta_Companies.Fill(ds_Rev.Companies);

            vs_Companies = ((System.Windows.Data.CollectionViewSource)(this.FindResource("companiesViewSource")));
            vs_Companies.View.MoveCurrentToFirst();

            //Data bindings
            //this.txt_Company.SetBinding(TextBox.TextProperty, new Binding() { Path = "TargetText", Source = this });
        }

        private void companiesDataGrid_SelChanged(object sender, SelectionChangedEventArgs e)
        {

        }
    }
}
4

2 回答 2

0

我会将您的 ViewModel 中的一个属性绑定到您希望从中获取更新 ID 的 DataGrid的SelectedItem属性。然后,您可以在视图的代码隐藏中使用SelectionChanged事件,或者使用绑定到SelectedItem的属性的设置器来触发对第二个集合的更新。

此外,请确保两个集合都是ObservableCollection类型,并且 VideModel 正在实现INotifyPropertyChanged

于 2012-10-13T20:09:47.383 回答
0

好的,正如所承诺的,这是一个例子。

场景:您有 2 个 DataGrid。一个 DataGrid 包含公司和其他站点。

条件:只要选择公司,所选网站就会更改以反映相关公司网站。

实现:MVVM,SelectedCompany 属性的更改会更新ViewModel 中的SelectedSite属性。

注意:我添加了额外的 DataGrid 样式以使 Lost-Focus 状态可见。默认情况下,所选行在“丢失焦点”上不可见。

型号

公司

using System;
using System.ComponentModel;

namespace CascadingDataGrids
{
    public class Company : INotifyPropertyChanged
    {
        private int _id;

        /// <summary>
        /// Gets or sets the id.
        /// </summary>
        /// <value>
        /// The id.
        /// </value>
        public int Id
        {
            get { return _id; }
            set
            {
                if (value != _id)
                {
                    _id = value;
                    NotifyPropertyChanged("Id");
                }
            }
        }

        private string _companyName;

        /// <summary>
        /// Gets or sets the name of the company.
        /// </summary>
        /// <value>
        /// The name of the company.
        /// </value>
        public string CompanyName
        {
            get { return _companyName; }
            set
            {
                {
                    if (value != _companyName)
                    {
                        _companyName = value;
                        NotifyPropertyChanged("CompanyName");
                    }
                }
            }
        }

        private int _siteId;

        /// <summary>
        /// Gets or sets the site id.
        /// </summary>
        /// <value>
        /// The site id.
        /// </value>
        public int SiteId
        {
            get { return _siteId; }
            set
            {
                if (value != _siteId)
                {
                    _siteId = value;
                    NotifyPropertyChanged("SiteId");
                }
            }
        }

        #region INotifyPropertyChanged

        public event PropertyChangedEventHandler PropertyChanged;
        private void NotifyPropertyChanged(String info)
        {
            if (PropertyChanged != null)
            {
                PropertyChanged(this, new PropertyChangedEventArgs(info));
            }
        }

        #endregion
    }
}

地点

using System;
using System.ComponentModel;

namespace CascadingDataGrids
{
    public class Site : INotifyPropertyChanged
    {
        private int _id;

        /// <summary>
        /// Gets or sets the id.
        /// </summary>
        /// <value>
        /// The id.
        /// </value>
        public int Id
        {
            get { return _id; }
            set
            {
                if (value != _id)
                {
                    _id = value;
                    NotifyPropertyChanged("Id");
                }
            }
        }

        private string _siteName;

        /// <summary>
        /// Gets or sets the name of the site.
        /// </summary>
        /// <value>
        /// The name of the site.
        /// </value>
        public string SiteName
        {
            get { return _siteName; }
            set
            {
                {
                    if (value != _siteName)
                    {
                        _siteName = value;
                        NotifyPropertyChanged("SiteName");
                    }
                }
            }
        }

        #region INotifyPropertyChanged

        public event PropertyChangedEventHandler PropertyChanged;
        private void NotifyPropertyChanged(String info)
        {
            if (PropertyChanged != null)
            {
                PropertyChanged(this, new PropertyChangedEventArgs(info));
            }
        }

        #endregion
    }
}

视图模型

using System;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Linq;

namespace CascadingDataGrids
{
    public class DemoViewModel : INotifyPropertyChanged
    {
        #region Properties

        private ObservableCollection<Company> _companies;

        /// <summary>
        /// Gets or sets the companies.
        /// </summary>
        /// <value>
        /// The companies.
        /// </value>
        public ObservableCollection<Company> Companies
        {
            get { return _companies; }
            set
            {
                if (value != _companies)
                {
                    _companies = value;
                    NotifyPropertyChanged("Companies");
                }
            }
        }

        private Company _selectedCompany;

        /// <summary>
        /// Gets or sets the selected company.
        /// </summary>
        /// <value>
        /// The selected company.
        /// </value>
        public Company SelectedCompany
        {
            get { return _selectedCompany; }
            set
            {
                if (value != _selectedCompany)
                {
                    _selectedCompany = value;
                    NotifyPropertyChanged("SelectedCompany");

                    // Set Site
                    var currentSite =
                        Sites.FirstOrDefault(x => x.Id == SelectedCompany.SiteId);

                    // Evaluate
                    if (currentSite != null)
                    {
                        SelectedSite = currentSite;
                    }
                }
            }
        }

        private ObservableCollection<Site> _sites;

        /// <summary>
        /// Gets or sets the sites.
        /// </summary>
        /// <value>
        /// The sites.
        /// </value>
        public ObservableCollection<Site> Sites
        {
            get { return _sites; }
            set
            {
                if (value != _sites)
                {
                    _sites = value;
                    NotifyPropertyChanged("Sites");
                }
            }
        }

        private Site _selectedSite;

        /// <summary>
        /// Gets or sets the selected site.
        /// </summary>
        /// <value>
        /// The selected site.
        /// </value>
        public Site SelectedSite
        {
            get { return _selectedSite; }
            set
            {
                if (value != _selectedSite)
                {
                    _selectedSite = value;
                    NotifyPropertyChanged("SelectedSite");
                }
            }
        }

        #endregion

        #region Constructors

        /// <summary>
        /// Initializes a new instance of the <see cref="DemoViewModel"/> class.
        /// </summary>
        public DemoViewModel()
        {
            // New instances
            Companies = new ObservableCollection<Company>();
            Sites = new ObservableCollection<Site>();

            // Build
            BuildCompanies();
            BuildSites();
        }

        #endregion

        #region Members

        /// <summary>
        /// Builds the companies.
        /// </summary>
        private void BuildCompanies()
        {
            // Set companies
            Companies = new ObservableCollection<Company>
            {
                new Company { Id = 1, CompanyName = "Microsoft", SiteId = 1 },
                new Company { Id = 2, CompanyName = "Google", SiteId = 3 },
                new Company { Id = 3, CompanyName = "Amazon", SiteId = 2 },
            };

            // Set selected to first value
            SelectedCompany = Companies.FirstOrDefault();
        }

        /// <summary>
        /// Builds the sites.
        /// </summary>
        private void BuildSites()
        {
            // Set sites
            Sites = new ObservableCollection<Site>
            {
                new Site { Id = 1, SiteName = "Redmond, WA" },
                new Site { Id = 2, SiteName = "Seattle, WA" },
                new Site { Id = 3, SiteName = "Mountain View, CA" }
            };

            // Set selected to first value
            SelectedSite = Sites.FirstOrDefault();
        }

        #endregion

        #region INotifyPropertyChanged

        public event PropertyChangedEventHandler PropertyChanged;
        private void NotifyPropertyChanged(String info)
        {
            if (PropertyChanged != null)
            {
                PropertyChanged(this, new PropertyChangedEventArgs(info));
            }
        }

        #endregion
    }
}

查看:XAML

<Window x:Class="CascadingDataGrids.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="Companies and Sites" Height="700" Width="500">

    <Window.Resources>
        <Style x:Key="Header" TargetType="TextBlock">
            <Setter Property="FontFamily" Value="Calibri" />
            <Setter Property="FontSize" Value="20" />
            <Setter Property="FontWeight" Value="Bold" />
        </Style>

        <!-- Datagrid -->
        <Style TargetType="{x:Type DataGrid}">
            <Setter Property="Background" Value="White" />
            <Setter Property="CanUserAddRows" Value="False" />
            <Setter Property="CanUserResizeRows" Value="False" />
            <Setter Property="CanUserDeleteRows" Value="False" />
            <Setter Property="SelectionMode" Value="Single" />
            <Setter Property="SelectionUnit" Value="FullRow" />
            <Setter Property="EnableRowVirtualization" Value="True" />
        </Style>

        <Style TargetType="{x:Type DataGridCell}">
            <Setter Property="Background" Value="Transparent" />
            <Setter Property="BorderBrush" Value="Transparent" />
            <Style.Triggers>
                <Trigger Property="IsSelected" Value="True">
                    <Setter Property="Foreground" Value="Black" />
                </Trigger>
            </Style.Triggers>
        </Style>

        <Style TargetType="{x:Type DataGridRow}">
            <Setter Property="Cursor" Value="Hand" />
            <Style.Triggers>

                <!-- Hover -->
                <Trigger Property="IsMouseOver" Value="True">
                    <Setter Property="Background">
                        <Setter.Value>
                            <LinearGradientBrush StartPoint="0.5,0" EndPoint="0.5,1" Opacity="0.5">
                                <GradientStop Color="#dceef7" Offset="0" />
                                <GradientStop Color="#f2f9fc" Offset="1" />
                            </LinearGradientBrush>
                        </Setter.Value>
                    </Setter>
                </Trigger>

                <!-- Selected -->
                <Trigger Property="IsSelected" Value="True">
                    <Setter Property="Background">
                        <Setter.Value>
                            <LinearGradientBrush StartPoint="0.5,0" EndPoint="0.5,1" Opacity="1">
                                <GradientStop Color="#333" Offset="0" />
                                <GradientStop Color="#333" Offset="0.01" />
                                <GradientStop Color="#e0e4e7" Offset="0.01" />
                                <GradientStop Color="#c2dbea" Offset="0.40" />
                                <GradientStop Color="#c2dbea" Offset="0.60" />
                                <GradientStop Color="#e0e4e7" Offset="0.99" />
                                <GradientStop Color="#333" Offset="0.99" />
                                <GradientStop Color="#333" Offset="1" />
                            </LinearGradientBrush>
                        </Setter.Value>
                    </Setter>
                </Trigger>
            </Style.Triggers>
        </Style>
    </Window.Resources>

    <Grid Margin="20">
        <Grid.RowDefinitions>
            <RowDefinition Height="24" />
            <RowDefinition Height="240" />
            <RowDefinition Height="40" />
            <RowDefinition Height="24" />
            <RowDefinition Height="240" />
        </Grid.RowDefinitions>

        <TextBlock Grid.Row="0" Style="{StaticResource Header}" Text="Companies" />
        <DataGrid Grid.Row="1" Margin="0 12 0 0"
            ItemsSource="{Binding Path=Companies}"
            SelectedItem="{Binding Path=SelectedCompany, Mode=TwoWay}" 
            RowHeight="20"
            IsReadOnly="True" />

        <TextBlock Grid.Row="3" Style="{StaticResource Header}" Text="Sites" />
        <DataGrid Grid.Row="4" Margin="0 12 0 0"
            ItemsSource="{Binding Path=Sites}"
            SelectedItem="{Binding Path=SelectedSite, Mode=TwoWay}" 
            RowHeight="20"
            IsReadOnly="True" />
    </Grid>
</Window>

查看:代码隐藏

using System.Windows;

namespace CascadingDataGrids
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        #region Members

        private readonly DemoViewModel _vm;

        #endregion

        #region Constructors

        /// <summary>
        /// Initializes a new instance of the <see cref="MainWindow"/> class.
        /// </summary>
        public MainWindow()
        {
            // Set viewmodel
            _vm = new DemoViewModel();

            // Set data context
            this.DataContext = _vm;

            // Initialize UI
            InitializeComponent();
        }

        #endregion
    }
}
于 2012-10-14T20:01:55.117 回答