Bladeren bron

Resource handles will now be null only if they have no UUID, regardless if their resource is loaded or not
- Since there is an .isLoaded method that can check for loaded resource specifically
Standalone builds will now properly always be in play-mode
Fixed an issue with GameSettings load that was calling Resources module which wasn't initialized at standalone startup
Fixed an issue with going fullscreen and incorrect resolution
Standalone builds will now properly load game script assembly
Properly show progress bar when building or opening a file in external code editor

BearishSun 10 jaren geleden
bovenliggende
commit
95a7c4063f

+ 10 - 1
BansheeCore/Include/BsResourceHandle.h

@@ -227,7 +227,7 @@ namespace BansheeEngine
 		 */
 		operator int Bool_struct<T>::*() const
 		{
-			return ((mData != nullptr && mData->mPtr != nullptr) ? &Bool_struct<T>::_Member : 0);
+			return ((mData != nullptr && !mData->mUUID.empty()) ? &Bool_struct<T>::_Member : 0);
 		}
 
 		/**
@@ -366,6 +366,15 @@ namespace BansheeEngine
 		return _Left.getHandleData() == _Right.getHandleData();
 	}
 
+	/**
+	 * @brief	Checks if a handle is null.
+	 */
+	template<class _Ty1, bool _Weak1, class _Ty2, bool _Weak2>
+	bool operator==(const TResourceHandle<_Ty1, _Weak1>& _Left, std::nullptr_t  _Right)
+	{	
+		return _Left.getHandleData() == nullptr || _Left.setHandleData().UUID.empty();
+	}
+
 	template<class _Ty1, bool _Weak1, class _Ty2, bool _Weak2>
 	bool operator!=(const TResourceHandle<_Ty1, _Weak1>& _Left, const TResourceHandle<_Ty2, _Weak2>& _Right)
 	{	

+ 1 - 1
BansheeCore/Source/BsMaterialRTTI.cpp

@@ -43,7 +43,7 @@ namespace BansheeEngine
 		std::shared_ptr<MaterialParams> params = bs_shared_ptr_new<MaterialParams>();
 
 		HShader shader = material->getShader();
-		if(shader != nullptr)
+		if(shader.isLoaded())
 		{
 			const Map<String, String>& validParamNames = material->getValidParamNames();
 

+ 1 - 1
BansheeCore/Source/BsResourceHandle.cpp

@@ -87,7 +87,7 @@ namespace BansheeEngine
 	void ResourceHandleBase::throwIfNotLoaded() const
 	{
 #if BS_DEBUG_MODE
-		if (!isLoaded())
+		if (!isLoaded(false))
 		{
 			BS_EXCEPT(InternalErrorException, "Trying to access a resource that hasn't been loaded yet.");
 		}

+ 30 - 4
BansheeCore/Source/BsResources.cpp

@@ -313,8 +313,21 @@ namespace BansheeEngine
 		if (resource == nullptr)
 			return;
 
-		if (!resource.isLoaded()) // If it's still loading wait until that finishes
-			resource.blockUntilLoaded();
+		if (!resource.isLoaded(false))
+		{
+			bool loadInProgress = false;
+			{
+				BS_LOCK_MUTEX(mInProgressResourcesMutex);
+				auto iterFind2 = mInProgressResources.find(resource.getUUID());
+				if (iterFind2 != mInProgressResources.end())
+					loadInProgress = true;
+			}
+
+			if (loadInProgress) // If it's still loading wait until that finishes
+				resource.blockUntilLoaded();
+			else
+				return; // Already unloaded
+		}
 
 		Vector<ResourceDependency> dependencies = Utility::findResourceDependencies(*resource.get());
 
@@ -380,8 +393,21 @@ namespace BansheeEngine
 		if (resource == nullptr)
 			return;
 
-		if(!resource.isLoaded())
-			resource.blockUntilLoaded();
+		if (!resource.isLoaded(false))
+		{
+			bool loadInProgress = false;
+			{
+				BS_LOCK_MUTEX(mInProgressResourcesMutex);
+				auto iterFind2 = mInProgressResources.find(resource.getUUID());
+				if (iterFind2 != mInProgressResources.end())
+					loadInProgress = true;
+			}
+
+			if (loadInProgress) // If it's still loading wait until that finishes
+				resource.blockUntilLoaded();
+			else
+				return; // Nothing to save
+		}
 
 		bool fileExists = FileSystem::isFile(filePath);
 		if(fileExists)

+ 14 - 4
BansheeD3D11RenderAPI/Source/BsD3D11RenderWindow.cpp

@@ -512,12 +512,22 @@ namespace BansheeEngine
 		if (!mWindow)
 			return;
 
+		mWindow->_windowMovedOrResized();
+
 		D3D11RenderWindowProperties& props = mProperties;
 
-		resizeSwapChainBuffers(mWindow->getWidth(), mWindow->getHeight());
-		mWindow->_windowMovedOrResized();
-		props.mTop = mWindow->getTop();
-		props.mLeft = mWindow->getLeft();
+		if (props.isFullScreen()) // Fullscreen is handled directly by this object
+		{
+			resizeSwapChainBuffers(props.getWidth(), props.getHeight());
+		}
+		else
+		{
+			resizeSwapChainBuffers(mWindow->getWidth(), mWindow->getHeight());
+			props.mWidth = mWindow->getWidth();
+			props.mHeight = mWindow->getHeight();
+			props.mTop = mWindow->getTop();
+			props.mLeft = mWindow->getLeft();
+		}
 
 		RenderWindowCore::_windowMovedOrResized();
 	}

+ 7 - 4
BansheeD3D9RenderAPI/Source/BsD3D9RenderWindow.cpp

@@ -370,10 +370,13 @@ namespace BansheeEngine
 		mWindow->_windowMovedOrResized();
 
 		D3D9RenderWindowProperties& props = mProperties;
-		props.mTop = mWindow->getTop();
-		props.mLeft = mWindow->getLeft();
-		props.mWidth = mWindow->getWidth();
-		props.mHeight = mWindow->getHeight();
+		if (!props.isFullScreen()) // Fullscreen is handled directly by this object
+		{
+			props.mTop = mWindow->getTop();
+			props.mLeft = mWindow->getLeft();
+			props.mWidth = mWindow->getWidth();
+			props.mHeight = mWindow->getHeight();
+		}
 
 		RenderWindowCore::_windowMovedOrResized();
 	}

+ 5 - 0
BansheeEditor/Include/BsEditorApplication.h

@@ -113,6 +113,11 @@ namespace BansheeEngine
 		 * @param	path	Absolute path to the root project folder.
 		 */
 		bool isValidProjectPath(const Path& path);
+
+		/**
+		 * @copydoc	Application::isEditor
+		 */
+		bool isEditor() const override { return true; }
 	private:
 		/**
 		 * @copydoc	Module::onStartUp

+ 5 - 0
BansheeEngine/Include/BsApplication.h

@@ -59,6 +59,11 @@ namespace BansheeEngine
 		 */
 		virtual Path getScriptAssemblyFolder() const;
 
+		/**
+		 * @brief	Returns true if the application is running in an editor, false if standalone.
+		 */
+		virtual bool isEditor() const { return false; }
+
 	protected:
 		/**
 		 * @copydoc	Module::onStartUp

+ 1 - 1
BansheeEngine/Include/BsGameSettings.h

@@ -12,7 +12,7 @@ namespace BansheeEngine
 	class BS_EXPORT GameSettings : public IReflectable
 	{
 	public:
-		WeakResourceHandle<Prefab> mainScene; /**< Resource UUID of the default scene that is loaded when the application is started. */
+		String mainSceneUUID; /**< Resource UUID of the default scene that is loaded when the application is started. */
 		bool fullscreen = true; /**< If true the application will be started in fullscreen using user's desktop resolution. */
 		bool useDesktopResolution = true; /**< If running in fullscreen should the user's desktop resolution be used instead of the specified resolution. */
 		UINT32 resolutionWidth = 1280; /**< Width of the window. */

+ 3 - 3
BansheeEngine/Include/BsGameSettingsRTTI.h

@@ -9,8 +9,8 @@ namespace BansheeEngine
 	class BS_EXPORT GameSettingsRTTI : public RTTIType <GameSettings, IReflectable, GameSettingsRTTI>
 	{
 	private:
-		WeakResourceHandle<Prefab>& getMainScene(GameSettings* obj) { return obj->mainScene; }
-		void setMainScene(GameSettings* obj, WeakResourceHandle<Prefab>& val) { obj->mainScene = val; }
+		String& getMainSceneUUID(GameSettings* obj) { return obj->mainSceneUUID; }
+		void setMainSceneUUID(GameSettings* obj, String& val) { obj->mainSceneUUID = val; }
 
 		bool& getFullscreen(GameSettings* obj) { return obj->fullscreen; }
 		void setFullscreen(GameSettings* obj, bool& val) { obj->fullscreen = val; }
@@ -30,7 +30,7 @@ namespace BansheeEngine
 	public:
 		GameSettingsRTTI()
 		{
-			addReflectableField("mainScene", 0, &GameSettingsRTTI::getMainScene, &GameSettingsRTTI::setMainScene);
+			addPlainField("mainSceneUUID", 0, &GameSettingsRTTI::getMainSceneUUID, &GameSettingsRTTI::setMainSceneUUID);
 			addPlainField("fullscreen", 1, &GameSettingsRTTI::getFullscreen, &GameSettingsRTTI::setFullscreen);
 			addPlainField("useDesktopResolution", 2, &GameSettingsRTTI::getUseDesktopResolution, &GameSettingsRTTI::setUseDesktopResolution);
 			addPlainField("resolutionWidth", 3, &GameSettingsRTTI::getResolutionWidth, &GameSettingsRTTI::setResolutionWidth);

+ 7 - 4
BansheeGLRenderAPI/Source/BsWin32RenderWindow.cpp

@@ -486,10 +486,13 @@ namespace BansheeEngine
 		mWindow->_windowMovedOrResized();
 
 		Win32RenderWindowProperties& props = mProperties;
-		props.mTop = mWindow->getTop();
-		props.mLeft = mWindow->getLeft();
-		props.mWidth = mWindow->getWidth();
-		props.mHeight = mWindow->getHeight();
+		if (!props.mIsFullScreen) // Fullscreen is handled directly by this object
+		{
+			props.mTop = mWindow->getTop();
+			props.mLeft = mWindow->getLeft();
+			props.mWidth = mWindow->getWidth();
+			props.mHeight = mWindow->getHeight();
+		}
 
 		RenderWindowCore::_windowMovedOrResized();
 	}

+ 1 - 1
Game/Source/Main.cpp

@@ -121,7 +121,7 @@ void runApplication()
 		gResources().registerResourceManifest(manifest);
 	}
 
-	HPrefab mainScene = gResources().load<Prefab>(gameSettings->mainScene);
+	HPrefab mainScene = static_resource_cast<Prefab>(gResources().loadFromUUID(gameSettings->mainSceneUUID));
 	if (mainScene != nullptr)
 	{
 		HSceneObject root = mainScene->instantiate();

+ 3 - 4
MBansheeEditor/BuildWindow.cs

@@ -14,7 +14,7 @@ namespace BansheeEditor
 
         private PlatformType selectedPlatform;
         private GUIScrollArea optionsScrollArea;
-        private bool buildScheduled;
+        private ulong buildScheduledFrame = ulong.MaxValue;
 
         private GUIToggle[] platformButtons;
 
@@ -99,14 +99,13 @@ namespace BansheeEditor
 
         private void OnEditorUpdate()
         {
-            if (buildScheduled)
+            if (buildScheduledFrame == Time.FrameIdx)
             {
                 BuildManager.Build();
                 ProgressBar.Hide();
 
                 EditorApplication.OpenExternally(BuildManager.OutputFolder);
                 DialogBox.Open(new LocEdString("Build complete"), new LocEdString("Build complete"), DialogBox.Type.OK);
-                buildScheduled = false;
             }
         }
 
@@ -238,7 +237,7 @@ namespace BansheeEditor
 
             EditorApplication.SaveProject();
             // HACK - Delay build one frame so that progress bar has a chance to show. Use coroutines here once implemented.
-            buildScheduled = true;
+            buildScheduledFrame = Time.FrameIdx + 1;
         }
 
         /// <summary>

+ 15 - 2
MBansheeEditor/Library/LibraryGUIEntry.cs

@@ -42,6 +42,7 @@ namespace BansheeEditor
 
         private bool delayedSelect;
         private float delayedSelectTime;
+        private ulong delayedOpenCodeEditorFrame = ulong.MaxValue;
 
         /// <summary>
         /// Bounds of the entry relative to part content area.
@@ -132,6 +133,18 @@ namespace BansheeEditor
                 owner.Window.Select(path);
                 delayedSelect = false;
             }
