Ptex源码学习笔记-2
写入纹理数据:
主要分为五种写入方式:新建纹理、编辑已有纹理、编辑ExtHeader中的指定项、写入元数据和写入指定面的纹理数据。写入过程中数据存在一个临时文件中,在close时才会把临时文件的内容拷贝到指定写入的文件中并删除临时文件。
- 新建纹理。调用对应的open函数,首先应该校验新建的纹理参数是否符合要求,然后用main writer(继承自base writer)写入,基本就是初始化header和ruduce函数的绑定,同时设置压缩方式并新建临时tile文件以供写入。新纹理写入到.new文件,保存时再写入到最终位置。初始化时用到了std::vector.reserve和resize,以前没注意,现在知道,增大时,reserve改变vector的容量(分配空间)并使所有迭代器无效,resize增加元素,减小时,reserve没有减小的功能(可用shrink_to_fit),resize会减小元素数,但不会改变容量,二者对应的大小用capacity和size获取。由于是新建,所以tex参数为空指针,在初始化PtexMainWriter时不会有纹理信息的复制。
- 编辑已有纹理。校验格式后需检查是否已有该文件,如果文件存在,编辑方式根据是否为incremental决定用incremental writer(继承自base writer)或main writer,如果文件存在,则关闭已打开文件后再用reader打开并校验header,否则和新建一样直接用main writer。incremental writer写入的数据不压缩(main writer要压缩,在base writer初始化时设置),从而避免每次保存都要压缩编辑又要解压缩,只在最终保存时压缩一次,提高保存效率。校验header和extended header(不需要用reader打开),通过后移到文件末位准备写入。
- 写入元数据。根据参数的不同,分为添加和复制,复制实际是对添加的一层封装,先校验key的长度和value的大小,如果当前key已存在,则覆盖value,不存在则新建。
- 写入指定面的纹理数据。分写入普通数据和常量数据,main writer和incremental writer写入方式不同:
- main writer
- 写入普通数据时,需校验faceinfo,记录当前面在文件中的位置后,写入面数据,如果有alpha通道,先将数据复制到临时buffer中,然后乘上alpha通道,然后再用临时buffer的数据覆盖原数据,最后,如果需要生成mipmap则生成第一级reduction,默认分辨率大于2x2才能生成,否则所有数据除以uv分辨率的乘积后保存到面的常量区,如果有alpha通道还要再除以alpha值。所有操作完成后释放临时buffer并标记有新数据写入。
- 写入常量数据时,校验faceinfo后,直接复制数据到面的常量区。
- incremental writer
- 写入普通数据时,与main writer大部分过程相似,但是因为要更新header信息,所以多了header写入,但是header的信息要在面数据写入后才能获得,所以先留出header的空间并记录位置,写完面信息后再倒回去写header,最后再把fp移到末尾。
- 写入常量数据时,同样需要写入header,不过因为是常量数据,所以header信息预先知道,所以可以写入header后再写入面数据就完成了。
- main writer
- 关闭文件。main writer和incremental writer的close函数都需要先调用base writer的close函数间接调用各自的finish函数写入新数据,main writer较为复杂,如果已有reader(在编辑的时候会将用reader打开纹理,reader存在说明新添加了纹理),则需要从reader中获取facedata,然后根据是否为常量写入数据(从reader里复制),如果没有reader(说明没有添加新纹理),则直接将缺失纹理的面标记为常量。然后根据需要生存mipmap,标记有常量相邻面的面,更新header的level和face数目信息。然后新建文件,根据ptex规定的存储顺序依次写入数据,注意header、extended header和level的部分信息(header大小和levelinfo)在数据写入完成前是不知道的,所以要预先留空,之后再填上。faceinfo和constdata直接写入新建文件,facedata需要按level写入,每一个level先写leveldataheader,然后再从之前写入的临时文件复制该level的各个面的纹理数据到新文件。所有都完成后关闭新文件(即保存的文件),如果之前是按tile写入的,base writer会在完成后删除tile文件,main writer需要释放reader和删除临时文件(如果有),最后删除原文件,将新文件的文件名(原文件名后面加了.new)改成原文件的文件名(去掉.new)。incremental writer在base writer关闭后关闭fp就可以了。
Ptex源码学习笔记-2的更多相关文章
- Ptex源码学习笔记-1
Ptex是Walt Disney Animation Studios开发的纹理映射工具.在看一个叫appleseed的渲染器时看到他支持这种纹理,所以就查看一下,发现比较轻量,所以就想趁此机会学习下. ...
- Underscore.js 源码学习笔记(下)
上接 Underscore.js 源码学习笔记(上) === 756 行开始 函数部分. var executeBound = function(sourceFunc, boundFunc, cont ...
- Underscore.js 源码学习笔记(上)
版本 Underscore.js 1.9.1 一共 1693 行.注释我就删了,太长了… 整体是一个 (function() {...}()); 这样的东西,我们应该知道这是一个 IIFE(立即执行 ...
- AXI_LITE源码学习笔记
AXI_LITE源码学习笔记 1. axi_awready信号的产生 准备接收写地址信号 // Implement axi_awready generation // axi_awready is a ...
- Hadoop源码学习笔记(6)——从ls命令一路解剖
Hadoop源码学习笔记(6) ——从ls命令一路解剖 Hadoop几个模块的程序我们大致有了点了解,现在我们得细看一下这个程序是如何处理命令的. 我们就从原头开始,然后一步步追查. 我们先选中ls命 ...
- Hadoop源码学习笔记(5) ——回顾DataNode和NameNode的类结构
Hadoop源码学习笔记(5) ——回顾DataNode和NameNode的类结构 之前我们简要的看过了DataNode的main函数以及整个类的大至,现在结合前面我们研究的线程和RPC,则可以进一步 ...
- Hadoop源码学习笔记(4) ——Socket到RPC调用
Hadoop源码学习笔记(4) ——Socket到RPC调用 Hadoop是一个分布式程序,分布在多台机器上运行,事必会涉及到网络编程.那这里如何让网络编程变得简单.透明的呢? 网络编程中,首先我们要 ...
- Hadoop源码学习笔记(3) ——初览DataNode及学习线程
Hadoop源码学习笔记(3) ——初览DataNode及学习线程 进入了main函数,我们走出了第一步,接下来看看再怎么走: public class DataNode extends Config ...
- Hadoop源码学习笔记(2) ——进入main函数打印包信息
Hadoop源码学习笔记(2) ——进入main函数打印包信息 找到了main函数,也建立了快速启动的方法,然后我们就进去看一看. 进入NameNode和DataNode的主函数后,发现形式差不多: ...
随机推荐
- phpinfo有mysqlnd没有mysql
这个着实是个坑,使用phpinfo查看,明明有mysqlnd这个项目,就是找不到mysql.以前用直接运行php.exe的方法可以看到错误,可是这次就没有任何错误. 中间把php的安装路径添加到了系统 ...
- Libevent Not Found Error While Install Tmux
First install libevent using –prefix=$HOME erro:“libevent not found” solve with using this when inst ...
- Dictionary的几种遍历方法
Dictionary<string, int> list = new Dictionary<string, int>(); list.Add("d", 1) ...
- [转]CAP原理与最终一致性 强一致性 透析
在足球比赛里,一个球员在一场比赛中进三个球,称之为帽子戏法(Hat-trick).在分布式数据系统中,也有一个帽子原理(CAP Theorem),不过此帽子非彼帽子.CAP原理中,有三个要素: 一致性 ...
- css 画基本图形
抄于http://dongtianee.sinaapp.com/demo9.html /******************************************************** ...
- 大规模IP地址黑名单高性能查询实现
嗯……前阵子接了个活儿,需要做一个基于IP地址黑名单的分流网关.刚接到的时候心想iptables不就行了么,没想到一看客户给的IP黑名单规模……我擦……上亿个…… 黑名单到了这个规模,就不得不考虑下优 ...
- webapp图片懒加载实现
图片懒加载在webapp上非常流行,应用的很广泛. 实现图片懒加载功能:zepto.picLazyLoad.min.js 引入类库 <script src="1.1.3/zepto.m ...
- Entity framework code first
EF Code First 不便之处,数据库结构改变时,需要利用程序包管理器控制台生成代码,再用update-database -Verbose更新数据库,这样的做法在很多时候不容易部署.下面介绍一种 ...
- ajax传递数组到后台
//实体类 public class Person { private int ID{get;set;} private string Name{get;set;} private int Age{g ...
- oracle安装不容易啊
oracle 配置方面,电脑端使用的是ORALE 10G 64位,PLSQL DEVELOPER使用32位,ORACLE CLIENT使用11.5版本.之前一直因为ORACLE 使用32位,导致在电脑 ...