在界面开发中,目前DirectUI是个热门的技术名称,因为众多的知名公司都是用DirectUI方式作出了很炫丽的界面。而对于大多数熟悉Win32控件,熟悉MFC开发的开发人员来说,我们应该做何选择?

因为传统的Win32/ MFC大家都比较了解,所以首先我们分析DirectUI,看看DirectUI能完成哪些普通Win32控件难以实现的功能,同时实现一个完整的DirectUI有那些关键点。

 基于DirectUI技术的界面库的优势

以下是我们总结的一个完善的DirectUI库的优势,这些特性Win32控件方式难以实现的:

  1. 界面完全换肤 
    这里的“界面完全换肤”,是指用户可完全定制化的换肤,软件界面控件大小,位置等都可能有变化等。DirectUI界面库一般都是用XML定义界面虚拟控件并直接布局界面,因此可以实现此功能。但实际上完全的换肤涉及到很多问题,目前很少有界面库产品可以实现这种完全换肤。从界面设计的发展来看,目前已经不流行这种界面的完全换肤,因为这不仅对技术要求比较多,同时也对UI设计要求很高。目前界面换肤大量采用的是更换色调局部的背景更换(如MSN/QQ最新版本)。
  2. 理论上更高的效率 
    由于在DirectUI控件中,更多的控件为逻辑上的虚拟控件。因此理论上来讲DirectUI运行效率会更高一些,但这个效率也与DirectUI界面库整体的软件架构及软件实现有密切关系。在实际考虑时,效率问题应该不是关注的重点,因为目前设计及实现良好的Win32 界面库在效率方面也没有任何问题。
  3. 容易实现更加炫丽的动态效果 
    由于DirectUI的技术特点,使其更容易实现一些特效的动画效果,如菜单的动态徐徐展开和收缩,窗口的动态渐隐渐显的弹出和关闭,控件的动画展开和关闭。当然以上这些特性也取决于开发团队的技术实力,同时也需要顶尖优秀的UI设计师配合,方能带来所期望的炫丽效果。 
  4. 防止软件被破解,防外挂 
    关于这一点,可能是众多关注DirectUI的人没有考虑到的。但实际上恰恰是这一点可能是最为关键的。众多知名互联网公司不遗余力研发DirectUI界面,这一点也是重要考量。传统的Win32控件由于其消息、原理公开,使得通过一些简单的Hook或其他方式可以很容易破解软件。而一个完全的DirectUI界面,其界面元素及内部逻辑完全为私有实现,外界无从得知。这就使得破解变得困难的多。
  5. 界面与逻辑的完全分离(需要完整脚本支持)

    在说明这个问题前,我们来了解这个基本问题: 

    什么是界面与逻辑的分离?

    界面是指涉及界面元素操作的部分代码,比如控件位置大小,控件的状态;窗口的大小;控件界面的绘制代码;控件的动态创建。 
    逻辑是指软件的程序逻辑,与界面操作完全无关,如网络操作,内部事件与消息。 
       
            在Win32控件或者MFC等设计里,实际上是将界面和程序逻辑完全糅合在一起,这样做的缺陷在于如果界面UI设计有一些改变,我们可能要大面积的修改程序代码并重新编译,同时程序也难以重用,我们可能需要重载好多类如CCongfigButton,CSettingButton,CXXXButton等。每一个新的界面效果的增加,我们都需要去修改程序,添加支持。 
            目前来说,基于Win32的大部分界面库已经能最大限度的分离界面与逻辑,最主要的是将界面控件的绘制代码分离出去,使得应用程序变得更加清晰,更加容易维护,容易重用;也能很容易适应界面UI设计的变化。

    什么是界面与逻辑的完全分离? 
    完全分离是指程序中不出现任何界面控件元素属性的相关操作,如调整界面控件位置,控制控件的显示/隐藏。即在不重新编译程序的情况下,仅通过修改界面配置文件(XML)和脚本文件,即可加载一个新的界面效果。

    理论上来说,Win32控件库不能做到界面与逻辑的完全分离。比如MFC框架,更是将界面与逻辑完全融合在一起。这也是很多大的互联网公司花重金研发完全的DirectUI界面引擎的原因,这类公司基本都是快速开发模式,产品更新快,界面UI设计更新快,常常一个软件开发出来,皮肤已经换了好几套了,界面调整无数次了。如果采用传统的方式,这里面会带来巨大的工作量及重复工作。