+
+            if (delayedOpenCodeEditorFrame == Time.FrameIdx)
+            {
+                LibraryEntry entry = ProjectLibrary.GetEntry(path);
+                if (entry != null && entry.Type == LibraryEntryType.File)
+                {
+                    FileEntry resEntry = (FileEntry) entry;
+                    CodeEditor.OpenFile(resEntry.Path, 0);
+                }
+
+                ProgressBar.Hide();
+            }
         }
 
         /// <summary>
@@ -332,8 +345,8 @@ namespace BansheeEditor
                     else if (resEntry.ResType == ResourceType.ScriptCode)
                     {
                         ProgressBar.Show("Opening external code editor...", 1.0f);
-                        CodeEditor.OpenFile(resEntry.Path, 0);
-                        ProgressBar.Hide();
+
+                        delayedOpenCodeEditorFrame = Time.FrameIdx + 1;
                     }
                 }
             }

+ 1 - 1
SBansheeEditor/Source/BsScriptBuildManager.cpp

@@ -391,7 +391,7 @@ namespace BansheeEngine
 		if (platformInfo != nullptr)
 		{
 			gameSettings = bs_shared_ptr_new<GameSettings>();
-			gameSettings->mainScene = platformInfo->mainScene;
+			gameSettings->mainSceneUUID = platformInfo->mainScene.getUUID();
 			gameSettings->fullscreen = platformInfo->fullscreen;
 			gameSettings->resolutionWidth = platformInfo->windowedWidth;
 			gameSettings->resolutionWidth = platformInfo->windowedHeight;

+ 8 - 0
SBansheeEngine/Source/BsEngineScriptLibrary.cpp

@@ -41,6 +41,14 @@ namespace BansheeEngine
 		ScriptVirtualInput::startUp();
 
 		ScriptAssemblyManager::instance().loadAssemblyInfo(ENGINE_ASSEMBLY);
+
+		Path gameAssemblyPath = gApplication().getGameAssemblyPath();
+		if (FileSystem::exists(gameAssemblyPath))
+		{
+			MonoManager::instance().loadAssembly(gameAssemblyPath.toString(), SCRIPT_GAME_ASSEMBLY);
+			ScriptAssemblyManager::instance().loadAssemblyInfo(SCRIPT_GAME_ASSEMBLY);
+		}
+
 		bansheeEngineAssembly.invoke(ASSEMBLY_ENTRY_POINT);
 	}
 

+ 11 - 1
SBansheeEngine/Source/BsPlayInEditorManager.cpp

@@ -3,16 +3,23 @@
 #include "BsTime.h"
 #include "BsSceneManager.h"
 #include "BsSceneObject.h"
+#include "BsApplication.h"
 
 namespace BansheeEngine
 {
 	PlayInEditorManager::PlayInEditorManager()
 		:mState(PlayInEditorState::Stopped), mNextState(PlayInEditorState::Stopped), 
 		mFrameStepActive(false), mScheduledStateChange(false), mPausableTime(0.0f)
-	{ }
+	{
+		if (!gApplication().isEditor())
+			mState = PlayInEditorState::Playing;
+	}
 
 	void PlayInEditorManager::setState(PlayInEditorState state)
 	{
+		if (!gApplication().isEditor())
+			return;
+
 		// Delay state change to next frame as this method could be called in middle of object update, in which case
 		// part of the objects before this call would receive different state than other objects.
 		mScheduledStateChange = true;
@@ -69,6 +76,9 @@ namespace BansheeEngine
 
 	void PlayInEditorManager::frameStep()
 	{
+		if (!gApplication().isEditor())
+			return;
+
 		switch (mState)
 		{
 		case PlayInEditorState::Stopped:

+ 1 - 0
TODO.txt

@@ -40,6 +40,7 @@ Optional:
  - Test VS 2015 Community as code editor (possibly also move the code to VS 2015)
 
  More optional:
+ - Add a way to use GUI elements in game window (Default GUI available to all, plus GUIWidget component for custom ones. Make sure skin can be changed for both.)
  - Clearing the console should also clear the status bar
  - When starting drag from hierarchy tree view it tends to select another object (can't repro)
  - Handle seems to lag behind the selected mesh