作者:马宁

    魅族在经历了两年多的开发后,M8终于上市了。能够被称为iPhone Killer,说明了M8有自身的优势。之前也有朋友问过我,会买一款M8试试吗?我说,不会,除非M8出SDK。今天是个可能破财的日子,因为M8真的出SDK了……

安装

    魅族M8用的是Windows CE的操作系统,所以配置开发环境并不是很难,以前有过Windows Mobile开发经验的人,配置起来不会太难。开发工具使用的是Visual Studio 2005 SP1,需要安装M8的SDK。

SDK下载地址:

http://www.meizu.com/service/downs.html?id=97

官方开发环境配置文档:

http://www.meizu.com/help/sdk.html

    因为官方文档对于开发环境配置介绍得非常仔细,所以,我们在这里就不多废话了。直接进入开发环境。需要注意的是:如果想用到M8界面库的方法,是一定要将LIB文件引入到工程中的。

创建工程

    M8创建工程的方式与Windows Mobile也是极其类似的。在 Visual Studio 2005的主菜单中选择File-New – Project. 在对话框中选择“Visual C++” – “Smart Device”中的“Win32 Smart Device Project”,填写工程名称,选择OK。

Meizu M8 SDK开发初体验_第1张图片

    Welcome界面,不多说了。

Meizu M8 SDK开发初体验_第2张图片

    选择开发平台,安装了魅族M8的SDK后,会在列表中出现M8SDK。选中该项,点击中间的>按钮,将M8SDK添加到“Selected SDKs”中。

Meizu M8 SDK开发初体验_第3张图片

    最后选择应用程序类型,选择“Windows application”,按Finish即可。

Meizu M8 SDK开发初体验_第4张图片

    进入开发主界面后,就和Windows Mobile开发不一样了。我们要先编译一个Sample code

C++开发

    魅族M8的开发,与普通WINCE程序开发最大的不同在于魅族使用了自己的UI类库。这套类库给人的第一印象是,接口简洁,小巧可爱,至少比丑陋的MFC是好多了。细看之下,还是有一些不尽人意的地方,或者说设计时欠考虑。不过,考虑到魅族是家手机厂商,而不是软件公司,设计成这样,已经非常厉害了。必须承认,魅族有高人在。写到这里,忽然有点羡慕魅族的开发人员和架构师,能够白手起家创建一套自己的类库,这不但需要技术,还需要际遇。这么多开发人员,又有几个人有机会从头设计一个类库呢?

    不知道魅族对于这套类库的未来是怎么想的,在我看来,开源也许是一个不错的选择,国内非常缺能够应用于嵌入式系统的轻量级UI类库,QT、MiniGUI大都源自类UNIX、Linux系统,对于Windows程序员来说学习曲线还是比较陡。如果魅族能够开源,或者以某种授权开放这套类库,一则可以解决后续开发乏力的问题,二则可以让这套类库平滑地移植到其他系统上。当然,这条路也是困难重重,需要仔细思量。

    先来说说第一个程序吧,示例程序可以从M8 SDK目录的帮助文件中找到,安装路径在:C:\Program Files\Windows CE Tools\wce600\M8SDK\Samples

    在Meizu M8 MZFC Documentation (CHS).chm文件里,包含示例代码。我选取了Hello MZFC的示例代码,将其拷贝到我创建工程的M8Test.cpp中(该文件名因为工程名不同而不同),替换掉所有的代码。

    在cpp文件的第一行要加上:

   
   
   
   
  1. #include "stdafx.h" 

    然后编译运行,按F5,就可以在模拟器上看到下面的界面了:

Meizu M8 SDK开发初体验_第5张图片 

    需要提醒的是,必须要按照官方文档,在工程里增加相关的LIB文件,编译才可以成功通过。

    看了看代码,没找到WinMain函数,消息循环也被封装在类库中,MZFC走的是MFC的路子,从名字上也能看出这种传承关系。运行人家的代码没意思,还是要自己写点代码才行的。好在代码不难理解,很快就能上手写点东西。

    首先要声明一个Button,叫做MZ_IDC_HELLOBTN。代码如下:

   
   
   
   
  1. #define MZ_IDC_TESTBTN1  101  
  2. #define MZ_IDC_HELLOBTN  102  
  3. // Main window derived from CMzWndEx  
  4. class CSample1MainWnd: public CMzWndEx  
  5. {  
  6.   MZ_DECLARE_DYNAMIC(CSample1MainWnd);  
  7. public:  
  8.   // A button control in the window  
  9.   UiButton m_btn;  
  10.   UiButton m_btnHello;  
  11. …  

    然后在OnInitDialog函数中,增加:

   
   
   
   
  1. m_btnHello.SetButtonType(MZC_BUTTON_ORANGE);  
  2.       m_btnHello.SetPos(100,350,280,100);  
  3.       m_btnHello.SetID(MZ_IDC_HELLOBTN);  
  4.       m_btnHello.SetText(_T("Hello wolf!"));  
  5.       m_btnHello.SetTextColor(RGB(255,255,255));  
  6.        // Add the control into the window.  
  7. AddUiWin(&m_btnHello); 

    这个写法就类似于.NET的风格了,不过需要聒噪几句:ButtonType里既包含颜色,也包含特定用途信息(MZC_BUTTON_DOWNLOAD),不方便未来的扩展,而且用户无法自定义颜色值。这个设计不可取。

    下面是处理Button的点击事件:

   
   
   
   
  1. // override the MZFC command handler  
  2.   virtual void OnMzCommand(WPARAM wParam, LPARAM lParam)  
  3.   {  
  4.     UINT_PTR id = LOWORD(wParam);  
  5.     switch(id)  
  6.     {  
  7.     case MZ_IDC_TESTBTN1:  
  8.       {  
  9.         if(1 == MzMessageBoxEx(m_hWnd, L"You have pressed Exit button, Really want exit?", L"Exit", MB_YESNO, false))  
  10.           PostQuitMessage(0);  
  11.       }  
  12.         break;  
  13.       case MZ_IDC_HELLOBTN:  
  14.             {  
  15.               MzMessageBoxEx(m_hWnd,_T("Hello wolf!"),_T("wolf"),MB_OK,false);  
  16.             }  
  17.       break;  
  18.     }  
  19.   }  
  20. }; 

    中规中矩的处理方式,与Win32程序类似。不过简化了子窗体的概念,将所有控件的ID都放在wParam参数中。如果将来需要扩展Button 的处理事件时,这种架构就比较麻烦了。比如,处理拖拽事件时,动作要通过lParam参数传进来吗?或者,这个OnMzCommand方法只处理Command。

    MzMessageBoxEx函数和MessageBox API一模一样,需要说一句的是,在Sample Code里用的都是L””,表示Unicode。在CE的编程规范里,这种地方应该用_T(“”)的宏来替代。小问题。

    好了,写完这些之后,我们F5一下:

Meizu M8 SDK开发初体验_第6张图片 

.NET CF开发

    如果不使用魅族的MZFC类库,直接创建一个Win32 Application的工程,也能够在模拟器上运行起来,能看到一个传统的空白窗口。这个我就不在这里展示了。不过这个小插曲给了我一个提示,既然Win32 Application能运行,那么.NET Compact Framework呢?

Meizu M8 SDK开发初体验_第7张图片 

    魅族M8是基于WINCE 6.0的。但是,在Visual Studio 2005的C#工程里,没有Windows CE 6.0的模板。所以,我们选择Visual C# - Smart Device – Windows CE 5.0节点,里的Device Application,然后为工程指定个名字。

    进入IDE主界面,我们修改一下窗体的Size,然后在工具栏的Device选择框里,选择部署到“M8SDK Emulator”中。然后在窗体中加入一个Button。

Meizu M8 SDK开发初体验_第8张图片

    再写个“Hello,wolf”的话,就太没品了。所以,我在Button_Click里写了:

   
   
   
   
  1. private void button1_Click(object sender, EventArgs e)  
  2.         {  
  3.             string str = string.Format(  
  4.                 "OS Version : {0}, .NET CF Version : {1}",  
  5.                 Environment.OSVersion.ToString(),  
  6.                 Environment.Version.ToString());  
  7.             MessageBox.Show(str);  
  8.   } 

    获取操作系统的版本信息和.NET CF CLR的版本信息。写完后,F5,第一次运行时,因为要部署.NET CF运行时,时间可能会长一些,少安毋躁。

    正义终将战胜邪恶,M8终将战胜iPhone,.NET CF终将运行在M8上……

Meizu M8 SDK开发初体验_第9张图片

    最后,我们证明魅族M8是运行在Windows CE 6.0上的,.NET CF版本是2.0。尽管界面丑一点。但是这说明,很多.NET CF程序改改界面就可以运行在M8上了。

    最后小抱怨一下,M8的分辨率实在太大了,我们这种还没脱贫,一直用小显示屏的程序员,要想看清M8模拟器的全部,就得把它横过来。所以,写这篇文章的时候,我一直是歪头调试程序的。这是魅族在帮我们治颈椎吗? 

总结

    总体来说,配置M8的开发环境难度并不大,关键是M8采用了不同于传统Win32 API的界面库,所以UI方面的开发还要重新学习。不过有胆量开发自己的控件库,这一点就值得佩服。

    魅族充分利用了微软开发者的Ecosystem,如果说魅族是站在微软的肩上,这句话不为过。不过魅族解决了一些别人没有解决的问题,比如用户界面的问题,可见采用什么技术不重要,关键是要有一颗倾听客户需求的心。建立自己的标准,让别人跟着我的标准一起玩,这才是魅族想做的事情。

    大家都在说魅族M8在学iPhone,如果说界面只是形似,那么现在魅族也逐渐开始神似了。想想iPhone的发展轨迹,在魅族亦步亦趋地有了SDK后,下一步会有什么呢?