初学者另外一个比较糊涂的概念是版本的问题,现在市面上能够见到Windows CE的两代产品,它们的内核分别基于Windows CE 3.0和Windows CE.NET(即4.0)。
微软将今年刚面世的Pocket PC 2003和Smart Phone 2003统称为Windows Mobile 2003,我们大多数时候还是习惯地沿用老称谓。
而市面上经常见到的Pocket PC 2002是基于Windows CE 3.0的平台,而Pocket PC 2003则是基于Windows CE.NET的平台,需要注意的是,Pocket PC 2003的内核是Windows CE.NET 4.2。而SmartPhone2003也是基于Windows CE.NET的。SmartPhone的最初版本是2002,基于Windows CE 3.0的,但是微软没有推出SmartPhone2002的中文版。
清晰了平台与CE之间的关系,解释平台与开发工具之间的关系就很容易了。微软提供给应用程序开发者的工具包括:Embedded Visual Tools 3.0,其中包括Embedded Visual C++ 3.0和Embedded Visual Basic 3.0;Embedded Visual C++ 4.0和Visual Studio.NET。
开发工具的版本号是与Windows CE的版本号对应的。EVC3.0和EVB3.0是用来开发基于Windows CE 3.0平台的应用程序的,比较常见的平台有:Pocket PC 2002、Pocket PC 2000、Palm-size PC、HPC。而EVC4.0是用来开发Windows CE.NET平台的程序的,主要包括Pocket PC 2003和SmartPhone 2003。
Visual Studio.NET针对嵌入式设备开发需要SDE的支持,而VS.NET 2003中包括了SDE,不需要另外安装。Visual Studio.NET开发的程序需要目标平台支持.NET Compact Framework。现在支持.NET Compact Framework的平台有Pocket PC 2002和Pocket PC 2003。这里需要注意的是SmartPhone 2003是不支持.NET Compact Framework的。
EVB开发入门
微软已经宣布EVB不再支持Windows CE.NET,所以EVB的最终版本是3.0。但由于EVB的易上手性和快速开发的特点,在VS.NET横空出世之前,它成为Windows CE平台上快速开发的不二之选。现在EVB仍然适合Windows CE 3.0平台上小型应用程序的快速开发。如果您不是专职的Windows CE程序员,而只是需要在Windows CE平台上开发整个系统的一部分,那么EVB可以让您用很短的时间开发出您想要的程序。
EVB的开发环境的搭建也是十分简单,您可以从微软的网站上下载EVT 2002,其中包含了EVC 3.0、EVB 3.0和Pocket PC 2002 SDK和SmartPhone 2002 SDK。按照提示将EVB和Pocket PC 2002 SDK安装好后就可以进行开发了。SDK中包含模拟器,在没有实际设备的情况下,可以利用模拟器来调试程序。
说这么多,让我们来创建一个EVC的工程。是不是和VC很像,需要提醒大家注意的是,由于嵌入式设备支持的CPU种类很多,我们在选择创建工程类型的同时,也要把该工程所支持的CPU类型选择好。创建工程的过程和VC是一样的。当然不同的平台支持的工程类型是不同的,比如Pocket PC 2003有支持MFC和API的两种工程,而SmartPhone 2003则只有支持API的一种工程。
可以说当我们花了大部分时间将已有的应用程序移植到Microsoft Windows CE中。一般说来,这个计划不是太难。我们起步于Microsoft Win32代码,当然Windows CE是基于Win32应用程序接口(API)的。有利的是,我们的应用程序(即Raima 数据管理器)有方便的使用接口,并包含一个大约由150个子函数组成的库,这些函数都是由C语言写成,可以用来创建、管理和访问数据库。
按建立应用程序的方式来说,我们原以为将它移植到Windows CE中是一项相对简单的C语言编程练习。然而,我们不久便遇到好些困难。从粗心大意的错误开始,比如在基于Windows NT 的Windows CE仿真器上使用Microsoft Windows NT库,接着又违背Windows CE的编程戒律,如"千万不要给Unicode(国际标准组织10646标准)字符分配奇数内存地址"。
/* MultiByteToWideChar () and WideCharToMultiByte() not supported o-n Windows CE 1.0 */ int atow(char *strA, wchar_t *strW, int lenW); int wtoa(wchar_t *strW, char *strA, int lenA);
endif /* _WIN32_WCE >= 101*/
#if (_WIN32_WCE <101)
int atow(char *strA, wchar_t *strW, int lenW) { int len; char *pA; wchar_t *pW;
/* Start with len=1, not len=0, as string length returned must include null terminator, as in MultiByteToWideChar() */ for(pA=strA, pW=strW, len=1; lenW; pA++, pW++, lenW--, len++) { *pW = (lenW = =1) ? 0 : (wchar_t)( *pA); if( ! (*pW)) break; } return len; }
int wtoa(wxhar_t *strW, char *strA, int lenA) { int len; char *pA; wchar_t *pW; /* Start with len=1,not len=0, as string length returned Must include null terminator, as in WideCharToMultiByte() */ for(pA=strA, pW=strW, len=1; lenA; pa++, pW++, lenA--, len++) { pA = (len==1)? 0 : (char)(pW); if(!(*pA)) break; } return len; }
#endif /*_WIN32_WCE<101*/
这种适合于Windows CE 1.0的实现办法比使用wsprintf()函数要容易,因为使用wsprintf()函数更难以限制目标指针所指向的字符串的长度。