Torque3D Documentation / _generateds / afxZodiacMgr_T3D.cpp

afxZodiacMgr_T3D.cpp

Engine/source/afx/ce/afxZodiacMgr_T3D.cpp

More...

Public Variables

Detailed Description

Public Variables

U32 last_terr_zode_idx 
  1
  2
  3//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~~//
  4// Arcane-FX for MIT Licensed Open Source version of Torque 3D from GarageGames
  5// Copyright (C) 2015 Faust Logic, Inc.
  6//
  7// Permission is hereby granted, free of charge, to any person obtaining a copy
  8// of this software and associated documentation files (the "Software"), to
  9// deal in the Software without restriction, including without limitation the
 10// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
 11// sell copies of the Software, and to permit persons to whom the Software is
 12// furnished to do so, subject to the following conditions:
 13//
 14// The above copyright notice and this permission notice shall be included in
 15// all copies or substantial portions of the Software.
 16//
 17// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 18// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 19// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 20// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 21// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
 22// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
 23// IN THE SOFTWARE.
 24//
 25//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~~//
 26
 27#include "afx/arcaneFX.h"
 28
 29#include "console/consoleTypes.h"
 30#include "core/stream/bitStream.h"
 31#include "scene/sceneRenderState.h"
 32#include "materials/shaderData.h"
 33#include "core/frameAllocator.h"
 34#include "terrain/terrRender.h"
 35#include "T3D/tsStatic.h"
 36#include "T3D/groundPlane.h"
 37#include "environment/meshRoad.h"
 38#include "collision/concretePolyList.h"
 39#include "gfx/primBuilder.h"
 40#include "terrain/terrCell.h"
 41
 42#include "afx/ce/afxZodiac.h"
 43#include "afx/ce/afxZodiacMgr.h"
 44#include "afx/afxZodiacTerrainRenderer_T3D.h"
 45#include "afx/afxZodiacGroundPlaneRenderer_T3D.h"
 46#include "afx/afxZodiacMeshRoadRenderer_T3D.h"
 47#include "afx/afxZodiacPolysoupRenderer_T3D.h"
 48
 49//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~~//
 50
 51// POLYSOUP INTERIOR ZODIACS //
 52
 53void afxZodiacMgr::renderPolysoupZodiacs(SceneRenderState* state, TSStatic* tss)
 54{
 55  // check for active interior zodiacs
 56  S32 n_zodes = inter_zodes.size();
 57  if (n_zodes <= 0)
 58    return;
 59 
 60  static SphereF dummy_sphere;
 61  const Box3F& mWorldBox = tss->getWorldBox();
 62  const Point3F& cam_pos = state->getCameraPosition(); 
 63
 64  // loop through the interior zodiacs
 65  for (U32 i = 0; i < n_zodes; i++) 
 66  {      
 67    // calculate zodiac extents
 68    F32 radius = inter_zodes[i].radius_xy;
 69    Box3F box_w; box_w.minExtents = box_w.maxExtents = inter_zodes[i].pos;
 70    box_w.minExtents -= Point3F(radius, radius, inter_zodes[i].vert_range.x);
 71    box_w.maxExtents += Point3F(radius, radius, inter_zodes[i].vert_range.y);
 72
 73    // skip zodiacs not overlapping this object
 74    if (mWorldBox.isOverlapped(box_w) == false)
 75      continue;
 76
 77    // collect list of zodiac-intersecting polygons
 78    ConcretePolyList* poly_list = new ConcretePolyList();
 79    ((SceneObject*)tss)->buildPolyList(PLC_Decal, poly_list, box_w, dummy_sphere);
 80
 81    // render the polys if we get any
 82    if (!poly_list->mPolyList.empty())
 83    {
 84      // calculate zodiac distance from camera
 85      Point3F cam_vec = cam_pos - inter_zodes[i].pos;
 86      F32 cam_dist = cam_vec.lenSquared();
 87
 88      // render zodiacs
 89      afxZodiacPolysoupRenderer::getMaster()->addZodiac(i, poly_list, inter_zodes[i].pos, inter_zodes[i].angle, tss, cam_dist);
 90      // note: poly_list will be deleted by render-manager after rendering is done.
 91    }
 92    else
 93    {
 94      delete poly_list; // avoids crash when overlapping box but not polygons
 95    }
 96  }
 97}
 98
 99ShaderData* afxZodiacMgr::getPolysoupZodiacShader()
100{
101  if (!polysoup_zode_shader)
102  {
103    if( !Sim::findObject("afxZodiacPolysoupShader", polysoup_zode_shader))
104    {
105      Con::errorf("afxZodiacMgr::getPolysoupZodiacShader() - failed to find shader 'afxZodiacPolysoupShader'.");
106      return 0;
107    }
108  }
109
110  return polysoup_zode_shader;
111}
112
113//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~~//
114  
115bool afxZodiacMgr::doesBoxOverlapZodiac(const Box3F& box, const afxZodiacMgr::ZodiacSpec& zode)
116{
117  if ((zode.pos.x - zode.radius_xy) > box.maxExtents.x ||
118      (zode.pos.y - zode.radius_xy) > box.maxExtents.y)
119     return false;
120  if ((zode.pos.x + zode.radius_xy) < box.minExtents.x ||
121     ( zode.pos.y + zode.radius_xy) < box.minExtents.y)
122     return false;
123  return true;
124}
125
126static U32 last_terr_zode_idx = 0;
127
128bool afxZodiacMgr::doesBlockContainZodiacs(SceneRenderState* state, TerrainBlock* block)
129{
130  // for now, only look at diffuse-passes
131  if (!state->isDiffusePass())
132    return false;
133
134  // check for active terrain zodiacs
135  S32 n_zodes = terr_zodes.size();
136  if (n_zodes <= 0)
137    return false;
138
139  const Box3F& block_box = block->getWorldBox();
140
141  last_terr_zode_idx = 0;
142  for (U32 i = 0; i < n_zodes; i++) 
143  { 
144    if (doesBoxOverlapZodiac(block_box, terr_zodes[i]))
145    {
146      last_terr_zode_idx = i;
147      return true;
148    }
149  }
150
151  return false;
152}
153
154//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~~//
155
156bool afxZodiacMgr::renderTerrainZodiacs(SceneRenderState* state, TerrainBlock* block, TerrCell* cell)
157{
158  // we assume here that afxZodiacMgr::doesBlockContainZodiacs() was recently called to
159  // determine that at least one zodiac intersects the block and its index is last_terr_zode_idx.
160
161  bool cell_has_zodiacs = false; 
162
163  const Point3F& cam_pos = state->getCameraPosition(); 
164  const Box3F& block_box = block->getWorldBox();
165
166  S32 n_zodes = terr_zodes.size();
167  for (U32 i = last_terr_zode_idx; i < n_zodes; i++) 
168  { 
169    // first test against block's box
170    if (!doesBoxOverlapZodiac(block_box, terr_zodes[i]))
171      continue;
172
173    const MatrixF& mRenderObjToWorld = block->getRenderTransform();
174    Box3F cell_box = cell->getBounds();
175    mRenderObjToWorld.mul(cell_box);
176    if (!doesBoxOverlapZodiac(cell_box, terr_zodes[i]))
177      continue;
178
179    // at this point we know the zodiac overlaps AABB of cell...
180
181    // calculate zodiac distance from camera
182    Point3F cam_vec = cam_pos - terr_zodes[i].pos;
183    F32 cam_dist = cam_vec.lenSquared();
184    //if (cam_dist > 2500)
185    //  continue;
186
187    // render zodiacs
188    afxZodiacTerrainRenderer::getMaster()->addZodiac(i, terr_zodes[i].pos, terr_zodes[i].angle, block, cell, mRenderObjToWorld, cam_dist);
189
190    cell_has_zodiacs = true;
191  }
192
193  last_terr_zode_idx = 0;
194
195  return cell_has_zodiacs;
196}
197
198ShaderData* afxZodiacMgr::getTerrainZodiacShader()
199{
200  if (!terrain_zode_shader)
201  {
202    if (!Sim::findObject("afxZodiacTerrainShader", terrain_zode_shader))
203    {
204      Con::errorf("afxZodiacMgr::getTerrainZodiacShader() - failed to find shader 'afxZodiacTerrainShader'.");
205      return 0;
206    }
207  }
208
209  return terrain_zode_shader;
210}
211
212//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~~//
213
214void afxZodiacMgr::renderGroundPlaneZodiacs(SceneRenderState* state, GroundPlane* ground_plane)
215{
216  // check for active terrain zodiacs
217  S32 n_zodes = terr_zodes.size();
218  if (n_zodes <= 0)
219    return;
220
221  // we currently expect gound-plane to be infinite
222  if (!ground_plane->isGlobalBounds())
223  {
224    return;
225  }
226
227  static SphereF dummy_sphere;
228  static Box3F dummy_box;
229
230  const Point3F& cam_pos = state->getCameraPosition(); 
231
232  // loop through the terrain zodiacs
233  for (U32 i = 0; i < n_zodes; i++) 
234  { 
235    // calculate zodiac distance from camera
236    Point3F cam_vec = cam_pos - terr_zodes[i].pos;
237    F32 cam_dist = cam_vec.lenSquared();
238
239    // render zodiacs
240    afxZodiacGroundPlaneRenderer::getMaster()->addZodiac(i, terr_zodes[i].pos, terr_zodes[i].angle, ground_plane, cam_dist);
241  }
242}
243
244ShaderData* afxZodiacMgr::getGroundPlaneZodiacShader()
245{
246  if (!terrain_zode_shader)
247  {
248    if (!Sim::findObject("afxZodiacTerrainShader", terrain_zode_shader))
249    {
250      Con::errorf("afxZodiacMgr::getTerrainZodiacShader() - failed to find shader 'afxZodiacTerrainShader'.");
251      return 0;
252    }
253  }
254
255  return terrain_zode_shader;
256}
257
258//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~~//
259
260void afxZodiacMgr::renderMeshRoadZodiacs(SceneRenderState* state, MeshRoad* mesh_road)
261{
262  // check for active terrain zodiacs
263  S32 n_zodes = terr_zodes.size();
264  if (n_zodes <= 0)
265    return;
266
267  const Box3F& mWorldBox = mesh_road->getWorldBox();
268  const Point3F& cam_pos = state->getCameraPosition(); 
269
270  // loop through the terrain zodiacs
271  for (U32 i = 0; i < n_zodes; i++) 
272  {      
273    // calculate zodiac extents
274    F32 radius = terr_zodes[i].radius_xy;
275    Box3F box_w; box_w.minExtents = box_w.maxExtents = terr_zodes[i].pos;
276    box_w.minExtents -= Point3F(radius, radius, terr_zodes[i].vert_range.x);
277    box_w.maxExtents += Point3F(radius, radius, terr_zodes[i].vert_range.y);
278
279    // skip zodiacs not overlapping this object
280    if (mWorldBox.isOverlapped(box_w) == false)
281      continue;
282
283    // collect list of zodiac-intersecting polygons
284    ConcretePolyList* poly_list = new ConcretePolyList();
285
286    mesh_road->buildTopPolyList(PLC_Decal, poly_list);
287
288    // render the polys if we get any
289    if (!poly_list->mPolyList.empty())
290    {
291      // calculate zodiac distance from camera
292      Point3F cam_vec = cam_pos - terr_zodes[i].pos;
293      F32 cam_dist = cam_vec.lenSquared();
294
295      // render zodiacs
296      afxZodiacMeshRoadRenderer::getMaster()->addZodiac(i, poly_list, terr_zodes[i].pos, terr_zodes[i].angle, mesh_road, cam_dist);
297      // note: poly_list will be deleted by render-manager after rendering is done.
298    }
299    else
300    {
301      delete poly_list; // avoids crash when overlapping box but not polygons
302    }
303  }
304}
305
306ShaderData* afxZodiacMgr::getMeshRoadZodiacShader()
307{
308  if (!terrain_zode_shader)
309  {
310    if (!Sim::findObject("afxZodiacTerrainShader", terrain_zode_shader))
311    {
312      Con::errorf("afxZodiacMgr::getTerrainZodiacShader() - failed to find shader 'afxZodiacTerrainShader'.");
313      return 0;
314    }
315  }
316
317  return terrain_zode_shader;
318}
319
320//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~//~~~~~~~~~~~~~~~~~~~~~//
321