Xamarin.Forms学习之Platform-specific API和文件操作
2016-07-10 23:47
309 查看
这篇文章的分享原由是由于上篇关于Properties的保存不了,调用SavePropertiesAsync()方法也不行,所以我希望通过操作文件的方式保存我的需要的数据,然后我看了一下电子书中的第二十章和需要相关知识的第九章,这篇文章中的内容则是我学习这两章的一点记录和分享,还是那样,有错请留言指正,谢谢!
不同的平台存在着一些特定的API,通过在电子书中两章的学习,实践一下如何调用这些API和将这些API封装成公共的库,供以后的项目调用。以一个显示平台信息的小实例开始做一个简单的演示,其运行效果如下:
C#代码如下(就是电子书中的实例,只不过只有IOS和Android的):
记得在程序集中添加对Mono.Android和Xamarin.IOS的引用。
也许只有这一个,你看不出很麻烦,但是如果你要调用更多的特定的API,那么可以想见,你的代码中将会有许多的“#if__IOS__xxxxx#elif__ANDROID__xxxxxx#endif”这样的代码,那能不能把这些特定的API封装在其相应的平台,实现分平台的调用呢,当然是可以的。。。。。。我就不写其他的废话,就是通过DependencyService来实现的,直接上代码:
添加如上图所的接口和类(Sorry,下面那个箭头搞错了)
记住DependencyService和Dependency的命名空间是Xamarin.Froms,我开始没注意就被坑了。IOS的代码没有什么变化,就是命名空间变了,就不贴出来了,我也没写。。。
当你看到“assembly:Dependency”这个的时候,你也许就联想到了反射--是的,就是通过反射。建议大家在实现相关的功能是首先使用DependencyService,至于原因我就不用我蹩脚的英语给大家翻译了,直接上原文:
DependencyServiceisnottheonlywaytoimplementplatform-specificcallsinaPCL.Adventurousdevelopersmightwanttousedependency-injectiontechniquestoconfigurethePCLtomakecallsintotheplatformprojects.ButDependencyServiceisveryeasytouse,anditeliminatesmostreasonstouseaSharedAssetProjectinaXamarin.Formsapplication.
不同的平台存在着一些特定的API,通过在电子书中两章的学习,实践一下如何调用这些API和将这些API封装成公共的库,供以后的项目调用。以一个显示平台信息的小实例开始做一个简单的演示,其运行效果如下:
C#代码如下(就是电子书中的实例,只不过只有IOS和Android的):
<?xmlversion="1.0"encoding="utf-8"?> <ContentPagexmlns="http://xamarin.com/schemas/2014/forms" xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml" x:Class="App3.Views.DisplayModelAndVersion"> <StackLayoutPadding="20"> <StackLayoutVerticalOptions="CenterAndExpand"> <LabelText="DeviceModel:"/> <ContentViewPadding="10,0,0,0"> <Labelx:Name="modelLabel" FontSize="Large" FontAttributes="Bold"/> </ContentView> </StackLayout> <StackLayoutVerticalOptions="CenterAndExpand"> <LabelText="OperatingSystemVersion:"/> <ContentViewPadding="10,0,0,0"> <Labelx:Name="versionLabel" FontSize="Large" FontAttributes="Bold"/> </ContentView> </StackLayout> </StackLayout> </ContentPage> #if__IOS__ usingUIKit; #elif__ANDROID__ usingAndroid.OS; #endif namespaceApp3.Views { publicpartialclassDisplayModelAndVersion:ContentPage { publicPlatInfoSap1Page() { InitializeComponent(); #if__IOS__ UIDevicedevice=newUIDevice(); modelLabel.Text=device.Model.ToString(); versionLabel.Text=String.Format("{0}{1}",device.SystemName, device.SystemVersion); #elif__ANDROID__ modelLabel.Text=String.Format("{0}{1}",Build.Manufacturer, Build.Model); versionLabel.Text=Build.VERSION.Release.ToString(); #endif } } }
记得在程序集中添加对Mono.Android和Xamarin.IOS的引用。
也许只有这一个,你看不出很麻烦,但是如果你要调用更多的特定的API,那么可以想见,你的代码中将会有许多的“#if__IOS__xxxxx#elif__ANDROID__xxxxxx#endif”这样的代码,那能不能把这些特定的API封装在其相应的平台,实现分平台的调用呢,当然是可以的。。。。。。我就不写其他的废话,就是通过DependencyService来实现的,直接上代码:
添加如上图所的接口和类(Sorry,下面那个箭头搞错了)
publicinterfaceIPlatformInfo { stringGetModel(); stringGetVersion(); } publicclassPlatformInfo { IPlatformInfofileHelper=DependencyService.Get<IPlatformInfo>(); publicstringGetModel() { returnfileHelper.GetModel(); } publicstringGetVersion() { returnfileHelper.GetVersion(); } } [assembly:Dependency(typeof(App3.Droid.PlatformInfo))] namespaceApp3.Droid { classPlatformInfo:IPlatformInfo { publicstringGetModel() { returnstring.Format("{0}{1}",Build.Manufacturer,Build.Model); } publicstringGetVersion() { returnBuild.VERSION.Release; } } }
记住DependencyService和Dependency的命名空间是Xamarin.Froms,我开始没注意就被坑了。IOS的代码没有什么变化,就是命名空间变了,就不贴出来了,我也没写。。。
当你看到“assembly:Dependency”这个的时候,你也许就联想到了反射--是的,就是通过反射。建议大家在实现相关的功能是首先使用DependencyService,至于原因我就不用我蹩脚的英语给大家翻译了,直接上原文:
DependencyServiceisnottheonlywaytoimplementplatform-specificcallsinaPCL.Adventurousdevelopersmightwanttousedependency-injectiontechniquestoconfigurethePCLtomakecallsintotheplatformprojects.ButDependencyServiceisveryeasytouse,anditeliminatesmostreasonstouseaSharedAssetProjectinaXamarin.Formsapplication.
现在我们继续说说如何把这些设置成公共的库,便于以后的项目调用,其实很简单,就像我们新建一个Xamarin.Froms项目一样,新建一个Xamarin.Platfrom.Tools项目,然后把上面PlatformInfo相关的类和接口再写一遍,建议再添加一个Init的cs文件,代码中不用实现什么具体的东西,其功能就是确保dll正确的加载了。
对于文件的操作,电子书中有个小标题“Goodnewsandbadnews”,当中的主要内容就是告诉大家操作文件的是System.IO命名空间(该命名空间下还有个FileInfo类)下的File类在Android和IOS是可以共用的,但是在Windows的三个平台不行,最明显的一个区别就是Windows的三个平台的文件操作是异步的,做过WP开发的应该知道。鉴于目前的移动端的情形,和使用Xamarin开发的主要需求,那个”badnews“我们基本可以忽略了(开发Windows的还是用UWP吧)。
在移动端,基本上都包含一些基本的文件夹,比如Pictures、Music等这些都是公共的,而APP所访问的文件夹和文件还有一个限制,在WP开发中有个名词叫“隔离存储”或者“独立存储”,IOS和Android我并没有太多的接触,但这方面应该都是大体相同的,所以每个应用程序都除了能访问前面说的公共的文件夹和文件之外,都只能访问自己的程序“域”下面的文件夹和文件,做过移动开发或者了解移动开发的应该都知道。对于这些文件夹,Xamarin定义一个SpecialFolder的枚举,其中的MyDocuments就是我们自己的APP才能访问的。通过下面的示例继续:
添加如上图所示的红色箭头的类和接口,代码如下(限于文章的篇幅,我就不贴整个代码,只上GetFiles的):
namespaceApp3.TestFile { publicinterfaceIFileHelper {IEnumerable<string>GetFiles(); } } namespaceApp3.TestFile { publicclassFileHelper { IFileHelperfileHelper=DependencyService.Get<IFileHelper>(); publicIEnumerable<string>GetFiles() { returnfileHelper.GetFiles(); } } }
[assembly:Dependency(typeof(App3.Droid.FileHelper))]
namespaceApp3.Droid
{
classFileHelper:IFileHelper
{
publicIEnumerable<string>GetFiles()
{
//Sortthefilenames.
//stringpath=GetDocsFolder();
//IEnumerable<string>filenames=
//fromfilepathinnewList<string>{path}
//selectfilepath;
IEnumerable<string>filenames=
fromfilepathinDirectory.EnumerateFiles(GetDocsFolder())
selectfilepath;
returnfilenames;
}
stringGetDocsFolder()
{
returnEnvironment.GetFolderPath(Environment.SpecialFolder.MyDocuments);
}
}
}
至于XAML呢么就是一个简单的ListView,这个倒没什么说的。大家自己试一试吧。
这里的文件操作能满足我们许多的需求了,但是有时候我们在项目中添加一个图片、文件或者其他的,该怎么办呢。。。下次再说操作本地文件的事吧!
其实最开始的那版文字描述更通顺一些,结果出去吃了饭,回来发现没有自动保存,而且以前写的忘了,然后又重新写了,现在自己读了一次。。。
对了,.netcore发布了,最近也在摸索,相比于Xamarin,分享和关注的人也更多,学习起来还是很方便的,上周自己也买了一个最便宜的阿里云的在玩,无语啊,linux也成必学的了,伤心~共勉!
相关文章推荐
- java操作mysql数据库时乱码
- Java开发工具之Eclipse
- LeetCode:Sum of Two Integers
- 用LinkedList链表模拟 堆栈、队列 两种数据结构
- ThinkPHP3.2.3 分页带入查询条件 JS重写
- 《机器学习》周志华习题4.4答案
- Android TV开发
- stagefright框架下的awesomeplayer设置数据源阶段
- [51nod]1019 逆序数
- Fiddler调试工具
- 手游页游和端游的服务端的架构与区别
- Codeforces 431C k-Tree (基础dp)
- Swift之旅 1 变量、常量和声明
- hdu 1002
- CM 11.0 13.0 源码编译过程
- poj3274 hash
- hdu-4263-最小生成树
- 追求代码质量: 用 AOP 进行防御性编程
- Frameworks , cat,kafka
- Maven常用