2012-03-20 01:57:42 +01:00
|
|
|
#include "lc_global.h"
|
2020-12-25 19:43:22 +01:00
|
|
|
#include "lc_view.h"
|
2020-12-27 22:05:55 +01:00
|
|
|
#include "lc_viewwidget.h"
|
2011-09-07 23:06:51 +02:00
|
|
|
#include <stdlib.h>
|
2014-05-03 23:16:48 +02:00
|
|
|
#include "lc_mainwindow.h"
|
2012-08-20 06:05:56 +02:00
|
|
|
#include "camera.h"
|
2014-05-18 01:03:05 +02:00
|
|
|
#include "texfont.h"
|
2014-08-24 00:56:59 +02:00
|
|
|
#include "lc_texture.h"
|
2014-11-29 03:55:58 +01:00
|
|
|
#include "piece.h"
|
2014-10-10 03:25:31 +02:00
|
|
|
#include "pieceinf.h"
|
2016-05-01 02:20:37 +02:00
|
|
|
#include "lc_synth.h"
|
2020-12-05 20:02:10 +01:00
|
|
|
#include "lc_scene.h"
|
2020-12-16 03:47:58 +01:00
|
|
|
#include "lc_context.h"
|
|
|
|
#include "lc_viewsphere.h"
|
2011-09-07 23:06:51 +02:00
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcView* lcView::mLastFocusedView;
|
|
|
|
std::vector<lcView*> lcView::mViews;
|
2020-12-25 19:37:59 +01:00
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcVertexBuffer lcView::mRotateMoveVertexBuffer;
|
|
|
|
lcIndexBuffer lcView::mRotateMoveIndexBuffer;
|
2015-04-27 02:47:31 +02:00
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcView::lcView(lcViewType ViewType, lcModel* Model)
|
2020-12-26 20:09:15 +01:00
|
|
|
: mViewType(ViewType), mScene(new lcScene()), mModel(Model)
|
2011-09-07 23:06:51 +02:00
|
|
|
{
|
2020-12-25 19:37:59 +01:00
|
|
|
mContext = new lcContext();
|
|
|
|
mViews.push_back(this);
|
|
|
|
|
2020-12-16 03:47:58 +01:00
|
|
|
mViewSphere = std::unique_ptr<lcViewSphere>(new lcViewSphere(this));
|
2015-04-14 06:14:10 +02:00
|
|
|
memset(mGridSettings, 0, sizeof(mGridSettings));
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-02-15 20:36:06 +01:00
|
|
|
mDragState = lcDragState::None;
|
2018-02-06 23:47:11 +01:00
|
|
|
mTrackToolFromOverlay = false;
|
2013-08-09 06:57:18 +02:00
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcView* ActiveView = gMainWindow->GetActiveView();
|
2014-05-03 23:16:48 +02:00
|
|
|
if (ActiveView)
|
|
|
|
SetCamera(ActiveView->mCamera, false);
|
2013-08-09 06:57:18 +02:00
|
|
|
else
|
|
|
|
SetDefaultCamera();
|
2011-09-07 23:06:51 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcView::~lcView()
|
2011-09-07 23:06:51 +02:00
|
|
|
{
|
2015-04-26 20:14:33 +02:00
|
|
|
mContext->DestroyVertexBuffer(mGridBuffer);
|
2015-04-14 06:14:10 +02:00
|
|
|
|
2020-12-24 20:32:56 +01:00
|
|
|
if (gMainWindow && mViewType == lcViewType::View)
|
2014-05-03 23:16:48 +02:00
|
|
|
gMainWindow->RemoveView(this);
|
2012-08-22 03:13:32 +02:00
|
|
|
|
2016-03-06 02:47:00 +01:00
|
|
|
if (mCamera && mCamera->IsSimple())
|
|
|
|
delete mCamera;
|
2020-12-25 19:37:59 +01:00
|
|
|
|
|
|
|
mViews.erase(std::find(mViews.begin(), mViews.end(), this));
|
|
|
|
|
|
|
|
if (mLastFocusedView == this)
|
|
|
|
mLastFocusedView = nullptr;
|
|
|
|
|
|
|
|
if (mDeleteContext)
|
|
|
|
delete mContext;
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::UpdateProjectViews(const Project* Project)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
2020-12-25 19:54:33 +01:00
|
|
|
for (lcView* View : mViews)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
const lcModel* ViewModel = View->GetActiveModel();
|
|
|
|
|
2020-12-29 02:30:41 +01:00
|
|
|
if (ViewModel && ViewModel->GetProject() == Project)
|
2020-12-25 19:37:59 +01:00
|
|
|
View->Redraw();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::UpdateAllViews()
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
2020-12-25 19:54:33 +01:00
|
|
|
for (lcView* View : mViews)
|
2020-12-25 19:37:59 +01:00
|
|
|
View->Redraw();
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::MakeCurrent()
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
2020-12-29 02:30:41 +01:00
|
|
|
if (mWidget)
|
|
|
|
mWidget->makeCurrent();
|
|
|
|
#ifdef LC_USE_QOPENGLWIDGET
|
|
|
|
else if (mOffscreenContext)
|
|
|
|
mOffscreenContext->makeCurrent(mOffscreenSurface.get());
|
|
|
|
#endif
|
2020-12-25 19:37:59 +01:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::Redraw()
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
2020-12-29 02:30:41 +01:00
|
|
|
if (mWidget)
|
|
|
|
mWidget->update();
|
2020-12-25 19:37:59 +01:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetContext(lcContext* Context)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
if (mDeleteContext)
|
|
|
|
delete mContext;
|
|
|
|
|
|
|
|
mContext = Context;
|
|
|
|
mDeleteContext = false;
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetFocus(bool Focus)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
if (Focus)
|
|
|
|
{
|
|
|
|
mLastFocusedView = this;
|
|
|
|
|
|
|
|
emit FocusReceived();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetMousePosition(int MouseX, int MouseY)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
mMouseX = MouseX;
|
|
|
|
mMouseY = MouseY;
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetMouseModifiers(Qt::KeyboardModifiers MouseModifiers)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
mMouseModifiers = MouseModifiers;
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcModel* lcView::GetActiveModel() const
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
return !mActiveSubmodelInstance ? mModel : mActiveSubmodelInstance->mPieceInfo->GetModel();
|
2011-09-07 23:06:51 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetTopSubmodelActive()
|
2018-10-14 01:45:14 +02:00
|
|
|
{
|
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
|
|
|
|
if (mActiveSubmodelInstance)
|
|
|
|
{
|
|
|
|
ActiveModel->SetActive(false);
|
|
|
|
mActiveSubmodelInstance = nullptr;
|
|
|
|
}
|
|
|
|
|
|
|
|
GetActiveModel()->UpdateInterface();
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetSelectedSubmodelActive()
|
2018-03-29 19:20:36 +02:00
|
|
|
{
|
2018-04-08 00:49:03 +02:00
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
lcObject* Object = ActiveModel->GetFocusObject();
|
|
|
|
|
2018-03-29 19:20:36 +02:00
|
|
|
if (mActiveSubmodelInstance)
|
|
|
|
{
|
2018-04-08 03:45:44 +02:00
|
|
|
ActiveModel->SetActive(false);
|
2018-03-29 19:20:36 +02:00
|
|
|
mActiveSubmodelInstance = nullptr;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (Object && Object->IsPiece())
|
|
|
|
{
|
|
|
|
lcPiece* Piece = (lcPiece*)Object;
|
|
|
|
|
|
|
|
if (Piece->mPieceInfo->IsModel())
|
|
|
|
{
|
2018-04-08 02:17:32 +02:00
|
|
|
mActiveSubmodelTransform = lcMatrix44Identity();
|
|
|
|
mModel->GetPieceWorldMatrix(Piece, mActiveSubmodelTransform);
|
2018-03-29 19:20:36 +02:00
|
|
|
mActiveSubmodelInstance = Piece;
|
2018-04-08 03:45:44 +02:00
|
|
|
ActiveModel = mActiveSubmodelInstance->mPieceInfo->GetModel();
|
|
|
|
ActiveModel->SetActive(true);
|
2019-02-10 01:30:11 +01:00
|
|
|
RemoveCamera();
|
2018-03-29 19:20:36 +02:00
|
|
|
}
|
|
|
|
}
|
2018-04-08 03:45:44 +02:00
|
|
|
|
|
|
|
GetActiveModel()->UpdateInterface();
|
2018-03-29 19:20:36 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::CreateResources(lcContext* Context)
|
2015-04-27 02:47:31 +02:00
|
|
|
{
|
|
|
|
gGridTexture = new lcTexture;
|
|
|
|
gGridTexture->CreateGridTexture();
|
|
|
|
|
|
|
|
CreateSelectMoveOverlayMesh(Context);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::CreateSelectMoveOverlayMesh(lcContext* Context)
|
2015-04-27 02:47:31 +02:00
|
|
|
{
|
|
|
|
float Verts[(51 + 138 + 10) * 3];
|
|
|
|
float* CurVert = Verts;
|
|
|
|
|
|
|
|
const float OverlayMovePlaneSize = 0.5f;
|
|
|
|
const float OverlayMoveArrowSize = 1.5f;
|
|
|
|
const float OverlayMoveArrowCapSize = 0.9f;
|
|
|
|
const float OverlayMoveArrowCapRadius = 0.1f;
|
|
|
|
const float OverlayMoveArrowBodySize = 1.2f;
|
|
|
|
const float OverlayMoveArrowBodyRadius = 0.05f;
|
|
|
|
const float OverlayRotateArrowStart = 1.0f;
|
|
|
|
const float OverlayRotateArrowEnd = 1.5f;
|
|
|
|
const float OverlayRotateArrowCenter = 1.2f;
|
|
|
|
|
|
|
|
*CurVert++ = OverlayMoveArrowSize; *CurVert++ = 0.0f; *CurVert++ = 0.0f;
|
|
|
|
|
|
|
|
for (int EdgeIdx = 0; EdgeIdx < 8; EdgeIdx++)
|
|
|
|
{
|
|
|
|
*CurVert++ = OverlayMoveArrowCapSize;
|
|
|
|
*CurVert++ = cosf(LC_2PI * EdgeIdx / 8) * OverlayMoveArrowCapRadius;
|
|
|
|
*CurVert++ = sinf(LC_2PI * EdgeIdx / 8) * OverlayMoveArrowCapRadius;
|
|
|
|
}
|
|
|
|
|
|
|
|
*CurVert++ = 0.0f; *CurVert++ = -OverlayMoveArrowBodyRadius; *CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = 0.0f; *CurVert++ = OverlayMoveArrowBodyRadius; *CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = 0.0f; *CurVert++ = 0.0f; *CurVert++ = -OverlayMoveArrowBodyRadius;
|
|
|
|
*CurVert++ = 0.0f; *CurVert++ = 0.0f; *CurVert++ = OverlayMoveArrowBodyRadius;
|
|
|
|
*CurVert++ = OverlayMoveArrowBodySize; *CurVert++ = -OverlayMoveArrowBodyRadius; *CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = OverlayMoveArrowBodySize; *CurVert++ = OverlayMoveArrowBodyRadius; *CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = OverlayMoveArrowBodySize; *CurVert++ = 0.0f; *CurVert++ = -OverlayMoveArrowBodyRadius;
|
|
|
|
*CurVert++ = OverlayMoveArrowBodySize; *CurVert++ = 0.0f; *CurVert++ = OverlayMoveArrowBodyRadius;
|
|
|
|
|
|
|
|
for (int VertIdx = 0; VertIdx < 17; VertIdx++)
|
|
|
|
{
|
|
|
|
*CurVert = *(CurVert - 50); CurVert++;
|
|
|
|
*CurVert = *(CurVert - 52); CurVert++;
|
|
|
|
*CurVert = *(CurVert - 51); CurVert++;
|
|
|
|
}
|
|
|
|
|
|
|
|
for (int VertIdx = 0; VertIdx < 17; VertIdx++)
|
|
|
|
{
|
|
|
|
*CurVert = *(CurVert - 100); CurVert++;
|
|
|
|
*CurVert = *(CurVert - 102); CurVert++;
|
|
|
|
*CurVert = *(CurVert - 104); CurVert++;
|
|
|
|
}
|
|
|
|
|
|
|
|
*CurVert++ = 0.0f; *CurVert++ = OverlayRotateArrowEnd - OverlayMoveArrowCapRadius; *CurVert++ = OverlayRotateArrowStart;
|
|
|
|
|
|
|
|
for (int EdgeIdx = 0; EdgeIdx < 8; EdgeIdx++)
|
|
|
|
{
|
|
|
|
*CurVert++ = cosf(LC_2PI * EdgeIdx / 8) * OverlayMoveArrowCapRadius;
|
|
|
|
*CurVert++ = sinf(LC_2PI * EdgeIdx / 8) * OverlayMoveArrowCapRadius + OverlayRotateArrowEnd - OverlayMoveArrowCapRadius;
|
|
|
|
*CurVert++ = OverlayRotateArrowCenter;
|
|
|
|
}
|
|
|
|
|
|
|
|
*CurVert++ = 0.0f; *CurVert++ = OverlayRotateArrowStart; *CurVert++ = OverlayRotateArrowEnd - OverlayMoveArrowCapRadius;
|
|
|
|
|
|
|
|
for (int EdgeIdx = 0; EdgeIdx < 8; EdgeIdx++)
|
|
|
|
{
|
|
|
|
*CurVert++ = cosf(LC_2PI * EdgeIdx / 8) * OverlayMoveArrowCapRadius;
|
|
|
|
*CurVert++ = OverlayRotateArrowCenter;
|
|
|
|
*CurVert++ = sinf(LC_2PI * EdgeIdx / 8) * OverlayMoveArrowCapRadius + OverlayRotateArrowEnd - OverlayMoveArrowCapRadius;
|
|
|
|
}
|
|
|
|
|
|
|
|
for (int EdgeIdx = 0; EdgeIdx < 7; EdgeIdx++)
|
|
|
|
{
|
|
|
|
const float Radius1 = OverlayRotateArrowEnd - OverlayMoveArrowCapRadius - OverlayRotateArrowCenter - OverlayMoveArrowBodyRadius;
|
|
|
|
const float Radius2 = OverlayRotateArrowEnd - OverlayMoveArrowCapRadius - OverlayRotateArrowCenter + OverlayMoveArrowBodyRadius;
|
|
|
|
float x = cosf(LC_2PI / 4 * EdgeIdx / 6);
|
|
|
|
float y = sinf(LC_2PI / 4 * EdgeIdx / 6);
|
|
|
|
|
|
|
|
*CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = OverlayRotateArrowCenter + x * Radius1;
|
|
|
|
*CurVert++ = OverlayRotateArrowCenter + y * Radius1;
|
|
|
|
*CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = OverlayRotateArrowCenter + x * Radius2;
|
|
|
|
*CurVert++ = OverlayRotateArrowCenter + y * Radius2;
|
|
|
|
}
|
|
|
|
|
|
|
|
for (int EdgeIdx = 0; EdgeIdx < 7; EdgeIdx++)
|
|
|
|
{
|
|
|
|
const float Radius = OverlayRotateArrowEnd - OverlayMoveArrowCapRadius - OverlayRotateArrowCenter;
|
|
|
|
float x = cosf(LC_2PI / 4 * EdgeIdx / 6);
|
|
|
|
float y = sinf(LC_2PI / 4 * EdgeIdx / 6);
|
|
|
|
|
|
|
|
*CurVert++ = -OverlayMoveArrowBodyRadius;
|
|
|
|
*CurVert++ = OverlayRotateArrowCenter + x * Radius;
|
|
|
|
*CurVert++ = OverlayRotateArrowCenter + y * Radius;
|
|
|
|
*CurVert++ = OverlayMoveArrowBodyRadius;
|
|
|
|
*CurVert++ = OverlayRotateArrowCenter + x * Radius;
|
|
|
|
*CurVert++ = OverlayRotateArrowCenter + y * Radius;
|
|
|
|
}
|
|
|
|
|
|
|
|
for (int VertIdx = 0; VertIdx < 46; VertIdx++)
|
|
|
|
{
|
|
|
|
*CurVert = *(CurVert - 137); CurVert++;
|
|
|
|
*CurVert = *(CurVert - 139); CurVert++;
|
|
|
|
*CurVert = *(CurVert - 138); CurVert++;
|
|
|
|
}
|
|
|
|
|
|
|
|
for (int VertIdx = 0; VertIdx < 46; VertIdx++)
|
|
|
|
{
|
|
|
|
*CurVert = *(CurVert - 274); CurVert++;
|
|
|
|
*CurVert = *(CurVert - 276); CurVert++;
|
|
|
|
*CurVert = *(CurVert - 278); CurVert++;
|
|
|
|
}
|
|
|
|
|
|
|
|
*CurVert++ = 0.0f; *CurVert++ = 0.0f; *CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = 0.0f; *CurVert++ = OverlayMovePlaneSize; *CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = 0.0f; *CurVert++ = OverlayMovePlaneSize; *CurVert++ = OverlayMovePlaneSize;
|
|
|
|
*CurVert++ = 0.0f; *CurVert++ = 0.0f; *CurVert++ = OverlayMovePlaneSize;
|
|
|
|
*CurVert++ = OverlayMovePlaneSize; *CurVert++ = 0.0f; *CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = OverlayMovePlaneSize; *CurVert++ = 0.0f; *CurVert++ = OverlayMovePlaneSize;
|
|
|
|
*CurVert++ = 0.0f; *CurVert++ = 0.0f; *CurVert++ = OverlayMovePlaneSize;
|
|
|
|
*CurVert++ = 0.0f; *CurVert++ = OverlayMovePlaneSize; *CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = OverlayMovePlaneSize; *CurVert++ = OverlayMovePlaneSize; *CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = OverlayMovePlaneSize; *CurVert++ = 0.0f; *CurVert++ = 0.0f;
|
|
|
|
|
|
|
|
const GLushort Indices[108 + 360 + 12] =
|
|
|
|
{
|
|
|
|
0, 1, 2, 0, 2, 3, 0, 3, 4, 0, 4, 5, 0, 5, 6, 0, 6, 7, 0, 7, 8, 0, 8, 1,
|
|
|
|
9, 10, 14, 14, 13, 9, 11, 12, 15, 15, 16, 12,
|
|
|
|
17, 18, 19, 17, 19, 20, 17, 20, 21, 17, 21, 22, 17, 22, 23, 17, 23, 24, 17, 24, 25, 17, 25, 18,
|
|
|
|
26, 27, 31, 31, 30, 26, 28, 29, 32, 32, 33, 29,
|
|
|
|
34, 35, 36, 34, 36, 37, 34, 37, 38, 34, 38, 39, 34, 39, 40, 34, 40, 41, 34, 41, 42, 34, 42, 35,
|
|
|
|
43, 44, 48, 48, 47, 43, 45, 46, 49, 49, 50, 46,
|
|
|
|
51, 52, 53, 51, 53, 54, 51, 54, 55, 51, 55, 56, 51, 56, 57, 51, 57, 58, 51, 58, 59, 51, 59, 52,
|
|
|
|
60, 61, 62, 60, 62, 63, 60, 63, 64, 60, 64, 65, 60, 65, 66, 60, 66, 67, 60, 67, 68, 60, 68, 61,
|
|
|
|
69, 70, 71, 71, 72, 70, 71, 72, 73, 73, 74, 72, 73, 74, 75, 75, 76, 74, 75, 76, 77, 77, 78, 76, 77, 78, 79, 79, 80, 78, 79, 80, 81, 81, 82, 80,
|
|
|
|
83, 84, 85, 85, 86, 84, 85, 86, 87, 87, 88, 86, 87, 88, 89, 89, 90, 88, 89, 90, 91, 91, 92, 90, 91, 92, 93, 93, 94, 92, 93, 94, 95, 95, 96, 94,
|
|
|
|
97, 98, 99, 97, 99, 100, 97, 100, 101, 97, 101, 102, 97, 102, 103, 97, 103, 104, 97, 104, 105, 97, 105, 98,
|
|
|
|
106, 107, 108, 106, 108, 109, 106, 109, 110, 106, 110, 111, 106, 111, 112, 106, 112, 113, 106, 113, 114, 106, 114, 107,
|
|
|
|
115, 116, 117, 117, 118, 116, 117, 118, 119, 119, 120, 118, 119, 120, 121, 121, 122, 120, 121, 122, 123, 123, 124, 122, 123, 124, 125, 125, 126, 124, 125, 126, 127, 127, 128, 126,
|
|
|
|
129, 130, 131, 131, 132, 130, 131, 132, 133, 133, 134, 132, 133, 134, 135, 135, 136, 134, 135, 136, 137, 137, 138, 136, 137, 138, 139, 139, 140, 138, 139, 140, 141, 141, 142, 140,
|
|
|
|
143, 144, 145, 143, 145, 146, 143, 146, 147, 143, 147, 148, 143, 148, 149, 143, 149, 150, 143, 150, 151, 143, 151, 144,
|
|
|
|
152, 153, 154, 152, 154, 155, 152, 155, 156, 152, 156, 157, 152, 157, 158, 152, 158, 159, 152, 159, 160, 152, 160, 153,
|
|
|
|
161, 162, 163, 163, 164, 162, 163, 164, 165, 165, 166, 164, 165, 166, 167, 167, 168, 166, 167, 168, 169, 169, 170, 168, 169, 170, 171, 171, 172, 170, 171, 172, 173, 173, 174, 172,
|
|
|
|
175, 176, 177, 177, 178, 176, 177, 178, 179, 179, 180, 178, 179, 180, 181, 181, 182, 180, 181, 182, 183, 183, 184, 182, 183, 184, 185, 185, 186, 184, 185, 186, 187, 187, 188, 186,
|
|
|
|
189, 190, 191, 192, 189, 193, 194, 195, 189, 196, 197, 198
|
|
|
|
};
|
|
|
|
|
|
|
|
mRotateMoveVertexBuffer = Context->CreateVertexBuffer(sizeof(Verts), Verts);
|
|
|
|
mRotateMoveIndexBuffer = Context->CreateIndexBuffer(sizeof(Indices), Indices);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::DestroyResources(lcContext* Context)
|
2015-04-27 02:47:31 +02:00
|
|
|
{
|
|
|
|
delete gGridTexture;
|
2017-04-14 02:26:40 +02:00
|
|
|
gGridTexture = nullptr;
|
2015-04-27 02:47:31 +02:00
|
|
|
|
|
|
|
Context->DestroyVertexBuffer(mRotateMoveVertexBuffer);
|
|
|
|
Context->DestroyIndexBuffer(mRotateMoveIndexBuffer);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::RemoveCamera()
|
2014-11-25 01:51:34 +01:00
|
|
|
{
|
|
|
|
if (mCamera && mCamera->IsSimple())
|
|
|
|
return;
|
|
|
|
|
|
|
|
lcCamera* Camera = mCamera;
|
|
|
|
mCamera = new lcCamera(true);
|
|
|
|
|
|
|
|
if (Camera)
|
|
|
|
mCamera->CopyPosition(Camera);
|
2015-03-02 00:17:50 +01:00
|
|
|
else
|
2020-12-13 01:58:40 +01:00
|
|
|
mCamera->SetViewpoint(lcViewpoint::Home);
|
2015-03-02 00:17:50 +01:00
|
|
|
|
2020-12-13 19:33:42 +01:00
|
|
|
emit CameraChanged();
|
2014-11-25 01:51:34 +01:00
|
|
|
Redraw();
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcVector3 lcView::ProjectPoint(const lcVector3& Point) const
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
int Viewport[4] = { 0, 0, mWidth, mHeight };
|
|
|
|
return lcProjectPoint(Point, mCamera->mWorldView, GetProjectionMatrix(), Viewport);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcVector3 lcView::UnprojectPoint(const lcVector3& Point) const
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
int Viewport[4] = { 0, 0, mWidth, mHeight };
|
|
|
|
return lcUnprojectPoint(Point, mCamera->mWorldView, GetProjectionMatrix(), Viewport);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::UnprojectPoints(lcVector3* Points, int NumPoints) const
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
int Viewport[4] = { 0, 0, mWidth, mHeight };
|
|
|
|
lcUnprojectPoints(Points, NumPoints, mCamera->mWorldView, GetProjectionMatrix(), Viewport);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcMatrix44 lcView::GetProjectionMatrix() const
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
float AspectRatio = (float)mWidth / (float)mHeight;
|
|
|
|
|
|
|
|
if (mCamera->IsOrtho())
|
|
|
|
{
|
|
|
|
float OrthoHeight = mCamera->GetOrthoHeight() / 2.0f;
|
|
|
|
float OrthoWidth = OrthoHeight * AspectRatio;
|
|
|
|
|
|
|
|
return lcMatrix44Ortho(-OrthoWidth, OrthoWidth, -OrthoHeight, OrthoHeight, mCamera->m_zNear, mCamera->m_zFar * 4);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
return lcMatrix44Perspective(mCamera->m_fovy, AspectRatio, mCamera->m_zNear, mCamera->m_zFar);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcMatrix44 lcView::GetTileProjectionMatrix(int CurrentRow, int CurrentColumn, int CurrentTileWidth, int CurrentTileHeight) const
|
2017-08-05 21:02:45 +02:00
|
|
|
{
|
|
|
|
int ImageWidth = mRenderImage.width();
|
|
|
|
int ImageHeight = mRenderImage.height();
|
|
|
|
|
2017-08-05 21:12:42 +02:00
|
|
|
double ImageLeft, ImageRight, ImageBottom, ImageTop, Near, Far;
|
2017-08-05 21:02:45 +02:00
|
|
|
double AspectRatio = (double)ImageWidth / (double)ImageHeight;
|
|
|
|
|
|
|
|
if (mCamera->IsOrtho())
|
|
|
|
{
|
|
|
|
float OrthoHeight = mCamera->GetOrthoHeight() / 2.0f;
|
|
|
|
float OrthoWidth = OrthoHeight * AspectRatio;
|
|
|
|
|
2017-08-05 21:12:42 +02:00
|
|
|
ImageLeft = -OrthoWidth;
|
|
|
|
ImageRight = OrthoWidth;
|
|
|
|
ImageBottom = -OrthoHeight;
|
|
|
|
ImageTop = OrthoHeight;
|
|
|
|
Near = mCamera->m_zNear;
|
|
|
|
Far = mCamera->m_zFar * 4;
|
2017-08-05 21:02:45 +02:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
double xmin, xmax, ymin, ymax;
|
|
|
|
ymax = mCamera->m_zNear * tan(mCamera->m_fovy * 3.14159265 / 360.0);
|
|
|
|
ymin = -ymax;
|
|
|
|
xmin = ymin * AspectRatio;
|
|
|
|
xmax = ymax * AspectRatio;
|
|
|
|
|
2017-08-05 21:12:42 +02:00
|
|
|
ImageLeft = xmin;
|
|
|
|
ImageRight = xmax;
|
|
|
|
ImageBottom = ymin;
|
|
|
|
ImageTop = ymax;
|
|
|
|
Near = mCamera->m_zNear;
|
|
|
|
Far = mCamera->m_zFar;
|
2017-08-05 21:02:45 +02:00
|
|
|
}
|
|
|
|
|
2017-08-05 21:12:42 +02:00
|
|
|
double Left = ImageLeft + (ImageRight - ImageLeft) * (CurrentColumn * mWidth) / ImageWidth;
|
|
|
|
double Right = Left + (ImageRight - ImageLeft) * CurrentTileWidth / ImageWidth;
|
|
|
|
double Bottom = ImageBottom + (ImageTop - ImageBottom) * (CurrentRow * mHeight) / ImageHeight;
|
|
|
|
double Top = Bottom + (ImageTop - ImageBottom) * CurrentTileHeight / ImageHeight;
|
2017-08-05 21:02:45 +02:00
|
|
|
|
|
|
|
if (mCamera->IsOrtho())
|
2017-08-05 21:12:42 +02:00
|
|
|
return lcMatrix44Ortho(Left, Right, Bottom, Top, Near, Far);
|
2017-08-05 21:02:45 +02:00
|
|
|
else
|
2017-08-05 21:12:42 +02:00
|
|
|
return lcMatrix44Frustum(Left, Right, Bottom, Top, Near, Far);
|
2017-08-05 21:02:45 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::ShowContextMenu() const
|
2015-12-04 21:32:10 +01:00
|
|
|
{
|
2020-12-26 20:44:41 +01:00
|
|
|
if (mViewType != lcViewType::View)
|
|
|
|
return;
|
|
|
|
|
2015-12-04 21:32:10 +01:00
|
|
|
QAction** Actions = gMainWindow->mActions;
|
|
|
|
|
2020-12-13 21:05:54 +01:00
|
|
|
QMenu* Popup = new QMenu(mWidget);
|
2015-12-04 21:32:10 +01:00
|
|
|
|
|
|
|
Popup->addAction(Actions[LC_EDIT_CUT]);
|
|
|
|
Popup->addAction(Actions[LC_EDIT_COPY]);
|
|
|
|
Popup->addAction(Actions[LC_EDIT_PASTE]);
|
2017-03-09 00:55:38 +01:00
|
|
|
Popup->addAction(Actions[LC_PIECE_DUPLICATE]);
|
2015-12-04 21:32:10 +01:00
|
|
|
|
|
|
|
Popup->addSeparator();
|
|
|
|
|
2016-03-03 01:04:49 +01:00
|
|
|
Popup->addAction(Actions[LC_PIECE_CONTROL_POINT_INSERT]);
|
|
|
|
Popup->addAction(Actions[LC_PIECE_CONTROL_POINT_REMOVE]);
|
|
|
|
|
|
|
|
Popup->addSeparator();
|
|
|
|
|
2018-03-29 19:20:36 +02:00
|
|
|
Popup->addAction(Actions[LC_PIECE_EDIT_SELECTED_SUBMODEL]);
|
2018-10-14 17:47:28 +02:00
|
|
|
Popup->addAction(Actions[LC_PIECE_EDIT_END_SUBMODEL]);
|
2015-12-04 23:41:08 +01:00
|
|
|
Popup->addAction(Actions[LC_PIECE_VIEW_SELECTED_MODEL]);
|
2015-12-04 21:32:10 +01:00
|
|
|
Popup->addAction(Actions[LC_PIECE_INLINE_SELECTED_MODELS]);
|
2015-12-04 23:41:08 +01:00
|
|
|
Popup->addAction(Actions[LC_PIECE_MOVE_SELECTION_TO_MODEL]);
|
2015-12-04 21:32:10 +01:00
|
|
|
|
|
|
|
Popup->addSeparator();
|
|
|
|
|
2017-11-14 23:56:37 +01:00
|
|
|
Popup->addMenu(gMainWindow->GetToolsMenu());
|
2015-12-04 21:32:10 +01:00
|
|
|
Popup->addMenu(gMainWindow->GetViewpointMenu());
|
2017-10-31 20:33:35 +01:00
|
|
|
Popup->addMenu(gMainWindow->GetCameraMenu());
|
|
|
|
Popup->addMenu(gMainWindow->GetProjectionMenu());
|
|
|
|
Popup->addMenu(gMainWindow->GetShadingMenu());
|
2015-12-04 21:32:10 +01:00
|
|
|
|
|
|
|
Popup->addSeparator();
|
|
|
|
|
|
|
|
Popup->addAction(Actions[LC_VIEW_SPLIT_HORIZONTAL]);
|
|
|
|
Popup->addAction(Actions[LC_VIEW_SPLIT_VERTICAL]);
|
|
|
|
Popup->addAction(Actions[LC_VIEW_REMOVE_VIEW]);
|
|
|
|
Popup->addAction(Actions[LC_VIEW_RESET_VIEWS]);
|
|
|
|
|
|
|
|
Popup->exec(QCursor::pos());
|
2019-06-23 22:15:12 +02:00
|
|
|
delete Popup;
|
2015-12-04 21:32:10 +01:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcVector3 lcView::GetMoveDirection(const lcVector3& Direction) const
|
2014-11-30 18:53:09 +01:00
|
|
|
{
|
|
|
|
if (lcGetPreferences().mFixedAxes)
|
|
|
|
return Direction;
|
|
|
|
|
|
|
|
// TODO: rewrite this
|
|
|
|
lcVector3 axis = Direction;
|
|
|
|
|
|
|
|
lcVector3 Pts[3] = { lcVector3(5.0f, 5.0f, 0.1f), lcVector3(10.0f, 5.0f, 0.1f), lcVector3(5.0f, 10.0f, 0.1f) };
|
|
|
|
UnprojectPoints(Pts, 3);
|
|
|
|
|
|
|
|
float ax, ay;
|
|
|
|
lcVector3 vx((Pts[1][0] - Pts[0][0]), (Pts[1][1] - Pts[0][1]), 0);//Pts[1][2] - Pts[0][2] };
|
|
|
|
vx.Normalize();
|
|
|
|
lcVector3 x(1, 0, 0);
|
|
|
|
ax = acosf(lcDot(vx, x));
|
|
|
|
|
|
|
|
lcVector3 vy((Pts[2][0] - Pts[0][0]), (Pts[2][1] - Pts[0][1]), 0);//Pts[2][2] - Pts[0][2] };
|
|
|
|
vy.Normalize();
|
|
|
|
lcVector3 y(0, -1, 0);
|
|
|
|
ay = acosf(lcDot(vy, y));
|
|
|
|
|
|
|
|
if (ax > 135)
|
|
|
|
axis[0] = -axis[0];
|
|
|
|
|
|
|
|
if (ay < 45)
|
|
|
|
axis[1] = -axis[1];
|
|
|
|
|
|
|
|
if (ax >= 45 && ax <= 135)
|
|
|
|
{
|
|
|
|
float tmp = axis[0];
|
|
|
|
|
|
|
|
ax = acosf(lcDot(vx, y));
|
|
|
|
if (ax > 90)
|
|
|
|
{
|
|
|
|
axis[0] = -axis[1];
|
|
|
|
axis[1] = tmp;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
axis[0] = axis[1];
|
|
|
|
axis[1] = -tmp;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return axis;
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcMatrix44 lcView::GetPieceInsertPosition(bool IgnoreSelected, PieceInfo* Info) const
|
2014-11-29 03:55:58 +01:00
|
|
|
{
|
2017-11-13 04:38:07 +01:00
|
|
|
lcPiece* HitPiece = (lcPiece*)FindObjectUnderPointer(true, IgnoreSelected).Object;
|
2018-03-29 19:20:36 +02:00
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
2014-11-29 03:55:58 +01:00
|
|
|
|
|
|
|
if (HitPiece)
|
|
|
|
{
|
2017-11-13 04:38:07 +01:00
|
|
|
lcVector3 Position(0, 0, HitPiece->GetBoundingBox().Max.z - Info->GetBoundingBox().Min.z);
|
2017-09-08 23:11:48 +02:00
|
|
|
|
|
|
|
if (gMainWindow->GetRelativeTransform())
|
2018-03-29 19:20:36 +02:00
|
|
|
Position = lcMul31(ActiveModel->SnapPosition(Position), HitPiece->mModelWorld);
|
2017-09-08 23:11:48 +02:00
|
|
|
else
|
2018-03-29 19:20:36 +02:00
|
|
|
Position = ActiveModel->SnapPosition(lcMul31(Position, HitPiece->mModelWorld));
|
2017-09-08 23:11:48 +02:00
|
|
|
|
2015-01-10 21:30:37 +01:00
|
|
|
lcMatrix44 WorldMatrix = HitPiece->mModelWorld;
|
|
|
|
WorldMatrix.SetTranslation(Position);
|
2014-11-29 03:55:58 +01:00
|
|
|
|
2015-01-10 21:30:37 +01:00
|
|
|
return WorldMatrix;
|
2014-11-29 03:55:58 +01:00
|
|
|
}
|
|
|
|
|
2020-12-05 17:45:29 +01:00
|
|
|
std::array<lcVector3, 2> ClickPoints = {{ lcVector3((float)mMouseX, (float)mMouseY, 0.0f), lcVector3((float)mMouseX, (float)mMouseY, 1.0f) }};
|
2018-04-08 03:45:44 +02:00
|
|
|
UnprojectPoints(ClickPoints.data(), 2);
|
|
|
|
|
|
|
|
if (ActiveModel != mModel)
|
|
|
|
{
|
|
|
|
lcMatrix44 InverseMatrix = lcMatrix44AffineInverse(mActiveSubmodelTransform);
|
|
|
|
|
|
|
|
for (lcVector3& Point : ClickPoints)
|
|
|
|
Point = lcMul31(Point, InverseMatrix);
|
|
|
|
}
|
2014-11-29 03:55:58 +01:00
|
|
|
|
2020-12-19 04:13:03 +01:00
|
|
|
const lcBoundingBox& BoundingBox = Info->GetBoundingBox();
|
2014-11-29 03:55:58 +01:00
|
|
|
lcVector3 Intersection;
|
|
|
|
|
2018-02-04 20:53:13 +01:00
|
|
|
if (lcLineSegmentPlaneIntersection(&Intersection, ClickPoints[0], ClickPoints[1], lcVector4(0, 0, 1, BoundingBox.Min.z)))
|
2014-11-29 03:55:58 +01:00
|
|
|
{
|
2018-03-29 19:20:36 +02:00
|
|
|
Intersection = ActiveModel->SnapPosition(Intersection);
|
2015-01-10 21:30:37 +01:00
|
|
|
return lcMatrix44Translation(Intersection);
|
2020-12-19 04:13:03 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
lcVector3 Position;
|
|
|
|
|
|
|
|
if (!ActiveModel->GetFocusPosition(Position))
|
|
|
|
Position = ActiveModel->GetSelectionOrModelCenter();
|
|
|
|
|
|
|
|
lcVector3 FrontVector(mCamera->mTargetPosition - mCamera->mPosition);
|
|
|
|
|
|
|
|
if (lcLineSegmentPlaneIntersection(&Intersection, ClickPoints[0], ClickPoints[1], lcVector4(FrontVector, -lcDot(FrontVector, Position))))
|
|
|
|
{
|
|
|
|
Intersection = ActiveModel->SnapPosition(Intersection);
|
|
|
|
return lcMatrix44Translation(Intersection);
|
2014-11-29 03:55:58 +01:00
|
|
|
}
|
|
|
|
|
2020-12-05 17:45:29 +01:00
|
|
|
return lcMatrix44Translation(UnprojectPoint(lcVector3((float)mMouseX, (float)mMouseY, 0.9f)));
|
2014-11-29 03:55:58 +01:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcVector3 lcView::GetCameraLightInsertPosition() const
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
|
|
|
|
std::array<lcVector3, 2> ClickPoints = { { lcVector3((float)mMouseX, (float)mMouseY, 0.0f), lcVector3((float)mMouseX, (float)mMouseY, 1.0f) } };
|
|
|
|
UnprojectPoints(ClickPoints.data(), 2);
|
|
|
|
|
|
|
|
if (ActiveModel != mModel)
|
|
|
|
{
|
|
|
|
lcMatrix44 InverseMatrix = lcMatrix44AffineInverse(mActiveSubmodelTransform);
|
|
|
|
|
|
|
|
for (lcVector3& Point : ClickPoints)
|
|
|
|
Point = lcMul31(Point, InverseMatrix);
|
|
|
|
}
|
|
|
|
|
|
|
|
lcVector3 Min, Max;
|
|
|
|
lcVector3 Center;
|
|
|
|
|
|
|
|
if (ActiveModel->GetPiecesBoundingBox(Min, Max))
|
|
|
|
Center = (Min + Max) / 2.0f;
|
|
|
|
else
|
|
|
|
Center = lcVector3(0.0f, 0.0f, 0.0f);
|
|
|
|
|
|
|
|
return lcRayPointClosestPoint(Center, ClickPoints[0], ClickPoints[1]);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::GetRayUnderPointer(lcVector3& Start, lcVector3& End) const
|
2016-03-03 01:04:49 +01:00
|
|
|
{
|
|
|
|
lcVector3 StartEnd[2] =
|
|
|
|
{
|
2020-12-05 17:45:29 +01:00
|
|
|
lcVector3((float)mMouseX, (float)mMouseY, 0.0f),
|
|
|
|
lcVector3((float)mMouseX, (float)mMouseY, 1.0f)
|
2016-03-03 01:04:49 +01:00
|
|
|
};
|
|
|
|
|
|
|
|
UnprojectPoints(StartEnd, 2);
|
|
|
|
|
|
|
|
Start = StartEnd[0];
|
|
|
|
End = StartEnd[1];
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcObjectSection lcView::FindObjectUnderPointer(bool PiecesOnly, bool IgnoreSelected) const
|
2014-05-03 18:59:57 +02:00
|
|
|
{
|
|
|
|
lcVector3 StartEnd[2] =
|
|
|
|
{
|
2020-12-05 17:45:29 +01:00
|
|
|
lcVector3((float)mMouseX, (float)mMouseY, 0.0f),
|
|
|
|
lcVector3((float)mMouseX, (float)mMouseY, 1.0f)
|
2014-05-03 18:59:57 +02:00
|
|
|
};
|
|
|
|
|
|
|
|
UnprojectPoints(StartEnd, 2);
|
|
|
|
|
|
|
|
lcObjectRayTest ObjectRayTest;
|
|
|
|
|
|
|
|
ObjectRayTest.PiecesOnly = PiecesOnly;
|
2017-11-13 04:38:07 +01:00
|
|
|
ObjectRayTest.IgnoreSelected = IgnoreSelected;
|
2014-05-03 18:59:57 +02:00
|
|
|
ObjectRayTest.ViewCamera = mCamera;
|
|
|
|
ObjectRayTest.Start = StartEnd[0];
|
|
|
|
ObjectRayTest.End = StartEnd[1];
|
|
|
|
ObjectRayTest.Distance = FLT_MAX;
|
2017-04-14 02:26:40 +02:00
|
|
|
ObjectRayTest.ObjectSection.Object = nullptr;
|
2014-05-03 18:59:57 +02:00
|
|
|
ObjectRayTest.ObjectSection.Section = 0;;
|
|
|
|
|
2018-03-29 19:20:36 +02:00
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
|
|
|
|
if (ActiveModel != mModel)
|
|
|
|
{
|
2018-04-08 02:17:32 +02:00
|
|
|
lcMatrix44 InverseMatrix = lcMatrix44AffineInverse(mActiveSubmodelTransform);
|
2018-03-29 19:20:36 +02:00
|
|
|
|
|
|
|
ObjectRayTest.Start = lcMul31(ObjectRayTest.Start, InverseMatrix);
|
|
|
|
ObjectRayTest.End = lcMul31(ObjectRayTest.End, InverseMatrix);
|
|
|
|
}
|
|
|
|
|
|
|
|
ActiveModel->RayTest(ObjectRayTest);
|
2014-05-03 18:59:57 +02:00
|
|
|
|
|
|
|
return ObjectRayTest.ObjectSection;
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcArray<lcObject*> lcView::FindObjectsInBox(float x1, float y1, float x2, float y2) const
|
2014-05-03 18:59:57 +02:00
|
|
|
{
|
|
|
|
float Left, Top, Bottom, Right;
|
|
|
|
|
|
|
|
if (x1 < x2)
|
|
|
|
{
|
|
|
|
Left = x1;
|
|
|
|
Right = x2;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
Left = x2;
|
|
|
|
Right = x1;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (y1 > y2)
|
|
|
|
{
|
|
|
|
Top = y1;
|
|
|
|
Bottom = y2;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
Top = y2;
|
|
|
|
Bottom = y1;
|
|
|
|
}
|
|
|
|
|
2018-04-08 03:45:44 +02:00
|
|
|
std::array<lcVector3, 6> Corners =
|
2019-03-12 02:29:19 +01:00
|
|
|
{{
|
2014-05-03 18:59:57 +02:00
|
|
|
lcVector3(Left, Top, 0),
|
|
|
|
lcVector3(Left, Bottom, 0),
|
|
|
|
lcVector3(Right, Bottom, 0),
|
|
|
|
lcVector3(Right, Top, 0),
|
|
|
|
lcVector3(Left, Top, 1),
|
|
|
|
lcVector3(Right, Bottom, 1)
|
2019-03-12 02:29:19 +01:00
|
|
|
}};
|
2014-05-03 18:59:57 +02:00
|
|
|
|
2019-05-18 20:33:27 +02:00
|
|
|
UnprojectPoints(Corners.data(), (int)Corners.size());
|
2018-04-08 03:45:44 +02:00
|
|
|
|
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
|
|
|
|
if (ActiveModel != mModel)
|
|
|
|
{
|
|
|
|
lcMatrix44 InverseMatrix = lcMatrix44AffineInverse(mActiveSubmodelTransform);
|
|
|
|
|
|
|
|
for (lcVector3& Point : Corners)
|
|
|
|
Point = lcMul31(Point, InverseMatrix);
|
|
|
|
}
|
2014-05-03 18:59:57 +02:00
|
|
|
|
|
|
|
lcVector3 PlaneNormals[6];
|
|
|
|
PlaneNormals[0] = lcNormalize(lcCross(Corners[4] - Corners[0], Corners[1] - Corners[0])); // Left
|
|
|
|
PlaneNormals[1] = lcNormalize(lcCross(Corners[5] - Corners[2], Corners[3] - Corners[2])); // Right
|
|
|
|
PlaneNormals[2] = lcNormalize(lcCross(Corners[3] - Corners[0], Corners[4] - Corners[0])); // Top
|
|
|
|
PlaneNormals[3] = lcNormalize(lcCross(Corners[1] - Corners[2], Corners[5] - Corners[2])); // Bottom
|
|
|
|
PlaneNormals[4] = lcNormalize(lcCross(Corners[1] - Corners[0], Corners[3] - Corners[0])); // Front
|
|
|
|
PlaneNormals[5] = lcNormalize(lcCross(Corners[1] - Corners[2], Corners[3] - Corners[2])); // Back
|
|
|
|
|
|
|
|
lcObjectBoxTest ObjectBoxTest;
|
|
|
|
ObjectBoxTest.ViewCamera = mCamera;
|
|
|
|
ObjectBoxTest.Planes[0] = lcVector4(PlaneNormals[0], -lcDot(PlaneNormals[0], Corners[0]));
|
|
|
|
ObjectBoxTest.Planes[1] = lcVector4(PlaneNormals[1], -lcDot(PlaneNormals[1], Corners[5]));
|
|
|
|
ObjectBoxTest.Planes[2] = lcVector4(PlaneNormals[2], -lcDot(PlaneNormals[2], Corners[0]));
|
|
|
|
ObjectBoxTest.Planes[3] = lcVector4(PlaneNormals[3], -lcDot(PlaneNormals[3], Corners[5]));
|
|
|
|
ObjectBoxTest.Planes[4] = lcVector4(PlaneNormals[4], -lcDot(PlaneNormals[4], Corners[0]));
|
|
|
|
ObjectBoxTest.Planes[5] = lcVector4(PlaneNormals[5], -lcDot(PlaneNormals[5], Corners[5]));
|
|
|
|
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->BoxTest(ObjectBoxTest);
|
2014-05-03 18:59:57 +02:00
|
|
|
|
2014-11-29 03:55:58 +01:00
|
|
|
return ObjectBoxTest.Objects;
|
2014-05-03 18:59:57 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
bool lcView::BeginRenderToImage(int Width, int Height)
|
2017-07-30 23:18:57 +02:00
|
|
|
{
|
2020-12-29 02:30:41 +01:00
|
|
|
#ifdef LC_USE_QOPENGLWIDGET
|
|
|
|
std::unique_ptr<QOpenGLContext> OffscreenContext(new QOpenGLContext());
|
|
|
|
|
|
|
|
if (!OffscreenContext)
|
|
|
|
return false;
|
|
|
|
|
|
|
|
OffscreenContext->setShareContext(QOpenGLContext::globalShareContext());
|
|
|
|
|
|
|
|
if (!OffscreenContext->create() || !OffscreenContext->isValid())
|
|
|
|
return false;
|
|
|
|
|
|
|
|
std::unique_ptr<QOffscreenSurface> OffscreenSurface(new QOffscreenSurface());
|
|
|
|
|
|
|
|
if (!OffscreenSurface)
|
|
|
|
return false;
|
|
|
|
|
|
|
|
OffscreenSurface->create();
|
|
|
|
|
|
|
|
if (!OffscreenSurface->isValid())
|
|
|
|
return false;
|
|
|
|
|
|
|
|
if (!OffscreenContext->makeCurrent(OffscreenSurface.get()))
|
|
|
|
return false;
|
|
|
|
|
|
|
|
mContext->SetGLContext(OffscreenContext.get());
|
|
|
|
|
|
|
|
mOffscreenContext = std::move(OffscreenContext);
|
|
|
|
mOffscreenSurface = std::move(OffscreenSurface);
|
|
|
|
#endif
|
|
|
|
|
2017-07-30 23:18:57 +02:00
|
|
|
GLint MaxTexture;
|
|
|
|
glGetIntegerv(GL_MAX_TEXTURE_SIZE, &MaxTexture);
|
|
|
|
|
|
|
|
MaxTexture = qMin(MaxTexture, 2048);
|
2020-12-27 22:05:55 +01:00
|
|
|
#ifdef LC_USE_QOPENGLWIDGET
|
2020-12-28 23:36:04 +01:00
|
|
|
const int Samples = QSurfaceFormat::defaultFormat().samples();
|
|
|
|
if (Samples > 1)
|
|
|
|
MaxTexture /= Samples;
|
2020-12-27 22:05:55 +01:00
|
|
|
#else
|
2018-02-25 03:22:53 +01:00
|
|
|
MaxTexture /= QGLFormat::defaultFormat().sampleBuffers() ? QGLFormat::defaultFormat().samples() : 1;
|
2020-12-27 22:05:55 +01:00
|
|
|
#endif
|
2017-07-30 23:18:57 +02:00
|
|
|
|
|
|
|
int TileWidth = qMin(Width, MaxTexture);
|
|
|
|
int TileHeight = qMin(Height, MaxTexture);
|
|
|
|
|
|
|
|
mWidth = TileWidth;
|
|
|
|
mHeight = TileHeight;
|
2018-01-01 16:56:25 +01:00
|
|
|
mRenderImage = QImage(Width, Height, QImage::Format_ARGB32);
|
2017-07-30 23:18:57 +02:00
|
|
|
|
2020-12-29 02:30:41 +01:00
|
|
|
#ifdef LC_USE_QOPENGLWIDGET
|
|
|
|
QOpenGLFramebufferObjectFormat Format;
|
|
|
|
Format.setAttachment(QOpenGLFramebufferObject::Depth);
|
|
|
|
|
|
|
|
if (QSurfaceFormat::defaultFormat().samples() > 1)
|
|
|
|
Format.setSamples(QSurfaceFormat::defaultFormat().samples());
|
|
|
|
|
2020-12-29 02:41:56 +01:00
|
|
|
mRenderFramebuffer = std::unique_ptr<QOpenGLFramebufferObject>(new QOpenGLFramebufferObject(QSize(TileWidth, TileHeight), Format));
|
2020-12-29 02:30:41 +01:00
|
|
|
|
|
|
|
return mRenderFramebuffer->bind();
|
|
|
|
#else
|
2018-01-01 16:56:25 +01:00
|
|
|
mRenderFramebuffer = mContext->CreateRenderFramebuffer(TileWidth, TileHeight);
|
2017-12-29 15:50:18 +01:00
|
|
|
mContext->BindFramebuffer(mRenderFramebuffer.first);
|
2020-12-29 02:30:41 +01:00
|
|
|
|
2017-12-29 15:50:18 +01:00
|
|
|
return mRenderFramebuffer.first.IsValid();
|
2020-12-29 02:30:41 +01:00
|
|
|
#endif
|
2017-07-30 23:18:57 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::EndRenderToImage()
|
2017-07-30 23:18:57 +02:00
|
|
|
{
|
2020-12-29 02:30:41 +01:00
|
|
|
#ifdef LC_USE_QOPENGLWIDGET
|
|
|
|
mOffscreenContext.reset();
|
|
|
|
mOffscreenSurface.reset();
|
|
|
|
mRenderFramebuffer.reset();
|
|
|
|
#else
|
2017-07-30 23:18:57 +02:00
|
|
|
mRenderImage = QImage();
|
2017-12-29 15:50:18 +01:00
|
|
|
mContext->DestroyRenderFramebuffer(mRenderFramebuffer);
|
|
|
|
mContext->ClearFramebuffer();
|
2020-12-29 02:30:41 +01:00
|
|
|
#endif
|
|
|
|
}
|
|
|
|
|
|
|
|
QImage lcView::GetRenderImage() const
|
|
|
|
{
|
|
|
|
return mRenderImage;
|
2017-07-30 23:18:57 +02:00
|
|
|
}
|
|
|
|
|
2020-12-29 02:30:41 +01:00
|
|
|
#ifdef LC_USE_QOPENGLWIDGET
|
|
|
|
|
|
|
|
QImage lcView::GetRenderFramebufferImage() const
|
|
|
|
{
|
|
|
|
mRenderFramebuffer->release();
|
|
|
|
QImage Image = mRenderFramebuffer->toImage();
|
|
|
|
mRenderFramebuffer->bind();
|
|
|
|
|
|
|
|
return Image;
|
|
|
|
}
|
|
|
|
|
|
|
|
#endif
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnDraw()
|
2011-09-07 23:06:51 +02:00
|
|
|
{
|
2018-01-07 00:01:04 +01:00
|
|
|
if (!mModel)
|
|
|
|
return;
|
|
|
|
|
2019-11-28 21:47:19 +01:00
|
|
|
const lcPreferences& Preferences = lcGetPreferences();
|
2020-12-26 20:44:41 +01:00
|
|
|
const bool DrawOverlays = mWidget != nullptr;
|
2020-12-24 03:45:34 +01:00
|
|
|
const bool DrawInterface = mWidget != nullptr && mViewType == lcViewType::View;
|
2019-11-28 21:47:19 +01:00
|
|
|
|
2020-12-05 20:02:10 +01:00
|
|
|
mScene->SetAllowLOD(Preferences.mAllowLOD && mWidget != nullptr);
|
|
|
|
mScene->SetLODDistance(Preferences.mMeshLODDistance);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-12-05 20:02:10 +01:00
|
|
|
mScene->Begin(mCamera->mWorldView);
|
2019-11-30 21:19:13 +01:00
|
|
|
|
2020-12-05 20:02:10 +01:00
|
|
|
mScene->SetActiveSubmodelInstance(mActiveSubmodelInstance, mActiveSubmodelTransform);
|
|
|
|
mScene->SetDrawInterface(DrawInterface);
|
2019-12-12 23:04:51 +01:00
|
|
|
|
2020-12-05 20:02:10 +01:00
|
|
|
mModel->GetScene(mScene.get(), mCamera, Preferences.mHighlightNewParts, Preferences.mFadeSteps);
|
2014-11-24 00:48:56 +01:00
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
if (DrawInterface && mTrackTool == lcTrackTool::Insert)
|
2015-01-02 17:21:07 +01:00
|
|
|
{
|
2016-12-16 18:14:19 +01:00
|
|
|
PieceInfo* Info = gMainWindow->GetCurrentPieceInfo();
|
2015-01-07 17:52:42 +01:00
|
|
|
|
|
|
|
if (Info)
|
2018-04-08 03:45:44 +02:00
|
|
|
{
|
2020-02-01 20:34:56 +01:00
|
|
|
lcMatrix44 WorldMatrix = GetPieceInsertPosition(false, Info);
|
2018-04-08 03:45:44 +02:00
|
|
|
|
|
|
|
if (GetActiveModel() != mModel)
|
|
|
|
WorldMatrix = lcMul(WorldMatrix, mActiveSubmodelTransform);
|
|
|
|
|
2020-12-05 20:02:10 +01:00
|
|
|
Info->AddRenderMeshes(mScene.get(), WorldMatrix, gMainWindow->mColorIndex, lcRenderMeshState::Focused, false);
|
2018-04-08 03:45:44 +02:00
|
|
|
}
|
2015-01-02 17:21:07 +01:00
|
|
|
}
|
|
|
|
|
2020-12-24 03:45:34 +01:00
|
|
|
if (DrawInterface)
|
2020-12-05 20:02:10 +01:00
|
|
|
mScene->SetPreTranslucentCallback([this]() { DrawGrid(); });
|
2019-11-30 20:38:11 +01:00
|
|
|
|
2020-12-05 20:02:10 +01:00
|
|
|
mScene->End();
|
2019-11-30 21:19:13 +01:00
|
|
|
|
2017-08-05 21:02:45 +02:00
|
|
|
int TotalTileRows = 1;
|
|
|
|
int TotalTileColumns = 1;
|
|
|
|
|
2017-07-30 23:18:57 +02:00
|
|
|
if (!mRenderImage.isNull())
|
|
|
|
{
|
2017-08-05 21:02:45 +02:00
|
|
|
int ImageWidth = mRenderImage.width();
|
|
|
|
int ImageHeight = mRenderImage.height();
|
2014-11-24 00:48:56 +01:00
|
|
|
|
2017-08-05 21:02:45 +02:00
|
|
|
if (ImageWidth > mWidth || ImageHeight > mHeight)
|
2017-07-30 23:18:57 +02:00
|
|
|
{
|
2017-08-05 21:02:45 +02:00
|
|
|
TotalTileColumns = (mWidth + ImageWidth - 1) / mWidth;
|
|
|
|
TotalTileRows = (mHeight + ImageHeight - 1) / mHeight;
|
2017-07-30 23:18:57 +02:00
|
|
|
}
|
|
|
|
}
|
2014-11-24 00:48:56 +01:00
|
|
|
|
2017-08-05 21:02:45 +02:00
|
|
|
for (int CurrentTileRow = 0; CurrentTileRow < TotalTileRows; CurrentTileRow++)
|
2017-07-30 23:18:57 +02:00
|
|
|
{
|
2017-08-05 21:02:45 +02:00
|
|
|
for (int CurrentTileColumn = 0; CurrentTileColumn < TotalTileColumns; CurrentTileColumn++)
|
2017-07-30 23:18:57 +02:00
|
|
|
{
|
2017-08-05 21:02:45 +02:00
|
|
|
mContext->SetDefaultState();
|
|
|
|
mContext->SetViewport(0, 0, mWidth, mHeight);
|
|
|
|
|
2020-11-26 21:07:41 +01:00
|
|
|
DrawBackground();
|
2017-07-30 23:18:57 +02:00
|
|
|
|
2017-08-05 21:02:45 +02:00
|
|
|
int CurrentTileWidth, CurrentTileHeight;
|
2017-07-30 23:18:57 +02:00
|
|
|
|
2017-08-05 21:02:45 +02:00
|
|
|
if (!mRenderImage.isNull() && (TotalTileRows > 1 || TotalTileColumns > 1))
|
|
|
|
{
|
|
|
|
if (CurrentTileRow < TotalTileRows - 1)
|
|
|
|
CurrentTileHeight = mHeight;
|
|
|
|
else
|
|
|
|
CurrentTileHeight = mRenderImage.height() - (TotalTileRows - 1) * (mHeight);
|
|
|
|
|
|
|
|
if (CurrentTileColumn < TotalTileColumns - 1)
|
|
|
|
CurrentTileWidth = mWidth;
|
|
|
|
else
|
|
|
|
CurrentTileWidth = mRenderImage.width() - (TotalTileColumns - 1) * (mWidth);
|
|
|
|
|
|
|
|
mContext->SetViewport(0, 0, CurrentTileWidth, CurrentTileHeight);
|
|
|
|
mContext->SetProjectionMatrix(GetTileProjectionMatrix(CurrentTileRow, CurrentTileColumn, CurrentTileWidth, CurrentTileHeight));
|
|
|
|
}
|
2017-07-30 23:18:57 +02:00
|
|
|
else
|
|
|
|
{
|
|
|
|
CurrentTileWidth = mWidth;
|
|
|
|
CurrentTileHeight = mHeight;
|
|
|
|
|
2017-08-05 21:02:45 +02:00
|
|
|
mContext->SetProjectionMatrix(GetProjectionMatrix());
|
|
|
|
}
|
2017-07-30 23:18:57 +02:00
|
|
|
|
2017-08-05 21:02:45 +02:00
|
|
|
mContext->SetLineWidth(Preferences.mLineWidth);
|
2017-07-30 23:18:57 +02:00
|
|
|
|
2020-12-05 20:02:10 +01:00
|
|
|
mScene->Draw(mContext);
|
2017-07-30 23:18:57 +02:00
|
|
|
|
2017-08-05 21:02:45 +02:00
|
|
|
if (!mRenderImage.isNull())
|
2017-07-30 23:18:57 +02:00
|
|
|
{
|
2020-12-29 02:30:41 +01:00
|
|
|
#ifdef LC_USE_QOPENGLWIDGET
|
|
|
|
QImage TileImage = GetRenderFramebufferImage();
|
|
|
|
quint8* Buffer = TileImage.bits();
|
|
|
|
#else
|
2017-12-02 21:22:04 +01:00
|
|
|
quint8* Buffer = (quint8*)malloc(mWidth * mHeight * 4);
|
2017-12-29 15:50:18 +01:00
|
|
|
mContext->GetRenderFramebufferImage(mRenderFramebuffer, Buffer);
|
2020-12-29 02:30:41 +01:00
|
|
|
#endif
|
|
|
|
uchar* ImageBuffer = mRenderImage.bits();
|
2017-08-05 21:02:45 +02:00
|
|
|
|
2017-12-26 19:19:20 +01:00
|
|
|
quint32 TileY = 0, SrcY = 0;
|
2017-08-05 21:02:45 +02:00
|
|
|
if (CurrentTileRow != TotalTileRows - 1)
|
2018-01-04 19:22:57 +01:00
|
|
|
TileY = (TotalTileRows - CurrentTileRow - 1) * mHeight - ((mHeight - mRenderImage.height() % mHeight) % mHeight);
|
|
|
|
else if (TotalTileRows > 1)
|
|
|
|
SrcY = (mHeight - mRenderImage.height() % mHeight) % mHeight;
|
2017-12-29 15:50:18 +01:00
|
|
|
|
2017-12-02 21:22:04 +01:00
|
|
|
quint32 TileStart = ((CurrentTileColumn * mWidth) + (TileY * mRenderImage.width())) * 4;
|
2017-08-05 21:02:45 +02:00
|
|
|
|
|
|
|
for (int y = 0; y < CurrentTileHeight; y++)
|
|
|
|
{
|
2018-01-04 19:22:57 +01:00
|
|
|
quint8* src = Buffer + (SrcY + y) * mWidth * 4;
|
2017-12-02 21:22:04 +01:00
|
|
|
quint8* dst = ImageBuffer + TileStart + y * mRenderImage.width() * 4;
|
2017-08-05 21:02:45 +02:00
|
|
|
|
2017-12-26 19:19:20 +01:00
|
|
|
memcpy(dst, src, CurrentTileWidth * 4);
|
2017-07-30 23:18:57 +02:00
|
|
|
}
|
|
|
|
|
2020-12-29 02:30:41 +01:00
|
|
|
#ifndef LC_USE_QOPENGLWIDGET
|
2017-08-05 21:02:45 +02:00
|
|
|
free(Buffer);
|
2020-12-29 02:30:41 +01:00
|
|
|
#endif
|
2017-08-05 21:02:45 +02:00
|
|
|
}
|
2017-07-30 23:18:57 +02:00
|
|
|
}
|
|
|
|
}
|
2014-11-24 00:48:56 +01:00
|
|
|
|
|
|
|
if (DrawInterface)
|
2020-12-05 20:02:10 +01:00
|
|
|
mScene->DrawInterfaceObjects(mContext);
|
2014-11-24 00:48:56 +01:00
|
|
|
|
2020-12-26 20:44:41 +01:00
|
|
|
if (DrawOverlays)
|
|
|
|
DrawAxes();
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-12-26 21:10:14 +01:00
|
|
|
if (DrawInterface)
|
|
|
|
{
|
2020-12-24 03:45:34 +01:00
|
|
|
lcTool Tool = gMainWindow->GetTool();
|
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
|
|
|
|
if ((Tool == lcTool::Select || Tool == lcTool::Move) && mTrackButton == lcTrackButton::None && ActiveModel->AnyObjectsSelected())
|
|
|
|
DrawSelectMoveOverlay();
|
|
|
|
else if (GetCurrentTool() == lcTool::Move && mTrackButton != lcTrackButton::None)
|
|
|
|
DrawSelectMoveOverlay();
|
|
|
|
else if ((Tool == lcTool::Rotate || (Tool == lcTool::Select && mTrackButton != lcTrackButton::None && mTrackTool >= lcTrackTool::RotateX && mTrackTool <= lcTrackTool::RotateXYZ)) && ActiveModel->AnyPiecesSelected())
|
|
|
|
DrawRotateOverlay();
|
|
|
|
else if ((mTrackTool == lcTrackTool::Select || mTrackTool == lcTrackTool::ZoomRegion) && mTrackButton != lcTrackButton::None)
|
|
|
|
DrawSelectZoomRegionOverlay();
|
|
|
|
else if (Tool == lcTool::RotateView && mTrackButton == lcTrackButton::None)
|
|
|
|
DrawRotateViewOverlay();
|
2020-12-26 21:10:14 +01:00
|
|
|
}
|
2020-12-24 03:45:34 +01:00
|
|
|
|
2020-12-26 21:10:14 +01:00
|
|
|
if (DrawOverlays)
|
|
|
|
{
|
2020-12-24 03:45:34 +01:00
|
|
|
mViewSphere->Draw();
|
2017-03-25 20:29:28 +01:00
|
|
|
|
2020-12-24 03:45:34 +01:00
|
|
|
DrawViewport();
|
2020-12-26 20:44:41 +01:00
|
|
|
}
|
2020-12-24 03:45:34 +01:00
|
|
|
|
2017-03-25 20:29:28 +01:00
|
|
|
mContext->ClearResources();
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::DrawBackground() const
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
const lcPreferences& Preferences = lcGetPreferences();
|
|
|
|
|
|
|
|
if (!Preferences.mBackgroundGradient)
|
|
|
|
{
|
2020-12-30 00:32:11 +01:00
|
|
|
lcVector4 BackgroundColor(lcVector3FromColor(Preferences.mBackgroundSolidColor), 0.0f);
|
|
|
|
mContext->ClearColorAndDepth(BackgroundColor);
|
2020-12-25 19:37:59 +01:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2020-12-30 00:32:11 +01:00
|
|
|
mContext->ClearDepth();
|
2020-12-25 19:37:59 +01:00
|
|
|
|
2020-12-27 01:30:28 +01:00
|
|
|
mContext->SetDepthWrite(false);
|
2020-12-25 19:37:59 +01:00
|
|
|
glDisable(GL_DEPTH_TEST);
|
|
|
|
|
|
|
|
float ViewWidth = (float)mWidth;
|
|
|
|
float ViewHeight = (float)mHeight;
|
|
|
|
|
2020-12-27 01:30:28 +01:00
|
|
|
mContext->SetWorldMatrix(lcMatrix44Identity());
|
|
|
|
mContext->SetViewMatrix(lcMatrix44Translation(lcVector3(0.375, 0.375, 0.0)));
|
|
|
|
mContext->SetProjectionMatrix(lcMatrix44Ortho(0.0f, ViewWidth, 0.0f, ViewHeight, -1.0f, 1.0f));
|
2020-12-25 19:37:59 +01:00
|
|
|
|
2020-12-27 01:30:28 +01:00
|
|
|
mContext->SetSmoothShading(true);
|
2020-12-25 19:37:59 +01:00
|
|
|
|
2020-12-27 01:30:28 +01:00
|
|
|
const quint32 Color1 = Preferences.mBackgroundGradientColorTop;
|
|
|
|
const quint32 Color2 = Preferences.mBackgroundGradientColorBottom;
|
|
|
|
|
|
|
|
struct lcBackgroundVertex
|
|
|
|
{
|
|
|
|
float x, y;
|
|
|
|
quint32 Color;
|
|
|
|
};
|
2020-12-25 19:37:59 +01:00
|
|
|
|
2020-12-27 01:30:28 +01:00
|
|
|
const lcBackgroundVertex Verts[4] =
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
2020-12-27 01:30:28 +01:00
|
|
|
{ ViewWidth, ViewHeight, Color1 }, { 0.0f, ViewHeight, Color1 }, { 0.0f, 0.0f, Color2 }, { ViewWidth, 0.0f, Color2 }
|
2020-12-25 19:37:59 +01:00
|
|
|
};
|
|
|
|
|
2020-12-27 01:30:28 +01:00
|
|
|
mContext->SetMaterial(lcMaterialType::UnlitVertexColor);
|
|
|
|
mContext->SetVertexBufferPointer(Verts);
|
|
|
|
mContext->SetVertexFormat(0, 2, 0, 0, 4, false);
|
2020-12-25 19:37:59 +01:00
|
|
|
|
2020-12-27 01:30:28 +01:00
|
|
|
mContext->DrawPrimitives(GL_TRIANGLE_FAN, 0, 4);
|
2020-12-25 19:37:59 +01:00
|
|
|
|
2020-12-27 01:30:28 +01:00
|
|
|
mContext->SetSmoothShading(false);
|
2020-12-25 19:37:59 +01:00
|
|
|
|
|
|
|
glEnable(GL_DEPTH_TEST);
|
2020-12-27 01:30:28 +01:00
|
|
|
mContext->SetDepthWrite(true);
|
2020-12-25 19:37:59 +01:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::DrawViewport() const
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
mContext->SetWorldMatrix(lcMatrix44Identity());
|
|
|
|
mContext->SetViewMatrix(lcMatrix44Translation(lcVector3(0.375, 0.375, 0.0)));
|
|
|
|
mContext->SetProjectionMatrix(lcMatrix44Ortho(0.0f, mWidth, 0.0f, mHeight, -1.0f, 1.0f));
|
2020-12-26 21:10:14 +01:00
|
|
|
mContext->SetLineWidth(1.0f);
|
2020-12-25 19:37:59 +01:00
|
|
|
|
|
|
|
mContext->SetDepthWrite(false);
|
|
|
|
glDisable(GL_DEPTH_TEST);
|
|
|
|
|
|
|
|
mContext->SetMaterial(lcMaterialType::UnlitColor);
|
|
|
|
|
|
|
|
if (mLastFocusedView == this)
|
|
|
|
mContext->SetColor(lcVector4FromColor(lcGetPreferences().mActiveViewColor));
|
|
|
|
else
|
|
|
|
mContext->SetColor(lcVector4FromColor(lcGetPreferences().mInactiveViewColor));
|
|
|
|
|
|
|
|
float Verts[8] = { 0.0f, 0.0f, mWidth - 1.0f, 0.0f, mWidth - 1.0f, mHeight - 1.0f, 0.0f, mHeight - 1.0f };
|
|
|
|
|
|
|
|
mContext->SetVertexBufferPointer(Verts);
|
|
|
|
mContext->SetVertexFormatPosition(2);
|
|
|
|
mContext->DrawPrimitives(GL_LINE_LOOP, 0, 4);
|
|
|
|
|
|
|
|
QString CameraName = mCamera->GetName();
|
|
|
|
|
|
|
|
if (!CameraName.isEmpty())
|
|
|
|
{
|
|
|
|
mContext->SetMaterial(lcMaterialType::UnlitTextureModulate);
|
2020-12-30 22:44:08 +01:00
|
|
|
mContext->SetColor(lcVector4FromColor(lcGetPreferences().mTextColor));
|
2020-12-25 19:37:59 +01:00
|
|
|
mContext->BindTexture2D(gTexFont.GetTexture());
|
|
|
|
|
|
|
|
glEnable(GL_BLEND);
|
|
|
|
|
|
|
|
gTexFont.PrintText(mContext, 3.0f, (float)mHeight - 1.0f - 6.0f, 0.0f, CameraName.toLatin1().constData());
|
|
|
|
|
|
|
|
glDisable(GL_BLEND);
|
|
|
|
}
|
|
|
|
|
|
|
|
mContext->SetDepthWrite(true);
|
|
|
|
glEnable(GL_DEPTH_TEST);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::DrawAxes() const
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
2020-12-26 20:44:41 +01:00
|
|
|
const lcPreferences& Preferences = lcGetPreferences();
|
|
|
|
|
|
|
|
switch (mViewType)
|
|
|
|
{
|
|
|
|
case lcViewType::View:
|
|
|
|
if (!Preferences.mDrawAxes)
|
|
|
|
return;
|
|
|
|
break;
|
|
|
|
|
|
|
|
case lcViewType::Preview:
|
|
|
|
if (!Preferences.mDrawPreviewAxis)
|
|
|
|
return;
|
|
|
|
break;
|
|
|
|
|
|
|
|
case lcViewType::Minifig:
|
2020-12-29 21:23:36 +01:00
|
|
|
case lcViewType::PartsList:
|
2020-12-26 20:44:41 +01:00
|
|
|
case lcViewType::Count:
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2020-12-30 00:32:11 +01:00
|
|
|
// mContext->ClearDepth();
|
2020-12-25 19:37:59 +01:00
|
|
|
|
2020-12-27 01:30:28 +01:00
|
|
|
struct lcAxisVertex
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
2020-12-27 01:30:28 +01:00
|
|
|
float x, y, z;
|
|
|
|
quint32 Color;
|
|
|
|
};
|
|
|
|
|
|
|
|
const quint32 Red = LC_RGBA(204, 0, 0, 255);
|
|
|
|
const quint32 Green = LC_RGBA(0, 204, 0, 255);
|
|
|
|
const quint32 Blue = LC_RGBA(0, 0, 204, 255);
|
|
|
|
|
|
|
|
const lcAxisVertex Verts[30] =
|
|
|
|
{
|
|
|
|
{ 0.00f, 0.00f, 0.00f, Red }, { 20.00f, 0.00f, 0.00f, Red }, { 12.00f, 3.00f, 0.00f, Red }, { 12.00f, 2.12f, 2.12f, Red }, { 12.00f, 0.00f, 3.00f, Red },
|
|
|
|
{ 12.00f, -2.12f, 2.12f, Red }, { 12.00f, -3.00f, 0.00f, Red }, { 12.00f, -2.12f, -2.12f, Red }, { 12.00f, 0.00f, -3.00f, Red }, { 12.00f, 2.12f, -2.12f, Red },
|
|
|
|
{ 0.00f, 0.00f, 0.00f, Green }, { 0.00f, 20.00f, 0.00f, Green }, { 3.00f, 12.00f, 0.00f, Green }, { 2.12f, 12.00f, 2.12f, Green }, { 0.00f, 12.00f, 3.00f, Green },
|
|
|
|
{ -2.12f, 12.00f, 2.12f, Green }, { -3.00f, 12.00f, 0.00f, Green }, { -2.12f, 12.00f, -2.12f, Green }, { 0.00f, 12.00f, -3.00f, Green }, { 2.12f, 12.00f, -2.12f, Green },
|
|
|
|
{ 0.00f, 0.00f, 0.00f, Blue }, { 0.00f, 0.00f, 20.00f, Blue }, { 0.00f, 3.00f, 12.00f, Blue }, { 2.12f, 2.12f, 12.00f, Blue }, { 3.00f, 0.00f, 12.00f, Blue },
|
|
|
|
{ 2.12f, -2.12f, 12.00f, Blue }, { 0.00f, -3.00f, 12.00f, Blue }, { -2.12f, -2.12f, 12.00f, Blue }, { -3.00f, 0.00f, 12.00f, Blue }, { -2.12f, 2.12f, 12.00f, Blue }
|
2020-12-25 19:37:59 +01:00
|
|
|
};
|
|
|
|
|
|
|
|
const GLushort Indices[78] =
|
|
|
|
{
|
2020-12-27 01:30:28 +01:00
|
|
|
0, 1, 10, 11, 20, 21,
|
2020-12-25 19:37:59 +01:00
|
|
|
1, 2, 3, 1, 3, 4, 1, 4, 5, 1, 5, 6, 1, 6, 7, 1, 7, 8, 1, 8, 9, 1, 9, 2,
|
2020-12-27 01:30:28 +01:00
|
|
|
11, 12, 13, 11, 13, 14, 11, 14, 15, 11, 15, 16, 11, 16, 17, 11, 17, 18, 11, 18, 19, 11, 19, 12,
|
|
|
|
21, 22, 23, 21, 23, 24, 21, 24, 25, 21, 25, 26, 21, 26, 27, 21, 27, 28, 21, 28, 29, 21, 29, 22
|
2020-12-25 19:37:59 +01:00
|
|
|
};
|
|
|
|
|
|
|
|
lcMatrix44 TranslationMatrix = lcMatrix44Translation(lcVector3(30.375f, 30.375f, 0.0f));
|
|
|
|
lcMatrix44 WorldViewMatrix = mCamera->mWorldView;
|
|
|
|
WorldViewMatrix.SetTranslation(lcVector3(0, 0, 0));
|
|
|
|
|
2020-12-26 21:10:14 +01:00
|
|
|
mContext->SetLineWidth(1.0f);
|
2020-12-27 01:30:28 +01:00
|
|
|
mContext->SetMaterial(lcMaterialType::UnlitVertexColor);
|
2020-12-25 19:37:59 +01:00
|
|
|
mContext->SetWorldMatrix(lcMatrix44Identity());
|
|
|
|
mContext->SetViewMatrix(lcMul(WorldViewMatrix, TranslationMatrix));
|
|
|
|
mContext->SetProjectionMatrix(lcMatrix44Ortho(0, mWidth, 0, mHeight, -50, 50));
|
|
|
|
|
|
|
|
mContext->SetVertexBufferPointer(Verts);
|
2020-12-27 01:30:28 +01:00
|
|
|
mContext->SetVertexFormat(0, 3, 0, 0, 4, false);
|
2020-12-25 19:37:59 +01:00
|
|
|
mContext->SetIndexBufferPointer(Indices);
|
|
|
|
|
2020-12-27 01:30:28 +01:00
|
|
|
mContext->DrawIndexedPrimitives(GL_LINES, 6, GL_UNSIGNED_SHORT, 0);
|
|
|
|
mContext->DrawIndexedPrimitives(GL_TRIANGLES, 72, GL_UNSIGNED_SHORT, 6 * 2);
|
2020-12-25 19:37:59 +01:00
|
|
|
|
|
|
|
mContext->SetMaterial(lcMaterialType::UnlitTextureModulate);
|
|
|
|
mContext->SetViewMatrix(TranslationMatrix);
|
|
|
|
mContext->BindTexture2D(gTexFont.GetTexture());
|
|
|
|
glEnable(GL_BLEND);
|
|
|
|
|
|
|
|
float TextBuffer[6 * 5 * 3];
|
|
|
|
lcVector3 PosX = lcMul30(lcVector3(25.0f, 0.0f, 0.0f), WorldViewMatrix);
|
|
|
|
gTexFont.GetGlyphTriangles(PosX.x, PosX.y, PosX.z, 'X', TextBuffer);
|
|
|
|
lcVector3 PosY = lcMul30(lcVector3(0.0f, 25.0f, 0.0f), WorldViewMatrix);
|
|
|
|
gTexFont.GetGlyphTriangles(PosY.x, PosY.y, PosY.z, 'Y', TextBuffer + 5 * 6);
|
|
|
|
lcVector3 PosZ = lcMul30(lcVector3(0.0f, 0.0f, 25.0f), WorldViewMatrix);
|
|
|
|
gTexFont.GetGlyphTriangles(PosZ.x, PosZ.y, PosZ.z, 'Z', TextBuffer + 5 * 6 * 2);
|
|
|
|
|
|
|
|
mContext->SetVertexBufferPointer(TextBuffer);
|
|
|
|
mContext->SetVertexFormat(0, 3, 0, 2, 0, false);
|
|
|
|
|
|
|
|
mContext->SetColor(lcVector4FromColor(lcGetPreferences().mAxesColor));
|
|
|
|
mContext->DrawPrimitives(GL_TRIANGLES, 0, 6 * 3);
|
|
|
|
|
|
|
|
glDisable(GL_BLEND);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::DrawSelectMoveOverlay()
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2020-03-22 21:44:20 +01:00
|
|
|
mContext->SetMaterial(lcMaterialType::UnlitColor);
|
2015-05-17 01:04:35 +02:00
|
|
|
mContext->SetViewMatrix(mCamera->mWorldView);
|
2014-05-18 01:03:05 +02:00
|
|
|
mContext->SetProjectionMatrix(GetProjectionMatrix());
|
|
|
|
|
|
|
|
glDisable(GL_DEPTH_TEST);
|
|
|
|
|
2016-03-13 21:07:28 +01:00
|
|
|
lcVector3 OverlayCenter;
|
|
|
|
lcMatrix33 RelativeRotation;
|
2018-03-29 19:20:36 +02:00
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
ActiveModel->GetMoveRotateTransform(OverlayCenter, RelativeRotation);
|
|
|
|
bool AnyPiecesSelected = ActiveModel->AnyPiecesSelected();
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2015-12-15 20:47:52 +01:00
|
|
|
lcMatrix44 WorldMatrix = lcMatrix44(RelativeRotation, OverlayCenter);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2018-03-29 19:20:36 +02:00
|
|
|
if (ActiveModel != mModel)
|
2018-04-08 02:17:32 +02:00
|
|
|
WorldMatrix = lcMul(WorldMatrix, mActiveSubmodelTransform);
|
2018-03-29 19:20:36 +02:00
|
|
|
|
2015-04-20 04:09:18 +02:00
|
|
|
const float OverlayScale = GetOverlayScale();
|
2015-05-17 01:04:35 +02:00
|
|
|
WorldMatrix = lcMul(lcMatrix44Scale(lcVector3(OverlayScale, OverlayScale, OverlayScale)), WorldMatrix);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2015-05-17 01:04:35 +02:00
|
|
|
mContext->SetWorldMatrix(WorldMatrix);
|
2020-12-26 21:10:14 +01:00
|
|
|
mContext->SetLineWidth(1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2015-04-27 02:47:31 +02:00
|
|
|
mContext->SetIndexBuffer(mRotateMoveIndexBuffer);
|
|
|
|
mContext->SetVertexBuffer(mRotateMoveVertexBuffer);
|
2017-03-24 17:34:53 +01:00
|
|
|
mContext->SetVertexFormatPosition(3);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2018-03-29 19:20:36 +02:00
|
|
|
lcObject* Focus = ActiveModel->GetFocusObject();
|
2017-12-02 21:22:04 +01:00
|
|
|
quint32 AllowedTransforms = Focus ? Focus->GetAllowedTransforms() : LC_OBJECT_TRANSFORM_MOVE_X | LC_OBJECT_TRANSFORM_MOVE_Y | LC_OBJECT_TRANSFORM_MOVE_Z | LC_OBJECT_TRANSFORM_ROTATE_X | LC_OBJECT_TRANSFORM_ROTATE_Y | LC_OBJECT_TRANSFORM_ROTATE_Z;
|
2016-05-01 02:20:37 +02:00
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
if (mTrackButton == lcTrackButton::None || (mTrackTool >= lcTrackTool::MoveX && mTrackTool <= lcTrackTool::MoveXYZ))
|
2015-04-20 04:09:18 +02:00
|
|
|
{
|
2016-05-01 02:20:37 +02:00
|
|
|
if (AllowedTransforms & LC_OBJECT_TRANSFORM_MOVE_X)
|
2015-04-20 04:09:18 +02:00
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
if ((mTrackTool == lcTrackTool::MoveX) || (mTrackTool == lcTrackTool::MoveXY) || (mTrackTool == lcTrackTool::MoveXZ))
|
2016-05-01 02:20:37 +02:00
|
|
|
{
|
|
|
|
mContext->SetColor(0.8f, 0.8f, 0.0f, 1.0f);
|
|
|
|
mContext->DrawIndexedPrimitives(GL_TRIANGLES, 36, GL_UNSIGNED_SHORT, 0);
|
|
|
|
}
|
2020-02-15 20:36:06 +01:00
|
|
|
else if (mTrackButton == lcTrackButton::None)
|
2016-05-01 02:20:37 +02:00
|
|
|
{
|
|
|
|
mContext->SetColor(0.8f, 0.0f, 0.0f, 1.0f);
|
|
|
|
mContext->DrawIndexedPrimitives(GL_TRIANGLES, 36, GL_UNSIGNED_SHORT, 0);
|
|
|
|
}
|
2015-04-20 04:09:18 +02:00
|
|
|
}
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2016-05-01 02:20:37 +02:00
|
|
|
if (AllowedTransforms & LC_OBJECT_TRANSFORM_MOVE_Y)
|
2015-04-20 04:09:18 +02:00
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
if (((mTrackTool == lcTrackTool::MoveY) || (mTrackTool == lcTrackTool::MoveXY) || (mTrackTool == lcTrackTool::MoveYZ)) && (AllowedTransforms & LC_OBJECT_TRANSFORM_MOVE_Y))
|
2016-05-01 02:20:37 +02:00
|
|
|
{
|
|
|
|
mContext->SetColor(0.8f, 0.8f, 0.0f, 1.0f);
|
|
|
|
mContext->DrawIndexedPrimitives(GL_TRIANGLES, 36, GL_UNSIGNED_SHORT, 36 * 2);
|
|
|
|
}
|
2020-02-15 20:36:06 +01:00
|
|
|
else if (mTrackButton == lcTrackButton::None)
|
2016-05-01 02:20:37 +02:00
|
|
|
{
|
|
|
|
mContext->SetColor(0.0f, 0.8f, 0.0f, 1.0f);
|
|
|
|
mContext->DrawIndexedPrimitives(GL_TRIANGLES, 36, GL_UNSIGNED_SHORT, 36 * 2);
|
|
|
|
}
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
2016-05-01 02:20:37 +02:00
|
|
|
if (AllowedTransforms & LC_OBJECT_TRANSFORM_MOVE_Z)
|
2015-04-20 04:09:18 +02:00
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
if (((mTrackTool == lcTrackTool::MoveZ) || (mTrackTool == lcTrackTool::MoveXZ) || (mTrackTool == lcTrackTool::MoveYZ)) && (AllowedTransforms & LC_OBJECT_TRANSFORM_MOVE_Z))
|
2016-05-01 02:20:37 +02:00
|
|
|
{
|
|
|
|
mContext->SetColor(0.8f, 0.8f, 0.0f, 1.0f);
|
|
|
|
mContext->DrawIndexedPrimitives(GL_TRIANGLES, 36, GL_UNSIGNED_SHORT, 72 * 2);
|
|
|
|
}
|
2020-02-15 20:36:06 +01:00
|
|
|
else if (mTrackButton == lcTrackButton::None)
|
2016-05-01 02:20:37 +02:00
|
|
|
{
|
|
|
|
mContext->SetColor(0.0f, 0.0f, 0.8f, 1.0f);
|
|
|
|
mContext->DrawIndexedPrimitives(GL_TRIANGLES, 36, GL_UNSIGNED_SHORT, 72 * 2);
|
|
|
|
}
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
if (gMainWindow->GetTool() == lcTool::Select && mTrackButton == lcTrackButton::None && AnyPiecesSelected)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2016-05-01 02:20:37 +02:00
|
|
|
if (AllowedTransforms & LC_OBJECT_TRANSFORM_ROTATE_X)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
if (mTrackTool == lcTrackTool::RotateX)
|
2016-05-01 02:20:37 +02:00
|
|
|
mContext->SetColor(0.8f, 0.8f, 0.0f, 1.0f);
|
|
|
|
else
|
|
|
|
mContext->SetColor(0.8f, 0.0f, 0.0f, 1.0f);
|
2015-04-20 04:09:18 +02:00
|
|
|
|
2016-05-01 02:20:37 +02:00
|
|
|
mContext->DrawIndexedPrimitives(GL_TRIANGLES, 120, GL_UNSIGNED_SHORT, 108 * 2);
|
|
|
|
}
|
2015-04-20 04:09:18 +02:00
|
|
|
|
2016-05-01 02:20:37 +02:00
|
|
|
if (AllowedTransforms & LC_OBJECT_TRANSFORM_ROTATE_Y)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
if (mTrackTool == lcTrackTool::RotateY)
|
2016-05-01 02:20:37 +02:00
|
|
|
mContext->SetColor(0.8f, 0.8f, 0.0f, 1.0f);
|
|
|
|
else
|
|
|
|
mContext->SetColor(0.0f, 0.8f, 0.0f, 1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2016-05-01 02:20:37 +02:00
|
|
|
mContext->DrawIndexedPrimitives(GL_TRIANGLES, 120, GL_UNSIGNED_SHORT, (108 + 120) * 2);
|
|
|
|
}
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2016-05-01 02:20:37 +02:00
|
|
|
if (AllowedTransforms & LC_OBJECT_TRANSFORM_ROTATE_Z)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
if (mTrackTool == lcTrackTool::RotateZ)
|
2016-05-01 02:20:37 +02:00
|
|
|
mContext->SetColor(0.8f, 0.8f, 0.0f, 1.0f);
|
|
|
|
else
|
|
|
|
mContext->SetColor(0.0f, 0.0f, 0.8f, 1.0f);
|
2015-04-20 04:09:18 +02:00
|
|
|
|
2016-05-01 02:20:37 +02:00
|
|
|
mContext->DrawIndexedPrimitives(GL_TRIANGLES, 120, GL_UNSIGNED_SHORT, (108 + 240) * 2);
|
|
|
|
}
|
2015-04-20 04:09:18 +02:00
|
|
|
}
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
if ((mTrackTool == lcTrackTool::MoveXY) || (mTrackTool == lcTrackTool::MoveXZ) || (mTrackTool == lcTrackTool::MoveYZ))
|
2015-04-20 04:09:18 +02:00
|
|
|
{
|
2014-05-18 01:03:05 +02:00
|
|
|
glEnable(GL_BLEND);
|
|
|
|
|
2015-05-04 02:51:41 +02:00
|
|
|
mContext->SetColor(0.8f, 0.8f, 0.0f, 0.3f);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
if (mTrackTool == lcTrackTool::MoveXY)
|
2015-04-27 02:47:31 +02:00
|
|
|
mContext->DrawIndexedPrimitives(GL_TRIANGLE_FAN, 4, GL_UNSIGNED_SHORT, (108 + 360 + 8) * 2);
|
2020-12-05 01:06:39 +01:00
|
|
|
else if (mTrackTool == lcTrackTool::MoveXZ)
|
2015-04-27 02:47:31 +02:00
|
|
|
mContext->DrawIndexedPrimitives(GL_TRIANGLE_FAN, 4, GL_UNSIGNED_SHORT, (108 + 360 + 4) * 2);
|
2020-12-05 01:06:39 +01:00
|
|
|
else if (mTrackTool == lcTrackTool::MoveYZ)
|
2015-04-27 02:47:31 +02:00
|
|
|
mContext->DrawIndexedPrimitives(GL_TRIANGLE_FAN, 4, GL_UNSIGNED_SHORT, (108 + 360) * 2);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
glDisable(GL_BLEND);
|
|
|
|
}
|
|
|
|
|
2016-03-12 01:05:49 +01:00
|
|
|
if (Focus && Focus->IsPiece())
|
|
|
|
{
|
|
|
|
lcPiece* Piece = (lcPiece*)Focus;
|
2017-12-02 21:22:04 +01:00
|
|
|
quint32 Section = Piece->GetFocusSection();
|
2016-03-12 01:05:49 +01:00
|
|
|
|
2020-03-22 19:12:15 +01:00
|
|
|
if (Section >= LC_PIECE_SECTION_CONTROL_POINT_FIRST && Section <= LC_PIECE_SECTION_CONTROL_POINT_LAST && Piece->mPieceInfo->GetSynthInfo() && Piece->mPieceInfo->GetSynthInfo()->IsCurve())
|
2016-03-12 01:05:49 +01:00
|
|
|
{
|
2020-03-22 19:12:15 +01:00
|
|
|
int ControlPointIndex = Section - LC_PIECE_SECTION_CONTROL_POINT_FIRST;
|
2016-03-12 01:05:49 +01:00
|
|
|
float Strength = Piece->GetControlPoints()[ControlPointIndex].Scale;
|
|
|
|
const float ScaleStart = 2.0f;
|
|
|
|
float Length = ScaleStart + Strength / OverlayScale;
|
|
|
|
const float OverlayScaleInnerRadius = 0.075f;
|
|
|
|
const float OverlayScaleRadius = 0.125f;
|
|
|
|
|
|
|
|
lcVector3 Verts[38];
|
|
|
|
int NumVerts = 0;
|
|
|
|
|
2016-04-19 18:30:29 +02:00
|
|
|
Verts[NumVerts++] = lcVector3(Length - OverlayScaleRadius, 0.0f, 0.0f);
|
|
|
|
Verts[NumVerts++] = lcVector3(OverlayScaleRadius - Length, 0.0f, 0.0f);
|
2016-03-12 01:05:49 +01:00
|
|
|
|
|
|
|
float SinTable[9], CosTable[9];
|
|
|
|
|
|
|
|
for (int Step = 0; Step <= 8; Step++)
|
|
|
|
{
|
|
|
|
SinTable[Step] = sinf((float)Step / 8.0f * LC_2PI);
|
|
|
|
CosTable[Step] = cosf((float)Step / 8.0f * LC_2PI);
|
|
|
|
}
|
|
|
|
|
|
|
|
for (int Step = 0; Step <= 8; Step++)
|
|
|
|
{
|
|
|
|
float x = CosTable[Step];
|
|
|
|
float y = SinTable[Step];
|
|
|
|
|
2016-04-19 18:30:29 +02:00
|
|
|
Verts[NumVerts++] = lcVector3(Length + x * OverlayScaleInnerRadius, 0.0f, y * OverlayScaleInnerRadius);
|
|
|
|
Verts[NumVerts++] = lcVector3(Length + x * OverlayScaleRadius, 0.0f, y * OverlayScaleRadius);
|
2016-03-12 01:05:49 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
for (int Step = 0; Step <= 8; Step++)
|
|
|
|
{
|
|
|
|
float x = CosTable[Step];
|
|
|
|
float y = SinTable[Step];
|
|
|
|
|
2016-04-19 18:30:29 +02:00
|
|
|
Verts[NumVerts++] = lcVector3(-Length + x * OverlayScaleInnerRadius, 0.0f, y * OverlayScaleInnerRadius);
|
|
|
|
Verts[NumVerts++] = lcVector3(-Length + x * OverlayScaleRadius, 0.0f, y * OverlayScaleRadius);
|
2016-03-12 01:05:49 +01:00
|
|
|
}
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
if (mTrackTool == lcTrackTool::ScalePlus || mTrackTool == lcTrackTool::ScaleMinus)
|
2016-03-12 01:05:49 +01:00
|
|
|
mContext->SetColor(0.8f, 0.8f, 0.0f, 0.3f);
|
|
|
|
else
|
|
|
|
mContext->SetColor(0.0f, 0.0f, 0.8f, 1.0f);
|
|
|
|
|
|
|
|
mContext->SetVertexBufferPointer(Verts);
|
|
|
|
mContext->ClearIndexBuffer();
|
2017-03-24 17:34:53 +01:00
|
|
|
mContext->SetVertexFormatPosition(3);
|
2016-03-12 01:05:49 +01:00
|
|
|
|
|
|
|
mContext->DrawPrimitives(GL_LINES, 0, 2);
|
|
|
|
mContext->DrawPrimitives(GL_TRIANGLE_STRIP, 2, 18);
|
|
|
|
mContext->DrawPrimitives(GL_TRIANGLE_STRIP, 20, 18);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-05-18 01:03:05 +02:00
|
|
|
glEnable(GL_DEPTH_TEST);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::DrawRotateOverlay()
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
const float OverlayScale = GetOverlayScale();
|
|
|
|
const float OverlayRotateRadius = 2.0f;
|
|
|
|
|
2020-03-22 21:44:20 +01:00
|
|
|
mContext->SetMaterial(lcMaterialType::UnlitColor);
|
2015-05-17 01:04:35 +02:00
|
|
|
mContext->SetViewMatrix(mCamera->mWorldView);
|
2014-05-18 01:03:05 +02:00
|
|
|
mContext->SetProjectionMatrix(GetProjectionMatrix());
|
2020-12-26 21:10:14 +01:00
|
|
|
mContext->SetLineWidth(1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
glDisable(GL_DEPTH_TEST);
|
|
|
|
|
|
|
|
int j;
|
|
|
|
|
2016-03-13 21:07:28 +01:00
|
|
|
lcVector3 OverlayCenter;
|
|
|
|
lcMatrix33 RelativeRotation;
|
2018-03-29 19:20:36 +02:00
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
ActiveModel->GetMoveRotateTransform(OverlayCenter, RelativeRotation);
|
|
|
|
lcVector3 MouseToolDistance = ActiveModel->SnapRotation(ActiveModel->GetMouseToolDistance());
|
2014-05-18 01:03:05 +02:00
|
|
|
bool HasAngle = false;
|
|
|
|
|
|
|
|
// Draw a disc showing the rotation amount.
|
2020-02-15 20:36:06 +01:00
|
|
|
if (MouseToolDistance.LengthSquared() != 0.0f && (mTrackButton != lcTrackButton::None))
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
lcVector4 Rotation;
|
|
|
|
float Angle, Step;
|
|
|
|
|
|
|
|
HasAngle = true;
|
|
|
|
|
|
|
|
switch (mTrackTool)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateX:
|
2015-05-04 02:51:41 +02:00
|
|
|
mContext->SetColor(0.8f, 0.0f, 0.0f, 0.3f);
|
2014-05-18 01:03:05 +02:00
|
|
|
Angle = MouseToolDistance[0];
|
|
|
|
Rotation = lcVector4(0.0f, 0.0f, 0.0f, 1.0f);
|
|
|
|
break;
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateY:
|
2015-05-04 02:51:41 +02:00
|
|
|
mContext->SetColor(0.0f, 0.8f, 0.0f, 0.3f);
|
2014-05-18 01:03:05 +02:00
|
|
|
Angle = MouseToolDistance[1];
|
|
|
|
Rotation = lcVector4(90.0f, 0.0f, 0.0f, 1.0f);
|
|
|
|
break;
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateZ:
|
2015-05-04 02:51:41 +02:00
|
|
|
mContext->SetColor(0.0f, 0.0f, 0.8f, 0.3f);
|
2014-05-18 01:03:05 +02:00
|
|
|
Angle = MouseToolDistance[2];
|
|
|
|
Rotation = lcVector4(90.0f, 0.0f, -1.0f, 0.0f);
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
Rotation = lcVector4(0.0f, 0.0f, 0.0f, 1.0f);
|
|
|
|
Angle = 0.0f;
|
|
|
|
break;
|
|
|
|
};
|
|
|
|
|
|
|
|
if (Angle > 0.0f)
|
|
|
|
{
|
|
|
|
Step = 360.0f / 32;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
Angle = -Angle;
|
|
|
|
Step = -360.0f / 32;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (fabsf(Angle) >= fabsf(Step))
|
|
|
|
{
|
2015-12-15 20:47:52 +01:00
|
|
|
lcMatrix44 WorldMatrix = lcMatrix44(RelativeRotation, OverlayCenter);
|
2015-05-17 01:04:35 +02:00
|
|
|
WorldMatrix = lcMul(lcMatrix44FromAxisAngle(lcVector3(Rotation[1], Rotation[2], Rotation[3]), Rotation[0] * LC_DTOR), WorldMatrix);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2015-05-17 01:04:35 +02:00
|
|
|
mContext->SetWorldMatrix(WorldMatrix);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
glEnable(GL_BLEND);
|
|
|
|
|
|
|
|
lcVector3 Verts[33];
|
|
|
|
Verts[0] = lcVector3(0.0f, 0.0f, 0.0f);
|
|
|
|
int NumVerts = 1;
|
|
|
|
|
2015-05-25 20:02:57 +02:00
|
|
|
mContext->SetVertexBufferPointer(Verts);
|
2017-03-24 17:34:53 +01:00
|
|
|
mContext->SetVertexFormatPosition(3);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
float StartAngle;
|
|
|
|
int i = 0;
|
|
|
|
|
|
|
|
if (Step < 0)
|
|
|
|
StartAngle = -Angle;
|
|
|
|
else
|
|
|
|
StartAngle = Angle;
|
|
|
|
|
|
|
|
do
|
|
|
|
{
|
|
|
|
float x = cosf((Step * i - StartAngle) * LC_DTOR) * OverlayRotateRadius * OverlayScale;
|
|
|
|
float y = sinf((Step * i - StartAngle) * LC_DTOR) * OverlayRotateRadius * OverlayScale;
|
|
|
|
|
|
|
|
Verts[NumVerts++] = lcVector3(0.0f, x, y);
|
|
|
|
|
|
|
|
if (NumVerts == 33)
|
|
|
|
{
|
2015-05-25 20:02:57 +02:00
|
|
|
mContext->DrawPrimitives(GL_TRIANGLE_FAN, 0, NumVerts);
|
2014-05-18 01:03:05 +02:00
|
|
|
Verts[1] = Verts[32];
|
|
|
|
NumVerts = 2;
|
|
|
|
}
|
|
|
|
|
|
|
|
i++;
|
|
|
|
if (Step > 0)
|
|
|
|
Angle -= Step;
|
|
|
|
else
|
|
|
|
Angle += Step;
|
|
|
|
|
|
|
|
} while (Angle >= 0.0f);
|
|
|
|
|
|
|
|
if (NumVerts > 2)
|
2015-05-25 20:02:57 +02:00
|
|
|
mContext->DrawPrimitives(GL_TRIANGLE_FAN, 0, NumVerts);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
glDisable(GL_BLEND);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// Draw the circles.
|
2020-12-05 00:38:49 +01:00
|
|
|
if (gMainWindow->GetTool() == lcTool::Rotate && !HasAngle && mTrackButton == lcTrackButton::None)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2015-05-17 01:04:35 +02:00
|
|
|
lcMatrix44 Mat = lcMatrix44AffineInverse(mCamera->mWorldView);
|
|
|
|
Mat.SetTranslation(OverlayCenter);
|
|
|
|
|
2014-05-18 01:03:05 +02:00
|
|
|
lcVector3 Verts[32];
|
|
|
|
|
|
|
|
for (j = 0; j < 32; j++)
|
|
|
|
{
|
|
|
|
lcVector3 Pt;
|
|
|
|
|
|
|
|
Pt[0] = cosf(LC_2PI * j / 32) * OverlayRotateRadius * OverlayScale;
|
|
|
|
Pt[1] = sinf(LC_2PI * j / 32) * OverlayRotateRadius * OverlayScale;
|
|
|
|
Pt[2] = 0.0f;
|
|
|
|
|
|
|
|
Verts[j] = lcMul31(Pt, Mat);
|
|
|
|
}
|
|
|
|
|
2015-05-04 02:51:41 +02:00
|
|
|
mContext->SetColor(0.1f, 0.1f, 0.1f, 1.0f);
|
2015-05-17 01:04:35 +02:00
|
|
|
mContext->SetWorldMatrix(lcMatrix44Identity());
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2015-05-25 20:02:57 +02:00
|
|
|
mContext->SetVertexBufferPointer(Verts);
|
2017-03-24 17:34:53 +01:00
|
|
|
mContext->SetVertexFormatPosition(3);
|
2015-05-25 20:02:57 +02:00
|
|
|
|
|
|
|
mContext->DrawPrimitives(GL_LINE_LOOP, 0, 32);
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
lcVector3 ViewDir = mCamera->mTargetPosition - mCamera->mPosition;
|
|
|
|
ViewDir.Normalize();
|
|
|
|
|
|
|
|
// Transform ViewDir to local space.
|
2015-12-15 20:47:52 +01:00
|
|
|
ViewDir = lcMul(ViewDir, lcMatrix33AffineInverse(RelativeRotation));
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2017-04-03 02:15:09 +02:00
|
|
|
mContext->SetWorldMatrix(lcMatrix44(RelativeRotation, OverlayCenter));
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
// Draw each axis circle.
|
|
|
|
for (int i = 0; i < 3; i++)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
if (static_cast<int>(mTrackTool) == static_cast<int>(lcTrackTool::RotateX) + i)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2015-05-04 02:51:41 +02:00
|
|
|
mContext->SetColor(0.8f, 0.8f, 0.0f, 1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2020-12-05 00:38:49 +01:00
|
|
|
if (gMainWindow->GetTool() != lcTool::Rotate || HasAngle || mTrackButton != lcTrackButton::None)
|
2014-05-18 01:03:05 +02:00
|
|
|
continue;
|
|
|
|
|
|
|
|
switch (i)
|
|
|
|
{
|
|
|
|
case 0:
|
2015-05-04 02:51:41 +02:00
|
|
|
mContext->SetColor(0.8f, 0.0f, 0.0f, 1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
case 1:
|
2015-05-04 02:51:41 +02:00
|
|
|
mContext->SetColor(0.0f, 0.8f, 0.0f, 1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
case 2:
|
2015-05-04 02:51:41 +02:00
|
|
|
mContext->SetColor(0.0f, 0.0f, 0.8f, 1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
lcVector3 Verts[64];
|
|
|
|
int NumVerts = 0;
|
|
|
|
|
|
|
|
for (j = 0; j < 32; j++)
|
|
|
|
{
|
|
|
|
lcVector3 v1, v2;
|
|
|
|
|
|
|
|
switch (i)
|
|
|
|
{
|
|
|
|
case 0:
|
|
|
|
v1 = lcVector3(0.0f, cosf(LC_2PI * j / 32), sinf(LC_2PI * j / 32));
|
|
|
|
v2 = lcVector3(0.0f, cosf(LC_2PI * (j + 1) / 32), sinf(LC_2PI * (j + 1) / 32));
|
|
|
|
break;
|
|
|
|
|
|
|
|
case 1:
|
|
|
|
v1 = lcVector3(cosf(LC_2PI * j / 32), 0.0f, sinf(LC_2PI * j / 32));
|
|
|
|
v2 = lcVector3(cosf(LC_2PI * (j + 1) / 32), 0.0f, sinf(LC_2PI * (j + 1) / 32));
|
|
|
|
break;
|
|
|
|
|
|
|
|
case 2:
|
|
|
|
v1 = lcVector3(cosf(LC_2PI * j / 32), sinf(LC_2PI * j / 32), 0.0f);
|
|
|
|
v2 = lcVector3(cosf(LC_2PI * (j + 1) / 32), sinf(LC_2PI * (j + 1) / 32), 0.0f);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
if (gMainWindow->GetTool() != lcTool::Rotate || HasAngle || mTrackButton != lcTrackButton::None || lcDot(ViewDir, v1 + v2) <= 0.0f)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
Verts[NumVerts++] = v1 * (OverlayRotateRadius * OverlayScale);
|
|
|
|
Verts[NumVerts++] = v2 * (OverlayRotateRadius * OverlayScale);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2015-05-25 20:02:57 +02:00
|
|
|
mContext->SetVertexBufferPointer(Verts);
|
2017-03-24 17:34:53 +01:00
|
|
|
mContext->SetVertexFormatPosition(3);
|
2015-05-25 20:02:57 +02:00
|
|
|
|
|
|
|
mContext->DrawPrimitives(GL_LINES, 0, NumVerts);
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
// Draw tangent vector.
|
2020-12-05 01:06:39 +01:00
|
|
|
if (mTrackButton != lcTrackButton::None && ((mTrackTool == lcTrackTool::RotateX) || (mTrackTool == lcTrackTool::RotateY) || (mTrackTool == lcTrackTool::RotateZ)))
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
const float OverlayRotateArrowSize = 1.5f;
|
|
|
|
const float OverlayRotateArrowCapSize = 0.25f;
|
|
|
|
|
|
|
|
lcVector4 Rotation;
|
|
|
|
float Angle;
|
|
|
|
|
|
|
|
switch (mTrackTool)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateX:
|
2014-05-18 01:03:05 +02:00
|
|
|
Angle = MouseToolDistance[0];
|
|
|
|
Rotation = lcVector4(0.0f, 0.0f, 0.0f, 1.0f);
|
|
|
|
break;
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateY:
|
2014-05-18 01:03:05 +02:00
|
|
|
Angle = MouseToolDistance[1];
|
|
|
|
Rotation = lcVector4(90.0f, 0.0f, 0.0f, 1.0f);
|
|
|
|
break;
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateZ:
|
2014-05-18 01:03:05 +02:00
|
|
|
Angle = MouseToolDistance[2];
|
|
|
|
Rotation = lcVector4(90.0f, 0.0f, -1.0f, 0.0f);
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
Angle = 0.0f;
|
|
|
|
Rotation = lcVector4(0.0f, 0.0f, 1.0f, 0.0f);
|
|
|
|
break;
|
|
|
|
};
|
|
|
|
|
2015-12-15 20:47:52 +01:00
|
|
|
lcMatrix44 WorldMatrix = lcMatrix44(RelativeRotation, OverlayCenter);
|
2015-05-17 01:04:35 +02:00
|
|
|
WorldMatrix = lcMul(lcMatrix44FromAxisAngle(lcVector3(Rotation[1], Rotation[2], Rotation[3]), Rotation[0] * LC_DTOR), WorldMatrix);
|
|
|
|
mContext->SetWorldMatrix(WorldMatrix);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2015-05-04 02:51:41 +02:00
|
|
|
mContext->SetColor(0.8f, 0.8f, 0.0f, 1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
if (HasAngle)
|
|
|
|
{
|
|
|
|
float StartY = OverlayScale * OverlayRotateRadius;
|
|
|
|
float EndZ = (Angle > 0.0f) ? OverlayScale * OverlayRotateArrowSize : -OverlayScale * OverlayRotateArrowSize;
|
|
|
|
float TipZ = (Angle > 0.0f) ? -OverlayScale * OverlayRotateArrowCapSize : OverlayScale * OverlayRotateArrowCapSize;
|
|
|
|
|
|
|
|
lcVector3 Verts[6];
|
|
|
|
|
|
|
|
Verts[0] = lcVector3(0.0f, StartY, 0.0f);
|
|
|
|
Verts[1] = lcVector3(0.0f, StartY, EndZ);
|
|
|
|
|
|
|
|
Verts[2] = lcVector3(0.0f, StartY, EndZ);
|
|
|
|
Verts[3] = lcVector3(0.0f, StartY + OverlayScale * OverlayRotateArrowCapSize, EndZ + TipZ);
|
|
|
|
|
|
|
|
Verts[4] = lcVector3(0.0f, StartY, EndZ);
|
|
|
|
Verts[5] = lcVector3(0.0f, StartY - OverlayScale * OverlayRotateArrowCapSize, EndZ + TipZ);
|
|
|
|
|
2015-05-25 20:02:57 +02:00
|
|
|
mContext->SetVertexBufferPointer(Verts);
|
2017-03-24 17:34:53 +01:00
|
|
|
mContext->SetVertexFormatPosition(3);
|
2015-05-25 20:02:57 +02:00
|
|
|
|
|
|
|
mContext->DrawPrimitives(GL_LINES, 0, 6);
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
// Draw text.
|
|
|
|
lcVector3 ScreenPos = ProjectPoint(OverlayCenter);
|
|
|
|
|
2020-03-22 21:44:20 +01:00
|
|
|
mContext->SetMaterial(lcMaterialType::UnlitTextureModulate);
|
2015-05-17 01:04:35 +02:00
|
|
|
mContext->SetWorldMatrix(lcMatrix44Identity());
|
|
|
|
mContext->SetViewMatrix(lcMatrix44Translation(lcVector3(0.375, 0.375, 0.0)));
|
2014-05-18 01:03:05 +02:00
|
|
|
mContext->SetProjectionMatrix(lcMatrix44Ortho(0.0f, mWidth, 0.0f, mHeight, -1.0f, 1.0f));
|
2017-12-26 19:19:20 +01:00
|
|
|
mContext->BindTexture2D(gTexFont.GetTexture());
|
2014-05-18 01:03:05 +02:00
|
|
|
glEnable(GL_BLEND);
|
|
|
|
|
|
|
|
char buf[32];
|
|
|
|
sprintf(buf, "[%.2f]", fabsf(Angle));
|
|
|
|
|
|
|
|
int cx, cy;
|
2014-08-24 00:56:59 +02:00
|
|
|
gTexFont.GetStringDimensions(&cx, &cy, buf);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2015-05-04 02:51:41 +02:00
|
|
|
mContext->SetColor(0.8f, 0.8f, 0.0f, 1.0f);
|
2015-05-25 19:36:22 +02:00
|
|
|
gTexFont.PrintText(mContext, ScreenPos[0] - (cx / 2), ScreenPos[1] + (cy / 2), 0.0f, buf);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
glDisable(GL_BLEND);
|
|
|
|
}
|
|
|
|
|
|
|
|
glEnable(GL_DEPTH_TEST);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::DrawSelectZoomRegionOverlay()
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2020-03-22 21:44:20 +01:00
|
|
|
mContext->SetMaterial(lcMaterialType::UnlitColor);
|
2015-05-17 01:04:35 +02:00
|
|
|
mContext->SetWorldMatrix(lcMatrix44Identity());
|
|
|
|
mContext->SetViewMatrix(lcMatrix44Translation(lcVector3(0.375, 0.375, 0.0)));
|
2014-05-18 01:03:05 +02:00
|
|
|
mContext->SetProjectionMatrix(lcMatrix44Ortho(0.0f, mWidth, 0.0f, mHeight, -1.0f, 1.0f));
|
2020-12-26 21:10:14 +01:00
|
|
|
mContext->SetLineWidth(1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
glDisable(GL_DEPTH_TEST);
|
|
|
|
|
|
|
|
float pt1x = (float)mMouseDownX;
|
|
|
|
float pt1y = (float)mMouseDownY;
|
2020-12-05 17:45:29 +01:00
|
|
|
float pt2x = (float)mMouseX;
|
|
|
|
float pt2y = (float)mMouseY;
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
float Left, Right, Bottom, Top;
|
|
|
|
|
|
|
|
if (pt1x < pt2x)
|
|
|
|
{
|
|
|
|
Left = pt1x;
|
|
|
|
Right = pt2x;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
Left = pt2x;
|
|
|
|
Right = pt1x;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (pt1y < pt2y)
|
|
|
|
{
|
|
|
|
Bottom = pt1y;
|
|
|
|
Top = pt2y;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
Bottom = pt2y;
|
|
|
|
Top = pt1y;
|
|
|
|
}
|
|
|
|
|
|
|
|
Left = lcMax(Left, 0.0f);
|
2015-04-26 20:14:33 +02:00
|
|
|
Right = lcMin(Right, mWidth - 1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
Bottom = lcMax(Bottom, 0.0f);
|
2015-04-26 20:14:33 +02:00
|
|
|
Top = lcMin(Top, mHeight - 1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
float BorderX = lcMin(2.0f, Right - Left);
|
|
|
|
float BorderY = lcMin(2.0f, Top - Bottom);
|
|
|
|
|
|
|
|
float Verts[14][2] =
|
|
|
|
{
|
|
|
|
{ Left, Bottom },
|
|
|
|
{ Left + BorderX, Bottom + BorderY },
|
|
|
|
{ Right, Bottom },
|
|
|
|
{ Right - BorderX, Bottom + BorderY },
|
|
|
|
{ Right, Top },
|
|
|
|
{ Right - BorderX, Top - BorderY },
|
|
|
|
{ Left, Top },
|
|
|
|
{ Left + BorderX, Top - BorderY },
|
|
|
|
{ Left, Bottom },
|
|
|
|
{ Left + BorderX, Bottom + BorderY },
|
|
|
|
{ Left + BorderX, Bottom + BorderY },
|
|
|
|
{ Right - BorderX, Bottom + BorderY },
|
|
|
|
{ Left + BorderX, Top - BorderY },
|
|
|
|
{ Right - BorderX, Top - BorderY },
|
|
|
|
};
|
|
|
|
|
2015-04-14 06:14:10 +02:00
|
|
|
mContext->SetVertexBufferPointer(Verts);
|
2017-03-24 17:34:53 +01:00
|
|
|
mContext->SetVertexFormatPosition(2);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2021-01-01 00:54:28 +01:00
|
|
|
const lcPreferences& Preferences = lcGetPreferences();
|
|
|
|
|
|
|
|
mContext->SetColor(lcVector4FromColor(Preferences.mMarqueeBorderColor));
|
2015-04-14 06:14:10 +02:00
|
|
|
mContext->DrawPrimitives(GL_TRIANGLE_STRIP, 0, 10);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2021-01-01 00:54:28 +01:00
|
|
|
if (LC_RGBA_ALPHA(Preferences.mMarqueeFillColor))
|
|
|
|
{
|
|
|
|
glEnable(GL_BLEND);
|
|
|
|
mContext->SetColor(lcVector4FromColor(Preferences.mMarqueeFillColor));
|
|
|
|
mContext->DrawPrimitives(GL_TRIANGLE_STRIP, 10, 4);
|
|
|
|
glDisable(GL_BLEND);
|
|
|
|
}
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
glEnable(GL_DEPTH_TEST);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::DrawRotateViewOverlay()
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
int x, y, w, h;
|
|
|
|
|
|
|
|
x = 0;
|
|
|
|
y = 0;
|
|
|
|
w = mWidth;
|
|
|
|
h = mHeight;
|
|
|
|
|
2020-03-22 21:44:20 +01:00
|
|
|
mContext->SetMaterial(lcMaterialType::UnlitColor);
|
2015-05-17 01:04:35 +02:00
|
|
|
mContext->SetWorldMatrix(lcMatrix44Identity());
|
|
|
|
mContext->SetViewMatrix(lcMatrix44Translation(lcVector3(0.375, 0.375, 0.0)));
|
2014-05-18 01:03:05 +02:00
|
|
|
mContext->SetProjectionMatrix(lcMatrix44Ortho(0, w, 0, h, -1, 1));
|
2020-12-26 21:10:14 +01:00
|
|
|
mContext->SetLineWidth(1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
glDisable(GL_DEPTH_TEST);
|
2020-07-11 19:47:52 +02:00
|
|
|
mContext->SetColor(lcVector4FromColor(lcGetPreferences().mOverlayColor));
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2015-04-14 06:14:10 +02:00
|
|
|
float Verts[32 * 16 * 2];
|
|
|
|
float* CurVert = Verts;
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
float r = lcMin(w, h) * 0.35f;
|
|
|
|
float cx = x + w / 2.0f;
|
|
|
|
float cy = y + h / 2.0f;
|
|
|
|
|
|
|
|
for (int i = 0; i < 32; i++)
|
|
|
|
{
|
2015-04-14 06:14:10 +02:00
|
|
|
*CurVert++ = cosf((float)i / 32.0f * (2.0f * LC_PI)) * r + cx;
|
|
|
|
*CurVert++ = sinf((float)i / 32.0f * (2.0f * LC_PI)) * r + cy;
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
2015-04-26 20:14:33 +02:00
|
|
|
const float OverlayCameraSquareSize = lcMax(8.0f, (w + h) / 200.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2015-04-14 06:14:10 +02:00
|
|
|
*CurVert++ = cx + OverlayCameraSquareSize; *CurVert++ = cy + r + OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx - OverlayCameraSquareSize; *CurVert++ = cy + r + OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx - OverlayCameraSquareSize; *CurVert++ = cy + r - OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx + OverlayCameraSquareSize; *CurVert++ = cy + r - OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx + OverlayCameraSquareSize; *CurVert++ = cy - r + OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx - OverlayCameraSquareSize; *CurVert++ = cy - r + OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx - OverlayCameraSquareSize; *CurVert++ = cy - r - OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx + OverlayCameraSquareSize; *CurVert++ = cy - r - OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx + r + OverlayCameraSquareSize; *CurVert++ = cy + OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx + r - OverlayCameraSquareSize; *CurVert++ = cy + OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx + r - OverlayCameraSquareSize; *CurVert++ = cy - OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx + r + OverlayCameraSquareSize; *CurVert++ = cy - OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx - r + OverlayCameraSquareSize; *CurVert++ = cy + OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx - r - OverlayCameraSquareSize; *CurVert++ = cy + OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx - r - OverlayCameraSquareSize; *CurVert++ = cy - OverlayCameraSquareSize;
|
|
|
|
*CurVert++ = cx - r + OverlayCameraSquareSize; *CurVert++ = cy - OverlayCameraSquareSize;
|
|
|
|
|
|
|
|
mContext->SetVertexBufferPointer(Verts);
|
2017-03-24 17:34:53 +01:00
|
|
|
mContext->SetVertexFormatPosition(2);
|
2015-04-14 06:14:10 +02:00
|
|
|
|
|
|
|
GLushort Indices[64 + 32] =
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2015-04-14 06:14:10 +02:00
|
|
|
0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 5, 6, 6, 7, 7, 8, 8, 9, 9, 10, 10, 11, 11, 12, 12, 13, 13, 14, 14, 15, 15, 16, 16,
|
|
|
|
17, 17, 18, 18, 19, 19, 20, 20, 21, 21, 22, 22, 23, 23, 24, 24, 25, 25, 26, 26, 27, 27, 28, 28, 29, 29, 30, 30, 31, 31, 0,
|
|
|
|
32, 33, 33, 34, 34, 35, 35, 32, 36, 37, 37, 38, 38, 39, 39, 36,
|
|
|
|
40, 41, 41, 42, 42, 43, 43, 40, 44, 45, 45, 46, 46, 47, 47, 44
|
2014-05-18 01:03:05 +02:00
|
|
|
};
|
|
|
|
|
2015-05-17 01:04:35 +02:00
|
|
|
mContext->SetIndexBufferPointer(Indices);
|
|
|
|
mContext->DrawIndexedPrimitives(GL_LINES, 96, GL_UNSIGNED_SHORT, 0);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
glEnable(GL_DEPTH_TEST);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::DrawGrid()
|
2014-08-24 00:56:59 +02:00
|
|
|
{
|
|
|
|
const lcPreferences& Preferences = lcGetPreferences();
|
2020-12-24 04:10:54 +01:00
|
|
|
|
2017-02-13 03:05:20 +01:00
|
|
|
if (!Preferences.mDrawGridStuds && !Preferences.mDrawGridLines)
|
|
|
|
return;
|
2014-08-24 00:56:59 +02:00
|
|
|
|
2020-12-24 04:10:54 +01:00
|
|
|
if (!Preferences.mGridEnabled)
|
|
|
|
return;
|
|
|
|
|
2014-08-24 00:56:59 +02:00
|
|
|
const int Spacing = lcMax(Preferences.mGridLineSpacing, 1);
|
|
|
|
int MinX, MaxX, MinY, MaxY;
|
2016-02-19 18:53:54 +01:00
|
|
|
lcVector3 Min(FLT_MAX, FLT_MAX, FLT_MAX), Max(-FLT_MAX, -FLT_MAX, -FLT_MAX);
|
2014-08-24 00:56:59 +02:00
|
|
|
|
2016-02-19 18:53:54 +01:00
|
|
|
bool GridSizeValid = mModel->GetPiecesBoundingBox(Min, Max);
|
2014-10-10 03:25:31 +02:00
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
if (mTrackTool == lcTrackTool::Insert)
|
2014-10-10 03:25:31 +02:00
|
|
|
{
|
2016-12-16 18:14:19 +01:00
|
|
|
PieceInfo* CurPiece = gMainWindow->GetCurrentPieceInfo();
|
2014-10-10 03:25:31 +02:00
|
|
|
|
2015-01-07 17:52:42 +01:00
|
|
|
if (CurPiece)
|
2014-10-10 03:25:31 +02:00
|
|
|
{
|
2016-02-19 18:53:54 +01:00
|
|
|
lcVector3 Points[8];
|
|
|
|
lcGetBoxCorners(CurPiece->GetBoundingBox(), Points);
|
2014-10-10 03:25:31 +02:00
|
|
|
|
2017-11-13 04:38:07 +01:00
|
|
|
lcMatrix44 WorldMatrix = GetPieceInsertPosition(false, CurPiece);
|
2014-10-10 03:25:31 +02:00
|
|
|
|
2015-01-07 17:52:42 +01:00
|
|
|
for (int i = 0; i < 8; i++)
|
|
|
|
{
|
2015-01-10 21:30:37 +01:00
|
|
|
lcVector3 Point = lcMul31(Points[i], WorldMatrix);
|
2015-01-07 17:52:42 +01:00
|
|
|
|
2016-02-19 18:53:54 +01:00
|
|
|
Min = lcMin(Point, Min);
|
|
|
|
Max = lcMax(Point, Max);
|
2015-01-07 17:52:42 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
GridSizeValid = true;
|
|
|
|
}
|
2014-10-10 03:25:31 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
if (GridSizeValid)
|
2014-08-24 00:56:59 +02:00
|
|
|
{
|
2016-02-19 18:53:54 +01:00
|
|
|
MinX = (int)(floorf(Min[0] / (20.0f * Spacing))) - 1;
|
|
|
|
MinY = (int)(floorf(Min[1] / (20.0f * Spacing))) - 1;
|
|
|
|
MaxX = (int)(ceilf(Max[0] / (20.0f * Spacing))) + 1;
|
|
|
|
MaxY = (int)(ceilf(Max[1] / (20.0f * Spacing))) + 1;
|
2014-08-24 00:56:59 +02:00
|
|
|
|
|
|
|
MinX = lcMin(MinX, -2);
|
|
|
|
MinY = lcMin(MinY, -2);
|
|
|
|
MaxX = lcMax(MaxX, 2);
|
|
|
|
MaxY = lcMax(MaxY, 2);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
MinX = -2;
|
|
|
|
MinY = -2;
|
|
|
|
MaxX = 2;
|
|
|
|
MaxY = 2;
|
|
|
|
}
|
|
|
|
|
2015-05-01 00:35:40 +02:00
|
|
|
if (!mGridBuffer.IsValid() || MinX != mGridSettings[0] || MinY != mGridSettings[1] || MaxX != mGridSettings[2] || MaxY != mGridSettings[3] ||
|
2015-04-14 06:14:10 +02:00
|
|
|
Spacing != mGridSettings[4] || (Preferences.mDrawGridStuds ? 1 : 0) != mGridSettings[5] || (Preferences.mDrawGridLines ? 1 : 0) != mGridSettings[6])
|
2014-08-24 00:56:59 +02:00
|
|
|
{
|
2015-04-26 20:14:33 +02:00
|
|
|
int VertexBufferSize = 0;
|
2015-04-14 06:14:10 +02:00
|
|
|
|
|
|
|
if (Preferences.mDrawGridStuds)
|
2015-04-26 20:14:33 +02:00
|
|
|
VertexBufferSize += 4 * 5 * sizeof(float);
|
2015-04-14 06:14:10 +02:00
|
|
|
|
|
|
|
if (Preferences.mDrawGridLines)
|
2015-04-26 20:14:33 +02:00
|
|
|
VertexBufferSize += 2 * (MaxX - MinX + MaxY - MinY + 2) * 3 * sizeof(float);
|
2015-04-14 06:14:10 +02:00
|
|
|
|
2015-04-26 20:14:33 +02:00
|
|
|
float* Verts = (float*)malloc(VertexBufferSize);
|
2017-04-03 02:15:09 +02:00
|
|
|
if (!Verts)
|
|
|
|
return;
|
2015-04-26 20:14:33 +02:00
|
|
|
float* CurVert = Verts;
|
2015-04-14 06:14:10 +02:00
|
|
|
|
|
|
|
if (Preferences.mDrawGridStuds)
|
|
|
|
{
|
|
|
|
float Left = MinX * 20.0f * Spacing;
|
|
|
|
float Right = MaxX * 20.0f * Spacing;
|
|
|
|
float Top = MinY * 20.0f * Spacing;
|
|
|
|
float Bottom = MaxY * 20.0f * Spacing;
|
|
|
|
float Z = 0;
|
|
|
|
float U = (MaxX - MinX) * Spacing;
|
|
|
|
float V = (MaxY - MinY) * Spacing;
|
|
|
|
|
|
|
|
*CurVert++ = Left;
|
|
|
|
*CurVert++ = Top;
|
|
|
|
*CurVert++ = Z;
|
|
|
|
*CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = V;
|
|
|
|
|
|
|
|
*CurVert++ = Left;
|
|
|
|
*CurVert++ = Bottom;
|
|
|
|
*CurVert++ = Z;
|
|
|
|
*CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = 0.0f;
|
|
|
|
|
|
|
|
*CurVert++ = Right;
|
2017-02-11 17:30:57 +01:00
|
|
|
*CurVert++ = Top;
|
2015-04-14 06:14:10 +02:00
|
|
|
*CurVert++ = Z;
|
|
|
|
*CurVert++ = U;
|
2017-02-11 17:30:57 +01:00
|
|
|
*CurVert++ = V;
|
2015-04-14 06:14:10 +02:00
|
|
|
|
|
|
|
*CurVert++ = Right;
|
2017-02-11 17:30:57 +01:00
|
|
|
*CurVert++ = Bottom;
|
2015-04-14 06:14:10 +02:00
|
|
|
*CurVert++ = Z;
|
|
|
|
*CurVert++ = U;
|
2017-02-11 17:30:57 +01:00
|
|
|
*CurVert++ = 0.0f;
|
2015-04-14 06:14:10 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
if (Preferences.mDrawGridLines)
|
|
|
|
{
|
|
|
|
float LineSpacing = Spacing * 20.0f;
|
|
|
|
|
|
|
|
for (int Step = MinX; Step < MaxX + 1; Step++)
|
|
|
|
{
|
|
|
|
*CurVert++ = Step * LineSpacing;
|
|
|
|
*CurVert++ = MinY * LineSpacing;
|
|
|
|
*CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = Step * LineSpacing;
|
|
|
|
*CurVert++ = MaxY * LineSpacing;
|
|
|
|
*CurVert++ = 0.0f;
|
|
|
|
}
|
|
|
|
|
|
|
|
for (int Step = MinY; Step < MaxY + 1; Step++)
|
|
|
|
{
|
|
|
|
*CurVert++ = MinX * LineSpacing;
|
|
|
|
*CurVert++ = Step * LineSpacing;
|
|
|
|
*CurVert++ = 0.0f;
|
|
|
|
*CurVert++ = MaxX * LineSpacing;
|
|
|
|
*CurVert++ = Step * LineSpacing;
|
|
|
|
*CurVert++ = 0.0f;
|
|
|
|
}
|
|
|
|
}
|
2014-08-24 00:56:59 +02:00
|
|
|
|
2015-04-14 06:14:10 +02:00
|
|
|
mGridSettings[0] = MinX;
|
|
|
|
mGridSettings[1] = MinY;
|
|
|
|
mGridSettings[2] = MaxX;
|
|
|
|
mGridSettings[3] = MaxY;
|
|
|
|
mGridSettings[4] = Spacing;
|
|
|
|
mGridSettings[5] = (Preferences.mDrawGridStuds ? 1 : 0);
|
|
|
|
mGridSettings[6] = (Preferences.mDrawGridLines ? 1 : 0);
|
|
|
|
|
2015-04-26 20:14:33 +02:00
|
|
|
mContext->DestroyVertexBuffer(mGridBuffer);
|
|
|
|
mGridBuffer = mContext->CreateVertexBuffer(VertexBufferSize, Verts);
|
|
|
|
free(Verts);
|
2015-04-14 06:14:10 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
int BufferOffset = 0;
|
|
|
|
mContext->SetVertexBuffer(mGridBuffer);
|
2019-11-30 20:38:11 +01:00
|
|
|
mContext->SetWorldMatrix(lcMatrix44Identity());
|
2015-04-14 06:14:10 +02:00
|
|
|
|
|
|
|
if (Preferences.mDrawGridStuds)
|
|
|
|
{
|
2017-12-26 19:19:20 +01:00
|
|
|
mContext->BindTexture2D(gGridTexture->mTexture);
|
2019-11-30 20:38:11 +01:00
|
|
|
mContext->SetDepthWrite(false);
|
2014-08-24 00:56:59 +02:00
|
|
|
glEnable(GL_BLEND);
|
|
|
|
|
2020-03-22 21:44:20 +01:00
|
|
|
mContext->SetMaterial(lcMaterialType::UnlitTextureModulate);
|
2015-05-04 02:51:41 +02:00
|
|
|
mContext->SetColor(lcVector4FromColor(Preferences.mGridStudColor));
|
2014-08-24 00:56:59 +02:00
|
|
|
|
2017-03-24 17:34:53 +01:00
|
|
|
mContext->SetVertexFormat(0, 3, 0, 2, 0, false);
|
2017-02-11 17:30:57 +01:00
|
|
|
mContext->DrawPrimitives(GL_TRIANGLE_STRIP, 0, 4);
|
2014-08-24 00:56:59 +02:00
|
|
|
|
|
|
|
glDisable(GL_BLEND);
|
2019-11-30 20:38:11 +01:00
|
|
|
mContext->SetDepthWrite(true);
|
2015-04-14 06:14:10 +02:00
|
|
|
|
|
|
|
BufferOffset = 4 * 5 * sizeof(float);
|
2014-08-24 00:56:59 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
if (Preferences.mDrawGridLines)
|
|
|
|
{
|
|
|
|
mContext->SetLineWidth(1.0f);
|
2020-03-22 21:44:20 +01:00
|
|
|
mContext->SetMaterial(lcMaterialType::UnlitColor);
|
2015-05-04 02:51:41 +02:00
|
|
|
mContext->SetColor(lcVector4FromColor(Preferences.mGridLineColor));
|
2014-08-24 00:56:59 +02:00
|
|
|
|
|
|
|
int NumVerts = 2 * (MaxX - MinX + MaxY - MinY + 2);
|
|
|
|
|
2017-03-24 17:34:53 +01:00
|
|
|
mContext->SetVertexFormat(BufferOffset, 3, 0, 0, 0, false);
|
2015-04-14 06:14:10 +02:00
|
|
|
mContext->DrawPrimitives(GL_LINES, 0, NumVerts);
|
2014-08-24 00:56:59 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcTrackTool lcView::GetOverrideTrackTool(Qt::MouseButton Button) const
|
2016-04-23 02:17:33 +02:00
|
|
|
{
|
2018-02-06 23:47:11 +01:00
|
|
|
if (mTrackToolFromOverlay)
|
2020-12-05 01:06:39 +01:00
|
|
|
return lcTrackTool::None;
|
2018-02-06 23:47:11 +01:00
|
|
|
|
2020-12-05 17:45:29 +01:00
|
|
|
lcTool OverrideTool = gMouseShortcuts.GetTool(Button, mMouseModifiers);
|
2016-04-23 02:17:33 +02:00
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
if (OverrideTool == lcTool::Count)
|
2020-12-05 01:06:39 +01:00
|
|
|
return lcTrackTool::None;
|
2016-04-23 02:17:33 +02:00
|
|
|
|
2020-12-06 20:26:55 +01:00
|
|
|
constexpr lcTrackTool TrackToolFromTool[] =
|
2020-12-05 00:38:49 +01:00
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
lcTrackTool::Insert, // lcTool::Insert
|
|
|
|
lcTrackTool::PointLight, // lcTool::Light
|
|
|
|
lcTrackTool::SpotLight, // lcTool::SpotLight
|
|
|
|
lcTrackTool::Camera, // lcTool::Camera
|
|
|
|
lcTrackTool::Select, // lcTool::Select
|
|
|
|
lcTrackTool::MoveXYZ, // lcTool::Move
|
|
|
|
lcTrackTool::RotateXYZ, // lcTool::Rotate
|
|
|
|
lcTrackTool::Eraser, // lcTool::Eraser
|
|
|
|
lcTrackTool::Paint, // lcTool::Paint
|
|
|
|
lcTrackTool::ColorPicker, // lcTool::ColorPicker
|
|
|
|
lcTrackTool::Zoom, // lcTool::Zoom
|
|
|
|
lcTrackTool::Pan, // lcTool::Pan
|
|
|
|
lcTrackTool::OrbitXY, // lcTool::RotateView
|
|
|
|
lcTrackTool::Roll, // lcTool::Roll
|
|
|
|
lcTrackTool::ZoomRegion // lcTool::ZoomRegion
|
2016-04-23 02:17:33 +02:00
|
|
|
};
|
|
|
|
|
2020-12-06 20:26:55 +01:00
|
|
|
LC_ARRAY_SIZE_CHECK(TrackToolFromTool, lcTool::Count);
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
return TrackToolFromTool[static_cast<int>(OverrideTool)];
|
2016-04-23 02:17:33 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
float lcView::GetOverlayScale() const
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2016-03-13 21:07:28 +01:00
|
|
|
lcVector3 OverlayCenter;
|
|
|
|
lcMatrix33 RelativeRotation;
|
2018-03-29 19:20:36 +02:00
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
ActiveModel->GetMoveRotateTransform(OverlayCenter, RelativeRotation);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
lcVector3 ScreenPos = ProjectPoint(OverlayCenter);
|
|
|
|
ScreenPos[0] += 10.0f;
|
|
|
|
lcVector3 Point = UnprojectPoint(ScreenPos);
|
|
|
|
|
|
|
|
lcVector3 Dist(Point - OverlayCenter);
|
|
|
|
return Dist.Length() * 5.0f;
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::BeginDrag(lcDragState DragState)
|
2014-05-27 00:58:08 +02:00
|
|
|
{
|
2018-01-12 19:50:25 +01:00
|
|
|
mDragState = DragState;
|
2014-05-27 00:58:08 +02:00
|
|
|
UpdateTrackTool();
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::EndDrag(bool Accept)
|
2014-05-27 00:58:08 +02:00
|
|
|
{
|
2020-12-16 02:19:32 +01:00
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
|
2014-05-27 00:58:08 +02:00
|
|
|
if (Accept)
|
2018-01-12 19:50:25 +01:00
|
|
|
{
|
|
|
|
switch (mDragState)
|
|
|
|
{
|
2020-02-15 20:36:06 +01:00
|
|
|
case lcDragState::None:
|
2018-01-12 19:50:25 +01:00
|
|
|
break;
|
|
|
|
|
2020-02-15 20:36:06 +01:00
|
|
|
case lcDragState::Piece:
|
2020-02-01 19:58:19 +01:00
|
|
|
{
|
|
|
|
PieceInfo* Info = gMainWindow->GetCurrentPieceInfo();
|
|
|
|
if (Info)
|
|
|
|
ActiveModel->InsertPieceToolClicked(GetPieceInsertPosition(false, Info));
|
|
|
|
} break;
|
2018-01-12 19:50:25 +01:00
|
|
|
|
2020-02-15 20:36:06 +01:00
|
|
|
case lcDragState::Color:
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->PaintToolClicked(FindObjectUnderPointer(true, false).Object);
|
2018-01-12 19:50:25 +01:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
2014-05-27 00:58:08 +02:00
|
|
|
|
2020-02-15 20:36:06 +01:00
|
|
|
mDragState = lcDragState::None;
|
2014-05-27 00:58:08 +02:00
|
|
|
UpdateTrackTool();
|
2020-12-16 02:19:32 +01:00
|
|
|
ActiveModel->UpdateAllViews();
|
2014-05-27 00:58:08 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetViewpoint(lcViewpoint Viewpoint)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
if (!mCamera || !mCamera->IsSimple())
|
|
|
|
{
|
|
|
|
lcCamera* OldCamera = mCamera;
|
|
|
|
|
|
|
|
mCamera = new lcCamera(true);
|
|
|
|
|
|
|
|
if (OldCamera)
|
|
|
|
mCamera->CopySettings(OldCamera);
|
|
|
|
}
|
|
|
|
|
|
|
|
mCamera->SetViewpoint(Viewpoint);
|
|
|
|
ZoomExtents();
|
|
|
|
Redraw();
|
|
|
|
|
|
|
|
emit CameraChanged();
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetViewpoint(const lcVector3& Position)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
if (!mCamera || !mCamera->IsSimple())
|
|
|
|
{
|
|
|
|
lcCamera* OldCamera = mCamera;
|
|
|
|
|
|
|
|
mCamera = new lcCamera(true);
|
|
|
|
|
|
|
|
if (OldCamera)
|
|
|
|
mCamera->CopySettings(OldCamera);
|
|
|
|
}
|
|
|
|
|
|
|
|
mCamera->SetViewpoint(Position);
|
|
|
|
ZoomExtents();
|
|
|
|
Redraw();
|
|
|
|
|
|
|
|
emit CameraChanged();
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetViewpoint(const lcVector3& Position, const lcVector3& Target, const lcVector3& Up)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
if (!mCamera || !mCamera->IsSimple())
|
|
|
|
{
|
|
|
|
lcCamera* OldCamera = mCamera;
|
|
|
|
|
|
|
|
mCamera = new lcCamera(true);
|
|
|
|
|
|
|
|
if (OldCamera)
|
|
|
|
mCamera->CopySettings(OldCamera);
|
|
|
|
}
|
|
|
|
|
|
|
|
mCamera->SetViewpoint(Position, Target, Up);
|
|
|
|
Redraw();
|
|
|
|
|
|
|
|
emit CameraChanged();
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetCameraAngles(float Latitude, float Longitude)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
if (!mCamera || !mCamera->IsSimple())
|
|
|
|
{
|
|
|
|
lcCamera* OldCamera = mCamera;
|
|
|
|
|
|
|
|
mCamera = new lcCamera(true);
|
|
|
|
|
|
|
|
if (OldCamera)
|
|
|
|
mCamera->CopySettings(OldCamera);
|
|
|
|
}
|
|
|
|
|
|
|
|
mCamera->SetAngles(Latitude, Longitude, 1.0f);
|
|
|
|
ZoomExtents();
|
|
|
|
Redraw();
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetDefaultCamera()
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
if (!mCamera || !mCamera->IsSimple())
|
|
|
|
mCamera = new lcCamera(true);
|
|
|
|
|
|
|
|
mCamera->SetViewpoint(lcViewpoint::Home);
|
|
|
|
|
|
|
|
emit CameraChanged();
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetCamera(lcCamera* Camera, bool ForceCopy)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
if (Camera->IsSimple() || ForceCopy)
|
|
|
|
{
|
|
|
|
if (!mCamera || !mCamera->IsSimple())
|
|
|
|
mCamera = new lcCamera(true);
|
|
|
|
|
|
|
|
mCamera->CopyPosition(Camera);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
if (mCamera && mCamera->IsSimple())
|
|
|
|
delete mCamera;
|
|
|
|
|
|
|
|
mCamera = Camera;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetCamera(const QString& CameraName)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
const lcArray<lcCamera*>& Cameras = mModel->GetCameras();
|
|
|
|
|
|
|
|
for (int CameraIdx = 0; CameraIdx < Cameras.GetSize(); CameraIdx++)
|
|
|
|
{
|
|
|
|
if (CameraName.compare(Cameras[CameraIdx]->GetName(), Qt::CaseInsensitive) == 0)
|
|
|
|
{
|
|
|
|
SetCameraIndex(CameraIdx);
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetCameraIndex(int Index)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
const lcArray<lcCamera*>& Cameras = mModel->GetCameras();
|
|
|
|
|
|
|
|
if (Index >= Cameras.GetSize())
|
|
|
|
return;
|
|
|
|
|
|
|
|
lcCamera* Camera = Cameras[Index];
|
|
|
|
SetCamera(Camera, false);
|
|
|
|
|
|
|
|
emit CameraChanged();
|
|
|
|
Redraw();
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetProjection(bool Ortho)
|
2014-11-30 18:53:09 +01:00
|
|
|
{
|
|
|
|
if (mCamera->IsSimple())
|
|
|
|
{
|
|
|
|
mCamera->SetOrtho(Ortho);
|
|
|
|
Redraw();
|
|
|
|
|
|
|
|
gMainWindow->UpdatePerspective();
|
|
|
|
}
|
|
|
|
else
|
2018-03-29 19:20:36 +02:00
|
|
|
{
|
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
if (ActiveModel)
|
|
|
|
ActiveModel->SetCameraOrthographic(mCamera, Ortho);
|
|
|
|
}
|
2014-11-30 18:53:09 +01:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::LookAt()
|
2014-11-30 18:53:09 +01:00
|
|
|
{
|
2018-03-29 19:20:36 +02:00
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
if (ActiveModel)
|
|
|
|
ActiveModel->LookAt(mCamera);
|
2014-11-30 18:53:09 +01:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::MoveCamera(const lcVector3& Direction)
|
2018-01-15 20:35:15 +01:00
|
|
|
{
|
2018-03-29 19:20:36 +02:00
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
if (ActiveModel)
|
|
|
|
ActiveModel->MoveCamera(mCamera, Direction);
|
2018-01-15 20:35:15 +01:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::Zoom(float Amount)
|
2019-02-10 01:30:11 +01:00
|
|
|
{
|
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
if (ActiveModel)
|
|
|
|
ActiveModel->Zoom(mCamera, Amount);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::ZoomExtents()
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
if (ActiveModel)
|
|
|
|
ActiveModel->ZoomExtents(mCamera, (float)mWidth / (float)mHeight);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcCursor lcView::GetCursor() const
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
if (mTrackButton != lcTrackButton::None)
|
|
|
|
return lcCursor::Hidden;
|
|
|
|
|
|
|
|
if (mTrackTool == lcTrackTool::Select)
|
|
|
|
{
|
|
|
|
if (mMouseModifiers & Qt::ControlModifier)
|
|
|
|
return lcCursor::SelectAdd;
|
|
|
|
|
|
|
|
if (mMouseModifiers & Qt::ShiftModifier)
|
|
|
|
return lcCursor::SelectRemove;
|
|
|
|
}
|
|
|
|
|
|
|
|
constexpr lcCursor CursorFromTrackTool[] =
|
|
|
|
{
|
|
|
|
lcCursor::Select, // lcTrackTool::None
|
|
|
|
lcCursor::Brick, // lcTrackTool::Insert
|
|
|
|
lcCursor::Light, // lcTrackTool::PointLight
|
|
|
|
lcCursor::Spotlight, // lcTrackTool::SpotLight
|
|
|
|
lcCursor::Camera, // lcTrackTool::Camera
|
|
|
|
lcCursor::Select, // lcTrackTool::Select
|
|
|
|
lcCursor::Move, // lcTrackTool::MoveX
|
|
|
|
lcCursor::Move, // lcTrackTool::MoveY
|
|
|
|
lcCursor::Move, // lcTrackTool::MoveZ
|
|
|
|
lcCursor::Move, // lcTrackTool::MoveXY
|
|
|
|
lcCursor::Move, // lcTrackTool::MoveXZ
|
|
|
|
lcCursor::Move, // lcTrackTool::MoveYZ
|
|
|
|
lcCursor::Move, // lcTrackTool::MoveXYZ
|
|
|
|
lcCursor::Rotate, // lcTrackTool::RotateX
|
|
|
|
lcCursor::Rotate, // lcTrackTool::RotateY
|
|
|
|
lcCursor::Rotate, // lcTrackTool::RotateZ
|
|
|
|
lcCursor::Rotate, // lcTrackTool::RotateXY
|
|
|
|
lcCursor::Rotate, // lcTrackTool::RotateXYZ
|
|
|
|
lcCursor::Move, // lcTrackTool::ScalePlus
|
|
|
|
lcCursor::Move, // lcTrackTool::ScaleMinus
|
|
|
|
lcCursor::Delete, // lcTrackTool::Eraser
|
|
|
|
lcCursor::Paint, // lcTrackTool::Paint
|
|
|
|
lcCursor::ColorPicker, // lcTrackTool::ColorPicker
|
|
|
|
lcCursor::Zoom, // lcTrackTool::Zoom
|
|
|
|
lcCursor::Pan, // lcTrackTool::Pan
|
|
|
|
lcCursor::RotateX, // lcTrackTool::OrbitX
|
|
|
|
lcCursor::RotateY, // lcTrackTool::OrbitY
|
|
|
|
lcCursor::RotateView, // lcTrackTool::OrbitXY
|
|
|
|
lcCursor::Roll, // lcTrackTool::Roll
|
|
|
|
lcCursor::ZoomRegion // lcTrackTool::ZoomRegion
|
|
|
|
};
|
|
|
|
|
|
|
|
LC_ARRAY_SIZE_CHECK(CursorFromTrackTool, lcTrackTool::Count);
|
|
|
|
|
|
|
|
if (mTrackTool >= lcTrackTool::None && mTrackTool < lcTrackTool::Count)
|
|
|
|
return CursorFromTrackTool[static_cast<int>(mTrackTool)];
|
|
|
|
|
|
|
|
return lcCursor::Select;
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::SetCursor(lcCursor CursorType)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
if (mCursor == CursorType)
|
|
|
|
return;
|
|
|
|
|
|
|
|
struct lcCursorInfo
|
|
|
|
{
|
|
|
|
int x, y;
|
|
|
|
const char* Name;
|
|
|
|
};
|
|
|
|
|
|
|
|
constexpr lcCursorInfo Cursors[] =
|
|
|
|
{
|
|
|
|
{ 0, 0, "" }, // lcCursor::Hidden
|
|
|
|
{ 0, 0, "" }, // lcCursor::Default
|
|
|
|
{ 8, 3, ":/resources/cursor_insert" }, // lcCursor::Brick
|
|
|
|
{ 15, 15, ":/resources/cursor_light" }, // lcCursor::Light
|
|
|
|
{ 7, 10, ":/resources/cursor_spotlight" }, // lcCursor::Spotlight
|
|
|
|
{ 15, 9, ":/resources/cursor_camera" }, // lcCursor::Camera
|
|
|
|
{ 0, 2, ":/resources/cursor_select" }, // lcCursor::Select
|
|
|
|
{ 0, 2, ":/resources/cursor_select_add" }, // lcCursor::SelectAdd
|
|
|
|
{ 0, 2, ":/resources/cursor_select_remove" }, // lcCursor::SelectRemove
|
|
|
|
{ 15, 15, ":/resources/cursor_move" }, // lcCursor::Move
|
|
|
|
{ 15, 15, ":/resources/cursor_rotate" }, // lcCursor::Rotate
|
|
|
|
{ 15, 15, ":/resources/cursor_rotatex" }, // lcCursor::RotateX
|
|
|
|
{ 15, 15, ":/resources/cursor_rotatey" }, // lcCursor::RotateY
|
|
|
|
{ 0, 10, ":/resources/cursor_delete" }, // lcCursor::Delete
|
|
|
|
{ 14, 14, ":/resources/cursor_paint" }, // lcCursor::Paint
|
|
|
|
{ 1, 13, ":/resources/cursor_color_picker" }, // lcCursor::ColorPicker
|
|
|
|
{ 15, 15, ":/resources/cursor_zoom" }, // lcCursor::Zoom
|
|
|
|
{ 9, 9, ":/resources/cursor_zoom_region" }, // lcCursor::ZoomRegion
|
|
|
|
{ 15, 15, ":/resources/cursor_pan" }, // lcCursor::Pan
|
|
|
|
{ 15, 15, ":/resources/cursor_roll" }, // lcCursor::Roll
|
|
|
|
{ 15, 15, ":/resources/cursor_rotate_view" }, // lcCursor::RotateView
|
|
|
|
};
|
|
|
|
|
|
|
|
LC_ARRAY_SIZE_CHECK(Cursors, lcCursor::Count);
|
|
|
|
|
|
|
|
if (CursorType == lcCursor::Hidden)
|
|
|
|
{
|
|
|
|
mWidget->setCursor(Qt::BlankCursor);
|
|
|
|
mCursor = CursorType;
|
|
|
|
}
|
|
|
|
else if (CursorType >= lcCursor::First && CursorType < lcCursor::Count)
|
|
|
|
{
|
|
|
|
const lcCursorInfo& Cursor = Cursors[static_cast<int>(CursorType)];
|
|
|
|
mWidget->setCursor(QCursor(QPixmap(Cursor.Name), Cursor.x, Cursor.y));
|
|
|
|
mCursor = CursorType;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
mWidget->unsetCursor();
|
|
|
|
mCursor = lcCursor::Default;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::UpdateCursor()
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
SetCursor(GetCursor());
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
lcTool lcView::GetCurrentTool() const
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
constexpr lcTool ToolFromTrackTool[] =
|
|
|
|
{
|
|
|
|
lcTool::Select, // lcTrackTool::None
|
|
|
|
lcTool::Insert, // lcTrackTool::Insert
|
|
|
|
lcTool::Light, // lcTrackTool::PointLight
|
|
|
|
lcTool::SpotLight, // lcTrackTool::SpotLight
|
|
|
|
lcTool::Camera, // lcTrackTool::Camera
|
|
|
|
lcTool::Select, // lcTrackTool::Select
|
|
|
|
lcTool::Move, // lcTrackTool::MoveX
|
|
|
|
lcTool::Move, // lcTrackTool::MoveY
|
|
|
|
lcTool::Move, // lcTrackTool::MoveZ
|
|
|
|
lcTool::Move, // lcTrackTool::MoveXY
|
|
|
|
lcTool::Move, // lcTrackTool::MoveXZ
|
|
|
|
lcTool::Move, // lcTrackTool::MoveYZ
|
|
|
|
lcTool::Move, // lcTrackTool::MoveXYZ
|
|
|
|
lcTool::Rotate, // lcTrackTool::RotateX
|
|
|
|
lcTool::Rotate, // lcTrackTool::RotateY
|
|
|
|
lcTool::Rotate, // lcTrackTool::RotateZ
|
|
|
|
lcTool::Rotate, // lcTrackTool::RotateXY
|
|
|
|
lcTool::Rotate, // lcTrackTool::RotateXYZ
|
|
|
|
lcTool::Move, // lcTrackTool::ScalePlus
|
|
|
|
lcTool::Move, // lcTrackTool::ScaleMinus
|
|
|
|
lcTool::Eraser, // lcTrackTool::Eraser
|
|
|
|
lcTool::Paint, // lcTrackTool::Paint
|
|
|
|
lcTool::ColorPicker, // lcTrackTool::ColorPicker
|
|
|
|
lcTool::Zoom, // lcTrackTool::Zoom
|
|
|
|
lcTool::Pan, // lcTrackTool::Pan
|
|
|
|
lcTool::RotateView, // lcTrackTool::OrbitX
|
|
|
|
lcTool::RotateView, // lcTrackTool::OrbitY
|
|
|
|
lcTool::RotateView, // lcTrackTool::OrbitXY
|
|
|
|
lcTool::Roll, // lcTrackTool::Roll
|
|
|
|
lcTool::ZoomRegion // lcTrackTool::ZoomRegion
|
|
|
|
};
|
|
|
|
|
|
|
|
LC_ARRAY_SIZE_CHECK(ToolFromTrackTool, lcTrackTool::Count);
|
|
|
|
|
|
|
|
if (mTrackTool >= lcTrackTool::None && mTrackTool < lcTrackTool::Count)
|
|
|
|
return ToolFromTrackTool[static_cast<int>(mTrackTool)];
|
|
|
|
|
|
|
|
return lcTool::Select;
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::UpdateTrackTool()
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2020-12-20 01:05:29 +01:00
|
|
|
if (mViewType != lcViewType::View)
|
|
|
|
{
|
|
|
|
mTrackTool = lcTrackTool::None;
|
|
|
|
UpdateCursor();
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2014-05-23 02:02:21 +02:00
|
|
|
lcTool CurrentTool = gMainWindow->GetTool();
|
2014-05-18 01:03:05 +02:00
|
|
|
lcTrackTool NewTrackTool = mTrackTool;
|
2020-12-05 17:45:29 +01:00
|
|
|
int x = mMouseX;
|
|
|
|
int y = mMouseY;
|
2014-05-18 01:03:05 +02:00
|
|
|
bool Redraw = false;
|
2018-02-06 23:47:11 +01:00
|
|
|
mTrackToolFromOverlay = false;
|
2018-03-29 19:20:36 +02:00
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
switch (CurrentTool)
|
|
|
|
{
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Insert:
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::Insert;
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Light:
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::PointLight;
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::SpotLight:
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::SpotLight;
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Camera:
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::Camera;
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Select:
|
|
|
|
case lcTool::Move:
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
const float OverlayScale = GetOverlayScale();
|
|
|
|
const float OverlayMovePlaneSize = 0.5f * OverlayScale;
|
|
|
|
const float OverlayMoveArrowSize = 1.5f * OverlayScale;
|
|
|
|
const float OverlayMoveArrowCapRadius = 0.1f * OverlayScale;
|
|
|
|
const float OverlayRotateArrowStart = 1.0f * OverlayScale;
|
|
|
|
const float OverlayRotateArrowEnd = 1.5f * OverlayScale;
|
2016-03-12 01:05:49 +01:00
|
|
|
const float OverlayScaleRadius = 0.125f;
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = (CurrentTool == lcTool::Move) ? lcTrackTool::MoveXYZ : lcTrackTool::Select;
|
2017-11-13 21:47:35 +01:00
|
|
|
mMouseDownPiece = nullptr;
|
2015-01-18 05:41:06 +01:00
|
|
|
|
|
|
|
lcVector3 OverlayCenter;
|
2016-03-13 21:07:28 +01:00
|
|
|
lcMatrix33 RelativeRotation;
|
2018-03-29 19:20:36 +02:00
|
|
|
if (!ActiveModel->GetMoveRotateTransform(OverlayCenter, RelativeRotation))
|
2015-01-18 05:41:06 +01:00
|
|
|
break;
|
|
|
|
|
2018-04-08 03:45:44 +02:00
|
|
|
lcMatrix44 WorldMatrix = lcMatrix44(RelativeRotation, OverlayCenter);
|
|
|
|
|
|
|
|
if (ActiveModel != mModel)
|
|
|
|
WorldMatrix = lcMul(WorldMatrix, mActiveSubmodelTransform);
|
|
|
|
OverlayCenter = WorldMatrix.GetTranslation();
|
|
|
|
|
2014-05-18 01:03:05 +02:00
|
|
|
lcVector3 PlaneNormals[3] =
|
|
|
|
{
|
|
|
|
lcVector3(1.0f, 0.0f, 0.0f),
|
|
|
|
lcVector3(0.0f, 1.0f, 0.0f),
|
|
|
|
lcVector3(0.0f, 0.0f, 1.0f),
|
|
|
|
};
|
|
|
|
|
|
|
|
for (int i = 0; i < 3; i++)
|
2018-04-08 03:45:44 +02:00
|
|
|
PlaneNormals[i] = lcMul30(PlaneNormals[i], WorldMatrix);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
lcVector3 StartEnd[2] = { lcVector3((float)x, (float)y, 0.0f), lcVector3((float)x, (float)y, 1.0f) };
|
|
|
|
UnprojectPoints(StartEnd, 2);
|
|
|
|
const lcVector3& Start = StartEnd[0];
|
|
|
|
const lcVector3& End = StartEnd[1];
|
|
|
|
float ClosestIntersectionDistance = FLT_MAX;
|
|
|
|
|
2018-03-29 19:20:36 +02:00
|
|
|
lcObject* Focus = ActiveModel->GetFocusObject();
|
2016-03-12 01:05:49 +01:00
|
|
|
int ControlPointIndex = -1;
|
|
|
|
if (Focus && Focus->IsPiece())
|
|
|
|
{
|
|
|
|
lcPiece* Piece = (lcPiece*)Focus;
|
2017-12-02 21:22:04 +01:00
|
|
|
quint32 Section = Piece->GetFocusSection();
|
2016-03-12 01:05:49 +01:00
|
|
|
|
2020-03-22 19:12:15 +01:00
|
|
|
if (Section >= LC_PIECE_SECTION_CONTROL_POINT_FIRST && Section <= LC_PIECE_SECTION_CONTROL_POINT_LAST)
|
2016-03-12 01:05:49 +01:00
|
|
|
ControlPointIndex = Section - LC_PIECE_SECTION_CONTROL_POINT_1;
|
|
|
|
}
|
|
|
|
|
2017-12-02 21:22:04 +01:00
|
|
|
quint32 AllowedTransforms = Focus ? Focus->GetAllowedTransforms() : LC_OBJECT_TRANSFORM_MOVE_X | LC_OBJECT_TRANSFORM_MOVE_Y | LC_OBJECT_TRANSFORM_MOVE_Z | LC_OBJECT_TRANSFORM_ROTATE_X | LC_OBJECT_TRANSFORM_ROTATE_Y | LC_OBJECT_TRANSFORM_ROTATE_Z;
|
2016-05-01 02:20:37 +02:00
|
|
|
|
2014-05-18 01:03:05 +02:00
|
|
|
for (int AxisIndex = 0; AxisIndex < 3; AxisIndex++)
|
|
|
|
{
|
|
|
|
lcVector4 Plane(PlaneNormals[AxisIndex], -lcDot(PlaneNormals[AxisIndex], OverlayCenter));
|
|
|
|
lcVector3 Intersection;
|
|
|
|
|
2018-02-04 20:53:13 +01:00
|
|
|
if (!lcLineSegmentPlaneIntersection(&Intersection, Start, End, Plane))
|
2014-05-18 01:03:05 +02:00
|
|
|
continue;
|
|
|
|
|
|
|
|
float IntersectionDistance = lcLengthSquared(Intersection - Start);
|
|
|
|
|
|
|
|
if (IntersectionDistance > ClosestIntersectionDistance)
|
|
|
|
continue;
|
|
|
|
|
|
|
|
lcVector3 Dir(Intersection - OverlayCenter);
|
|
|
|
|
|
|
|
float Proj1 = lcDot(Dir, PlaneNormals[(AxisIndex + 1) % 3]);
|
|
|
|
float Proj2 = lcDot(Dir, PlaneNormals[(AxisIndex + 2) % 3]);
|
|
|
|
|
|
|
|
if (Proj1 > 0.0f && Proj1 < OverlayMovePlaneSize && Proj2 > 0.0f && Proj2 < OverlayMovePlaneSize)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
lcTrackTool PlaneModes[] = { lcTrackTool::MoveYZ, lcTrackTool::MoveXZ, lcTrackTool::MoveXY };
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2016-05-01 02:20:37 +02:00
|
|
|
if (IsTrackToolAllowed(PlaneModes[AxisIndex], AllowedTransforms))
|
|
|
|
{
|
|
|
|
NewTrackTool = PlaneModes[AxisIndex];
|
|
|
|
ClosestIntersectionDistance = IntersectionDistance;
|
|
|
|
}
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
if (CurrentTool == lcTool::Select && Proj1 > OverlayRotateArrowStart && Proj1 < OverlayRotateArrowEnd && Proj2 > OverlayRotateArrowStart && Proj2 < OverlayRotateArrowEnd && ActiveModel->AnyPiecesSelected())
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
lcTrackTool PlaneModes[] = { lcTrackTool::RotateX, lcTrackTool::RotateY, lcTrackTool::RotateZ };
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2016-05-01 02:20:37 +02:00
|
|
|
if (IsTrackToolAllowed(PlaneModes[AxisIndex], AllowedTransforms))
|
|
|
|
{
|
|
|
|
NewTrackTool = PlaneModes[AxisIndex];
|
|
|
|
ClosestIntersectionDistance = IntersectionDistance;
|
|
|
|
}
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
if (fabs(Proj1) < OverlayMoveArrowCapRadius && Proj2 > 0.0f && Proj2 < OverlayMoveArrowSize)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
lcTrackTool DirModes[] = { lcTrackTool::MoveZ, lcTrackTool::MoveX, lcTrackTool::MoveY };
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2016-05-01 02:20:37 +02:00
|
|
|
if (IsTrackToolAllowed(DirModes[AxisIndex], AllowedTransforms))
|
|
|
|
{
|
|
|
|
NewTrackTool = DirModes[AxisIndex];
|
|
|
|
ClosestIntersectionDistance = IntersectionDistance;
|
|
|
|
}
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
if (fabs(Proj2) < OverlayMoveArrowCapRadius && Proj1 > 0.0f && Proj1 < OverlayMoveArrowSize)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
lcTrackTool DirModes[] = { lcTrackTool::MoveY, lcTrackTool::MoveZ, lcTrackTool::MoveX };
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2016-05-01 02:20:37 +02:00
|
|
|
if (IsTrackToolAllowed(DirModes[AxisIndex], AllowedTransforms))
|
|
|
|
{
|
|
|
|
NewTrackTool = DirModes[AxisIndex];
|
|
|
|
ClosestIntersectionDistance = IntersectionDistance;
|
|
|
|
}
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
2016-03-12 01:05:49 +01:00
|
|
|
|
2016-05-01 02:20:37 +02:00
|
|
|
lcPiece* Piece = (lcPiece*)Focus;
|
|
|
|
|
2017-03-27 20:02:33 +02:00
|
|
|
if (ControlPointIndex != -1 && Piece->mPieceInfo->GetSynthInfo() && Piece->mPieceInfo->GetSynthInfo()->IsCurve())
|
2016-03-12 01:05:49 +01:00
|
|
|
{
|
|
|
|
float Strength = Piece->GetControlPoints()[ControlPointIndex].Scale;
|
|
|
|
const float ScaleStart = (2.0f - OverlayScaleRadius) * OverlayScale + Strength;
|
|
|
|
const float ScaleEnd = (2.0f + OverlayScaleRadius) * OverlayScale + Strength;
|
|
|
|
|
2016-04-19 18:30:29 +02:00
|
|
|
if (AxisIndex == 1 && fabs(Proj1) < OverlayScaleRadius * OverlayScale)
|
2016-03-12 01:05:49 +01:00
|
|
|
{
|
|
|
|
if (Proj2 > ScaleStart && Proj2 < ScaleEnd)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
if (IsTrackToolAllowed(lcTrackTool::ScalePlus, AllowedTransforms))
|
2016-05-01 02:20:37 +02:00
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::ScalePlus;
|
2016-05-01 02:20:37 +02:00
|
|
|
ClosestIntersectionDistance = IntersectionDistance;
|
|
|
|
}
|
2016-03-12 01:05:49 +01:00
|
|
|
}
|
|
|
|
else if (Proj2 < -ScaleStart && Proj2 > -ScaleEnd)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
if (IsTrackToolAllowed(lcTrackTool::ScaleMinus, AllowedTransforms))
|
2016-05-01 02:20:37 +02:00
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::ScaleMinus;
|
2016-05-01 02:20:37 +02:00
|
|
|
ClosestIntersectionDistance = IntersectionDistance;
|
|
|
|
}
|
2016-03-12 01:05:49 +01:00
|
|
|
}
|
|
|
|
}
|
2016-04-19 18:30:29 +02:00
|
|
|
else if (AxisIndex == 2 && fabs(Proj2) < OverlayScaleRadius * OverlayScale)
|
2016-03-12 01:05:49 +01:00
|
|
|
{
|
|
|
|
if (Proj1 > ScaleStart && Proj1 < ScaleEnd)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
if (IsTrackToolAllowed(lcTrackTool::ScalePlus, AllowedTransforms))
|
2016-05-01 02:20:37 +02:00
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::ScalePlus;
|
2016-05-01 02:20:37 +02:00
|
|
|
ClosestIntersectionDistance = IntersectionDistance;
|
|
|
|
}
|
2016-03-12 01:05:49 +01:00
|
|
|
}
|
|
|
|
else if (Proj1 < -ScaleStart && Proj1 > -ScaleEnd)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
if (IsTrackToolAllowed(lcTrackTool::ScaleMinus, AllowedTransforms))
|
2016-05-01 02:20:37 +02:00
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::ScaleMinus;
|
2016-05-01 02:20:37 +02:00
|
|
|
ClosestIntersectionDistance = IntersectionDistance;
|
|
|
|
}
|
2016-03-12 01:05:49 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
2020-12-05 17:45:29 +01:00
|
|
|
if (CurrentTool == lcTool::Select && NewTrackTool == lcTrackTool::Select && mMouseModifiers == Qt::NoModifier)
|
2017-11-13 04:38:07 +01:00
|
|
|
{
|
|
|
|
lcObjectSection ObjectSection = FindObjectUnderPointer(false, false);
|
|
|
|
lcObject* Object = ObjectSection.Object;
|
|
|
|
|
2017-11-19 22:27:42 +01:00
|
|
|
if (Object && Object->IsPiece() && ObjectSection.Section == LC_PIECE_SECTION_POSITION && Object->IsSelected())
|
2017-11-13 04:38:07 +01:00
|
|
|
{
|
|
|
|
lcPiece* Piece = (lcPiece*)Object;
|
|
|
|
mMouseDownPosition = Piece->mModelWorld.GetTranslation();
|
|
|
|
mMouseDownPiece = Piece->mPieceInfo;
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::MoveXYZ;
|
2017-11-13 04:38:07 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
mTrackToolFromOverlay = NewTrackTool != lcTrackTool::MoveXYZ && NewTrackTool != lcTrackTool::Select;
|
2014-05-18 01:03:05 +02:00
|
|
|
Redraw = true;
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Rotate:
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
const float OverlayScale = GetOverlayScale();
|
|
|
|
const float OverlayRotateRadius = 2.0f;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::RotateXYZ;
|
2015-01-18 05:41:06 +01:00
|
|
|
|
|
|
|
lcVector3 OverlayCenter;
|
2016-03-13 21:07:28 +01:00
|
|
|
lcMatrix33 RelativeRotation;
|
2018-03-29 19:20:36 +02:00
|
|
|
if (!ActiveModel->GetMoveRotateTransform(OverlayCenter, RelativeRotation))
|
2015-01-18 05:41:06 +01:00
|
|
|
break;
|
|
|
|
|
2014-05-18 01:03:05 +02:00
|
|
|
// Calculate the distance from the mouse pointer to the center of the sphere.
|
|
|
|
lcVector3 StartEnd[2] = { lcVector3((float)x, (float)y, 0.0f), lcVector3((float)x, (float)y, 1.0f) };
|
|
|
|
UnprojectPoints(StartEnd, 2);
|
|
|
|
const lcVector3& SegStart = StartEnd[0];
|
|
|
|
const lcVector3& SegEnd = StartEnd[1];
|
|
|
|
|
|
|
|
lcVector3 Line = SegEnd - SegStart;
|
|
|
|
lcVector3 Vec = OverlayCenter - SegStart;
|
|
|
|
|
|
|
|
float u = lcDot(Vec, Line) / Line.LengthSquared();
|
|
|
|
|
|
|
|
// Closest point in the line to the mouse.
|
|
|
|
lcVector3 Closest = SegStart + Line * u;
|
|
|
|
|
|
|
|
float Distance = (Closest - OverlayCenter).Length();
|
|
|
|
const float Epsilon = 0.25f * OverlayScale;
|
|
|
|
|
|
|
|
if (Distance > (OverlayRotateRadius * OverlayScale + Epsilon))
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::RotateXYZ;
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
else if (Distance < (OverlayRotateRadius * OverlayScale + Epsilon))
|
|
|
|
{
|
|
|
|
// 3D rotation unless we're over one of the axis circles.
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::RotateXYZ;
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
// Point P on a line defined by two points P1 and P2 is described by P = P1 + u (P2 - P1)
|
|
|
|
// A sphere centered at P3 with radius r is described by (x - x3)^2 + (y - y3)^2 + (z - z3)^2 = r^2
|
|
|
|
// Substituting the equation of the line into the sphere gives a quadratic equation where:
|
|
|
|
// a = (x2 - x1)^2 + (y2 - y1)^2 + (z2 - z1)^2
|
|
|
|
// b = 2[ (x2 - x1) (x1 - x3) + (y2 - y1) (y1 - y3) + (z2 - z1) (z1 - z3) ]
|
|
|
|
// c = x32 + y32 + z32 + x12 + y12 + z12 - 2[x3 x1 + y3 y1 + z3 z1] - r2
|
|
|
|
// The solutions to this quadratic are described by: (-b +- sqrt(b^2 - 4 a c) / 2 a
|
|
|
|
// The exact behavior is determined by b^2 - 4 a c:
|
|
|
|
// If this is less than 0 then the line does not intersect the sphere.
|
|
|
|
// If it equals 0 then the line is a tangent to the sphere intersecting it at one point
|
|
|
|
// If it is greater then 0 the line intersects the sphere at two points.
|
|
|
|
|
|
|
|
float x1 = SegStart[0], y1 = SegStart[1], z1 = SegStart[2];
|
|
|
|
float x2 = SegEnd[0], y2 = SegEnd[1], z2 = SegEnd[2];
|
|
|
|
float x3 = OverlayCenter[0], y3 = OverlayCenter[1], z3 = OverlayCenter[2];
|
|
|
|
float r = OverlayRotateRadius * OverlayScale;
|
|
|
|
|
|
|
|
// TODO: rewrite using vectors.
|
|
|
|
float a = (x2 - x1)*(x2 - x1) + (y2 - y1)*(y2 - y1) + (z2 - z1)*(z2 - z1);
|
|
|
|
float b = 2 * ((x2 - x1)*(x1 - x3) + (y2 - y1)*(y1 - y3) + (z2 - z1)*(z1 - z3));
|
|
|
|
float c = x3*x3 + y3*y3 + z3*z3 + x1*x1 + y1*y1 + z1*z1 - 2*(x3*x1 + y3*y1 + z3*z1) - r*r;
|
|
|
|
float f = b * b - 4 * a * c;
|
|
|
|
|
|
|
|
if (f >= 0.0f)
|
|
|
|
{
|
|
|
|
lcVector3 ViewDir(mCamera->mTargetPosition - mCamera->mPosition);
|
|
|
|
|
|
|
|
float u1 = (-b + sqrtf(f)) / (2*a);
|
|
|
|
float u2 = (-b - sqrtf(f)) / (2*a);
|
|
|
|
|
|
|
|
lcVector3 Intersections[2] =
|
|
|
|
{
|
|
|
|
lcVector3(x1 + u1*(x2-x1), y1 + u1*(y2-y1), z1 + u1*(z2-z1)),
|
|
|
|
lcVector3(x1 + u2*(x2-x1), y1 + u2*(y2-y1), z1 + u2*(z2-z1))
|
|
|
|
};
|
|
|
|
|
|
|
|
for (int i = 0; i < 2; i++)
|
|
|
|
{
|
|
|
|
lcVector3 Dist = Intersections[i] - OverlayCenter;
|
|
|
|
|
|
|
|
if (lcDot(ViewDir, Dist) > 0.0f)
|
|
|
|
continue;
|
|
|
|
|
2015-12-15 20:47:52 +01:00
|
|
|
Dist = lcMul(Dist, RelativeRotation);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
// Check if we're close enough to one of the axis.
|
|
|
|
Dist.Normalize();
|
|
|
|
|
|
|
|
float dx = fabsf(Dist[0]);
|
|
|
|
float dy = fabsf(Dist[1]);
|
|
|
|
float dz = fabsf(Dist[2]);
|
|
|
|
|
|
|
|
if (dx < dy)
|
|
|
|
{
|
|
|
|
if (dx < dz)
|
|
|
|
{
|
|
|
|
if (dx < Epsilon)
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::RotateX;
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
if (dz < Epsilon)
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::RotateZ;
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
if (dy < dz)
|
|
|
|
{
|
|
|
|
if (dy < Epsilon)
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::RotateY;
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
if (dz < Epsilon)
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::RotateZ;
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
if (NewTrackTool != lcTrackTool::RotateXYZ)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
switch (NewTrackTool)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateX:
|
2014-05-18 01:03:05 +02:00
|
|
|
Dist[0] = 0.0f;
|
|
|
|
break;
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateY:
|
2014-05-18 01:03:05 +02:00
|
|
|
Dist[1] = 0.0f;
|
|
|
|
break;
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateZ:
|
2014-05-18 01:03:05 +02:00
|
|
|
Dist[2] = 0.0f;
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
2018-02-06 23:47:11 +01:00
|
|
|
mTrackToolFromOverlay = true;
|
2014-05-18 01:03:05 +02:00
|
|
|
Dist *= r;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
Redraw = true;
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Eraser:
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::Eraser;
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Paint:
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::Paint;
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::ColorPicker:
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::ColorPicker;
|
2020-02-15 20:14:12 +01:00
|
|
|
break;
|
2020-02-15 19:59:14 +01:00
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Zoom:
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::Zoom;
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Pan:
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::Pan;
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::RotateView:
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
int vx, vy, vw, vh;
|
|
|
|
|
|
|
|
vx = 0;
|
|
|
|
vy = 0;
|
|
|
|
vw = mWidth;
|
|
|
|
vh = mHeight;
|
|
|
|
|
|
|
|
int cx = vx + vw / 2;
|
|
|
|
int cy = vy + vh / 2;
|
|
|
|
|
|
|
|
float d = sqrtf((float)((cx - x) * (cx - x) + (cy - y) * (cy - y)));
|
|
|
|
float r = lcMin(vw, vh) * 0.35f;
|
|
|
|
|
2015-04-26 20:14:33 +02:00
|
|
|
const float SquareSize = lcMax(8.0f, (vw + vh) / 200.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
if ((d < r + SquareSize) && (d > r - SquareSize))
|
|
|
|
{
|
|
|
|
if ((cx - x < SquareSize) && (cx - x > -SquareSize))
|
2018-02-06 23:47:11 +01:00
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::OrbitY;
|
2018-02-06 23:47:11 +01:00
|
|
|
mTrackToolFromOverlay = true;
|
|
|
|
}
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
if ((cy - y < SquareSize) && (cy - y > -SquareSize))
|
2018-02-06 23:47:11 +01:00
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::OrbitX;
|
2018-02-06 23:47:11 +01:00
|
|
|
mTrackToolFromOverlay = true;
|
|
|
|
}
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
if (d < r)
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::OrbitXY;
|
2014-05-18 01:03:05 +02:00
|
|
|
else
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::Roll;
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Roll:
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::Roll;
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::ZoomRegion:
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::ZoomRegion;
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
2016-04-23 02:17:33 +02:00
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Count:
|
2016-04-23 02:17:33 +02:00
|
|
|
break;
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
2014-05-27 00:58:08 +02:00
|
|
|
switch (mDragState)
|
|
|
|
{
|
2020-02-15 20:36:06 +01:00
|
|
|
case lcDragState::None:
|
2014-05-27 00:58:08 +02:00
|
|
|
break;
|
|
|
|
|
2020-02-15 20:36:06 +01:00
|
|
|
case lcDragState::Piece:
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::Insert;
|
2014-05-27 00:58:08 +02:00
|
|
|
Redraw = true;
|
|
|
|
break;
|
2018-01-12 19:50:25 +01:00
|
|
|
|
2020-02-15 20:36:06 +01:00
|
|
|
case lcDragState::Color:
|
2020-12-05 01:06:39 +01:00
|
|
|
NewTrackTool = lcTrackTool::Paint;
|
2018-01-12 19:50:25 +01:00
|
|
|
break;
|
2014-05-27 00:58:08 +02:00
|
|
|
}
|
|
|
|
|
2020-12-06 20:15:23 +01:00
|
|
|
mTrackTool = NewTrackTool;
|
|
|
|
UpdateCursor();
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-12-06 20:15:23 +01:00
|
|
|
if (Redraw)
|
2020-12-16 02:19:32 +01:00
|
|
|
ActiveModel->UpdateAllViews();
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
bool lcView::IsTrackToolAllowed(lcTrackTool TrackTool, quint32 AllowedTransforms) const
|
2016-05-01 02:20:37 +02:00
|
|
|
{
|
|
|
|
switch (TrackTool)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::None:
|
|
|
|
case lcTrackTool::Insert:
|
|
|
|
case lcTrackTool::PointLight:
|
|
|
|
case lcTrackTool::SpotLight:
|
|
|
|
case lcTrackTool::Camera:
|
|
|
|
case lcTrackTool::Select:
|
2016-05-01 02:20:37 +02:00
|
|
|
return true;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::MoveX:
|
2016-05-01 02:20:37 +02:00
|
|
|
return AllowedTransforms & LC_OBJECT_TRANSFORM_MOVE_X;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::MoveY:
|
2016-05-01 02:20:37 +02:00
|
|
|
return AllowedTransforms & LC_OBJECT_TRANSFORM_MOVE_Y;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::MoveZ:
|
2016-05-01 02:20:37 +02:00
|
|
|
return AllowedTransforms & LC_OBJECT_TRANSFORM_MOVE_Z;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::MoveXY:
|
2016-05-01 02:20:37 +02:00
|
|
|
return (AllowedTransforms & (LC_OBJECT_TRANSFORM_MOVE_X | LC_OBJECT_TRANSFORM_MOVE_Y)) == (LC_OBJECT_TRANSFORM_MOVE_X | LC_OBJECT_TRANSFORM_MOVE_Y);
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::MoveXZ:
|
2016-05-01 02:20:37 +02:00
|
|
|
return (AllowedTransforms & (LC_OBJECT_TRANSFORM_MOVE_X | LC_OBJECT_TRANSFORM_MOVE_Z)) == (LC_OBJECT_TRANSFORM_MOVE_X | LC_OBJECT_TRANSFORM_MOVE_Z);
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::MoveYZ:
|
2016-05-01 02:20:37 +02:00
|
|
|
return (AllowedTransforms & (LC_OBJECT_TRANSFORM_MOVE_Y | LC_OBJECT_TRANSFORM_MOVE_Z)) == (LC_OBJECT_TRANSFORM_MOVE_Y | LC_OBJECT_TRANSFORM_MOVE_Z);
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::MoveXYZ:
|
2016-05-01 02:20:37 +02:00
|
|
|
return (AllowedTransforms & (LC_OBJECT_TRANSFORM_MOVE_X | LC_OBJECT_TRANSFORM_MOVE_Y | LC_OBJECT_TRANSFORM_MOVE_Z)) == (LC_OBJECT_TRANSFORM_MOVE_X | LC_OBJECT_TRANSFORM_MOVE_Y | LC_OBJECT_TRANSFORM_MOVE_Z);
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateX:
|
2016-05-01 02:20:37 +02:00
|
|
|
return AllowedTransforms & LC_OBJECT_TRANSFORM_ROTATE_X;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateY:
|
2016-05-01 02:20:37 +02:00
|
|
|
return AllowedTransforms & LC_OBJECT_TRANSFORM_ROTATE_Y;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateZ:
|
2016-05-01 02:20:37 +02:00
|
|
|
return AllowedTransforms & LC_OBJECT_TRANSFORM_ROTATE_Z;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateXY:
|
2016-05-01 02:20:37 +02:00
|
|
|
return (AllowedTransforms & (LC_OBJECT_TRANSFORM_ROTATE_X | LC_OBJECT_TRANSFORM_ROTATE_Y)) == (LC_OBJECT_TRANSFORM_ROTATE_X | LC_OBJECT_TRANSFORM_ROTATE_Y);
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateXYZ:
|
2016-05-01 02:20:37 +02:00
|
|
|
return (AllowedTransforms & (LC_OBJECT_TRANSFORM_ROTATE_X | LC_OBJECT_TRANSFORM_ROTATE_Y | LC_OBJECT_TRANSFORM_ROTATE_Z)) == (LC_OBJECT_TRANSFORM_ROTATE_X | LC_OBJECT_TRANSFORM_ROTATE_Y | LC_OBJECT_TRANSFORM_ROTATE_Z);
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::ScalePlus:
|
|
|
|
case lcTrackTool::ScaleMinus:
|
2016-05-01 02:20:37 +02:00
|
|
|
return AllowedTransforms & (LC_OBJECT_TRANSFORM_SCALE_X | LC_OBJECT_TRANSFORM_SCALE_Y | LC_OBJECT_TRANSFORM_SCALE_Z);
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Eraser:
|
|
|
|
case lcTrackTool::Paint:
|
|
|
|
case lcTrackTool::ColorPicker:
|
|
|
|
case lcTrackTool::Zoom:
|
|
|
|
case lcTrackTool::Pan:
|
|
|
|
case lcTrackTool::OrbitX:
|
|
|
|
case lcTrackTool::OrbitY:
|
|
|
|
case lcTrackTool::OrbitXY:
|
|
|
|
case lcTrackTool::Roll:
|
|
|
|
case lcTrackTool::ZoomRegion:
|
2016-05-01 02:20:37 +02:00
|
|
|
return true;
|
2020-02-24 23:31:08 +01:00
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Count:
|
2020-02-24 23:31:08 +01:00
|
|
|
return false;
|
2016-05-01 02:20:37 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::StartOrbitTracking()
|
2018-09-12 01:36:10 +02:00
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
mTrackTool = lcTrackTool::OrbitXY;
|
2020-12-05 21:17:09 +01:00
|
|
|
UpdateCursor();
|
2020-02-15 20:36:06 +01:00
|
|
|
OnButtonDown(lcTrackButton::Left);
|
2018-09-12 01:36:10 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:37:59 +01:00
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::StartTracking(lcTrackButton TrackButton)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
mTrackButton = TrackButton;
|
|
|
|
mTrackUpdated = false;
|
|
|
|
mMouseDownX = mMouseX;
|
|
|
|
mMouseDownY = mMouseY;
|
|
|
|
lcTool Tool = GetCurrentTool();
|
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
|
|
|
|
switch (Tool)
|
|
|
|
{
|
|
|
|
case lcTool::Insert:
|
|
|
|
case lcTool::Light:
|
|
|
|
break;
|
|
|
|
|
|
|
|
case lcTool::SpotLight:
|
|
|
|
{
|
|
|
|
lcVector3 Position = GetCameraLightInsertPosition();
|
|
|
|
lcVector3 Target = Position + lcVector3(0.1f, 0.1f, 0.1f);
|
|
|
|
ActiveModel->BeginSpotLightTool(Position, Target);
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
|
|
|
|
case lcTool::Camera:
|
|
|
|
{
|
|
|
|
lcVector3 Position = GetCameraLightInsertPosition();
|
|
|
|
lcVector3 Target = Position + lcVector3(0.1f, 0.1f, 0.1f);
|
|
|
|
ActiveModel->BeginCameraTool(Position, Target);
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
|
|
|
|
case lcTool::Select:
|
|
|
|
break;
|
|
|
|
|
|
|
|
case lcTool::Move:
|
|
|
|
case lcTool::Rotate:
|
|
|
|
ActiveModel->BeginMouseTool();
|
|
|
|
break;
|
|
|
|
|
|
|
|
case lcTool::Eraser:
|
|
|
|
case lcTool::Paint:
|
|
|
|
case lcTool::ColorPicker:
|
|
|
|
break;
|
|
|
|
|
|
|
|
case lcTool::Zoom:
|
|
|
|
case lcTool::Pan:
|
|
|
|
case lcTool::RotateView:
|
|
|
|
case lcTool::Roll:
|
|
|
|
ActiveModel->BeginMouseTool();
|
|
|
|
break;
|
|
|
|
|
|
|
|
case lcTool::ZoomRegion:
|
|
|
|
break;
|
|
|
|
|
|
|
|
case lcTool::Count:
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
UpdateCursor();
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::StopTracking(bool Accept)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2020-02-15 20:36:06 +01:00
|
|
|
if (mTrackButton == lcTrackButton::None)
|
2014-05-18 01:03:05 +02:00
|
|
|
return;
|
|
|
|
|
|
|
|
lcTool Tool = GetCurrentTool();
|
2018-03-29 19:20:36 +02:00
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
switch (Tool)
|
|
|
|
{
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Insert:
|
|
|
|
case lcTool::Light:
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::SpotLight:
|
|
|
|
case lcTool::Camera:
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->EndMouseTool(Tool, Accept);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Select:
|
2020-12-05 17:45:29 +01:00
|
|
|
if (Accept && mMouseDownX != mMouseX && mMouseDownY != mMouseY)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2020-12-05 17:45:29 +01:00
|
|
|
lcArray<lcObject*> Objects = FindObjectsInBox(mMouseDownX, mMouseDownY, mMouseX, mMouseY);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-12-05 17:45:29 +01:00
|
|
|
if (mMouseModifiers & Qt::ControlModifier)
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->AddToSelection(Objects, true, true);
|
2020-12-05 17:45:29 +01:00
|
|
|
else if (mMouseModifiers & Qt::ShiftModifier)
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->RemoveFromSelection(Objects);
|
2014-05-18 01:03:05 +02:00
|
|
|
else
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->SetSelectionAndFocus(Objects, nullptr, 0, true);
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Move:
|
|
|
|
case lcTool::Rotate:
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->EndMouseTool(Tool, Accept);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Eraser:
|
|
|
|
case lcTool::Paint:
|
|
|
|
case lcTool::ColorPicker:
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Zoom:
|
|
|
|
case lcTool::Pan:
|
|
|
|
case lcTool::RotateView:
|
|
|
|
case lcTool::Roll:
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->EndMouseTool(Tool, Accept);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::ZoomRegion:
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2020-12-05 17:45:29 +01:00
|
|
|
if (mMouseX == mMouseDownX || mMouseY == mMouseDownY)
|
2015-02-14 21:47:50 +01:00
|
|
|
break;
|
|
|
|
|
|
|
|
lcVector3 Points[6] =
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2020-12-05 17:45:29 +01:00
|
|
|
lcVector3((mMouseDownX + lcMin(mMouseX, mWidth - 1)) / 2, (mMouseDownY + lcMin(mMouseY, mHeight - 1)) / 2, 0.0f),
|
|
|
|
lcVector3((mMouseDownX + lcMin(mMouseX, mWidth - 1)) / 2, (mMouseDownY + lcMin(mMouseY, mHeight - 1)) / 2, 1.0f),
|
|
|
|
lcVector3((float)mMouseX, (float)mMouseY, 0.0f),
|
|
|
|
lcVector3((float)mMouseX, (float)mMouseY, 1.0f),
|
2015-02-14 21:47:50 +01:00
|
|
|
lcVector3(mMouseDownX, mMouseDownY, 0.0f),
|
|
|
|
lcVector3(mMouseDownX, mMouseDownY, 1.0f)
|
2014-05-18 01:03:05 +02:00
|
|
|
};
|
|
|
|
|
2015-02-14 21:47:50 +01:00
|
|
|
UnprojectPoints(Points, 5);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2018-03-29 19:20:36 +02:00
|
|
|
lcVector3 Center = ActiveModel->GetSelectionOrModelCenter();
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2015-02-14 21:47:50 +01:00
|
|
|
lcVector3 PlaneNormal(mCamera->mPosition - mCamera->mTargetPosition);
|
|
|
|
lcVector4 Plane(PlaneNormal, -lcDot(PlaneNormal, Center));
|
|
|
|
lcVector3 Target, Corners[2];
|
|
|
|
|
2018-02-04 20:53:13 +01:00
|
|
|
if (lcLineSegmentPlaneIntersection(&Target, Points[0], Points[1], Plane) && lcLineSegmentPlaneIntersection(&Corners[0], Points[2], Points[3], Plane) && lcLineSegmentPlaneIntersection(&Corners[1], Points[3], Points[4], Plane))
|
2015-02-15 03:24:08 +01:00
|
|
|
{
|
|
|
|
float AspectRatio = (float)mWidth / (float)mHeight;
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->ZoomRegionToolClicked(mCamera, AspectRatio, Points[0], Target, Corners);
|
2015-02-15 03:24:08 +01:00
|
|
|
}
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
break;
|
2016-04-23 02:17:33 +02:00
|
|
|
|
2020-12-05 00:38:49 +01:00
|
|
|
case lcTool::Count:
|
2016-04-23 02:17:33 +02:00
|
|
|
break;
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
2020-02-15 20:36:06 +01:00
|
|
|
mTrackButton = lcTrackButton::None;
|
2014-05-18 01:03:05 +02:00
|
|
|
UpdateTrackTool();
|
2020-12-16 02:19:32 +01:00
|
|
|
ActiveModel->UpdateAllViews();
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::CancelTrackingOrClearSelection()
|
2014-11-29 03:55:58 +01:00
|
|
|
{
|
2020-02-15 20:36:06 +01:00
|
|
|
if (mTrackButton != lcTrackButton::None)
|
2014-11-29 03:55:58 +01:00
|
|
|
StopTracking(false);
|
|
|
|
else
|
2018-03-29 19:20:36 +02:00
|
|
|
{
|
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
if (ActiveModel)
|
|
|
|
ActiveModel->ClearSelection(true);
|
|
|
|
}
|
2014-11-29 03:55:58 +01:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnButtonDown(lcTrackButton TrackButton)
|
2011-09-07 23:06:51 +02:00
|
|
|
{
|
2018-03-29 19:20:36 +02:00
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
2020-12-28 19:42:51 +01:00
|
|
|
mToolClicked = false;
|
2018-03-29 19:20:36 +02:00
|
|
|
|
2014-05-18 01:03:05 +02:00
|
|
|
switch (mTrackTool)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::None:
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Insert:
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2016-12-16 18:14:19 +01:00
|
|
|
PieceInfo* CurPiece = gMainWindow->GetCurrentPieceInfo();
|
2015-01-07 17:52:42 +01:00
|
|
|
|
|
|
|
if (!CurPiece)
|
|
|
|
break;
|
|
|
|
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->InsertPieceToolClicked(GetPieceInsertPosition(false, gMainWindow->GetCurrentPieceInfo()));
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-12-05 17:45:29 +01:00
|
|
|
if ((mMouseModifiers & Qt::ControlModifier) == 0)
|
2020-12-05 00:38:49 +01:00
|
|
|
gMainWindow->SetTool(lcTool::Select);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-12-28 19:42:51 +01:00
|
|
|
mToolClicked = true;
|
2014-05-18 01:03:05 +02:00
|
|
|
UpdateTrackTool();
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::PointLight:
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2019-08-10 21:31:28 +02:00
|
|
|
ActiveModel->PointLightToolClicked(GetCameraLightInsertPosition());
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-12-05 17:45:29 +01:00
|
|
|
if ((mMouseModifiers & Qt::ControlModifier) == 0)
|
2020-12-05 00:38:49 +01:00
|
|
|
gMainWindow->SetTool(lcTool::Select);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-12-28 19:42:51 +01:00
|
|
|
mToolClicked = true;
|
2014-05-18 01:03:05 +02:00
|
|
|
UpdateTrackTool();
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::SpotLight:
|
|
|
|
case lcTrackTool::Camera:
|
2016-05-09 03:59:10 +02:00
|
|
|
StartTracking(TrackButton);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Select:
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2017-11-13 04:38:07 +01:00
|
|
|
lcObjectSection ObjectSection = FindObjectUnderPointer(false, false);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-12-05 17:45:29 +01:00
|
|
|
if (mMouseModifiers & Qt::ControlModifier)
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->FocusOrDeselectObject(ObjectSection);
|
2020-12-05 17:45:29 +01:00
|
|
|
else if (mMouseModifiers & Qt::ShiftModifier)
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->RemoveFromSelection(ObjectSection);
|
2014-05-18 01:03:05 +02:00
|
|
|
else
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->ClearSelectionAndSetFocus(ObjectSection, true);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2016-05-09 03:59:10 +02:00
|
|
|
StartTracking(TrackButton);
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::MoveX:
|
|
|
|
case lcTrackTool::MoveY:
|
|
|
|
case lcTrackTool::MoveZ:
|
|
|
|
case lcTrackTool::MoveXY:
|
|
|
|
case lcTrackTool::MoveXZ:
|
|
|
|
case lcTrackTool::MoveYZ:
|
|
|
|
case lcTrackTool::MoveXYZ:
|
2018-03-29 19:20:36 +02:00
|
|
|
if (ActiveModel->AnyObjectsSelected())
|
2016-05-09 03:59:10 +02:00
|
|
|
StartTracking(TrackButton);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateX:
|
|
|
|
case lcTrackTool::RotateY:
|
|
|
|
case lcTrackTool::RotateZ:
|
|
|
|
case lcTrackTool::RotateXY:
|
|
|
|
case lcTrackTool::RotateXYZ:
|
2018-03-29 19:20:36 +02:00
|
|
|
if (ActiveModel->AnyPiecesSelected())
|
2016-05-09 03:59:10 +02:00
|
|
|
StartTracking(TrackButton);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::ScalePlus:
|
|
|
|
case lcTrackTool::ScaleMinus:
|
2018-03-29 19:20:36 +02:00
|
|
|
if (ActiveModel->AnyPiecesSelected())
|
2016-05-09 03:59:10 +02:00
|
|
|
StartTracking(TrackButton);
|
2016-03-12 01:05:49 +01:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Eraser:
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->EraserToolClicked(FindObjectUnderPointer(false, false).Object);
|
2020-12-28 19:42:51 +01:00
|
|
|
mToolClicked = true;
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Paint:
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->PaintToolClicked(FindObjectUnderPointer(true, false).Object);
|
2020-12-28 19:42:51 +01:00
|
|
|
mToolClicked = true;
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::ColorPicker:
|
2020-02-15 20:14:12 +01:00
|
|
|
ActiveModel->ColorPickerToolClicked(FindObjectUnderPointer(true, false).Object);
|
2020-12-28 19:42:51 +01:00
|
|
|
mToolClicked = true;
|
2020-02-15 20:14:12 +01:00
|
|
|
break;
|
2020-02-15 19:59:14 +01:00
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Zoom:
|
|
|
|
case lcTrackTool::Pan:
|
|
|
|
case lcTrackTool::OrbitX:
|
|
|
|
case lcTrackTool::OrbitY:
|
|
|
|
case lcTrackTool::OrbitXY:
|
|
|
|
case lcTrackTool::Roll:
|
|
|
|
case lcTrackTool::ZoomRegion:
|
2016-05-09 03:59:10 +02:00
|
|
|
StartTracking(TrackButton);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
2020-02-24 23:31:08 +01:00
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Count:
|
2020-02-24 23:31:08 +01:00
|
|
|
break;
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
2011-09-07 23:06:51 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnLeftButtonDown()
|
2016-05-09 03:59:10 +02:00
|
|
|
{
|
2020-02-15 20:36:06 +01:00
|
|
|
if (mTrackButton != lcTrackButton::None)
|
2016-05-09 03:59:10 +02:00
|
|
|
{
|
|
|
|
StopTracking(false);
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2020-12-16 03:47:58 +01:00
|
|
|
if (mViewSphere->OnLeftButtonDown())
|
2018-09-11 22:34:59 +02:00
|
|
|
return;
|
|
|
|
|
2016-05-09 03:59:10 +02:00
|
|
|
lcTrackTool OverrideTool = GetOverrideTrackTool(Qt::LeftButton);
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
if (OverrideTool != lcTrackTool::None)
|
2016-05-09 03:59:10 +02:00
|
|
|
{
|
|
|
|
mTrackTool = OverrideTool;
|
2020-12-05 21:17:09 +01:00
|
|
|
UpdateCursor();
|
2016-05-09 03:59:10 +02:00
|
|
|
}
|
|
|
|
|
2020-02-15 20:36:06 +01:00
|
|
|
OnButtonDown(lcTrackButton::Left);
|
2016-05-09 03:59:10 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnLeftButtonUp()
|
2011-09-07 23:06:51 +02:00
|
|
|
{
|
2020-02-15 20:36:06 +01:00
|
|
|
StopTracking(mTrackButton == lcTrackButton::Left);
|
2018-08-20 05:27:58 +02:00
|
|
|
|
2020-12-16 03:47:58 +01:00
|
|
|
if (mViewSphere->OnLeftButtonUp())
|
2018-08-20 05:27:58 +02:00
|
|
|
return;
|
2011-09-07 23:06:51 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnLeftButtonDoubleClick()
|
2011-09-07 23:06:51 +02:00
|
|
|
{
|
2020-12-26 21:10:14 +01:00
|
|
|
if (mViewType != lcViewType::View)
|
|
|
|
{
|
|
|
|
ZoomExtents();
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2017-11-13 04:38:07 +01:00
|
|
|
lcObjectSection ObjectSection = FindObjectUnderPointer(false, false);
|
2018-03-29 19:20:36 +02:00
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-12-05 17:45:29 +01:00
|
|
|
if (mMouseModifiers & Qt::ControlModifier)
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->FocusOrDeselectObject(ObjectSection);
|
2020-12-05 17:45:29 +01:00
|
|
|
else if (mMouseModifiers & Qt::ShiftModifier)
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->RemoveFromSelection(ObjectSection);
|
2014-05-18 01:03:05 +02:00
|
|
|
else
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->ClearSelectionAndSetFocus(ObjectSection, true);
|
2011-09-07 23:06:51 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnMiddleButtonDown()
|
2012-01-28 03:10:19 +01:00
|
|
|
{
|
2020-02-15 20:36:06 +01:00
|
|
|
if (mTrackButton != lcTrackButton::None)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
StopTracking(false);
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2016-09-22 17:04:51 +02:00
|
|
|
#if (QT_VERSION >= QT_VERSION_CHECK(4, 7, 0))
|
2016-04-23 02:17:33 +02:00
|
|
|
lcTrackTool OverrideTool = GetOverrideTrackTool(Qt::MiddleButton);
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
if (OverrideTool != lcTrackTool::None)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2016-04-23 02:17:33 +02:00
|
|
|
mTrackTool = OverrideTool;
|
2020-12-05 21:17:09 +01:00
|
|
|
UpdateCursor();
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
2016-09-22 17:04:51 +02:00
|
|
|
#endif
|
2020-02-15 20:36:06 +01:00
|
|
|
OnButtonDown(lcTrackButton::Middle);
|
2012-01-28 03:10:19 +01:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnMiddleButtonUp()
|
2012-01-28 03:10:19 +01:00
|
|
|
{
|
2020-02-15 20:36:06 +01:00
|
|
|
StopTracking(mTrackButton == lcTrackButton::Middle);
|
2012-01-28 03:10:19 +01:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnRightButtonDown()
|
2011-09-07 23:06:51 +02:00
|
|
|
{
|
2020-02-15 20:36:06 +01:00
|
|
|
if (mTrackButton != lcTrackButton::None)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
StopTracking(false);
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2016-04-23 02:17:33 +02:00
|
|
|
lcTrackTool OverrideTool = GetOverrideTrackTool(Qt::RightButton);
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
if (OverrideTool != lcTrackTool::None)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2016-04-23 02:17:33 +02:00
|
|
|
mTrackTool = OverrideTool;
|
2020-12-05 21:17:09 +01:00
|
|
|
UpdateCursor();
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
|
2020-02-15 20:36:06 +01:00
|
|
|
OnButtonDown(lcTrackButton::Right);
|
2011-09-07 23:06:51 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnRightButtonUp()
|
2011-09-07 23:06:51 +02:00
|
|
|
{
|
2020-12-28 19:42:51 +01:00
|
|
|
bool ShowMenu = !mToolClicked && (mTrackButton == lcTrackButton::None || !mTrackUpdated);
|
2016-05-19 23:16:31 +02:00
|
|
|
|
2020-02-15 20:36:06 +01:00
|
|
|
if (mTrackButton != lcTrackButton::None)
|
|
|
|
StopTracking(mTrackButton == lcTrackButton::Right);
|
2016-05-19 23:16:31 +02:00
|
|
|
|
|
|
|
if (ShowMenu)
|
|
|
|
ShowContextMenu();
|
2011-09-07 23:06:51 +02:00
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnBackButtonDown()
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnBackButtonUp()
|
2015-09-06 21:52:17 +02:00
|
|
|
{
|
|
|
|
gMainWindow->HandleCommand(LC_VIEW_TIME_PREVIOUS);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnForwardButtonDown()
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnForwardButtonUp()
|
2015-09-06 21:52:17 +02:00
|
|
|
{
|
|
|
|
gMainWindow->HandleCommand(LC_VIEW_TIME_NEXT);
|
|
|
|
}
|
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnMouseMove()
|
2011-09-07 23:06:51 +02:00
|
|
|
{
|
2018-03-29 19:20:36 +02:00
|
|
|
lcModel* ActiveModel = GetActiveModel();
|
|
|
|
|
|
|
|
if (!ActiveModel)
|
2018-01-07 00:01:04 +01:00
|
|
|
return;
|
|
|
|
|
2020-02-15 20:36:06 +01:00
|
|
|
if (mTrackButton == lcTrackButton::None)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2020-12-16 03:47:58 +01:00
|
|
|
if (mViewSphere->OnMouseMove())
|
2018-09-19 21:56:45 +02:00
|
|
|
{
|
2020-12-16 03:47:58 +01:00
|
|
|
lcTrackTool NewTrackTool = mViewSphere->IsDragging() ? lcTrackTool::OrbitXY : lcTrackTool::None;
|
2018-09-19 21:56:45 +02:00
|
|
|
|
|
|
|
if (NewTrackTool != mTrackTool)
|
|
|
|
{
|
|
|
|
mTrackTool = NewTrackTool;
|
2020-12-05 21:17:09 +01:00
|
|
|
UpdateCursor();
|
2018-09-19 21:56:45 +02:00
|
|
|
}
|
|
|
|
|
2018-08-20 05:27:58 +02:00
|
|
|
return;
|
2018-09-19 21:56:45 +02:00
|
|
|
}
|
2018-08-20 05:27:58 +02:00
|
|
|
|
2014-05-27 00:58:08 +02:00
|
|
|
UpdateTrackTool();
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
if (mTrackTool == lcTrackTool::Insert)
|
2020-12-16 02:19:32 +01:00
|
|
|
ActiveModel->UpdateAllViews();
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2016-05-19 23:16:31 +02:00
|
|
|
mTrackUpdated = true;
|
2019-03-01 01:12:18 +01:00
|
|
|
const float MouseSensitivity = 0.5f / (21.0f - lcGetPreferences().mMouseSensitivity);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
switch (mTrackTool)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::None:
|
|
|
|
case lcTrackTool::Insert:
|
|
|
|
case lcTrackTool::PointLight:
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::SpotLight:
|
2019-08-10 21:31:28 +02:00
|
|
|
ActiveModel->UpdateSpotLightTool(GetCameraLightInsertPosition());
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Camera:
|
2019-08-10 21:31:28 +02:00
|
|
|
ActiveModel->UpdateCameraTool(GetCameraLightInsertPosition());
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Select:
|
2014-05-18 01:03:05 +02:00
|
|
|
Redraw();
|
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::MoveX:
|
|
|
|
case lcTrackTool::MoveY:
|
|
|
|
case lcTrackTool::MoveZ:
|
|
|
|
case lcTrackTool::MoveXY:
|
|
|
|
case lcTrackTool::MoveXZ:
|
|
|
|
case lcTrackTool::MoveYZ:
|
|
|
|
case lcTrackTool::MoveXYZ:
|
|
|
|
case lcTrackTool::ScalePlus:
|
|
|
|
case lcTrackTool::ScaleMinus:
|
2016-03-12 01:05:49 +01:00
|
|
|
{
|
2014-05-18 01:03:05 +02:00
|
|
|
lcVector3 Points[4] =
|
|
|
|
{
|
2020-12-05 17:45:29 +01:00
|
|
|
lcVector3((float)mMouseX, (float)mMouseY, 0.0f),
|
|
|
|
lcVector3((float)mMouseX, (float)mMouseY, 1.0f),
|
2014-05-18 01:03:05 +02:00
|
|
|
lcVector3(mMouseDownX, mMouseDownY, 0.0f),
|
|
|
|
lcVector3(mMouseDownX, mMouseDownY, 1.0f)
|
|
|
|
};
|
|
|
|
|
|
|
|
UnprojectPoints(Points, 4);
|
|
|
|
|
|
|
|
const lcVector3& CurrentStart = Points[0];
|
|
|
|
const lcVector3& CurrentEnd = Points[1];
|
|
|
|
const lcVector3& MouseDownStart = Points[2];
|
|
|
|
const lcVector3& MouseDownEnd = Points[3];
|
2016-03-13 21:07:28 +01:00
|
|
|
|
|
|
|
lcVector3 Center;
|
|
|
|
lcMatrix33 RelativeRotation;
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->GetMoveRotateTransform(Center, RelativeRotation);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
if (mTrackTool == lcTrackTool::MoveX || mTrackTool == lcTrackTool::MoveY || mTrackTool == lcTrackTool::MoveZ)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
lcVector3 Direction;
|
2020-12-05 01:06:39 +01:00
|
|
|
if (mTrackTool == lcTrackTool::MoveX)
|
2016-03-12 01:05:49 +01:00
|
|
|
Direction = lcVector3(1.0f, 0.0f, 0.0f);
|
2020-12-05 01:06:39 +01:00
|
|
|
else if (mTrackTool == lcTrackTool::MoveY)
|
2016-03-12 01:05:49 +01:00
|
|
|
Direction = lcVector3(0.0f, 1.0f, 0.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
else
|
2016-03-12 01:05:49 +01:00
|
|
|
Direction = lcVector3(0.0f, 0.0f, 1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2015-12-15 20:47:52 +01:00
|
|
|
Direction = lcMul(Direction, RelativeRotation);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
lcVector3 Intersection;
|
2017-04-14 02:26:40 +02:00
|
|
|
lcClosestPointsBetweenLines(Center, Center + Direction, CurrentStart, CurrentEnd, &Intersection, nullptr);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
lcVector3 MoveStart;
|
2017-04-14 02:26:40 +02:00
|
|
|
lcClosestPointsBetweenLines(Center, Center + Direction, MouseDownStart, MouseDownEnd, &MoveStart, nullptr);
|
2014-05-18 01:03:05 +02:00
|
|
|
|
|
|
|
lcVector3 Distance = Intersection - MoveStart;
|
2015-12-15 20:47:52 +01:00
|
|
|
Distance = lcMul(Distance, lcMatrix33AffineInverse(RelativeRotation));
|
2020-02-15 20:36:06 +01:00
|
|
|
ActiveModel->UpdateMoveTool(Distance, mTrackButton != lcTrackButton::Left);
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
2020-12-05 01:06:39 +01:00
|
|
|
else if (mTrackTool == lcTrackTool::MoveXY || mTrackTool == lcTrackTool::MoveXZ || mTrackTool == lcTrackTool::MoveYZ)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
lcVector3 PlaneNormal;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
if (mTrackTool == lcTrackTool::MoveXY)
|
2014-05-18 01:03:05 +02:00
|
|
|
PlaneNormal = lcVector3(0.0f, 0.0f, 1.0f);
|
2020-12-05 01:06:39 +01:00
|
|
|
else if (mTrackTool == lcTrackTool::MoveXZ)
|
2014-05-18 01:03:05 +02:00
|
|
|
PlaneNormal = lcVector3(0.0f, 1.0f, 0.0f);
|
|
|
|
else
|
|
|
|
PlaneNormal = lcVector3(1.0f, 0.0f, 0.0f);
|
|
|
|
|
2015-12-15 20:47:52 +01:00
|
|
|
PlaneNormal = lcMul(PlaneNormal, RelativeRotation);
|
2014-05-18 01:03:05 +02:00
|
|
|
lcVector4 Plane(PlaneNormal, -lcDot(PlaneNormal, Center));
|
|
|
|
lcVector3 Intersection;
|
|
|
|
|
2018-02-04 20:53:13 +01:00
|
|
|
if (lcLineSegmentPlaneIntersection(&Intersection, CurrentStart, CurrentEnd, Plane))
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
lcVector3 MoveStart;
|
|
|
|
|
2018-02-04 20:53:13 +01:00
|
|
|
if (lcLineSegmentPlaneIntersection(&MoveStart, MouseDownStart, MouseDownEnd, Plane))
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
lcVector3 Distance = Intersection - MoveStart;
|
2015-12-15 20:47:52 +01:00
|
|
|
Distance = lcMul(Distance, lcMatrix33AffineInverse(RelativeRotation));
|
2020-02-15 20:36:06 +01:00
|
|
|
ActiveModel->UpdateMoveTool(Distance, mTrackButton != lcTrackButton::Left);
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2020-12-05 01:06:39 +01:00
|
|
|
else if (mTrackTool == lcTrackTool::MoveXYZ && mMouseDownPiece)
|
2017-11-13 04:38:07 +01:00
|
|
|
{
|
|
|
|
lcMatrix44 NewPosition = GetPieceInsertPosition(true, mMouseDownPiece);
|
|
|
|
lcVector3 Distance = NewPosition.GetTranslation() - mMouseDownPosition;
|
2020-02-15 20:36:06 +01:00
|
|
|
ActiveModel->UpdateMoveTool(Distance, mTrackButton != lcTrackButton::Left);
|
2017-11-13 04:38:07 +01:00
|
|
|
}
|
2020-12-05 01:06:39 +01:00
|
|
|
else if (mTrackTool == lcTrackTool::ScalePlus || mTrackTool == lcTrackTool::ScaleMinus)
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
2016-03-12 01:05:49 +01:00
|
|
|
lcVector3 Direction;
|
2020-12-05 01:06:39 +01:00
|
|
|
if (mTrackTool == lcTrackTool::ScalePlus)
|
2016-04-19 18:30:29 +02:00
|
|
|
Direction = lcVector3(1.0f, 0.0f, 0.0f);
|
2016-03-12 01:05:49 +01:00
|
|
|
else
|
2016-04-19 18:30:29 +02:00
|
|
|
Direction = lcVector3(-1.0f, 0.0f, 0.0f);
|
2016-03-12 01:05:49 +01:00
|
|
|
|
|
|
|
Direction = lcMul(Direction, RelativeRotation);
|
|
|
|
|
|
|
|
lcVector3 Intersection;
|
2017-04-14 02:26:40 +02:00
|
|
|
lcClosestPointsBetweenLines(Center, Center + Direction, CurrentStart, CurrentEnd, &Intersection, nullptr);
|
2016-03-12 01:05:49 +01:00
|
|
|
|
2018-03-29 19:20:36 +02:00
|
|
|
lcObject* Focus = ActiveModel->GetFocusObject();
|
2016-03-12 01:05:49 +01:00
|
|
|
if (Focus && Focus->IsPiece())
|
|
|
|
{
|
|
|
|
lcPiece* Piece = (lcPiece*)Focus;
|
2017-12-02 21:22:04 +01:00
|
|
|
quint32 Section = Piece->GetFocusSection();
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-03-22 19:12:15 +01:00
|
|
|
if (Section >= LC_PIECE_SECTION_CONTROL_POINT_FIRST && Section <= LC_PIECE_SECTION_CONTROL_POINT_LAST)
|
2016-03-12 01:05:49 +01:00
|
|
|
{
|
|
|
|
const float ScaleMax = 200.0f;
|
|
|
|
const float OverlayScale = GetOverlayScale();
|
|
|
|
const float ScaleStart = 2.0f * OverlayScale;
|
|
|
|
|
|
|
|
lcVector3 Position = Piece->GetSectionPosition(Section);
|
|
|
|
lcVector3 Start = Position + Direction * ScaleStart;
|
|
|
|
|
|
|
|
float Distance = lcLength(Intersection - Start);
|
|
|
|
if (lcDot(Direction, Intersection - Start) < 0.0f)
|
|
|
|
Distance = 0.0f;
|
|
|
|
|
|
|
|
float Scale = lcClamp(Distance, 0.1f, ScaleMax);
|
|
|
|
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->UpdateScaleTool(Scale);
|
2016-03-12 01:05:49 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2014-05-18 01:03:05 +02:00
|
|
|
lcVector3 PlaneNormal = lcNormalize(mCamera->mTargetPosition - mCamera->mPosition);
|
|
|
|
lcVector4 Plane(PlaneNormal, -lcDot(PlaneNormal, Center));
|
|
|
|
lcVector3 Intersection;
|
|
|
|
|
2018-02-04 20:53:13 +01:00
|
|
|
if (lcLineSegmentPlaneIntersection(&Intersection, CurrentStart, CurrentEnd, Plane))
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
lcVector3 MoveStart;
|
|
|
|
|
2018-02-04 20:53:13 +01:00
|
|
|
if (lcLineSegmentPlaneIntersection(&MoveStart, MouseDownStart, MouseDownEnd, Plane))
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
lcVector3 Distance = Intersection - MoveStart;
|
2020-02-15 20:36:06 +01:00
|
|
|
ActiveModel->UpdateMoveTool(Distance, mTrackButton != lcTrackButton::Left);
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateX:
|
|
|
|
case lcTrackTool::RotateY:
|
|
|
|
case lcTrackTool::RotateZ:
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
lcVector3 ScreenX = lcNormalize(lcCross(mCamera->mTargetPosition - mCamera->mPosition, mCamera->mUpVector));
|
|
|
|
lcVector3 ScreenY = mCamera->mUpVector;
|
|
|
|
lcVector3 Dir1;
|
|
|
|
|
|
|
|
switch (mTrackTool)
|
|
|
|
{
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateX:
|
2016-01-25 20:57:27 +01:00
|
|
|
Dir1 = lcVector3(1.0f, 0.0f, 0.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateY:
|
2016-01-25 20:57:27 +01:00
|
|
|
Dir1 = lcVector3(0.0f, 1.0f, 0.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateZ:
|
2016-01-25 20:57:27 +01:00
|
|
|
Dir1 = lcVector3(0.0f, 0.0f, 1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
default:
|
2016-01-25 20:57:27 +01:00
|
|
|
Dir1 = lcVector3(0.0f, 0.0f, 1.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
lcVector3 MoveX, MoveY;
|
|
|
|
|
|
|
|
float dx1 = lcDot(ScreenX, Dir1);
|
|
|
|
float dy1 = lcDot(ScreenY, Dir1);
|
|
|
|
|
|
|
|
if (fabsf(dx1) > fabsf(dy1))
|
|
|
|
{
|
|
|
|
if (dx1 >= 0.0f)
|
|
|
|
MoveX = Dir1;
|
|
|
|
else
|
|
|
|
MoveX = -Dir1;
|
|
|
|
|
|
|
|
MoveY = lcVector3(0, 0, 0);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
MoveX = lcVector3(0, 0, 0);
|
|
|
|
|
|
|
|
if (dy1 > 0.0f)
|
|
|
|
MoveY = Dir1;
|
|
|
|
else
|
|
|
|
MoveY = -Dir1;
|
|
|
|
}
|
|
|
|
|
2020-12-05 17:45:29 +01:00
|
|
|
MoveX *= 36.0f * (float)(mMouseX - mMouseDownX) * MouseSensitivity;
|
|
|
|
MoveY *= 36.0f * (float)(mMouseY - mMouseDownY) * MouseSensitivity;
|
2014-05-18 01:03:05 +02:00
|
|
|
|
2020-02-15 20:36:06 +01:00
|
|
|
ActiveModel->UpdateRotateTool(MoveX + MoveY, mTrackButton != lcTrackButton::Left);
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateXY:
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
lcVector3 ScreenZ = lcNormalize(mCamera->mTargetPosition - mCamera->mPosition);
|
|
|
|
lcVector3 ScreenX = lcCross(ScreenZ, mCamera->mUpVector);
|
|
|
|
lcVector3 ScreenY = mCamera->mUpVector;
|
|
|
|
|
2020-12-05 17:45:29 +01:00
|
|
|
lcVector3 MoveX = 36.0f * (float)(mMouseX - mMouseDownX) * MouseSensitivity * ScreenX;
|
|
|
|
lcVector3 MoveY = 36.0f * (float)(mMouseY - mMouseDownY) * MouseSensitivity * ScreenY;
|
2020-02-15 20:36:06 +01:00
|
|
|
ActiveModel->UpdateRotateTool(MoveX + MoveY, mTrackButton != lcTrackButton::Left);
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::RotateXYZ:
|
2014-05-18 01:03:05 +02:00
|
|
|
{
|
|
|
|
lcVector3 ScreenZ = lcNormalize(mCamera->mTargetPosition - mCamera->mPosition);
|
|
|
|
|
2020-12-05 17:45:29 +01:00
|
|
|
ActiveModel->UpdateRotateTool(36.0f * (float)(mMouseY - mMouseDownY) * MouseSensitivity * ScreenZ, mTrackButton != lcTrackButton::Left);
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Eraser:
|
|
|
|
case lcTrackTool::Paint:
|
|
|
|
case lcTrackTool::ColorPicker:
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Zoom:
|
2020-12-05 17:45:29 +01:00
|
|
|
ActiveModel->UpdateZoomTool(mCamera, 2.0f * MouseSensitivity * (mMouseY - mMouseDownY));
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Pan:
|
2015-02-08 22:05:50 +01:00
|
|
|
{
|
|
|
|
lcVector3 Points[4] =
|
|
|
|
{
|
2020-12-05 17:45:29 +01:00
|
|
|
lcVector3((float)mMouseX, (float)mMouseY, 0.0f),
|
|
|
|
lcVector3((float)mMouseX, (float)mMouseY, 1.0f),
|
2015-02-08 22:05:50 +01:00
|
|
|
lcVector3(mMouseDownX, mMouseDownY, 0.0f),
|
|
|
|
lcVector3(mMouseDownX, mMouseDownY, 1.0f)
|
|
|
|
};
|
|
|
|
|
|
|
|
UnprojectPoints(Points, 4);
|
|
|
|
|
|
|
|
const lcVector3& CurrentStart = Points[0];
|
|
|
|
const lcVector3& CurrentEnd = Points[1];
|
|
|
|
const lcVector3& MouseDownStart = Points[2];
|
|
|
|
const lcVector3& MouseDownEnd = Points[3];
|
2018-03-29 19:20:36 +02:00
|
|
|
lcVector3 Center = ActiveModel->GetSelectionOrModelCenter();
|
2015-02-08 22:05:50 +01:00
|
|
|
|
|
|
|
lcVector3 PlaneNormal(mCamera->mPosition - mCamera->mTargetPosition);
|
|
|
|
lcVector4 Plane(PlaneNormal, -lcDot(PlaneNormal, Center));
|
2018-02-04 20:53:13 +01:00
|
|
|
lcVector3 Intersection, MoveStart;
|
2015-02-08 22:05:50 +01:00
|
|
|
|
2018-02-04 20:53:13 +01:00
|
|
|
if (!lcLineSegmentPlaneIntersection(&Intersection, CurrentStart, CurrentEnd, Plane) || !lcLineSegmentPlaneIntersection(&MoveStart, MouseDownStart, MouseDownEnd, Plane))
|
2015-02-08 22:05:50 +01:00
|
|
|
{
|
2018-02-04 20:53:13 +01:00
|
|
|
Center = MouseDownStart + lcNormalize(MouseDownEnd - MouseDownStart) * 10.0f;
|
|
|
|
Plane = lcVector4(PlaneNormal, -lcDot(PlaneNormal, Center));
|
2015-02-08 22:05:50 +01:00
|
|
|
|
2018-02-04 20:53:13 +01:00
|
|
|
if (!lcLineSegmentPlaneIntersection(&Intersection, CurrentStart, CurrentEnd, Plane) || !lcLineSegmentPlaneIntersection(&MoveStart, MouseDownStart, MouseDownEnd, Plane))
|
|
|
|
break;
|
2015-02-08 22:05:50 +01:00
|
|
|
}
|
2018-02-04 20:53:13 +01:00
|
|
|
|
2018-03-29 19:20:36 +02:00
|
|
|
ActiveModel->UpdatePanTool(mCamera, MoveStart - Intersection);
|
2015-02-08 22:05:50 +01:00
|
|
|
}
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::OrbitX:
|
2020-12-05 17:45:29 +01:00
|
|
|
ActiveModel->UpdateOrbitTool(mCamera, 0.1f * MouseSensitivity * (mMouseX - mMouseDownX), 0.0f);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::OrbitY:
|
2020-12-05 17:45:29 +01:00
|
|
|
ActiveModel->UpdateOrbitTool(mCamera, 0.0f, 0.1f * MouseSensitivity * (mMouseY - mMouseDownY));
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::OrbitXY:
|
2020-12-05 17:45:29 +01:00
|
|
|
ActiveModel->UpdateOrbitTool(mCamera, 0.1f * MouseSensitivity * (mMouseX - mMouseDownX), 0.1f * MouseSensitivity * (mMouseY - mMouseDownY));
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Roll:
|
2020-12-05 17:45:29 +01:00
|
|
|
ActiveModel->UpdateRollTool(mCamera, 2.0f * MouseSensitivity * (mMouseX - mMouseDownX) * LC_DTOR);
|
2014-05-18 01:03:05 +02:00
|
|
|
break;
|
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::ZoomRegion:
|
2014-05-18 01:03:05 +02:00
|
|
|
Redraw();
|
|
|
|
break;
|
2020-02-24 23:31:08 +01:00
|
|
|
|
2020-12-05 01:06:39 +01:00
|
|
|
case lcTrackTool::Count:
|
2020-02-24 23:31:08 +01:00
|
|
|
break;
|
2014-05-18 01:03:05 +02:00
|
|
|
}
|
2013-01-28 20:57:33 +01:00
|
|
|
}
|
2020-12-25 19:37:59 +01:00
|
|
|
|
2020-12-25 19:54:33 +01:00
|
|
|
void lcView::OnMouseWheel(float Direction)
|
2020-12-25 19:37:59 +01:00
|
|
|
{
|
|
|
|
mModel->Zoom(mCamera, (int)(((mMouseModifiers & Qt::ControlModifier) ? 100 : 10) * Direction));
|
|
|
|
}
|