本章将会提示GDI句柄的每个细节和这些GDI句柄背后重要的数据结构,你也许对GDI数据结构的细节不感兴趣,但是理解GDI/DirectDraw的内部设计会使你成为知识渊博的程序员。
对于GDI来说,常见的对象包括设备上下文、逻辑画笔、逻辑画刷、逻辑调色板、设备相关位图。因此所有的设备上下文对象都是设备上下文类的实例,所有逻辑调色板是逻辑调色板类的实例。Win32API中的对象可以认为是使用没有数据成员的抽象基类实现的,对象的数据表示对用户程序是完全隐藏的。Win32API提供的信息隐藏大大改善了程序的可移植性。
#指针与句柄
在面向对象语言中创建对象,需要分配一块保存对象成员变量的内存。如果它的类有虚函数,就要再分配一个额外的指针,并将它赋值成指向该类所有虚函数实现例程表的指针。在C++这样的语言中,指向对象的指针很重要。它被传递给该类的所有非静态成员函数,这样才能访问该对象的数据成员,调用正确的虚函数。这样的指针被称为C++中的this指针。
对于Win32API,尽管为每个对象分配了数据块,但微软不想向用户应用程序返回指针。因为指针给出了对象存储的确切位置,指针一般允许对对象的内部表示进行读写操作,而这些内部表示也许正是操作系统想隐藏的。指针还使越过进程地址空间共识对象变得困难。
为了对程序员进一步隐藏信息,Win32对象创建例程一般会返回对象句柄,而不是返回指针。句柄被定义为唯一地标识对象的值,或者是对象的间接引用。
对象指针和句柄之间的映射可由函数Encode和Decode实现可视化。
#基于表格的映射
对象指针和句柄之间的映射最普通的机制是基于表格的映射。 在Win32API中,内核对象是用进程表实现的。内核对象包括