以上几点是一个基于DirectUI技术的界面库可以实现的,但基于Win32控件的界面库难以实现的。但同时我们也会发现,还没有一个通用的DirectUI界面库产品中实现以上所有特性;即DirectUI的真正优势还未能在实践中实现。以下的关键点是一个完整,通用的DirectUI界面库难以实现的原因。

  DirectUI界面框架开发的关键点(或者称为难点)

  1. DirectUI界面库整体架构设计 
            一个完整的DirectUI界面库,可以等同于一个Mini的QT、WPF,Flash等。需要一整套的系统级别的架构,而不仅仅只是界面元素的绘制。这个架构非常重要,同时也对软件架构师有非常高的要求。
  2. 完整的事件响应模块 
          Win32控件的事件很多,而一般的DirectUI界面库指实现基本的几个事件如单击,mouse in, mouse leave。其他一些事件如双击,右键,滚轮这些,也许不常用,但如果不能提供这些事件,会是一个比较头疼的问题。
  3. 复杂控件的支持 
         复杂控件的支持也是众多DirectUI界面库的软肋。复杂的控件如Menu,list control,tree control,Edit等,也许实现起来必须并不复杂,但要实现一个可完全替代Win32标准控件的控件就比较麻烦了。这涉及到三个方面:  
        功能特性的完整性 
        很多DirectUI提供商实际上只实现了部分的功能就宣称支持某某控件,这种说法是不负责任的。例如树形控件,其涉及的接口函数有40多个,Notify消息有20多个。这些函数和消息中,可能常用的只有小部分,但其他不常用的也是不能忽略的。  
       效率问题 
        拥有这个功能的实现,不一定代表能广泛通用。是否能承受大数据量的插入?是否保证内存的占用问题?这些都是我们在测试一个自绘控件需要考虑的问题。 另外也需要保证在自绘模式下的效率问题。
  4. 剪贴,拖拽,热键快捷键等 
           Windows标准控件我们用了好久了,但其中很多我们非常常用的功能,会常常被的DirectUI的设计者忽略。也许正因为这些功能太平常,太常用了,所以容易被人忽略。如剪贴,拖拽,热键,快捷键,tooltips等。这些功能特性也是不能缺少的,因为太常用了!
  5. 界面样式多样性的支持 
          目前有些DirectUI类的产品在控件设计时只是模仿MFC等相应控件的API。例如: 
    ListView::SetItemImage函数,用来为list的一个item设置图片。但实际上当前软件界面中,设置一张图片是远远不够的,一般Item中不仅需要根据程序逻辑动态显示多个图片,而且还需要显示一些可以响应事件的图片,如QQ好友列表树。对于DirectUI类产品来说,应该对这些提供完整支持,而不是仅仅提供一个自绘结构,让用户自己来处理。
  6. 高效灵活的自绘机制 
        当前的软件界面控件的样式是多样的,需要有灵活高效的自绘机制来保证。 
         Windows标准控件提供了非常灵活的自绘处理,我们可以在WM_PAINT,WM_ERASEGRND等消息中绘制自己的界面。同时对于Button,Menu,List Control,Tree Control, list Box等控件,微软提供WM_DRAWITEM, CustomDraw 等机制,使得我们可以随心所欲的绘制item内容。而各种情况下的效率则由标准控件内部保证。我们只需要在OnDrawItem等消息中绘制item内容即可。 
         众观所有UI框架,QT,WPF等都提供了完整的自绘机制。如QT甚至提供了CSS等方式来配置界面。足以看出灵活的自绘机制对一个界面产品的重要性。如果DirectUI类界面库不能提供一种高效,灵活的自绘机制,则无法满足软件对界面库的基本需求。
  7. 与脚本语言的整合        
           我们坚持认为一个完整的DirectUI界面库应该提供完整的脚本支持。如果将内部的XXLabel, XXButton, XXProgress,  XXSliderCtrl等内部类或结构暴露给界面库的使用者,则势必带来界面和逻辑的重新糅合,同时使得应用程序变得深度依赖界面库,带来很多不稳定因素。如无法将界面和逻辑很好的分离,DirectUI就变得没有意义。 

    一些知名的互联网公司不但在自己的DirectUI系统中深度整合脚本语言,在脚本语言的选择上也在变化,之前常用的是vbscrip/jsscript语言,目前多使用lua脚本语言,lua脚本为开源项目,其特点是灵活,高效,容易扩展。

  与DirectUI界面库相比,DSkinLite界面库的优势

  1. 对开发人员界面开发能力要求低 
    如上面所描述的,由于目前还未有一个完整的DirectUI类型界面库,大多数情况我们需要在DirectUI界面库的源码上做开发,这对参与二次开发的人员有很高要求,需要对界面开发的各方面有所积累。而DSkinLite界面库主要基于Win32控件,封装完整,无需开发人员熟悉界面开发,同时我们设计时非常重视界面库的易用性,对MFC,WTL,Win32控件有些基本了解的开发人员即可胜任。
  2. 可迅速实施到项目中 
    如果已有VC项目,使用DSkinLite这类Win32控件库,可以很容易整合到现有项目中,基本无需修改已有程序逻辑。对于新的项目由于省去了整合并扩展DirectUI框架的工作,使用DSkinLite也会比较快。
  3. 项目风险小,投入少 
  1. 由于一个完整的DirectUI库相当于一个新的GUI Framework框架,这样DirectUI界面库本身在架构设计,程序代码质量等方面会给项目带来新的风险。同时需要对项目增加相应的界面开发人员,用以维护DirectUI界面库产品。而基于Win32控件的DSkinLite界面库没有方面的问题。
 
 
