Windows CE 编程的十点忠告 #1 本文是根据作者在Windows CE上编写Raima 数据管理器的经验总结出来的,值得CE开发人 员借鉴。
最近两周我们花了大部分时间将已有的应用程序移植到Microsoft Windows CE中。一般说 来,这个计划不是太难。我们起步于Microsoft Win32代码,当然Windows CE是基于Win32 应用程序接口(API)的。有利的是,我们的应用程序(即Raima 数据管理器)有方便的使 用接口,并包含一个大约由150个子函数组成的库,这些函数都是由C语言写成,可以用来 创建、管理和访问数据库。
按建立应用程序的方式来说,我们原以为将它移植到Windows CE中是一项相对简单的 C语言编程练习。然而,我们不久便遇到好些困难。从粗心大意的错误开始,比如在基于W indows NT 的Windows CE仿真器上使用Microsoft Windows NT库,接着又违背Windows CE 的编程戒律,如"千万不要给Unicode(国际标准组织10646标准)字符分配奇数内存地址" 。
你不能在Windows CE上处理一个ANSI字符串,因为没有操纵它们的库函数。最好的解 决办法是将ANSI字符串转换成Unicode字符串用到H/PC上,然后再将Unicode字符串转换回 ANSI字符串用到PC上。为了完成这些转换,可采用MultiByteToWideChar()和WideCharToM ultiByte () Win32 API 函数。 5. 对于Windows CE 1.0的字符串转换,劈开(hack)
在Windows CE 1.0 版本中,这些Win32API函数还没有完成。所以如果你想既要支持C E 1.0又能支持CE 2.0,就必须采用其它函数。将ANSI字符串转换成Unicode字符串可以用 wsprintf(),其中第一个参数采用一widechar字符串,并且认识"%S"(大写),意思是一个 字符串。由于没有wsscanf() 和 wsprintfA(),你必须想别的办法将Unicode字符串转换回 ANSI字符串。由于Windows CE 1.0不在国家语言支持(NLS)中,你也许得求助于hack,如下 所示:
/* Definition / prototypes of conversion functions Multi-Byte (ANSI) to WideChar (Unicode)
atow() converts from ANSI to widechar wtoa() converts from widechar to ANSI */ #if ( _WIN32_WCE >= 101)
/* 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()函数要容易,因为使用wspr intf()函数更难以限制目标指针所指向的字符串的长度。
第三类函数是Win32函数CompareString()。这个函数类似于第二类函数,但是它允许 你指定当地设置(the locale)作为一个参数,而不是使用现有的当地设置(current loc ale settings)。CompareString()函数允许你选择性地指定两个字符串的长度。你可以将 第二个参数设置为NORM_IGNORECASE,从而使函数比较字符串时不比较大小写。
通常,即使不将第二个参数设置为NORM_IGNORECASE,CompareString()函数也不用来 区分大小写。我们经常用wcsncoll()函数来区分大小写,除非使用当地的字符"C"("C" l ocale)。所以,在我们的代码中,不使用CompareString()函数来区分大小写,而用wcsn coll()函数来区分大小写