Пример #1
0
//////////////////////////////////////////////////////////////////////////
// haveAnyValidResources
BcBool CsPackage::haveAnyValidResources() const
{
	BcAssert( BcIsGameThread() );

	// If the data isn't ready, we will have valid resources soon.
	if( pLoader_->isDataReady() == BcFalse )
	{
		return BcTrue;
	}

	// If our resource list is empty we can exit early.
	if( Resources_.size() == 0 )
	{
		return BcFalse;
	}

	// Search through list for all valid resources.
	for( BcU32 Idx = 0; Idx < Resources_.size(); ++Idx )
	{
		const CsResourceRef<>& Resource( Resources_[ Idx ] );

		if( Resource.isValid() == BcTrue )
		{
			return BcTrue;
		}
	}

	//
	return BcFalse;
}
Пример #2
0
//////////////////////////////////////////////////////////////////////////
// getContext
//virtual
RsContext* RsCoreImplGL::getContext( OsClient* pClient )
{
    BcAssert( BcIsGameThread() );
    TContextMapIterator It = ContextMap_.find( pClient );

    if( It != ContextMap_.end() )
    {
        return It->second;
    }
    else
    {
        if( pClient != NULL )
        {
            RsContextGL* pResource = new RsContextGL( pClient, ContextMap_[ NULL ] );
            createResource( pResource );

            // If we have no default context, set it.
            if( ContextMap_[ NULL ] == NULL )
            {
                ContextMap_[ NULL ] = pResource;
            }

            // Store mapped to client.
            ContextMap_[ pClient ] = pResource;

            return pResource;
        }
    }

    return NULL;
}
Пример #3
0
//////////////////////////////////////////////////////////////////////////
// hasUnreferencedResources
BcBool CsPackage::hasUnreferencedResources() const
{
	BcAssert( BcIsGameThread() );

	// If the data isn't ready, we are still referenced.
	if( pLoader_->isDataReady() == BcFalse )
	{
		return BcFalse;
	}

	BcBool IsUnreferenced = BcTrue;
	
	for( BcU32 Idx = 0; Idx < Resources_.size(); ++Idx )
	{
		const CsResourceRef<>& Resource( Resources_[ Idx ] );

		// If we've got invalid resources, or a ref count of 1 (self-ref'd) we have unreferenced resources.
		if( Resource.isValid() == BcFalse || Resource.refCount() == 1 )
		{
			return BcTrue;
		}
	}

	return BcFalse;
}
Пример #4
0
	ReEnum* GetEnum( BcName Name )
	{
		auto NameString = ( *Name );

		// If it begins with "class", "struct", or "enum", strip it.
		// NOTE: We should move this work into the demangling stuff.
		if( NameString.substr( 0, 5 ) == "enum " )
		{
			Name = BcName( NameString.substr( NameString.find( " " ) + 1, NameString.length() - 1 ) );
		}

		// Try find class.
		ReClass* FoundType = GetType( Name );
		if( FoundType == nullptr )
		{
			BcAssertMsg( BcIsGameThread(), "Reflection can only modify database on the game thread." );
			FoundType = new ReEnum( Name );
			Types_[ Name ] = FoundType;
		}

		if( FoundType->isTypeOf< ReEnum >() )
		{
			return static_cast< ReEnum* >( FoundType );
		}
		else
		{
			return nullptr;
		}
	}
Пример #5
0
	ReClass* GetClass( BcName Name )
	{
		auto NameString = (*Name);

		// If it begins with "class", "struct", or "enum", strip it.
		// NOTE: We should move this work into the demangling stuff.
		if( NameString.substr( 0, 6 ) == "class " ||
			NameString.substr( 0, 7 ) == "struct " ||
			NameString.substr( 0, 5 ) == "enum " )
		{
			Name = BcName( NameString.substr( NameString.find( " " ) + 1, NameString.length() - 1 ) );
		}

		// Try find class.
		ReClass* FoundType = GetType( Name );
		if( FoundType == nullptr )
		{
			BcAssertMsg( BcIsGameThread(), "Reflection can only modify database on the game thread." );
			FoundType = new ReClass( Name );
			Types_[ Name ] = FoundType;
		}

		// Use dynamic cast here instead of our internal RTTI.
		// It may still be under construction so not yet valid.
		return dynamic_cast< ReClass* >( FoundType );
	}
