zoukankan      html  css  js  c++  java
  • 为 ItemsControl 类型的控件提供行号,mvvm模式 绑定集合

    从网络上看到的两种方式,一种是,在 codebehind 里为 控件写事件,下面是将集合绑定到 DataGrid 控件:

    private void DataGridSoftware_LoadingRow(object sender, DataGridRowEventArgs e)
    {
        e.Row.Header = e.Row.GetIndex() + 1;
    }

    貌似可行,但是先不说 mvvm 下这种方式的可行性,更新列表某一项,就必须得再写一套处理逻辑。

    于是,直接在 ViewModel 里定义一个 Index 属性就成为了另一个可行的方法:

        public class MainDataViewModel : ObservableObject
        {
            private string _MyProperty;
            public string MyProperty
            {
                get { return _MyProperty; }
                set
                {
                    _MyProperty = value;
                    RaisePropertyChanged("MyProperty");
                }
            }
    
            private int _Index;
            public int Index
            {
                get { return _Index; }
                set
                {
                    _Index = value;
                    RaisePropertyChanged("Index");
                }
            }        
        }

    结果同样令人汗颜, 因为同样得自己处理逻辑为定义的 Index 属性动态更改数值,不然位置一样是假的。

    接下来还试过几种方式,都觉得很乱,需要处理的东西太多,到底有没有一个好的方式去搞定他呢!

    首先,系统的看一下微软的MSDN -- <数据绑定概述> 这一节,一开始你会觉得哎呀太简单了,但是切入点就在这里。

    你会发现两段代码,不是很显眼:

    <Window.Resources>
    ...
    
    <CollectionViewSource 
          Source="{Binding Source={x:Static Application.Current}, Path=AuctionItems}"  x:Key="listingDataView" />
    ...
    </Window.Resources>
    
    <ListBox Name="Master" Grid.Row="2" Grid.ColumnSpan="3" Margin="8"
        ItemsSource="{Binding Source={StaticResource listingDataView}}">
    ...
    
    </ListBox>

    答案就在这里,切入点就是 CollectionView

    其实接下来,我就不知道该如何去做了,只是隐隐的感觉到它就是能解决问题的关键,但是我不甘心就在这里停下,就跟着微软的示范(后面有提到),将这个CollectionView加入了Converter:

        /// <summary>
        /// 获取 定义视图中 该项的位置,从 1 开始
        /// </summary>
        [ValueConversion(typeof(object), typeof(int))]
        public class Item2IndexConverter : IValueConverter
        {
            public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
            {
                int resault = 0;
                var iLi = parameter as CollectionViewSource;
                if (null != iLi)
                {
                    CollectionView cv = (CollectionView)iLi.View;
                    resault = cv.IndexOf(value) + 1;
                }
                return resault > 0 ? resault : System.Windows.DependencyProperty.UnsetValue;
            }
    
            public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
            {
                throw new NotImplementedException();
            }
        }

    于是,控件的获取就简单了,把你的当前项和视图,都传进来,我判断一下这个项在哪个位置就行了。

    前台如果是DataGrid,就是类似于这样:

        <Window.Resources>
            <converter:Item2IndexConverter x:Key="item_index_converter"/>
            <CollectionViewSource Source="{Binding VmMainDataListing}" x:Key="listingDataView" />
        </Window.Resources>
    
      <Grid>    
    <DataGrid RowHeaderWidth="40" ItemsSource="{Binding Source={StaticResource listingDataView}}" > <DataGrid.RowHeaderStyle> <!-- 显示行号 --> <Style TargetType="{x:Type DataGridRowHeader}"> <Setter Property="Content" Value="{Binding Converter={StaticResource item_index_converter},ConverterParameter={StaticResource listingDataView}}" /> </Style> </DataGrid.RowHeaderStyle> <DataGrid.Columns> 列表内容 </DataGrid.Columns> </DataGrid> </Grid>

     整体的思路如下:

    1.首先,我们的列表类型控件,获取到的源,是一个中间提供者——CollectionViewSource,他支持数据的封装,用于显示方面的排序、分组、序列

    2.有了这种会自己更改排序的源,我们就可以放心的将前台序号的统计任务交给他,剩下的工作就是获取我们想要的序号。

    3.获取序号的方式,是采用了微软的示范代码的形式,使用Converter进行获取,可以在 《DataGrid.RowHeaderStyle》的介绍页面的示范下找到,不过它的源是直接获取的一个控件,这种方式实际应用起来是不可行的。

    最后,如果你们有更好的法子,请留言交流,期待你们的墨水……

  • 相关阅读:
    mysql 视图
    CSS 上下居中和最低高度语法
    escape()、encodeURI()、encodeURIComponent()区别详解
    YII事件EVENT示例
    linux history命令优化
    mysql 之full join
    redis学习之数据类型
    <canvas>设置宽高遇到的问题
    关于块级元素撑满整个浏览器窗口
    jquery中bind()绑定多个事件
  • 原文地址:https://www.cnblogs.com/3Tai/p/3897338.html
Copyright © 2011-2022 走看看