Browse Source

Work on handles:
- Proper distance scaling
- Compensate for mouse wrapping so the handle doesn't jump suddenly in wrong direction
- Move editor settings to implementation file because VS fails to properly recompile files if I modify the values in header
- Fix the issue with scene and gizmo rendering updating only while interacting with scene view

Marko Pintera 11 years ago
parent
commit
17e7648476

+ 2 - 0
BansheeCore/Source/BsInput.cpp

@@ -68,6 +68,8 @@ namespace BansheeEngine
 			}
 		}
 
+		mPointerDelta = Vector2I::ZERO; // Reset delta in case we don't receive any mouse input this frame
+
 		if(mRawInputHandler == nullptr)
 		{
 			LOGERR("Raw input handler not initialized!");

+ 14 - 12
BansheeEditor/Include/BsEditorSettings.h

@@ -8,6 +8,8 @@ namespace BansheeEngine
 	class BS_ED_EXPORT EditorSettings
 	{
 	public:
+		EditorSettings();
+
 		bool getMoveHandleSnapActive() const { return mMoveSnapActive; }
 		bool getRotateHandleSnapActive() const { return mRotateSnapActive; }
 		bool getScaleHandleSnapActive() const { return mScaleSnapActive; }
@@ -43,21 +45,21 @@ namespace BansheeEngine
 	private:
 		void markAsDirty() const { mHash++; }
 
-		bool mMoveSnapActive = false;
-		bool mRotateSnapActive = false;
-		bool mScaleSnapActive = false;
+		bool mMoveSnapActive;
+		bool mRotateSnapActive;
+		bool mScaleSnapActive;
 
-		float mMoveSnap = 0.1f;
-		Degree mRotationSnap = Degree(20.0f);
-		float mScaleSnap = 0.1f;
+		float mMoveSnap;
+		Degree mRotationSnap;
+		float mScaleSnap;
 
-		UINT32 mGridSize = 256;
-		float mGridAxisSpacing = 1.0f;
-		UINT32 mGridMajorAxisSpacing = 10;
-		UINT32 mGridAxisMarkerSpacing = 25;
+		UINT32 mGridSize;
+		float mGridAxisSpacing;
+		UINT32 mGridMajorAxisSpacing;
+		UINT32 mGridAxisMarkerSpacing;
 
-		float mHandleSize = 0.025f;
+		float mHandleSize;
 
-		mutable UINT32 mHash = 0;
+		mutable UINT32 mHash;
 	};
 }

+ 6 - 2
BansheeEditor/Include/BsSceneViewHandler.h

@@ -1,6 +1,7 @@
 #pragma once
 
 #include "BsEditorPrerequisites.h"
+#include "BsVector2I.h"
 
 namespace BansheeEngine
 {
@@ -10,7 +11,8 @@ namespace BansheeEngine
 		SceneViewHandler(EditorWidgetBase* parentWidget, const SPtr<CameraHandler>& camera);
 		virtual ~SceneViewHandler();
 
-		void update(const Vector2I& position, const Vector2I& delta);
+		void update();
+		void updateHandle(const Vector2I& position, const Vector2I& delta);
 		void trySelectHandle(const Vector2I& position);
 		bool isHandleActive() const;
 		void clearHandleSelection();
@@ -19,12 +21,14 @@ namespace BansheeEngine
 	protected:
 		void render(const Viewport* viewport, DrawList& drawList);
 
-		void wrapCursorToWindow();
+		Vector2I wrapCursorToWindow();
 
 	private:
 		EditorWidgetBase* mParentWidget;
 		SPtr<CameraHandler> mCamera;
 		SceneGrid* mSceneGrid;
 		HEvent mRenderCallback;
+
+		Vector2I mMouseDeltaCompensate;
 	};
 }

+ 5 - 1
BansheeEditor/Source/BsEditorSettings.cpp

@@ -2,5 +2,9 @@
 
 namespace BansheeEngine
 {
-
+	EditorSettings::EditorSettings()
+		:mMoveSnapActive(false), mRotateSnapActive(false), mScaleSnapActive(false), mMoveSnap(0.1f),
+		mRotationSnap(20.0f), mScaleSnap(0.1f), mGridSize(256), mGridAxisSpacing(1.0f), mGridMajorAxisSpacing(10),
+		mGridAxisMarkerSpacing(25), mHandleSize(0.15f), mHash(0)
+	{ }
 }