Пример #6
0
//////////////////////////////////////////////////////////////////////////
// tick
void SysKernel::tick()
{
	BcAssert( BcIsGameThread() );

	if( ShuttingDown_ == BcFalse )
	{
		BcScopedLock< BcMutex > Lock( SystemLock_ );

		// Add systems.
		addSystems();
	
		// Remove systems.	
		removeSystems();
	
		// Iterate over and process all systems.
		TSystemListIterator Iter = SystemList_.begin();
	
		while( Iter != SystemList_.end() && ShuttingDown_ == BcFalse )
		{
			// Cache system.
			SysSystem* pSystem = (*Iter);
		
			// Process system.
			if( pSystem->process() == BcFalse )
			{
				PendingRemoveSystemList_.push_back( pSystem );		
			}
		
			// Next system.
			++Iter;
		}
	}
	else
	{
		BcScopedLock< BcMutex > Lock( SystemLock_ );

		// Iterate over and process all systems.
		TSystemListReverseIterator Iter = SystemList_.rbegin();
		
		if( Iter != SystemList_.rend() )
		{
			// Cache system.
			SysSystem* pSystem = (*Iter);
			
			//  Process system.
			if( pSystem->process() == BcFalse )
			{
				PendingRemoveSystemList_.push_back( pSystem );		
			}
		}
		
		// Remove systems.
		removeSystems();
	}
	
	// Dispatch callbacks.
	DelegateDispatcher_.dispatch();
}
Пример #7
0
//////////////////////////////////////////////////////////////////////////
// createResource
void RsCoreImplGL::createResource( RsResource* pResource )
{
    BcAssert( BcIsGameThread() );

    // Call create.
    {
        SysSystem::CreateDelegate Delegate( SysSystem::CreateDelegate::bind< SysResource, &SysResource::create >( pResource ) );
        SysKernel::pImpl()->enqueueDelegateJob( RsCore::WORKER_MASK, Delegate );
    }
}
Пример #8
0
//////////////////////////////////////////////////////////////////////////
// open
//virtual
void RsCoreImplGL::open()
{
    BcAssert( BcIsGameThread() );
    BcDelegate< void(*)() > Delegate( BcDelegate< void(*)() >::bind< RsCoreImplGL, &RsCoreImplGL::open_threaded >( this ) );
    SysKernel::pImpl()->enqueueDelegateJob( RsCore::WORKER_MASK, Delegate );

    // Wait for the render thread to complete.
    SysFence Fence;
    Fence.queue( RsCore::WORKER_MASK );
    Fence.wait();
}
Пример #9
0
//////////////////////////////////////////////////////////////////////////
// allocateFrame
RsFrame* RsCoreImplGL::allocateFrame( RsContext* pContext )
{
    BcAssert( BcIsGameThread() );
    if( pContext != NULL )
    {
        return new RsFrameGL( pContext );
    }
    else
    {
        return new RsFrameGL( ContextMap_[ NULL ] );
    }
}
Пример #10
0
//////////////////////////////////////////////////////////////////////////
// destroyResource
void RsCoreImplGL::destroyResource( RsResource* pResource )
{
    BcAssert( BcIsGameThread() );

    pResource->preDestroy();

    // Call destroy and wait.
    {
        SysSystem::DestroyDelegate Delegate( SysSystem::DestroyDelegate::bind< SysResource, &SysResource::destroy >( pResource ) );
        SysKernel::pImpl()->enqueueDelegateJob( RsCore::WORKER_MASK, Delegate );
    }
}
Пример #11
0
//////////////////////////////////////////////////////////////////////////
// update
//virtual
void RsCoreImplGL::update()
{
    BcAssert( BcIsGameThread() );
    // Increment fence so we know how far we're getting ahead of ourselves.
    RenderSyncFence_.increment();

    // Queue update job.
    BcDelegate< void(*)() > Delegate( BcDelegate< void(*)() >::bind< RsCoreImplGL, &RsCoreImplGL::update_threaded >( this ) );
    SysKernel::pImpl()->enqueueDelegateJob( RsCore::WORKER_MASK, Delegate );

    // Wait for frames if we fall more than 1 update cycle behind.
    RenderSyncFence_.wait( 1 );
}
Пример #12
0
//////////////////////////////////////////////////////////////////////////
// destroyContext
//virtual
void RsCoreImplGL::destroyContext( OsClient* pClient )
{
    BcAssert( BcIsGameThread() );
    TContextMapIterator It = ContextMap_.find( pClient );

    if( It != ContextMap_.end() )
    {
        // If we're destroying the default context, NULL it.
        if( ContextMap_[ NULL ] == It->second )
        {
            ContextMap_[ NULL ] = NULL;
        }

        // Destory resource.
        destroyResource( It->second );

        // Erase from context map.
        ContextMap_.erase( It );
    }
}
Пример #13
0
//////////////////////////////////////////////////////////////////////////
// releaseUnreferencedResources
void CsPackage::releaseUnreferencedResources()
{
	BcAssert( BcIsGameThread() );

	// If the data isn't ready, we are still referenced.
	if( pLoader_->isDataReady() == BcFalse )
	{
		return;
	}
	
	for( BcU32 Idx = 0; Idx < Resources_.size(); ++Idx )
	{
		CsResourceRef<>& Resource( Resources_[ Idx ] );

		// Check that the package is the only referencer, if so, NULL it.
		if( Resource.isValid() && Resource.refCount() == 1 )
		{
			Resource = NULL;
		}
	}
}
Пример #14
0
////////////////////////////////////////////////////////////////////////////////
// publishInternal
BcBool EvtPublisher::publishInternal( EvtID ID, const EvtBaseEvent& EventBase, BcSize EventSize, BcBool AllowProxy )
{
	BcAssert( BcIsGameThread() );
	BcUnusedVar( EventSize );

#if PSY_USE_PROFILER
	PSY_PROFILER_INSTANT_EVENT( boost::str( boost::format( "EvtPublisher::publishInternal( ID: %1%, Size: %2% )" ) % ID % EventSize ) );
#endif

	// Proxy event through all attached proxies if this event allows it.
	if( AllowProxy == BcTrue )
	{
		for( TProxyListIterator It( Proxies_.begin() ); It != Proxies_.end(); ++It )
		{	
			EvtProxy* pProxy( *It );
			eEvtReturn RetVal = pProxy->proxy( ID, EventBase, EventSize );

			switch( RetVal )
			{
			// Event passed. Publisher, or next proxy can deal with it.
			case evtRET_PASS:
				break;
			// Event blocked. If we are a parent, we want our child publisher to abort (normal behaviour).
			case evtRET_BLOCK:
				return BcFalse;
				break;
			// Unsupported enum value.
			default:
				BcBreakpoint;
				break;
			}
		}
	}

	// Update binding map before going ahead.
	updateBindingMap();
	
	// If we have a parent, publish to them first.
	BcBool ShouldPublish = BcTrue;
	
	if( pParent_ != NULL )
	{
		ShouldPublish = pParent_->publishInternal( ID, EventBase, EventSize );
	}

	// Only publish if the previous call to our parent allows us to.
	if( ShouldPublish == BcTrue )
	{
		// Find the appropriate binding list.
		TBindingListMapIterator BindingListMapIterator = BindingListMap_.find( ID );
		
		// Add list if we need to, and grab iterator.
		if( BindingListMapIterator != BindingListMap_.end() )
		{
			// Iterate over all bindings in list and call.
			TBindingList& BindingList = BindingListMapIterator->second;
			TBindingListIterator Iter = BindingList.begin();
			
			while( Iter != BindingList.end() )
			{
				EvtBinding& Binding = (*Iter);
				
				// Call binding and handle it's return.
				eEvtReturn RetVal = Binding( ID, EventBase );
				switch( RetVal )
				{
					case evtRET_PASS:
						++Iter;
						break;

					case evtRET_BLOCK:
						return BcFalse;
						break;

					case evtRET_REMOVE:
						Iter = BindingList.erase( Iter );
						break;
						
					default:
						BcBreakpoint;
						break;
				}
			}
		}
	}

	return BcTrue;
}
Пример #15
0
//////////////////////////////////////////////////////////////////////////
// queueFrame
void RsCoreImplGL::queueFrame( RsFrame* pFrame )
{
    BcAssert( BcIsGameThread() );
    BcDelegate< void(*)( RsFrameGL* ) > Delegate( BcDelegate< void(*)( RsFrameGL* ) >::bind< RsCoreImplGL, &RsCoreImplGL::queueFrame_threaded >( this ) );
    SysKernel::pImpl()->enqueueDelegateJob( RsCore::WORKER_MASK, Delegate, (RsFrameGL*)pFrame );
}
Пример #16
0
////////////////////////////////////////////////////////////////////////////////
// publishInternal
BcBool EvtPublisher::publishInternal( EvtID ID, const EvtBaseEvent& EventBase, BcSize EventSize )
{
	BcAssert( BcIsGameThread() );
	BcUnusedVar( EventSize );
	
	/*
	{
		BcChar PrefixA = ( ID >> 24 ) & 0xff;
		BcChar PrefixB = ( ID >> 16 ) & 0xff;
		BcU32 Group = ( ID >> 8 ) & 0xff;
		BcU32 Item = ( ID ) & 0xff;
		
		BcPrintf( "EvtPublish: %x, \"%c%c\": Group=%u Item=%u\n", ID, PrefixA, PrefixB, Group, Item );
	}
	 //*/

	// Update binding map before going ahead.
	updateBindingMap();
	
	// If we have a parent, publish to them first.
	BcBool ShouldPublish = BcTrue;
	
	if( pParent_ != NULL )
	{
		ShouldPublish = pParent_->publishInternal( ID, EventBase, EventSize );
	}

	// Only publish if the previous call to our parent allows us to.
	if( ShouldPublish == BcTrue )
	{
		// Find the appropriate binding list.
		TBindingListMapIterator BindingListMapIterator = BindingListMap_.find( ID );
		
		// Add list if we need to, and grab iterator.
		if( BindingListMapIterator != BindingListMap_.end() )
		{
			// Iterate over all bindings in list and call.
			TBindingList& BindingList = BindingListMapIterator->second;
			TBindingListIterator Iter = BindingList.begin();
			
			while( Iter != BindingList.end() )
			{
				EvtBinding& Binding = (*Iter);
				
				// Call binding and handle it's return.
				eEvtReturn RetVal = Binding( ID, EventBase );
				switch( RetVal )
				{
					case evtRET_PASS:
						++Iter;
						break;

					case evtRET_BLOCK:
						return BcFalse;
						break;

					case evtRET_REMOVE:
						Iter = BindingList.erase( Iter );
						break;
						
					default:
						BcBreakpoint;
						break;
				}
			}
		}
	}

	return BcTrue;
}