⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 waterblock.cc

📁 五行MMORPG引擎系统V1.0
💻 CC
📖 第 1 页 / 共 3 页
字号:
    }

    if( !Parent::onAdd() )
        return false;

    if( isClientObject() )
    {
      // load textures
      bool success = true;

      mSurfaceTexture      = TextureHandle( mSurfaceName,     MeshTexture );
      mSpecMaskTex         = TextureHandle( mSpecMaskName,    MeshTexture );
      mEnvMapOverTexture   = TextureHandle( mEnvMapOverName,  MeshTexture );
      mEnvMapUnderTexture  = TextureHandle( mEnvMapUnderName, MeshTexture );
      mShoreTexture        = TextureHandle( mShoreName,       MeshTexture );

      for( int i=0; i<WC_NUM_SUBMERGE_TEX; i++ )
      {
         if( mSubmergeName[i] && mSubmergeName[i][0] )
         {
            mLocalSubmergeTexture[i] = TextureHandle( mSubmergeName[i], MeshTexture );
            mSubmergeTexture[i] = mLocalSubmergeTexture[i];
            if(!mLocalSubmergeTexture[i])
               success = false;
         }
      }

      if(!success && !bool(mServerObject))
         return false;

      mDepthBitmap = new GBitmap(eDepthMapResolution, eDepthMapResolution, false, GBitmap::RGBA);
      if(!mDepthBitmap)
         return false;

      mDepthTexture = TextureHandle(NULL, mDepthBitmap, false);

      mShoreDepthBitmap = new GBitmap(eDepthMapResolution, eDepthMapResolution, false, GBitmap::RGBA);
      if(!mShoreDepthBitmap)
         return false;

      mShoreDepthTexture = TextureHandle(NULL, mShoreDepthBitmap, false);

      mFluid.SetTextures( mSurfaceTexture,
                           mEnvMapOverTexture,
                           mEnvMapUnderTexture,
                           mShoreTexture,
                           mDepthTexture,
                           mShoreDepthTexture,
                           mSpecMaskTex);
    }

    resetWorldBox();
    if(!mRemoveWetEdges)
    {
       setGlobalBounds();
    }
    addToScene();

    return( true );
}

//==============================================================================

void WaterBlock::onRemove()
{
   // clear static texture handles
   for( int i=0; i<WC_NUM_SUBMERGE_TEX; i++ )
      mSubmergeTexture[i] = NULL;

   removeFromScene();
   Parent::onRemove();
}

//==============================================================================

bool WaterBlock::onSceneAdd( SceneGraph* pGraph )
{
   if( Parent::onSceneAdd(pGraph) )
   {
      // Attempt to get the terrain.
      if( (mpTerrain == NULL) && (mContainer != NULL) )
      {
         mContainer->findObjects( mWorldBox, (U32)TerrainObjectType, SnagTerrain, this );
         if( mpTerrain )
         {
            mFluid.SetTerrainData( mpTerrain->heightMap );

            if (isClientObject())
               CalculateDepthMaps();
         }
      }

      return( true );
   }
   return( false );
}

//==============================================================================
// The incoming matrix transforms the water into the WORLD.  This includes any
// offset in the terrain, so the translation can be negative.  We need to get
// the translation to be expressed in "terrain square" terms.  The terrain
// offset is always -1024,-1024.

void WaterBlock::setTransform( const MatrixF &mat )
{
   mObjToWorld = mat;
   UpdateFluidRegion();
}

//==============================================================================

void WaterBlock::setScale( const VectorF & scale )
{
   mObjScale = scale;
   UpdateFluidRegion();
}

//==============================================================================

bool WaterBlock::prepRenderImage( SceneState* state,
                                 const U32   stateKey,
                                 const U32,
                                 const bool )
{
   // Attempt to get the terrain.
   if( (mpTerrain == NULL) && (mContainer != NULL) )
   {
      mContainer->findObjects( mWorldBox, (U32)TerrainObjectType, SnagTerrain, this );
      if( mpTerrain )
      {
         mFluid.SetTerrainData( mpTerrain->heightMap );

         // MM: Calculate Depth Maps.
         if (isClientObject()) 
            CalculateDepthMaps();
      }
   }

   if (isLastState(state, stateKey))
      return false;
   setLastState(state, stateKey);

   // This should be sufficient for most objects that don't manage zones, and
   //  don't need to return a specialized RenderImage...
   if (state->isObjectRendered(this))
   {
      SceneRenderImage* image = new SceneRenderImage;
      image->obj = this;
      image->isTranslucent = true;

      image->sortType = SceneRenderImage::Plane;
      image->plane    = PlaneF(0, 0, 1, -mSurfaceZ);
      image->poly[0]  = Point3F(mObjBox.min.x, mObjBox.min.y, 1);
      image->poly[1]  = Point3F(mObjBox.min.x, mObjBox.max.y, 1);
      image->poly[2]  = Point3F(mObjBox.max.x, mObjBox.max.y, 1);
      image->poly[3]  = Point3F(mObjBox.max.x, mObjBox.min.y, 1);

      for (U32 i = 0; i < 4; i++)
      {
         image->poly[i].convolve(mObjScale);
         getTransform().mulP(image->poly[i]);
      }

      // Calc the area of this poly
      Point3F intermed;
      mCross(image->poly[2] - image->poly[0], image->poly[3] - image->poly[1], &intermed);
      image->polyArea = intermed.len() * 0.5;

      state->insertRenderImage(image);
   }

   return false;
}