+ 22 - 22
BansheeEditor/Source/BsHandleDrawManager.cpp

@@ -67,88 +67,88 @@ namespace BansheeEngine
 
 	void HandleDrawManager::drawCube(const Vector3& position, const Vector3& extents, float size)
 	{
-		Matrix4 scale(Vector3::ZERO, Quaternion::IDENTITY, Vector3(size, size, size));
-		mDrawHelper->setTransform(scale * mTransform);
+		Matrix4 scale = Matrix4::scaling(size);
+		mDrawHelper->setTransform(mTransform * scale);
 
 		mDrawHelper->cube(position, extents);
 	}
 
 	void HandleDrawManager::drawSphere(const Vector3& position, float radius, float size)
 	{
-		Matrix4 scale(Vector3::ZERO, Quaternion::IDENTITY, Vector3(size, size, size));
-		mDrawHelper->setTransform(scale * mTransform);
+		Matrix4 scale = Matrix4::scaling(size);
+		mDrawHelper->setTransform(mTransform * scale);
 
 		mDrawHelper->sphere(position, radius);
 	}
 
 	void HandleDrawManager::drawWireCube(const Vector3& position, const Vector3& extents, float size)
 	{
-		Matrix4 scale(Vector3::ZERO, Quaternion::IDENTITY, Vector3(size, size, size));
-		mDrawHelper->setTransform(scale * mTransform);
+		Matrix4 scale = Matrix4::scaling(size);
+		mDrawHelper->setTransform(mTransform * scale);
 
 		mDrawHelper->wireCube(position, extents);
 	}
 
 	void HandleDrawManager::drawWireSphere(const Vector3& position, float radius, float size)
 	{
-		Matrix4 scale(Vector3::ZERO, Quaternion::IDENTITY, Vector3(size, size, size));
-		mDrawHelper->setTransform(scale * mTransform);
+		Matrix4 scale = Matrix4::scaling(size);
+		mDrawHelper->setTransform(mTransform * scale);
 
 		mDrawHelper->wireSphere(position, radius);
 	}
 
 	void HandleDrawManager::drawCone(const Vector3& base, const Vector3& normal, float height, float radius, float size)
 	{
-		Matrix4 scale(Vector3::ZERO, Quaternion::IDENTITY, Vector3(size, size, size));
-		mDrawHelper->setTransform(scale * mTransform);
+		Matrix4 scale = Matrix4::scaling(size);
 
+		mDrawHelper->setTransform(mTransform * scale);
 		mDrawHelper->cone(base, normal, height, radius);
 	}
 
 	void HandleDrawManager::drawLine(const Vector3& start, const Vector3& end, float size)
 	{
-		Matrix4 scale(Vector3::ZERO, Quaternion::IDENTITY, Vector3(size, size, size));
-		mDrawHelper->setTransform(scale * mTransform);
+		Matrix4 scale = Matrix4::scaling(size);
+		mDrawHelper->setTransform(mTransform * scale);
 
 		mDrawHelper->line(start, end);
 	}
 
 	void HandleDrawManager::drawDisc(const Vector3& position, const Vector3& normal, float radius, float size)
 	{
-		Matrix4 scale(Vector3::ZERO, Quaternion::IDENTITY, Vector3(size, size, size));
-		mDrawHelper->setTransform(scale * mTransform);
+		Matrix4 scale = Matrix4::scaling(size);
+		mDrawHelper->setTransform(mTransform * scale);
 
 		mDrawHelper->disc(position, normal, radius);
 	}
 
 	void HandleDrawManager::drawWireDisc(const Vector3& position, const Vector3& normal, float radius, float size)
 	{
-		Matrix4 scale(Vector3::ZERO, Quaternion::IDENTITY, Vector3(size, size, size));
-		mDrawHelper->setTransform(scale * mTransform);
+		Matrix4 scale = Matrix4::scaling(size);
+		mDrawHelper->setTransform(mTransform * scale);
 
 		mDrawHelper->wireDisc(position, normal, radius);
 	}
 
 	void HandleDrawManager::drawArc(const Vector3& position, const Vector3& normal, float radius, Degree startAngle, Degree amountAngle, float size)
 	{
-		Matrix4 scale(Vector3::ZERO, Quaternion::IDENTITY, Vector3(size, size, size));
-		mDrawHelper->setTransform(scale * mTransform);
+		Matrix4 scale = Matrix4::scaling(size);
+		mDrawHelper->setTransform(mTransform * scale);
 
 		mDrawHelper->arc(position, normal, radius, startAngle, amountAngle);
 	}
 
 	void HandleDrawManager::drawWireArc(const Vector3& position, const Vector3& normal, float radius, Degree startAngle, Degree amountAngle, float size)
 	{
-		Matrix4 scale(Vector3::ZERO, Quaternion::IDENTITY, Vector3(size, size, size));
-		mDrawHelper->setTransform(scale * mTransform);
+		Matrix4 scale = Matrix4::scaling(size);
+		mDrawHelper->setTransform(mTransform * scale);
 
 		mDrawHelper->wireArc(position, normal, radius, startAngle, amountAngle);
 	}
 
 	void HandleDrawManager::drawRect(const Rect3& area, float size)
 	{
-		Matrix4 scale(Vector3::ZERO, Quaternion::IDENTITY, Vector3(size, size, size));
-		mDrawHelper->setTransform(scale * mTransform);
+		Matrix4 scale = Matrix4::scaling(size);
+		mDrawHelper->setTransform(mTransform * scale);
 
 		mDrawHelper->rectangle(area);
 	}

