大气层散射球类AtmosphericScatteringSphere代表地球外面的大气层散射球模型,可以控制开启/关闭渲染该对象。该类的类图如下。

该类所包含的主要字段、属性和方法如下:

public float m_radius;//大气层散射球半径,默认为地球赤道半径的1.025倍

protected int m_numberSlices; //大气层散射球切片数目,默认为75

protected int m_numberSections; //大气层散射球半径分割段数,默认为75

public static float m_fInnerRadius = 0; //大气层散射球内半径

public static float m_fOuterRadius = 0; //大气层散射球外半径

public static int TilesHigh = 4; //大气层散射球瓦片高度

public static int TilesWide = 8; //大气层散射球瓦片宽度

System.Collections.Generic.List<MeshSubset> m_meshList = new System.Collections.Generic.List<MeshSubset>();//存储大气层散射球剖分的格网子集

Vector3 m_lastSunPosition = Vector3.Empty;//太阳位置

System.Threading.Thread m_backgroundThread = null;//渲染大气层散射球的后台线程

bool active = false;//是否激活大气层散射球

System.DateTime m_lastOpticalUpdate = System.DateTime.MinValue; //大气层散射球最后的不透明度更新时间

bool m_canDoShaders = false;//是否能够执行着色器

short[] m_indices = null;//剖分散射球时的顶点索引,用来构造索引缓冲区

short[] m_indicesHighResolution = null;//精细的顶点索引,实际是通过指定精细的格网顶点密度是前者的2倍来重新计算实现的,75/4=18.75,取整为18,则精细的格网顶点密度为36

float[] fCameraDepth = new float[4] { 0, 0, 0, 0 };//相机深度

float[] fLightDepth = new float[4];//光照深度

float[] fSampleDepth = new float[4];//采样深度

float[] fRayleighSum = new float[] { 0, 0, 0 };//瑞利散射和

float[] fMieSum = new float[] { 0, 0, 0 };//米尔散射和

Vector3 vPos = new Vector3();//光照位置

float[] fAttenuation = new float[3];//环境光

Vector3 vCamera = new Vector3();相机位置

public void Init(float radius, int slices, int sections)方法用来初始化大气层散射球,内部调用SunCalculator类、TimeKeeper类和BoundingBox类的静态函数,这两个类在本篇结束时附后讲解。将散射球切分成4行×8列=32块,每一步内部又按照指定的格网子集密度(如纵、横密度均为18)进一步剖分计算需要绘制的格网顶点。默认经度和纬度的分割间隔均为45度。内部又调用CustomVertex.PositionColored[] CreateMesh(double minLat, double maxLat, double minLon, double maxLon, int meshPointCount)函数根据输入的经纬度范围创建格网子集。

public void Update(DrawArgs drawArgs)方法用来更新大气散射球的光照、模型等渲染元素,内部实际上是发起后台线程backgroundThread来实现的,线程绑定的处理函数为private void Updater()。而Update函数是在World类的public override void Update(DrawArgs drawArgs)中被调用的。

CustomVertex.PositionColored[] CreateMesh(double minLat, double maxLat, double minLon, double maxLon, int meshPointCount) 函数根据输入的经、纬度范围和格网子集密度来创建格网子集的顶点数组。

short[] computeIndices(int meshPointCount)方法根据指定的格网子集密度来计算每个格网顶点的索引,以便渲染时索引缓冲区使用。其中,索引总数=纵向点数×横向点数×2×3。在数组中索引范围为[0,索引总数-1]。

void Interpolate(ref float[] p, float x, float y)被SetColor函数调用。

public void SetColor(ref CustomVertex.PositionColored pVertex, DrawArgs drawArgs)被UpdateColor和getAtmosphereColor函数调用。

int getAtmosphereColor(DrawArgs drawArgs,CustomVertex.PositionColored pVertex)被ColoredSpherePartial函数调用。

private void UpdateColor(DrawArgs drawArgs, MeshSubset meshSubset, bool doHighResolution)函数暂时未被调用,所以处理颜色函数可以暂时不用分析。

private Mesh ColoredSpherePartial(DrawArgs drawArgs, float radius, double startLat, double endLat, int slices, int stacks, double lonSpan, double heading) 被UpdateSkyMesh函数调用。

void UpdateLightVector(),根据太阳位置更新光照位置和方向,被Render()和Updater()函数调用。

private void UpdateSkyMesh(DrawArgs drawArgs, double horizonSpan)被Render()函数调用。

public void Render(DrawArgs drawArgs) 方法在World类的public override void Render(DrawArgs drawArgs)中被调用的。

void MakeOpticalDepthBuffer(float fInnerRadius, float fOuterRadius, float fRayleighScaleHeight, float fMieScaleHeight) 被Updater()函数调用。

  实际上,大气散射球类只需要重点关注Update(DrawArgs drawArgs)和Render(DrawArgs drawArgs)两个方法,其余方法均直接或间接的被这两个方法调用。而这两个方法又分别被World类的Update(DrawArgs drawArgs)和Render(DrawArgs drawArgs)函数调用。

