CM支持通过ViewModel进行导航,并通过支持参数传递,但是内部只是通过反射的方式构造Uri的参数进行导航,所以只支持简单类型的参数传递,下面对其进行扩展,在页面导航时支持复杂类型的参数传递,并扩展了部分方法,比如,导航后删除上一个页面,清空导航,清空跳转等,详细的看代码

// *************************************************
//
// 作者:bomo
// 小组:WP开发组
// 创建日期:2014/5/22 23:03:26
// 版本号:V1.00
// 说明: 扩展 CM2.0 的INavigationService
//
// *************************************************
//
// 修改历史:
// Date WhoChanges Made
// 2014/5/22 23:03:26 bomo Initial creation
//
// ************************************************* using System;
using System.Linq;
using System.Reflection;
using System.Windows;
using System.Windows.Navigation;
using Caliburn.Micro; namespace XTuOne.Utility.Helpers
{
/// <summary>
/// INavigationService的扩展方法
/// </summary>
public static class NavigationExtensions
{
/// <summary>
/// 返回到第一个导航页面
/// </summary>
public static void BackToMainView(this INavigationService navigationService)
{
var count = navigationService.BackStack.Count();
for (int i = ; i < count; i++)
{
var entry = navigationService.RemoveBackEntry();
}
navigationService.GoBack();
} /// <summary>
/// 返回到匹配的导航页面(true:存在且返回成功,false:不存在不操作)
/// </summary>
public static bool Back2View(this INavigationService navigationService, string pageUri)
{
if (navigationService.ContainsView(pageUri))
{
var list = navigationService.BackStack.ToList(); foreach (var journalEntry in list)
{
if (!journalEntry.Source.OriginalString.Contains(pageUri))
{
var entry = navigationService.RemoveBackEntry();
}
else
{
break;
}
}
navigationService.GoBack();
return true;
}
return false;
} /// <summary>
/// 导航后删除上一个导航
/// </summary>
public static void NavAndRemoveBack<TViewModel>(this INavigationService navigationService) where TViewModel:class
{
navigationService.Navigate<TViewModel>(vm => navigationService.RemoveBackEntry());
} /// <summary>
/// 根据ViewModel类型跳转到指定页面(清空导航历史)
/// </summary>
public static void GoToView<T>(this INavigationService navigationService)
{
navigationService.UriFor<T>().Navigate();
ClearHistory(navigationService);
} /// <summary>
/// 判断导航历史是否存在ViewModel对应的View
/// </summary>
public static bool ContainsView<TViewModel>(this INavigationService navigationService)
{
return
navigationService.BackStack.Any(bs => bs.Source.OriginalString.Contains(GetViewUriString<TViewModel>()));
} /// <summary>
/// 判断导航历史是否存在Page
/// </summary>
public static bool ContainsView(this INavigationService navigationService, string pageUri)
{
return navigationService.BackStack.Any(bs=>bs.Source.OriginalString.Contains(pageUri));
} /// <summary>
/// 清空导航历史
/// </summary>
private static void ClearHistory(INavigationService navigationService)
{
var count = navigationService.BackStack.Count();
for (int i = ; i < count; i++)
{
navigationService.RemoveBackEntry();
}
} /// <summary>
/// 退出App
/// </summary>
public static void Exit(this INavigationService navigationService)
{
if (Environment.OSVersion.Version.Major < )
{
var asmb = Assembly.Load("Microsoft.Xna.Framework.Game, Version=4.0.0.0, Culture=neutral, PublicKeyToken=842cf8be1de50553");
var type = asmb.GetType("Microsoft.Xna.Framework.Game");
var constructorInfo = type.GetConstructor(new Type[] {});
if (constructorInfo != null)
{
var obj = constructorInfo.Invoke(new object[] {});
type.GetMethod("Exit").Invoke(obj, new object[] {});
}
}
else
{
var type = Application.Current.GetType();
type.GetMethod("Terminate").Invoke(Application.Current, new object[] {});
}
} /// <summary>
/// 通过ViewModel获取View的字符串
/// </summary>
public static string GetViewUriString<TViewModel>()
{
var viewType = ViewLocator.LocateTypeForModelType(typeof (TViewModel), null, null);
if (viewType == null)
{
throw new InvalidOperationException(
string.Format("No view was found for {0}. See the log for searched views.",
typeof (TViewModel).FullName));
}
return ViewLocator.DeterminePackUriFromType(typeof (TViewModel), viewType);
} /// <summary>
/// 扩展INavigationService,让导航支持复杂对象赋值
/// </summary>
public static void Navigate<TViewModel>(this INavigationService navigationService, Action<TViewModel> action) where TViewModel : class
{
var uri = GetViewUriString<TViewModel>();
NavigatedEventHandler navigationServerOnNavigated = null;
navigationServerOnNavigated = (s, e) =>
{
var viewModel = ViewModelLocator.LocateForView(e.Content) as TViewModel;
if (viewModel != null)
{
action(viewModel);
}
navigationService.Navigated -= navigationServerOnNavigated;
}; navigationService.Navigated += navigationServerOnNavigated;
navigationService.Navigate(new Uri(uri, UriKind.Relative));
} /// <summary>
/// 扩展UriBuilder,让导航支持复杂对象赋值
/// </summary>
public static void Navigate<TViewModel>(this UriBuilder<TViewModel> uriBuilder, Action<TViewModel> action) where TViewModel :class
{
var navigationService = IoC.Get<INavigationService>();
NavigatedEventHandler navigationServerOnNavigated = null;
navigationServerOnNavigated= (s, e) =>
{
var viewModel = ViewModelLocator.LocateForView(e.Content) as TViewModel;
if (viewModel != null)
{
action(viewModel);
}
navigationService.Navigated -= navigationServerOnNavigated;
}; navigationService.Navigated += navigationServerOnNavigated; uriBuilder.Navigate();
}
}
}

