/src/away3d/core/traverse/EntityCollector.as

http://github.com/away3d/away3d-core-fp11 · ActionScript · 314 lines · 220 code · 34 blank · 60 comment · 11 complexity · 50eb334a3c81dd9e8aa8bddacbcfdee0 MD5 · raw file

  1. package away3d.core.traverse
  2. {
  3. import away3d.arcane;
  4. import away3d.cameras.Camera3D;
  5. import away3d.core.base.IRenderable;
  6. import away3d.core.data.EntityListItem;
  7. import away3d.core.data.EntityListItemPool;
  8. import away3d.core.data.RenderableListItem;
  9. import away3d.core.data.RenderableListItemPool;
  10. import away3d.core.math.Matrix3DUtils;
  11. import away3d.core.math.Matrix3DUtils;
  12. import away3d.core.math.Plane3D;
  13. import away3d.core.partition.NodeBase;
  14. import away3d.entities.Entity;
  15. import away3d.lights.DirectionalLight;
  16. import away3d.lights.LightBase;
  17. import away3d.lights.LightProbe;
  18. import away3d.lights.PointLight;
  19. import away3d.materials.MaterialBase;
  20. import flash.geom.Vector3D;
  21. use namespace arcane;
  22. /**
  23. * The EntityCollector class is a traverser for scene partitions that collects all scene graph entities that are
  24. * considered potientially visible.
  25. *
  26. * @see away3d.partition.Partition3D
  27. * @see away3d.partition.Entity
  28. */
  29. public class EntityCollector extends PartitionTraverser
  30. {
  31. protected var _skyBox:IRenderable;
  32. protected var _opaqueRenderableHead:RenderableListItem;
  33. protected var _blendedRenderableHead:RenderableListItem;
  34. private var _entityHead:EntityListItem;
  35. protected var _renderableListItemPool:RenderableListItemPool;
  36. protected var _entityListItemPool:EntityListItemPool;
  37. protected var _lights:Vector.<LightBase>;
  38. private var _directionalLights:Vector.<DirectionalLight>;
  39. private var _pointLights:Vector.<PointLight>;
  40. private var _lightProbes:Vector.<LightProbe>;
  41. protected var _numEntities:uint;
  42. protected var _numLights:uint;
  43. protected var _numTriangles:uint;
  44. protected var _numMouseEnableds:uint;
  45. protected var _camera:Camera3D;
  46. private var _numDirectionalLights:uint;
  47. private var _numPointLights:uint;
  48. private var _numLightProbes:uint;
  49. protected var _cameraForward:Vector3D;
  50. private var _customCullPlanes:Vector.<Plane3D>;
  51. private var _cullPlanes:Vector.<Plane3D>;
  52. private var _numCullPlanes:uint;
  53. /**
  54. * Creates a new EntityCollector object.
  55. */
  56. public function EntityCollector()
  57. {
  58. init();
  59. }
  60. private function init():void
  61. {
  62. _lights = new Vector.<LightBase>();
  63. _directionalLights = new Vector.<DirectionalLight>();
  64. _pointLights = new Vector.<PointLight>();
  65. _lightProbes = new Vector.<LightProbe>();
  66. _renderableListItemPool = new RenderableListItemPool();
  67. _entityListItemPool = new EntityListItemPool();
  68. }
  69. /**
  70. * The camera that provides the visible frustum.
  71. */
  72. public function get camera():Camera3D
  73. {
  74. return _camera;
  75. }
  76. public function set camera(value:Camera3D):void
  77. {
  78. _camera = value;
  79. _entryPoint = _camera.scenePosition;
  80. _cameraForward = Matrix3DUtils.getForward(_camera.transform, _cameraForward);
  81. _cullPlanes = _camera.frustumPlanes;
  82. }
  83. public function get cullPlanes():Vector.<Plane3D>
  84. {
  85. return _customCullPlanes;
  86. }
  87. public function set cullPlanes(value:Vector.<Plane3D>):void
  88. {
  89. _customCullPlanes = value;
  90. }
  91. /**
  92. * The amount of IRenderable objects that are mouse-enabled.
  93. */
  94. public function get numMouseEnableds():uint
  95. {
  96. return _numMouseEnableds;
  97. }
  98. /**
  99. * The sky box object if encountered.
  100. */
  101. public function get skyBox():IRenderable
  102. {
  103. return _skyBox;
  104. }
  105. /**
  106. * The list of opaque IRenderable objects that are considered potentially visible.
  107. * @param value
  108. */
  109. public function get opaqueRenderableHead():RenderableListItem
  110. {
  111. return _opaqueRenderableHead;
  112. }
  113. public function set opaqueRenderableHead(value:RenderableListItem):void
  114. {
  115. _opaqueRenderableHead = value;
  116. }
  117. /**
  118. * The list of IRenderable objects that require blending and are considered potentially visible.
  119. * @param value
  120. */
  121. public function get blendedRenderableHead():RenderableListItem
  122. {
  123. return _blendedRenderableHead;
  124. }
  125. public function set blendedRenderableHead(value:RenderableListItem):void
  126. {
  127. _blendedRenderableHead = value;
  128. }
  129. public function get entityHead():EntityListItem
  130. {
  131. return _entityHead;
  132. }
  133. /**
  134. * The lights of which the affecting area intersects the camera's frustum.
  135. */
  136. public function get lights():Vector.<LightBase>
  137. {
  138. return _lights;
  139. }
  140. public function get directionalLights():Vector.<DirectionalLight>
  141. {
  142. return _directionalLights;
  143. }
  144. public function get pointLights():Vector.<PointLight>
  145. {
  146. return _pointLights;
  147. }
  148. public function get lightProbes():Vector.<LightProbe>
  149. {
  150. return _lightProbes;
  151. }
  152. /**
  153. * Clears all objects in the entity collector.
  154. */
  155. public function clear():void
  156. {
  157. if (_camera) {
  158. _entryPoint = _camera.scenePosition;
  159. _cameraForward = Matrix3DUtils.getForward(_camera.transform, _cameraForward);
  160. }
  161. _cullPlanes = _customCullPlanes? _customCullPlanes : (_camera? _camera.frustumPlanes : null);
  162. _numCullPlanes = _cullPlanes? _cullPlanes.length : 0;
  163. _numTriangles = _numMouseEnableds = 0;
  164. _blendedRenderableHead = null;
  165. _opaqueRenderableHead = null;
  166. _entityHead = null;
  167. _renderableListItemPool.freeAll();
  168. _entityListItemPool.freeAll();
  169. _skyBox = null;
  170. if (_numLights > 0)
  171. _lights.length = _numLights = 0;
  172. if (_numDirectionalLights > 0)
  173. _directionalLights.length = _numDirectionalLights = 0;
  174. if (_numPointLights > 0)
  175. _pointLights.length = _numPointLights = 0;
  176. if (_numLightProbes > 0)
  177. _lightProbes.length = _numLightProbes = 0;
  178. }
  179. /**
  180. * Returns true if the current node is at least partly in the frustum. If so, the partition node knows to pass on the traverser to its children.
  181. *
  182. * @param node The Partition3DNode object to frustum-test.
  183. */
  184. override public function enterNode(node:NodeBase):Boolean
  185. {
  186. var enter:Boolean = _collectionMark != node._collectionMark && node.isInFrustum(_cullPlanes, _numCullPlanes);
  187. node._collectionMark = _collectionMark;
  188. return enter;
  189. }
  190. /**
  191. * Adds a skybox to the potentially visible objects.
  192. * @param renderable The skybox to add.
  193. */
  194. override public function applySkyBox(renderable:IRenderable):void
  195. {
  196. _skyBox = renderable;
  197. }
  198. /**
  199. * Adds an IRenderable object to the potentially visible objects.
  200. * @param renderable The IRenderable object to add.
  201. */
  202. override public function applyRenderable(renderable:IRenderable):void
  203. {
  204. var material:MaterialBase;
  205. var entity:Entity = renderable.sourceEntity;
  206. if (renderable.mouseEnabled)
  207. ++_numMouseEnableds;
  208. _numTriangles += renderable.numTriangles;
  209. material = renderable.material;
  210. if (material) {
  211. var item:RenderableListItem = _renderableListItemPool.getItem();
  212. item.renderable = renderable;
  213. item.materialId = material._uniqueId;
  214. item.renderOrderId = material._renderOrderId;
  215. item.cascaded = false;
  216. var entityScenePos:Vector3D = entity.scenePosition;
  217. var dx:Number = _entryPoint.x - entityScenePos.x;
  218. var dy:Number = _entryPoint.y - entityScenePos.y;
  219. var dz:Number = _entryPoint.z - entityScenePos.z;
  220. // project onto camera's z-axis
  221. item.zIndex = dx*_cameraForward.x + dy*_cameraForward.y + dz*_cameraForward.z + entity.zOffset;
  222. item.renderSceneTransform = renderable.getRenderSceneTransform(_camera);
  223. if (material.requiresBlending) {
  224. item.next = _blendedRenderableHead;
  225. _blendedRenderableHead = item;
  226. } else {
  227. item.next = _opaqueRenderableHead;
  228. _opaqueRenderableHead = item;
  229. }
  230. }
  231. }
  232. /**
  233. * @inheritDoc
  234. */
  235. override public function applyEntity(entity:Entity):void
  236. {
  237. ++_numEntities;
  238. var item:EntityListItem = _entityListItemPool.getItem();
  239. item.entity = entity;
  240. item.next = _entityHead;
  241. _entityHead = item;
  242. }
  243. /**
  244. * Adds a light to the potentially visible objects.
  245. * @param light The light to add.
  246. */
  247. override public function applyUnknownLight(light:LightBase):void
  248. {
  249. _lights[_numLights++] = light;
  250. }
  251. override public function applyDirectionalLight(light:DirectionalLight):void
  252. {
  253. _lights[_numLights++] = light;
  254. _directionalLights[_numDirectionalLights++] = light;
  255. }
  256. override public function applyPointLight(light:PointLight):void
  257. {
  258. _lights[_numLights++] = light;
  259. _pointLights[_numPointLights++] = light;
  260. }
  261. override public function applyLightProbe(light:LightProbe):void
  262. {
  263. _lights[_numLights++] = light;
  264. _lightProbes[_numLightProbes++] = light;
  265. }
  266. /**
  267. * The total number of triangles collected, and which will be pushed to the render engine.
  268. */
  269. public function get numTriangles():uint
  270. {
  271. return _numTriangles;
  272. }
  273. /**
  274. * Cleans up any data at the end of a frame.
  275. */
  276. public function cleanUp():void
  277. {
  278. }
  279. }
  280. }