#include "mungal4.h" #pragma hdrstop #include "l4vidrnd.h" #include "..\munga\vector2d.h" #include "..\munga\matrix.h" #include "..\munga\mover.h" #include "..\munga\player.h" #include "l4video.h" #include "..\munga\nttmgr.h" #include "l4app.h" #include "..\RP\VTV.h" // RB 1/14/07 //#include //#include //#include //#include //#include #if defined(TRACE_VIDEO_MECH_CULL_RENDERABLE) static BitTrace Video_Mech_Cull_Renderable("Video Mech Cull Renderable"); #define SET_VIDEO_MECH_CULL_RENDERABLE() Video_Mech_Cull_Renderable.Set() #define CLEAR_VIDEO_MECH_CULL_RENDERABLE() Video_Mech_Cull_Renderable.Clear() #else #define SET_VIDEO_MECH_CULL_RENDERABLE() #define CLEAR_VIDEO_MECH_CULL_RENDERABLE() #endif // // Below allows the use of DPLDelayDCSFlush to be on or off // #if 1 # define HACK_DPL_FLUSH_DCS(a)\ {L4Application *l4_application = Cast_Object(L4Application*, application);\ Check(l4_application);\ l4_application->GetVideoRenderer()->DPLDelayDCSFlush(a);} # define DPL_FLUSH_DCS(a)\ {myRenderer->DPLDelayDCSFlush(a);} #else # define DPL_FLUSH_DCS(a)\ dpl_FlushDCS(a) # define HACK_DPL_FLUSH_DCS(a)\ dpl_FlushDCS(a) #endif // // All renderables that need to use "Now()" should use renderer frame time // as it should be much quicker (it returns the time at the start of the // frame execution. All the renderables should know which renderer they belong // to, but since many don't, this macro will supply the time from the default one // #define GET_CURRENT_FRAME_TIME() \ {L4Application *l4_application = Cast_Object(L4Application*, application);\ Check(l4_application);\ l4_application->GetVideoRenderer()->GetCurrentFrameTime();} //===========================================================================// //===========================================================================// //===========================================================================// //===========================================================================// // All the stuff between these big ugly bars is the new video component stuff// //===========================================================================// //===========================================================================// //===========================================================================// //===========================================================================// HierarchicalDrawComponent::HierarchicalDrawComponent(RegisteredClass::ClassID classId) :Component(classId), isDeathDraw(false) { L4Application *l4_application = Cast_Object(L4Application*, application); myRenderer = l4_application->GetVideoRenderer(); m_parent = NULL; } HierarchicalDrawComponent::HierarchicalDrawComponent(RegisteredClass::ClassID classId, HierarchicalDrawComponent *parent) :Component(classId), isDeathDraw(false), graphicalObject(NULL) { L4Application *l4_application = Cast_Object(L4Application*, application); Check(l4_application); myRenderer = l4_application->GetVideoRenderer(); m_parent = parent; if (m_parent != NULL) { m_parent->addChild(this); } } HierarchicalDrawComponent::~HierarchicalDrawComponent() { if (m_parent != NULL) { m_parent->removeChild(this); } for (int i=0; i < m_children.size(); i++) { m_children[i]->clearParent(); } m_children.clear(); } void HierarchicalDrawComponent::ExecuteChildren() { std::vector::iterator iter = m_children.begin(); while(iter != m_children.end()) { (*iter)->Execute(); iter++; } } std::vector::const_iterator HierarchicalDrawComponent::Enumerate() { return this->m_children.begin(); } std::vector::const_iterator HierarchicalDrawComponent::End() { return this->m_children.end(); } void HierarchicalDrawComponent::ResetDrawObj() { this->graphicalObject = NULL; } void HierarchicalDrawComponent::Execute() { ExecuteChildren(); if (graphicalObject != NULL) { if (isDeathDraw || !l4_application->IsDead()) { bool addedToOpaqueList = false, addedToAlphaList = false, addedToDecalList = false, addedToSphereList = false, addedToSkyList = false; for (int i=0; iGetDrawOpCount(); i++) { if (graphicalObject->GetDrawOp(i)->alphaTest) { if (!addedToAlphaList) { myRenderer->AddToPassList(graphicalObject, PASS_ALPHABLEND); addedToAlphaList = true; } } else if (graphicalObject->GetDrawOp(i)->drawAsDecal) { if (!addedToDecalList) { myRenderer->AddToPassList(graphicalObject, PASS_DECAL); addedToDecalList = true; } } else if (graphicalObject->GetDrawOp(i)->drawAsSky) { if (!addedToSkyList) { myRenderer->AddToPassList(graphicalObject, PASS_SKY); addedToSkyList = true; } } else if (graphicalObject->GetMesh() == NULL) { if (!addedToSphereList) { myRenderer->AddToPassList(graphicalObject, PASS_SPHERE); addedToSphereList = true; } } else { if (!addedToOpaqueList) { myRenderer->AddToPassList(graphicalObject, PASS_OPAQUE); addedToOpaqueList = true; } } } } } } void HierarchicalDrawComponent::Render(int pass, const D3DXMATRIX *viewTransform) { //if (graphicalObject != NULL && (isDeathDraw || l4_application->GetMissionPlayer()->GetPlayerVehicle()->GetSimulationState() != VTV::BurningState)) //{ // myRenderer->GetDevice()->SetTransform(D3DTS_WORLD, &myLocalToWorld); // graphicalObject->Draw(pass, &myLocalToWorld, viewTransform); //} //std::vector::iterator iter = m_children.begin(); //while (iter != m_children.end()) //{ // (*iter)->Render(pass, viewTransform); // iter++; //} } void HierarchicalDrawComponent::addChild(HierarchicalDrawComponent *child) { m_children.insert(m_children.end(), child); } void HierarchicalDrawComponent::removeChild(HierarchicalDrawComponent *child) { //Seek and remove std::vector::iterator iter = m_children.begin(); while(iter != m_children.end()) { if (child == (*iter)) { m_children.erase(iter); child->clearParent(); break; } iter++; } } void HierarchicalDrawComponent::clearParent() { m_parent = NULL; } // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~This is a special class to speed up projectiles~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for InnerProjectileRenderable // InnerProjectileRenderable::InnerProjectileRenderable( d3d_OBJECT *graphical_object, // object to hang on the DCS, may be a list later bool isDeathZone // DPL Zone this stuff will live in (for culling) ): HierarchicalDrawComponent(TrivialNodeClassID) // Inherited constructor { isDeathDraw = isDeathZone; graphicalObject = graphical_object; //STUBBED: DPL RB 1/14/07 //// //// Check incoming data //// //Check_Pointer(this_zone); //Check_Pointer(graphical_object); //// //// Construct the hiearchy the projectile needs to be renderable //// //myDCS = dpl_NewDCS (); //myInstance = dpl_NewInstance(); //Check_Pointer (myDCS); //Check_Pointer (myInstance); //dpl_SetDCSZone (myDCS, this_zone); //dpl_SetInstanceObject (myInstance, graphical_object); //dpl_SetInstanceIntersect (myInstance, dpl_isect_mode_obj ); //dpl_SetInstanceSectMask (myInstance, NULL ); //dpl_SetInstanceVisibility (myInstance, 1 ); //dpl_AddInstanceToDCS (myDCS, myInstance ); //dpl_AddDCSToScene (myDCS ); //dpl_FlushInstance (myInstance); //dpl_FlushDCS (myDCS); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for InnerProjectileRenderable // InnerProjectileRenderable::~InnerProjectileRenderable() { //STUBBED: DPL RB 1/14/07 //// //// Check our structure before we do anything //// //Check(this); //// //// Delete the instance(s) hanging on the DCS (if any) //// NOTE: we may want to iterate through all the instances here using DPL routines //// //dpl_RemoveInstanceFromDCS(myDCS, myInstance); //dpl_RemoveDCSFromScene(myDCS); //dpl_DeleteInstance(myInstance); //// //// Delete the DCS //// //dpl_DeleteDCS(myDCS); //myDCS = NULL; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the InnerProjectileRenderable // Logical InnerProjectileRenderable::TestInstance() const { // // Call our parent's TestInstance first // Component::TestInstance(); // // Test our own variables // Check_Pointer(myInstance); Check_Pointer(myDCS); return True; } void InnerProjectileRenderable::Execute() { //myLocalToWorld = *myRenderer->GetMatrixStack()->GetTop(); SetLocalToWorld(myRenderer->GetMatrixStack()->GetTop()); HierarchicalDrawComponent::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for ProjectileRootRenderable // ProjectileRootRenderable::ProjectileRootRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable d3d_OBJECT *graphical_object, // object to hang on the DCS, may be a list later bool isDeathZone // DPL Zone this stuff will live in (for culling) ): VideoRenderable(entity, execution_type) { isDeathDraw = isDeathZone; // // Check the incoming pointers // Check_Pointer(graphical_object); //Check_Pointer(this_zone); // // Get a projectile renderable we can use // L4Application *l4_application = Cast_Object(L4Application*, application); Check(l4_application); myInnerProjectile = l4_application->GetVideoRenderer()->GetProjectile( graphical_object, isDeathZone); Check(myInnerProjectile); addChild(myInnerProjectile); oldLocalToWorld = myEntity->localToWorld; transMatrix = myEntity->localToWorld; ////This is necessary? //myRenderer->mRenderables.Add(this); l4_application->GetVideoRenderer()->AddRenderable(this); // // Set the DCS matrix and std::flush it // //float32* tempMatrix = dpl_GetDCSMatrix( myInnerProjectile->GetDCS()); //Check_Pointer ( tempMatrix ); //*(Matrix4x4*)tempMatrix = myEntity->localToWorld; //DPL_FLUSH_DCS ( myInnerProjectile->GetDCS()); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for ProjectileRootRenderable // ProjectileRootRenderable::~ProjectileRootRenderable() { // // Check our structure before we do anything // Check(this); // // return our inner renderable to the pool // Point3D infinity(0.0f, 10000.0f, 0.0f); transMatrix = infinity; //float32* tempMatrix = dpl_GetDCSMatrix(myInnerProjectile->GetDCS()); //Check_Pointer (tempMatrix); //*(Matrix4x4*)tempMatrix = infinity; //DPL_FLUSH_DCS ( myInnerProjectile->GetDCS() ); L4Application *l4_application = Cast_Object(L4Application*, application); Check(l4_application); l4_application->GetVideoRenderer()->ReleaseProjectile(myInnerProjectile); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the ProjectileRootRenderable // Logical ProjectileRootRenderable::TestInstance() const { // // Call our parent's TestInstance first // VideoRenderable::TestInstance(); // // Test our own variables // Check(&oldLocalToWorld); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the ProjectileRootRenderable // Nothing to execute here so we just pass it down to the next lower level. // void ProjectileRootRenderable::Execute() { // // Check our variables // Check(this); // // If our entity has changed it's localToWorld matrix, update DPL // if(oldLocalToWorld != myEntity->localToWorld) { oldLocalToWorld = myEntity->localToWorld; transMatrix = oldLocalToWorld; } //// //// Call the next lower execute method //// //#if DEBUG_LEVEL > 0 //VideoRenderable::Execute(); //#endif myRenderer->GetMatrixStack()->Push(); myRenderer->GetMatrixStack()->MultMatrix(&transMatrix.ToD3DMatrix()); VideoRenderable::Execute(); myRenderer->GetMatrixStack()->Pop(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for DPLObjectWrapper // DPLObjectWrapper::DPLObjectWrapper( Entity *entity, // Entity to attach the renderable to const CString &name, // Name of the DPL object to load into the wrapper dpl_LOAD_MODE cache_mode // DPL Zone this stuff will live in (for culling) ): VideoRenderable(entity, DPLObjectWrapper::Static) { //STUBBED: DPL RB 1/14/07 // // Check the incoming pointers // Check(&name); myDPLObject = d3d_OBJECT::LoadObject(myRenderer->GetDevice(),(char*)name); myDPLObjectName = name; //// //// Load the DPL object into the wrapper, try to get the object pointer from //// the cache, if it isn't there, do a regular load. //// //if(cache_mode == dpl_load_nocache) //{ // L4Application *l4_application = Cast_Object(L4Application*, application); // Check(l4_application); // myDPLObject = l4_application->GetVideoRenderer()->GetCachedObject(name); // if(!myDPLObject) // { // myDPLObject = dpl_LoadObject(name, cache_mode); // } //} //else //{ // myDPLObject = dpl_LoadObject(name, cache_mode); //} //myCacheMode = cache_mode; //myDPLObjectName = name; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for DPLObjectWrapper // DPLObjectWrapper::~DPLObjectWrapper() { //STUBBED: DPL RB 1/14/07 //// //// Check our structure before we do anything //// //Check(this); //// //// Handle the unloading of DPL objects //// //if(myCacheMode == dpl_load_nocache) //{ // // // // If this object was not cached, we will eventually return it to the video // // renderer's list of unused uncached objects for later use by someone else // // // L4Application *l4_application = Cast_Object(L4Application*, application); // Check(l4_application); // l4_application->GetVideoRenderer()->PutCachedObject(myDPLObjectName, myDPLObject); //} //else //{ // // // // Do nothing (should unload the object) // // // //dpl_UnloadObject(myDPLObject); //} myDPLObject = NULL; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLObjectWrapper // Logical DPLObjectWrapper::TestInstance() const { // // Call our parent's TestInstance first // VideoRenderable::TestInstance(); // // Test our own variables // Check_Pointer(myDPLObject); Check(&myDPLObjectName); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the DPLObjectWrapper // Nothing to execute here so we just pass it down to the next lower level. // void DPLObjectWrapper::Execute() { // // Check our variables // Check(this); // // Call the next lower execute method // VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~New Class Hiearchy for Renderables~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for VideoRenderable // VideoRenderable::VideoRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable HierarchicalDrawComponent *parent ): HierarchicalDrawComponent(TrivialNodeClassID, parent) // Inherited constructor { // // Check incoming data // Check(entity); // // Remember the entity and execution type // myEntity = entity; myExecutionType = execution_type; // // HACK HACK HACK // This initializes the video renderable's pointer back to the renderer that // owns it so it can get information from that renderer. The renderer pointer // really should be passed in as an argument, this is a concession to avoid // spending the time to edit all references to the renderer so they support // a new argument. This will be fixed later, for now we know there is only // on renderer so we grab the application pointer and get the video renderer // from it. // // SB - moved to HierarchicalDrawComponent // // Register us as static or dynamic // switch(myExecutionType) { case Static: myEntity->AddStaticVideoComponent(this); break; case Dynamic: // myEntity->AddDynamicVideoComponent(this); myEntity->AddStaticVideoComponent(this); myRenderer->AddDynamicRenderable(this); break; case Watcher: myEntity->AddStaticVideoComponent(this); break; case Dependant: myEntity->AddStaticVideoComponent(this); break; default: Fail("VideoRenderable--Illegal execution type\n"); break; } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for VideoRenderable // VideoRenderable::~VideoRenderable() { // // Check our structure before we do anything // Check(this); // // Nothing else to do here // } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the VideoRenderable // Logical VideoRenderable::TestInstance() const { // // Call our parent's TestInstance first // Component::TestInstance(); // // Test our own variables // Check(myEntity); Check(myRenderer); Verify(myExecutionType >= Static && myExecutionType <= Dependant); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the VideoRenderable // This method just checks to be sure we are not trying to execute a static // renderable, then returns. // void VideoRenderable::Execute() { // if we're a static renderable then only execute the // children and don't add ourselves to any render lists //if (myExecutionType == Static) // HierarchicalDrawComponent::ExecuteChildren(); //else HierarchicalDrawComponent::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for the ChildLightRenderable // // This renderable is used to connect a light as a child of an existing DCS // the light isn't setup to move on it's own and creates a DCS only for the // purpose of offsetting it from it's parent. // ChildLightRenderable::ChildLightRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable bool isDeathZone, // DPL Zone this stuff will live in (for culling) HierarchicalDrawComponent *parent, // the parent DCS we will be offsetting from LinearMatrix *offset_matrix, // offset matrix to be applied prior to joint DCS Scalar red, // light color Scalar green, Scalar blue, Scalar inner_radius, Scalar outer_radius, dpl_LIGHT_TYPE light_type, int light_mask ): VideoRenderable(entity, execution_type, parent) { isDeathDraw = isDeathZone; //STUBBED: DPL RB 1/14/07 // // // // Check the inbound data // // // Check_Pointer(this_zone); // Check_Pointer(parent_DCS); // Check(offset_matrix); // // // // Remember the interesting parameters // // // myZone = this_zone; // myParentDCS = parent_DCS; myOffsetMatrix = *offset_matrix; // // // // Create the dpl DCS and the light that we will be using // // // myDCS = dpl_NewDCS (); // myLight = dpl_NewLight(); // Check_Pointer(myDCS); // Check_Pointer(myLight); // // // // Setup light type and color // // // dpl_SetLightType (myLight, light_type ); // dpl_SetLightColor (myLight, red, green, blue ); // dpl_SetLightDCS (myLight, myDCS ); // dpl_SetLightRadii (myLight, inner_radius, outer_radius ); // dpl_SetLightLightingMask (myLight, light_mask); // // // // Connect the DCS just created to a parent // // // dpl_AddDCSToDCS ( myParentDCS, myDCS ); // // // // Set the DCS into the requested zone for culling // // // dpl_SetDCSZone ( myDCS, this_zone ); // // // // Load up the DCS matrix with the supplied matrix // // // float32* tempMatrix = dpl_GetDCSMatrix(myDCS); // Check_Pointer(tempMatrix); // *(Matrix4x4*)tempMatrix = myOffsetMatrix; // // // // Flip the light around to point the correct direction // // //// dpl_RotateDCS ( myDCS, 180.0f, dpl_Y ); // // // // Flush out the instance and DCS // // // dpl_FlushLight ( myLight); // dpl_FlushDCS ( myDCS ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for ChildLightRenderable // ChildLightRenderable::~ChildLightRenderable() { //STUBBED: DPL RB 1/14/07 //Check(this); //dpl_DeleteDCS(myDCS); //dpl_DeleteLight(myLight); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the ChildLightRenderable // Logical ChildLightRenderable::TestInstance() const { Component::TestInstance(); Check_Pointer(myDCS); Check_Pointer(myParentDCS); Check_Pointer(myLight); Check(&myOffsetMatrix); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute method for ChildLightRenderable // void ChildLightRenderable::Execute() { myRenderer->GetMatrixStack()->Push(); myRenderer->GetMatrixStack()->MultMatrixLocal(&myOffsetMatrix.ToD3DMatrix()); //myLocalToWorld = *myRenderer->GetMatrixStack()->GetTop(); HierarchicalDrawComponent::SetLocalToWorld(myRenderer->GetMatrixStack()->GetTop()); //Do something with light? VideoRenderable::Execute(); myRenderer->GetMatrixStack()->Pop(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for DCSObjectRenderable // DCSObjectRenderable::DCSObjectRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable d3d_OBJECT *graphical_object, // object to hang on the DCS, may be a list later bool isDeathZone, // DPL Zone this stuff will live in (for culling) dpl_ISECT_MODE intersect_mode, // type of intersections to do on this object uint32 intersect_mask, // intersection mask for the object HierarchicalDrawComponent *parent ): VideoRenderable(entity, execution_type, parent) { isDeathDraw = isDeathZone; // // Check incoming data // #if DEBUG_LEVEL > 0 if(graphical_object) Check_Pointer(graphical_object); // allowed to be null #endif Check_Pointer(this_zone); // // Remember my d3d object, intersect and offset data // graphicalObject = graphical_object; //myDPLZone = this_zone; myIntersectMode = intersect_mode; myIntersectMask = intersect_mask; myDCS = NULL; myInstance = NULL; // // We need to construct a DCS node here and remember it. The next class up is // expected to handle the std::flushing and connecting of structure so we just setup // the DCS and zone information here, leaving std::flushing to someone else. // // myDCS = dpl_NewDCS (); Check_Pointer ( myDCS ); // dpl_SetDCSZone ( myDCS, myDPLZone ); // // Construct the instance(s) and hang them on the DCS. Since we may be building // more than one instance, we have to take care of std::flushing them here. // if(myD3DObject) { // myInstance = dpl_NewInstance(); Check_Pointer ( myInstance); // dpl_SetInstanceObject ( myInstance, myDPLObject); // dpl_SetInstanceIntersect ( myInstance, myIntersectMode ); // dpl_SetInstanceSectMask ( myInstance, myIntersectMask ); // dpl_SetInstanceVisibility ( myInstance, 1 ); // dpl_AddInstanceToDCS ( myDCS, myInstance ); // dpl_FlushInstance ( myInstance ); } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for DCSObjectRenderable // DCSObjectRenderable::~DCSObjectRenderable() { //STUBBED: DPL RB 1/14/07 //// //// Check our structure before we do anything //// //Check(this); //// //// Delete the instance(s) hanging on the DCS (if any) //// NOTE: we may want to iterate through all the instances here using DPL routines //// //if(myInstance) //{ // dpl_RemoveInstanceFromDCS(myDCS, myInstance); // dpl_DeleteInstance(myInstance); //} //// //// Delete the DCS //// //dpl_DeleteDCS(myDCS); //myDCS = NULL; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DCSObjectRenderable // Logical DCSObjectRenderable::TestInstance() const { // // Call our parent's TestInstance first // VideoRenderable::TestInstance(); // // Test our own variables // #if DEBUG_LEVEL > 0 if(myDPLObject) Check_Pointer(myDPLObject); if(myInstance) Check_Pointer(myInstance); #endif Check_Pointer(myDPLZone); Check_Pointer(myDCS); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the DCSObjectRenderable // Nothing to execute here so we just pass it down to the next lower level. // void DCSObjectRenderable::Execute() { //// //// Check our variables //// //Check(this); //// //// Call the next lower execute method //// //#if DEBUG_LEVEL > 0 //VideoRenderable::Execute(); // #endif //myLocalToWorld = *myRenderer->GetMatrixStack()->GetTop(); HierarchicalDrawComponent::SetLocalToWorld(myRenderer->GetMatrixStack()->GetTop()); //HierarchicalDrawComponent::Execute(); VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for DCSInstanceRenderable // DCSInstanceRenderable::DCSInstanceRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable d3d_OBJECT *graphical_object, // object to connect to the instance HierarchicalDrawComponent *parent, // the DCS to add the instance to dpl_ISECT_MODE intersect_mode, // type of intersections to do on this object uint32 intersect_mask, // intersection mask for the object Logical visible // initial visibility setting ): VideoRenderable(entity, execution_type, parent) { // // Check incoming data // Check_Pointer(graphical_object); Check_Pointer(parent_DCS); // // Remember my dpl object, intersect and offset data // graphicalObject = graphical_object; myIntersectMode = intersect_mode; myIntersectMask = intersect_mask; // myDCS = parent_DCS; //myInstance = dpl_NewInstance(); Check_Pointer(myInstance); // // Construct the instance(s) and hang them on the parent DCS // //dpl_SetInstanceObject ( myInstance, myDPLObject); //dpl_SetInstanceIntersect ( myInstance, myIntersectMode ); //dpl_SetInstanceSectMask ( myInstance, myIntersectMask ); //dpl_SetInstanceVisibility ( myInstance, visible ); //dpl_AddInstanceToDCS ( myDCS, myInstance ); //dpl_FlushInstance ( myInstance ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for DCSInstanceRenderable // DCSInstanceRenderable::~DCSInstanceRenderable() { //STUBBED: DPL RB 1/14/07 //// //// Check our structure before we do anything //// //Check(this); //// //// Disconnect the instance from the DCS and delete the instance //// //dpl_RemoveInstanceFromDCS(myDCS, myInstance); //dpl_DeleteInstance(myInstance); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DCSInstanceRenderable // Logical DCSInstanceRenderable::TestInstance() const { // // Call our parent's TestInstance first // VideoRenderable::TestInstance(); // // Test our own variables // Check_Pointer(myDPLObject); Check_Pointer(myInstance); Check_Pointer(myDCS); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the DCSInstanceRenderable // Nothing to execute here so we just pass it down to the next lower level. // void DCSInstanceRenderable::Execute() { //// //// Check our variables //// //Check(this); //myLocalToWorld = *myRenderer->GetMatrixStack()->GetTop(); //HierarchicalDrawComponent::Execute(); //// //// Call the next lower execute method //// //#if DEBUG_LEVEL > 0 //VideoRenderable::Execute(); //#endif myRenderer->GetMatrixStack()->Push(); //myRenderer->GetMatrixStack()->MultMatrixLocal(&OrientationMatrix.ToD3DMatrix()); //myLocalToWorld = *myRenderer->GetMatrixStack()->GetTop(); HierarchicalDrawComponent::SetLocalToWorld(myRenderer->GetMatrixStack()->GetTop()); VideoRenderable::Execute(); myRenderer->GetMatrixStack()->Pop(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for RootRenderable // RootRenderable::RootRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable d3d_OBJECT *graphical_object, bool isDeathZone, // DPL Zone this stuff will live in (for culling) dpl_ISECT_MODE intersect_mode, // type of intersections to do on this object uint32 intersect_mask // intersection mask for the object ): DCSObjectRenderable( entity, // Entity to attach the renderable to execution_type, // How/when to execute the renderable graphical_object, // object to hang on the DCS, may be a list later isDeathZone, // DPL Zone this stuff will live in (for culling) intersect_mode, // type of intersections to do on this object intersect_mask) // intersection mask for the object { // // All the incoming data will have been checked by DCSObjectRenderable // already, so we don't have to check anything locally. // // // Initialize our variables // oldLocalToWorld = myEntity->localToWorld; // // Now we finish the work of hooking up and initializing the root renderable // Add the DCS to the scene and initialize it's matrix with the localToWorld // transformation from our entity // L4Application *l4_application = Cast_Object(L4Application*, application); Check(l4_application); l4_application->GetVideoRenderer()->AddRenderable(this); // dpl_AddDCSToScene ( myDCS ); // float32* tempMatrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix ); // *(Matrix4x4*)tempMatrix = myEntity->localToWorld; // dpl_FlushDCS ( myDCS ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for RootRenderable // RootRenderable::~RootRenderable() { //STUBBED: DPL RB 1/14/07 //// //// Check our structure before we do anything //// //Check(this); //// //// Remove the DCS from the scene, deletion of the DCS and it's instances is //// handled by our parent class. //// //dpl_RemoveDCSFromScene(myDCS); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the RootRenderable // Logical RootRenderable::TestInstance() const { // // Call our parent's TestInstance first // DCSObjectRenderable::TestInstance(); // // Test our own variables // Check(&oldLocalToWorld); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the RootRenderable // Nothing to execute here so we just pass it down to the next lower level. // void RootRenderable::Execute() { // // Check our variables // Check(this); // We don't need to do this because we're going to use the matrix directly // // // // If our entity has changed it's localToWorld matrix, update DPL // // // if(oldLocalToWorld != myEntity->localToWorld) // { // oldLocalToWorld = myEntity->localToWorld; // float32* tempMatrix = dpl_GetDCSMatrix(myDCS); // Check_Pointer (tempMatrix); // *(Matrix4x4*)tempMatrix = oldLocalToWorld; // DPL_FLUSH_DCS ( myDCS ); // } myRenderer->GetMatrixStack()->Push(); Matrix4x4 tempMatrix; tempMatrix = myEntity->localToWorld; myRenderer->GetMatrixStack()->MultMatrix(&tempMatrix.ToD3DMatrix()); //myLocalToWorld = *myRenderer->GetMatrixStack()->GetTop(); HierarchicalDrawComponent::SetLocalToWorld(myRenderer->GetMatrixStack()->GetTop()); DCSObjectRenderable::Execute(); myRenderer->GetMatrixStack()->Pop(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for ChildOffsetRenderable // ChildOffsetRenderable::ChildOffsetRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable d3d_OBJECT *graphical_object, // object to hang on the DCS, may be a list later bool isDeathZone, // DPL Zone this stuff will live in (for culling) dpl_ISECT_MODE intersect_mode, // type of intersections to do on this object uint32 intersect_mask, // intersection mask for the object HierarchicalDrawComponent *parent, // the parent DCS we will be offsetting from LinearMatrix *offset_matrix // offset matrix to be applied prior to joint DCS ): DCSObjectRenderable( entity, // Entity to attach the renderable to execution_type, // How/when to execute the renderable graphical_object, // object to hang on the DCS, may be a list later isDeathZone, // DPL Zone this stuff will live in (for culling) intersect_mode, // type of intersections to do on this object intersect_mask, // intersection mask for the object parent) { // // Check incoming data not handled by lower levels // Check(offset_matrix); // // Remember my offset matrix // myOffsetMatrix = *offset_matrix; myOffsetDCS = NULL; //myParentDCS = parent_DCS; // // We construct the offset DCS node and link the DCS carrying our our // graphical instances to it. // // myOffsetDCS = dpl_NewDCS (); Check_Pointer ( myOffsetDCS ); // dpl_SetDCSZone ( myDCS, myDPLZone ); // dpl_AddDCSToDCS ( myOffsetDCS, myDCS ); // // Now we connect that DCS to our parent // // dpl_AddDCSToDCS ( myParentDCS, myOffsetDCS); // // Then fill in the offset DCS and std::flush it // // float32* tempMatrix = dpl_GetDCSMatrix( myOffsetDCS ); // Check_Pointer ( tempMatrix ); // *(Matrix4x4*)tempMatrix = myOffsetMatrix; // dpl_FlushDCS ( myOffsetDCS ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for ChildOffsetRenderable // ChildOffsetRenderable::~ChildOffsetRenderable() { //STUBBED: DPL RB 1/14/07 //// //// Check our structure before we do anything //// //Check(this); //// //// Delete the connection to our parent DCS //// //dpl_RemoveDCSFromDCS(myParentDCS, myOffsetDCS); //// //// Delete the static DCS and it's connections to the dynamic one //// //dpl_RemoveDCSFromDCS(myOffsetDCS, myDCS); //dpl_DeleteDCS(myOffsetDCS); //myOffsetDCS = NULL; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the ChildOffsetRenderable // Logical ChildOffsetRenderable::TestInstance() const { // // Call our parent's TestInstance first // DCSObjectRenderable::TestInstance(); // // Test our own variables // Check_Pointer(myParentDCS); Check_Pointer(myOffsetDCS); Check(&myOffsetMatrix); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the ChildOffsetRenderable // Nothing to execute here so we just pass it down to the next lower level. // void ChildOffsetRenderable::Execute() { // // Check our variables // Check(this); // // Call the next lower execute method // myRenderer->GetMatrixStack()->Push(); myRenderer->GetMatrixStack()->MultMatrixLocal(&myOffsetMatrix.ToD3DMatrix()); DCSObjectRenderable::Execute(); myRenderer->GetMatrixStack()->Pop(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for HingeRenderable // #define SINGLE_AXIS_HINGE True HingeRenderable::HingeRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable d3d_OBJECT *graphical_object, // object to hang on the DCS, may be a list later bool isDeathZone, // DPL Zone this stuff will live in (for culling) dpl_ISECT_MODE intersect_mode, // type of intersections to do on this object uint32 intersect_mask, // intersection mask for the object HierarchicalDrawComponent *parent, // the parent DCS we will be offsetting from LinearMatrix *offset_matrix, // offset matrix to be applied prior to joint DCS const Hinge *my_hinge // Hinge attribute we will use to control the joint ): ChildOffsetRenderable( entity, // Entity to attach the renderable to execution_type, // How/when to execute the renderable graphical_object, // object to hang on the DCS, may be a list later isDeathZone, // DPL Zone this stuff will live in (for culling) intersect_mode, // type of intersections to do on this object intersect_mask, // intersection mask for the object parent, // the parent DCS we will be offsetting from offset_matrix) // offset matrix to be applied prior to joint DCS { // // Check the incomming data // Check(my_hinge); // // Initialize our variables // myHinge = my_hinge; oldHinge = *my_hinge; // // Dump the initial value of the hing into the DCS our instances are attached // to, then std::flush it out. We have to copy the hinge to a quaternion because // the math library doesn't support direct assignment of hing to matrix yet. // hingeOffsetMatrix.BuildIdentity(); /*#if SINGLE_AXIS_HINGE SinCosPair temp_sin_cos_pair; temp_sin_cos_pair = myHinge->rotationAmount; switch(myHinge->axisNumber) { case X_Axis: // dpl_SetDCSXAxis(myDCS, temp_sin_cos_pair.sine, temp_sin_cos_pair.cosine); hingeOffsetMatrix. break; case Y_Axis: // dpl_SetDCSYAxis(myDCS, temp_sin_cos_pair.sine, temp_sin_cos_pair.cosine); break; case Z_Axis: // dpl_SetDCSZAxis(myDCS, temp_sin_cos_pair.sine, temp_sin_cos_pair.cosine); break; } #else*/ Quaternion temp_quaternion; // float32 // *temp_matrix; // temp_matrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer( temp_matrix ); temp_quaternion = oldHinge; hingeOffsetMatrix.BuildRotation(temp_quaternion); // *(Matrix4x4*)temp_matrix = temp_quaternion; //#endif // dpl_FlushDCS ( myDCS ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for HingeRenderable // HingeRenderable::~HingeRenderable() { // // Check our structure before we do anything // Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the HingeRenderable // Logical HingeRenderable::TestInstance() const { // // Call our parent's TestInstance first // ChildOffsetRenderable::TestInstance(); // // Test our own variables // Check(myHinge); Check(&oldHinge); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the HingeRenderable // Nothing to execute here so we just pass it down to the next lower level. // void HingeRenderable::Execute() { // // Check our variables // Check(this); // // If the hinge we're watching has changed, update our matrix // if(oldHinge != *myHinge) { oldHinge = *myHinge; hingeOffsetMatrix.BuildIdentity(); //#if SINGLE_AXIS_HINGE // SinCosPair // temp_sin_cos_pair; // temp_sin_cos_pair = myHinge->rotationAmount; // switch(myHinge->axisNumber) // { // case X_Axis: // dpl_SetDCSXAxis(myDCS, temp_sin_cos_pair.sine, temp_sin_cos_pair.cosine); // break; // case Y_Axis: // dpl_SetDCSYAxis(myDCS, temp_sin_cos_pair.sine, temp_sin_cos_pair.cosine); // break; // case Z_Axis: // dpl_SetDCSZAxis(myDCS, temp_sin_cos_pair.sine, temp_sin_cos_pair.cosine); // break; // } //#else Quaternion temp_quaternion; // float32 // *temp_matrix; // temp_matrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer( temp_matrix ); temp_quaternion = oldHinge; hingeOffsetMatrix.BuildRotation(temp_quaternion); // *(Matrix4x4*)temp_matrix = temp_quaternion; //#endif // DPL_FLUSH_DCS ( myDCS ); } myRenderer->GetMatrixStack()->Push(); myRenderer->GetMatrixStack()->MultMatrixLocal(&myOffsetMatrix.ToD3DMatrix()); myRenderer->GetMatrixStack()->MultMatrixLocal(&hingeOffsetMatrix.ToD3DMatrix()); // // Call the execute method in our parent // DCSObjectRenderable::Execute(); myRenderer->GetMatrixStack()->Pop(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for BallJointRenderable // BallJointRenderable::BallJointRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable d3d_OBJECT *graphical_object, // object to hang on the DCS, may be a list later bool isDeathZone, // DPL Zone this stuff will live in (for culling) dpl_ISECT_MODE intersect_mode, // type of intersections to do on this object uint32 intersect_mask, // intersection mask for the object HierarchicalDrawComponent *parent, // the parent DCS we will be offsetting from LinearMatrix *offset_matrix, // offset matrix to be applied prior to joint DCS const EulerAngles *my_euler // Euler angles to control rotation of the ball joint ): ChildOffsetRenderable( entity, // Entity to attach the renderable to execution_type, // How/when to execute the renderable graphical_object, // object to hang on the DCS, may be a list later isDeathZone, // DPL Zone this stuff will live in (for culling) intersect_mode, // type of intersections to do on this object intersect_mask, // intersection mask for the object parent, // the parent DCS we will be offsetting from offset_matrix) // offset matrix to be applied prior to joint DCS { //float32 // *temp_matrix; // // Check the incomming data // Check(my_euler); // // Initialize our variables // myEuler = my_euler; oldEuler = *my_euler; // // Dump the initial value of the euler angles into the DCS our instances are attached // to, then std::flush it out. // eulerMatrix = *myEuler; //temp_matrix = dpl_GetDCSMatrix( myDCS ); //Check_Pointer( temp_matrix ); //*(Matrix4x4*)temp_matrix = oldEuler; //dpl_FlushDCS ( myDCS ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for BallJointRenderable // BallJointRenderable::~BallJointRenderable() { // // Check our structure before we do anything // Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the BallJointRenderable // Logical BallJointRenderable::TestInstance() const { // // Call our parent's TestInstance first // ChildOffsetRenderable::TestInstance(); // // Test our own variables // Check(myEuler); Check(&oldEuler); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the BallJointRenderable // void BallJointRenderable::Execute() { //float32 // *temp_matrix; // // Check our variables // Check(this); // // If the hinge we're watching has changed, update our matrix // if(oldEuler != *myEuler) { oldEuler = *myEuler; eulerMatrix = oldEuler; // temp_matrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer( temp_matrix ); // *(Matrix4x4*)temp_matrix = oldEuler; // DPL_FLUSH_DCS ( myDCS ); } myRenderer->GetMatrixStack()->Push(); myRenderer->GetMatrixStack()->MultMatrixLocal(&myOffsetMatrix.ToD3DMatrix()); myRenderer->GetMatrixStack()->MultMatrixLocal(&eulerMatrix.ToD3DMatrix()); DCSObjectRenderable::Execute(); myRenderer->GetMatrixStack()->Pop(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for BallTranslateJointRenderable // BallTranslateJointRenderable::BallTranslateJointRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable d3d_OBJECT *graphical_object, // object to hang on the DCS, may be a list later bool isDeathZone, // DPL Zone this stuff will live in (for culling) dpl_ISECT_MODE intersect_mode, // type of intersections to do on this object uint32 intersect_mask, // intersection mask for the object HierarchicalDrawComponent *parent, // the parent DCS we will be offsetting from LinearMatrix *offset_matrix, // offset matrix to be applied prior to joint DCS const EulerAngles *my_euler, // Euler angles to control rotation of the ball joint const Point3D *my_translation // offset for the translation part of the joint ): ChildOffsetRenderable( entity, // Entity to attach the renderable to execution_type, // How/when to execute the renderable graphical_object, // object to hang on the DCS, may be a list later isDeathZone, // DPL Zone this stuff will live in (for culling) intersect_mode, // type of intersections to do on this object intersect_mask, // intersection mask for the object parent, // the parent DCS we will be offsetting from offset_matrix) // offset matrix to be applied prior to joint DCS { AffineMatrix tempAffine(True); //float32 // *temp_matrix; // // Check the incomming data // Check(my_euler); Check(my_translation); // // Initialize our variables // myEuler = my_euler; oldEuler = *my_euler; myTranslation = my_translation; oldTranslation = *my_translation; // // Dump the initial value of the euler angles into the DCS our instances are attached // to, then std::flush it out. // //temp_matrix = dpl_GetDCSMatrix( myDCS ); Check_Pointer( temp_matrix ); tempAffine = oldTranslation; tempAffine = oldEuler; jointMatrix = tempAffine; //*(Matrix4x4*)temp_matrix = tempAffine; //dpl_FlushDCS ( myDCS ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for BallTranslateJointRenderable // BallTranslateJointRenderable::~BallTranslateJointRenderable() { // // Check our structure before we do anything // Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the BallTranslateJointRenderable // Logical BallTranslateJointRenderable::TestInstance() const { // // Call our parent's TestInstance first // ChildOffsetRenderable::TestInstance(); // // Test our own variables // Check(myEuler); Check(&oldEuler); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the BallTranslateJointRenderable // void BallTranslateJointRenderable::Execute() { //float32 // *temp_matrix; // // Check our variables // Check(this); // // If the hinge we're watching has changed, update our matrix // if(oldEuler != *myEuler || oldTranslation != *myTranslation) { oldEuler = *myEuler; oldTranslation = *myTranslation; // temp_matrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer( temp_matrix ); AffineMatrix tempAffine(True); tempAffine = oldTranslation; tempAffine = oldEuler; jointMatrix = tempAffine; // *(Matrix4x4*)temp_matrix = tempAffine; // DPL_FLUSH_DCS ( myDCS ); } myRenderer->GetMatrixStack()->Push(); myRenderer->GetMatrixStack()->MultMatrixLocal(&myOffsetMatrix.ToD3DMatrix()); myRenderer->GetMatrixStack()->MultMatrixLocal(&jointMatrix.ToD3DMatrix()); DCSObjectRenderable::Execute(); myRenderer->GetMatrixStack()->Pop(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for SpinScaleQuatRenderable // SpinScaleQuatRenderable::SpinScaleQuatRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable d3d_OBJECT *graphical_object, // object to hang on the DCS, may be a list later bool isDeathZone, // DPL Zone this stuff will live in (for culling) dpl_ISECT_MODE intersect_mode, // type of intersections to do on this object uint32 intersect_mask, // intersection mask for the object HierarchicalDrawComponent *parent, // the parent DCS we will be offsetting from LinearMatrix *offset_matrix, // offset matrix to be applied prior to joint DCS Quaternion *rotation_quaternion,// rotates the object Vector3D *scale_vector, // Scales the object Logical *visible, // turns the object on and off Scalar z_spin_rate // spins the object about z (radians/frame) ): ChildOffsetRenderable( entity, // Entity to attach the renderable to execution_type, // How/when to execute the renderable graphical_object, // object to hang on the DCS, may be a list later isDeathZone, // DPL Zone this stuff will live in (for culling) intersect_mode, // type of intersections to do on this object intersect_mask, // intersection mask for the object parent, // the parent DCS we will be offsetting from offset_matrix) // offset matrix to be applied prior to joint DCS { //STUBBED: DPL RB 1/14/07 //// //// Check the inbound data //// //Check(rotation_quaternion); //Check(scale_vector); //Check_Pointer(visible); //// //// Remember the entity that this renderable is attached to and the //// orientation matrix that offsets it to the correct position. //// //myRotationQuaternion = rotation_quaternion; //myScaleVector = scale_vector; //myVisible = visible; //myZSpinRate = z_spin_rate; //OldVisible = *visible; //OldZSpin = 0; //// //// Setup the dcs matrix to it's initial state //// //float32* tempMatrix = dpl_GetDCSMatrix( myDCS ); //Check_Pointer ( tempMatrix ); //AffineMatrix tempAffine(True); //tempAffine *= (*myScaleVector); //tempAffine *= (*myRotationQuaternion); //*(Matrix4x4*)tempMatrix = tempAffine; //dpl_FlushDCS ( myDCS ); //// //// Set the instance visibility correctly //// //dpl_SetInstanceVisibility ( myInstance, OldVisible ); //dpl_FlushInstance ( myInstance ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for SpinScaleQuatRenderable // SpinScaleQuatRenderable::~SpinScaleQuatRenderable() { // // Check our structure before we do anything // Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the SpinScaleQuatRenderable // Logical SpinScaleQuatRenderable::TestInstance() const { // // Call our parent's TestInstance first // ChildOffsetRenderable::TestInstance(); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the SpinScaleQuatRenderable // Nothing to execute here so we just pass it down to the next lower level. // void SpinScaleQuatRenderable::Execute() { //STUBBED: DPL RB 1/14/07 //// //// Check our variables //// //Check(this); //// //// Load up the DCS matrix with the localToWorld matrix from the entity //// then std::flush out the new DCS //// //if(OldVisible != *myVisible) //{ // OldVisible = *myVisible; // dpl_SetInstanceVisibility ( myInstance, OldVisible ); // dpl_FlushInstance ( myInstance ); //} //// //// If the beam is visible, we have to update it //// //if(OldVisible) //{ // OldZSpin += myZSpinRate; // if(OldZSpin > TWO_PI) // OldZSpin -= TWO_PI; // Hinge temp_hinge(Z_Axis, OldZSpin); // float32* tempMatrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix ); // AffineMatrix tempAffine(True); // Quaternion temp_quaternion; // temp_quaternion = temp_hinge; // tempAffine = temp_quaternion; // tempAffine *= (*myScaleVector); // temp_quaternion = *myRotationQuaternion; // tempAffine *= temp_quaternion; // *(Matrix4x4*)tempMatrix = tempAffine; // DPL_FLUSH_DCS ( myDCS ); //} // // Call the execute method in our parent // ChildOffsetRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for POVTranslocateRenderable // POVTranslocateRenderable::POVTranslocateRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable bool isDeathZone, // DPL zone the world is in dpl_ZONE *death_zone, // DPL zone the player's VTV and death effect are in HierarchicalDrawComponent *parent, // the parent DCS we will be offsetting from StateIndicator *effect_trigger, // State dial we use to control the translocation unsigned effect_control_state // State that controls start/end of the effect ): VideoRenderable(entity, execution_type, parent) { isDeathDraw = isDeathZone; //STUBBED: DPL RB 1/14/07 #define COLLAPSE_TIME 1.3f // Time in seconds for initial collapse #define COLLAPSE_START_SCALE 100.0f // Scale factor of the sphere when we start collapse #define EXPAND_TIME 1.0f // Time that expansion of the sphere should take #define EXPAND_END_SCALE 150.0f // Scale factor of the sphere when expansion ends #define ROTATE_RATE (0.5f * (0.01745329222222)) #define ROTATE_LIMIT (20.0f * (0.01745329222222)) #define TRANSLATE_RATE 0.2f #define TRANSLATE_LIMIT 2.0f // // HACK HACK HACK this should be removed once red planet is checked out if(execution_type != Watcher) std::cout<<"POVTranslocateRenderable wants to be a watcher and isn't!\n"; // // Check the inbound data, note that the parent DCS could be a null pointer // // Check_Pointer(this_zone); // Check_Pointer(death_zone); // Check_Pointer(parent_DCS); Check(effect_trigger); // // Remember the entity and DCS this renderable is attached to // // myZone = this_zone; // myDeathZone = death_zone; // myParentDCS = parent_DCS; myEffectTrigger = effect_trigger; myEffectControlState = effect_control_state; myState = IdleState; myRotateY = 0.0f; myRotateYSpeed = TRANSLATE_RATE; // // Load up the object we're going to use for the translocation // L4Application *l4_application = Cast_Object(L4Application*, application); Check(l4_application); // dpl_OBJECT* myTranslocateSphere = dpl_LoadObject ( "tsphere.bgf", dpl_load_normal ); myDevice = l4_application->GetVideoRenderer()->GetDevice(); myTranslocateSphere = d3d_OBJECT::LoadObject(myDevice, "tsphere.bgf"); graphicalObject = myTranslocateSphere; if (isDeathDraw) { //Draw this as sky for (int i = 0; i < graphicalObject->GetDrawOpCount(); i++) { graphicalObject->GetDrawOp(i)->drawAsSky = true; } } // Check_Pointer(myTranslocateSphere); // // Setup a DCS that we can put the sphere on so it can be rotated and scaled // around the VTV. Attach the sphere to this DCS but make it invisible. // // myInstance = dpl_NewInstance(); // myDCS = dpl_NewDCS(); Check_Pointer (myInstance); Check_Pointer (myDCS); // dpl_AddDCSToDCS (myParentDCS, myDCS); // dpl_SetDCSZone (myDCS, myDeathZone); // dpl_SetInstanceObject (myInstance, myTranslocateSphere); // dpl_SetInstanceIntersect (myInstance, dpl_isect_mode_obj); // dpl_SetInstanceSectMask (myInstance, NULL); // dpl_SetInstanceVisibility (myInstance, False); visible = false; // dpl_AddInstanceToDCS (myDCS, myInstance); // dpl_FlushInstance (myInstance); // dpl_FlushDCS (myDCS); // // Connect us to the state dial's watcher hook // //l4_application->GetVideoRenderer()->mDeathRenderables.Add(this); myEffectTrigger->AddVideoWatcher(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for POVTranslocationRenderable // POVTranslocateRenderable::~POVTranslocateRenderable() { //STUBBED: DPL RB 1/14/07 //Check(this); //// //// Disconnect the structure we have setup //// //dpl_RemoveDCSFromDCS(myParentDCS, myDCS); //dpl_RemoveInstanceFromDCS(myDCS,myInstance); //// //// Delete the DPL elements we created //// //dpl_DeleteInstance(myInstance); //dpl_DeleteDCS(myDCS); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the POVTranslocateRenderable // Logical POVTranslocateRenderable::TestInstance() const { VideoRenderable::TestInstance(); Check_Pointer(myZone); Check_Pointer(myDeathZone); Check_Pointer(myParentDCS); Check(myEffectTrigger); Check_Pointer(myInstance); Check_Pointer(myDCS); Verify(myState >= IdleState && myState <= ExpandRevealState); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute method for POVTranslocateRenderable. // void POVTranslocateRenderable::Execute() { Scalar elapsed_time, current_time, percent_time_left, percent_time_used, scale_factor; unsigned current_trigger_state; // // Get the current state and the current time for later use // Check(myEffectTrigger); current_trigger_state = myEffectTrigger->GetState(); current_time = myRenderer->GetCurrentFrameTime(); // // State engine (running off myState) to manage running of the death effect // // std::cout<<"POVTranslocateRenderable::Execute\n"; switch(myState) { // // IdleState waits for a transition in the effect control state and starts // the effect state machine when it detects one. // case IdleState: { if(current_trigger_state == myEffectControlState) { myState = InitialCollapseState; myCollapseEnd = current_time + COLLAPSE_TIME; visible = true; // dpl_SetInstanceVisibility (myInstance, True); // dpl_FlushInstance (myInstance); myRenderer->AddDynamicRenderable(this); std::cout<<"POVTranslocateRenderable::Going Dynamic\n"; } break; } // // This case handles ending the screen flash when we need to // case FlashScreenState: { myState = InitialCollapseState; break; } // // InitialCollapseState handles reducing the sphere from its max size down // to one over a period of time. We figure the percentage of the time // left then multiply it by the size the sphere started at to get the // scale factor. // case InitialCollapseState: { percent_time_left = (myCollapseEnd - current_time)/COLLAPSE_TIME; // // See how much time is left in the effect. // if(percent_time_left <= 0.0f) { // // Time's up! Go to WaitForReincarnate state, force scale factor to // 1.0, and turn off the outside world4 // scale_factor = 1.0f; // dpl_SetZoneAllViewsOff (myZone); // dpl_FlushZone (myZone); myCollapseEnd = current_time; myState = WaitForReincarnateState; l4_application->SetIsDead(true); } else { // // Recalculate the scale factor based on time left // //visible = false; scale_factor = (percent_time_left * COLLAPSE_START_SCALE) + 1.0f; } // // Build a scaling identity matrix based on our scale factor // AffineMatrix tempAffine(True); tempAffine(0,0) = scale_factor; tempAffine(1,1) = scale_factor; tempAffine(2,2) = scale_factor; // // Put the scale matrix into the DCS and std::flush it. // localToWorld = tempAffine; // tempMatrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix ); // *(Matrix4x4*)tempMatrix = tempAffine; // DPL_FLUSH_DCS (myDCS); break; } // // WaitForReincarnateState waits till we the trigger state switches off // then does what we want to get us back into the world. // case WaitForReincarnateState: { if(current_trigger_state != myEffectControlState) { // // Switch the world back on, then change states // // dpl_SetZoneAllViewsOn (myZone); // dpl_FlushZone (myZone); myState = ExpandRevealState; myCollapseEnd = current_time + EXPAND_TIME; l4_application->SetIsDead(false); } else { // // Mess with the DCS to make the tunnel effect more pronounced // elapsed_time = current_time - myCollapseEnd; Point3D temp_point( (cos(elapsed_time * 3.33) * TRANSLATE_LIMIT), (sin(elapsed_time * 2.5) * TRANSLATE_LIMIT), 0.0); // tempMatrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer( tempMatrix ); localToWorld = temp_point; // *(Matrix4x4*)tempMatrix = temp_point; // DPL_FLUSH_DCS(myDCS); } break; } // // ExpandRevealState expands the sphere rapidly in size to reveal the world // getting rid of the sphere when it hits a maximum size. // case ExpandRevealState: { // // In case we get killed again while in this state, I watch for // a change back into the trigger state and retrigger the // effect if it shows up // if(current_trigger_state == myEffectControlState) { myState = InitialCollapseState; myCollapseEnd = current_time + COLLAPSE_TIME; //// dpl_SetInstanceVisibility (myInstance, True); //// dpl_FlushInstance (myInstance); //// myRenderer->AddDynamicRenderable(this); //// std::cout<<"POVTranslocateRenderable::Going Dynamic\n"; } percent_time_used = 1.0f - ((myCollapseEnd - current_time)/EXPAND_TIME); if(percent_time_used >= 1.0f) { visible = false; // dpl_SetInstanceVisibility (myInstance, False); // dpl_FlushInstance (myInstance); myState = IdleState; scale_factor = 1.0f; myRenderer->RemoveDynamicRenderable(this); //// std::cout<<"POVTranslocateRenderable::Going Static\n"; } else { scale_factor = (percent_time_used * EXPAND_END_SCALE) + 1.0f; } // // Build a scaling identity matrix based on our scale factor // AffineMatrix tempAffine(True); tempAffine(0,0) = scale_factor; tempAffine(1,1) = scale_factor; tempAffine(2,2) = scale_factor; // // Put the scale matrix into the DCS and std::flush it. // localToWorld = tempAffine; // tempMatrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix ); // *(Matrix4x4*)tempMatrix = tempAffine; // DPL_FLUSH_DCS (myDCS); break; } } if (!visible) { graphicalObject = NULL; } else { graphicalObject = myTranslocateSphere; myRenderer->GetMatrixStack()->Push(); myRenderer->GetMatrixStack()->MultMatrixLocal(&localToWorld.ToD3DMatrix()); //myLocalToWorld = *myRenderer->GetMatrixStack()->GetTop(); HierarchicalDrawComponent::SetLocalToWorld(myRenderer->GetMatrixStack()->GetTop()); VideoRenderable::Execute(); myRenderer->GetMatrixStack()->Pop(); } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for POVStartEndRenderable This handles the effect we use when // the mission begins and ends (different from death) // POVStartEndRenderable::POVStartEndRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable bool isDeathZone, // DPL zone the world is in dpl_ZONE *death_zone, // DPL zone the player's VTV and death effect are in dpl_VIEW *this_view, // The view containing our eye StateIndicator *effect_trigger, // State dial we use to control the translocation float red_fog, // Fog color float green_fog, float blue_fog, float near_fog, // The near fog plane float far_fog, // The far fog plane unsigned start_mission_state, // State that signals start of mission unsigned end_mission_state // State that signals end of mission ): VideoRenderable(entity, execution_type) { isDeathDraw = isDeathZone; #define FLASH_TIME (0.1f) // Time the screen will stay stark white #define FADE_IN_TIME (1.0f) // Time to fade from white to the world #define FADE_OUT_TIME (0.5f) // Time to fade to black at the end of the game // HACK HACK HACK this should be removed once red planet is checked out if(execution_type != Watcher) std::cout<<"POVStartEndRenderable wants to be a watcher and isn't!\n"; // // Check the inbound data, note that the parent DCS could be a null pointer // Check_Pointer(this_zone); Check_Pointer(death_zone); Check_Pointer(this_view); Check(effect_trigger); // // Remember the entity and DCS this renderable is attached to // // myZone = this_zone; myDeathZone = death_zone; myEffectTrigger = effect_trigger; myView = this_view; myState = WaitForStartState; myFogRed = red_fog; myFogGreen = green_fog; myFogBlue = blue_fog; myFogNear = near_fog; myFogFar = far_fog; myStartMissionState = start_mission_state; myEndMissionState = end_mission_state; myRenderer->SetFogStyle(DPLRenderer::noUpdateFogSetting); l4_application->GetVideoRenderer()->AddRenderable(this); // // Connect us to the state dial's watcher hook // myEffectTrigger->AddVideoWatcher(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for POVStartEndRenderable // POVStartEndRenderable::~POVStartEndRenderable() { Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the POVStartEndRenderable // Logical POVStartEndRenderable::TestInstance() const { VideoRenderable::TestInstance(); Check_Pointer(myZone); Check_Pointer(myDeathZone); Check(myEffectTrigger); Verify(myState >= WaitForStartState && myState <= FadeOutState); Verify(myFogRed >= 0.0f && myFogRed <= 1.0f); Verify(myFogGreen >= 0.0f && myFogGreen <= 1.0f); Verify(myFogBlue >= 0.0f && myFogBlue <= 1.0f); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute method for POVStartEndRenderable. // void POVStartEndRenderable::Execute() { Scalar current_time, percent_time_left, percent_time_used; unsigned current_trigger_state; // // Get the current state and the current time for later use // Check(myEffectTrigger); current_trigger_state = myEffectTrigger->GetState(); current_time = myRenderer->GetCurrentFrameTime(); // // State engine (running off myState) to manage running of the death effect // //std::cout<<"POVStartEndRenderable::Executing\n"; switch(myState) { // // WaitForStartState waits for the state that signals the start of the mission // then sends the screen to full white by manipulating the fog color and limits. // case WaitForStartState: { myRenderer->SetFogStyle(DPLRenderer::noUpdateFogSetting); if(current_trigger_state == myStartMissionState) { myState = FlashScreenState; myStateTimer = current_time + FLASH_TIME; float fogNear = 0.01f; float fogFar = 0.05f; float fogRed = 1.0f; float fogGreen = 1.0f; float fogBlue = 1.0f; myRenderer->SetCurrentFogLimits(fogNear, fogFar); myRenderer->GetDevice()->SetRenderState(D3DRS_FOGCOLOR, D3DCOLOR_XRGB((int)(255 * fogRed), (int)(255 * fogGreen), (int)(255 * fogBlue))); // dpl_SetViewFog( // myView, // dpl_fog_type_pixel_lin, // 1.0, // 1.0, // 1.0, // 0.01, // 0.05 ); // dpl_FlushView(myView); myRenderer->AddDynamicRenderable(this); // std::cout<<"POVStartEndRenderable::Going Dynamic\n"; } break; } // // FlashScreenState is a state we park in for a short time so the screen will // stay white for more than one frame. // case FlashScreenState: { if(myStateTimer <= current_time) { myStateTimer = current_time + FADE_IN_TIME; myState = FadeInState; } break; } // // FadeInState fades the fog color down from white to what it's supposed to // be, while sweeping the fog ranges out to their proper ranges. // case FadeInState: { percent_time_left = (myStateTimer - current_time)/FADE_IN_TIME; if(percent_time_left <= 0.0f) { percent_time_left = 0.0f; myState = MissionRunningState; myRenderer->SetFogStyle(DPLRenderer::updateFogSetting); myRenderer->RemoveDynamicRenderable(this); // std::cout<<"POVStartEndRenderable::Going Static\n"; } percent_time_used = 1.0f - percent_time_left; myRenderer->GetCurrentFogSettings( &myFogRed, &myFogGreen, &myFogBlue, &myFogNear, &myFogFar); myFogRed += (1.0f - myFogRed) * percent_time_left; myFogGreen += (1.0f - myFogGreen) * percent_time_left; myFogBlue += (1.0f - myFogBlue) * percent_time_left; myFogNear *= percent_time_used; myFogFar *= percent_time_used; myFogNear += 0.01f; myFogFar += 0.05f; myRenderer->SetCurrentFogLimits(myFogNear, myFogFar); myRenderer->GetDevice()->SetRenderState(D3DRS_FOGCOLOR, D3DCOLOR_XRGB((int)(255 * myFogRed), (int)(255 * myFogGreen), (int)(255 * myFogBlue))); // dpl_SetViewFog( // myView, // dpl_fog_type_pixel_lin, // myFogRed + ((1.0f - myFogRed) * percent_time_left), // myFogGreen + ((1.0f - myFogGreen) * percent_time_left), // myFogBlue + ((1.0f - myFogBlue) * percent_time_left), // (myFogNear * percent_time_used) + 0.01f, // (myFogFar * percent_time_used) + 0.05f); // dpl_FlushView(myView); break; } // // MissionRunningState is where we park while the mission is going on, waiting // for the state that signals the end of the game // case MissionRunningState: { if(current_trigger_state == myEndMissionState) { myState = FadeOutState; myStateTimer = current_time + FADE_OUT_TIME; myRenderer->SetFogStyle(DPLRenderer::noUpdateFogSetting); myRenderer->AddDynamicRenderable(this); // std::cout<<"POVStartEndRenderable::Going Dynamic\n"; } else { myRenderer->GetCurrentFogSettings( &myFogRed, &myFogGreen, &myFogBlue, &myFogNear, &myFogFar); myRenderer->SetCurrentFogLimits(myFogNear, myFogFar); } break; } // // FadeOutState handles doing a fade-to-black at the end of the game // case FadeOutState: { percent_time_left = (myStateTimer - current_time)/FADE_OUT_TIME; if(percent_time_left <= 0.0f) { myState = WaitForStartState; percent_time_left = 0.0f; myRenderer->RemoveDynamicRenderable(this); // std::cout<<"POVStartEndRenderable::Going Static\n"; } myRenderer->GetCurrentFogSettings( &myFogRed, &myFogGreen, &myFogBlue, &myFogNear, &myFogFar); myFogRed *= percent_time_left; myFogGreen *= percent_time_left; myFogBlue *= percent_time_left; myFogNear *= percent_time_left; myFogFar *= percent_time_left; myFogNear += 0.01f; myFogFar += 0.05f; myRenderer->SetCurrentFogLimits(myFogNear, myFogFar); myRenderer->GetDevice()->SetRenderState(D3DRS_FOGCOLOR, D3DCOLOR_XRGB((int)(255 * myFogRed), (int)(255 * myFogGreen), (int)(255 * myFogBlue))); // dpl_SetViewFog( // myView, // dpl_fog_type_pixel_lin, // myFogRed * percent_time_left, // myFogGreen * percent_time_left, // myFogBlue * percent_time_left, // (myFogNear * percent_time_left) + 0.01f, // (myFogFar * percent_time_left) + 0.05f); // dpl_FlushView(myView); break; } } VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for the ReticleRenderable // This produces a movable crosshair reticle that can be either static or // dynamic. If static, it will position the graphic at wherever the reticle // points when we construct this. // ReticleRenderable::ReticleRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable Reticle **my_reticle, // points to renderable reticle pointer that points to entity's reticle dpl_VIEW *this_view // the view associated with our eye ): VideoRenderable(entity, execution_type), mVB(NULL) { // // Remember the entity that this renderable is attached to // rendererReticle = my_reticle; myReticle = *my_reticle; myOldReticlePosition = myReticle->reticlePosition; LPDIRECT3DDEVICE9 device = myRenderer->GetDevice(); device->CreateVertexBuffer(sizeof(L4VERTEX_2D) * 8, D3DUSAGE_WRITEONLY, L4VERTEX_2D_FVF, D3DPOOL_MANAGED, &mVB, NULL); L4VERTEX_2D *verts; mVB->Lock(0, 0, (void**)&verts, 0); DWORD color = D3DCOLOR_XRGB(0, 128, 0); float segmentLen = 5.0f / 192.0f; float spread = 5.0f / 256.0f; float width = myRenderer->GetWidth(); float height = myRenderer->GetHeight(); float centerX = width / 2.0f; float centerY = height / 2.0f; // top segment verts[0].x = centerX; verts[0].y = centerY - (spread + segmentLen) * height; verts[0].z = 0.0f; verts[0].rhw = 1.0f; verts[0].color = color; verts[1].x = centerX; verts[1].y = centerY - spread * height; verts[1].z = 0.0f; verts[1].rhw = 1.0f; verts[1].color = color; // right segment verts[2].x = centerX + (spread + segmentLen) * height; verts[2].y = centerY; verts[2].z = 0.0f; verts[2].rhw = 1.0f; verts[2].color = color; verts[3].x = centerX + spread * height; verts[3].y = centerY; verts[3].z = 0.0f; verts[3].rhw = 1.0f; verts[3].color = color; // bottom segment verts[4].x = centerX; verts[4].y = centerY + (spread + segmentLen) * height; verts[4].z = 0.0f; verts[4].rhw = 1.0f; verts[4].color = color; verts[5].x = centerX; verts[5].y = centerY + spread * height; verts[5].z = 0.0f; verts[5].rhw = 1.0f; verts[5].color = color; // left segment verts[6].x = centerX - (spread + segmentLen) * height; verts[6].y = centerY; verts[6].z = 0.0f; verts[6].rhw = 1.0f; verts[6].color = color; verts[7].x = centerX - spread * height; verts[7].y = centerY; verts[7].z = 0.0f; verts[7].rhw = 1.0f; verts[7].color = color; mVB->Unlock(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for the ReticleRenderable // ReticleRenderable::~ReticleRenderable() { if (mVB) { mVB->Release(); mVB = NULL; } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLDrawReticleRenderable // Not much to check here, the entity and DCS pointers must be valid while // the instance is allowed to be NULL // Logical ReticleRenderable::TestInstance() const { VideoRenderable::TestInstance(); Check_Pointer(myReticle); Check_Pointer(rendererReticle); Check_Pointer(myView); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the ReticleRenderable // Nothing to execute here so we just pass it down to the next lower level. // void ReticleRenderable::Execute() { // // See if the reticle has moved // if(myOldReticlePosition != myReticle->reticlePosition) { myOldReticlePosition = myReticle->reticlePosition; // // Re-create the display list that positions the reticle // // dpl2d_OpenDisplayList( // myPositionDisplayList, // dpl2d_open_mode_clear); // dpl2d_IdMatrix(my_2d_matrix); // dpl2d_TranslateMatrix( // my_2d_matrix, // myOldReticlePosition.x, // myOldReticlePosition.y ); // dpl2d_AddSetMatrix( // myPositionDisplayList, // my_2d_matrix ); // dpl2d_CloseDisplayList(myPositionDisplayList); // dpl2d_FlushDisplayList(myPositionDisplayList); } // we've done everything that needs to be done, no need to call parent } void ReticleRenderable::Render(int pass, const D3DXMATRIX *viewTransform) { if (myReticle->reticleState == Reticle::ReticleState::ReticleOn) { LPDIRECT3DDEVICE9 device = myRenderer->GetDevice(); device->SetTexture(0, NULL); device->SetStreamSource(0, mVB, 0, sizeof(L4VERTEX_2D)); device->DrawPrimitive(D3DPT_LINELIST, 0, 4); } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for the CameraShipHUDRenderable // CameraShipHUDRenderable::CameraShipHUDRenderable(Entity *entity, ExecutionType execution_type, int *player_index, Logical *display_ranking_window) : VideoRenderable(entity, execution_type) { //STUBBED: DPL RB 1/14/07 // // Remember the entity that this renderable is attached to // LPDIRECT3DDEVICE9 device = myRenderer->GetDevice(); device->CreateVertexBuffer(sizeof(L4VERTEX_2D_TEX) * 4, D3DUSAGE_WRITEONLY, L4VERTEX_2D_TEX_FVF, D3DPOOL_MANAGED, &mVB, NULL); L4VERTEX_2D_TEX *verts; mVB->Lock(0, 0, (void**)&verts, 0); memset(verts, 0, sizeof(L4VERTEX_2D_TEX) * 4); DWORD color = D3DCOLOR_XRGB(0, 128, 0); float width = myRenderer->GetWidth(); float height = myRenderer->GetHeight(); float centerX = width / 2.0f; float centerY = height / 2.0f; float nameWidth = (width * 0.32f) / 2.0f; float nameHeight = height * 0.10f; // top right verts[0].x = centerX + nameWidth; verts[0].y = height - (nameHeight * 2.0f); verts[0].u = 1.0f; verts[0].v = 0.0f; verts[0].rhw = 1.0f; verts[0].color = color; // top left verts[1].x = centerX - nameWidth; verts[1].y = height - (nameHeight * 2.0f); verts[1].u = 0.0f; verts[1].v = 0.0f; verts[1].rhw = 1.0f; verts[1].color = color; // bottom right verts[2].x = centerX + nameWidth; verts[2].y = height - nameHeight; verts[2].u = 1.0f; verts[2].v = 1.0f; verts[2].rhw = 1.0f; verts[2].color = color; // bottom left verts[3].x = centerX - nameWidth; verts[3].y = height - nameHeight; verts[3].u = 0.0f; verts[3].v = 1.0f; verts[3].rhw = 1.0f; verts[3].color = color; mVB->Unlock(); // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Read in PlayerName Geometry //~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // //playerNameObject[0] = dpl_LoadObject("PNAME1.bgf", dpl_load_normal); //playerNameObject[1] = dpl_LoadObject("PNAME2.bgf", dpl_load_normal); //playerNameObject[2] = dpl_LoadObject("PNAME3.bgf", dpl_load_normal); //playerNameObject[3] = dpl_LoadObject("PNAME4.bgf", dpl_load_normal); //playerNameObject[4] = dpl_LoadObject("PNAME5.bgf", dpl_load_normal); //playerNameObject[5] = dpl_LoadObject("PNAME6.bgf", dpl_load_normal); //playerNameObject[6] = dpl_LoadObject("PNAME7.bgf", dpl_load_normal); //playerNameObject[7] = dpl_LoadObject("PNAME8.bgf", dpl_load_normal); // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Read in Ordinal Rankings Geometry //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // //ordinalObject[0] = dpl_LoadObject("PLACE1.bgf", dpl_load_normal); //ordinalObject[1] = dpl_LoadObject("PLACE2.bgf", dpl_load_normal); //ordinalObject[2] = dpl_LoadObject("PLACE3.bgf", dpl_load_normal); //ordinalObject[3] = dpl_LoadObject("PLACE4.bgf", dpl_load_normal); //ordinalObject[4] = dpl_LoadObject("PLACE5.bgf", dpl_load_normal); //ordinalObject[5] = dpl_LoadObject("PLACE6.bgf", dpl_load_normal); //ordinalObject[6] = dpl_LoadObject("PLACE7.bgf", dpl_load_normal); //ordinalObject[7] = dpl_LoadObject("PLACE8.bgf", dpl_load_normal); // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Initialize CameraFollowing //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // followedPlayerIndex = player_index; oldFollowedPlayerIndex = -1; // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Create One DCS for a Camera Following Name Bitmap //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // //followedNameDCS = dpl_NewDCS(); //followedNameInstance = dpl_NewInstance(); //dpl_ScaleDCS ( followedNameDCS, 0.20f, 0.20f, 1.0f ); //dpl_TranslateDCS ( followedNameDCS, 0.0f, -0.15f, -0.5f ); //dpl_SetDCSIgnoreGeo ( followedNameDCS, 1 ); //dpl_SetDCSTraversal ( followedNameDCS, 0x7 ); //dpl_AddDCSToScene ( followedNameDCS ); //dpl_SetInstanceObject ( followedNameInstance, playerNameObject[0] ); //dpl_AddInstanceToDCS ( followedNameDCS, followedNameInstance ); //dpl_SetInstanceVisibility ( followedNameInstance, 1 ); //dpl_FlushInstance ( followedNameInstance ); //dpl_FlushDCS ( followedNameDCS ); // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Create One DCS for Camera Following Ordinal Ranking Bitmap //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // //followedOrdinalDCS = dpl_NewDCS(); //followedOrdinalInstance = dpl_NewInstance(); //dpl_AddDCSToDCS ( followedNameDCS, followedOrdinalDCS ); //dpl_SetInstanceObject ( followedOrdinalInstance, ordinalObject[0] ); //dpl_AddInstanceToDCS ( followedOrdinalDCS, followedOrdinalInstance ); //dpl_SetDCSIgnoreGeo ( followedOrdinalDCS, 1 ); //dpl_SetDCSTraversal ( followedOrdinalDCS, 0x7 ); //dpl_TranslateDCS ( followedOrdinalDCS, -0.75f, 0.0f, 0.0f ); //dpl_SetInstanceVisibility ( followedOrdinalInstance, 0 ); //dpl_FlushInstance ( followedOrdinalInstance ); //dpl_FlushDCS ( followedOrdinalDCS ); // //~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Create the Ranking Window //~~~~~~~~~~~~~~~~~~~~~~~~~~~ // displayRankingWindow = display_ranking_window; oldDisplayRankingWindow = False; Scalar rank_window_y; rank_window_y = 0.16f; //rankingWindowDCS = dpl_NewDCS(); //dpl_ScaleDCS ( rankingWindowDCS, 0.12f, 0.12f, 1.0f ); //dpl_TranslateDCS ( rankingWindowDCS, 0.22f, rank_window_y, -0.5f ); //dpl_SetDCSIgnoreGeo ( rankingWindowDCS, 1 ); //dpl_SetDCSTraversal ( rankingWindowDCS, 0x7 ); //dpl_AddDCSToScene ( rankingWindowDCS ); //dpl_FlushDCS ( rankingWindowDCS ); // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Initialize the pointer's to the player Ranks //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // playerRank = NULL; oldPlayerRank = NULL; nameDCS = NULL; rankDCS = NULL; nameInstance = NULL; rankInstance = NULL; // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // See How Many Regular Players and CameraShip Players! //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // playerCount = 0; Check(application); EntityManager *entity_mgr = application->GetEntityManager(); Check(entity_mgr); EntityGroup *player_group = entity_mgr->FindGroup("Players"); if (player_group) { Check(player_group); ChainIteratorOf player_iterator(player_group->groupMembers); playerCount = player_iterator.GetSize(); } EntityGroup *camera_player_group = entity_mgr->FindGroup("CameraPlayers"); int camera_player_count=0; if (camera_player_group) { Check(player_group); ChainIteratorOf camera_iterator(camera_player_group->groupMembers); camera_player_count = camera_iterator.GetSize(); } // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Make the Arrays for Ranking the size of regular and cameras players // summed up. This is necessary since GameMachineHost type of Camera // Ships also have a bitmapIndex! //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // if (playerCount) { camera_player_count += playerCount; Verify(camera_player_count <= MAX_PLAYER_NAMES); playerRank = new (int (*[camera_player_count])); Register_Pointer(playerRank); Player *active_player; if(player_group) { Check(player_group); ChainIteratorOf player_iterator(player_group->groupMembers); while ((active_player = (Player*) player_iterator.ReadAndNext()) != NULL) { // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // PlayerRank Array indexed by bitmapIndex // holds that player's ranking //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Check(active_player); Verify( active_player->playerBitmapIndex > 0 && active_player->playerBitmapIndex <= MAX_PLAYER_NAMES ); playerRank[active_player->playerBitmapIndex - 1] = &active_player->playerRanking ; } } if (camera_player_group) { ChainIteratorOf camera_iterator(camera_player_group->groupMembers); while ((active_player = (Player*) camera_iterator.ReadAndNext()) != NULL) { // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // PlayerRank Array indexed by bitmapIndex // holds that player's ranking //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Check(active_player); Verify( active_player->playerBitmapIndex > 0 && active_player->playerBitmapIndex <= MAX_PLAYER_NAMES ); playerRank[active_player->playerBitmapIndex - 1] = &active_player->playerRanking ; } } // //~~~~~~~~~~~~~~~~~~~~~~~~~ // Initialize OldPlayerRank //~~~~~~~~~~~~~~~~~~~~~~~~~ // oldPlayerRank = new int[camera_player_count]; Register_Pointer(oldPlayerRank); int ii; for(ii=0; iiGetApplicationState() == Application::StoppingMission || application->GetApplicationState() == Application::EndingMission) { //dpl_SetInstanceVisibility ( followedOrdinalInstance, 0 ); //dpl_SetInstanceVisibility ( followedNameInstance, 0 ); //dpl_FlushInstance ( followedOrdinalInstance ); //dpl_FlushInstance ( followedNameInstance ); } VideoRenderable::Execute(); } void CameraShipHUDRenderable::Render(int pass, const D3DXMATRIX *viewTransform) { if (application->GetApplicationState() == Application::RunningMission && oldFollowedPlayerIndex >= 0 && oldFollowedPlayerIndex < MAX_PLAYER_NAMES) { LPDIRECT3DDEVICE9 device = myRenderer->GetDevice(); device->SetFVF(L4VERTEX_2D_TEX_FVF); device->SetStreamSource(0, mVB, 0, sizeof(L4VERTEX_2D_TEX)); device->SetTexture(0, myRenderer->GetNameTexture(oldFollowedPlayerIndex)); device->DrawPrimitive(D3DPT_TRIANGLESTRIP, 0, 2); } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Logical CameraShipHUDRenderable::TestInstance() const { VideoRenderable::TestInstance(); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for DCSMorphObjectRenderable // DCSMorphObjectRenderable::DCSMorphObjectRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable dpl_OBJECT *destination_object, // destination dpl_OBJECT *start_object, // start object dpl_OBJECT *end_object, // end object Scalar *morph_control, // pointer to control variable int32 morph_mode, // Defines type of morph to do bool isDeathZone, // DPL Zone this stuff will live in (for culling) dpl_ISECT_MODE intersect_mode, // type of intersections to do on this object uint32 intersect_mask // intersection mask for the object ): VideoRenderable(entity, execution_type) { isDeathDraw = isDeathZone; //STUBBED: DPL RB 1/14/07 //// //// Check incoming data //// //Check_Pointer(destination_object); //Check_Pointer(start_object); //Check_Pointer(end_object); //Check_Pointer(morph_control); //Check_Pointer(this_zone); //// //// Remember my dpl object, intersect and offset data //// //myDPLObject = destination_object; //myStartObject = start_object; //myEndObject = end_object; //myMorphControl = morph_control; //oldMorphControl = *myMorphControl; //myMorphMode = morph_mode; //myDPLZone = this_zone; //myIntersectMode = intersect_mode; //myIntersectMask = intersect_mask; //myDCS = NULL; //myInstance = NULL; //// //// We need to construct a DCS node here and remember it. The next class up is //// expected to handle the std::flushing and connecting of structure so we just setup //// the DCS and zone information here, leaving std::flushing to someone else. //// //myDCS = dpl_NewDCS (); //Check_Pointer ( myDCS ); //dpl_SetDCSZone ( myDCS, myDPLZone ); //// //// Construct the instance(s) and hang them on the DCS. Since we may be building //// more than one instance, we have to take care of std::flushing them here. //// //myInstance = dpl_NewInstance(); //Check_Pointer ( myInstance); //dpl_SetInstanceObject ( myInstance, myDPLObject); //dpl_SetInstanceIntersect ( myInstance, myIntersectMode ); //dpl_SetInstanceSectMask ( myInstance, myIntersectMask ); //dpl_SetInstanceVisibility ( myInstance, 1 ); //dpl_AddInstanceToDCS ( myDCS, myInstance ); //dpl_FlushInstance ( myInstance ); //// //// Setup the morph and do the initial morph to get the destination object ////-------------------------------------------------------------------------- //// NOTE: dpl_MorphObject seems to have Start and End objects reversed //// so they are reversed here as well...(two negatives make positive) ////-------------------------------------------------------------------------- //dpl_MorphObject(myDPLObject,myStartObject,myEndObject,oldMorphControl,myMorphMode); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for DCSMorphObjectRenderable // DCSMorphObjectRenderable::~DCSMorphObjectRenderable() { //STUBBED: DPL RB 1/14/07 //// //// Check our structure before we do anything //// //Check(this); //// //// Delete the instance(s) hanging on the DCS (if any) //// NOTE: we may want to iterate through all the instances here using DPL routines //// //dpl_RemoveInstanceFromDCS(myDCS, myInstance); //dpl_DeleteInstance(myInstance); //// //// Delete the DCS //// //dpl_DeleteDCS(myDCS); //myDCS = NULL; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DCSMorphObjectRenderable // Logical DCSMorphObjectRenderable::TestInstance() const { // // Call our parent's TestInstance first // VideoRenderable::TestInstance(); // // Test our own variables // Check_Pointer(myDPLObject); Check_Pointer(myStartObject); Check_Pointer(myEndObject); Check_Pointer(myMorphControl); Check_Pointer(myDPLZone); Check_Pointer(myDCS); Check_Pointer(myInstance); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the DCSMorphObjectRenderable // If the morph control variable has changed, we re-do the morph // void DCSMorphObjectRenderable::Execute() { //STUBBED: DPL RB 1/14/07 //// //// Check our variables //// //Check(this); //// //// See if the morph control varaible has changed //// //if(oldMorphControl != *myMorphControl) //{ // oldMorphControl = *myMorphControl; // //-------------------------------------------------------------------------- // // NOTE: dpl_MorphObject seems to have Start and End objects reversed // // so they are reversed here as well...(two negatives make positive) // //-------------------------------------------------------------------------- // dpl_MorphObject(myDPLObject,myStartObject,myEndObject,oldMorphControl,myMorphMode); //} //// //// Call the next lower execute method //// //#if DEBUG_LEVEL > 0 //VideoRenderable::Execute(); // #endif VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for RootMorphRenderable // RootMorphRenderable::RootMorphRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable dpl_OBJECT *destination_object, // destination dpl_OBJECT *start_object, // start object dpl_OBJECT *end_object, // end object Scalar *morph_control, // pointer to control variable int32 morph_mode, // Defines type of morph to do bool isDeathZone, // DPL Zone this stuff will live in (for culling) dpl_ISECT_MODE intersect_mode, // type of intersections to do on this object uint32 intersect_mask // intersection mask for the object ): DCSMorphObjectRenderable( entity, // Entity to attach the renderable to execution_type, // How/when to execute the renderable destination_object, // destination start_object, // start object end_object, // end object morph_control, // pointer to control variable morph_mode, // Defines type of morph to do isDeathZone, // DPL Zone this stuff will live in (for culling) intersect_mode, // type of intersections to do on this object intersect_mask) // intersection mask for the object { //STUBBED: DPL RB 1/14/07 //// //// All the incoming data will have been checked by DCSObjectRenderable //// already, so we don't have to check anything locally. //// //// //// Initialize our variables //// //oldLocalToWorld = myEntity->localToWorld; //// //// Now we finish the work of hooking up and initializing the root renderable //// Add the DCS to the scene and initialize it's matrix with the localToWorld //// transformation from our entity //// //dpl_AddDCSToScene ( myDCS ); //float32* tempMatrix = dpl_GetDCSMatrix( myDCS ); //Check_Pointer ( tempMatrix ); //*(Matrix4x4*)tempMatrix = myEntity->localToWorld; //dpl_FlushDCS ( myDCS ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for RootMorphRenderable // RootMorphRenderable::~RootMorphRenderable() { //STUBBED: DPL RB 1/14/07 //// //// Check our structure before we do anything //// //Check(this); //// //// Remove the DCS from the scene, deletion of the DCS and it's instances is //// handled by our parent class. //// //dpl_RemoveDCSFromScene(myDCS); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the RootMorphRenderable // Logical RootMorphRenderable::TestInstance() const { // // Call our parent's TestInstance first // DCSMorphObjectRenderable::TestInstance(); // // Test our own variables // Check(&oldLocalToWorld); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the RootMorphRenderable // Nothing to execute here so we just pass it down to the next lower level. // void RootMorphRenderable::Execute() { //STUBBED: DPL RB 1/14/07 //// //// Check our variables //// //Check(this); //// //// If our entity has changed it's localToWorld matrix, update DPL //// //if(oldLocalToWorld != myEntity->localToWorld) //{ // oldLocalToWorld = myEntity->localToWorld; // float32* tempMatrix = dpl_GetDCSMatrix(myDCS); // Check_Pointer (tempMatrix); // *(Matrix4x4*)tempMatrix = oldLocalToWorld; // DPL_FLUSH_DCS ( myDCS ); //} //// //// Call the execute method in our parent //// DCSMorphObjectRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for ChildMorphRenderable // ChildMorphRenderable::ChildMorphRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable dpl_OBJECT *destination_object, // destination dpl_OBJECT *start_object, // start object dpl_OBJECT *end_object, // end object Scalar *morph_control, // pointer to control variable int32 morph_mode, // Defines type of morph to do bool isDeathZone, // DPL Zone this stuff will live in (for culling) dpl_ISECT_MODE intersect_mode, // type of intersections to do on this object uint32 intersect_mask, // intersection mask for the object dpl_DCS *parent_DCS // the parent DCS we will be offsetting from ): DCSMorphObjectRenderable( entity, // Entity to attach the renderable to execution_type, // How/when to execute the renderable destination_object, // destination start_object, // start object end_object, // end object morph_control, // pointer to control variable morph_mode, // Defines type of morph to do isDeathZone, // DPL Zone this stuff will live in (for culling) intersect_mode, // type of intersections to do on this object intersect_mask) // intersection mask for the object { //STUBBED: DPL RB 1/14/07 //// //// All the incoming data will have been checked by DCSObjectRenderable //// already, so we don't have to check anything locally. //// //Check_Pointer(parent_DCS); //// //// Now we finish the work of hooking up and initializing the root renderable //// Add the DCS to the scene and initialize it's matrix with the localToWorld //// transformation from our entity //// //dpl_AddDCSToDCS ( parent_DCS, myDCS ); //dpl_FlushDCS ( myDCS ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for ChildMorphRenderable // ChildMorphRenderable::~ChildMorphRenderable() { // // Check our structure before we do anything // Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the ChildMorphRenderable // Logical ChildMorphRenderable::TestInstance() const { // // Call our parent's TestInstance first // DCSMorphObjectRenderable::TestInstance(); // // Test our own variables // return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the ChildMorphRenderable // Nothing to execute here so we just pass it down to the next lower level. // void ChildMorphRenderable::Execute() { // // Check our variables // Check(this); // // Call the execute method in our parent // DCSMorphObjectRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for ScalingExplosionRenderable // ScalingExplosionRenderable::ScalingExplosionRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable d3d_OBJECT *graphical_object, // This will be the scaling explosion object bool isDeathZone, // DPL Zone this stuff will live in (for culling) dpl_ISECT_MODE intersect_mode, // type of intersections to do on this object uint32 intersect_mask, // intersection mask for the object HierarchicalDrawComponent *parent, // the parent DCS we will be offsetting from LinearMatrix *offset_matrix, // offset matrix to be applied prior to joint DCS Vector3D *control_vector, // Effect control velocity vector Vector3D *accel_vector, // rate of change of control vector Scalar gravity, int *trigger // doesn't run till the trigger comes up ): ChildOffsetRenderable( entity, // Entity to attach the renderable to execution_type, // How/when to execute the renderable graphical_object, // object to hang on the DCS, may be a list later isDeathZone, // DPL Zone this stuff will live in (for culling) intersect_mode, // type of intersections to do on this object intersect_mask, // intersection mask for the object parent, // the parent DCS we will be offsetting from offset_matrix) // offset matrix to be applied prior to joint DCS { // // Check the incoming data // Check(control_vector); #if DEBUG_LEVEL > 0 if(trigger) Check_Pointer(trigger); #endif // // Initialize our variables // myScalingVector.x = 0.01; myScalingVector.y = 0.01; myScalingVector.z = 0.01; myVelocityVector = *control_vector; myVelocityChange = *accel_vector; myGravity = gravity; myVelocity = 0.0f; myTranslation.x = 0.0; myTranslation.y = 0.0; myTranslation.z = 0.0; myTrigger = trigger; // // Initialize the matrix in this dcs // //float32* tempMatrix = dpl_GetDCSMatrix( myDCS ); //Check_Pointer ( tempMatrix ); //AffineMatrix tempAffine(True); //tempAffine *= myScalingVector; //tempAffine *= myTranslation; //*(Matrix4x4*)tempMatrix = tempAffine; //dpl_FlushDCS ( myDCS ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for ScalingExplosionRenderable // ScalingExplosionRenderable::~ScalingExplosionRenderable() { // // Check our structure before we do anything // Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the ScalingExplosionRenderable // Logical ScalingExplosionRenderable::TestInstance() const { // // Call our parent's TestInstance first // DCSObjectRenderable::TestInstance(); // // Test our own variables // Check(&myScalingVector); Check(&myVelocityVector); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the ScalingExplosionRenderable // Nothing to execute here so we just pass it down to the next lower level. // void ScalingExplosionRenderable::Execute() { // // Check our variables // Check(this); if(!myTrigger || *myTrigger != 0) { // // Apply the scaling factor to the object // myVelocityVector += myVelocityChange; myScalingVector += myVelocityVector; myVelocity += myGravity; myTranslation.y += myVelocity; // // Initialize the matrix in this dcs // //float32* tempMatrix = dpl_GetDCSMatrix( myDCS ); //Check_Pointer ( tempMatrix ); //AffineMatrix tempAffine(True); //tempAffine *= myScalingVector; //tempAffine *= myTranslation; //*(Matrix4x4*)tempMatrix = tempAffine; //DPL_FLUSH_DCS ( myDCS ); // // Call the execute method in our parent // ChildOffsetRenderable::Execute(); } } // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Micro Renderables //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // // From here to the row of === is pretty kludgy stuff to allow dave to prototype // some explosion stuff. // I expect to replace most of it within a week with the all-new micro // renderable system. // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for DependantRenderable // This is a class of renderable that has other dependant renderables which it // will execute on command. This is a base for this type of renderable and is // not ment to be used by itself. // DependantRenderable::DependantRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type // How/when to execute the renderable ): VideoRenderable(entity, execution_type), dependantRenderableSocket(NULL) { // Check incoming data // Initialize variables } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for DependantRenderable DependantRenderable::~DependantRenderable() { // Check our structure before we do anything Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DependantRenderable Logical DependantRenderable::TestInstance() const { // Call our parent's TestInstance first VideoRenderable::TestInstance(); // Now do our checking Check(&dependantRenderableSocket); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // AddDependantRenderable for the DependantRenderable // This adds an existing renderable as a dependant on this renderable so it // will be run when this renderable is executed. void DependantRenderable::AddDependantRenderable(Component *dependant) { Check(dependant); dependantRenderableSocket.Add(dependant); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the DependantRenderable void DependantRenderable::Execute() { Component *dependant; // // Make an iterator for our components then execute them all // // std::cout<<"DependantRenderable::Execute()\n"; SChainIteratorOf dependant_iterator(&dependantRenderableSocket); while ((dependant = dependant_iterator.ReadAndNext()) != NULL) { dependant->Execute(); // std::cout<<"dependant->Execute();\n"; } // Call the next lower execute method VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for ScalarTriggerRenderable // Whenever "watched_value" changes by "watched_precision" the dependants of this // renderable will be called. // ScalarTriggerRenderable::ScalarTriggerRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable Scalar *watched_value, // we run dependants when this changes Scalar watched_precision // watched_value must change by this much ): DependantRenderable(entity, execution_type) { // // Check incoming data // Check_Pointer(watched_value); // // Initialize variables // myWatchedValue = watched_value; myOldWatchedValue = *myWatchedValue; myPrecision = watched_precision; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for ScalarTriggerRenderable ScalarTriggerRenderable::~ScalarTriggerRenderable() { // Check our structure before we do anything Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the ScalarTriggerRenderable Logical ScalarTriggerRenderable::TestInstance() const { // Call our parent's TestInstance first DependantRenderable::TestInstance(); // Now do our checking Check_Pointer(myWatchedValue); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the ScalarTriggerRenderable void ScalarTriggerRenderable::Execute() { Check(this); // // If there hasn't been a significant enough change, return right now // if(Abs((*myWatchedValue - myOldWatchedValue)) < myPrecision) return; // // Update my watcher data, then call my parent to execute the dependants // myOldWatchedValue = *myWatchedValue; DependantRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for TimeCullRenderable // This renderable will run all it's dependants at a set frequency based on // a clock value supplied by the culling system. // TimeCullRenderable::TimeCullRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable Scalar delay_between_runs // Time delay between executions of dependants ): DependantRenderable(entity, execution_type) { // // Check incoming data // // // Initialize the renderable, set clock so this will execute the first time // it's called. // delayBetweenRuns = delay_between_runs; nextRunTime = myRenderer->GetCurrentFrameTime(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for TimeCullRenderable TimeCullRenderable::~TimeCullRenderable() { // Check our structure before we do anything Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the TimeCullRenderable Logical TimeCullRenderable::TestInstance() const { // Call our parent's TestInstance first DependantRenderable::TestInstance(); // Now do our checking return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the TimeCullRenderable void TimeCullRenderable::Execute() { Check(this); // // If it's time, call my parent to execute the dependants // if(nextRunTime <= myRenderer->GetCurrentFrameTime()) { nextRunTime = myRenderer->GetCurrentFrameTime() + delayBetweenRuns; DependantRenderable::Execute(); // std::cout<<"Time Cull ran dependants\n"; } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // MechCullRenderable::MechCullRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable Logical always_run_all, // If true, disable culling and run everything bool isDeathZone // Switch off this zone when the mech goes off screen ): DependantRenderable(entity, execution_type), legRenderableSocket(NULL) { isDeathDraw = isDeathZone; Check_Pointer(my_zone); myAlwaysRunAll = always_run_all; //myZone = my_zone; myMechWasVisible = True; myNextRootUpdate = myRenderer->GetCurrentFrameTime(); myNextLegUpdate = myRenderer->GetCurrentFrameTime(); myRootUpdateRate = 0.0; myLegUpdateRate = 0.0; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for MechCullRenderable MechCullRenderable::~MechCullRenderable() { // Check our structure before we do anything Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // AddDependantLegRenderable for the MechCullRenderable // This adds an existing renderable as a dependant of the leg chain. void MechCullRenderable::AddDependantLegRenderable(Component *dependant) { Check(dependant); legRenderableSocket.Add(dependant); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the MechCullRenderable Logical MechCullRenderable::TestInstance() const { // Call our parent's TestInstance first DependantRenderable::TestInstance(); // Now do our checking Check_Pointer(myZone); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the MechCullRenderable void MechCullRenderable::Execute() { //STUBBED: DPL RB 1/14/07 //#define CULL_VOLUME_SIZE 11.0 // Assume mech (or other object) fills 10 meter bubble Scalar current_time; //Point3D // target_point; //Component // *dependant; //Check(this); //// //// If we've been told to always run everything, do so. I don't flip the //// profile bit here because I only want to time the actual cull algorithim. //// //if(myAlwaysRunAll) //{ // DependantRenderable::Execute(); // SChainIteratorOf dependant_iterator(&legRenderableSocket); // while ((dependant = dependant_iterator.ReadAndNext()) != NULL) // { // dependant->Execute(); // } // myMechWasVisible = True; // return; //} //SET_VIDEO_MECH_CULL_RENDERABLE(); //// //// Continue on to do the full culling process //// current_time = myRenderer->GetCurrentFrameTime(); //// //// Transform this entities position into eye space //// //target_point = myEntity->localOrigin.linearPosition; //target_point *= (*myRenderer->GetWorldToEyeMatrix()); //Check(this); //// //// See if this is inside the viewing volume //// HACK, viewing volume is hard coded here for now //// negative z goes into the screen //// //// See if it's behind me //// //if((target_point.z - CULL_VOLUME_SIZE) >= 0.0f) //{ // if(myMechWasVisible) // { // myMechWasVisible = False; // dpl_SetZoneAllViewsOff (myZone); // dpl_FlushZone (myZone); // // // // Set the root rate to slow and the leg rate to stopped // // // myRootUpdateRate = 1.0f; // myLegUpdateRate = 60.0f; // myNextRootUpdate = current_time + myRootUpdateRate; // myNextLegUpdate = current_time + myLegUpdateRate; // } //} //else //{ // // // // Fix up the Z so objects very close behind us (close enough they might // // stick into our view) will be properly culled. // // // if(target_point.z >= 0) // target_point.z = 0.1; // else // target_point.z = Abs(target_point.z); // Check(this); // // // // See if the object's volume is to the left or right of the culling // // volume. // // // if(((Abs(target_point.x)-CULL_VOLUME_SIZE)/target_point.z) > myRenderer->GetViewRatio()) // { // // // // If we were visible before, we're not any more // // // Check(this); // if(myMechWasVisible) // { // myMechWasVisible = False; // dpl_SetZoneAllViewsOff (myZone); // dpl_FlushZone (myZone); // // // // Set the root rate to slow and the leg rate to stopped // // // myRootUpdateRate = 1.0f; // myLegUpdateRate = 60.0f; // myNextRootUpdate = current_time + myRootUpdateRate; // myNextLegUpdate = current_time + myLegUpdateRate; // } // } // else // { // // // // If we were invisible before, we're visible now // // // Check(this); // if(!myMechWasVisible) // { // myMechWasVisible = True; // dpl_SetZoneAllViewsOn (myZone); // dpl_FlushZone (myZone); // // // // Set the various update rates appropriately and force an update // // // myRootUpdateRate = 0.0; // myNextRootUpdate = current_time; // myNextLegUpdate = current_time; // } // // // // Set the leg update rate based on range (really should be a formulia) // // // if(target_point.z < 500.0f) // myLegUpdateRate = 0.0; // else // myLegUpdateRate = 0.25; // } //} //// //// Flip the trace bit here because I don't want to include the cost of the //// dependant renderables. //// //CLEAR_VIDEO_MECH_CULL_RENDERABLE(); //// //// Use the data already calculated to determine which of the dependant //// renderable groups we should execute. //// //if(myNextLegUpdate <= current_time) //{ // myNextLegUpdate = current_time + myLegUpdateRate; // // // // Execute all the leg renderables // // // SChainIteratorOf dependant_iterator(&legRenderableSocket); // while ((dependant = dependant_iterator.ReadAndNext()) != NULL) // { // dependant->Execute(); // } //} if(myNextRootUpdate <= current_time) { myNextRootUpdate = current_time + myRootUpdateRate; DependantRenderable::Execute(); } return; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for InstanceSwitchRenderable InstanceSwitchRenderable::InstanceSwitchRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable dpl_INSTANCE *this_instance, // the instance to control Logical sense, // instance on when trigger is.... int *trigger // true if the instance is on, false if off ): VideoRenderable(entity, execution_type) { //STUBBED: DPL RB 1/14/07 //// Check incoming data //Check_Pointer(this_instance); //Check_Pointer(trigger); //// Initialize variables //mySense = sense; //myInstance = this_instance; //myTriggerAttribute = trigger; //oldTriggerAttribute = *myTriggerAttribute; //if(mySense == oldTriggerAttribute) //{ // dpl_SetInstanceVisibility ( myInstance, 1 ); //} //else //{ // dpl_SetInstanceVisibility ( myInstance, 0 ); //} // dpl_FlushInstance ( myInstance ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for InstanceSwitchRenderable InstanceSwitchRenderable::~InstanceSwitchRenderable() { // Check our structure before we do anything Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the InstanceSwitchRenderable Logical InstanceSwitchRenderable::TestInstance() const { // Call our parent's TestInstance first VideoRenderable::TestInstance(); Check_Pointer(myInstance); Check_Pointer(myTriggerAttribute); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the InstanceSwitchRenderable void InstanceSwitchRenderable::Execute() { //STUBBED: DPL RB 1/14/07 //// Check our variables //Check(this); //if(*myTriggerAttribute != oldTriggerAttribute) //{ // oldTriggerAttribute = *myTriggerAttribute; // if(mySense == oldTriggerAttribute) // { // dpl_SetInstanceVisibility ( myInstance, 1 ); // } // else // { // dpl_SetInstanceVisibility ( myInstance, 0 ); // } // dpl_FlushInstance ( myInstance ); //} //// Call the next lower execute method VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // StateInstanceSwitchRenderable is designed to be a watcher that connects to // a state dial. Whenever the state dial changes we are called and check to // see if the trigger state has been entered. If we are in the trigger state // we will change the instance visibility based on the sense variable passed // into the constructor. This lets you have an instance on while in a // certain state or off while in that state and on in others. // Messages Sent: None // Messages Received: None //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for StateInstanceSwitchRenderable // StateInstanceSwitchRenderable::StateInstanceSwitchRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable dpl_INSTANCE *this_instance, // the instance to control Logical sense, // true to turn on in this state, false for off StateIndicator *state_dial, // State dial we use to control the on/off unsigned trigger_state // State that we look for ): VideoRenderable(entity, execution_type) { //STUBBED: DPL RB 1/14/07 //// //// Check incoming data for correctness //// //Check_Pointer(this_instance); //Check(state_dial); //// //// Initialize variables //// //myInstance = this_instance; //mySense = sense; //myStateDial = state_dial; //myTriggerState = trigger_state; //// //// Put the instance in the proper state and std::flush it //// //if(myStateDial->GetState() == myTriggerState) //{ // if(mySense == True) // myLastInstanceState = True; // else // myLastInstanceState = False; //} //else //{ // if(mySense == True) // myLastInstanceState = False; // else // myLastInstanceState = True; //} //dpl_SetInstanceVisibility ( myInstance, myLastInstanceState ); //dpl_FlushInstance ( myInstance ); //// //// Connect us to the state dial's watcher hook //// //state_dial->AddVideoWatcher(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for StateInstanceSwitchRenderable StateInstanceSwitchRenderable::~StateInstanceSwitchRenderable() { // Check our structure before we do anything Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the StateInstanceSwitchRenderable Logical StateInstanceSwitchRenderable::TestInstance() const { // Call our parent's TestInstance first VideoRenderable::TestInstance(); Check_Pointer(myInstance); Check(myStateDial); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the StateInstanceSwitchRenderable --- called by the state dial // watcher hook when the state changes. The state dial won't call us if unless // the state actually changes so there is no need to filter transitions between // two identical states. // void StateInstanceSwitchRenderable::Execute() { //STUBBED: DPL RB 1/14/07 //unsigned // new_state; //// //// Check our variables //// //Check(this); //// //// See what state we should go into //// //if(myStateDial->GetState() == myTriggerState) //{ // if(mySense == True) // new_state = True; // else // new_state = False; //} //else //{ // if(mySense == True) // new_state = False; // else // new_state = True; //} //if(new_state != myLastInstanceState) //{ // myLastInstanceState = new_state; // dpl_SetInstanceVisibility ( myInstance, myLastInstanceState ); // dpl_FlushInstance ( myInstance ); //} //// Call the next lower execute method VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for MakeDCSFall MakeDCSFall::MakeDCSFall( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable dpl_DCS *this_DCS, // the DCS to control Scalar gravity, // Gravity in meters/sec squared int *trigger // true if the instance is on, false if off ): VideoRenderable(entity, execution_type) { // Check incoming data Check_Pointer(this_DCS); Check_Pointer(trigger); // // Was an input trigger provided? // if(trigger) { // Yes, remember a pointer to it and it's state myTrigger = trigger; oldMyTrigger = *myTrigger; } else { // No, point it at a fake trigger that is turned on fakeTrigger = 1; myTrigger = &fakeTrigger; oldMyTrigger = 0; } // // Initialize other variables // myDCS = this_DCS; myDisplacement = Point3D::Identity; myHalfAcceleration = gravity/2.0f; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for MakeDCSFall MakeDCSFall::~MakeDCSFall() { // Check our structure before we do anything Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the MakeDCSFall Logical MakeDCSFall::TestInstance() const { // Call our parent's TestInstance first VideoRenderable::TestInstance(); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the MakeDCSFall void MakeDCSFall::Execute() { //STUBBED: DPL RB 1/14/07 //// Check our variables //Check(this); //// //// Look for an edge in the trigger input //// //if(*myTrigger != oldMyTrigger) //{ // // // // A transition from zero to nonzero resets the DCS position and // // starts us falling again. // // // if(oldMyTrigger == 0) // { // myFallStart = myRenderer->GetCurrentFrameTime(); // myDisplacement = Point3D::Identity; // } // oldMyTrigger = *myTrigger; //} //// //// If the trigger is nonzero and the sweep isn't at 1 yet, update //// the sweep values. //// //if(oldMyTrigger != 0) //{ // Scalar // elapsed_time, // current_time; // // Figure displacement do to gravity... 0.5 * a * t^2 // // note that we've already taken a * 0.5 in the constructor // current_time = myRenderer->GetCurrentFrameTime(); // elapsed_time = current_time - myFallStart; // myDisplacement.y = myHalfAcceleration * (elapsed_time * elapsed_time); // float32* tempMatrix = dpl_GetDCSMatrix(myDCS); // Check_Pointer (tempMatrix); // *(Matrix4x4*)tempMatrix = myDisplacement; // DPL_FLUSH_DCS ( myDCS ); //} //// Call the next lower execute method VideoRenderable::Execute(); } //============================================================================= #if 0 //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for SquareWaveRenderable SquareWaveRenderable::SquareWaveRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable Scalar time_false, // time to spend in zero state Scalar time_true, // time to spend in one state int *trigger // starts square wave when it goes to 1 int start_state // state we start in int cycles // number of transitions before we stop ): VideoRenderable(entity, execution_type) { if(trigger) { // Yes, remember a pointer to it and it's state myTriggerInput = trigger; oldTriggerInput = *myTrigger; } else { // No, point it at a fake trigger that is turned on fakeTrigger = 1; myTriggerInput = &fakeTrigger; oldTriggerInput = 0; } // Initialize variables myTriggerInput = trigger; oldTriggerInput = 0; myNextStateChange = 0; myTimeFalse = time_false; myTimeTrue = time_true; myTriggerAttribute = start_state; myCyclesLeft = cycles; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for SquareWaveRenderable SquareWaveRenderable::~SquareWaveRenderable() { // Check our structure before we do anything Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the SquareWaveRenderable Logical SquareWaveRenderable::TestInstance() const { // Call our parent's TestInstance first VideoRenderable::TestInstance(); Verify(myTriggerTime > 0.0f); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the SquareWaveRenderable void SquareWaveRenderable::Execute() { Scalar current_time; // Check our variables Check(this); if(*myTriggerInput != oldTriggerInput && oldTriggerInput == 0) { if(myStartState) { myNextStateChange = myRenderer->GetCurrentFrameTime(); myNextStateChange += myTimeTrue; myTriggerAttribute = True; } else { myNextStateChange = myRenderer->GetCurrentFrameTime(); myNextStateChange += myTimeFalse; myTriggerAttribute = False; } myCyclesLeft = myCycles; } if(*myTriggerInput == 1 && myCyclesLeft > 0) { current_time = myRenderer->GetCurrentFrameTime(); if(current_time >= myNextStateChange) { myCyclesLeft--; myTriggerAttribute = (!myTriggerAttribute); if(myTriggerAttribute) { myNextStateChange = myRenderer->GetCurrentFrameTime(); myNextStateChange += myTimeTrue; } else { myNextStateChange = myRenderer->GetCurrentFrameTime(); myNextStateChange += myTimeFalse; } } } // Call the next lower execute method #if DEBUG_LEVEL > 0 VideoRenderable::Execute(); #endif } #endif //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for OneShotDelayRenderable // This renderable delays for a fixed amount after it's creation, then turns on // a trigger attribute. It is used for the triggering of other renderables a // fixed time after an object is created. OneShotDelayRenderable::OneShotDelayRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable Scalar delay_time, // How long to wait before raising the trigger Scalar duration_time // How long trigger is up (0.0 == stay up) ): VideoRenderable(entity, execution_type) { // Check incoming data Verify(delay_time >= 0.0f); Verify(duration_time >= 0.0f); // Initialize variables myState = WaitingForTriggerTime; myEndTimeFlag = !Small_Enough(duration_time); myTriggerTime = myRenderer->GetCurrentFrameTime(); myTriggerTime += delay_time; myTriggerEndTime = myTriggerTime + duration_time; myTriggerAttribute = NULL; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for OneShotDelayRenderable OneShotDelayRenderable::~OneShotDelayRenderable() { // Check our structure before we do anything Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the OneShotDelayRenderable Logical OneShotDelayRenderable::TestInstance() const { // Call our parent's TestInstance first VideoRenderable::TestInstance(); Verify(myTriggerTime > 0.0f); Verify(myTriggerEndTime >= myTriggerTime); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the OneShotDelayRenderable void OneShotDelayRenderable::Execute() { Scalar current_time; // Check our variables Check(this); if (myState != WaitingForEternity) { current_time = myRenderer->GetCurrentFrameTime(); // putting this here insures that the one-time will always spend // at least one frame at True before resetting. if (myState == WaitingForTriggerTime) { if (current_time > myTriggerTime) { myTriggerAttribute = 1; if (myEndTimeFlag) { myState = WaitingForTriggerEndTime; } else { myState = WaitingForEternity; myRenderer->RemoveDynamicRenderable(this); } } } else if (myState == WaitingForTriggerEndTime) { if (current_time > myTriggerEndTime) { myTriggerAttribute = NULL; myState = WaitingForEternity; myRenderer->RemoveDynamicRenderable(this); } } else { Dump(myState); Fail("invalid myState"); } } // Call the next lower execute method #if DEBUG_LEVEL > 0 VideoRenderable::Execute(); #endif VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for SweepRenderable // When triggered this renderable sweeps it's output attribute from 0.0 to 1.0 // over a preset time interval. Used for controling morphs. SweepRenderable::SweepRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable Scalar delay_time, // How long to take to sweep from 0 to 1 int cycles, // number of times to cycle before stopping int *trigger, // When it goes from 0 to 1 it resets the sweep generator Scalar start_value, // Initial value of sweep (default = 0.0f) Scalar end_value, // Final value of sweep (default = 1.0f) SweepFunction sweep_function // Function applied to sweep ): VideoRenderable(entity, execution_type) { // // Verify incoming data // Verify(delay_time >= 0.0f); Verify(start_value <= end_value); if (sweep_function == Y_SQR_X) { Verify(start_value >= 0.0f); } // // Was an input trigger provided? // if(trigger) { // Yes, remember a pointer to it and it's state myTrigger = trigger; oldMyTrigger = *myTrigger; } else { // No, point it at a fake trigger that is turned on fakeTrigger = 1; myTrigger = &fakeTrigger; oldMyTrigger = 0; } // // Initialize other variables // mySweepFunction = sweep_function; myStartValue = start_value; myEndValue = end_value; myCycleCount = cycles; mySweepTime = delay_time; mySweepAttribute = myStartValue; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for SweepRenderable SweepRenderable::~SweepRenderable() { // Check our structure before we do anything Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the SweepRenderable Logical SweepRenderable::TestInstance() const { // Call our parent's TestInstance first VideoRenderable::TestInstance(); Verify(mySweepTime >= 0.0f) Verify((mySweepAttribute >= myStartValue) && (mySweepAttribute <= myEndValue)); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the SweepRenderable void SweepRenderable::Execute() { // Check our variables Check(this); // // Look for an edge in the trigger input // if(*myTrigger != oldMyTrigger) { // // A transition from zero to nonzero resets all the sweep parameters // and starts the process over again. // if(oldMyTrigger == 0) { // A transition from zero to nonzero causes a reset of sweep timers // and starts the sweep running. mySweepStart = myRenderer->GetCurrentFrameTime(); mySweepAttribute = myStartValue; myCyclesLeft = myCycleCount; } oldMyTrigger = *myTrigger; } // // If the trigger is nonzero and the sweep isn't at 1 yet, update // the sweep values. // if(oldMyTrigger != 0 && myCyclesLeft > 0) { Scalar current_time; // putting this here insures that the sweep will always spend one frame at // {EndValue} before resetting. current_time = myRenderer->GetCurrentFrameTime(); if(mySweepAttribute >= myEndValue) { myCyclesLeft--; if(myCyclesLeft > 0) { mySweepStart = current_time; } } mySweepAttribute = myStartValue + (myEndValue - myStartValue) * (current_time - mySweepStart) / mySweepTime; if (mySweepFunction == Y_SQR_X) { mySweepAttribute = Sqrt(mySweepAttribute); } // else if (mySweepFunction == Y_ ) // { // } if(mySweepAttribute > myEndValue) { mySweepAttribute = myEndValue; } } // Call the next lower execute method #if DEBUG_LEVEL > 0 VideoRenderable::Execute(); #endif VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for PullFogRenderable // This routine handles swapping the fog settings in and out when you // turn headlight systems on and off. // PullFogRenderable::PullFogRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable Logical *light_1, Logical *light_2 // address containing the trigger ): VideoRenderable(entity, execution_type) { // // Check the inbound data, note that the parent DCS could be a null pointer // Check_Pointer(light_1); myLight1 = light_1; myOldLight1 = !(*myLight1); if(light_2 == NULL) { myLight2 = myLight1; } else { Check_Pointer(light_2); myLight2 = light_2; } myOldLight2 = !(*myLight2); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for PullFogRenderable // PullFogRenderable::~PullFogRenderable() { Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the PullFogRenderable // Logical PullFogRenderable::TestInstance() const { VideoRenderable::TestInstance(); Check_Pointer(myLight1); Check_Pointer(myLight2); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute method for PullFogRenderable. // void PullFogRenderable::Execute() { Check(this); if(*myLight1 != myOldLight1 || *myLight2 != myOldLight2) { myOldLight1 = *myLight1; myOldLight2 = *myLight2; if(myOldLight1 || myOldLight2) { myRenderer->SetFogStyle(DPLRenderer::searchLightOnFogStyle); } else { myRenderer->SetFogStyle(DPLRenderer::searchLightOffFogStyle); } } // Call the next lower execute method VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for DPLEffectRenderable // This routine handles the creation of a DPL special effect whenever the // trigger attribute changes. This is an edge triggered renderable and will // generate an effect on ANY form of state change. The only way to effect the // size and speed of the effect is by way of the DPL effect tables. // DPLEffectRenderable::DPLEffectRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable int *trigger, // address containing the trigger int effect_type, // DPL effect number to trigger HierarchicalDrawComponent *parent, // DCS the effect is relative to (may be NULL) Point3D *offset_point // Offset (or world coordinants if DCS is NULL) ): VideoRenderable(entity, execution_type, parent) { // // Check the inbound data, note that the parent DCS could be a null pointer // Check_Pointer(trigger); Verify(effect_type >= 0); #if DEBUG_LEVEL > 0 if(effect_DCS != NULL) Check_Pointer(effect_DCS); #endif Check(offset_point); // // Initialze the local variables // myTrigger = trigger; oldMyTrigger = *myTrigger; myEffectType = effect_type; // myEffectDCS = effect_DCS; myEffectOffset = *offset_point; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for DPLEffectRenderable // DPLEffectRenderable::~DPLEffectRenderable() { Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLEffectRenderable // Logical DPLEffectRenderable::TestInstance() const { VideoRenderable::TestInstance(); Check_Pointer(myTrigger); Verify(myEffectType >= 0); #if DEBUG_LEVEL > 0 if(myEffectDCS != NULL) Check_Pointer(myEffectDCS); #endif Check(&myEffectOffset); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute method for DPLEffectRenderable. // void DPLEffectRenderable::Execute() { //STUBBED: DPL RB 1/14/07 //Check_Pointer(myTrigger); //if(*myTrigger != oldMyTrigger) //{ // dpl_EXPLOSION_EFFECT_INFO my_explosion; // oldMyTrigger = *myTrigger; // my_explosion.type = myEffectType; // my_explosion.x = myEffectOffset.x; // my_explosion.y = myEffectOffset.y; // my_explosion.z = myEffectOffset.z; // dpl_Effect ( dpl_effect_type_explosion, myEffectDCS, &my_explosion ); //} //// Call the next lower execute method //#if DEBUG_LEVEL > 0 VideoRenderable::Execute(); // #endif } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for DPLPSFXRenderable // This routine triggers a pfx whenever the trigger attribute goes true. // since pfx effects have built-in durations we don't attempt to do any repeats // or other controls here, we just start one and kill it if the entity dies. // DPLPSFXRenderable::DPLPSFXRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable int *trigger, // address containing the trigger dpl_PARTICLESTART_EFFECT_INFO *psfx_definition, // name of file with the PFX description in it HierarchicalDrawComponent *parent, // DCS the effect is relative to (may be NULL) Point3D *offset_point // Offset (or world coordinants if DCS is NULL) ): VideoRenderable(entity, execution_type, parent) { // // Check the inbound data, note that the parent DCS could be a null pointer // Check_Pointer(trigger); #if DEBUG_LEVEL > 0 if(effect_DCS != NULL) Check_Pointer(effect_DCS); #endif Check(offset_point); if(!psfx_definition) { Fail("A pfx was not defined in the .ini file\n"); } // // Initialze the local variables // myTrigger = trigger; myOldTrigger = *myTrigger; // myEffectDCS = effect_DCS; myEffectOffset = *offset_point; myPSFXInfo = *psfx_definition; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for DPLPSFXRenderable // DPLPSFXRenderable::~DPLPSFXRenderable() { //STUBBED: DPL RB 1/14/07 //// !!!!HACK Note that because the effect id changes every time we start one, //// the destructor will only stop the last PFX played. We should probably //// be keeping track of all the ID's we've sent down to make sure everything //// attached to the DCS gets properly killed. //Check(this); //dpl_Effect ( dpl_effect_type_particlestop, NULL, &myPSFXInfo ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLPSFXRenderable // Logical DPLPSFXRenderable::TestInstance() const { VideoRenderable::TestInstance(); Check_Pointer(myTrigger); #if DEBUG_LEVEL > 0 if(myEffectDCS != NULL) Check_Pointer(myEffectDCS); #endif Check(&myEffectOffset); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute method for DPLPSFXRenderable. // void DPLPSFXRenderable::Execute() { Check_Pointer(myTrigger); if(*myTrigger != myOldTrigger) { myOldTrigger = *myTrigger; if(myOldTrigger == True) { // we put our id into the lower 16 bits because (at least) the upper 8 bits are flags L4Application *l4_application = Cast_Object(L4Application*, application); Check(l4_application); //myPSFXInfo.identifier = // (myPSFXInfo.identifier & 0xffff0000) | // l4_application->GetVideoRenderer()->GetUniqueID(); //dpl_Effect ( dpl_effect_type_particlestart, myEffectDCS, &myPSFXInfo ); } } // Call the next lower execute method VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for DPLPSFXStateRenderable // This routine triggers a pfx whenever a state dial transitions to a designated // state. // NOTE this currently does NOT trigger if the state dial is in the trigger state // when this renderable is created. // DPLPSFXStateRenderable::DPLPSFXStateRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable StateIndicator *effect_trigger, // Trigger effect when this state changes unsigned my_trigger, // The state to edge trigger on dpl_PARTICLESTART_EFFECT_INFO *psfx_definition, // name of file with the PFX description in it HierarchicalDrawComponent *parent, // DCS the effect is relative to (may be NULL) Point3D *offset_point // Offset (or world coordinants if DCS is NULL) ): VideoRenderable(entity, execution_type, parent) { // // Check the inbound data, note that the parent DCS could be a null pointer // Check(effect_trigger); Check_Pointer(psfx_definition); #if DEBUG_LEVEL > 0 if(effect_DCS != NULL) Check_Pointer(effect_DCS); #endif Check(offset_point); if(!psfx_definition) { Fail("A pfx was not defined in the .ini file\n"); } // // Initialze the local variables // myTriggerState = my_trigger; myStateDial = effect_trigger; // myEffectDCS = effect_DCS; myEffectOffset = *offset_point; myPSFXInfo = *psfx_definition; // // Add us to the state's watcher socket // effect_trigger->AddVideoWatcher(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for DPLPSFXStateRenderable // DPLPSFXStateRenderable::~DPLPSFXStateRenderable() { //STUBBED: DPL RB 1/14/07 //// !!!!HACK Note that because the effect id changes every time we start one, //// the destructor will only stop the last PFX played. We should probably //// be keeping track of all the ID's we've sent down to make sure everything //// attached to the DCS gets properly killed. //Check(this); //dpl_Effect ( dpl_effect_type_particlestop, NULL, &myPSFXInfo ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLPSFXStateRenderable // Logical DPLPSFXStateRenderable::TestInstance() const { VideoRenderable::TestInstance(); #if DEBUG_LEVEL > 0 if(myEffectDCS != NULL) Check_Pointer(myEffectDCS); #endif Check(&myEffectOffset); Check(myStateDial); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute method for DPLPSFXStateRenderable. // Note that this will get called by the state dial, not by the renderer // void DPLPSFXStateRenderable::Execute() { Check(myStateDial); // // If the state dial is in the right state, trigger // if(myStateDial->GetState() == myTriggerState) { // we put our id into the lower 16 bits because (at least) the upper 8 bits are flags L4Application *l4_application = Cast_Object(L4Application*, application); Check(l4_application); //myPSFXInfo.identifier = // (myPSFXInfo.identifier & 0xffff0000) | // l4_application->GetVideoRenderer()->GetUniqueID(); //dpl_Effect ( dpl_effect_type_particlestart, myEffectDCS, &myPSFXInfo ); } // // Call the next lower execute method // VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for DPLMaterialRenderable // This renderable creates a DPL Material structure and encapsulates it so // it will be properly deleted when the object it's part of gets deleted. DPLMaterialRenderable::DPLMaterialRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable Scalar ambient_red, // Material's ambient component Scalar ambient_green, Scalar ambient_blue, Scalar emissive_red, // Material's emissive component Scalar emissive_green, Scalar emissive_blue, Scalar diffuse_red, // Material's diffuse component Scalar diffuse_green, Scalar diffuse_blue, Scalar specular_red, // Material's specular component Scalar specular_green, Scalar specular_blue, Scalar specular_shininess, Scalar opacity_red, // Material's opacity Scalar opacity_green, Scalar opacity_blue, dpl_TEXTURE *texture, // Material's texture pointer Scalar z_dither, // Material's Z dither value int fog_immune // Material's Fog Imunity value ): VideoRenderable(entity, execution_type) { //STUBBED: DPL RB 1/14/07 //// Check input pointers //#if DEBUG_LEVEL > 0 //if(texture) // Check_Pointer(texture); //#endif //// Create and initialize the DPL material //myMaterial = dpl_NewMaterial(); //Check_Pointer(myMaterial); //// //// Materials should be static most of the time, if they are dynamic it means someone //// inheriting from us is going to try and modify the material. So if we are dynamic //// we leave the rest of this stuff for that routine to do //// //if(execution_type == DPLMaterialRenderable::Static) //{ // dpl_SetMaterialAmbient (myMaterial, ambient_red, ambient_green, ambient_blue); // dpl_SetMaterialEmissive (myMaterial, emissive_red, emissive_green, emissive_blue); // dpl_SetMaterialDiffuse (myMaterial, diffuse_red, diffuse_green, diffuse_blue); // dpl_SetMaterialSpecular (myMaterial, specular_red, specular_green, specular_blue, specular_shininess); // dpl_SetMaterialOpacity (myMaterial, opacity_red, opacity_green, opacity_blue); // if(texture) // dpl_SetMaterialTexture(myMaterial, texture); // if(z_dither) // dpl_SetMaterialDitherZ(myMaterial, z_dither); // if(fog_immune) // dpl_SetMaterialFogImmunity(myMaterial,fog_immune); // dpl_FlushMaterial(myMaterial); //} } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for DPLMaterialRenderable DPLMaterialRenderable::~DPLMaterialRenderable() { //STUBBED: DPL RB 1/14/07 //// Check our structure before we do anything //Check(this); //dpl_DeleteMaterial(myMaterial); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLMaterialRenderable Logical DPLMaterialRenderable::TestInstance() const { // Call our parent's TestInstance first VideoRenderable::TestInstance(); Check_Pointer(myMaterial); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the DPLMaterialRenderable void DPLMaterialRenderable::Execute() { Check(this); // Call the next lower execute method VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for MorphMaterialRenderable // This renderable takes two material specifications and loads up a third // material with a morph between the first two. MorphMaterialRenderable::MorphMaterialRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable Scalar ambient_red_1, // Material's ambient component Scalar ambient_green_1, Scalar ambient_blue_1, Scalar emissive_red_1, // Material's emissive component Scalar emissive_green_1, Scalar emissive_blue_1, Scalar diffuse_red_1, // Material's diffuse component Scalar diffuse_green_1, Scalar diffuse_blue_1, Scalar specular_red_1, // Material's specular component Scalar specular_green_1, Scalar specular_blue_1, Scalar specular_shininess_1, Scalar opacity_red_1, // Material's opacity Scalar opacity_green_1, Scalar opacity_blue_1, dpl_TEXTURE *texture_1, // Material's texture pointer Scalar z_dither_1, // Material's Z dither value int fog_immune_1, // Material's Fog Imunity value Scalar ambient_red_2, // Material's ambient component Scalar ambient_green_2, Scalar ambient_blue_2, Scalar emissive_red_2, // Material's emissive component Scalar emissive_green_2, Scalar emissive_blue_2, Scalar diffuse_red_2, // Material's diffuse component Scalar diffuse_green_2, Scalar diffuse_blue_2, Scalar specular_red_2, // Material's specular component Scalar specular_green_2, Scalar specular_blue_2, Scalar specular_shininess_2, Scalar opacity_red_2, // Material's opacity Scalar opacity_green_2, Scalar opacity_blue_2, Scalar z_dither_2, // Material's Z dither value Scalar *morph_control ): DPLMaterialRenderable( entity, // Entity to attach the renderable to execution_type, ambient_red_1, ambient_green_1, ambient_blue_1, // Material's ambient component emissive_red_1, emissive_green_1, emissive_blue_1, // Material's emissive component diffuse_red_1, diffuse_green_1, diffuse_blue_1, // Material's diffuse component specular_red_1, specular_green_1, specular_blue_1, specular_shininess_1, // Material's specular component opacity_red_1, opacity_green_1, opacity_blue_1, // Material's opacity texture_1, // Material's texture pointer z_dither_1, // Material's Z dither value fog_immune_1) // Material's Fog Imunity value { //STUBBED: DPL RB 1/14/07 //Scalar // Weight1, // Weight2; //// //// Remember the parameters of the two materials we are morphing between //// //myAmbientRed1 = ambient_red_1; // Material's ambient component //myAmbientGreen1 = ambient_green_1; //myAmbientBlue1 = ambient_blue_1; //myEmissiveRed1 = emissive_red_1; // Material's emissive component //myEmissiveGreen1 = emissive_green_1; //myEmissiveBlue1 = emissive_blue_1; //myDiffuseRed1 = diffuse_red_1; // Material's diffuse component //myDiffuseGreen1 = diffuse_green_1; //myDiffuseBlue1 = diffuse_blue_1; //mySpecularRed1 = specular_red_1; // Material's specular component //mySpecularGreen1 = specular_green_1; //mySpecularBlue1 = specular_blue_1; //mySpecularShininess1 = specular_shininess_1; //myOpacityRed1 = opacity_red_1; // Material's opacity //myOpacityGreen1 = opacity_green_1; //myOpacityBlue1 = opacity_blue_1; //myTexture1 = texture_1; // Material's texture pointer //myZDither1 = z_dither_1; // Material's Z dither value //myFogImmune1 = fog_immune_1; // Material's Fog Imunity value //myAmbientRed2 = ambient_red_2; // Material's ambient component //myAmbientGreen2 = ambient_green_2; //myAmbientBlue2 = ambient_blue_2; //myEmissiveRed2 = emissive_red_2; // Material's emissive component //myEmissiveGreen2 = emissive_green_2; //myEmissiveBlue2 = emissive_blue_2; //myDiffuseRed2 = diffuse_red_2; // Material's diffuse component //myDiffuseGreen2 = diffuse_green_2; //myDiffuseBlue2 = diffuse_blue_2; //mySpecularRed2 = specular_red_2; // Material's specular component //mySpecularGreen2 = specular_green_2; //mySpecularBlue2 = specular_blue_2; //mySpecularShininess2 = specular_shininess_2; //myOpacityRed2 = opacity_red_2; // Material's opacity //myOpacityGreen2 = opacity_green_2; //myOpacityBlue2 = opacity_blue_2; //myZDither2 = z_dither_2; // Material's Z dither value //myMorphControl = morph_control; //oldMorphControl = *morph_control; //// //// Calculate the target material //// //Weight1 = 1.0 - oldMorphControl; //Weight2 = oldMorphControl; //myAmbientRed = (myAmbientRed1*Weight1) + (myAmbientRed2*Weight2); //myAmbientGreen = (myAmbientGreen1*Weight1) + (myAmbientGreen2*Weight2); //myAmbientBlue = (myAmbientBlue1*Weight1) + (myAmbientBlue2*Weight2); //myEmissiveRed = (myEmissiveRed1*Weight1) + (myEmissiveRed2*Weight2); //myEmissiveGreen = (myEmissiveGreen1*Weight1) + (myEmissiveGreen2*Weight2); //myEmissiveBlue = (myEmissiveBlue1*Weight1) + (myEmissiveBlue2*Weight2); //myDiffuseRed = (myDiffuseRed1*Weight1) + (myDiffuseRed2*Weight2); //myDiffuseGreen = (myDiffuseGreen1*Weight1) + (myDiffuseGreen2*Weight2); //myDiffuseBlue = (myDiffuseBlue1*Weight1) + (myDiffuseBlue2*Weight2); //mySpecularRed = (mySpecularRed1*Weight1) + (mySpecularRed2*Weight2); //mySpecularGreen = (mySpecularGreen1*Weight1) + (mySpecularGreen2*Weight2); //mySpecularBlue = (mySpecularBlue1*Weight1) + (mySpecularBlue2*Weight2); //mySpecularShininess = (mySpecularShininess1*Weight1) + (mySpecularShininess2*Weight2); //myOpacityRed = (myOpacityRed1*Weight1) + (myOpacityRed2*Weight2); //myOpacityGreen = (myOpacityGreen1*Weight1) + (myOpacityGreen2*Weight2); //myOpacityBlue = (myOpacityBlue1*Weight1) + (myOpacityBlue2*Weight2); //myZDither = (myZDither1*Weight1) + (myZDither2*Weight2); //// //// Initialize the target material //// //dpl_SetMaterialAmbient (myMaterial, myAmbientRed, myAmbientGreen, myAmbientBlue); //dpl_SetMaterialEmissive (myMaterial, myEmissiveRed, myEmissiveGreen, myEmissiveBlue); //dpl_SetMaterialDiffuse (myMaterial, myDiffuseRed, myDiffuseGreen, myDiffuseBlue); //dpl_SetMaterialSpecular (myMaterial, mySpecularRed, mySpecularGreen, mySpecularBlue, mySpecularShininess); //dpl_SetMaterialOpacity (myMaterial, myOpacityRed, myOpacityGreen, myOpacityBlue); //if(myTexture1) // dpl_SetMaterialTexture(myMaterial, myTexture1); //if(myZDither) // dpl_SetMaterialDitherZ(myMaterial,myZDither); //if(myFogImmune1) // dpl_SetMaterialFogImmunity(myMaterial,myFogImmune1); //dpl_FlushMaterial(myMaterial); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for MorphMaterialRenderable MorphMaterialRenderable::~MorphMaterialRenderable() { // Check our structure before we do anything Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the MorphMaterialRenderable Logical MorphMaterialRenderable::TestInstance() const { // Call our parent's TestInstance first VideoRenderable::TestInstance(); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the MorphMaterialRenderable void MorphMaterialRenderable::Execute() { //STUBBED: DPL RB 1/14/07 //Scalar // Weight1, // Weight2; //Check(this); //// See if the morph control variable has changed //if(oldMorphControl != *myMorphControl) //{ // // // // Re-calculate the target material // // // oldMorphControl = *myMorphControl; // Weight1 = 1.0 - oldMorphControl; // Weight2 = oldMorphControl; // myAmbientRed = (myAmbientRed1*Weight1) + (myAmbientRed2*Weight2); // myAmbientGreen = (myAmbientGreen1*Weight1) + (myAmbientGreen2*Weight2); // myAmbientBlue = (myAmbientBlue1*Weight1) + (myAmbientBlue2*Weight2); // myEmissiveRed = (myEmissiveRed1*Weight1) + (myEmissiveRed2*Weight2); // myEmissiveGreen = (myEmissiveGreen1*Weight1) + (myEmissiveGreen2*Weight2); // myEmissiveBlue = (myEmissiveBlue1*Weight1) + (myEmissiveBlue2*Weight2); // myDiffuseRed = (myDiffuseRed1*Weight1) + (myDiffuseRed2*Weight2); // myDiffuseGreen = (myDiffuseGreen1*Weight1) + (myDiffuseGreen2*Weight2); // myDiffuseBlue = (myDiffuseBlue1*Weight1) + (myDiffuseBlue2*Weight2); // mySpecularRed = (mySpecularRed1*Weight1) + (mySpecularRed2*Weight2); // mySpecularGreen = (mySpecularGreen1*Weight1) + (mySpecularGreen2*Weight2); // mySpecularBlue = (mySpecularBlue1*Weight1) + (mySpecularBlue2*Weight2); // mySpecularShininess = (mySpecularShininess1*Weight1) + (mySpecularShininess2*Weight2); // myOpacityRed = (myOpacityRed1*Weight1) + (myOpacityRed2*Weight2); // myOpacityGreen = (myOpacityGreen1*Weight1) + (myOpacityGreen2*Weight2); // myOpacityBlue = (myOpacityBlue1*Weight1) + (myOpacityBlue2*Weight2); // myZDither = (myZDither1*Weight1) + (myZDither2*Weight2); // // // // Reset the target material and std::flush it // // Note we don't try to morph texture or fog immune // // // dpl_SetMaterialAmbient (myMaterial, myAmbientRed, myAmbientGreen, myAmbientBlue); // dpl_SetMaterialEmissive (myMaterial, myEmissiveRed, myEmissiveGreen, myEmissiveBlue); // dpl_SetMaterialDiffuse (myMaterial, myDiffuseRed, myDiffuseGreen, myDiffuseBlue); // dpl_SetMaterialSpecular (myMaterial, mySpecularRed, mySpecularGreen, mySpecularBlue, mySpecularShininess); // dpl_SetMaterialOpacity (myMaterial, myOpacityRed, myOpacityGreen, myOpacityBlue); // if(myZDither) // dpl_SetMaterialDitherZ(myMaterial,myZDither); // dpl_FlushMaterial(myMaterial); //} //// Call the next lower execute method VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for DPLDamageMaterialRenderable // This renderable handles modifying a material in response to damage. We // get the pointer to an existing DPL material on startup and we get out // color and texture settings from that DPLDamageMaterialRenderable::DPLDamageMaterialRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable dpl_MATERIAL *damage_material, // The material we want to control Scalar *damage_attribute, // The attribute containing the current damage level Scalar damage_percent // Degradation factor to make damaged material ): VideoRenderable(entity, execution_type) { //STUBBED: DPL RB 1/14/07 // Scalar // Weight1, // Weight2; // // Check_Pointer(damage_material); // Check_Pointer(damage_attribute); // Verify(damage_percent >= 0.0f && damage_percent <= 1.0f); // // // // Grab the material's components, remember them and figure the target colors // // // myMaterial = damage_material; // myDamageAttribute = damage_attribute; // oldDamageAttribute = *myDamageAttribute; // dpl_GetMaterialAmbient (myMaterial, &myAmbientRed1, &myAmbientGreen1, &myAmbientBlue1); // dpl_GetMaterialEmissive (myMaterial, &myEmissiveRed1, &myEmissiveGreen1, &myEmissiveBlue1); // dpl_GetMaterialDiffuse (myMaterial, &myDiffuseRed1, &myDiffuseGreen1, &myDiffuseBlue1); // dpl_GetMaterialSpecular (myMaterial, &mySpecularRed1, &mySpecularGreen1, &mySpecularBlue1, &mySpecularShininess1); // dpl_GetMaterialOpacity (myMaterial, &myOpacityRed1, &myOpacityGreen1, &myOpacityBlue1); // myAmbientRed2 = damage_percent * myAmbientRed1; // Material's ambient component // myAmbientGreen2 = damage_percent * myAmbientGreen1; // myAmbientBlue2 = damage_percent * myAmbientBlue1; // myEmissiveRed2 = damage_percent * myEmissiveRed1; // Material's emissive component // myEmissiveGreen2 = damage_percent * myEmissiveGreen1; // myEmissiveBlue2 = damage_percent * myEmissiveBlue1; // myDiffuseRed2 = damage_percent * myDiffuseRed1; // Material's diffuse component // myDiffuseGreen2 = damage_percent * myDiffuseGreen1; // myDiffuseBlue2 = damage_percent * myDiffuseBlue1; // mySpecularRed2 = damage_percent * mySpecularRed1; // Material's specular component // mySpecularGreen2 = damage_percent * mySpecularGreen1; // mySpecularBlue2 = damage_percent * mySpecularBlue1; // mySpecularShininess2 = damage_percent * mySpecularShininess1; // myOpacityRed2 = damage_percent * myOpacityRed1; // Material's opacity // myOpacityGreen2 = damage_percent * myOpacityGreen1; // myOpacityBlue2 = damage_percent * myOpacityBlue1; // // // // Calculate the target material using the current level of damage // // // Weight1 = 1.0f - oldDamageAttribute; // Weight2 = oldDamageAttribute; // myAmbientRed = (myAmbientRed1*Weight1) + (myAmbientRed2*Weight2); // myAmbientGreen = (myAmbientGreen1*Weight1) + (myAmbientGreen2*Weight2); // myAmbientBlue = (myAmbientBlue1*Weight1) + (myAmbientBlue2*Weight2); // myEmissiveRed = (myEmissiveRed1*Weight1) + (myEmissiveRed2*Weight2); // myEmissiveGreen = (myEmissiveGreen1*Weight1) + (myEmissiveGreen2*Weight2); // myEmissiveBlue = (myEmissiveBlue1*Weight1) + (myEmissiveBlue2*Weight2); // myDiffuseRed = (myDiffuseRed1*Weight1) + (myDiffuseRed2*Weight2); // myDiffuseGreen = (myDiffuseGreen1*Weight1) + (myDiffuseGreen2*Weight2); // myDiffuseBlue = (myDiffuseBlue1*Weight1) + (myDiffuseBlue2*Weight2); // mySpecularRed = (mySpecularRed1*Weight1) + (mySpecularRed2*Weight2); // mySpecularGreen = (mySpecularGreen1*Weight1) + (mySpecularGreen2*Weight2); // mySpecularBlue = (mySpecularBlue1*Weight1) + (mySpecularBlue2*Weight2); // mySpecularShininess = (mySpecularShininess1*Weight1)+ (mySpecularShininess2*Weight2); // myOpacityRed = (myOpacityRed1*Weight1) + (myOpacityRed2*Weight2); // myOpacityGreen = (myOpacityGreen1*Weight1) + (myOpacityGreen2*Weight2); // myOpacityBlue = (myOpacityBlue1*Weight1) + (myOpacityBlue2*Weight2); // // // // Set the target material // // // dpl_SetMaterialAmbient (myMaterial, myAmbientRed, myAmbientGreen, myAmbientBlue); // dpl_SetMaterialEmissive (myMaterial, myEmissiveRed, myEmissiveGreen, myEmissiveBlue); // dpl_SetMaterialDiffuse (myMaterial, myDiffuseRed, myDiffuseGreen, myDiffuseBlue); // dpl_SetMaterialSpecular (myMaterial, mySpecularRed, mySpecularGreen, mySpecularBlue, mySpecularShininess); //// dpl_SetMaterialOpacity (myMaterial, myOpacityRed, myOpacityGreen, myOpacityBlue); // dpl_FlushMaterial(myMaterial); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for DPLDamageMaterialRenderable DPLDamageMaterialRenderable::~DPLDamageMaterialRenderable() { // Check our structure before we do anything Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLDamageMaterialRenderable Logical DPLDamageMaterialRenderable::TestInstance() const { // Call our parent's TestInstance first VideoRenderable::TestInstance(); Check_Pointer(myMaterial); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the DPLDamageMaterialRenderable void DPLDamageMaterialRenderable::Execute() { //STUBBED: DPL RB 1/14/07 // Scalar // Weight1, // Weight2; // // Check(this); // if(oldDamageAttribute != *myDamageAttribute) // { // // // // Re-calculate the target material // // // oldDamageAttribute = *myDamageAttribute; // Weight1 = 1.0 - oldDamageAttribute; // Weight2 = oldDamageAttribute; // myAmbientRed = (myAmbientRed1*Weight1) + (myAmbientRed2*Weight2); // myAmbientGreen = (myAmbientGreen1*Weight1) + (myAmbientGreen2*Weight2); // myAmbientBlue = (myAmbientBlue1*Weight1) + (myAmbientBlue2*Weight2); // myEmissiveRed = (myEmissiveRed1*Weight1) + (myEmissiveRed2*Weight2); // myEmissiveGreen = (myEmissiveGreen1*Weight1) + (myEmissiveGreen2*Weight2); // myEmissiveBlue = (myEmissiveBlue1*Weight1) + (myEmissiveBlue2*Weight2); // myDiffuseRed = (myDiffuseRed1*Weight1) + (myDiffuseRed2*Weight2); // myDiffuseGreen = (myDiffuseGreen1*Weight1) + (myDiffuseGreen2*Weight2); // myDiffuseBlue = (myDiffuseBlue1*Weight1) + (myDiffuseBlue2*Weight2); // mySpecularRed = (mySpecularRed1*Weight1) + (mySpecularRed2*Weight2); // mySpecularGreen = (mySpecularGreen1*Weight1) + (mySpecularGreen2*Weight2); // mySpecularBlue = (mySpecularBlue1*Weight1) + (mySpecularBlue2*Weight2); // mySpecularShininess = (mySpecularShininess1*Weight1)+ (mySpecularShininess2*Weight2); // myOpacityRed = (myOpacityRed1*Weight1) + (myOpacityRed2*Weight2); // myOpacityGreen = (myOpacityGreen1*Weight1) + (myOpacityGreen2*Weight2); // myOpacityBlue = (myOpacityBlue1*Weight1) + (myOpacityBlue2*Weight2); // // // // Reset the target material and std::flush it // // // dpl_SetMaterialAmbient (myMaterial, myAmbientRed, myAmbientGreen, myAmbientBlue); // dpl_SetMaterialEmissive (myMaterial, myEmissiveRed, myEmissiveGreen, myEmissiveBlue); // dpl_SetMaterialDiffuse (myMaterial, myDiffuseRed, myDiffuseGreen, myDiffuseBlue); // dpl_SetMaterialSpecular (myMaterial, mySpecularRed, mySpecularGreen, mySpecularBlue, mySpecularShininess); //// dpl_SetMaterialOpacity (myMaterial, myOpacityRed, myOpacityGreen, myOpacityBlue); // dpl_FlushMaterial(myMaterial); // } // // Call the next lower execute method VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~End of the new renderable class hiearchy~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~Dynamic Renderables~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~these renderables allow things to change after construction~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // //############################################################################# // This is the DPLEyeRenderable class. This is a DYNAMIC renderable that // places the renderer's eyepoint relative to some other DCS/renderable. // At the moment the eyepoint won't actually move in response to an argument // but this will be changed after we have something to hook the eye to. //############################################################################# // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for the DPLEyeRenderable // All the arguments are required. // DPLEyeRenderable::DPLEyeRenderable( Entity* This_Entity, const LinearMatrix& Offset_Matrix, HierarchicalDrawComponent* parent, EulerAngles* eyepoint_rotation // Pointer to attribute that contains eye rotations ): HierarchicalDrawComponent(TrivialNodeClassID, parent) { //STUBBED: DPL RB 1/14/07 // // // // Check the inbound data // // Check(This_Entity); Check(&Offset_Matrix); Check_Pointer(Parent_DCS); #if DEBUG_LEVEL > 0 if(eyepoint_rotation) Check(eyepoint_rotation); #endif // // Remember the entity that this renderable is attached to and the // orientation matrix that sets the eye location // myEntity = This_Entity; // myParentDCS = Parent_DCS; myOrientationMatrix = Offset_Matrix; myEyepointRotation = eyepoint_rotation; if(myEyepointRotation) { oldEyepointRotation = *myEyepointRotation; } else { oldEyepointRotation = NULL; } // // Create the dpl DCS for this renderable, connect it to it's parent // and set it into the current zone. // // myDCS = dpl_NewDCS (); // Check_Pointer(myDCS); // dpl_AddDCSToDCS ( myParentDCS, myDCS ); // dpl_SetDCSZone ( myDCS, This_Zone ); // // Load up the DCS matrix with the supplied matrix // // float32* dplMatrix = dpl_GetDCSMatrix(myDCS); // Check_Pointer(dplMatrix); // *((Matrix4x4*)dplMatrix) = rotation_matrix; // // float32* tempMatrix = dpl_GetDCSMatrix(myDCS); // Check_Pointer(tempMatrix); // *(Matrix4x4*)tempMatrix = OrientationMatrix; // // Flush out the instance and DCS // // dpl_SetViewDCS ( This_View, myDCS); // dpl_FlushView ( This_View); // dpl_FlushDCS ( myDCS ); // myEntity->AddDynamicVideoComponent(this); // // HACK HACK this needs to be folded back into the new videorenderable hiearchy // // myEntity->AddStaticVideoComponent(this); L4Application *l4_application = Cast_Object(L4Application*, application); Check(l4_application); l4_application->GetVideoRenderer()->AddDynamicRenderable(this); //l4_application->GetVideoRenderer()->mDeathRenderables.Add(this); myDevice = l4_application->GetVideoRenderer()->GetDevice(); camMatrix = myOrientationMatrix; if (myEyepointRotation) { Matrix4x4 rotation; rotation = *myEyepointRotation; //camMatrix.entries[14] /= 1.1f; camMatrix *= rotation; } Matrix4x4 mat4; mat4 = camMatrix; Matrix4x4 prev; prev = *myRenderer->GetMatrixStack()->GetTop(); mat4 *= prev; LinearMatrix mat(True); mat = mat4; D3DXVECTOR3 pos(mat(3,0), mat(3, 1), mat(3,2)); mat(3,0) = 0; mat(3,1) = 0; mat(3,2) = 0; Matrix4x4 temp; temp = mat; D3DXMATRIX drot = temp.ToD3DMatrix(); D3DXVECTOR3 at(0,0,1); D3DXVECTOR3 up(0,1,0); at.x = drot._31 + drot._41; at.y = drot._32 + drot._42; at.z = drot._33 + drot._43; at += pos; up.x = drot._21 + drot._41; up.y = drot._22 + drot._42; up.z = drot._23 + drot._43; //D3DXVECTOR3 dir; //D3DXVec3Subtract(&dir,&at, &pos); //D3DXVec3Normalize(&dir, &dir); //D3DXVec3Scale(&dir, &dir, 50); //D3DXVec3Subtract(&pos, &pos, &dir); D3DXMATRIX view; D3DXMatrixLookAtRH(&view,&pos,&at,&up); //myDevice->SetTransform(D3DTS_VIEW, &view); oldLocalToWorld = myEntity->localToWorld; mForceUpdate = true; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for DPLEyeRenderable // After calling this the eyepoint must be relocated to another DCS before // the execute method of the renderer is called. // DPLEyeRenderable::~DPLEyeRenderable() { //STUBBED: DPL RB 1/14/07 // Check(this); //// Below is probably unnecessary as the parent should be destroyed too //// but Phil is making a patch to allow us to check that. //// dpl_RemoveDCSFromDCS(myParentDCS, myDCS); // dpl_DeleteDCS(myDCS); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLEyeRenderable // Logical DPLEyeRenderable::TestInstance() const { Component::TestInstance(); Check_Pointer(myDCS); Check_Pointer(myParentDCS); Check(&myOrientationMatrix); Check(myEntity); if(myEyepointRotation) { Check(myEyepointRotation); } return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute method for DPLEyeRenderable. // void DPLEyeRenderable::Execute() { //STUBBED: DPL RB 1/14/07 // //---------------------------------------------------------------------- // If we have an eyepoint rotation specified, generate a new matrix each // time based upon the setting of the eyepoint rotation //---------------------------------------------------------------------- // if((myEyepointRotation && *myEyepointRotation != oldEyepointRotation) || oldLocalToWorld != myEntity->localToWorld || mForceUpdate) { mForceUpdate = false; oldLocalToWorld = myEntity->localToWorld; if (myEyepointRotation) { oldEyepointRotation = *myEyepointRotation; camMatrix = *myEyepointRotation; } else camMatrix = Matrix4x4::Identity; camMatrix *= myOrientationMatrix; myRenderer->GetMatrixStack()->Push(); Matrix4x4 mat4; mat4 = camMatrix; Matrix4x4 prev; prev = *myRenderer->GetMatrixStack()->GetTop(); mat4 *= prev; LinearMatrix mat(True); mat = mat4; D3DXVECTOR3 pos(mat(3,0), mat(3, 1), mat(3,2)); mat(3,0) = 0; mat(3,1) = 0; mat(3,2) = 0; Matrix4x4 temp; temp = mat; D3DXMATRIX drot = temp.ToD3DMatrix(); D3DXVECTOR3 at(0,0,1); D3DXVECTOR3 up(0,1,0); at.x = drot._31 + drot._41; at.y = drot._32 + drot._42; at.z = drot._33 + drot._43; at += pos; up.x = drot._21 + drot._41; up.y = drot._22 + drot._42; up.z = drot._23 + drot._43; //D3DXVECTOR3 dir; //D3DXVec3Subtract(&dir,&at, &pos); //D3DXVec3Normalize(&dir, &dir); //D3DXVec3Scale(&dir, &dir, 10.0f); //D3DXVec3Add(&pos, &pos, &dir); //D3DXVec3Add(&pos, &pos, &(D3DXVECTOR3(0, 0.15f, 0))); //D3DXVec3Add(&at, &pos,&( D3DXVECTOR3(0, 0, 1))); D3DXMATRIX view; D3DXMatrixLookAtRH(&view,&pos,&at,&up); myDevice->SetTransform(D3DTS_VIEW, &view); myRenderer->GetMatrixStack()->Pop(); } myRenderer->GetMatrixStack()->Push(); myRenderer->GetMatrixStack()->MultMatrixLocal(&camMatrix.ToD3DMatrix()); HierarchicalDrawComponent::Execute(); myRenderer->GetMatrixStack()->Pop(); } // //############################################################################# // This is the DPLChildPointRenderable class. This is a dynamic renderable that // lets you build a translating joint between two objects. If you supply a // NULL Graphic_Object pointer when constructing the renderable it will be // built without hooking up an instance of a graphical object. //############################################################################# // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for the DPLChildPointRenderable // DPLChildPointRenderable::DPLChildPointRenderable( Entity* This_Entity, bool isDeathZone, d3d_OBJECT* Graphic_Object, dpl_ISECT_MODE Intersect_Mode, uint32 Intersect_Mask, const LinearMatrix &Offset_Matrix, HierarchicalDrawComponent *Parent, Point3D *my_point ): HierarchicalDrawComponent(TrivialNodeClassID, Parent) { isDeathDraw = isDeathZone; //STUBBED: DPL RB 1/14/07 // // Check the inbound data // Check(This_Entity); Check_Pointer(This_Zone); #if DEBUG_LEVEL > 0 if(Graphic_Object != NULL) Check_Pointer(Graphic_Object); #endif Check(&Offset_Matrix); //Check_Pointer(Parent_DCS); Check(my_point); // // Remember the entity that this renderable is attached to and the // orientation matrix that sets the eye location // myEntity = This_Entity; // myParentDCS = Parent_DCS; myPoint = my_point; OrientationMatrix = Offset_Matrix; OldPoint = *my_point; // // Create the dpl DCS, add it to the parent DCS, set it into the current zone, // and stuff the orientation matrix into it // // myOffsetDCS = dpl_NewDCS(); //Check_Pointer ( myOffsetDCS ); // dpl_AddDCSToDCS ( myParentDCS, myOffsetDCS ); // dpl_SetDCSZone ( myOffsetDCS, This_Zone ); // myDCS = dpl_NewDCS(); Check_Pointer ( myDCS ); // dpl_AddDCSToDCS ( myOffsetDCS, myDCS ); // dpl_SetDCSZone ( myDCS, This_Zone ); // // Setup the offset matrix in the offset DCS // // float32* tempMatrix = dpl_GetDCSMatrix( myOffsetDCS ); Check_Pointer ( tempMatrix ); // *(Matrix4x4*)tempMatrix = OrientationMatrix; // // Setup the initial state of the hinge joint // // float32* tempMatrix2 = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix2 ); // *(Matrix4x4*)tempMatrix2 = *myPoint; // // If there was a graphic, create an instance with that graphic in it and link // it to the DCS. // graphicalObject = Graphic_Object; Matrix4x4 temp,temp2; temp = OrientationMatrix; temp2 = *myPoint; temp *= temp2; HierarchicalDrawComponent::SetLocalToWorld(&temp.ToD3DMatrix()); //if(Graphic_Object == NULL) //{ // graphicalObject = myObject; //} //else //{ // myInstance = dpl_NewInstance(); //Check_Pointer ( myInstance ); // dpl_SetInstanceObject ( myInstance, Graphic_Object ); // dpl_SetInstanceIntersect ( myInstance, Intersect_Mode ); // dpl_SetInstanceSectMask ( myInstance, Intersect_Mask ); // dpl_SetInstanceVisibility ( myInstance, 1 ); // dpl_AddInstanceToDCS ( myDCS, myInstance ); // dpl_FlushInstance ( myInstance ); //} // // Flush out the DCS and add this to the static component list // // dpl_FlushDCS ( myOffsetDCS ); // dpl_FlushDCS ( myDCS ); // myEntity->AddDynamicVideoComponent(this); // // HACK HACK this needs to be folded back into the new videorenderable hiearchy myEntity->AddStaticVideoComponent(this); L4Application *l4_application = Cast_Object(L4Application*, application); Check(l4_application); //l4_application->GetVideoRenderer()->AddDynamicRenderable(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for the DPLChildPointRenderable // DPLChildPointRenderable::~DPLChildPointRenderable() { // Check(this); //// Below is probably unnecessary as the parent should be destroyed too //// but Phil is making a patch to allow us to check that. //// dpl_RemoveDCSFromDCS(myParentDCS, myDCS); // // dpl_DeleteDCS(myDCS); // dpl_DeleteDCS(myOffsetDCS); // if(myInstance != NULL) // { // dpl_DeleteInstance(myInstance); // } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the DPLChildPointRenderable // This method should really use a watcher to make sure the position of the // object has changed before updating the DCS matrix. // void DPLChildPointRenderable::Execute() { //STUBBED: DPL RB 1/14/07 // Check(this); //// //// Load up the DCS matrix with the localToWorld matrix from the entity //// then std::flush out the new DCS //// // if(OldPoint != *myPoint) // { // OldPoint = *myPoint; // float32* tempMatrix2 = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix2 ); // *(Matrix4x4*)tempMatrix2 = OldPoint; // HACK_DPL_FLUSH_DCS ( myDCS ); // } myRenderer->GetMatrixStack()->Push(); Matrix4x4 temp,temp2; temp = OrientationMatrix; temp2 = *myPoint; temp *= temp2; myRenderer->GetMatrixStack()->MultMatrixLocal(&temp.ToD3DMatrix()); //myLocalToWorld = *myRenderer->GetMatrixStack()->GetTop(); HierarchicalDrawComponent::SetLocalToWorld(myRenderer->GetMatrixStack()->GetTop()); HierarchicalDrawComponent::Execute(); myRenderer->GetMatrixStack()->Pop(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLChildPointRenderable // Logical DPLChildPointRenderable::TestInstance() const { Component::TestInstance(); Check_Pointer ( myDCS ); Check_Pointer ( myParentDCS ); Check_Pointer ( myOffsetDCS ); Check(myPoint); if(myInstance != NULL) { Check_Pointer(myInstance); } Check(&OrientationMatrix); Check(myEntity); return True; } // //############################################################################# // This is the DPLScaleRenderable class. This is a dynamic renderable that // lets you scale everything downstream of it in the hiearchy. It is also // setup to switch it's own instances on and off based on the value in visible. //############################################################################# // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for the DPLScaleRenderable // DPLScaleRenderable::DPLScaleRenderable( Entity* This_Entity, bool isDeathZone, d3d_OBJECT* Graphic_Object, dpl_ISECT_MODE Intersect_Mode, uint32 Intersect_Mask, const LinearMatrix &Offset_Matrix, HierarchicalDrawComponent *Parent, Vector3D *scale_vector, Logical *visible ): HierarchicalDrawComponent(TrivialNodeClassID, Parent) { isDeathDraw = isDeathZone; //STUBBED: DPL RB 1/14/07 //// //// Check the inbound data //// // Check(This_Entity); // Check_Pointer(This_Zone); // Check_Pointer(Graphic_Object); // Check(&Offset_Matrix); // Check_Pointer(Parent_DCS); // Check(scale_vector); // Check_Pointer(visible); //// //// Remember the entity that this renderable is attached to and the //// orientation matrix that offsets it to the correct position. //// myEntity = This_Entity; // myParentDCS = Parent_DCS; myScaleVector = scale_vector; myVisible = visible; OffsetMatrix = Offset_Matrix; OldScaleVector = *scale_vector; OldVisible = *visible; myObject = Graphic_Object; //// //// Create the dpl DCS, add it to the parent DCS, set it into the current zone, //// and stuff the orientation matrix into it //// // myDCS = dpl_NewDCS(); // Check_Pointer ( myDCS ); // dpl_AddDCSToDCS ( myParentDCS, myDCS ); // dpl_SetDCSZone ( myDCS, This_Zone ); // // Setup the dcs matrix to it's initial state // // float32* tempMatrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix ); AffineMatrix tempAffine(True); tempAffine *= OldScaleVector; tempAffine *= OffsetMatrix; transMatrix = tempAffine; // *(Matrix4x4*)tempMatrix = tempAffine; //// //// If there was a graphic, create an instance with that graphic in it and link //// it to the DCS. //// // myInstance = dpl_NewInstance(); // Check_Pointer ( myInstance ); // dpl_SetInstanceObject ( myInstance, Graphic_Object ); // dpl_SetInstanceIntersect ( myInstance, Intersect_Mode ); // dpl_SetInstanceSectMask ( myInstance, Intersect_Mask ); // dpl_SetInstanceVisibility ( myInstance, OldVisible ); // dpl_AddInstanceToDCS ( myDCS, myInstance ); // dpl_FlushInstance ( myInstance ); //// //// Flush out the DCS and add this to the static component list //// // dpl_FlushDCS ( myDCS ); //// myEntity->AddDynamicVideoComponent(this); //// //// HACK HACK this needs to be folded back into the new videorenderable hiearchy // myEntity->AddStaticVideoComponent(this); // L4Application *l4_application = Cast_Object(L4Application*, application); // Check(l4_application); // l4_application->GetVideoRenderer()->AddDynamicRenderable(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for the DPLScaleRenderable // DPLScaleRenderable::~DPLScaleRenderable() { //STUBBED: DPL RB 1/14/07 // Check(this); //// Below is probably unnecessary as the parent should be destroyed too //// but Phil is making a patch to allow us to check that. //// dpl_RemoveDCSFromDCS(myParentDCS, myDCS); // // dpl_DeleteDCS(myDCS); // dpl_DeleteInstance(myInstance); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the DPLScaleRenderable // This method should really use a watcher to make sure the position of the // object has changed before updating the DCS matrix. // void DPLScaleRenderable::Execute() { //STUBBED: DPL RB 1/14/07 // Check(this); // // Load up the DCS matrix with the localToWorld matrix from the entity // then std::flush out the new DCS // if(OldVisible != *myVisible) { OldVisible = *myVisible; // dpl_SetInstanceVisibility ( myInstance, OldVisible ); // dpl_FlushInstance ( myInstance ); } if(OldScaleVector != *myScaleVector) { OldScaleVector = *myScaleVector; // float32* tempMatrix2 = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix2 ); AffineMatrix tempAffine(True); tempAffine *= OldScaleVector; tempAffine *= OffsetMatrix; transMatrix = tempAffine; // *(Matrix4x4*)tempMatrix2 = tempAffine; // HACK_DPL_FLUSH_DCS ( myDCS ); } if (!(*myVisible)) { graphicalObject = NULL; } else { graphicalObject = myObject; myRenderer->GetMatrixStack()->Push(); myRenderer->GetMatrixStack()->MultMatrixLocal(&transMatrix.ToD3DMatrix()); //myLocalToWorld = *myRenderer->GetMatrixStack()->GetTop(); HierarchicalDrawComponent::SetLocalToWorld(myRenderer->GetMatrixStack()->GetTop()); HierarchicalDrawComponent::Execute(); myRenderer->GetMatrixStack()->Pop(); } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLChildRenderable // Logical DPLScaleRenderable::TestInstance() const { Component::TestInstance(); Check_Pointer ( myDCS ); Check_Pointer ( myParentDCS ); Check_Pointer(myInstance); Check(&OffsetMatrix); Check(myEntity); Check(myScaleVector); return True; } // //############################################################################# // This is the DPLScaleQuatRenderable class. This is a dynamic renderable that // lets you control joint position with a Quaternion, Scale with a vector and // switch the instance on and off with a logical. //############################################################################# // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for the DPLScaleQuatRenderable // DPLScaleQuatRenderable::DPLScaleQuatRenderable( Entity* This_Entity, bool isDeathZone, d3d_OBJECT* Graphic_Object, dpl_ISECT_MODE Intersect_Mode, uint32 Intersect_Mask, const LinearMatrix &Offset_Matrix, HierarchicalDrawComponent *Parent, Quaternion *rotation_quaternion, Vector3D *scale_vector, Logical *visible ): HierarchicalDrawComponent(TrivialNodeClassID, Parent) { isDeathDraw = isDeathZone; //STUBBED: DPL RB 1/14/07 Quaternion my_quat; //// //// Check the inbound data //// // Check(This_Entity); // Check_Pointer(This_Zone); // Check_Pointer(Graphic_Object); // Check(&Offset_Matrix); // Check_Pointer(Parent_DCS); // Check(rotation_quaternion); // Check(scale_vector); // Check_Pointer(visible); // // Remember the entity that this renderable is attached to and the // orientation matrix that offsets it to the correct position. // myEntity = This_Entity; // myParentDCS = Parent_DCS; myRotationQuaternion = rotation_quaternion; myScaleVector = scale_vector; myVisible = visible; OffsetMatrix = Offset_Matrix; OldRotationQuaternion = *rotation_quaternion; OldScaleVector = *scale_vector; OldVisible = *visible; myObject = Graphic_Object; //// //// Create the dpl DCS, add it to the parent DCS, set it into the current zone, //// and stuff the orientation matrix into it //// // myDCS = dpl_NewDCS(); // Check_Pointer ( myDCS ); // dpl_AddDCSToDCS ( myParentDCS, myDCS ); // dpl_SetDCSZone ( myDCS, This_Zone ); // // Setup the dcs matrix to it's initial state // // float32* tempMatrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix ); AffineMatrix tempAffine(True); // tempAffine.Multiply(OldRotationQuaternion,OffsetMatrix); tempAffine *= OldScaleVector; tempAffine *= OldRotationQuaternion; tempAffine *= OffsetMatrix; tempMatrix = tempAffine; // *(Matrix4x4*)tempMatrix = tempAffine; //// //// If there was a graphic, create an instance with that graphic in it and link //// it to the DCS. //// // myInstance = dpl_NewInstance(); // Check_Pointer ( myInstance ); // dpl_SetInstanceObject ( myInstance, Graphic_Object ); // dpl_SetInstanceIntersect ( myInstance, Intersect_Mode ); // dpl_SetInstanceSectMask ( myInstance, Intersect_Mask ); // dpl_SetInstanceVisibility ( myInstance, OldVisible ); // dpl_AddInstanceToDCS ( myDCS, myInstance ); // dpl_FlushInstance ( myInstance ); //// //// Flush out the DCS and add this to the static component list //// // dpl_FlushDCS ( myDCS ); //// myEntity->AddDynamicVideoComponent(this); //// //// HACK HACK this needs to be folded back into the new videorenderable hiearchy // myEntity->AddStaticVideoComponent(this); // L4Application *l4_application = Cast_Object(L4Application*, application); // Check(l4_application); // l4_application->GetVideoRenderer()->AddDynamicRenderable(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for the DPLScaleQuatRenderable // DPLScaleQuatRenderable::~DPLScaleQuatRenderable() { //STUBBED: DPL RB 1/14/07 // Check(this); //// Below is probably unnecessary as the parent should be destroyed too //// but Phil is making a patch to allow us to check that. //// dpl_RemoveDCSFromDCS(myParentDCS, myDCS); // // dpl_DeleteDCS(myDCS); // dpl_DeleteInstance(myInstance); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the DPLScaleQuatRenderable // This method should really use a watcher to make sure the position of the // object has changed before updating the DCS matrix. // void DPLScaleQuatRenderable::Execute() { //STUBBED: DPL RB 1/14/07 Check(this); // // Load up the DCS matrix with the localToWorld matrix from the entity // then std::flush out the new DCS // if(OldVisible != *myVisible) { OldVisible = *myVisible; // dpl_SetInstanceVisibility ( myInstance, OldVisible ); // dpl_FlushInstance ( myInstance ); } // // The memcmp below is sort of a HACK but all I really care about is if the // value in the quaternion has been changed since last time I saw it, this // seems to be the easiest way to find out as JM hasn't written an == operator // if((OldScaleVector != *myScaleVector) || (memcmp(&OldRotationQuaternion,myRotationQuaternion, sizeof(Quaternion)) != 0)) { OldScaleVector = *myScaleVector; OldRotationQuaternion = *myRotationQuaternion; // float32* tempMatrix2 = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix2 ); AffineMatrix tempAffine(True); // tempAffine.Multiply(OldRotationQuaternion,OffsetMatrix); tempAffine *= OldScaleVector; tempAffine *= OldRotationQuaternion; tempAffine *= OffsetMatrix; tempMatrix = tempAffine; // *(Matrix4x4*)tempMatrix2 = tempAffine; // HACK_DPL_FLUSH_DCS ( myDCS ); } if (!(*myVisible)) { graphicalObject = NULL; } else { graphicalObject = myObject; myRenderer->GetMatrixStack()->Push(); myRenderer->GetMatrixStack()->MultMatrixLocal(&tempMatrix.ToD3DMatrix()); //myLocalToWorld = *myRenderer->GetMatrixStack()->GetTop(); HierarchicalDrawComponent::SetLocalToWorld(myRenderer->GetMatrixStack()->GetTop()); HierarchicalDrawComponent::Execute(); myRenderer->GetMatrixStack()->Pop(); } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLScaleQuatRenderable // Logical DPLScaleQuatRenderable::TestInstance() const { Component::TestInstance(); Check_Pointer ( myDCS ); Check_Pointer ( myParentDCS ); Check_Pointer(myInstance); Check(&OffsetMatrix); Check(myEntity); Check(myRotationQuaternion); Check(myScaleVector); Check_Pointer(myVisible); return True; } // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~Static Renderables~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~these renderables remain constant after construction~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // // //############################################################################# // This is the DPLStaticChildRenderable class. This is a STATIC renderable that // lets you build a DCS that is a child of a pre-existing DCS. If you supply a // NULL Graphic_Object pointer when constructing the renderable it will be // built without hooking up an instance of a graphical object. //############################################################################# // //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for the DPLStaticChildRenderable // DPLStaticChildRenderable::DPLStaticChildRenderable( Entity* This_Entity, bool isDeathZone, d3d_OBJECT* Graphic_Object, dpl_ISECT_MODE Intersect_Mode, uint32 Intersect_Mask, const LinearMatrix& Offset_Matrix, HierarchicalDrawComponent* Parent ): HierarchicalDrawComponent(TrivialNodeClassID, Parent) { isDeathDraw = isDeathZone; //STUBBED: DPL RB 1/14/07 // // Check the inbound data // Check(This_Entity); Check_Pointer(This_Zone); Check(&Offset_Matrix); //Check_Pointer(Parent_DCS); // #if DEBUG_LEVEL > 0 if(Graphic_Object != NULL) Check_Pointer(Graphic_Object); // #endif // // Remember the entity that this renderable is attached to and the // orientation matrix that sets the eye location // myEntity = This_Entity; // myParentDCS = Parent_DCS; OrientationMatrix = Offset_Matrix; graphicalObject = Graphic_Object; // // Create the dpl DCS, add it to the parent DCS, set it into the current zone, // and stuff the orientation matrix into it // // myDCS = dpl_NewDCS(); // Check_Pointer(myDCS); // dpl_AddDCSToDCS( myParentDCS, myDCS); // dpl_SetDCSZone(myDCS, This_Zone); // float32* tempMatrix = dpl_GetDCSMatrix(myDCS); // Check_Pointer(tempMatrix); // *(Matrix4x4*)tempMatrix = OrientationMatrix; // // If there was a graphic, create an instance with that graphic in it and link // it to the DCS. // if(Graphic_Object == NULL) { //myInstance = NULL; } else { // myInstance = dpl_NewInstance(); // Check_Pointer(myInstance ); // dpl_SetInstanceObject(myInstance, Graphic_Object); // dpl_SetInstanceIntersect(myInstance, Intersect_Mode); // dpl_SetInstanceSectMask(myInstance, Intersect_Mask); // dpl_SetInstanceVisibility(myInstance, 1); // dpl_AddInstanceToDCS(myDCS, myInstance); // dpl_FlushInstance(myInstance); } // // Flush out the DCS and add this to the static component list // // dpl_FlushDCS(myDCS); //myEntity->AddStaticVideoComponent(this); //L4Application *l4_application = Cast_Object(L4Application*, application); //Check(l4_application); //l4_application->GetVideoRenderer()->mRenderables.Add(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for the DPLStaticChildRenderable // DPLStaticChildRenderable::~DPLStaticChildRenderable() { //STUBBED: DPL RB 1/14/07 // Check(this); //// Below is probably unnecessary as the parent should be destroyed too //// but Phil is making a patch to allow us to check that. //// dpl_RemoveDCSFromDCS(myParentDCS, myDCS); // // dpl_DeleteDCS(myDCS); // if(myInstance != NULL) // { // dpl_DeleteInstance(myInstance); // } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLStaticChildRenderable // Logical DPLStaticChildRenderable::TestInstance() const { Component::TestInstance(); Check_Pointer(myDCS); Check_Pointer(myParentDCS); if(myInstance != NULL) { Check_Pointer(myInstance); } Check(&OrientationMatrix); Check(myEntity); return True; } void DPLStaticChildRenderable::Execute() { myRenderer->GetMatrixStack()->Push(); myRenderer->GetMatrixStack()->MultMatrixLocal(&OrientationMatrix.ToD3DMatrix()); //myLocalToWorld = *myRenderer->GetMatrixStack()->GetTop(); HierarchicalDrawComponent::SetLocalToWorld(myRenderer->GetMatrixStack()->GetTop()); HierarchicalDrawComponent::Execute(); //std::vector::iterator iter = m_children.begin(); //while(iter != m_children.end()) //{ // (*iter)->Execute(); // iter++; //} myRenderer->GetMatrixStack()->Pop(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~Special Effects Renderables~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //############################################################################# // This is the DPLSFXRenderable class. This renderable is used to trigger a // special effect in the world. The effect can be relative to a DCS or can be // positioned in world coordinants by passing NULL as Parent_DCS. The trigger // is a specific attribute entering a specific state. The effect will be // generated repeatedly till the trigger changes state. // // This renderable is useful for triggering one-shot effects like puffs of smoke // from guns or for triggering effects that the renderer will automatically // repeat on it's own. //############################################################################# #define DPLSFXRenderable_MAX_RATE 28.0 // Repeat rate when speed = 1.0 //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for DPLSFXRenderable // DPLSFXRenderable::DPLSFXRenderable( Entity *This_Entity, // Entity to attach the effect to bool isDeathZone , //*This_Zone, // DPL zone everything will be in const Point3D &Offset_Point, // Point offset from the parent DCS HierarchicalDrawComponent *Parent, // Parent DCS (can be NULL for world) StateIndicator *Effect_Trigger, // Trigger effect when this state changes int Trigger_State, // Trigger effect when in this state int Effect_Type, // Type of effect to trigger Scalar Repeat_Speed // Effect repeat speed. ): HierarchicalDrawComponent(TrivialNodeClassID, Parent) { isDeathDraw = isDeathZone; // // Check the inbound data, note that the parent DCS could be a null pointer // Check(This_Entity); // Check_Pointer(This_Zone); Check(&Offset_Point); #if DEBUG_LEVEL > 0 if(Parent_DCS != NULL) Check_Pointer(Parent_DCS); #endif Check(Effect_Trigger); // // Remember the entity and DCS this renderable is attached to // myEntity = This_Entity; //myParentDCS = Parent_DCS; myOffsetPoint = Offset_Point; myEffectTrigger = Effect_Trigger; myEffectTriggerOld = myEffectTrigger->GetState(); myEffectTriggerState = Trigger_State; myEffectType = Effect_Type; mEmitter.SetEffect(myEffectType); myRepeatSpeed = 1.0/(Repeat_Speed * DPLSFXRenderable_MAX_RATE); myLastEffect = 0.0; // // Register this effect as a dynamic renderable of the entity // myEntity->AddDynamicVideoComponent(this); // // HACK HACK this needs to be folded back into the new videorenderable hiearchy myEntity->AddStaticVideoComponent(this); L4Application *l4_application = Cast_Object(L4Application*, application); Check(l4_application); l4_application->GetVideoRenderer()->AddDynamicRenderable(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for DPLSFXRenderable // DPLSFXRenderable::~DPLSFXRenderable() { Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLSFXRenderable // Logical DPLSFXRenderable::TestInstance() const { Component::TestInstance(); Check(myEntity); #if DEBUG_LEVEL > 0 if(myParentDCS != NULL) Check_Pointer(myParentDCS); #endif Check(&myOffsetPoint) Check_Pointer(myEffectTrigger); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute method for DPLSFXRenderable. // This watches the pre-assigned attribute pointer and triggers a special effect // whenever that attribute changes. // void DPLSFXRenderable::Execute() { Scalar current_time; Matrix4x4 mat; mat = myEntity->localToWorld; D3DXMATRIX transform = mat.ToD3DMatrix(); D3DXVECTOR4 v4; D3DXVECTOR3 v3(myOffsetPoint.x, myOffsetPoint.y, myOffsetPoint.z); D3DXVec3Transform(&v4, &v3, &transform); mEmitter.SetPosition(v4.x, v4.y, v4.z); mEmitter.Execute(); // // Is the attribute in the trigger state? // if(myEffectTrigger->GetState() == myEffectTriggerState) { // // The effect is on, see if this is an edge // if(myEffectTriggerOld != myEffectTrigger->GetState()) { // // An edge, reset the repeat timers so we will get an effect right now. // myLastEffect = 0.0; } // // Is it time for another effect yet? // current_time = Now(); if((myLastEffect + myRepeatSpeed) < current_time) { // // Trigger the effect // // dpl_EXPLOSION_EFFECT_INFO my_explosion; // my_explosion.type = myEffectType; // my_explosion.x = myOffsetPoint.x; // my_explosion.y = myOffsetPoint.y; // my_explosion.z = myOffsetPoint.z; // dpl_Effect ( dpl_effect_type_explosion, myParentDCS, &my_explosion ); mEmitter.Fire(); myLastEffect = current_time; } } myEffectTriggerOld = myEffectTrigger->GetState(); //HierarchicalDrawComponent::Execute(); } //############################################################################# // This is the DPLRepeatSFXRenderable class. This renderable is used to trigger // a special effect that repeats periodically with the repeat rate under program // control. The most common use will probably be generating smoke trails. If // the density argument is set to zero, no smoke will be generated. //############################################################################# #define DPLRepeatSFXRenderable_MAX_RATE 30.0 //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for DPLRepeatSFXRenderable // DPLRepeatSFXRenderable::DPLRepeatSFXRenderable( Entity *This_Entity, bool isDeathZone , //*This_Zone, const Point3D &Offset_Point, HierarchicalDrawComponent *Parent, // offset is relative to this int Effect_Type, // type code for the effect Scalar *Speed ): HierarchicalDrawComponent(TrivialNodeClassID, Parent) { isDeathDraw = isDeathZone; // // Check the inbound data // Check(This_Entity); // Check_Pointer(This_Zone); Check(&Offset_Point); #if DEBUG_LEVEL > 0 if(Parent_DCS != NULL) Check_Pointer(Parent_DCS); // it is allowed to be null #endif Check_Pointer(Speed); // // Remember the entity and DCS this renderable is attached to // myEntity = This_Entity; // myParentDCS = Parent_DCS; myParent = Parent; myOffsetPoint = Offset_Point; myEffectType = Effect_Type; mEmitter.SetEffect(myEffectType); mySpeed = Speed; myLastSmoke = 0.0; mOldLocalToWorld = This_Entity->localToWorld; mTransMatrix = This_Entity->localToWorld; // // Setup as a dynamic renderable // // myEntity->AddDynamicVideoComponent(this); // // HACK HACK this needs to be folded back into the new videorenderable hiearchy myEntity->AddStaticVideoComponent(this); L4Application *l4_application = Cast_Object(L4Application*, application); Check(l4_application); l4_application->GetVideoRenderer()->AddDynamicRenderable(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for DPLRepeatSFXRenderable // DPLRepeatSFXRenderable::~DPLRepeatSFXRenderable() { Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLRepeatSFXRenderable // Logical DPLRepeatSFXRenderable::TestInstance() const { Component::TestInstance(); Check(myEntity); #if DEBUG_LEVEL > 0 if(myParentDCS != NULL) Check_Pointer(myParentDCS); // it is allowed to be null #endif Check(&myOffsetPoint); Check_Pointer(mySpeed); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute method for DPLRepeatSFXRenderable. // This watches the pre-assigned attribute pointer and triggers a special effect // whenever that attribute changes. // void DPLRepeatSFXRenderable::Execute() { Scalar current_time = Now(); if(mOldLocalToWorld != myEntity->localToWorld) { mOldLocalToWorld = myEntity->localToWorld; mTransMatrix = mOldLocalToWorld; } Matrix4x4 mat; mat = myEntity->localToWorld; D3DXMATRIX transform = mat.ToD3DMatrix(); D3DXVECTOR4 v4; D3DXVECTOR3 v3(myOffsetPoint.x, myOffsetPoint.y, myOffsetPoint.z); D3DXVec3Transform(&v4, &v3, &transform); mEmitter.SetPosition(v4.x, v4.y, v4.z); mEmitter.Execute(); // If speed is zero, the effect is turned off so we do nothing if(*mySpeed == 0.0) { myLastSmoke = 0.0; return; } // Figure how often we should generate smoke, speed ranges from 0 to 1, with // 1 being the fastest if((myLastSmoke + (1.0 / ((*mySpeed) * mEmitter.GetMaxRepeat()))) < current_time) { //dpl_EXPLOSION_EFFECT_INFO my_explosion; myLastSmoke = current_time; //my_explosion.type = myEffectType; //my_explosion.x = myOffsetPoint.x; //my_explosion.y = myOffsetPoint.y; //my_explosion.z = myOffsetPoint.z; //dpl_Effect(dpl_effect_type_explosion, myParentDCS, &my_explosion); mEmitter.Fire(); } //HierarchicalDrawComponent::Execute(); } //############################################################################# // This is the DPLTranslocationRenderable class. This renderable handles the // entire process of doing a UFT translocation effect from the perspective of // people watching the player. This renderable is connected to the player object // and manages positioning itself in the world based on information from that // object. HACK HACK HACK (this will be obsolete when RP is fixed) //############################################################################# //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for DPLTranslocationRenderable // DPLTranslocationRenderable::DPLTranslocationRenderable( Entity *This_Entity, // Entity to attach the effect to bool isDeathZone, // DPL zone everything will be in StateIndicator *Effect_Trigger, // Trigger effects off of this state dial Point3D *Drop_Zone_Location, // Attribute that holds where the new drop will be unsigned Drop_Zone_State ): HierarchicalDrawComponent(TrivialNodeClassID) { isDeathDraw = isDeathZone; //STUBBED: DPL RB 1/14/07 //// //// Check the inbound data, note that the parent DCS could be a null pointer //// // Check(This_Entity); // Check_Pointer(This_Zone); // Check(Effect_Trigger); // Check(Drop_Zone_Location); //// //// Remember the entity and DCS this renderable is attached to //// // myEntity = This_Entity; // myZone = This_Zone; // myEffectTrigger = Effect_Trigger; // myEffectTriggerOld = myEffectTrigger->GetState(); // myDropZoneLocation = Drop_Zone_Location; // myDropZoneState = Drop_Zone_State; // myState = IdleState; //// //// Load up the object we're going to use for the translocation //// // dpl_OBJECT* myTranslocateSphere = dpl_LoadObject ( "tsphere", dpl_load_normal ); // Check_Pointer(myTranslocateSphere); //// //// Setup a DCS that we can put the effect on so it can be rotated, scaled and //// placed anywhere we want in the world. //// // myInstance = dpl_NewInstance(); // myDCS = dpl_NewDCS(); // Check_Pointer (myInstance); // Check_Pointer (myDCS); // dpl_AddDCSToScene (myDCS); // dpl_SetDCSZone (myDCS, myZone); // dpl_SetInstanceObject (myInstance, myTranslocateSphere); // dpl_SetInstanceIntersect (myInstance, dpl_isect_mode_obj); // dpl_SetInstanceSectMask (myInstance, NULL); // dpl_SetInstanceVisibility (myInstance, False); // dpl_AddInstanceToDCS (myDCS, myInstance); // dpl_FlushInstance (myInstance); // dpl_FlushDCS (myDCS); //// //// Register this effect as a dynamic renderable of the entity //// //// myEntity->AddDynamicVideoComponent(this); //// //// HACK HACK this needs to be folded back into the new videorenderable hiearchy // myEntity->AddStaticVideoComponent(this); // L4Application *l4_application = Cast_Object(L4Application*, application); // Check(l4_application); // l4_application->GetVideoRenderer()->AddDynamicRenderable(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for DPLTranslocationRenderable // DPLTranslocationRenderable::~DPLTranslocationRenderable() { Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the DPLTranslocationRenderable // Logical DPLTranslocationRenderable::TestInstance() const { Component::TestInstance(); Check(myEntity); Check(myEffectTrigger); Check_Pointer(myZone); Check(myDropZoneLocation); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute method for DPLTranslocationRenderable. // Note that the states listed here are temporary for testing and will be changed // to player based effects as things are finalized. // void DPLTranslocationRenderable::Execute() { //STUBBED: DPL RB 1/14/07 // Scalar // current_time, // scale_factor; // unsigned // current_trigger_state; // // // // Check data we're going to use and get our current state to a local variable // // // Check_Pointer(myEffectTrigger); // current_trigger_state = myEffectTrigger->GetState(); // // HACK, because this renderable doesn't know what renderer it's on yet. // {L4Application *l4_application = Cast_Object(L4Application*, application); // Check(l4_application); // current_time = l4_application->GetVideoRenderer()->GetCurrentFrameTime();} //// current_time = myRenderer->GetCurrentFrameTime(); // // // // Simple state engine to manage the death/translocation effect // // // switch(myState) // { // case IdleState: // { // // // // Watch for transition to the dropzone acquired state // // // if(current_trigger_state == myDropZoneState) // { // myState = InitialExpandState; // myEffectTimer = current_time; // scale_factor = current_time - myEffectTimer; // if(scale_factor < 0.05f) // scale_factor = 0.05f; // float32* tempMatrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix ); // AffineMatrix tempAffine(True); // tempAffine(0,0) = scale_factor; // tempAffine(1,1) = scale_factor; // tempAffine(2,2) = scale_factor; // tempAffine = *myDropZoneLocation; // *(Matrix4x4*)tempMatrix = tempAffine; // dpl_SetInstanceVisibility (myInstance, True); // dpl_FlushInstance (myInstance); // HACK_DPL_FLUSH_DCS (myDCS); // } // break; // } // case InitialExpandState: // { // scale_factor = current_time - myEffectTimer; // if(scale_factor < 0.05f) // scale_factor = 0.05f; // if(scale_factor >= 1.0) // { // scale_factor = 1.0; // myState = HoldAtSizeState; // } // // Below is a hack to build a scaling identity matrix // float32* tempMatrix2 = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix2 ); // AffineMatrix tempAffine(True); // tempAffine(0,0) = scale_factor; // tempAffine(1,1) = scale_factor; // tempAffine(2,2) = scale_factor; // tempAffine = *myDropZoneLocation; // *(Matrix4x4*)tempMatrix2 = tempAffine; // HACK_DPL_FLUSH_DCS (myDCS); // break; // } // case HoldAtSizeState: // { // if((current_time - myEffectTimer) >= 3.0) // { // myState = ColapseState; // myEffectTimer = current_time + 1.0; // } // break; // } // case ColapseState: // { // scale_factor = myEffectTimer - current_time; // if(scale_factor < 0.05f) // { // scale_factor = 0.05f; // dpl_SetInstanceVisibility (myInstance, False); // dpl_FlushInstance (myInstance); // myState = IdleState; // } // // Below is a hack to build a scaling identity matrix // float32* tempMatrix2 = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix2 ); // AffineMatrix tempAffine(True); // tempAffine(0,0) = scale_factor; // tempAffine(1,1) = scale_factor; // tempAffine(2,2) = scale_factor; // tempAffine = *myDropZoneLocation; // *(Matrix4x4*)tempMatrix2 = tempAffine; // HACK_DPL_FLUSH_DCS (myDCS); // break; // } // } HierarchicalDrawComponent::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // This is brand new stuff as of 5/12/96 //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for OnePSFXRenderable // This renderable triggers off a single PSFX effect and then hangs around and // kills the effect when the renderable goes away. This is useful for things // like missiles which you want to leave a smoke trail that stops if the object // is destroyed. You REALLY want to do this whenever you attach an effect to // a DCS since if the DCS goes away the DPL renderer will go wackey. // OnePSFXRenderable::OnePSFXRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable dpl_PARTICLESTART_EFFECT_INFO *psfx_definition, // name of file with the PFX description in it HierarchicalDrawComponent *parent, // DCS the effect is relative to (may be NULL) Point3D *offset_point // Offset (or world coordinants if DCS is NULL) ): VideoRenderable(entity, execution_type, parent) { // // Check the inbound data, note that the parent DCS could be a null pointer // #if DEBUG_LEVEL > 0 if(effect_DCS != NULL) Check_Pointer(effect_DCS); #endif Check(offset_point); if(!psfx_definition) { Fail("A pfx was not defined in the .ini file\n"); } // // Initialze the local variables // myPSFXInfo = *psfx_definition; // // Start the PFX immediately // // myPSFXInfo.identifier = (myPSFXInfo.identifier & 0xffff0000) | myRenderer->GetUniqueID(); // dpl_Effect ( dpl_effect_type_particlestart, effect_DCS, &myPSFXInfo ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for OnePSFXRenderable // OnePSFXRenderable::~OnePSFXRenderable() { //STUBBED: DPL RB 1/14/07 //// //// Since this renderable only sends one PSFX ID down, we only have to kill //// one PSFX, no need to track how many are spawned. //// //Check(this); //dpl_Effect ( dpl_effect_type_particlestop, NULL, &myPSFXInfo ); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the OnePSFXRenderable // Logical OnePSFXRenderable::TestInstance() const { VideoRenderable::TestInstance(); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute method for OnePSFXRenderable. // void OnePSFXRenderable::Execute() { // Call the next lower execute method VideoRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for TranslocationRenderable // This renderable does the UFT translocation effect from the perspective of // someone else watching the person translocating. We connect this to the // player object and uses information from that object to position itself. // TranslocationRenderable::TranslocationRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable bool isDeathZone, // DPL zone everything will be in StateIndicator *effect_trigger, // Trigger effects off of this state dial Point3D *drop_zone_location, // Attribute that holds where the new drop will be unsigned drop_zone_state // State that indicates drop zone is valid (starts effect) ): VideoRenderable(entity, execution_type) { isDeathDraw = isDeathZone; //STUBBED: DPL RB 1/14/07 //// //// Check the inbound data, note that the parent DCS could be a null pointer //// // Check_Pointer(this_zone); Check(effect_trigger); Check(drop_zone_location); //// //// Remember the entity and DCS this renderable is attached to //// // myZone = this_zone; myEffectTrigger = effect_trigger; myDropZoneLocation = drop_zone_location; myDropZoneState = drop_zone_state; myState = IdleState; L4Application *l4_application = Cast_Object(L4Application*, application); Check(l4_application); //// //// Load up the object we're going to use for the translocation //// // dpl_OBJECT* myTranslocateSphere = dpl_LoadObject ( "tsphere", dpl_load_normal ); myDevice = l4_application->GetVideoRenderer()->GetDevice(); myTranslocateSphere = d3d_OBJECT::LoadObject(myDevice, "tsphere.bgf"); // Check_Pointer(myTranslocateSphere); //// //// Setup a DCS that we can put the effect on so it can be rotated, scaled and //// placed anywhere we want in the world. //// // myInstance = dpl_NewInstance(); // myDCS = dpl_NewDCS(); // Check_Pointer (myInstance); // Check_Pointer (myDCS); // dpl_AddDCSToScene (myDCS); l4_application->GetVideoRenderer()->AddRenderable(this); // dpl_SetDCSZone (myDCS, myZone); // dpl_SetInstanceObject (myInstance, myTranslocateSphere); // dpl_SetInstanceIntersect (myInstance, dpl_isect_mode_obj); // dpl_SetInstanceSectMask (myInstance, NULL); // dpl_SetInstanceVisibility (myInstance, False); //TODO set visibility // dpl_AddInstanceToDCS (myDCS, myInstance); // dpl_FlushInstance (myInstance); // dpl_FlushDCS (myDCS); //// //// Plug us into the watcher hook of the effect trigger state dial //// myEffectTrigger->AddVideoWatcher(this); visible = false; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for TranslocationRenderable // TranslocationRenderable::~TranslocationRenderable() { Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the TranslocationRenderable // Logical TranslocationRenderable::TestInstance() const { Component::TestInstance(); Check(myEffectTrigger); Check_Pointer(myZone); Check(myDropZoneLocation); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute method for TranslocationRenderable. // Note that the states listed here are temporary for testing and will be changed // to player based effects as things are finalized. // void TranslocationRenderable::Execute() { //STUBBED: DPL RB 1/14/07 Scalar current_time, scale_factor; unsigned current_trigger_state; // // Check data we're going to use and get our current state to a local variable // Check(myEffectTrigger); current_trigger_state = myEffectTrigger->GetState(); current_time = myRenderer->GetCurrentFrameTime(); // // Simple state engine to manage the death/translocation effect // // std::cout<<"TranslocationRenderable::Execute\n"; switch(myState) { case IdleState: { // // Watch for transition to the dropzone acquired state // if(current_trigger_state == myDropZoneState) { myState = InitialExpandState; myEffectTimer = current_time; scale_factor = current_time - myEffectTimer; if(scale_factor < 0.05f) scale_factor = 0.05f; // float32* tempMatrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix ); AffineMatrix tempAffine(True); tempAffine(0,0) = scale_factor; tempAffine(1,1) = scale_factor; tempAffine(2,2) = scale_factor; tempAffine = *myDropZoneLocation; localToWorld = tempAffine; // *(Matrix4x4*)tempMatrix = tempAffine; // dpl_SetInstanceVisibility (myInstance, True); visible = true; // dpl_FlushInstance (myInstance); // DPL_FLUSH_DCS (myDCS); myRenderer->AddDynamicRenderable(this); // std::cout<<"TranslocationRenderable Going Dynamic\n"; } break; } case InitialExpandState: { scale_factor = current_time - myEffectTimer; if(scale_factor < 0.05f) scale_factor = 0.05f; if(scale_factor >= 1.0) { scale_factor = 1.0; myState = HoldAtSizeState; } // // Below is a hack to build a scaling identity matrix // float32* tempMatrix2 = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix2 ); AffineMatrix tempAffine(True); tempAffine(0,0) = scale_factor; tempAffine(1,1) = scale_factor; tempAffine(2,2) = scale_factor; tempAffine = *myDropZoneLocation; localToWorld = tempAffine; // *(Matrix4x4*)tempMatrix2 = tempAffine; // DPL_FLUSH_DCS (myDCS); break; } case HoldAtSizeState: { if((current_time - myEffectTimer) >= 3.0) { myState = ColapseState; myEffectTimer = current_time + 1.0; } break; } case ColapseState: { scale_factor = myEffectTimer - current_time; if(scale_factor < 0.05f) { scale_factor = 0.05f; visible = false; // dpl_SetInstanceVisibility (myInstance, False); // dpl_FlushInstance (myInstance); myState = IdleState; myRenderer->RemoveDynamicRenderable(this); //// std::cout<<"TranslocationRenderable Going Static\n"; } // Below is a hack to build a scaling identity matrix // float32* tempMatrix2 = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix2 ); AffineMatrix tempAffine(True); tempAffine(0,0) = scale_factor; tempAffine(1,1) = scale_factor; tempAffine(2,2) = scale_factor; tempAffine = *myDropZoneLocation; localToWorld = tempAffine; // *(Matrix4x4*)tempMatrix2 = tempAffine; // DPL_FLUSH_DCS (myDCS); break; } } if (!visible) { graphicalObject = NULL; } else { graphicalObject = myTranslocateSphere; myRenderer->GetMatrixStack()->Push(); D3DXMATRIX transform = localToWorld.ToD3DMatrix(); myRenderer->GetMatrixStack()->MultMatrixLocal(&transform); //myLocalToWorld = *myRenderer->GetMatrixStack()->GetTop(); HierarchicalDrawComponent::SetLocalToWorld(myRenderer->GetMatrixStack()->GetTop()); VideoRenderable::Execute(); myRenderer->GetMatrixStack()->Pop(); } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for SpinScaleQuatWatcherRenderable // SpinScaleQuatWatcherRenderable::SpinScaleQuatWatcherRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable d3d_OBJECT *graphical_object, // object to hang on the DCS, may be a list later bool isDeathZone, // DPL Zone this stuff will live in (for culling) dpl_ISECT_MODE intersect_mode, // type of intersections to do on this object uint32 intersect_mask, // intersection mask for the object HierarchicalDrawComponent *parent, // the parent DCS we will be offsetting from LinearMatrix *offset_matrix, // offset matrix to be applied prior to joint DCS StateIndicator *control, // the state dial that controls this renderable unsigned effect_trigger_state,// the state that turns on the renderable Quaternion *rotation_quaternion,// rotates the object Vector3D *scale_vector, // Scales the object Scalar z_spin_rate // spins the object about z (radians/frame) ): ChildOffsetRenderable( entity, // Entity to attach the renderable to execution_type, // How/when to execute the renderable graphical_object, // object to hang on the DCS, may be a list later isDeathZone, // DPL Zone this stuff will live in (for culling) intersect_mode, // type of intersections to do on this object intersect_mask, // intersection mask for the object parent, // the parent DCS we will be offsetting from offset_matrix) // offset matrix to be applied prior to joint DCS { //STUBBED: DPL RB 1/14/07 // // // // Check the inbound data // // // Check(control); // Check(rotation_quaternion); // Check(scale_vector); // // // // Remember the entity that this renderable is attached to and the // // orientation matrix that offsets it to the correct position. // // // myControl = control; // myTriggerState = effect_trigger_state; // myVisible = False; // myRotationQuaternion = rotation_quaternion; // myScaleVector = scale_vector; // myZSpinRate = z_spin_rate; // OldZSpin = 0; // // // // Setup the dcs matrix to it's initial state // // // float32* tempMatrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix ); // AffineMatrix tempAffine(True); // tempAffine *= (*myScaleVector); // tempAffine *= (*myRotationQuaternion); // *(Matrix4x4*)tempMatrix = tempAffine; // dpl_FlushDCS ( myDCS ); // // // // Set the instance visibility correctly // // // dpl_SetInstanceVisibility ( myInstance, myVisible ); // dpl_FlushInstance ( myInstance ); //// //// Plug us into the watcher hook of the effect trigger state dial //// // myControl->AddVideoWatcher(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for SpinScaleQuatWatcherRenderable // SpinScaleQuatWatcherRenderable::~SpinScaleQuatWatcherRenderable() { // // Check our structure before we do anything // Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the SpinScaleQuatWatcherRenderable // Logical SpinScaleQuatWatcherRenderable::TestInstance() const { // // Call our parent's TestInstance first // ChildOffsetRenderable::TestInstance(); Check(myControl); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the SpinScaleQuatWatcherRenderable // Nothing to execute here so we just pass it down to the next lower level. // void SpinScaleQuatWatcherRenderable::Execute() { //STUBBED: DPL RB 1/14/07 // // // // Check our variables // // // Check(this); // // // // Check data we're going to use and get our current state to a local variable // // //// std::cout<<"SpinScaleQuatWatcherRenderable::Execute "<GetState()<<"\n"; // if(myControl->GetState() == myTriggerState) // { // // // // We're in the trigger state, if we aren't already visible, make us // // visible and dynamic now. // // // if(!myVisible) // { // myVisible = True; // dpl_SetInstanceVisibility ( myInstance, True ); // dpl_FlushInstance ( myInstance ); // myRenderer->AddDynamicRenderable(this); //// std::cout<<"SpinScaleQuatWatcherRenderable Going Dynamic\n"; // } // // // // Now update the beam // // // OldZSpin += myZSpinRate; // if(OldZSpin > TWO_PI) // OldZSpin -= TWO_PI; // Hinge temp_hinge(Z_Axis, OldZSpin); // // float32* tempMatrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix ); // // AffineMatrix tempAffine(True); // Quaternion temp_quaternion; // temp_quaternion = temp_hinge; // tempAffine = temp_quaternion; // tempAffine *= (*myScaleVector); // tempAffine *= (*myRotationQuaternion); // *(Matrix4x4*)tempMatrix = tempAffine; // DPL_FLUSH_DCS ( myDCS ); // } // else // { // // // // We've left the trigger state, so if we're visible we make the beam // // invisible and go static. // // // if(myVisible) // { // myVisible = False; // dpl_SetInstanceVisibility ( myInstance, False ); // dpl_FlushInstance ( myInstance ); // myRenderer->RemoveDynamicRenderable(this); //// std::cout<<"SpinScaleQuatWatcherRenderable Going Static\n"; // } // } // // Call the execute method in our parent // ChildOffsetRenderable::Execute(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Constructor for ScaleQuatWatcherRenderable // ScaleQuatWatcherRenderable::ScaleQuatWatcherRenderable( Entity *entity, // Entity to attach the renderable to ExecutionType execution_type, // How/when to execute the renderable d3d_OBJECT *graphical_object, // object to hang on the DCS, may be a list later bool isDeathZone, // DPL Zone this stuff will live in (for culling) dpl_ISECT_MODE intersect_mode, // type of intersections to do on this object uint32 intersect_mask, // intersection mask for the object HierarchicalDrawComponent *parent, // the parent DCS we will be offsetting from LinearMatrix *offset_matrix, // offset matrix to be applied prior to joint DCS StateIndicator *control, // the state dial that controls this renderable unsigned effect_trigger_state,// the state that turns on the renderable Quaternion *rotation_quaternion,// rotates the object Vector3D *scale_vector // Scales the object ): ChildOffsetRenderable( entity, // Entity to attach the renderable to execution_type, // How/when to execute the renderable graphical_object, // object to hang on the DCS, may be a list later isDeathZone, // DPL Zone this stuff will live in (for culling) intersect_mode, // type of intersections to do on this object intersect_mask, // intersection mask for the object parent, // the parent DCS we will be offsetting from offset_matrix) // offset matrix to be applied prior to joint DCS { //STUBBED: DPL RB 1/14/07 // // // // Check the inbound data // // // Check(control); // Check(rotation_quaternion); // Check(scale_vector); // // // // Remember the entity that this renderable is attached to and the // // orientation matrix that offsets it to the correct position. // // // myControl = control; // myTriggerState = effect_trigger_state; // myVisible = False; // myRotationQuaternion = rotation_quaternion; // myScaleVector = scale_vector; // // // // Setup the dcs matrix to it's initial state // // // float32* tempMatrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix ); // AffineMatrix tempAffine(True); // tempAffine *= (*myScaleVector); // tempAffine *= (*myRotationQuaternion); // *(Matrix4x4*)tempMatrix = tempAffine; // dpl_FlushDCS ( myDCS ); // // // // Set the instance visibility correctly // // // dpl_SetInstanceVisibility ( myInstance, myVisible ); // dpl_FlushInstance ( myInstance ); //// //// Plug us into the watcher hook of the effect trigger state dial //// // myControl->AddVideoWatcher(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Destructor for ScaleQuatWatcherRenderable // ScaleQuatWatcherRenderable::~ScaleQuatWatcherRenderable() { // // Check our structure before we do anything // Check(this); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // TestInstance for the ScaleQuatWatcherRenderable // Logical ScaleQuatWatcherRenderable::TestInstance() const { // // Call our parent's TestInstance first // ChildOffsetRenderable::TestInstance(); Check(myControl); return True; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Execute for the ScaleQuatWatcherRenderable // Nothing to execute here so we just pass it down to the next lower level. // void ScaleQuatWatcherRenderable::Execute() { //STUBBED: DPL RB 1/14/07 // // // // Check our variables // // // Check(this); // // // // Check data we're going to use and get our current state to a local variable // // // //std::cout<<"ScaleQuatWatcherRenderable::Execute "<GetState()<<"\n"; // if(myControl->GetState() == myTriggerState) // { // // // // We're in the trigger state, if we aren't already visible, make us // // visible and dynamic now. // // // if(!myVisible) // { // myVisible = True; // dpl_SetInstanceVisibility ( myInstance, True ); // dpl_FlushInstance ( myInstance ); // myRenderer->AddDynamicRenderable(this); //// std::cout<<"ScaleQuatWatcherRenderable Going Dynamic\n"; // } // // // // Now update the beam // // // float32* tempMatrix = dpl_GetDCSMatrix( myDCS ); // Check_Pointer ( tempMatrix ); // AffineMatrix tempAffine(True); // tempAffine *= (*myScaleVector); // tempAffine *= (*myRotationQuaternion); // *(Matrix4x4*)tempMatrix = tempAffine; // DPL_FLUSH_DCS ( myDCS ); // } // else // { // // // // We've left the trigger state, so if we're visible we make the beam // // invisible and go static. // // // if(myVisible) // { // myVisible = False; // dpl_SetInstanceVisibility ( myInstance, False ); // dpl_FlushInstance ( myInstance ); // myRenderer->RemoveDynamicRenderable(this); //// std::cout<<"ScaleQuatWatcherRenderable Going Static\n"; // } // } //// if(*myTest != myVisible) //// { //// std::cout<<"myTest="<<*myTest<<" myVisible="<