【WP8】扩展CM的INavigationService方法的更多相关文章

  1. ORA-01652:无法通过128(在表空间temp中)扩展temp段 解决方法

    ORA-01652:无法通过128(在表空间temp中)扩展temp段 解决方法 (2016-10-21 16:49:53)   今天在做一个查询的时候,报了一个"ORA-01652无法通过 ...

  2. Easyui扩展或者重载(方法和属性)

    1: 使用$.fn.datagrid.defaults.editors重载默认值. 每个编辑器都有以下方法: 名称 属性 描述 init container, options 初始化编辑器并返回目标对 ...

  3. php安装扩展的几种方法

    转自:http://doc3.workerman.net/appendices/install-extension.html 安装扩展 注意 与Apache+PHP或者Nginx+PHP的运行模式不同 ...

  4. Scala中使用implict 扩展现有类的方法

    Scala中implict的一种用法就是扩展现有类的方法,有点类似于.Net中的扩展方法(MS对扩展方法的介绍:扩展方法使你能够向现有类型“添加”方法,而无需创建新的派生类型.重新编译或以其他方式修改 ...

  5. Python扩展之类的魔术方法

    Python中类的魔术方法 在Python中以两个下划线开头的方法,__init__.__str__.__doc__.__new__等,被称为"魔术方法"(Magic method ...

  6. PHP Socket(套接字连接)扩展简介和使用方法

    PHP socket扩展是基于流行的BSD sockets,实现了和socket通讯功能的底层接口,它可以和客户端一样当做一个socket服务器. 使用这些函数时请注意,虽然他们中有很多和C函数同名的 ...

  7. UWP 扩展/自定义标题栏的方法,一些概念和一些注意事项

    原文 UWP 扩展/自定义标题栏的方法,一些概念和一些注意事项 在 Windows 10 的前几个版本中将页面内容扩展到标题栏上还算简单,主要是没什么坑.直到一些新控件的引入和一些外观设计趋势变化之后 ...

  8. swap分区扩展的三种方法

    redhat linux swap分区扩展的三种方法 2016-12-26 11:41:08 分类: LINUX 原文地址:redhat linux swap分区扩展的三种方法 作者:quanshen ...

  9. 【WP8】扩展CM的WindowManager

    14-09-09更新:修复AppBar冲突bug 关于WindowManager,一直都很想写一篇博客分享一下,一直在忙别的,今天抽空把这个分享一下 在弹窗在移动开发是一个很常见的交互,很多时候我们都 ...

随机推荐

  1. spark streaming checkpoint

    Checkpoint机制 通过前期对Spark Streaming的理解,我们知道,Spark Streaming应用程序如果不手动停止,则将一直运行下去,在实际中应用程序一般是24小时*7天不间断运 ...

  2. git学习相关的博客地址

    Git分支管理策略: http://www.ruanyifeng.com/blog/2012/07/git.html Git 使用规范流程: http://www.ruanyifeng.com/blo ...

  3. 【WPF】右键菜单ContextMenu可点击区域太小的问题

    问题描述 正常使用右键菜单ContextMenu时,如果菜单项是不变的,可以直接在XAML中写死,如下是给一个Button按钮添加了右键菜单功能. <Button Content="T ...

  4. <孤独者生存(小小辛巴投资手记)>读书笔记

    书在这里 让投机客梦醒的办法就是让资产损失至少一半 天不会塌下来,世界末日也不会这么快就降临,经济也许会萧条但不会崩溃,人们还得穿衣吃饭.休息劳作 每个笨蛋都会从自己的错误中吸取教训,聪明的人则从别人 ...

  5. [phy]在uboot阶段失能phy芯片

    在uboot阶段power down掉phy芯片 uenvcmd=mdio 0x800; mmc rescan mdio为uboot支持命令 7:phy芯片地址 0:phy芯片工作模式寄存器地址 0x ...

  6. Java编程的逻辑 (54) - 剖析Collections - 设计模式

    本系列文章经补充和完善,已修订整理成书<Java编程的逻辑>,由机械工业出版社华章分社出版,于2018年1月上市热销,读者好评如潮!各大网店和书店有售,欢迎购买,京东自营链接:http:/ ...

  7. vba的一个File操作类

    Option Explicit '-------------------------------------------------------- '[Class name]: clsTxtFile ...

  8. [数据结构]最小生成树算法Prim和Kruskal算法

    最小生成树 在含有n个顶点的连通图中选择n-1条边,构成一棵极小连通子图,并使该连通子图中n-1条边上权值之和达到最小,则称其为连通网的最小生成树.  例如,对于如上图G4所示的连通网可以有多棵权值总 ...

  9. android 中解析json格式数据

    本文来自http://tonysun3544.iteye.com/category/188238 package com.tony.json; import android.app.Activity; ...

  10. Android训练课程(Android Training) - 测试你的Android Activity

    你应该开始编写和启动测试作为你的android程序开发周期的一部分.写的好的测试能够帮助你更早的发现bug和使你对你的代码有信心. 一个测试用例定义了一些对象和方法的集合,用于启动多样的彼此独立的测试 ...