Ejemplo n.º 1
0
void FStaticMesh::AddToDrawLists(FScene* Scene)
{
	if (GRHIFeatureLevel >= ERHIFeatureLevel::SM3)
	{
		if (CastShadow)
		{
			FShadowDepthDrawingPolicyFactory::AddStaticMesh(Scene,this);
		}

		if (!bShadowOnly && PrimitiveSceneInfo->Proxy->ShouldRenderInMainPass())
		{
			// not all platforms need this
			const bool bRequiresHitProxies = Scene->RequiresHitProxies();
			if ( bRequiresHitProxies && PrimitiveSceneInfo->Proxy->IsSelectable() )
			{
				// Add the static mesh to the DPG's hit proxy draw list.
				FHitProxyDrawingPolicyFactory::AddStaticMesh(Scene,this);
			}

			if(!IsTranslucent())
			{
				extern TAutoConsoleVariable<int32> CVarEarlyZPass;
				int32 EarlyZPass = CVarEarlyZPass.GetValueOnRenderThread();

				extern int32 GEarlyZPassMovable;

				// Render non-masked materials in the depth only pass
				if (PrimitiveSceneInfo->Proxy->ShouldUseAsOccluder() 
					&& (!IsMasked() || EarlyZPass == 2)
					&& (!PrimitiveSceneInfo->Proxy->IsMovable() || GEarlyZPassMovable))
				{
					FDepthDrawingPolicyFactory::AddStaticMesh(Scene,this);
				}

				// Add the static mesh to the DPG's base pass draw list.
				FBasePassOpaqueDrawingPolicyFactory::AddStaticMesh(Scene,this);

				FVelocityDrawingPolicyFactory::AddStaticMesh(Scene, this);
			}
		}
	}
	else
	{
		if (!bShadowOnly && !IsTranslucent())
		{
			// Add the static mesh to the DPG's base pass draw list.
			FBasePassForwardOpaqueDrawingPolicyFactory::AddStaticMesh(Scene,this);
		}
	}
}
void FStaticMesh::AddToDrawLists(FRHICommandListImmediate& RHICmdList, FScene* Scene)
{
	const auto FeatureLevel = Scene->GetFeatureLevel();

	if (CastShadow)
	{
		FShadowDepthDrawingPolicyFactory::AddStaticMesh(Scene, this);
	}

	if (!PrimitiveSceneInfo->Proxy->ShouldRenderInMainPass())
	{
		return;
	}

	if (bUseForMaterial && Scene->RequiresHitProxies() && PrimitiveSceneInfo->Proxy->IsSelectable())
	{
		// Add the static mesh to the DPG's hit proxy draw list.
		FHitProxyDrawingPolicyFactory::AddStaticMesh(Scene, this);
	}

	if (IsTranslucent(FeatureLevel))
	{
		return;
	}

	if (Scene->ShouldUseDeferredRenderer())
	{
		if (bUseAsOccluder)
		{
			// Render non-masked materials in the depth only pass
			extern TAutoConsoleVariable<int32> CVarEarlyZPass;
			int32 EarlyZPass = CVarEarlyZPass.GetValueOnRenderThread();

			extern int32 GEarlyZPassMovable;

			// WARNING : If you change this condition, also change the logic in FStaticMeshSceneProxy::DrawStaticElements.
			if (PrimitiveSceneInfo->Proxy->ShouldUseAsOccluder() 
				&& (!IsMasked(FeatureLevel) || EarlyZPass == 2)
				&& (!PrimitiveSceneInfo->Proxy->IsMovable() || GEarlyZPassMovable))
			{
				FDepthDrawingPolicyFactory::AddStaticMesh(Scene,this);
			}
		}

		if (bUseForMaterial)
		{
			// Add the static mesh to the DPG's base pass draw list.
			FBasePassOpaqueDrawingPolicyFactory::AddStaticMesh(RHICmdList, Scene, this);
			FVelocityDrawingPolicyFactory::AddStaticMesh(Scene, this);
		}
	}
	else
	{
		if (bUseForMaterial)
		{
			// Add the static mesh to the DPG's base pass draw list.
			FBasePassForwardOpaqueDrawingPolicyFactory::AddStaticMesh(RHICmdList, Scene, this);
		}
	}
}
Ejemplo n.º 3
0
void CWsWindow::SetVisibleRegion(const TRegion& aNewRegion, const TRegion* aTop, TRegion& aNewFadableRegion)
	{
	STACK_REGION difference;
	TBool diffs = EFalse;

	difference.Copy(iVisibleRegion);
	difference.SubRegion(aNewRegion);
	if (!difference.IsEmpty())
		{
		diffs = ETrue;
		if (IsTranslucent())
			{
			// Andy - If this is a client window (what else could it be) we can also subtract the
			// user defined opaque region before doing this:
			iScreen->AddRedrawRegion(difference, EFalse);
			}
		}

	difference.Copy(aNewRegion);
	if (HasBeenDrawnToScreen())
		{
		difference.SubRegion(iVisibleRegion);
		}
	if (!difference.IsEmpty())
		{
		diffs = ETrue;
		STACK_REGION topDiff;
		topDiff.Copy(difference);
		WS_ASSERT_DEBUG(aTop,EWsPanicRegion);
		topDiff.Intersect(*aTop);
		difference.SubRegion(topDiff);
		iScreen->AddRedrawRegion(topDiff, EFalse, ERedrawTopOnly);
		iScreen->AddRedrawRegion(difference, EFalse, ERedrawAll);
		topDiff.Close();
		}

	difference.Close();

	AbortDsaIfRequired(aNewRegion, aTop);

	if (diffs)
		{
		ResetVisibleRegion();
		iVisibleRegion.Copy(aNewRegion);
		PossibleVisibilityChangedEvent(EFalse);
		}

	iFadableRegion.Copy( aNewFadableRegion );
	
	// Just because the visible region (screen coordinates) didn't change doesn't
	// mean the invalid region (window coordinates) didn't change, so we always call this.
	iRedraw->VisibleRegionChange();
	}
Ejemplo n.º 4
0
void hsVertexShader::IShadeSpan( plGeometrySpan *span, INode* node )
{
    hsColorRGBA         preDiffuse, rtDiffuse, matAmbient;
    hsBitVector         dirtyVector;
    int                 i;
    bool                translucent, shadeIt, addingIt;
    plLayerInterface    *layer = nil;


    hsGuardBegin("hsVertexShader::ShadeSpan");
    
    const char* dbgNodeName = node->GetName(); 

    if( span->fNumVerts == 0 )
        return;

    fShadeColorTable = new hsColorRGBA[ span->fNumVerts ];  
    fIllumColorTable = new hsColorRGBA[ span->fNumVerts ];  
    
    translucent = IsTranslucent( span->fMaterial );

    /// Get material layer #0
    addingIt = false;
    shadeIt = !( span->fProps & plGeometrySpan::kPropNoPreShade );

    if( span->fMaterial->GetNumLayers() != 0 )
    {
        layer = span->fMaterial->GetLayer( 0 );
        if( layer->GetShadeFlags() & hsGMatState::kShadeNoShade )
            shadeIt = false;
        if( layer->GetBlendFlags() & hsGMatState::kBlendAdd )
            addingIt = true;
    }
    float opacity = 1.f;
    for( i = 0; i < span->fMaterial->GetNumLayers(); i++ )
    {
        plLayerInterface* lay = span->fMaterial->GetLayer(i);
        if( (lay->GetBlendFlags() & hsGMatState::kBlendAlpha)
            &&
            (
                !i  
                ||
                (lay->GetMiscFlags() & hsGMatState::kMiscRestartPassHere)
            )
          )
        {
            opacity = span->fMaterial->GetLayer(i)->GetOpacity();
        }
    }

    /// Generate color table
    if( shadeIt )
        IShadeVertices( span, &dirtyVector, node, translucent );
    else
    {
        for( i = 0; i < span->fNumVerts; i++ )  
        {
            /// This is good for the old way, but not sure about the new way. Test once new way is in again -mcn
//          fShadeColorTable[ i ].Set( 1, 1, 1, 1 );
//          fIllumColorTable[ i ].Set( 0, 0, 0, 1 );
            hsPoint3    position;
            hsVector3   normal;
            hsColorRGBA color, illum;

            span->ExtractVertex( i, &position, &normal, &color, &illum );
            span->ExtractInitColor( i, &color, &illum );
            fShadeColorTable[ i ].Set( color.r, color.g, color.b, color.a );
            fIllumColorTable[ i ].Set( illum.r, illum.g, illum.b, 1 );
        }
    }

    /// Get mat colors to modulate by
    if( layer == nil )
    {
        preDiffuse.Set( 1, 1, 1, 1 );
        rtDiffuse.Set( 1, 1, 1, 1 );
        matAmbient.Set( 0, 0, 0, 0 );
    }
    else
    {
        if( layer->GetShadeFlags() & hsGMatState::kShadeWhite )
        {
            preDiffuse.Set( 1, 1, 1, 1 );
            rtDiffuse.Set( 1, 1, 1, 1 );
            matAmbient.Set( 0, 0, 0, 0 );
        }
        else
        {
            preDiffuse = layer->GetPreshadeColor();     // This is for vertex-based lighting, which basically ignores preshading
            rtDiffuse = layer->GetRuntimeColor();       // This is for vertex-based lighting, which basically ignores preshading
            matAmbient = layer->GetAmbientColor();
            matAmbient.a = 0;
        }
        preDiffuse.a = opacity;
        rtDiffuse.a = opacity;
    }
#if 0

    /// Multiply by the material color, and scale by opacity if we're additive blending
    /// Apply colors now, multiplying by the material color as we go
    for( i = 0; i < span->fNumVerts; i++ )
    {
        fShadeColorTable[ i ] *= matDiffuse;
        fShadeColorTable[ i ] += matAmbient;
        fIllumColorTable[ i ] *= matDiffuse;
        fIllumColorTable[ i ] += matAmbient;
    }

    if( addingIt )
    {
        for( i = 0; i < span->fNumVerts; i++ )
        {
            float opacity = fShadeColorTable[ i ].a;
            fShadeColorTable[ i ] *= opacity;
            fIllumColorTable[ i ] *= opacity;
        }
    }
#else
    /// Combine shade and illum together into the diffuse color
    if( ( span->fProps & plGeometrySpan::kLiteMask ) != plGeometrySpan::kLiteMaterial )
    {
        /// The two vertex lighting formulas take in a vetex color pre-processed, i.e. in 
        /// the form of: vtxColor = ( maxVtxColor * materialDiffuse + maxIllumColor )
        span->fProps |= plGeometrySpan::kDiffuseFoldedIn;
        if( !shadeIt )
        {
            for( i = 0; i < span->fNumVerts; i++ )
            {
                fIllumColorTable[ i ].a = 0;
                fShadeColorTable[ i ] = (fShadeColorTable[ i ] * rtDiffuse) + fIllumColorTable[ i ];
                fIllumColorTable[ i ].Set( 0, 0, 0, 0 );
            }
        }
        else
        {
            for( i = 0; i < span->fNumVerts; i++ )
            {
                fIllumColorTable[ i ].a = 1.f;
                // Following needs to be changed to allow user input vertex colors to modulate
                // the runtime light values.
//              fShadeColorTable[ i ] = fIllumColorTable[ i ] * rtDiffuse;
                fShadeColorTable[ i ] = fShadeColorTable[ i ] * fIllumColorTable[ i ] * rtDiffuse;
                fIllumColorTable[ i ].Set( 0, 0, 0, 0 );
            }
        }
    }
    else
    {
        if( !shadeIt )
        {
            // Not shaded, so runtime lit, so we want BLACK vertex colors
            for( i = 0; i < span->fNumVerts; i++ )
            {
                fShadeColorTable[ i ].Set( 0, 0, 0, 0 );
                fIllumColorTable[ i ].Set( 0, 0, 0, 0 );
            }
        }
        else
        {
            for( i = 0; i < span->fNumVerts; i++ )
            {
                fShadeColorTable[ i ] *= fIllumColorTable[ i ];
                fIllumColorTable[ i ].Set( 0, 0, 0, 0 );
            }
        }
    }
#endif

    /// Loop and stuff
    for( i = 0; i < span->fNumVerts; i++ )
        span->StuffVertex( i, fShadeColorTable + i, fIllumColorTable + i );

    delete [] fShadeColorTable;       
    delete [] fIllumColorTable;       

    hsGuardEnd;
}
Ejemplo n.º 5
0
//This function sets up the quick fadable region.
//It removes anything that cannot be quick faded, and schedules it to be drawn in the normal fashion.
void CWsWindow::SetFadeableRegion(const TRegion& aNewFadableRegion, const TRegion& aTop)
	{
	WS_ASSERT_DEBUG(iScreen, EWsPanicNoScreen);
	iFadableRegion.Copy(aNewFadableRegion);

	//Try to figure out if any part of iFadableRegion can be quick faded (i.e. fading applied to 
	//the screen without first having to redraw all visible windows intersecting the region).
	if ( !iFadableRegion.IsEmpty() && iScreen->IsQuickFadeScheduled(this) )
		{
		if (IsTranslucent())
			{
			//If a window is semitransparent, then we cannot apply a quickfade to it if
			//the window below is faded too.
			iScreen->AddRedrawRegion(iVisibleRegion, EFalse, ERedrawAll);
			iScreen->RemoveFromQuickFadeList(this);
			}
		else
			{
			iQuickFadeRegion.Intersection(iFadableRegion, aTop);
			
			//Remove any regions not possible to quick fade from iQuickFadeRegion and
			//schedule these regions for full back-front rendering instead.
			STACK_REGION nonQuickFadableRegion;

			for(CWsSpriteBase * sprite = iSpriteList; sprite; sprite = sprite->Next())
				{
				nonQuickFadableRegion.AddRect(sprite->Rect());
				}

			for(CWsAnim * anim = iAnimList; anim; anim = anim->Next())
				{
				nonQuickFadableRegion.AddRect(anim->BestRect());
				}

			RWsTextCursor* const cursor = CWsTop::CurrentTextCursor();
			if( cursor && (cursor->Window()==this) && cursor->IsStandardCursorActive() )
				{
				nonQuickFadableRegion.AddRect(cursor->Rect());
				}

			//Any regions scheduled for fading but partly or fully covered by transparent windows above them
			STACK_REGION coveredFadableRegion;
			coveredFadableRegion.Copy(iFadableRegion);
			coveredFadableRegion.SubRegion(iQuickFadeRegion);
			nonQuickFadableRegion.Union(coveredFadableRegion);
			coveredFadableRegion.Close();

			nonQuickFadableRegion.Tidy();

			//Remove any regions not possible to quick fade from iQuickFadeRegion
			iQuickFadeRegion.SubRegion(nonQuickFadableRegion);

			if (!nonQuickFadableRegion.CheckError())
				{
				//Schedule normal drawing (full back to front rendering) for the region not possible to quick fade
				if (!nonQuickFadableRegion.IsEmpty())
					{ 
					iScreen->AddRedrawRegion(nonQuickFadableRegion, EFalse, ERedrawAll);
					}
				}
			else
				{
				//Schedule normal drawing for the whole iVisibleRegion if the calculations are broken
				iScreen->AddRedrawRegion(iVisibleRegion, EFalse, ERedrawAll);
				}
			nonQuickFadableRegion.Close();
			}
		}
	else
		{
		iQuickFadeRegion.Reset();
		}
	}
