Ani动态光标格式解析
数据结构:
Ani文件中的数据是按区段存放的,区段数据结构如下:
标识符(4字节ASCII),数据长度(一个DWORD),数据
按照此规则来看Ani文件,文件起始12字节可以理解为标准文件头,除数据长度外,其余两个字段不会改变:
0x0000 52 49 46 46 标识符'RIFF'
0x0004 40 4D 00 00 数据长度
0x0008 41 43 4F 4E 'ACON'
标准头之后,就是各个区段了,在我的探索中共发现了:'anih', 'rate', 'seq ', 'LIST'4种区段('seq '区段标识最后一个字符是空格,共4个字符)。
'anih'
此区段数据长度恒为36,里面存储的是一个结构体:
struct _anih
{
DWORD dwHeaderSize; //结构体大小
DWORD dwNumFrames; //图像帧数
DWORD dwNumSteps; //播放帧数,当'seq '存在时可能大于dwNumFrames
DWORD dwWidth; //图像宽度
DWORD dwHeight; //图像高度
DWORD dwBitCount; //色彩位数
DWORD dwNumPlanes; //设备平面数
DWORD dwDisplayRate; //显示频率(Time Delay,单位为1/60秒)
DWORD dwFlags; //标志
};
dwFlags的第0位为1时,表示图像帧数据格式为Icon或Cursor,为0表示图像帧数据为位图raw数据,使用_anih结构中的尺寸、色彩深度等信息。
第1位解释为bool型,表示文件是否含有'seq '段。
'seq '
此区段为可选段(不一定存在),段内的数据为一个DWORD数组,长度为 “区段数据长度” / sizeof(DWORD)。
0x0000 73 65 71 20 标识符'seq '
0x0004 24 00 00 00 数据长度
0x0008 00 00 00 00 数组元素[0],值为0表示此处显示第0帧图像
0x000C 01 00 00 00 数组元素[1],值为1表示第一帧图像
0x0010 02 00 00 00 [2],第2帧
0x0014 03 00 00 00 [3],第3帧
0x0018 00 00 00 00 [4],第0帧
0x001C 04 00 00 00 ...
0x0020 05 00 00 00
0x0024 01 00 00 00
0x0028 00 00 00 00
此区段存储的是播放顺序,当Ani文件播放时,按照DWORD数组下标递增,依次从此数组中取出图像帧号,再到存储图像帧数据的'LIST'段中获取对应的图像帧进行显示。所以在一次播放中,同一个图像帧可以出现多次。_anih结构中的dwNumSteps即为播放起始数组下标。
此区段不存在时,'LIST'中图像帧的顺序即为播放顺序,_anih结构中的dwNumSteps为播放起始帧号。
'rate'
此区段为可选段,段内数据为一个DWORD数组,长度为 “区段数据长度” / sizeof(DWORD)。
0x0000 72 61 74 65 标识符'rate'
0x0004 24 00 00 00 数据长度
0x0008 0F 00 00 00 x 1/60秒 = Time Delay
0x000C 0F 00 00 00
0x0010 0F 00 00 00
0x0014 0F 00 00 00
0x0018 46 00 00 00
0x001C 0F 00 00 00
0x0020 0F 00 00 00
0x0024 0F 00 00 00
0x0028 0F 00 00 00
此区段内存储的为播放频率(Time Delay),同样以1/60秒为单位,当'seq '存在时,按相同下标与'seq '中的每个元素相对应,数组大小与'seq '相等。当'seq '不存在时,与'LIST'中图像帧相对应,数组大小等于_anih结构中的dwNumFrames。
'LIST'
同样拥有12字节“标准头”,探索中发现,此区段内存储的数据有两种可能:
1.Ani文件的名称、作者
2.图像帧数据
当存储名称、作者信息时,格式为:
0x0000 4C 49 53 54 标识符'LIST',前12字节为“标准头”
0x0004 26 00 00 00 数据长度
0x0008 49 4E 46 4F 标识符'INFO'表示此列表为信息列表 0x000C 49 4E 41 4D 标识符'INAM'表示名称
0x0010 0C 00 00 00 数据长度
0x0014 68 65 61 72 74 73 74 69 63 6B 31 00 字符串'heartstick1' 0x0020 49 41 52 54 标识符'IART'表示作者
0x0024 06 00 00 00 数据长度
0x0028 68 75 61 6C 69 00 字符串'huali'
当存储图像帧数据时,格式为:
0x0000 4C 49 53 54 标识符'LIST',前12字节为“标准头”
0x0004 90 11 00 00 数据长度
0x0008 66 72 61 6D 标识符'fram'表明此列表为图像数据帧列表 0x000C 69 63 6F 6E 标识符'icon'标识图像数据帧数据区段
0x0010 BE 08 00 00 数据长度
0x0014 00 00 02 00 图像数据
... ... 多帧图像
至此,数据结构解析完毕。
Ani动态光标格式解析的更多相关文章
- JSON格式解析和libjson使用简介(关于cjson的使用示例)
JSON格式解析和libjson使用简介 在阅读本文之前,请先阅读下<Rss Reader实例开发之系统设计>一文. Rss Reader实例开发中,进行网络数据交换时主要使用到了两种数据 ...
- 虚拟机VHD格式解析到NTFS文件系统解析
本来的需求是XEN下的镜像取证,但这篇仅包括他支持的一种格式,就是VHD,此项目从头开始大概用了两周时间,中间遇到了很多让人头大的问题,光是思考的笔记就写了十几页纸,不过实际上并没有那么难,主要是很久 ...
- configure.ac和Makefile.am的格式解析概述
1. configure.ac和Makefile.am的格式解析概述 1.1. Autotools相关工具链 1.1.1. Autotools 1.1.2. 其他相关工具 1.2. 工具链的流程 1. ...
- plist文件、NSUserDefault 对文件进行存储的类、json格式解析
========================== 文件操作 ========================== Δ一 .plist文件 .plist文件是一个属性字典数组的一个文件: .plis ...
- MySQL binlog的格式解析
我搜集到了一些资料,对理解代码比较有帮助. 在头文件中binlog_event.h中,有描述 class Log_event_header class Log_event_footer 参见[Myst ...
- 转:YUV RGB 常见视频格式解析
转: http://www.cnblogs.com/qinjunni/archive/2012/02/23/2364446.html YUV RGB 常见视频格式解析 I420是YUV格式的一种,而Y ...
- TS格式解析
1.TS格式介绍 TS:全称为MPEG2-TS.TS即"Transport Stream"的缩写.它是分包发送的,每一个包长为188字节(还有192和204个字节的包).包的结构为 ...
- Window下 Qt 编译MySQL驱动(居然用到了动态库格式转换工具)
一步步在Window下开发Qt 今天开始安装MySQL,看了些关于MySQL安装的博文,方法大致相同,但是遇到的细节问题各有不同,或者没有讲全面,下面来说说个人的安装过程及遇到的问题. 1.首先下载, ...
- ABP中动态WebAPI原理解析
ABP中动态WebAPI原理解析 动态WebAPI应该算是ABP中最Magic的功能之一了吧.开发人员无须定义继承自ApiController的类,只须重用Application Service中的类 ...
随机推荐
- WPF DataGrid复制单元格问题
当复制出现 以下错误时:System.Runtime.InteropServices.COMException (0x800401D0),这是在WPF剪贴板程序错误. 解决方法:则在需要在App.xa ...
- OpenSCAD 建模:矿泉水瓶盖
下载地址:https://github.com/ZhangGaoxing/openscad-models/tree/master/BottleCap 代码: module screw(r=){ ::] ...
- springcloud之服务注册与发现(Eureka)
springcloud服务注册与发现 使用Eureka实现服务治理 作用:实现服务治理(服务注册与发现) 简介: Spring Cloud Eureka是Spring Cloud Netflix项目下 ...
- linux root修改密码失败
问题: 当使用root修改密码时,报错passwd:Authentication token manipulation error 解决: 1.查看是否权限问题, /etc/passwd /etc/s ...
- 66、django之模型层(model)--多表相关操作(图书管理小练习)
前面几篇随笔的数据库增删改查操作都是在单表的操作上的,然而现实中不可能都是单表操作,更多的是多表操作,一对一,一对多,多对多的表结构才是我们经常需要处理的,本篇将带我们了解多表操作的一些相关操作.也会 ...
- 双十一临近,怎样让买家流畅地秒杀? ——腾讯WeTest独家开放电商产品压测服务
WeTest 导读 十一月临近,一年一度的电商大戏"双十一"又将隆重出场,目前各大商家已经开始各类优惠券的发放,各类大促的商品表单也已经提前流出,即将流入各个用户的购物车中. 作为 ...
- 轻松学会ES6新特性之生成器
生成器虽然是ES6最具魔性的新特性,但也是最难懂得的一节,笔者写了大量的实例来具体化这种抽象的概念,能够让人一看就懂,目的是希望别人不要重复或者减少笔者学习生成器的痛苦经历. 在说具体的ES6生成器之 ...
- java自动化-juint框架简述
本人使用的是java的juint框架来组织的自动化测试,故我这边需要简单介绍一下juint框架 首先,建议自行百度一下juint框架,先有一个大概的了解 所谓的接口自动化测试,会对多个接口中每一个接口 ...
- Java:什么是面向对象?
1.首先我们去区分对象的属性和方法. 一).什么是对象? 比如:所有的东西都可以叫做对象.而对象就是提供给我们研究对象,这就是对象. 二).怎么区分"属性"和"方法&qu ...
- Ionic3 组件懒加载
使用懒加载能够减少程序启动时间,减少打包后的体积,而且可以很方便的使用路由的功能. 使用懒加载: 右侧红色区域可以省略掉(引用.声明也删掉) 若使用ionic命令新建page,则无需进行下面的操作,否 ...