+ 10 - 1
BansheeEditor/Source/BsHandleSlider.cpp

@@ -14,7 +14,10 @@ namespace BansheeEngine
 	void HandleSlider::update(const CameraHandlerPtr& camera)
 	{
 		if (mFixedScale)
+		{
 			mDistanceScale = HandleManager::instance().getHandleSize(camera, mPosition);
+			mTransformDirty = true;
+		}
 	}
 
 	void HandleSlider::setPosition(const Vector3& position)
@@ -54,11 +57,17 @@ namespace BansheeEngine
 	void HandleSlider::updateCachedTransform() const
 	{
 		if (mFixedScale)
+		{
 			mTransform.setTRS(mPosition, mRotation, mScale * mDistanceScale);
+			mTransformInv.setInverseTRS(mPosition, mRotation, mScale * mDistanceScale);
+		}
 		else
+		{
 			mTransform.setTRS(mPosition, mRotation, mScale);
+			mTransformInv.setInverseTRS(mPosition, mRotation, mScale);
+		}
 
-		mTransformInv = mTransform.inverseAffine();
+		//mTransformInv = mTransform.inverseAffine();
 		mTransformDirty = false;
 	}
 

+ 13 - 2
BansheeEditor/Source/BsHandleSliderLine.cpp

@@ -6,6 +6,8 @@
 #include "BsSphere.h"
 #include "BsRay.h"
 
+#include "BsDebug.h"
+
 namespace BansheeEngine
 {
 	const float HandleSliderLine::CAPSULE_RADIUS = 0.05f;
@@ -37,7 +39,7 @@ namespace BansheeEngine
 	bool HandleSliderLine::intersects(const Ray& ray, float& t) const
 	{
 		Ray localRay = ray;
-		localRay.transform(getTransformInv());
+		localRay.transformAffine(getTransformInv());
 
 		auto capsuleIntersect = mCapsuleCollider.intersects(localRay);
 		auto sphereIntersect = mSphereCollider.intersects(localRay);
@@ -60,6 +62,13 @@ namespace BansheeEngine
 			}
 		}
 
+		if (gotIntersect)
+		{
+			Vector3 intrPoint = localRay.getPoint(t);
+			intrPoint = getTransform().multiplyAffine(intrPoint);
+			t = (intrPoint - ray.getOrigin()).length(); // Get distance in world space
+		}
+
 		return gotIntersect;
 	}
 
@@ -68,6 +77,8 @@ namespace BansheeEngine
 		assert(getState() == State::Active);
 
 		mCurrentPointerPos += inputDelta;
-		mDelta = calcDelta(camera, mStartPosition, getTransform().multiplyAffine(mDirection), mStartPointerPos, mCurrentPointerPos);
+
+		Vector3 worldDir = getRotation().rotate(mDirection);
+		mDelta = calcDelta(camera, mStartPosition, worldDir, mStartPointerPos, mCurrentPointerPos);
 	}
 }

+ 25 - 10
BansheeEditor/Source/BsSceneViewHandler.cpp

@@ -13,6 +13,8 @@
 #include "BsRenderWindow.h"
 #include "BsCursor.h"
 
