图4-1 TW_FRAME结构
DG_IMAGE / DAT_IMAGEINFO / MSG_GET操作传达将被传输的图像的其它一些信息。 请注意TW_IMAGEINFO中ImageWidth、ImageLength和TW_IMAGELAYOUT中描述的框架之间的关联。
4.3.2 变更图像属性
通常用户会去选择所要求的属性,但应用程序可能希望在状态4进行初始化。例如,如果用户界面不会被显示,程序则可能希望选取框架。程序可使用DG_IMAGE / DAT_IMAGELAYOUT / MSG_SET操作来定义要获取的区域(框架)。但是并不存在相应的DG_IMAGE / DAT_IMAGEINFO / MSG_SET操作。 TW_IMAGEINFO 域 XResolution YResolution ImageWidth * ImageLength * SamplesPerPixel BitsPerSample BitsPerPixel Planar 性能或相关数据结构 ICAP_XRESOLUTION ICAP_YRESOLUTION TW_IMAGELAYOUT.TW_FRAME.Right - TW_FRAME.Left TW_IMAGELAYOUT.TW_FRAME.Bottom - TW_FRAME.Top ICAP_PIXELTYPE BitsPerPixel 除以SamplesPerPixel ICAP_BITDEPTH ICAP_PLANARCHUNKY PixelType Compression ICAP_PIXELTYPE ICAP_COMPRESSION 注:ImageWidth和ImageLength以像素为单位,而TW_FRAME使用ICAP_UNITS。
4.3.3 解决ICAP_FRAMES、ICAP_SUPPORTEDSIZES和DAT_IMAGELAYOUT之间的冲突
由于有几种方式可用于协商扫描区域,可能难以确定应优先使用哪种方式。一种合理的方案是用设置上一个框架的方式来设置当前框架。不过对于MSG_GET操作而言这三种方式依然难以确定。下列行为是推荐的:
注:框架区域只被ICAP_PHYSICALWIDTH和ICAP_PHYSICALHEIGHT限制,设置ICAP_SUPPORTEDSIZES不会增加新的限制。TWSS_xxxx是只预定义的固定框架尺寸。 若框架由DAT_IMAGELAYOUT设置:
ICAP_FRAMES应以DAT_IMAGELAYOUT调用中设置的框架尺寸来响应MSG_GETCURRENT。
ICAP_SUPPORTEDSIZES应用TWSS_NONE来响应MSG_GETCURRENT。 若当前框架由ICAP_FRAMES设置:
ICAP_FRAMES应以ICAP_FRAMES中设置的当前框架尺寸作为响应。 ICAP_SUPPORTEDSIZES应用TWSS_NONE来响应MSG_GETCURRENT。 若当前固定框架由ICAP_SUPPORTEDSIZES设置,则:
DAT_IMAGELAYOUT应以ICAP_SUPPORTEDSIZES中指定的固定框架尺寸来响应MSG_GET。
ICAP_FRAMES应以ICAP_SUPPORTEDSIZES中指定的固定框架尺寸来响应MSG_GETCURRENT。
4.3.4 ICAP_RETATION,ICAP_ORIENTATION对ICAP_FRAMES,DAT_IMAGELAYOUT、DAT_IMAGEINFO的影响
在尝试处理对当前框架和图像布局的旋转和取向的影响时存在更大的混乱。出于规范化的考虑,约定ICAP_ROTATION and ICAP_ORIENTATION应该在ICAP_FRAMES 和 DAT_IMAGELAYOUT之后应用。
显然取向的改变会影响到输出图形的尺寸,因此DAT_IMAGEINFO中必须予以考虑(状态6)。源报告的作为结果的图像尺寸应考虑当前框架的旋转。
ICAP_ORIENTATION 和 ICAP_ROTATION 是叠加的。最初的框架在从设备下载到源时被ICAP_ORIENTATION修改,体现所扫描的纸张的朝向。然后应用ICAP_ROTATION,得到最终报告给应用程序的框架信息(状态6至7)。结合这两个值的一个可能的理由是使用它们互相抵消。例如,某些内置文档自动传送机的扫描仪可通过将ICAP_ORIENTATION设置为TWOR_LANDSCAPE结合将ICAP_ROTATION设置为90度,来获得更好的性能。因为这将允许用户横向传送它们的图像(传送得更快),然后再通过旋转使采集到的图像重新变为竖向(用户观察的方式)。
4.4 传输多个图像
第3章讨论了单个图像的传输。传输多个图像只是简单地重复单个图像传输的处理过程。在TWAIN下传输多个图像有两类问题:
1. 当会话处于中间图像的边界时传输可处于什么状态?
2. 什么能力可用于支持文档传送机操作?这关系到扫描的高效性。
本段以对单个图像传输过程的回顾作为开始。然后再讨论单个图像传输完毕后应用程序可执行的操作,最后再展示文档传送机。 以下为对单图像传输的简要回顾: 1. 程序启动源,会话状态从4变为5。
2. 准备好图像后,源向程序发送MSG_XFERREADY。
3. 程序使用DG_IMAGE / DAT_IMAGEINFO / MSG_GET和DG_IMAGE / DAT_IMAGELAYOUT / MSG_GET获取将要传输的图像信息。
4. 程序使用DG_CONTROL / DAT_IMAGExxxxFER / MSG_GET操作初始化传输。 5. 传送成功后,源返回TWRC_XFERDONE。
6. 程序发送DG_CONTROL / DAT_PENDINGXFERSR / MSG_ENDXFER操作通知传输结束并获取挂起的传输数量。
如果单个图像传输的背后只是为了将其从源中清除的话,那么一个操作就可以了:
? 发送DG_CONTROL / DAT_PENDINGXFERSR / MSG_ENDXFER操作。正如普通图像传输那样,此操作告诉源程序已经获取完当前图像,并且源报告挂起的传输数量作为响应。
4.4.1 多图像传输的准备
图像传输完成后的DG_CONTROL / DAT_PENDINGXFERSR / MSG_ENDXFER操作有两个重要的功能:
1. 它返回挂起的传输数量(TW_PENDINGXFERS.Count)
2. 若挂起的传输数量大于0,它使会话状态变更为6(准备传输);否则变更为5(源启用)。前面说过当源知道可获取的图像数量时,它返回的数量值为一个正整数;若源不知道可用的图像数量,则返回的数量值为-1。后者在诸如使用了文档传送机的时候可能出现。需要注意的是不知道可用的图像数量也包括了没有可用图像的可能性。请参考DG_CONTROL / DAT_PENDINGXFERSR / MSG_ENDXFER以获取更多相关信息。
我们刚刚了解到MSG_ENDXFER发送后,会话状态可能处于5或6,也就是说会话依然处于活动状态。如果会话处于状态6,则程序可以采取两种行为以使会话状态最终变为5: ? 继续执行单个图像的传输处理过程直至没有更多图像可用。
? 发送一个DG_CONTROL / DAT_PENDINGXFERS / MSG_RESET 清空源中所有挂起的传输。
一旦会话状态返回5,程序就必须决定是停留在状态5还是变更为4。这里有两种可用的方案: ? 程序让源控制未来的状态变更。若源发送MSG_XFERREADY消息,程序重新开始进行多图像传输;如果源发送MSG_CLOSEDSREQ(例如用户激活了源显示的UI上的“关闭”触发器),程序应返回一个DG_CONTROL / DAT_USERINTERFACE / MSG_DISABLEDS使会话回到状态4。
? 程序直接控制会话状态。例如,程序可能希望在当前批次的图像传输完成后关闭,在这上,程序将在没有可用图像后立即发送DG_CONTROL / DAT_USERINTERFACE / MSG_DISABLEDS。
需要注意的是,在当前图像集传输完成后,并没有什么“正确”、“错误”或“首选”的方案可供程序遵照执行。如果程序希望明确地由用户来控制会话的结束,它可以等待源发送
MSG_CLOSEDSREQ给它。另一方面,程序可能非常清楚会话的构成,例如,它可能希望扫
描会话在遇到一张空白纸张时结束。在这种情况下,程序可能希望借助MSG_DISABLEDS来进行控制。
4.4.2 使用文档传送机(Document Feeder)
文档传送机这个名词即可指物理实体上的自动送稿机(例如用于扫描仪的),也可指逻辑上的图像库的传送功能。两种输入机制都适用于下列讨论的内容。此部分的主题是: 1. 对扫描来自文档传送机还是还是platen(滚筒)的页面进行控制。 2. 检测是否有纸张已准备扫描。 3. 控制预扫描。
注意:这些概念适用于没有传送机的扫描仪。 4.4.2.1 选择文档传送机
有时使用文档传送机将改变图像采集的方式。举例来说,当一张纸放置在台板上时,扫描仪需要在纸上移动它的光标,若使用文档传送器,则扫描仪可能使其光标固定而扫描移动的纸张。为应对这种差异,程序和源可明确地同意是否使用文档传送机。此行为的协商必须在状态4(源启用前)下进行。
CAP_FEEDERENABLED
判断源是否有可用的文档传送机,若是,则选择相关设置。
1. 使用DG_CONTROL / DAT_CAPABILITY / MSG_GET 操作来判断源是否支持此性能。TWRC_FAILURE / TWCC_CAPUNSUPPORTED 表示源不支持选择文档传送机。 2. 若支持,则在状态4下使用DG_CONTROL / DAT_CAPABILITY / MSG_SET操作。 3. 将TW_CAPABILITY.Cap设置为CAP_FEEDERENABLED。
4. 创建一个TW_ONEVALUE窗口并置为TRUE,将TW_CAPABILITY.hContainer指向此结构。
5. 执行MSG_SET操作并检查返回值。
若返回TWRC_SUCCESS,则传送机可用,并且您要求使用它的请求已被接受。程序现在可以设置文档传送机的其它性能了。
若返回TWRC_FAILURE 、TWCC_CAPUNSUPPORTED, TWCC_CAPBADOPERATION或TWCC_BADVALUE,则源不支持文档传送机或不允许使用。