网友说:
虽然时间过去很久了,仍旧觉得写得很有道理,目前我认为WPF的机制是已知的最好的UI解决方案,只是效率上还需要再提高些,单纯的界面怎么都好画,但与数据表现关联起来,难度陡增10倍,那些所谓的开源UI库,仅仅能提供视觉上的炫酷,关联和处理数据,实时响应底层数据变化还差得远。
 
回答: 其实比较大的数据完全可以用别的数据控件来做,目前还是能实现的;如某界面库下的  Girdctrl是能够实现的。
 

DirectUI/DirectUser是一个用户界面框架(http://msdn.microsoft.com/en-us/library/system.windows.automation.automationelement.automationelementinformation.frameworkid.aspx)。用Spy++可以在MSN Messenger、Windows XP、Office、IE和Windows Media Player中看到窗口类名字是DirectUIHWND的窗口。

从文件描述来看,DUI70.dll和DUser.dll看起来是这个框架的实现文件,而没有导入这些DLL的软件应该是复制了这个库的代码。举例来说,Windows Vista和IE7的测试版的IEFrame.dll导入了DUser.dll(http://social.msdn.microsoft.com/Forums/en-US/windowsuidevelopment/thread/6b801577-1699-4093-8a58-198c64b120e0)而正式版使用IEUI.DLL。这应该是微软不愿意公开支持这个功能变化频繁的类库,而反垄断案禁止非Windows组件调用未公开Windows API的缘故。

再看看DUser.dll的函数导出表(http://www.webtropy.com/articles/dll-api.aspx?dll=duser),可以看到Gadget这个词被广泛使用,而没有具体的控件。因为没有窗口句柄,所以控件不是用的窗口类来区分,而是可能和Windows Vista Sidebar Gadgets一样采用HTML做接口根据Office Communicator的资源来看,是使用XML做接口。

从这个类库的名字和行为来看,实际上应该是基于DirectX,和WPF类似的界面类库框架。在微软的招聘网站上可以看到Office Communications项目组的一个职位的介绍中描述说“Native Win32/64 UX experience via DirectUI, and Web UX experience via Silverlight”,说明这个项目组把它和Silverlight同等对待。DirectUIHWND窗口可以在需要性能和安全性的场合看到,例如IE的Tab窗口、Shell中的DefView、Windows登录界面等等。在Windows Vista上使用DirectUI的微软程序和WPF程序一样兼容Desktop Composition和远程桌面,应该是直接或者间接调用的Direct3D。

那么我们怎么做到类似的效果?

无窗口模式的用户界面并不是一个新的概念(http://blogs.msdn.com/oldnewthing/archive/2005/02/11/371042.aspx),Visual C++的应用程序向导就可以创建无窗口ActiveX。但是做过无窗口模式的RichEdit的实现的人都知道,微软的系统控件集中了各种各样的功能,比如各种快捷键、滚动条、界面风格、Accessibility、用户界面自动化等等,要像IE项目组那样几乎完全实现无窗口并不容易。Raymond Chen在http://blogs.msdn.com/oldnewthing/archive/2005/02/11/371042.aspx提到可以使用DrawThemeBackground和DrawFrameControl这两个API,不过这只对和Windows界面风格一致的程序有用。要是界面不复杂的话,可以简单的集成IE的Trident引擎,比如使用MFC的CHTMLView和CDHTMLDialog,以及Windows Forms的WebBrowser类。这样做的代价就是程序需要牺牲性能和可能在严格的IE安全性配置下无法工作,Visual Studio.Net开始的各种向导、Google Task、Microsoft Outlook、Outlook Express等就是使用的这种方案。

另外一个方案就是集成WPF或者Silverlight。VC项目组在用户调查中发现,需要使用WPF的Visual C++用户大都用C#编写WPF代码再用C++/CLI和非托管代码做接口(http://social.msdn.microsoft.com/forums/en-US/wpf/thread/dd1e31bb-feb4-4d77-b524-42a282f519b1/),所以他们决定致力于改进更多用户使用的功能,例如编辑器的智能感知,而不提供对WPF的支持。Visual Studio 2010就是使用这种方案。

为什么不能使用未公开的API?如果要看惊恐故事的话,可以参考http://blogs.msdn.com/oldnewthing/archive/2003/12/23/45481.aspxhttp://blogs.technet.com/stefan_gossner/archive/2005/07/27/undocumented_API_Part1.aspx

题后话:

*如果微软在产品文档中讨论未公开的API,那么API还是未公开的吗?(http://msdn.microsoft.com/en-us/library/aa140182(office.10).aspx

*Visual Studio代码画廊中有个叫作DirectUI的类库,设计思想和微软的DirectUser库类似(http://visualstudiogallery.msdn.microsoft.com/en-us/1B69C9FE-E422-4799-9EB5-6AC7034C52E1),不过也有人误认为这就是微软用来实现MSN的界面的库。

*IE9将会使用Dierct2D作为渲染引擎,不知道IE项目组在移植完代码之后是否能把控件类库的接口公开。从VC项目组征求下一个版本意见的问题(http://www.surveymonkey.com/s/HDQWGJR)来看,微软也有意开发利用GPU的类库。

 
http://blog.csdn.net/bible521125/article/details/46620959

Direct UI 思想阐述(好多相关文章)的更多相关文章

  1. 深入研究 Win32 结构化异常处理(好多相关文章)

    摘要 就像人们常说的那样,Win32 结构化异常处理(SEH)是一个操作系统提供的服务.你能找到的所有关于 SEH 的文档讲的都是针对某个特定编译器的.建立在操作系统层之上的封装库.我将从 SEH 的 ...

  2. 谈Delphi中SSL协议的应用(好多相关文章)

    摘要:本文主要介绍如何在Delphi中使用SSL协议.一共分为七个部分:(1)SSL协议是什么?(2)Delphi中如何使用SSL协议?(3)SSL客户端编程实例.(4)SSL服务端编程实例.(5)S ...

  3. Delphi从内存流中判断图片格式(好多相关文章)

    废话不多说了,利用内存流来判断文件的格式,其实判断文件的前几个字节就可以简单的判断这个文件是什么类型的文件,例如jpg文件 是 FFD8 (从低位到高位就要反过来 D8FF 下面都是一样)BMP文件  ...

  4. OpenCV图片类cv::Mat和QImage之间进行转换(好多相关文章)

    在使用Qt和OpenCV混合编程时,我们有时需要在两种图片类cv::Mat和QImage之间进行转换,下面的代码参考了网上这个帖子: //##### cv::Mat ---> QImage ## ...

  5. [置顶] Direct UI

    有个坑爹的说法:其实Direct UI只是一个思想,要实现这个思想,还要靠自己. 采用windowless方式用api或gdi实现ui的绘制. DirectUI意为直接在父窗口上绘图(Paint on ...

  6. Spring全家桶相关文章汇总(Spring,SpringBoot,SpringData,SpringCloud)

      因为Spring框架包含的组件比较多,写的博客内容也比较多,虽然有分专栏但是依然不方便查找,所以专门用一篇文章来记录相关文章,会不定期更新. 一.Spring 1.基础内容 Spring介绍 Sp ...

  7. 两篇很好的EPG相关文章

    两篇很好的EPG相关文章 原文地址:http://blog.sina.com.cn/s/blog_53220cef0100pi8j.html 1 基于DVB-SI的数字有线电视机顶盒节目指南的设计实现 ...

  8. 【目录】Newlife XCode组件相关文章目录

    本博客所有文章分类的总目录链接:本博客博文总目录-实时更新  1.Newlife XCode组件相关文章目录  1.Newlife XCode组件资源目录汇总[2013年版]    2.Newlife ...

  9. phpcms 移植【添加相关文章】功能

    添加相关文章功能相当有用,移植一个过来基本上可以实现比较复杂的页面内包含分类功能,做二次开发时可以省下不少力气. 用例:如果一个产品,属于一个厂家,而这个厂家是动态添加的,既不是一个分类,而是一个厂家 ...

随机推荐

  1. Python 字符、整型、列表字典等操作(二)

    在上次课程中简要的讲述了Python的基础常识,现在来详细的学习一下吧! 一.类和对象 面向过程和面向对象 面向过程:C 面向对象:Java.Python等 类和对象的含义: 类,是对事物的抽象,比如 ...

  2. QSplashScreen无法背景透明的解决办法(强制StyleSheet生效)

    setWindowFlags(Qt::WindowStaysOnTopHint | Qt::SplashScreen | Qt::FramelessWindowHint); setAttribute( ...

  3. Python 数据处理扩展包: numpy 和 pandas 模块介绍

    一.numpy模块 NumPy(Numeric Python)模块是Python的一种开源的数值计算扩展.这种工具可用来存储和处理大型矩阵,比Python自身的嵌套列表(nested list str ...

  4. 如何自学 Python(干货合集)

    http://wenku.baidu.com/view/5108f974192e45361066f583.html

  5. [置顶] hdu3018解题报告--也是白话几笔画学习总结

    1.题意 2.分析难点(结合图形) 1.首先说说题意吧...题意很简单...但是一开始很菜的我就很迷惑..在想啊...题目怎么就会有没有连接边的点呢....因为你每次给出一条边..就把 a,b连接啦. ...

  6. 找唯一不出现三次而出现1次的数子O(n)位运算算法

    之前两次那个是异或运算处理.这次以为也是类似.可是没想出来. 高富帅想出来了算法,转为bitset,然后加起来 同样的话 要么0+0+0 要么1+1+1,最后剩下的 能够通过%3 算出0 或1.思想是 ...

  7. Sublime 脚本 配置 (lua 和 JavaScript篇)

    { "cmd" :["C:/Lua/Lua.exe","$file"], "file_regex" :"^(? ...

  8. Java--CyclicBarrier使用简介

    CyclicBarrier介绍 (一)一 个同步辅助类,它允许一组线程互相等待,直到到达某个公共屏障点 (common barrier point).在涉及一组固定大小的线程的程序中,这些线程必须不时 ...

  9. SSH框架总结(框架分析+环境搭建+实例源码下载)(转)

    首先,SSH不是一个框架,而是多个框架(struts+spring+hibernate)的集成,是目前较流行的一种Web应用程序开源集成框架,用于构建灵活.易于扩展的多层Web应用程序. 集成SSH框 ...

  10. android代码控制seekbar的样式

    package com.zte; import android.app.Activity; import android.graphics.Color; import android.graphics ...