+#include "BsDebug.h"
+
 using namespace std::placeholders;
 
 namespace BansheeEngine
@@ -35,16 +37,24 @@ namespace BansheeEngine
 			GizmoManager::instance().clearRenderData();
 	}
 
-	void SceneViewHandler::update(const Vector2I& position, const Vector2I& delta)
+	void SceneViewHandler::update()
 	{
-		if (HandleManager::instance().isHandleActive())
-			wrapCursorToWindow();
-
 		GizmoManager::instance().update(mCamera);
-		HandleManager::instance().update(mCamera, position, delta);
 		mSceneGrid->update();
 	}
 
+	void SceneViewHandler::updateHandle(const Vector2I& position, const Vector2I& delta)
+	{
+		// If mouse wrapped around last frame then we need to compensate for the jump amount
+		Vector2I realDelta = delta - mMouseDeltaCompensate;
+		mMouseDeltaCompensate = Vector2I::ZERO;
+
+		if (HandleManager::instance().isHandleActive())
+			mMouseDeltaCompensate = wrapCursorToWindow();
+
+		HandleManager::instance().update(mCamera, position, realDelta);
+	}
+
 	void SceneViewHandler::trySelectHandle(const Vector2I& position)
 	{
 		HandleManager::instance().trySelect(mCamera, position);
@@ -102,24 +112,29 @@ namespace BansheeEngine
 		mSceneGrid->render(mCamera, drawList);
 	}
 
-	void SceneViewHandler::wrapCursorToWindow()
+	Vector2I SceneViewHandler::wrapCursorToWindow()
 	{
 		RenderWindowPtr parentWindow = mParentWidget->getParentWindow()->_getRenderWindow();
 
 		Vector2I windowPos = parentWindow->screenToWindowPos(Cursor::instance().getScreenPosition());
 		const RenderWindowProperties& rwProps = parentWindow->getProperties();
 
+		Vector2I offset;
 		if (windowPos.x < 0)
-			windowPos.x += rwProps.getWidth();
+			offset.x = (INT32)rwProps.getWidth();
 		else if (windowPos.x >= (INT32)rwProps.getWidth())
-			windowPos.x -= rwProps.getWidth();
+			offset.x = -(INT32)rwProps.getWidth();
 
 		if (windowPos.y < 0)
-			windowPos.y += rwProps.getHeight();
+			offset.y = (INT32)rwProps.getHeight();
 		else if (windowPos.y >= (INT32)rwProps.getHeight())
-			windowPos.y -= rwProps.getHeight();
+			offset.y = -(INT32)rwProps.getHeight();
 
+		windowPos += offset;
+		
 		Vector2I wrappedScreenPos = parentWindow->windowToScreenPos(windowPos);
 		Cursor::instance().setScreenPosition(wrappedScreenPos);
+
+		return offset;
 	}
 }

+ 34 - 8
BansheeUtility/Include/BsMatrix4.h

@@ -65,14 +65,6 @@ namespace BansheeEngine
 			m[3][0] = 0.0f; m[3][1] = 0.0f; m[3][2] = 0.0f; m[3][3] = 1.0f;
         }
 
-        /**
-         * @brief	Creates a 4x4 transformation matrix with translation, rotation and scale.
-         */
-        Matrix4(const Vector3& translation, const Quaternion& rot, const Vector3& scale)
-        {
-			setTRS(translation, rot, scale);
-        }
-        
 		/**
 		 * @brief	Swaps the contents of this matrix with another.
 		 */
@@ -445,6 +437,40 @@ namespace BansheeEngine
 		 */
 		void makeProjectionOrtho(float left, float right, float top, float bottom, float near, float far);
 
+		/**
+		 * @brief	Creates a 4x4 transformation matrix that performs translation.
+		 */
+		static Matrix4 translation(const Vector3& translation);
+
+		/**
+		 * @brief	Creates a 4x4 transformation matrix that performs scaling.
+		 */
+		static Matrix4 scaling(const Vector3& scale);
+
+		/**
+		 * @brief	Creates a 4x4 transformation matrix that performs uniform scaling.
+		 */
+		static Matrix4 scaling(float scale);
+
+		/**
+		 * @brief	Creates a 4x4 transformation matrix that performs rotation.
+		 */
+		static Matrix4 rotation(const Quaternion& rotation);
+
+        /**
+         * @brief	Creates a matrix from translation, rotation and scale. 
+         * 			
+		 * @note	The transformation are applied in scale->rotation->translation order.
+         */
+		static Matrix4 TRS(const Vector3& translation, const Quaternion& rotation, const Vector3& scale);
+
+        /**
+         * @brief	Creates a matrix from inverse translation, rotation and scale. 
+         * 			
+		 * @note	This is cheaper than "setTRS" and then performing "inverse".
+         */
+		static Matrix4 inverseTRS(const Vector3& translation, const Quaternion& rotation, const Vector3& scale);
+
 		static const Matrix4 ZERO;
 		static const Matrix4 IDENTITY;
     };