WorldWind源码剖析系列:大气层散射球类AtmosphericScatteringSphere的更多相关文章

  1. WorldWind源码剖析系列:星球类World

    星球类World代表通用的星球类,因为可能需要绘制除地球之外的其它星球,如月球.火星等.该类的类图如下. 需要说明的是,在WorldWind中星球球体的渲染和经纬网格的渲染时分别绘制的.经纬网格的渲染 ...

  2. WorldWind源码剖析系列:星球球体的加载与渲染

    WorldWind源码剖析系列:星球球体的加载与渲染 WorldWind中主函数Main()的分析 在文件WorldWind.cs中主函数Main()阐明了WorldWind的初始化运行机制(如图1所 ...

  3. WorldWind源码剖析系列:星球表面渲染类WorldSurfaceRenderer

    星球表面渲染类WorldSurfaceRenderer描述如何渲染星球类(如地球)表面影像纹理.该类的类图如下. 星球类World包含的主要的字段.属性和方法如下: public const int ...

  4. WorldWind源码剖析系列:表面影像类SurfaceImage

    表面影像类SurfaceImage描述星球类(如地球)表面纹理影像.该类的类图如下. 表面影像类SurfaceImage包含的主要的字段.属性和方法如下: string m_ImageFilePath ...

  5. WorldWind源码剖析系列:影像存储类ImageStore、Nlt影像存储类NltImageStore和WMS影像存储类WmsImageStore

    影像存储类ImageStore 影像存储类ImageStore提供了计算本地影像路径和远程影像影像URL访问的各种接口,是WmsImageStore类和NltImageStore类的基类.当划分完层次 ...

  6. WorldWind源码剖析系列:设置类SettingsBase

    PluginSDK中的星球设置类WorldSettings 和WorldWind.程序设置类WorldWindSettings均继承自父类SettingsBase.类图如下所示.其中父类Setting ...

  7. WorldWind源码剖析系列:表面瓦片类SurfaceTile

    表面瓦片类SurfaceTile描述星球类(如地球)表面纹理影像的瓦片模型.其类图如下. 表面瓦片类SurfaceTile包含的主要的字段.属性和方法如下: int m_Level;//该瓦片所属金字 ...

  8. WorldWind源码剖析系列:挂件类Widgets

    WorldWindow用户定制控件类中所包含的的挂件类Widgets控件主要有如下图所示的派生类.它们的类图如下所示. 鉴于挂件类Widgets及其派生类,相对简单,基本上都是些利用DirectX3D ...

  9. WorldWind源码剖析系列:外包围盒类BoundingBox和外包围球类BoundingSphere

    PluginSDK中的外包围盒.外包围球分别用类 BoundingBox和BoundingSphere描述,其类图如下所示. 外包围盒BoundingBox类的corners字段用来存储外包围盒的8个 ...

随机推荐

  1. oracle逐步学习总结之oracle数字函数和日期函数(基础四)

    原创作品,转自请注明出处:https://www.cnblogs.com/sunshine5683/p/10140716.html 继上篇总结,继续进行总结: 以下下数字函数: 1.abs(n):返回 ...

  2. 理解JVM之垃圾收集器详解

    前言 垃圾收集器作为内存回收的具体表现,Java虚拟机规范并未对垃圾收集器的实现做规定,因而不同版本的虚拟机有很大区别,因而我们在这里主要讨论基于Sun HotSpot虚拟机1.6版本Update22 ...

  3. python基础技巧综合训练题2

    1,判断一个字符串中的每一个字母是否都在另一个字符串中,可以利用集合的特性来解,集合的元素如果存在,再次更新(update) 是添加不进集合的,那么集合的长度还是跟原来一样,如果添加进去,集合长度就会 ...

  4. 设计模式(17)--Mediator(中介者模式)行为型

    作者QQ:1095737364    QQ群:123300273     欢迎加入! 1.模式定义: 用一个中介者对象封装一系列的对象交互,中介者使各对象不需要显示地相互作用,从而使耦合松散,而且可以 ...

  5. CSS让DIV按照背景图片的比例缩放,并让背景图片填充整个元素(转)

    目的是:通过background的一系列属性,让DIV按照背景图片的比例缩放,并让背景图片填充整个DIV 首先我们需要让背景图片在指定的DIV中全部填充显示 之前看有用类似 background-at ...

  6. Everything实用技巧随手记

    Everything是一款非常好用的即时搜索软件,针对文件名目录名搜索,并且支持通配符.正则表达式,胜过windows自带搜索N倍. 在使用中有些许不便,比如搜索结果中出现很多快捷方式,或者搜索到不想 ...

  7. JQuery判断数组中是否包含某个字符串

    var arry = [ "C#", "html", "css", "JavaScript" ]; var result ...

  8. java基础(十一) 枚举类型

    枚举类型Enum的简介 1.什么是枚举类型 枚举类型: 就是由一组具有名的值的有限集合组成新的类型.(即新的类). 好像还是不懂,别急,咱们先来看一下 为什么要引入枚举类型 在没有引入枚举类型前,当我 ...

  9. 一种通过async/await实现函数同步执行的方式

    const testArr = [ () => { return new Promise((resolve, reject) => { setTimeout(()=> { alert ...

  10. python-docx 使用教程

    快速入门 入门python-docx很容易.让我们来看一下基础知识. 官方文档地址请点击 打开文档 你需要的第一件事是工作的文档.最简单的方法是: from docx import Document ...