dazzle.cpp 52 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703
  1. /*
  2. ** Command & Conquer Renegade(tm)
  3. ** Copyright 2025 Electronic Arts Inc.
  4. **
  5. ** This program is free software: you can redistribute it and/or modify
  6. ** it under the terms of the GNU General Public License as published by
  7. ** the Free Software Foundation, either version 3 of the License, or
  8. ** (at your option) any later version.
  9. **
  10. ** This program is distributed in the hope that it will be useful,
  11. ** but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. ** GNU General Public License for more details.
  14. **
  15. ** You should have received a copy of the GNU General Public License
  16. ** along with this program. If not, see <http://www.gnu.org/licenses/>.
  17. */
  18. /***********************************************************************************************
  19. *** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
  20. ***********************************************************************************************
  21. * *
  22. * Project Name : WW3D *
  23. * *
  24. * $Archive:: /Commando/Code/ww3d2/dazzle.cpp $*
  25. * *
  26. * Original Author:: Jani Penttinen *
  27. * *
  28. * $Author:: Steve_t $*
  29. * *
  30. * $Modtime:: 1/02/02 2:55p $*
  31. * *
  32. * $Revision:: 31 $*
  33. * *
  34. *---------------------------------------------------------------------------------------------*
  35. * Functions: *
  36. * - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
  37. #include "dazzle.h"
  38. #include "simplevec.h"
  39. #include "vector2.h"
  40. #include "camera.h"
  41. #include "ww3d.h"
  42. #include "wwstring.h"
  43. #include "wwdebug.h"
  44. #include "assetmgr.h"
  45. #include "vector3i.h"
  46. #include "quat.h"
  47. #include "ini.h"
  48. #include "point.h"
  49. #include "rinfo.h"
  50. #include "vertmaterial.h"
  51. #include "chunkio.h"
  52. #include "wwfile.h"
  53. #include "inisup.h"
  54. #include "persistfactory.h"
  55. #include "ww3dids.h"
  56. #include "dx8wrapper.h"
  57. #include "dx8vertexbuffer.h"
  58. #include "dx8indexbuffer.h"
  59. #include "sortingrenderer.h"
  60. #include "texture.h"
  61. #include "scene.h"
  62. #include "wwprofile.h"
  63. #include "visrasterizer.h"
  64. #include <cstdio>
  65. #include <limits.h>
  66. #include <wwprofile.h>
  67. // All dazzle types appear under Dazzles_List in the dazzle.ini file.
  68. const char* DAZZLE_LIST_STRING="Dazzles_List";
  69. // After the dot product between the camera direction and the camera space location of the light source,
  70. // we do a power to Halopow for the halo size and power to DazzlePow for the dazzle size. Halo/DazzleArea
  71. // defines the angle where the values are valid, so any angle beyond HaloArea/DazzleArea results the halo or
  72. // dazzle being scaled to zero. The angles are re-scaled from normalized angle scale of (-1.0...1.0)
  73. // only HaloArea/DazzleArea defined part is used.
  74. const char* DAZZLE_INTENSITY_POW_STRING = "DazzleIntensityPow";
  75. const char* DAZZLE_SIZE_POW_STRING = "DazzleSizePow";
  76. const char* DAZZLE_AREA_STRING = "DazzleArea"; // Something like 0.05 is a good starting point for a dazzle...
  77. // Halo and dazzle are scaled by these values
  78. const char* HALO_SCALE_X_STRING = "HaloScaleX";
  79. const char* HALO_SCALE_Y_STRING = "HaloScaleY";
  80. const char* DAZZLE_SCALE_X_STRING = "DazzleScaleX";
  81. const char* DAZZLE_SCALE_Y_STRING = "DazzleScaleY";
  82. // Dazzle and halo intensity control the base intensities.
  83. const char* HALO_INTENSITY_STRING = "HaloIntensity";
  84. const char* DAZZLE_INTENSITY_STRING = "DazzleIntensity";
  85. // Direction area defines the maximum difference between the light direction and the eyespace location,
  86. // so the dazzle can only be seen if the camera is inside the light cone. Value 0.0 means dazzle is not
  87. // directional, it can be seen from any direction. Halo is not affected. Dazzle direction defines the light
  88. // direction vector.
  89. const char* DAZZLE_DIRECTION_AREA_STRING = "DazzleDirectionArea"; // Something like 0.5 might be a good test value
  90. const char* DAZZLE_DIRECTION_STRING = "DazzleDirection";
  91. // Dazzle and halo start to afde out after FadeoutStart meters and are completely gone by FadeoutEnd meters.
  92. const char* FADEOUT_START_STRING = "FadeoutStart";
  93. const char* FADEOUT_END_STRING = "FadeoutEnd";
  94. // To be done: This parameter needs to be redefined.
  95. const char* SIZE_OPTIMIZATION_LIMIT_STRING = "SizeOptimizationLimit";
  96. // The weight of history for the intensities. The history weight is per millisecond, so if you want to have
  97. // any real history, values higher than 0.95 are recommended (don't use value of 1.0 or anything higher!)
  98. const char* HISTORY_WEIGHT_STRING = "HistoryWeight";
  99. // Textures to be used.
  100. const char* DAZZLE_TEXTURE_STRING = "DazzleTextureName";
  101. const char* HALO_TEXTURE_STRING = "HaloTextureName";
  102. // If false, camera matrix's translation term isn't used. If translation isn't used the dazzle is treated as
  103. // always visible, scene graph visibility is not used.
  104. const char* USE_CAMERA_TRANSLATION = "UseCameraTranslation";
  105. // Halo and dazzle colors, RGB, (1.0, 1.0, 1.0) is white and (0.0, 0.0, 0.0) is black
  106. const char* HALO_COLOR_STRING = "HaloColor";
  107. const char* DAZZLE_COLOR_STRING = "DazzleColor";
  108. // Dazzle test color could be white in many cases but if the level has a lot of white then another color can be defined.
  109. const char* DAZZLE_TEST_COLOR_STRING = "DazzleTestColor";
  110. // Dazzles can blink on and off. The blink period defines the time for one cycle, the blink "on time" defines
  111. // the amount of time within that period that the dazzle is "on"
  112. const char* BLINK_PERIOD_STRING = "BlinkPeriod";
  113. const char* BLINK_ON_TIME_STRING = "BlinkOnTime";
  114. // Dazzle can use a lensflare by defining a name of lensflare in the ini
  115. const char* DAZZLE_LENSFLARE_STRING = "LensflareName";
  116. // Lensflare definitions
  117. const char* LENSFLARE_LIST_STRING = "Lensflares_List";
  118. // Texture to be used by the lensflare
  119. const char* LENSFLARE_TEXTURE_STRING = "TextureName";
  120. // The number of flare sprites in lensflare. The FlareLocation, FlareSize and FlareColor paremeters are procedural, the
  121. // names are produced based on this parameter. If FlareCount is 3, there exists FlareLocation1, FlareLocation2 and
  122. // FlareLocation3... And so on.
  123. const char* FLARE_COUNT_STRING = "FlareCount";
  124. // 1D-locations of the flares. 0.0 means the location of the center of the screen and 1.0 means the location of the
  125. // lightsource. The values can be smaller than zero and larger than 1.0.
  126. const char* FLARE_LOCATION_STRING = "FlareLocation";
  127. // Normalized flare sizes
  128. const char* FLARE_SIZE_STRING = "FlareSize";
  129. // Colors for each flare sprite
  130. const char* FLARE_COLOR_STRING = "FlareColor";
  131. // Uv coordinates (as there can be only one texture used, but one may want multiple images). The values is a 4-float
  132. // vector: start_u, start_v, end_u, end_v.
  133. const char* FLARE_UV_STRING = "FlareUV";
  134. // Radius of dazzle used for raycast tests
  135. const char * RADIUS_STRING = "Radius";
  136. /*
  137. ; DAZZLE.INI example
  138. [Lensflares_List]
  139. 0=DEFAULT_LENSFLARE
  140. [Dazzles_List]
  141. 0=DEFAULT
  142. ;========================================== LENSFLARE DEFINITIONS =================
  143. [DEFAULT_LENSFLARE]
  144. TextureName=dazzle_secondary.jpg
  145. FlareCount=5
  146. FlareLocation1=0.1
  147. FlareLocation2=0.5
  148. FlareLocation3=1.1
  149. FlareLocation4=1.5
  150. FlareLocation5=-0.4
  151. FlareSize1=0.1
  152. FlareSize2=0.05
  153. FlareSize3=0.08
  154. FlareSize4=0.15
  155. FlareSize5=0.10
  156. FlareColor1=1.0,0.5,0.5
  157. FlareColor2=0.5,1.0,0.5
  158. FlareColor3=0.5,0.5,1.0
  159. FlareColor4=0.5,0.5,1.0
  160. FlareColor5=0.5,0.5,1.0
  161. ;========================================== DAZZLE DEFINITIONS ====================
  162. [DEFAULT]
  163. HaloIntensity=1.0
  164. HaloIntensityPow=0.95
  165. HaloSizePow=0.95
  166. HaloArea=1.0
  167. HaloScaleX=0.2
  168. HaloScaleY=0.2
  169. DazzleArea=0.05
  170. DazzleDirectionArea=0
  171. DazzleDirection=0,1,1
  172. DazzleSizePow=0.9
  173. DazzleIntensityPow=0.9
  174. DazzleIntensity=50
  175. DazzleScaleX=1.0
  176. DazzleScaleY=1.0
  177. FadeoutStart=30.0
  178. FadeoutEnd=40.0
  179. SizeOptimizationLimit=0.05
  180. HistoryWeight=0.975
  181. UseCameraTranslation=1
  182. DazzleTextureName=dazzle_primary.jpg
  183. HaloTextureName=dazzle_secondary.jpg
  184. DazzleColor=1,1,1
  185. HaloColor=0,0,1
  186. DazzleTestColor=1,1,1
  187. LensflareName=DEFAULT_LENSFLARE
  188. */
  189. // Global instance of a dazzle loader
  190. DazzleLoaderClass _DazzleLoader;
  191. static SimpleVecClass<DazzleRenderObjClass*> temp_ptrs;
  192. static DazzleTypeClass** types;
  193. static unsigned type_count;
  194. // Current dazzle layer - must be set before rendering
  195. static DazzleLayerClass * current_dazzle_layer = NULL;
  196. static LensflareTypeClass** lensflares;
  197. static unsigned lensflare_count;
  198. static ShaderClass default_dazzle_shader;
  199. static ShaderClass default_halo_shader;
  200. static ShaderClass vis_shader;
  201. static ShaderClass debug_shader;
  202. // static instance of a default dazzle visibility handler
  203. static DazzleVisibilityClass _DefaultVisibilityHandler;
  204. static const DazzleVisibilityClass * _VisibilityHandler = &_DefaultVisibilityHandler;
  205. bool DazzleRenderObjClass::_dazzle_rendering_enabled = true;
  206. static void Init_Shaders()
  207. {
  208. default_dazzle_shader.Set_Cull_Mode( ShaderClass::CULL_MODE_DISABLE );
  209. default_dazzle_shader.Set_Depth_Mask( ShaderClass::DEPTH_WRITE_DISABLE );
  210. default_dazzle_shader.Set_Depth_Compare( ShaderClass::PASS_ALWAYS );
  211. default_dazzle_shader.Set_Dst_Blend_Func( ShaderClass::DSTBLEND_ONE );
  212. default_dazzle_shader.Set_Src_Blend_Func( ShaderClass::SRCBLEND_ONE );
  213. default_dazzle_shader.Set_Fog_Func( ShaderClass::FOG_DISABLE );
  214. default_dazzle_shader.Set_Primary_Gradient( ShaderClass::GRADIENT_MODULATE );
  215. default_dazzle_shader.Set_Texturing( ShaderClass::TEXTURING_ENABLE );
  216. default_halo_shader.Set_Cull_Mode( ShaderClass::CULL_MODE_DISABLE );
  217. default_halo_shader.Set_Depth_Mask( ShaderClass::DEPTH_WRITE_DISABLE );
  218. default_halo_shader.Set_Depth_Compare( ShaderClass::PASS_LEQUAL );
  219. default_halo_shader.Set_Dst_Blend_Func( ShaderClass::DSTBLEND_ONE );
  220. default_halo_shader.Set_Src_Blend_Func( ShaderClass::SRCBLEND_ONE );
  221. default_halo_shader.Set_Fog_Func( ShaderClass::FOG_DISABLE );
  222. default_halo_shader.Set_Primary_Gradient( ShaderClass::GRADIENT_MODULATE );
  223. default_halo_shader.Set_Texturing( ShaderClass::TEXTURING_ENABLE );
  224. vis_shader.Set_Cull_Mode( ShaderClass::CULL_MODE_DISABLE );
  225. vis_shader.Set_Depth_Mask( ShaderClass::DEPTH_WRITE_DISABLE );
  226. vis_shader.Set_Dst_Blend_Func( ShaderClass::DSTBLEND_ZERO );
  227. vis_shader.Set_Src_Blend_Func( ShaderClass::SRCBLEND_ONE );
  228. vis_shader.Set_Fog_Func( ShaderClass::FOG_DISABLE );
  229. vis_shader.Set_Primary_Gradient( ShaderClass::GRADIENT_MODULATE );
  230. vis_shader.Set_Texturing( ShaderClass::TEXTURING_DISABLE );
  231. debug_shader.Set_Cull_Mode( ShaderClass::CULL_MODE_DISABLE );
  232. debug_shader.Set_Depth_Mask( ShaderClass::DEPTH_WRITE_DISABLE );
  233. debug_shader.Set_Dst_Blend_Func( ShaderClass::DSTBLEND_SRC_ALPHA );
  234. debug_shader.Set_Src_Blend_Func( ShaderClass::SRCBLEND_ONE );
  235. debug_shader.Set_Fog_Func( ShaderClass::FOG_DISABLE );
  236. debug_shader.Set_Primary_Gradient( ShaderClass::GRADIENT_MODULATE );
  237. debug_shader.Set_Texturing( ShaderClass::TEXTURING_DISABLE );
  238. }
  239. /*
  240. ** Derived INI to support Vector4
  241. */
  242. class DazzleINIClass : public INIClass {
  243. public:
  244. DazzleINIClass(FileClass & file) : INIClass(file) {}
  245. const Vector2 Get_Vector2(char const *section, char const *entry, const Vector2 & defvalue = Vector2(0,0) );
  246. const Vector3 Get_Vector3(char const *section, char const *entry, const Vector3 & defvalue = Vector3(0,0,0) );
  247. const Vector4 Get_Vector4(char const *section, char const *entry, const Vector4 & defvalue = Vector4(0,0,0,0) ) const;
  248. };
  249. const Vector2 DazzleINIClass::Get_Vector2(char const *section, char const *entry, const Vector2 & defvalue)
  250. {
  251. if (section != NULL && entry != NULL) {
  252. INIEntry * entryptr = Find_Entry(section, entry);
  253. if (entryptr && entryptr->Value != NULL) {
  254. Vector2 ret;
  255. if ( sscanf( entryptr->Value, "%f,%f", &ret[0], &ret[1], &ret[2] ) == 2 ) {
  256. return ret;
  257. }
  258. }
  259. }
  260. return defvalue;
  261. }
  262. const Vector3 DazzleINIClass::Get_Vector3(char const *section, char const * entry, const Vector3 & defvalue )
  263. {
  264. if (section != NULL && entry != NULL) {
  265. INIEntry * entryptr = Find_Entry(section, entry);
  266. if (entryptr && entryptr->Value != NULL) {
  267. Vector3 ret;
  268. if ( sscanf( entryptr->Value, "%f,%f,%f", &ret[0], &ret[1], &ret[2] ) == 3 ) {
  269. return ret;
  270. }
  271. }
  272. }
  273. return defvalue;
  274. }
  275. const Vector4 DazzleINIClass::Get_Vector4(char const *section, char const *entry, const Vector4 & defvalue) const
  276. {
  277. if (section != NULL && entry != NULL) {
  278. INIEntry * entryptr = Find_Entry(section, entry);
  279. if (entryptr && entryptr->Value != NULL) {
  280. Vector4 ret;
  281. if ( sscanf( entryptr->Value, "%f,%f,%f,%f", &ret[0], &ret[1], &ret[2], &ret[3] ) == 4 ) {
  282. return ret;
  283. }
  284. }
  285. }
  286. return defvalue;
  287. }
  288. // ----------------------------------------------------------------------------
  289. LensflareTypeClass::LensflareTypeClass(const LensflareInitClass& is)
  290. :
  291. lic(is),
  292. texture(NULL)
  293. {
  294. }
  295. LensflareTypeClass::~LensflareTypeClass()
  296. {
  297. REF_PTR_RELEASE(texture);
  298. }
  299. TextureClass* LensflareTypeClass::Get_Texture()
  300. {
  301. if (!texture) {
  302. texture = WW3DAssetManager::Get_Instance()->Get_Texture(lic.texture_name);
  303. SET_REF_OWNER(texture);
  304. }
  305. return texture;
  306. }
  307. void LensflareTypeClass::Generate_Vertex_Buffers(
  308. VertexFormatXYZNDUV2* vertex,
  309. int& vertex_count,
  310. float screen_x_scale,
  311. float screen_y_scale,
  312. float dazzle_intensity,
  313. const Vector4& transformed_location)
  314. {
  315. // Lensflares are placed on a line 2D that goes through the lightsource and the center of the screen
  316. // float scale=sqrt(transformed_location[0]*transformed_location[0]+transformed_location[1]*transformed_location[1]);
  317. float z=transformed_location[2];
  318. float distance_multiplier=sqrt(transformed_location[0]*transformed_location[0]+transformed_location[1]*transformed_location[1])+1.0f;
  319. for (int a=0;a<lic.flare_count;++a) {
  320. float x=lic.flare_locations[a]*transformed_location[0];
  321. float y=lic.flare_locations[a]*transformed_location[1];
  322. float size=lic.flare_sizes[a]*distance_multiplier;
  323. float ix=size*screen_x_scale;
  324. float iy=size*screen_y_scale;
  325. Vector3 col=lic.flare_colors[a]*dazzle_intensity;
  326. if (col[0]>1.0f) col[0]=1.0f;
  327. if (col[1]>1.0f) col[1]=1.0f;
  328. if (col[2]>1.0f) col[2]=1.0f;
  329. unsigned color=DX8Wrapper::Convert_Color(col,1.0f);
  330. vertex->x=x+ix;
  331. vertex->y=y-iy;
  332. vertex->z=z;
  333. vertex->u1=lic.flare_uv[a][0];
  334. vertex->v1=lic.flare_uv[a][1];
  335. vertex->diffuse=color;
  336. vertex++;
  337. vertex->x=x+ix;
  338. vertex->y=y+iy;
  339. vertex->z=z;
  340. vertex->u1=lic.flare_uv[a][2];
  341. vertex->v1=lic.flare_uv[a][1];
  342. vertex->diffuse=color;
  343. vertex++;
  344. vertex->x=x-ix;
  345. vertex->y=y+iy;
  346. vertex->z=z;
  347. vertex->u1=lic.flare_uv[a][2];
  348. vertex->v1=lic.flare_uv[a][3];
  349. vertex->diffuse=color;
  350. vertex++;
  351. vertex->x=x-ix;
  352. vertex->y=y-iy;
  353. vertex->z=z;
  354. vertex->u1=lic.flare_uv[a][0];
  355. vertex->v1=lic.flare_uv[a][3];
  356. vertex->diffuse=color;
  357. vertex++;
  358. vertex_count+=4;
  359. }
  360. }
  361. // ----------------------------------------------------------------------------
  362. DazzleTypeClass::DazzleTypeClass(const DazzleInitClass& is)
  363. :
  364. ic(is),
  365. dazzle_shader(default_dazzle_shader),
  366. halo_shader(default_halo_shader),
  367. primary_texture(NULL),
  368. secondary_texture(NULL),
  369. lensflare_id(DazzleRenderObjClass::Get_Lensflare_ID(is.lensflare_name)),
  370. radius(is.radius)
  371. {
  372. fadeout_end_sqr=ic.fadeout_end*ic.fadeout_end;
  373. fadeout_start_sqr=ic.fadeout_start*ic.fadeout_start;
  374. dazzle_test_color_integer=
  375. 0xff000000|
  376. (unsigned(255.0f*ic.dazzle_test_color[2])<<16)|
  377. (unsigned(255.0f*ic.dazzle_test_color[1])<<8)|
  378. (unsigned(255.0f*ic.dazzle_test_color[0]));
  379. dazzle_test_mask_integer=dazzle_test_color_integer&0xf8f8f8f8;
  380. }
  381. DazzleTypeClass::~DazzleTypeClass()
  382. {
  383. REF_PTR_RELEASE(primary_texture);
  384. REF_PTR_RELEASE(secondary_texture);
  385. }
  386. // ----------------------------------------------------------------------------
  387. void DazzleTypeClass::Set_Dazzle_Shader(const ShaderClass& s) // Set shader for the dazzle type
  388. {
  389. dazzle_shader=s;
  390. }
  391. // ----------------------------------------------------------------------------
  392. void DazzleTypeClass::Set_Halo_Shader(const ShaderClass& s) // Set shader for the dazzle type
  393. {
  394. halo_shader=s;
  395. }
  396. // ----------------------------------------------------------------------------
  397. TextureClass* DazzleTypeClass::Get_Dazzle_Texture()
  398. {
  399. if (!primary_texture) {
  400. primary_texture = WW3DAssetManager::Get_Instance()->Get_Texture(ic.primary_texture_name);
  401. if ( primary_texture ) {
  402. SET_REF_OWNER(primary_texture);
  403. }
  404. }
  405. return primary_texture;
  406. }
  407. // ----------------------------------------------------------------------------
  408. TextureClass* DazzleTypeClass::Get_Halo_Texture()
  409. {
  410. if (!secondary_texture) {
  411. secondary_texture = WW3DAssetManager::Get_Instance()->Get_Texture(ic.secondary_texture_name);
  412. if ( secondary_texture ) {
  413. SET_REF_OWNER(secondary_texture);
  414. }
  415. }
  416. return secondary_texture;
  417. }
  418. // ----------------------------------------------------------------------------
  419. void DazzleTypeClass::Calculate_Intensities(
  420. float& dazzle_intensity,
  421. float& dazzle_size,
  422. float& halo_intensity,
  423. const Vector3& camera_dir,
  424. const Vector3& dazzle_dir,
  425. float distance) const
  426. {
  427. if (ic.use_camera_translation && distance>(fadeout_end_sqr)) {
  428. dazzle_intensity=0.0f;
  429. return;
  430. }
  431. dazzle_intensity-=1.0f-ic.dazzle_area;
  432. dazzle_intensity/=ic.dazzle_area;
  433. dazzle_intensity=WWMath::Clamp(dazzle_intensity);
  434. if (ic.dazzle_direction_area>0.0f) {
  435. float angle=-Vector3::Dot_Product(camera_dir,dazzle_dir);
  436. angle-=1.0f-ic.dazzle_direction_area;
  437. angle/=ic.dazzle_direction_area;
  438. angle=WWMath::Clamp(angle);
  439. dazzle_intensity*=angle;
  440. }
  441. if (dazzle_intensity>0.0f) {
  442. dazzle_size=pow(dazzle_intensity,ic.dazzle_size_pow);
  443. dazzle_intensity=pow(dazzle_intensity,ic.dazzle_intensity_pow);
  444. }
  445. else {
  446. dazzle_intensity=0.0f;
  447. }
  448. dazzle_intensity*=ic.dazzle_intensity;
  449. halo_intensity*=ic.halo_intensity;
  450. // Flare fadeout distance - fade it out...
  451. if (ic.use_camera_translation) {
  452. if (distance>(fadeout_start_sqr)) {
  453. distance=sqrt(distance);
  454. distance-=ic.fadeout_start;
  455. distance/=ic.fadeout_end-ic.fadeout_start;
  456. dazzle_intensity*=1.0f-distance; // Scale down intensity
  457. halo_intensity*=1.0f-distance; // Scale down intensity
  458. }
  459. }
  460. return;
  461. }
  462. // ----------------------------------------------------------------------------
  463. void DazzleRenderObjClass::Init_From_INI(const INIClass* ini)
  464. {
  465. if (!ini) return;
  466. if (ini->Section_Count()==0) return;
  467. Init_Shaders();
  468. unsigned count=ini->Entry_Count( LENSFLARE_LIST_STRING );
  469. unsigned entry;
  470. for ( entry = 0; entry < count; entry++ ) {
  471. char section_name[80];
  472. ini->Get_String(
  473. LENSFLARE_LIST_STRING,
  474. ini->Get_Entry( LENSFLARE_LIST_STRING, entry),
  475. "",
  476. section_name,
  477. sizeof( section_name ));
  478. LensflareInitClass lic;
  479. ini->Get_String(lic.texture_name,section_name,LENSFLARE_TEXTURE_STRING);
  480. lic.flare_count=ini->Get_Int(section_name,FLARE_COUNT_STRING,0);
  481. if (lic.flare_count) {
  482. lic.flare_locations=new float[lic.flare_count]; // Flare location is 1D
  483. lic.flare_sizes=new float[lic.flare_count];
  484. lic.flare_colors=new Vector3[lic.flare_count];
  485. lic.flare_uv=new Vector4[lic.flare_count];
  486. }
  487. else {
  488. lic.flare_locations=NULL;
  489. lic.flare_sizes=NULL;
  490. lic.flare_colors=NULL;
  491. }
  492. for (int flare=0;flare<lic.flare_count;++flare) {
  493. // Flare location
  494. StringClass tmp_name(true);
  495. tmp_name.Format("%s%d",FLARE_LOCATION_STRING,flare+1);
  496. lic.flare_locations[flare]=ini->Get_Float(section_name,tmp_name,0.0f);
  497. // Flare size
  498. tmp_name.Format("%s%d",FLARE_SIZE_STRING,flare+1);
  499. lic.flare_sizes[flare]=ini->Get_Float(section_name,tmp_name,1.0f);
  500. // Flare color
  501. tmp_name.Format("%s%d",FLARE_COLOR_STRING,flare+1);
  502. TPoint3D<float> tp=ini->Get_Point(section_name,tmp_name,TPoint3D<float>(1.0f,1.0f,1.0f));
  503. lic.flare_colors[flare]=reinterpret_cast<const Vector3&>(tp);
  504. // Flare uv
  505. const DazzleINIClass* dini=reinterpret_cast<const DazzleINIClass*>(ini);
  506. tmp_name.Format("%s%d",FLARE_UV_STRING,flare+1);
  507. lic.flare_uv[flare]=dini->Get_Vector4(section_name,tmp_name,Vector4(0.0f,0.0f,1.0f,1.0f));
  508. }
  509. lic.type=entry;
  510. Init_Lensflare(lic);
  511. lensflares[entry]->name=section_name;
  512. }
  513. count=ini->Entry_Count( DAZZLE_LIST_STRING );
  514. for ( entry = 0; entry < count; entry++ ) {
  515. char section_name[80];
  516. ini->Get_String(
  517. DAZZLE_LIST_STRING,
  518. ini->Get_Entry( DAZZLE_LIST_STRING, entry),
  519. "",
  520. section_name,
  521. sizeof( section_name ));
  522. DazzleInitClass dic;
  523. ini->Get_String(dic.primary_texture_name,section_name,DAZZLE_TEXTURE_STRING);
  524. ini->Get_String(dic.secondary_texture_name,section_name,HALO_TEXTURE_STRING);
  525. dic.halo_intensity=ini->Get_Float(section_name,HALO_INTENSITY_STRING,0.95f);
  526. dic.halo_scale_x=ini->Get_Float(section_name,HALO_SCALE_X_STRING,2.0f);
  527. dic.halo_scale_y=ini->Get_Float(section_name,HALO_SCALE_Y_STRING,2.0f);
  528. dic.dazzle_area=ini->Get_Float(section_name,DAZZLE_AREA_STRING,0.05f);
  529. dic.dazzle_direction_area=ini->Get_Float(section_name,DAZZLE_DIRECTION_AREA_STRING,0.50f);
  530. dic.dazzle_intensity=ini->Get_Float(section_name,DAZZLE_INTENSITY_STRING,0.90f);
  531. dic.dazzle_intensity_pow=ini->Get_Float(section_name,DAZZLE_INTENSITY_POW_STRING,0.90f);
  532. dic.dazzle_size_pow=ini->Get_Float(section_name,DAZZLE_SIZE_POW_STRING,0.90f);
  533. dic.dazzle_scale_x=ini->Get_Float(section_name,DAZZLE_SCALE_X_STRING,100.0f);
  534. dic.dazzle_scale_y=ini->Get_Float(section_name,DAZZLE_SCALE_Y_STRING,25.0f);
  535. dic.fadeout_start=ini->Get_Float(section_name,FADEOUT_START_STRING,25.0f);
  536. dic.fadeout_end=ini->Get_Float(section_name,FADEOUT_END_STRING,50.0f);
  537. dic.size_optimization_limit=ini->Get_Float(section_name,SIZE_OPTIMIZATION_LIMIT_STRING,0.05f);
  538. dic.history_weight=ini->Get_Float(section_name,HISTORY_WEIGHT_STRING,0.5f);
  539. dic.use_camera_translation=!!ini->Get_Int(section_name,USE_CAMERA_TRANSLATION,1);
  540. ini->Get_String(dic.lensflare_name,section_name,DAZZLE_LENSFLARE_STRING);
  541. dic.type=entry;
  542. TPoint3D<float> tp=ini->Get_Point(section_name,DAZZLE_DIRECTION_STRING,TPoint3D<float>(0.0f,0.0f,0.0f));
  543. tp.Normalize();
  544. dic.dazzle_direction=reinterpret_cast<const Vector3&>(tp);
  545. tp=ini->Get_Point(section_name,DAZZLE_TEST_COLOR_STRING,TPoint3D<float>(1.0f,1.0f,1.0f));
  546. dic.dazzle_test_color=reinterpret_cast<const Vector3&>(tp);
  547. tp=ini->Get_Point(section_name,DAZZLE_COLOR_STRING,TPoint3D<float>(1.0f,1.0f,1.0f));
  548. dic.dazzle_color=reinterpret_cast<const Vector3&>(tp);
  549. tp=ini->Get_Point(section_name,HALO_COLOR_STRING,TPoint3D<float>(1.0f,1.0f,1.0f));
  550. dic.halo_color=reinterpret_cast<const Vector3&>(tp);
  551. dic.radius=ini->Get_Float(section_name,RADIUS_STRING,1.0f);
  552. dic.blink_period=ini->Get_Float(section_name,BLINK_PERIOD_STRING,0.0f);
  553. dic.blink_on_time=ini->Get_Float(section_name,BLINK_ON_TIME_STRING,0.0f);
  554. Init_Type(dic);
  555. types[entry]->name=section_name;
  556. }
  557. }
  558. // ----------------------------------------------------------------------------
  559. void DazzleRenderObjClass::Init_Type(const DazzleInitClass& i)
  560. {
  561. Init_Shaders();
  562. if (i.type>=type_count) {
  563. unsigned new_count=i.type+1;
  564. DazzleTypeClass** new_types=new DazzleTypeClass*[new_count];
  565. for (unsigned a=0;a<type_count;++a) {
  566. new_types[a]=types[a];
  567. }
  568. for (;a<new_count;++a) {
  569. new_types[a]=0;
  570. }
  571. delete[] types;
  572. types=new_types;
  573. type_count=new_count;
  574. }
  575. delete types[i.type];
  576. types[i.type]=new DazzleTypeClass(i);
  577. }
  578. // ----------------------------------------------------------------------------
  579. void DazzleRenderObjClass::Init_Lensflare(const LensflareInitClass& i)
  580. {
  581. Init_Shaders();
  582. if (i.type>=lensflare_count) {
  583. unsigned new_count=i.type+1;
  584. LensflareTypeClass** new_lensflares=new LensflareTypeClass*[new_count];
  585. for (unsigned a=0;a<lensflare_count;++a) {
  586. new_lensflares[a]=lensflares[a];
  587. }
  588. for (;a<new_count;++a) {
  589. new_lensflares[a]=0;
  590. }
  591. delete[] lensflares;
  592. lensflares=new_lensflares;
  593. lensflare_count=new_count;
  594. }
  595. delete lensflares[i.type];
  596. lensflares[i.type]=new LensflareTypeClass(i);
  597. }
  598. // ----------------------------------------------------------------------------
  599. void DazzleRenderObjClass::Deinit()
  600. {
  601. // Deinit dazzle types
  602. if (types) {
  603. for (unsigned a=0;a<type_count;++a) {
  604. delete types[a];
  605. }
  606. delete[] types;
  607. }
  608. types=NULL;
  609. type_count=0;
  610. // Deinit lensflare types
  611. if (lensflares) {
  612. for (unsigned a=0;a<lensflare_count;++a) {
  613. delete lensflares[a];
  614. }
  615. delete[] lensflares;
  616. }
  617. lensflares=NULL;
  618. lensflare_count=0;
  619. }
  620. void DazzleRenderObjClass::Install_Dazzle_Visibility_Handler(const DazzleVisibilityClass * visibility_handler)
  621. {
  622. if (visibility_handler == NULL) {
  623. _VisibilityHandler = &_DefaultVisibilityHandler;
  624. } else {
  625. _VisibilityHandler = visibility_handler;
  626. }
  627. }
  628. // ----------------------------------------------------------------------------
  629. //
  630. // The parameter t defines the dazzle type. t has to be a valid type id in order
  631. // for the dazzle to work.
  632. //
  633. // ----------------------------------------------------------------------------
  634. DazzleRenderObjClass::DazzleRenderObjClass(unsigned t)
  635. :
  636. succ(NULL),
  637. type(t),
  638. current_dazzle_intensity(0.0f),
  639. current_dazzle_size(0.0f),
  640. dazzle_color(1.0f,1.0f,1.0f),
  641. halo_color(1.0f,1.0f,1.0f),
  642. lensflare_intensity(1.0f),
  643. on_list(false),
  644. visibility(0.0f)
  645. {
  646. if (types && types[t]) {
  647. radius = types[t]->radius;
  648. } else {
  649. radius = 0.0f;
  650. }
  651. creation_time = WW3D::Get_Sync_Time();
  652. }
  653. // ----------------------------------------------------------------------------
  654. //
  655. // Creating a dazzle with its type name is a bit slower (due to scanning) but
  656. // works equally to the creation with id.
  657. //
  658. // ----------------------------------------------------------------------------
  659. DazzleRenderObjClass::DazzleRenderObjClass(const char * type_name)
  660. :
  661. succ(NULL),
  662. type(Get_Type_ID(type_name)),
  663. current_dazzle_intensity(0.0f),
  664. current_dazzle_size(0.0f),
  665. dazzle_color(1.0f,1.0f,1.0f),
  666. halo_color(1.0f,1.0f,1.0f),
  667. lensflare_intensity(1.0f),
  668. on_list(false),
  669. visibility(0.0f)
  670. {
  671. int id = Get_Type_ID(type_name);
  672. if (types && types[id]) {
  673. radius = types[id]->radius;
  674. } else {
  675. radius = 0.0f;
  676. }
  677. creation_time = WW3D::Get_Sync_Time();
  678. }
  679. // ----------------------------------------------------------------------------
  680. //
  681. // Copy constructor creates an exact copy of the object, except for the visibility
  682. // information, which is initialised with default values.
  683. //
  684. // ----------------------------------------------------------------------------
  685. DazzleRenderObjClass::DazzleRenderObjClass(const DazzleRenderObjClass & src)
  686. :
  687. succ(NULL),
  688. type(src.type),
  689. current_dazzle_intensity(src.current_dazzle_intensity),
  690. current_dazzle_size(src.current_dazzle_size),
  691. current_dir(src.current_dir),
  692. dazzle_color(src.dazzle_color),
  693. halo_color(src.halo_color),
  694. lensflare_intensity(src.lensflare_intensity),
  695. on_list(false),
  696. visibility(src.visibility),
  697. radius(src.radius)
  698. {
  699. creation_time = WW3D::Get_Sync_Time();
  700. }
  701. DazzleRenderObjClass& DazzleRenderObjClass::operator = (const DazzleRenderObjClass & src)
  702. {
  703. type=src.type;
  704. current_dir=src.current_dir;
  705. current_dazzle_intensity=src.current_dazzle_intensity;
  706. current_dazzle_size=src.current_dazzle_size;
  707. dazzle_color=src.dazzle_color;
  708. halo_color=src.halo_color;
  709. lensflare_intensity=src.lensflare_intensity;
  710. visibility=src.visibility;
  711. radius=src.radius;
  712. creation_time = WW3D::Get_Sync_Time();
  713. return *this;
  714. }
  715. void DazzleRenderObjClass::Get_Obj_Space_Bounding_Sphere(SphereClass & sphere) const
  716. {
  717. sphere.Center.Set(0,0,0);
  718. sphere.Radius = radius;
  719. }
  720. void DazzleRenderObjClass::Get_Obj_Space_Bounding_Box(AABoxClass & box) const
  721. {
  722. box.Center.Set(0,0,0);
  723. box.Extent.Set(radius,radius,radius);
  724. }
  725. void DazzleRenderObjClass::Set_Layer(DazzleLayerClass *layer)
  726. {
  727. // Never insert a dazzle into a list if it already is on one - this caould create infinite
  728. // loops in the dazzle list.
  729. if (on_list) return;
  730. // This function sets the dazzle to be visible in the given layer.
  731. if (!layer) {
  732. WWASSERT(0);
  733. return;
  734. }
  735. if (type>=type_count) return; // If the type doesn't exist the visibility can't be changed
  736. // Insert at the head of the layer's visible list
  737. succ = layer->visible_lists[type];
  738. layer->visible_lists[type] = this;
  739. on_list = true;
  740. Add_Ref();
  741. }
  742. void DazzleRenderObjClass::Set_Current_Dazzle_Layer(DazzleLayerClass *layer)
  743. {
  744. current_dazzle_layer = layer;
  745. }
  746. /////////////////////////////////////////////////////////////////////////////
  747. // Render Object Interface
  748. /////////////////////////////////////////////////////////////////////////////
  749. RenderObjClass* DazzleRenderObjClass::Clone(void) const
  750. {
  751. return NEW_REF(DazzleRenderObjClass, (*this));
  752. }
  753. // ----------------------------------------------------------------------------
  754. //
  755. // DazzleRenderObjClass's Render() function doesn't actually render the dazzle
  756. // immediatelly but just sets the dazzle visible. This is due to the way the
  757. // dazzle system works (the dazzles need to be rendered after everything else).
  758. // Having the Render() function flag the visibility offers us the visibility
  759. // functionality of the scene graph.
  760. //
  761. // ----------------------------------------------------------------------------
  762. void DazzleRenderObjClass::Render(RenderInfoClass & rinfo)
  763. {
  764. WWPROFILE("Dazzle::Render");
  765. if ( Is_Not_Hidden_At_All() &&
  766. _dazzle_rendering_enabled &&
  767. !DX8Wrapper::Is_Render_To_Texture() )
  768. {
  769. // First check if the dazzle is blinking and is "off"
  770. bool is_on = true;
  771. DazzleInitClass & ic = types[type]->ic;
  772. if (ic.blink_period > 0.0f) {
  773. float elapsed_time = ((float)(WW3D::Get_Sync_Time() - creation_time)) / 1000.0f;
  774. float wrapped_time = fmodf(elapsed_time,ic.blink_period);
  775. if (wrapped_time > ic.blink_on_time) {
  776. is_on = false;
  777. }
  778. }
  779. // Next, check visibility
  780. visibility = 1.0f;
  781. if (is_on == false) {
  782. visibility = 0.0f;
  783. } else {
  784. // Vector3 position;
  785. // Get_Transform().Get_Translation(&position);
  786. // visibility = _VisibilityHandler->Compute_Dazzle_Visibility(rinfo,this,position);
  787. Matrix4 view_transform,projection_transform;
  788. DX8Wrapper::Get_Transform(D3DTS_VIEW,view_transform);
  789. DX8Wrapper::Get_Transform(D3DTS_PROJECTION,projection_transform);
  790. Vector3 camera_loc(rinfo.Camera.Get_Position());
  791. Vector3 camera_dir(-view_transform[2][0],-view_transform[2][1],-view_transform[2][2]);
  792. // Matrix3D cam(rinfo.Camera.Get_Transform());
  793. // Vector3 camera_dir(-cam[2][0],-cam[2][1],-cam[2][2]);
  794. // camera_dir.Normalize();
  795. Vector3 loc=Get_Position();
  796. transformed_loc=view_transform*loc;
  797. transformed_loc=projection_transform*transformed_loc;
  798. transformed_loc[0]/=transformed_loc[3];
  799. transformed_loc[1]/=transformed_loc[3];
  800. transformed_loc[2]/=transformed_loc[3];
  801. transformed_loc[3]=1.0f;
  802. current_vloc=Vector3(transformed_loc[0],transformed_loc[1],transformed_loc[2]);
  803. float dazzle_intensity;
  804. Vector3 dir;
  805. dir=camera_loc-loc;
  806. current_distance=dir.Length2();
  807. dir.Normalize();
  808. dazzle_intensity=-Vector3::Dot_Product(dir,camera_dir);
  809. // dazzle_intensity*=visibility;
  810. float dazzle_size;
  811. current_halo_intensity=1.0f;
  812. const DazzleTypeClass* params=types[type];
  813. params->Calculate_Intensities(dazzle_intensity,dazzle_size,current_halo_intensity,camera_dir,current_dir,current_distance);
  814. unsigned time_ms=WW3D::Get_Frame_Time();
  815. if (time_ms==0) time_ms=1;
  816. float weight=pow(params->ic.history_weight,time_ms);
  817. if (dazzle_intensity>0.0f) {
  818. visibility = _VisibilityHandler->Compute_Dazzle_Visibility(rinfo,this,loc);
  819. //visibility=1.0f;
  820. dazzle_intensity*=visibility;
  821. }
  822. else {
  823. visibility=0.0f;
  824. }
  825. if (visibility == 0.0f) {
  826. float i=dazzle_intensity*(1.0f-weight)+current_dazzle_intensity*weight;
  827. current_dazzle_intensity=i;
  828. if (current_dazzle_intensity<0.05f) current_dazzle_intensity=0.0f;
  829. dazzle_intensity=i;
  830. float s=dazzle_size*(1.0f-weight)+current_dazzle_size*weight;
  831. current_dazzle_size=s;
  832. dazzle_size=s;
  833. } else {
  834. current_dazzle_intensity = dazzle_intensity;
  835. current_dazzle_size = dazzle_size;
  836. }
  837. }
  838. // If this dazzle is visible or it is currently fading, submit it for rendering
  839. if (/*visibility > 0.0f ||*/ current_dazzle_intensity>0.0f || current_halo_intensity>0.0f) {
  840. WWASSERT(types[type]);
  841. Set_Layer(current_dazzle_layer);
  842. }
  843. }
  844. else {
  845. visibility=0.0f;
  846. }
  847. }
  848. void DazzleRenderObjClass::Render_Dazzle(CameraClass* camera)
  849. {
  850. WWPROFILE("Dazzle::Render");
  851. Matrix4 old_view_transform;
  852. Matrix4 old_world_transform;
  853. Matrix4 old_projection_transform;
  854. Matrix4 view_transform;
  855. Matrix4 world_transform;
  856. Matrix4 projection_transform;
  857. DX8Wrapper::Get_Transform(D3DTS_VIEW,view_transform);
  858. DX8Wrapper::Get_Transform(D3DTS_WORLD,world_transform);
  859. DX8Wrapper::Get_Transform(D3DTS_PROJECTION,projection_transform);
  860. old_view_transform=view_transform;
  861. old_world_transform=world_transform;
  862. old_projection_transform=projection_transform;
  863. Vector3 camera_loc(camera->Get_Position());
  864. Vector3 camera_dir(-view_transform[2][0],-view_transform[2][1],-view_transform[2][2]);
  865. int display_width,display_height,display_bits;
  866. bool windowed;
  867. WW3D::Get_Device_Resolution(display_width,display_height,display_bits,windowed);
  868. float w=float(display_width);
  869. float h=float(display_height);
  870. float screen_x_scale=1.0f;
  871. float screen_y_scale=1.0f;
  872. if (w>h) {
  873. screen_y_scale=w/h;
  874. }
  875. else {
  876. screen_x_scale=h/w;
  877. }
  878. // unsigned time_ms=WW3D::Get_Frame_Time();
  879. // if (time_ms==0) time_ms=1;
  880. float halo_scale_x=types[type]->ic.halo_scale_x;
  881. float halo_scale_y=types[type]->ic.halo_scale_y;
  882. float dazzle_scale_x=types[type]->ic.dazzle_scale_x;
  883. float dazzle_scale_y=types[type]->ic.dazzle_scale_y;
  884. // Allocate some arrays for the dazzle rendering
  885. int vertex_count=4;
  886. const DazzleTypeClass* params=types[type];
  887. int halo_vertex_count=0;
  888. int dazzle_vertex_count=0;
  889. int lensflare_vertex_count=0;
  890. Vector3 dl;
  891. int lens_max_verts=0;
  892. LensflareTypeClass* lensflare = DazzleRenderObjClass::Get_Lensflare_Class(types[type]->lensflare_id);
  893. if (lensflare) {
  894. lens_max_verts=4*lensflare->lic.flare_count;
  895. }
  896. DynamicVBAccessClass vb_access(BUFFER_TYPE_DYNAMIC_DX8,dynamic_fvf_type,vertex_count*2+lens_max_verts);
  897. {
  898. DynamicVBAccessClass::WriteLockClass lock(&vb_access);
  899. VertexFormatXYZNDUV2* verts=lock.Get_Formatted_Vertex_Array();
  900. float halo_size=1.0f;
  901. Vector3 dazzle_dxt(screen_x_scale,0.0f,0.0f);
  902. Vector3 halo_dxt=dazzle_dxt*halo_scale_x;
  903. dazzle_dxt*=dazzle_scale_x;
  904. Vector3 dazzle_dyt(0.0f,screen_y_scale,0.0f);
  905. Vector3 halo_dyt=dazzle_dyt*halo_scale_y;
  906. dazzle_dyt*=dazzle_scale_y;
  907. if (current_dazzle_intensity>0.0f) {
  908. VertexFormatXYZNDUV2* vertex=verts;
  909. dazzle_vertex_count+=4;
  910. Vector3 col(
  911. dazzle_color[0]*params->ic.dazzle_color[0],
  912. dazzle_color[1]*params->ic.dazzle_color[1],
  913. dazzle_color[2]*params->ic.dazzle_color[2]);
  914. col*=current_dazzle_intensity;
  915. if (col[0]>1.0f) col[0]=1.0f;
  916. if (col[1]>1.0f) col[1]=1.0f;
  917. if (col[2]>1.0f) col[2]=1.0f;
  918. unsigned color=DX8Wrapper::Convert_Color(col,1.0f);
  919. dl=current_vloc+(dazzle_dxt-dazzle_dyt)*current_dazzle_size;
  920. reinterpret_cast<Vector3&>(vertex->x)=dl;
  921. vertex->u1=0.0f;
  922. vertex->v1=0.0f;
  923. vertex->diffuse=color;
  924. vertex++;
  925. dl=current_vloc+(dazzle_dxt+dazzle_dyt)*current_dazzle_size;
  926. reinterpret_cast<Vector3&>(vertex->x)=dl;
  927. vertex->u1=1.0f;
  928. vertex->v1=0.0f;
  929. vertex->diffuse=color;
  930. vertex++;
  931. dl=current_vloc-(dazzle_dxt-dazzle_dyt)*current_dazzle_size;
  932. reinterpret_cast<Vector3&>(vertex->x)=dl;
  933. vertex->u1=1.0f;
  934. vertex->v1=1.0f;
  935. vertex->diffuse=color;
  936. vertex++;
  937. dl=current_vloc-(dazzle_dxt+dazzle_dyt)*current_dazzle_size;
  938. reinterpret_cast<Vector3&>(vertex->x)=dl;
  939. vertex->u1=0.0f;
  940. vertex->v1=1.0f;
  941. vertex->diffuse=color;
  942. }
  943. if (current_halo_intensity) {
  944. VertexFormatXYZNDUV2* vertex=verts+dazzle_vertex_count;
  945. halo_vertex_count+=4;
  946. Vector3 col(
  947. halo_color[0]*params->ic.halo_color[0],
  948. halo_color[1]*params->ic.halo_color[1],
  949. halo_color[2]*params->ic.halo_color[2]);
  950. col*=current_halo_intensity;
  951. if (col[0]>1.0f) col[0]=1.0f;
  952. if (col[1]>1.0f) col[1]=1.0f;
  953. if (col[2]>1.0f) col[2]=1.0f;
  954. unsigned color=DX8Wrapper::Convert_Color(col,1.0f);
  955. dl=current_vloc+(halo_dxt-halo_dyt)*halo_size;
  956. reinterpret_cast<Vector3&>(vertex->x)=dl;
  957. vertex->u1=0.0f;
  958. vertex->v1=0.0f;
  959. vertex->diffuse=color;
  960. vertex++;
  961. dl=current_vloc+(halo_dxt+halo_dyt)*halo_size;
  962. reinterpret_cast<Vector3&>(vertex->x)=dl;
  963. vertex->u1=1.0f;
  964. vertex->v1=0.0f;
  965. vertex->diffuse=color;
  966. vertex++;
  967. dl=current_vloc-(halo_dxt-halo_dyt)*halo_size;
  968. reinterpret_cast<Vector3&>(vertex->x)=dl;
  969. vertex->u1=1.0f;
  970. vertex->v1=1.0f;
  971. vertex->diffuse=color;
  972. vertex++;
  973. dl=current_vloc-(halo_dxt+halo_dyt)*halo_size;
  974. reinterpret_cast<Vector3&>(vertex->x)=dl;
  975. vertex->u1=0.0f;
  976. vertex->v1=1.0f;
  977. vertex->diffuse=color;
  978. }
  979. if (lensflare && current_dazzle_intensity>0.0f) {
  980. VertexFormatXYZNDUV2* vertex=verts+halo_vertex_count+dazzle_vertex_count;
  981. lensflare->Generate_Vertex_Buffers(
  982. vertex,
  983. lensflare_vertex_count,
  984. screen_x_scale,
  985. screen_y_scale,
  986. current_dazzle_intensity * lensflare_intensity,
  987. transformed_loc);
  988. vertex_count+=lensflare_vertex_count;
  989. }
  990. }
  991. int dazzle_poly_count=dazzle_vertex_count>>1;
  992. int halo_poly_count=halo_vertex_count>>1;
  993. int lensflare_poly_count=lensflare_vertex_count>>1;
  994. int poly_count=halo_poly_count>dazzle_poly_count ? halo_poly_count : dazzle_poly_count;
  995. if (lensflare_poly_count>poly_count) poly_count=lensflare_poly_count;
  996. if (!poly_count) {
  997. return;
  998. }
  999. DX8Wrapper::Set_Vertex_Buffer(vb_access);
  1000. DynamicIBAccessClass ib_access(BUFFER_TYPE_DYNAMIC_DX8,poly_count*3);
  1001. {
  1002. DynamicIBAccessClass::WriteLockClass lock(&ib_access);
  1003. unsigned short* inds=lock.Get_Index_Array();
  1004. // Proceed two polygons at a time
  1005. for (int a=0;a<poly_count/2;a++) {
  1006. *inds++=short(4*a);
  1007. *inds++=short(4*a+1);
  1008. *inds++=short(4*a+2);
  1009. *inds++=short(4*a);
  1010. *inds++=short(4*a+2);
  1011. *inds++=short(4*a+3);
  1012. }
  1013. }
  1014. DX8Wrapper::Set_World_Identity();
  1015. DX8Wrapper::Set_View_Identity();
  1016. DX8Wrapper::Set_Transform(D3DTS_PROJECTION,Matrix4(true));
  1017. if (halo_poly_count) {
  1018. DX8Wrapper::Set_Index_Buffer(ib_access,dazzle_vertex_count);
  1019. DX8Wrapper::Set_Shader(default_halo_shader);
  1020. DX8Wrapper::Set_Texture(0,types[type]->Get_Halo_Texture());
  1021. SphereClass sphere(Get_Position(),0.1f);
  1022. DX8Wrapper::Draw_Triangles(0,halo_poly_count,0,vertex_count);
  1023. }
  1024. if (dazzle_poly_count) {
  1025. DX8Wrapper::Set_Index_Buffer(ib_access,0);
  1026. DX8Wrapper::Set_Shader(default_dazzle_shader);
  1027. DX8Wrapper::Set_Texture(0,types[type]->Get_Dazzle_Texture());
  1028. SphereClass sphere(Vector3(0.0f,0.0f,0.0f),0.0f);
  1029. DX8Wrapper::Draw_Triangles(0,dazzle_poly_count,0,vertex_count);
  1030. }
  1031. if (lensflare_poly_count) {
  1032. DX8Wrapper::Set_Index_Buffer(ib_access,dazzle_vertex_count+halo_vertex_count);
  1033. DX8Wrapper::Set_Shader(default_dazzle_shader);
  1034. DX8Wrapper::Set_Texture(0,lensflare->Get_Texture());
  1035. SphereClass sphere(Vector3(0.0f,0.0f,0.0f),0.0f);
  1036. DX8Wrapper::Draw_Triangles(0,lensflare_poly_count,0,vertex_count);
  1037. }
  1038. DX8Wrapper::Set_Transform(D3DTS_PROJECTION,old_projection_transform);
  1039. DX8Wrapper::Set_Transform(D3DTS_VIEW,old_view_transform);
  1040. DX8Wrapper::Set_Transform(D3DTS_WORLD,old_world_transform);
  1041. }
  1042. // ----------------------------------------------------------------------------
  1043. void DazzleRenderObjClass::Set_Transform(const Matrix3D &m)
  1044. {
  1045. RenderObjClass::Set_Transform(m);
  1046. if (type<type_count) {
  1047. Matrix3D::Rotate_Vector(m,types[type]->ic.dazzle_direction,&current_dir);
  1048. }
  1049. }
  1050. // ----------------------------------------------------------------------------
  1051. //
  1052. // Return the type id of a dazzle class with given name. If such type is not
  1053. // found, return UINT_MAX.
  1054. //
  1055. // ----------------------------------------------------------------------------
  1056. unsigned DazzleRenderObjClass::Get_Type_ID(const char* name)
  1057. {
  1058. for (unsigned a=0;a<type_count;++a) {
  1059. if (types[a] && types[a]->name==name) return a;
  1060. }
  1061. return UINT_MAX;
  1062. }
  1063. // ----------------------------------------------------------------------------
  1064. //
  1065. // Return the type name of a dazzle class with given id. If the id is out
  1066. // of range, return "DEFAULT" which by convention is always defined and is
  1067. // id 0.
  1068. //
  1069. // ----------------------------------------------------------------------------
  1070. const char * DazzleRenderObjClass::Get_Type_Name(unsigned id)
  1071. {
  1072. if ((id < type_count) && (id >= 0)) {
  1073. return types[id]->name;
  1074. } else {
  1075. return "DEFAULT";
  1076. }
  1077. }
  1078. // ----------------------------------------------------------------------------
  1079. //
  1080. // Return pointer to DazzleTypeClass object with given id. If the id is out
  1081. // of range (usually UINT_MAX, in can the id was obtained with invalid name
  1082. // string) return NULL.
  1083. //
  1084. // ----------------------------------------------------------------------------
  1085. DazzleTypeClass* DazzleRenderObjClass::Get_Type_Class(unsigned id) // Return dazzle type class pointer, or NULL if not found
  1086. {
  1087. if (id>=type_count) return NULL;
  1088. return types[id];
  1089. }
  1090. // ----------------------------------------------------------------------------
  1091. //
  1092. // Return the type id of a lensflare type class with given name. If such type is
  1093. // not found, return UINT_MAX.
  1094. //
  1095. // ----------------------------------------------------------------------------
  1096. unsigned DazzleRenderObjClass::Get_Lensflare_ID(const char* name)
  1097. {
  1098. for (unsigned a=0;a<lensflare_count;++a) {
  1099. if (lensflares[a] && lensflares[a]->name==name) return a;
  1100. }
  1101. return UINT_MAX;
  1102. }
  1103. // ----------------------------------------------------------------------------
  1104. //
  1105. // Return pointer to LensflareTypeClass object with given id. If the id is out
  1106. // of range (usually UINT_MAX, in can the id was obtained with invalid name
  1107. // string) return NULL.
  1108. //
  1109. // ----------------------------------------------------------------------------
  1110. LensflareTypeClass* DazzleRenderObjClass::Get_Lensflare_Class(unsigned id) // Return lensflare type class pointer, or NULL if not found
  1111. {
  1112. if (id>=lensflare_count) return NULL;
  1113. return lensflares[id];
  1114. }
  1115. // ----------------------------------------------------------------------------
  1116. //
  1117. // Should static dazzles require vis information, here's a function that renders
  1118. // a quad at the location of the dazzle
  1119. //
  1120. // ----------------------------------------------------------------------------
  1121. void DazzleRenderObjClass::vis_render_dazzle(SpecialRenderInfoClass & rinfo)
  1122. {
  1123. WWASSERT(rinfo.VisRasterizer != NULL);
  1124. rinfo.VisRasterizer->Enable_Two_Sided_Rendering(true);
  1125. /*
  1126. ** Create a transform which is facing the camera
  1127. */
  1128. Vector3 cam_point = rinfo.VisRasterizer->Peek_Camera()->Get_Transform().Get_Translation();
  1129. Vector3 daz_point = Get_Transform().Get_Translation();
  1130. Matrix3D tm;
  1131. tm.Look_At(daz_point,cam_point,0.0f);
  1132. rinfo.VisRasterizer->Set_Model_Transform(tm);
  1133. /*
  1134. ** Now, generate a single triangle on the X-Y plane
  1135. */
  1136. Vector3 verts[4];
  1137. TriIndex polys[2];
  1138. polys[0] = TriIndex(0,1,2);
  1139. polys[1] = TriIndex(0,2,3);
  1140. Vector2 view_min,view_max;
  1141. rinfo.VisRasterizer->Peek_Camera()->Get_View_Plane(view_min,view_max);
  1142. float scale_x=types[type]->ic.halo_scale_x;
  1143. if ((scale_x < 0.001f) && (types[type]->ic.dazzle_scale_x > scale_x)) {
  1144. scale_x = types[type]->ic.dazzle_scale_x;
  1145. }
  1146. float scale_y=types[type]->ic.halo_scale_y;
  1147. if ((scale_y < 0.001f) && (types[type]->ic.dazzle_scale_y > scale_y)) {
  1148. scale_y = types[type]->ic.dazzle_scale_y;
  1149. }
  1150. float dist = (daz_point - cam_point).Length();
  1151. Vector3 dxt(dist * scale_x / (view_max.X - view_min.X),0.0f,0.0f);
  1152. Vector3 dyt(0.0f,dist * scale_y / (view_max.Y - view_min.Y),0.0f);
  1153. verts[0].Set(dxt+dyt);
  1154. verts[1].Set(dxt-dyt);
  1155. verts[2].Set(-dxt-dyt);
  1156. verts[3].Set(-dxt+dyt);
  1157. AABoxClass bounds;
  1158. float extent = 1.1f * (dxt+dyt).Length();
  1159. bounds.Center = daz_point; //making up a conservative bounding box
  1160. bounds.Extent.Set(extent,extent,extent);
  1161. /*
  1162. ** Render
  1163. */
  1164. rinfo.VisRasterizer->Enable_Two_Sided_Rendering(true);
  1165. rinfo.VisRasterizer->Render_Triangles(verts,4,polys,2,bounds);
  1166. rinfo.VisRasterizer->Enable_Two_Sided_Rendering(false);
  1167. }
  1168. void DazzleRenderObjClass::Special_Render(SpecialRenderInfoClass & rinfo)
  1169. {
  1170. if (rinfo.RenderType == SpecialRenderInfoClass::RENDER_VIS) {
  1171. vis_render_dazzle(rinfo);
  1172. }
  1173. }
  1174. /****************************************************************************************
  1175. DazzleRenderObjClass - Persistant object support.
  1176. Dazzles are going to save their type and their transform and simply
  1177. re-create another dazzle of the same type when loaded.
  1178. ****************************************************************************************/
  1179. class DazzlePersistFactoryClass : public PersistFactoryClass
  1180. {
  1181. virtual uint32 Chunk_ID(void) const;
  1182. virtual PersistClass * Load(ChunkLoadClass & cload) const;
  1183. virtual void Save(ChunkSaveClass & csave,PersistClass * obj) const;
  1184. enum
  1185. {
  1186. DAZZLEFACTORY_CHUNKID_VARIABLES = 1212000336,
  1187. DAZZLEFACTORY_VARIABLE_OBJPOINTER = 0x00,
  1188. OBSOLETE_DAZZLEFACTORY_VARIABLE_TYPE,
  1189. DAZZLEFACTORY_VARIABLE_TRANSFORM,
  1190. DAZZLEFACTORY_VARIABLE_TYPENAME,
  1191. };
  1192. };
  1193. static DazzlePersistFactoryClass _DazzleFactory;
  1194. uint32 DazzlePersistFactoryClass::Chunk_ID(void) const
  1195. {
  1196. return WW3D_PERSIST_CHUNKID_DAZZLE;
  1197. }
  1198. PersistClass * DazzlePersistFactoryClass::Load(ChunkLoadClass & cload) const
  1199. {
  1200. DazzleRenderObjClass * old_obj = NULL;
  1201. Matrix3D tm(1);
  1202. char dazzle_type[256];
  1203. dazzle_type[0] = 0;
  1204. /*
  1205. ** Load the dazzle parameters
  1206. */
  1207. while (cload.Open_Chunk()) {
  1208. switch (cload.Cur_Chunk_ID()) {
  1209. case DAZZLEFACTORY_CHUNKID_VARIABLES:
  1210. while (cload.Open_Micro_Chunk()) {
  1211. switch(cload.Cur_Micro_Chunk_ID()) {
  1212. READ_MICRO_CHUNK(cload,DAZZLEFACTORY_VARIABLE_OBJPOINTER,old_obj);
  1213. READ_MICRO_CHUNK(cload,DAZZLEFACTORY_VARIABLE_TRANSFORM,tm);
  1214. READ_MICRO_CHUNK_STRING(cload,DAZZLEFACTORY_VARIABLE_TYPENAME,dazzle_type,sizeof(dazzle_type));
  1215. }
  1216. cload.Close_Micro_Chunk();
  1217. }
  1218. break;
  1219. default:
  1220. WWDEBUG_SAY(("Unhandled Chunk: 0x%X File: %s Line: %d\r\n",__FILE__,__LINE__));
  1221. break;
  1222. };
  1223. cload.Close_Chunk();
  1224. }
  1225. /*
  1226. ** Create a new dazzle object
  1227. */
  1228. int type_index = 0;
  1229. if (strlen(dazzle_type) > 0) {
  1230. type_index = DazzleRenderObjClass::Get_Type_ID(dazzle_type);
  1231. }
  1232. RenderObjClass * new_obj = NEW_REF(DazzleRenderObjClass,(dazzle_type));
  1233. /*
  1234. ** If we failed to create it, replace it with a NULL
  1235. */
  1236. if (new_obj == NULL) {
  1237. static int count = 0;
  1238. if ( ++count < 10 ) {
  1239. WWDEBUG_SAY(("DazzlePersistFactory failed to create dazzle of type: %s!!\r\n",dazzle_type));
  1240. WWDEBUG_SAY(("Replacing it with a NULL render object!\r\n"));
  1241. }
  1242. new_obj = WW3DAssetManager::Get_Instance()->Create_Render_Obj("NULL");
  1243. }
  1244. WWASSERT(new_obj != NULL);
  1245. if (new_obj) {
  1246. new_obj->Set_Transform(tm);
  1247. }
  1248. /*
  1249. ** Register the old pointer for re-mapping to the new pointer
  1250. */
  1251. SaveLoadSystemClass::Register_Pointer(old_obj,new_obj);
  1252. return new_obj;
  1253. }
  1254. void DazzlePersistFactoryClass::Save(ChunkSaveClass & csave,PersistClass * obj) const
  1255. {
  1256. DazzleRenderObjClass * robj = (DazzleRenderObjClass *)obj;
  1257. unsigned int dazzle_type = robj->Get_Dazzle_Type();
  1258. const char * dazzle_type_name = DazzleRenderObjClass::Get_Type_Name(dazzle_type);
  1259. Matrix3D tm = robj->Get_Transform();
  1260. csave.Begin_Chunk(DAZZLEFACTORY_CHUNKID_VARIABLES);
  1261. WRITE_MICRO_CHUNK(csave,DAZZLEFACTORY_VARIABLE_OBJPOINTER,robj);
  1262. WRITE_MICRO_CHUNK(csave,DAZZLEFACTORY_VARIABLE_TRANSFORM,tm);
  1263. WRITE_MICRO_CHUNK_STRING(csave,DAZZLEFACTORY_VARIABLE_TYPENAME,dazzle_type_name);
  1264. csave.End_Chunk();
  1265. }
  1266. /*
  1267. ** DazzleRenderObj save-load.
  1268. */
  1269. const PersistFactoryClass & DazzleRenderObjClass::Get_Factory (void) const
  1270. {
  1271. return _DazzleFactory;
  1272. }
  1273. /**********************************************************************************************
  1274. **
  1275. ** DazzleLayerClass Implementation
  1276. **
  1277. **********************************************************************************************/
  1278. DazzleLayerClass::DazzleLayerClass(void) :
  1279. visible_lists(NULL)
  1280. {
  1281. if (type_count != 0) {
  1282. // Generate an array with one visible list for each type.
  1283. // NOTE - this means that this constructor must be called AFTER all types
  1284. // are initialized
  1285. WWASSERT(type_count);
  1286. visible_lists = new DazzleRenderObjClass *[type_count];
  1287. for (unsigned int i = 0; i < type_count; i++) {
  1288. visible_lists[i] = NULL;
  1289. }
  1290. }
  1291. }
  1292. DazzleLayerClass::~DazzleLayerClass(void)
  1293. {
  1294. // NOTE - this destructor must be called BEFORE DeInit().
  1295. WWASSERT(type_count);
  1296. for (unsigned int i = 0; i < type_count; i++) {
  1297. Clear_Visible_List(i);
  1298. }
  1299. delete [] visible_lists;
  1300. }
  1301. void DazzleLayerClass::Render(CameraClass* camera)
  1302. {
  1303. if (!camera) return;
  1304. camera->Apply();
  1305. unsigned time_ms=WW3D::Get_Frame_Time();
  1306. if (time_ms==0) time_ms=1;
  1307. DX8Wrapper::Set_Material(NULL);
  1308. for (unsigned type=0;type<type_count;++type) {
  1309. if (!types[type]) continue;
  1310. int count = Get_Visible_Item_Count(type);
  1311. if (!count) continue;
  1312. DazzleRenderObjClass* n = visible_lists[type];
  1313. while (n) {
  1314. n->Render_Dazzle(camera);
  1315. n=n->Succ();
  1316. }
  1317. // Must clear the visible list at the end of each render.
  1318. Clear_Visible_List(type);
  1319. }
  1320. }
  1321. // ----------------------------------------------------------------------------
  1322. int DazzleLayerClass::Get_Visible_Item_Count(unsigned int type) const
  1323. {
  1324. if (type >= type_count) {
  1325. WWASSERT(0);
  1326. return 0;
  1327. }
  1328. int count=0;
  1329. DazzleRenderObjClass* n = visible_lists[type];
  1330. while (n) {
  1331. count++;
  1332. n=n->Succ();
  1333. }
  1334. return count;
  1335. }
  1336. // ----------------------------------------------------------------------------
  1337. void DazzleLayerClass::Clear_Visible_List(unsigned int type)
  1338. {
  1339. if (type >= type_count) {
  1340. WWASSERT(0);
  1341. return;
  1342. }
  1343. DazzleRenderObjClass* n = visible_lists[type];
  1344. while (n) {
  1345. n->Release_Ref();
  1346. n->on_list = false;
  1347. n=n->Succ();
  1348. }
  1349. visible_lists[type] = NULL;
  1350. }
  1351. /**********************************************************************************************
  1352. **
  1353. ** DazzleVisibilityClass Implementation
  1354. ** The default dazzle visibility handler asks the scene to determine whether the dazzle
  1355. ** is occluded.
  1356. **
  1357. **********************************************************************************************/
  1358. float DazzleVisibilityClass::Compute_Dazzle_Visibility
  1359. (
  1360. RenderInfoClass & rinfo,
  1361. DazzleRenderObjClass * dazzle,
  1362. const Vector3 & point
  1363. ) const
  1364. {
  1365. /*
  1366. ** Look up the scene this dazzle is in
  1367. */
  1368. SceneClass * scene = dazzle->Get_Scene();
  1369. RenderObjClass * container = dazzle->Get_Container();
  1370. while ((scene == NULL) && (container != NULL)) {
  1371. scene = container->Get_Scene();
  1372. container = container->Get_Container();
  1373. }
  1374. /*
  1375. ** If we found the scene (we SHOULD!) then ask it to compute the visibility
  1376. */
  1377. if (scene != NULL) {
  1378. float value = scene->Compute_Point_Visibility(rinfo,point);
  1379. scene->Release_Ref();
  1380. return value;
  1381. } else {
  1382. return 1.0f;
  1383. }
  1384. }
  1385. /**********************************************************************************************
  1386. **
  1387. ** DazzlePrototypeClass Implementation
  1388. **
  1389. **********************************************************************************************/
  1390. RenderObjClass * DazzlePrototypeClass::Create(void)
  1391. {
  1392. return NEW_REF(DazzleRenderObjClass,(DazzleType));
  1393. }
  1394. WW3DErrorType DazzlePrototypeClass::Load_W3D(ChunkLoadClass & cload)
  1395. {
  1396. StringClass dazzle_type;
  1397. while (cload.Open_Chunk()) {
  1398. switch (cload.Cur_Chunk_ID())
  1399. {
  1400. READ_WWSTRING_CHUNK(cload,W3D_CHUNK_DAZZLE_NAME,Name);
  1401. READ_WWSTRING_CHUNK(cload,W3D_CHUNK_DAZZLE_TYPENAME,dazzle_type);
  1402. default:
  1403. break;
  1404. }
  1405. cload.Close_Chunk();
  1406. }
  1407. DazzleType = DazzleRenderObjClass::Get_Type_ID(dazzle_type);
  1408. if (DazzleType == UINT_MAX) {
  1409. DazzleType = 0;
  1410. }
  1411. return WW3D_ERROR_OK;
  1412. }
  1413. /**********************************************************************************************
  1414. **
  1415. ** DazzleLoaderClass Implementation
  1416. **
  1417. **********************************************************************************************/
  1418. PrototypeClass * DazzleLoaderClass::Load_W3D(ChunkLoadClass & cload)
  1419. {
  1420. DazzlePrototypeClass * new_proto = new DazzlePrototypeClass;
  1421. new_proto->Load_W3D(cload);
  1422. return new_proto;
  1423. }