+ 14 - 0
BansheeUtility/Include/BsString.h

@@ -505,6 +505,13 @@ namespace BansheeEngine
      */
     BS_UTILITY_EXPORT WString toWString(const Vector2& val);
 
+    /**
+     * @brief	Converts a 2 dimensional integer vector to a string.
+     * 			
+	 * @note	Format is "x y".
+     */
+    BS_UTILITY_EXPORT WString toWString(const Vector2I& val);
+
     /**
      * @brief	Converts a 3 dimensional vector to a string.
      * 			
@@ -629,6 +636,13 @@ namespace BansheeEngine
      */
     BS_UTILITY_EXPORT String toString(const Vector2& val);
 
+    /**
+     * @brief	Converts a 2 dimensional integer vector to a string.
+     * 			
+	 * @note	Format is "x y".
+     */
+    BS_UTILITY_EXPORT String toString(const Vector2I& val);
+
     /**
      * @brief	Converts a 3 dimensional vector to a string.
      * 			

+ 2 - 0
BansheeUtility/Include/BsVector2I.h

@@ -199,5 +199,7 @@ namespace BansheeEngine
         {
             return x * vec.x + y * vec.y;
         }
+
+		static const Vector2I ZERO;
 	};
 }

+ 2 - 0
BansheeUtility/Include/BsVector3.h

@@ -22,6 +22,8 @@ namespace BansheeEngine
             :x(x), y(y), z(z)
         { }
 
+		explicit Vector3(const Vector4& vec);
+
 		/**
 		 * @brief	Exchange the contents of this vector with another.
 		 */

+ 2 - 2
BansheeUtility/Include/BsVector4.h

@@ -22,8 +22,8 @@ namespace BansheeEngine
             :x(x), y(y), z(z), w(w)
         { }
 
-		explicit Vector4(const Vector3& vec)
-			:x(vec.x), y(vec.y), z(vec.z), w(0.0f)
+		explicit Vector4(const Vector3& vec, float w = 0.0f)
+			:x(vec.x), y(vec.y), z(vec.z), w(w)
 		{ }
 
 		/**

+ 60 - 0
BansheeUtility/Source/BsMatrix4.cpp

@@ -278,4 +278,64 @@ namespace BansheeEngine
 		m[3][2] = 0.0f;
 		m[3][3] = 1.0f;
 	}
+
+	Matrix4 Matrix4::translation(const Vector3& translation)
+	{
+		Matrix4 mat;
+
+		mat[0][0] = 1.0f; mat[0][1] = 0.0f; mat[0][2] = 0.0f; mat[0][3] = translation.x;
+		mat[1][0] = 0.0f; mat[1][1] = 1.0f; mat[1][2] = 0.0f; mat[1][3] = translation.y;
+		mat[2][0] = 0.0f; mat[2][1] = 0.0f; mat[2][2] = 1.0f; mat[2][3] = translation.z;
+		mat[3][0] = 0.0f; mat[3][1] = 0.0f; mat[3][2] = 0.0f; mat[3][3] = 1.0f;
+
+		return mat;
+	}
+
+	Matrix4 Matrix4::scaling(const Vector3& scale)
+	{
+		Matrix4 mat;
+
+		mat[0][0] = scale.x; mat[0][1] = 0.0f; mat[0][2] = 0.0f; mat[0][3] = 0.0f;
+		mat[1][0] = 0.0f; mat[1][1] = scale.y; mat[1][2] = 0.0f; mat[1][3] = 0.0f;
+		mat[2][0] = 0.0f; mat[2][1] = 0.0f; mat[2][2] = scale.z; mat[2][3] = 0.0f;
+		mat[3][0] = 0.0f; mat[3][1] = 0.0f; mat[3][2] = 0.0f; mat[3][3] = 1.0f;
+
+		return mat;
+	}
+
+	Matrix4 Matrix4::scaling(float scale)
+	{
+		Matrix4 mat;
+
+		mat[0][0] = scale; mat[0][1] = 0.0f; mat[0][2] = 0.0f; mat[0][3] = 0.0f;
+		mat[1][0] = 0.0f; mat[1][1] = scale; mat[1][2] = 0.0f; mat[1][3] = 0.0f;
+		mat[2][0] = 0.0f; mat[2][1] = 0.0f; mat[2][2] = scale; mat[2][3] = 0.0f;
+		mat[3][0] = 0.0f; mat[3][1] = 0.0f; mat[3][2] = 0.0f; mat[3][3] = 1.0f;
+
+		return mat;
+	}
+
+	Matrix4 Matrix4::rotation(const Quaternion& rotation)
+	{
+		Matrix3 mat;
+		rotation.toRotationMatrix(mat);
+
+		return Matrix4(mat);
+	}
+
+	Matrix4 Matrix4::TRS(const Vector3& translation, const Quaternion& rotation, const Vector3& scale)
+	{
+		Matrix4 mat;
+		mat.setTRS(translation, rotation, scale);
+
+		return mat;
+	}
+
+	Matrix4 Matrix4::inverseTRS(const Vector3& translation, const Quaternion& rotation, const Vector3& scale)
+	{
+		Matrix4 mat;
+		mat.setInverseTRS(translation, rotation, scale);
+
+		return mat;
+	}
 }

+ 15 - 0
BansheeUtility/Source/BsString.cpp

@@ -6,6 +6,7 @@
 #include "BsVector2.h"
 #include "BsVector3.h"
 #include "BsVector4.h"
+#include "BsVector2I.h"
 #include "BsException.h"
 
 namespace BansheeEngine 
@@ -265,6 +266,13 @@ namespace BansheeEngine
 		return stream.str();
 	}
 
+	WString toWString(const Vector2I& val)
+	{
+		WStringStream stream;
+		stream << val.x << L" " << val.y;
+		return stream.str();
+	}
+
 	WString toWString(const Vector3& val)
 	{
 		WStringStream stream;
@@ -489,6 +497,13 @@ namespace BansheeEngine
 		return stream.str();
 	}
 
+	String toString(const Vector2I& val)
+	{
+		StringStream stream;
+		stream << val.x << " " << val.y;
+		return stream.str();
+	}
+
 	String toString(const Vector3& val)
 	{
 		StringStream stream;

+ 6 - 1
BansheeUtility/Source/BsVector2I.cpp

@@ -1 +1,6 @@
-#include "BsVector2I.h"
+#include "BsVector2I.h"
+
+namespace BansheeEngine
+{
+	const Vector2I Vector2I::ZERO(0, 0);
+}

+ 7 - 0
BansheeUtility/Source/BsVector3.cpp

@@ -1,8 +1,15 @@
 #include "BsVector3.h"
 #include "BsMath.h"
+#include "BsVector4.h"
 
 namespace BansheeEngine
 {
+	Vector3::Vector3(const Vector4& vec)
+		:x(vec.x), y(vec.y), z(vec.z)
+	{
+
+	}
+
     const Vector3 Vector3::ZERO(0, 0, 0);
 	const Vector3 Vector3::ONE(1, 1, 1);
 	const Vector3 Vector3::INF =

+ 10 - 10
MBansheeEditor/Scene/MoveHandle.cs

@@ -63,10 +63,7 @@ namespace BansheeEditor
 
         protected override void Draw()
         {
-            Vector3 center = position;
-            Vector3 xEnd = center + GetXDir();
-            Vector3 yEnd = center + GetYDir();
-            Vector3 zEnd = center + GetZDir();
+            HandleDrawing.SetTransform(Matrix4.TRS(Position, Rotation, Vector3.one));
 
             if (xAxis.State == HandleSlider.StateType.Active)
                 HandleDrawing.SetColor(Color.white);
@@ -77,8 +74,9 @@ namespace BansheeEditor
 
             float handleSize = Handles.GetHandleSize(EditorApplication.SceneViewCamera, position);
 
-            HandleDrawing.DrawLine(center, xEnd - GetXDir() * CONE_HEIGHT, handleSize);
-            HandleDrawing.DrawCone(xEnd - GetXDir() * CONE_HEIGHT, GetXDir(), CONE_HEIGHT, CONE_RADIUS, handleSize);
+            Vector3 xConeStart = Vector3.xAxis*(1.0f - CONE_HEIGHT);
+            HandleDrawing.DrawLine(Vector3.zero, xConeStart, handleSize);
+            HandleDrawing.DrawCone(xConeStart, Vector3.xAxis, CONE_HEIGHT, CONE_RADIUS, handleSize);
 
             if (yAxis.State == HandleSlider.StateType.Active)
                 HandleDrawing.SetColor(Color.white);
@@ -87,8 +85,9 @@ namespace BansheeEditor
             else
                 HandleDrawing.SetColor(Color.green);
 
-            HandleDrawing.DrawLine(center, yEnd - GetYDir() * CONE_HEIGHT, handleSize);
-            HandleDrawing.DrawCone(yEnd - GetYDir() * CONE_HEIGHT, GetYDir(), CONE_HEIGHT, CONE_RADIUS, handleSize);
+            Vector3 yConeStart = Vector3.yAxis * (1.0f - CONE_HEIGHT);
+            HandleDrawing.DrawLine(Vector3.zero, yConeStart, handleSize);
+            HandleDrawing.DrawCone(yConeStart, Vector3.yAxis, CONE_HEIGHT, CONE_RADIUS, handleSize);
 
             if (zAxis.State == HandleSlider.StateType.Active)
                 HandleDrawing.SetColor(Color.white);
@@ -97,8 +96,9 @@ namespace BansheeEditor
             else
                 HandleDrawing.SetColor(Color.blue);
 
-            HandleDrawing.DrawLine(center, zEnd - GetZDir() * CONE_HEIGHT, handleSize);
-            HandleDrawing.DrawCone(zEnd - GetZDir() * CONE_HEIGHT, GetZDir(), CONE_HEIGHT, CONE_RADIUS, handleSize);
+            Vector3 zConeStart = Vector3.zAxis * (1.0f - CONE_HEIGHT);
+            HandleDrawing.DrawLine(Vector3.zero, zConeStart, handleSize);
+            HandleDrawing.DrawCone(zConeStart, Vector3.zAxis, CONE_HEIGHT, CONE_RADIUS, handleSize);
         }
 
         private Vector3 GetXDir()

+ 11 - 3
MBansheeEditor/Scene/SceneViewHandler.cs

@@ -15,9 +15,14 @@ namespace BansheeEditor
             Internal_Create(this, parent.GetCachedPtr(), sceneCamera.Handler.GetCachedPtr());
         }
 
-        internal void Update(Vector2I pointerPos, Vector2I inputDelta)
+        internal void Update()
         {
-            Internal_Update(mCachedPtr, pointerPos, inputDelta);
+            Internal_Update(mCachedPtr);
+        }
+
+        internal void UpdateHandle(Vector2I pointerPos, Vector2I inputDelta)
+        {
+            Internal_UpdateHandle(mCachedPtr, pointerPos, inputDelta);
         }
 
         internal void TrySelectHandle(Vector2I pointerPos)
@@ -44,7 +49,10 @@ namespace BansheeEditor
         private static extern void Internal_Create(SceneViewHandler managedInstance, IntPtr parentWindow, IntPtr camera);
 
         [MethodImpl(MethodImplOptions.InternalCall)]
-        private static extern void Internal_Update(IntPtr thisPtr, Vector2I pointerPos, Vector2I inputDelta);
+        private static extern void Internal_Update(IntPtr thisPtr);
+
+        [MethodImpl(MethodImplOptions.InternalCall)]
+        private static extern void Internal_UpdateHandle(IntPtr thisPtr, Vector2I pointerPos, Vector2I inputDelta);
 
         [MethodImpl(MethodImplOptions.InternalCall)]
         private static extern void Internal_TrySelectHandle(IntPtr thisPtr, Vector2I pointerPos);

+ 3 - 2
MBansheeEditor/Scene/SceneWindow.cs

@@ -46,13 +46,14 @@ namespace BansheeEditor
 
         private void EditorUpdate()
         {
+            sceneViewHandler.Update();
+
             if (!HasFocus)
                 return;
 
             Vector2I scenePos;
             if (ScreenToScenePos(Input.PointerPosition, out scenePos))
             {
-                Debug.Log(scenePos);
                 if (Input.IsButtonDown(ButtonCode.MouseLeft))
                 {
                     sceneViewHandler.TrySelectHandle(scenePos);
@@ -68,7 +69,7 @@ namespace BansheeEditor
                         sceneViewHandler.PickObject(scenePos, ctrlHeld);
                 }
 
-                sceneViewHandler.Update(scenePos, Input.PointerDelta);
+                sceneViewHandler.UpdateHandle(scenePos, Input.PointerDelta);
             }
         }
 

+ 2 - 1
SBansheeEditor/Include/BsScriptSceneViewHandler.h

@@ -12,7 +12,8 @@ namespace BansheeEngine
 
 	private:
 		static void internal_Create(MonoObject* managedInstance, ScriptEditorWindow* parentWindow, ScriptCameraHandler* camera);
-		static void internal_Update(ScriptSceneViewHandler* thisPtr, Vector2I inputPos, Vector2I inputDelta);
+		static void internal_Update(ScriptSceneViewHandler* thisPtr);
+		static void internal_UpdateHandle(ScriptSceneViewHandler* thisPtr, Vector2I inputPos, Vector2I inputDelta);
 		static void internal_TrySelectHandle(ScriptSceneViewHandler* thisPtr, Vector2I inputPos);
 		static bool internal_IsHandleActive(ScriptSceneViewHandler* thisPtr, Vector2I inputPos);
 		static void internal_ClearHandleSelection(ScriptSceneViewHandler* thisPtr, Vector2I inputPos);

+ 8 - 2
SBansheeEditor/Source/BsScriptSceneViewHandler.cpp

@@ -25,6 +25,7 @@ namespace BansheeEngine
 	{
 		metaData.scriptClass->addInternalCall("Internal_Create", &ScriptSceneViewHandler::internal_Create);
 		metaData.scriptClass->addInternalCall("Internal_Update", &ScriptSceneViewHandler::internal_Update);
+		metaData.scriptClass->addInternalCall("Internal_UpdateHandle", &ScriptSceneViewHandler::internal_UpdateHandle);
 		metaData.scriptClass->addInternalCall("Internal_TrySelectHandle", &ScriptSceneViewHandler::internal_TrySelectHandle);
 		metaData.scriptClass->addInternalCall("Internal_IsHandleActive", &ScriptSceneViewHandler::internal_IsHandleActive);
 		metaData.scriptClass->addInternalCall("Internal_ClearHandleSelection", &ScriptSceneViewHandler::internal_ClearHandleSelection);
@@ -38,9 +39,14 @@ namespace BansheeEngine
 		new (bs_alloc<ScriptSceneViewHandler>()) ScriptSceneViewHandler(managedInstance, widget, camera->getInternal());
 	}
 
-	void ScriptSceneViewHandler::internal_Update(ScriptSceneViewHandler* thisPtr, Vector2I inputPos, Vector2I inputDelta)
+	void ScriptSceneViewHandler::internal_Update(ScriptSceneViewHandler* thisPtr)
 	{
-		thisPtr->mHandler->update(inputPos, inputDelta);
+		thisPtr->mHandler->update();
+	}
+
+	void ScriptSceneViewHandler::internal_UpdateHandle(ScriptSceneViewHandler* thisPtr, Vector2I inputPos, Vector2I inputDelta)
+	{
+		thisPtr->mHandler->updateHandle(inputPos, inputDelta);
 	}
 
 	void ScriptSceneViewHandler::internal_TrySelectHandle(ScriptSceneViewHandler* thisPtr, Vector2I inputPos)

+ 5 - 7
TODO.txt

@@ -12,19 +12,17 @@
 
 See GDrive/Resources doc for resources refactor
 
-Handle lines don't draw in front of geometry
-I think mouse delta isn't properly reset between mouse movement
-Gizmos don't start rendering until you click on screen
+Slider colliders are not valid after handle moves
+ - Caused by distance scaling
+Wrapping the cursor causes mouse delta to be huge. I need to compensate.
+Don't forget to update mDirection calculations for all slider types
 
 I can get mono errors by checking g_print calls in goutput.c
-
-Icon gizmo seems to sometimes get struck to the side of the camera
+ - Calling thunks incorrectly can cause those weird errors with no real callstack
 
 Other:
 Window resize end callback
-
 Add cutoff plane when rendering discs for rotation handle.
-
 What happens when I close widgets from C++ code (e.g. due to layout reload or change)? Will C# still try to access them?
 
 C# SceneView: