AssortedWidgets, 我的开源界面库
最近很少写博,一直在埋头编程。下面隆重推出一直埋头编写的AssortedWidgets——我的开源界面库。可能会用在我的下一版pillow中。
我曾经多次在博客的日志中提到了我对选择C++的界面库犹豫不决,似乎每一款现成的界面都不尽人意。前段时间发现www.bramstein.nl上面的基于OpenGL和SDL的界面库,从它的介绍上看,和我理想中的界面很一致,比如有java swing的代码风格,可以自定义外观等等。但是因为它是一个刚刚开始的工程,所以很多东西都不完善,所以如果我打算用这个界面的话,势必还要自己写很多的东西。而且看过它的代码之后,觉得很多东西还是不理想。我觉得与其把时间浪费在比较不同的界面上,不如干脆按照自己的想法来实现一个界面库。这样,我的AssortedWidgets计划就产生了。起AssortedWidgets这样一个名字是因为有一天吃巧克力的时候看到它盒子上写的Assorted Chocolate。程序至今已经写了两个多星期了。
AssortedWidgets的特色:
开源,BSD协议。
类似C#的delegate代码风格。
可以自定义界面的外观。
有跨平台的可能(OpenGL和SDL)。
可以替换其它的io库(目前用的SDL,但是应该可以替换成glut)。
AssortedWidgets目前支持:
控件:Button, Label, Text Field, Drop List, Check, Radio, Menu, Progress Bar, Slider
容器:Scroll Panel, Panel, Dialog
布局:Flow Layout, Border Layout, Gird Layout
以下是目前演示程序的截图效果,程序在我的网络硬盘中可以下载:
下面是我关于界面的一些思考,想到什么写什么,没有什么调理:
1、好的界面应该提供给用户自定义外观的可能。这种可能应该是代码级别上的,而不仅仅是支持自定义外部的皮肤文件。这样做的好处就是可以让界面满足任意的外观需要。要做到这一点,界面库应当将程序的绘制部分和处理消息,场景管理的部分分开。在界面外观的问题上,不同的程序有不同的追求,像wxWidgets就希望它的程序能和操作系统的外观尽量一致。同样的一个wxWidgets程序,在xp上运行就是xp的样子,在苹果上运行就是苹果的样子。我觉得这样的设计是好的,但是不应该把它限制死,毕竟不同的使用者有不同的需求。在我的AssortedWidgets中,我定义了一个抽象的类,叫做绘制引擎,任何实现了这个类的类都可以担负绘制界面的工作。这个绘制引擎是唯一负责和绘制有关工作的类。因此它也是唯一能出现OpenGL函数的地方。如果有人希望把AssortedWidgets搬到DirectX上去,他就可以利用DirectX的函数来实现一个自己的绘制引擎。总之我觉得把绘制单独出来可以最大限度保证程序的灵活性。
2、界面的布局用程序代码来定义,不要用外部文件。用一种外部文件来定义程序的布局好像是最近比较时兴的。CEGUI就支持XML的布局文件,直接编辑好一个XML,再在程序里面调用就可以得到一个对话框之类的东西。另外还有一些编辑GTK+的工具,最开始都是直接生成代码的,到后来变成生成文件。有的wxWidgets编辑工具也一样。我不喜欢这样,因为这样的外部文件会使得最后的程序很累赘,另外效率也受一些影响,而且存在文件被别人改动的可能。最关键的就是有时候写xml太麻烦了。
3、通过边界盒来检测鼠标。我觉得边界盒的方法是最直接和高效的检测鼠标是否在某个位置的方法。在 的那个界面的作者写了一篇文章介绍在OpenGL中最常用到的检测鼠标的方法,有边界盒发,投影射线法,还有颜色拾取法。在他的界面程序中,他用的颜色拾取法。我觉得很奇怪,这个是我在做pillow的3D拾取的时候用到的方法,界面既然都是2D的,觉得没有必要。用颜色拾取的方法倒是一劳永逸,但是效率不高,而且这样一来在非绘制的程序中势必要夹在一些OpenGL的函数,我觉得这样不好。我写过邮件问那个作者,为什么用颜色拾取。他说他有什么3D界面,只能用颜色拾取。我当时不明白他说的3D界面是什么东西,现在想起来估计是他把界面绘制到一个贴图上,再把贴图贴到3D物体上面。
4、最好是java的代码风格。我最早接触的面向对象就是java,一直觉得很方便。后来适应了wxWidgets那种mfc风格之后,觉得也还行。不过java的另一个好处就是有很多方便的布局管理器。但是在C++里面,完全模仿java swing也有不方便的地方,我之前写过了。所幸后来发现了FastDelegate这个东西,现在实现的是类似C#的方式。
5、场景应该组织成树的结构。场景组织成树的好处就是可以尽快地检测到鼠标碰撞。比如说首先确定鼠标在一个对话框中,那它只可能和这个对话框中包含的控件发生碰撞,而不在这个对话框中的就根本不用考虑了。但是这样也有问题,有些控件的外形会变化,比如说菜单栏和下拉列表都会展开,展开之后可能会超出包含它的对话框,这样超出的部分就不可能响应鼠标了。这是我最开始没有考虑周全的地方,后来只好对这类控件单独处理,绕了一些弯子。
5 comments:
界面的色彩清亮多了,你调整了?你说的也许是对的,界面的底色深一些,这样3D的作品的颜色就可以鲜明、突出一些。
请问一下可以用纯OPENGL而不用SDL吗,不喜欢SDL的那些dll
opengl是跨平台的,从这点上你就知道不能光用纯的opengl了,怎么也要和你的平台建立联系。你可以用mfc,也可以用sdl,也可以用glut,或者找个其他的图形界面库,总之用一样。sdl存在是有道理的,跨平台而且比用别的方便,至少我觉得还不错。glut也不错,没sdl复杂,但是也要dll。
那么SDL和GLUT相比较有什么优劣呢?呵呵,我是菜鸟,只是稍有接触,请别见笑.
ps:你的界面库风格真的很不错,不愧是学图形出身的,赞一个:)
glut简单一点,但是功能相对少一点。比如sdl里面处理音效的东西glut就没有。但是glut用起来真的很简单。之所以我用sdl是因为我觉得sdl的输入输出控制要比glut功能强一点。如果就是要写简单的程序,glut应该是首选。
Post a Comment