Ejemplo n.º 6
0
void CWsWindow::SetVisibleRegion(const TRegion& aNewRegion, const TRegion* aTop)
	{
	WS_ASSERT_DEBUG(iScreen, EWsPanicNoScreen);
	STACK_REGION difference;
	TBool diffs = EFalse;

	difference.Copy(iVisibleRegion);	
	difference.SubRegion(aNewRegion);
	if (!difference.IsEmpty())
		{
		diffs = ETrue;
		if (IsTranslucent())
			{
			iScreen->AddRedrawRegion(difference, EFalse);	
			}
		}

	difference.Copy(aNewRegion);
	if (HasBeenDrawnToScreen())
		{
		difference.SubRegion(iVisibleRegion);
		}
	if (!difference.IsEmpty())
		{
		diffs = ETrue;
		if(!iScreen->ChangeTracking())
			{
			//the following code will restart animations
			STACK_REGION topDiff;
			topDiff.Copy(difference);
			WS_ASSERT_DEBUG(aTop,EWsPanicRegion);
			topDiff.Intersect(*aTop);
			difference.SubRegion(topDiff);
			iScreen->AddRedrawRegion(topDiff, EFalse, ERedrawTopOnly);
			iScreen->AddRedrawRegion(difference, EFalse, ERedrawAll);
			topDiff.Close();
			}
		else if(IsVisible())
			{
			RestartAnimations(aNewRegion);
			}
		}

	difference.Close();

	AbortDsaIfRequired(aNewRegion, aTop);

	if (diffs)
		{
		ResetVisibleRegion();
		iVisibleRegion.Copy(aNewRegion);
		PossibleVisibilityChangedEvent(EFalse);
		
		if (Redraw()->HasElement())
			{
			WS_ASSERT_DEBUG(WinType()==EWinTypeClient,EWsPanicWindowType);
			
			if (WinType()==EWinTypeClient)
				{
				iScreen->WindowElements().SetVisibleRegion(*static_cast<CWsClientWindow*>(this));
				}
			}
		}

	// Just because the visible region (screen coordinates) didn't change doesn't
	// mean the invalid region (window coordinates) didn't change, so we always call this.
	iRedraw->VisibleRegionChange();
	}