“Win10 UAP 开发系列”之 在MVVM模式中控制ListView滚动位置

这个扩展属性从WP8.1就开始用了,主要是为了解决MVVM模式中无法直接控制ListView滚动位置的问题。比如在VM中刷新了数据,需要将View中的ListView滚动到顶部,ListView只有一个ScrollIntoView()方法可以控制滚动的位置,但最好在VM中不要出现直接控制View的代码,需要通过其他的方式。

使用一个扩展属性即可实现:

/// <summary>
    /// 将ListView滚动到顶部 使用方法:在ListView增加扩展属性
    /// ext:ListViewScrollToProperties.ScrollToIndex="{Binding ScrollToIndex}"
    /// 在VM中先vm.ScrollToIndex = 1;再vm.ScrollToIndex = 0;
    /// </summary>
    public class ListViewScrollToProperties : DependencyObject
    {
        public static readonly DependencyProperty ScrollToIndexProperty =
            DependencyProperty.RegisterAttached("ScrollToIndex", typeof(int), typeof(ListViewScrollToProperties), new PropertyMetadata("", OnScrollToIndexChanged));

        public static string GetScrollToIndex(DependencyObject dependencyObject)
        {
            return (string)dependencyObject.GetValue(ScrollToIndexProperty);
        }

        public static void SetScrollToIndex(DependencyObject dependencyObject, string scrollToIndex)
        {
            dependencyObject.SetValue(ScrollToIndexProperty, scrollToIndex);
        }

        private static void OnScrollToIndexChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            if ((int)e.NewValue != 1)
            {
                var listview = (ListView)d;
                if (listview != null)
                {
                    if (listview.Items.Count > 0)
                    {
                        try
                        {
                            var target = listview.Items[int.Parse(e.NewValue.ToString())];
                            if (target != null)
                            {
                                listview.UpdateLayout();
                                listview.ScrollIntoView(target);
                            }
                        }
                        catch (Exception ex)
                        {
                            System.Diagnostics.Debug.WriteLine(ex.Message);
                        }
                    }
                }
            }
        }
    }

使用方式比较丑,可以将就用:

在VM中提供一个ScrollToIndex属性,绑定到ListView上:

<ListView ItemsSource="{Binding ArticleItemList}"
                              controlHelper:ListViewScrollToProperties.ScrollToIndex="{Binding ScrollToIndex}"
                              Margin="0"></ListView>

在VM中刷新数据后,需要手动更改值来触发:

//滚动到顶部
ScrollToIndex = 1;
ScrollToIndex = 0;

我觉得这种实现方式比较丑,如果大家有好的实现方式欢迎留言讨论。

时间: 2024-10-20 05:06:37

“Win10 UAP 开发系列”之 在MVVM模式中控制ListView滚动位置的相关文章

“Win10 UAP 开发系列”之主题模式切换

微软动作真是快,本来想写WP8.1RT系列,结果刚整理了一点就出Win10 UAP了.不过还好RT到Win10的差别还不算太大.前两天参加了Win10开发极客秀,虽然没获奖,不过在韦恩卑鄙的帮助下顺利将澎湃新闻WP8.1版升级到了Win10UAP,使用了一些新的特性,最近争取有时间慢慢把一些东西总结一下. 今天先说一下如何在Win10 UAP中切换主题模式. 切换日间.夜间主题模式这个功能我从WP8就实现了,并封装成了一个库,用在我所有的WP8的app里.到了WP8.1因为系统主题样式都改了,又

Win10 UWP开发系列:解决Win10不同版本的Style差异导致的兼容性问题

原文:Win10 UWP开发系列:解决Win10不同版本的Style差异导致的兼容性问题 最近在开发一个项目时,遇到了一个奇怪的问题,项目依赖的最低版本是10586,目标版本是14393,开发完毕发布到商店后,很多用户报无法正常加载页面.经查,有问题的都是Win10 10586版本. 我上篇博客中写到的自定义的AppBar控件,也存在这个问题,10586会报错. 为此特意下载了10586的SDK调试.错误显示,一个样式找不到,名为ListViewItemBackground.因为开发的时候是基于

Win10 UWP开发系列:使用VS2015 Update2+ionic开发第一个Cordova App

安装VS2015 Update2的过程是非常曲折的.还好经过不懈的努力,终于折腾成功了. 如果开发Cordova项目的话,推荐大家用一下ionic这个框架,效果还不错.对于Cordova.PhoneGap.ionic.AngularJS这些框架或库的关系,我个人理解是这样,PhoneGap是一个商业项目,用来实现HTML5式的跨平台开发,后来Adobe公司将其中的核心代码开源,就是Cordova,Cordova只负责实现JavaScript调用原生代码的功能,是一个壳,而壳里具体用什么样式,在H

通用Windows应用《博客园-开发者的网上家园》开发(1)——MVVM模式

最近开发了个WP8.1和Windows8.1平台上的应用——<博客园-开发者的网上家园>,基于 Windows Runtime .在此有必要说明一下,WP8.0以前的应用程序是基于Silverlight的,微软为了统一Windows Phone OS 和 Windows RT,从开发人员的角度上,也统一了两个平台上大部分的API,使得开发人员可以共享代码(而不是一次编写,跨平台运行). 本文着重描述MVVM在Windows Runtime应用程序下的表现,关于MVVM模式的理解,可参考园子里 

Win10 UWP开发系列——开源控件库:UWPCommunityToolkit

原文:Win10 UWP开发系列--开源控件库:UWPCommunityToolkit 在开发应用的过程中,不可避免的会使用第三方类库.之前用过一个WinRTXamlToolkit.UWP,现在微软官方发布了一个新的开源控件库—— UWPCommunityToolkit 项目代码托管在Github上:https://github.com/Microsoft/UWPCommunityToolkit 包括以下几个类库: 都可以很方便的从Nuget上安装. NuGet Package Name des

在MVVM模式中,按钮Click事件的绑定方法

原文:在MVVM模式中,按钮Click事件的绑定方法 在MVVM模式中,我们将Button的方法写到ViewModel中,然后绑定到前端界面.通常的做法是写一个类,继承ICommand接口,然而如果按钮比较多的话,就需要写很多的类,对于后期维护造成很大的不变,微软提供了一个DelegateCommand类,可以简化开发. 使用方法如下: 首先生命ViewModel属性,GetMsg函数, public DelegateCommand GetMsg { get { return new Deleg

WPF MVVM模式中,通过命令实现窗体拖动、跳转以及显隐控制

在WPF中使用MVVM模式,可以让我们的程序实现界面与功能的分离,方便开发,易于维护.但是,很多初学者会在使用MVVM的过程中遇到一个显而易见且无法回避的问题,那就是不同的窗体之间如何跳转?很多人在介绍MVVM的使用时,都没有明显提到该如何解决这一问题,不知是因为觉得太简单了还是其他原因. 博主根据自己的开发经验,写了一个简单的示例程序,介绍MVVM模式中,如何通过命令来控制窗体的跳转.拖动与显隐控制. 先看效果: 主窗体中只有一个按钮,点击该按钮后,可以打开新的窗. 新窗体可以为自定义样式窗体

Messenger在MVVM模式中的应用

Messenger在MVVM模式中的应用 Messenger在MVVM中应用的前提 我们知道在MVVM架构中,系统平台的Silverlight客户端界面开发和业务逻辑已经被分开,XAML是SL的主要部分,界面设计者只需要绑定ViewModel里的数据即可.但是在ViewModel里有些时候是需要界面发出响应的,在这种情况下,Messenger显示出它的用处. Messenger的架构 Messager构件代码 定义Imessager接口 注册一个接收消息的类型,比如某一控件来接收消息 void

silverlighter下MVVM模式中利用Behavior和TargetedTriggerAction实现文本框的一些特效

在silverlight一般开发模式中,给文本框添加一些事件是轻而易举的,然而MVVM开发模式中,想要给文本框添加一些事件并非那么容易,因为MVVM模式中,只有ICommand接口,而且也只有Button中才有Command属性,通过ViewModel可以将方法绑定到Button上面,却无法绑定到文本框和其他一些控件.. Behavior的出现解决了这一难题,下面就来说一下具体的实现方法: 实例一:在用户登录窗口,用户点击Reset按钮后,让用户名输入框自动获取焦点. 首先要先将ViewMode