//==============================================================================

void WaterBlock::renderObject( SceneState* state, SceneRenderImage* )
{
   AssertFatal( dglIsInCanonicalState(),
      "Error, GL not in canonical state on entry" );

   RectI   viewport;
   Point3F Eye;    // Camera in water space.
   bool    CameraSubmergedFlag = false;

   dglGetViewport  ( &viewport );
   glMatrixMode    ( GL_PROJECTION );
   glPushMatrix    ();
   state->setupObjectProjection( this );

   /****
   // Debug assist.
   // Render a wire outline around the base of the water block.
   if( 0 )
   {
   glMatrixMode    ( GL_MODELVIEW );
   glPushMatrix    ();
   dglMultMatrix   ( &mObjToWorld );

   F32 X0 = 0;
   F32 Y0 = 0;
   F32 X1 = mObjScale.x;
   F32 Y1 = mObjScale.y;
   F32 Z  = 0;

   glDisable       ( GL_TEXTURE_2D );
   glDisable       ( GL_DEPTH_TEST );
   glEnable        ( GL_BLEND );
   glBlendFunc     ( GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA );
   glPolygonMode   ( GL_FRONT_AND_BACK, GL_LINE );
   glColor4f       ( 0.6f, 0.6f, 0.0f, 0.5f );
   glBegin         ( GL_QUADS );

   glVertex3f      ( X0, Y0, Z );
   glVertex3f      ( X1, Y0, Z );
   glVertex3f      ( X1, Y1, Z );
   glVertex3f      ( X0, Y1, Z );

   glEnd           ();
   glEnable        ( GL_DEPTH_TEST );
   glColor4f       ( 0.8f, 0.8f, 0.8f, 0.8f );
   glBegin         ( GL_QUADS );

   glVertex3f      ( X0, Y0, Z );
   glVertex3f      ( X1, Y0, Z );
   glVertex3f      ( X1, Y1, Z );
   glVertex3f      ( X0, Y1, Z );

   glEnd           ();
   glPolygonMode   ( GL_FRONT_AND_BACK, GL_FILL );

   glPopMatrix     ();
   glMatrixMode    ( GL_MODELVIEW );
   }
   ****/

   // Handle the fluid.
   {
      // The water block lives in terrain space which is -1024,-1024.
      // To get into world space, we just add 1024,1024.
      // The fluid lives in world space.

      Point3F W2Lv(  1024.0f,  1024.0f, 0.0f );   // World to Local vector
      Point3F L2Wv( -1024.0f, -1024.0f, 0.0f );   // Local to World vector
      MatrixF L2Wm;                               // Local to World matrix

      L2Wm.identity();
      L2Wm.setPosition( L2Wv );

      glMatrixMode    ( GL_MODELVIEW );
      glPushMatrix    ();
      dglMultMatrix   ( &L2Wm );


      // We need the eye in water space.
      {
         Eye = state->getCameraPosition() + W2Lv;
         mFluid.SetEyePosition( Eye.x, Eye.y, Eye.z );
      }

      // We need the frustrum in water space.
      {
         MatrixF L2Cm;
         dglGetModelview( &L2Cm );
         L2Cm.inverse();

         Point3F Dummy;
         Dummy = L2Cm.getPosition();

         F64 frustumParam[6];
         dglGetFrustum(&frustumParam[0], &frustumParam[1],
            &frustumParam[2], &frustumParam[3],
            &frustumParam[4], &frustumParam[5]);

         sgComputeOSFrustumPlanes(frustumParam,
            L2Cm,
            Dummy,
            mClipPlane[1],
            mClipPlane[2],
            mClipPlane[3],
            mClipPlane[4],
            mClipPlane[5]);

         // near plane is needed as well...
         PlaneF p(0, 1, 0, -frustumParam[4]);
         mTransformPlane(L2Cm, Point3F(1,1,1), p, &mClipPlane[0]);
         mFluid.SetFrustrumPlanes( (F32*)mClipPlane );
      }

      // Fog stuff.
      {
         pSceneState = state;
         ColorF FogColor = state->getFogColor();
         mFluid.SetFogParameters( FogColor.red,
            FogColor.green,
            FogColor.blue,
            state->getVisibleDistance() );
      }

      // And RENDER!
      {
         mFluid.Render( CameraSubmergedFlag );
      }

      // Clean up.
      glPopMatrix     ();
      glMatrixMode    ( GL_MODELVIEW );
   }

   //
   // And now the closing ceremonies...
   //
   glMatrixMode    ( GL_PROJECTION );
   glPopMatrix     ();
   glTexEnvi       ( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE );
   dglSetViewport  ( viewport );

   //
   // Oh yes.  We have to set some state information for the scene...
   //

   if( CameraSubmergedFlag )
   {
      mCameraSubmerged = true;
      mSubmergedType   = mLiquidType;
   }

   AssertFatal( dglIsInCanonicalState(),
      "Error, GL not in canonical state on exit" );
}

//==============================================================================

void WaterBlock::inspectPostApply()
{
   // MM: Flag Editor Applied.
   mEditorApplied = true;

   resetWorldBox();
   setMaskBits(1);
}

//==============================================================================

static EnumTable::Enums gLiquidTypeEnums[] =
{
   { WaterBlock::eWater,         "Water"         },
   { WaterBlock::eOceanWater,    "OceanWater"    },

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -