17#include <QMdiSubWindow>
18#include <QSurfaceFormat>
24#include "WorldEditor.h"
25#include "SceneWindow.h"
26#include "EngineWindow.h"
27#include "aeongames/Node.hpp"
29#include "aeongames/StringId.hpp"
32#pragma warning( push )
33#pragma warning( disable : PROTOBUF_WARNINGS )
35#include <google/protobuf/message.h>
47 QWidget* widget = QWidget::createWindowContainer ( mEngineWindow, mUi.splitter );
48 QSizePolicy size_policy ( QSizePolicy::Ignored, QSizePolicy::Ignored );
49 size_policy.setHorizontalStretch ( 1 );
50 size_policy.setVerticalStretch ( 1 );
51 widget->setSizePolicy ( size_policy );
52 mUi.splitter->addWidget ( widget );
53 mUi.sceneTreeView->setModel ( &mSceneModel );
54 mUi.componentListView->setModel ( &mComponentListModel );
55 mUi.componentPropertyTreeView->setModel ( &mComponentModel );
56 mUi.componentPropertyTreeView->setItemDelegate ( &mPropertyDelegate );
57 mEngineWindow->setScene ( &mSceneModel.GetScene() );
61 QString text ( tr (
"Add " ) );
62 text.append ( aComponentConstructor.
GetString() );
63 text.append ( tr (
" Data" ) );
64 QAction *action =
new QAction ( QIcon (
":/icons/icon_add" ), text,
this );
65 mComponentAddActions.append ( action );
66 action->setStatusTip ( tr (
"Adds a new component of the specified type to the selected node" ) );
67 connect ( action, &QAction::triggered,
this,
68 [
this, aComponentConstructor]()
70 QModelIndex index = mUi.sceneTreeView->currentIndex();
71 if ( index.isValid() )
73 Node* node =
reinterpret_cast<Node*
> ( index.internalPointer() );
74 mComponentListModel.SetNode ( node );
84 void SceneWindow::on_actionRemoveNode_triggered()
86 QModelIndex index = mUi.sceneTreeView->currentIndex();
87 mSceneModel.
RemoveNode ( index.row(), index.parent() );
90 void SceneWindow::on_actionSetCameraNode_triggered()
92 QModelIndex index = mUi.sceneTreeView->currentIndex();
96 void SceneWindow::on_actionRemoveComponent_triggered()
98 QModelIndex index = mUi.componentListView->currentIndex();
103 void SceneWindow::on_actionAddNode_triggered()
105 QModelIndex index = mUi.sceneTreeView->currentIndex();
106 mSceneModel.InsertNode ( mSceneModel.rowCount ( index ), index, std::make_unique<Node>() );
107 mUi.sceneTreeView->expand ( index );
110 void SceneWindow::on_sceneContextMenuRequested (
const QPoint& aPoint )
112 QList<QAction *> actions;
113 QModelIndex index = mUi.sceneTreeView->indexAt ( aPoint );
114 actions.append ( mUi.actionAddNode );
115 if ( index.isValid() )
117 actions.append ( mUi.actionRemoveNode );
118 actions.append ( mUi.actionSetCameraNode );
120 mUi.sceneTreeView->setCurrentIndex ( index );
121 QMenu::exec ( actions, mUi.sceneTreeView->mapToGlobal ( aPoint ) );
124 void SceneWindow::on_componentContextMenuRequested (
const QPoint& aPoint )
126 if ( !mUi.sceneTreeView->currentIndex().isValid() )
130 QList<QAction *> actions;
131 actions.append ( mComponentAddActions );
132 QModelIndex index = mUi.componentListView->indexAt ( aPoint );
133 if ( index.isValid() )
135 actions.append ( mUi.actionRemoveComponent );
137 mUi.componentListView->setCurrentIndex ( index );
138 if ( actions.size() )
140 QMenu::exec ( actions, mUi.componentListView->mapToGlobal ( aPoint ) );
144 void SceneWindow::UpdateLocalTransformData (
const Node* aNode )
146 static std::array<std::tuple<QWidget*, bool>, 9> widgets
149 {mUi.localScaleX, {}},
150 {mUi.localScaleY, {}},
151 {mUi.localScaleZ, {}},
152 {mUi.localRotationPitch, {}},
153 {mUi.localRotationRoll, {}},
154 {mUi.localRotationYaw, {}},
155 {mUi.localTranslationX, {}},
156 {mUi.localTranslationY, {}},
157 {mUi.localTranslationZ, {}}
160 for (
auto& i : widgets )
162 std::get<1> ( i ) = std::get<0> ( i )->blockSignals (
true );
166 const Transform& local = aNode->GetLocalTransform();
167 mUi.localScaleX->setValue ( local.GetScale() [0] );
168 mUi.localScaleY->setValue ( local.GetScale() [1] );
169 mUi.localScaleZ->setValue ( local.GetScale() [2] );
170 mUi.localRotationPitch->setValue ( local.GetRotation().GetEuler() [0] );
171 mUi.localRotationRoll->setValue ( local.GetRotation().GetEuler() [1] );
172 mUi.localRotationYaw->setValue ( local.GetRotation().GetEuler() [2] );
173 mUi.localTranslationX->setValue ( local.GetTranslation() [0] );
174 mUi.localTranslationY->setValue ( local.GetTranslation() [1] );
175 mUi.localTranslationZ->setValue ( local.GetTranslation() [2] );
179 mUi.localScaleX->setValue ( 1 );
180 mUi.localScaleY->setValue ( 1 );
181 mUi.localScaleZ->setValue ( 1 );
182 mUi.localRotationPitch->setValue ( 0 );
183 mUi.localRotationRoll->setValue ( 0 );
184 mUi.localRotationYaw->setValue ( 0 );
185 mUi.localTranslationX->setValue ( 0 );
186 mUi.localTranslationY->setValue ( 0 );
187 mUi.localTranslationZ->setValue ( 0 );
189 for (
auto& i : widgets )
191 std::get<0> ( i )->blockSignals ( std::get<1> ( i ) );
195 void SceneWindow::UpdateGlobalTransformData (
const Node* aNode )
197 static std::array<std::tuple<QWidget*, bool>, 9> widgets
200 {mUi.globalScaleX, {}},
201 {mUi.globalScaleY, {}},
202 {mUi.globalScaleZ, {}},
203 {mUi.globalRotationPitch, {}},
204 {mUi.globalRotationRoll, {}},
205 {mUi.globalRotationYaw, {}},
206 {mUi.globalTranslationX, {}},
207 {mUi.globalTranslationY, {}},
208 {mUi.globalTranslationZ, {}}
211 for (
auto& i : widgets )
213 std::get<1> ( i ) = std::get<0> ( i )->blockSignals (
true );
217 const Transform& global = aNode->GetGlobalTransform();
218 mUi.globalScaleX->setValue ( global.GetScale() [0] );
219 mUi.globalScaleY->setValue ( global.GetScale() [1] );
220 mUi.globalScaleZ->setValue ( global.GetScale() [2] );
221 mUi.globalRotationPitch->setValue ( global.GetRotation().GetEuler() [0] );
222 mUi.globalRotationRoll->setValue ( global.GetRotation().GetEuler() [1] );
223 mUi.globalRotationYaw->setValue ( global.GetRotation().GetEuler() [2] );
224 mUi.globalTranslationX->setValue ( global.GetTranslation() [0] );
225 mUi.globalTranslationY->setValue ( global.GetTranslation() [1] );
226 mUi.globalTranslationZ->setValue ( global.GetTranslation() [2] );
230 mUi.globalScaleX->setValue ( 1 );
231 mUi.globalScaleY->setValue ( 1 );
232 mUi.globalScaleZ->setValue ( 1 );
233 mUi.globalRotationPitch->setValue ( 0 );
234 mUi.globalRotationRoll->setValue ( 0 );
235 mUi.globalRotationYaw->setValue ( 0 );
236 mUi.globalTranslationX->setValue ( 0 );
237 mUi.globalTranslationY->setValue ( 0 );
238 mUi.globalTranslationZ->setValue ( 0 );
240 for (
auto& i : widgets )
242 std::get<0> ( i )->blockSignals ( std::get<1> ( i ) );
246 void SceneWindow::on_localTransformChanged()
248 QModelIndex index = mUi.sceneTreeView->currentIndex();
249 if ( index.isValid() )
251 if ( Node * node =
reinterpret_cast<Node *
> ( index.internalPointer() ) )
256 static_cast<float> ( mUi.localScaleX->value() ),
257 static_cast<float> ( mUi.localScaleY->value() ),
258 static_cast<float> ( mUi.localScaleZ->value() )
261 static_cast<float> ( mUi.localRotationPitch->value() ),
262 static_cast<float> ( mUi.localRotationRoll->value() ),
263 static_cast<float> ( mUi.localRotationYaw->value() )
266 static_cast<float> ( mUi.localTranslationX->value() ),
267 static_cast<float> ( mUi.localTranslationY->value() ),
268 static_cast<float> ( mUi.localTranslationZ->value() )
271 node->SetLocalTransform ( local );
272 UpdateGlobalTransformData ( node );
277 void SceneWindow::on_globalTransformChanged()
279 QModelIndex index = mUi.sceneTreeView->currentIndex();
280 if ( index.isValid() )
282 if ( Node * node =
reinterpret_cast<Node *
> ( index.internalPointer() ) )
287 static_cast<float> ( mUi.globalScaleX->value() ),
288 static_cast<float> ( mUi.globalScaleY->value() ),
289 static_cast<float> ( mUi.globalScaleZ->value() )
292 static_cast<float> ( mUi.globalRotationPitch->value() ),
293 static_cast<float> ( mUi.globalRotationRoll->value() ),
294 static_cast<float> ( mUi.globalRotationYaw->value() )
297 static_cast<float> ( mUi.globalTranslationX->value() ),
298 static_cast<float> ( mUi.globalTranslationY->value() ),
299 static_cast<float> ( mUi.globalTranslationZ->value() )
302 node->SetGlobalTransform ( global );
303 UpdateLocalTransformData ( node );
308 void SceneWindow::on_sceneTreeViewClicked (
const QModelIndex& aModelIndex )
310 if ( aModelIndex.isValid() )
312 if ( Node * node =
reinterpret_cast<Node *
> ( aModelIndex.internalPointer() ) )
314 mComponentListModel.SetNode ( node );
315 mComponentModel.SetComponent (
nullptr );
316 UpdateLocalTransformData ( node );
317 UpdateGlobalTransformData ( node );
321 mComponentListModel.SetNode (
nullptr );
322 mComponentModel.SetComponent (
nullptr );
323 UpdateLocalTransformData (
nullptr );
324 UpdateGlobalTransformData (
nullptr );
327 void SceneWindow::on_componentListViewClicked (
const QModelIndex& aModelIndex )
329 if ( aModelIndex.isValid() && mComponentListModel.GetNode() )
331 mComponentModel.SetComponent ( mComponentListModel.GetNode()->GetComponentByIndex ( aModelIndex.row() ) );
335 mComponentModel.SetComponent (
nullptr );
342 file.exceptions ( std::ifstream::failbit | std::ifstream::badbit );
343 file.open ( mFilename, std::ifstream::in | std::ifstream::binary );
344 std::string buffer ( ( std::istreambuf_iterator<char> ( file ) ), std::istreambuf_iterator<char>() );
346 mSceneModel.Deserialize ( buffer );
350 std::string scene = mSceneModel.Serialize (
false );
351 std::ofstream scene_file ( mFilename, std::ifstream::out );
352 scene_file.write ( scene.data(), scene.size() );
357 mEngineWindow->SetFieldOfView ( aFieldOfView );
361 mEngineWindow->SetNear ( aNear );
365 mEngineWindow->SetFar ( aFar );
369 std::cout <<
LogLevel::Info <<
"Closing SceneWindow" << std::endl;
373 QCoreApplication::sendEvent ( mEngineWindow, &
closeEvent );
375 QWidget::closeEvent ( event );
Defines log severity levels and stream output for the AeonGames engine.
Provides the DLL_PROTOBUF export/import macro for protobuf wrapper classes.
Rendering window that hosts the engine viewport.
Scene graph node representing an entity in the game world.
DLL Component * AddComponent(std::unique_ptr< Component > aComponent)
Add a component to this node.
void SetCameraNode(const QModelIndex &index=QModelIndex())
Set the camera to the node at the given index.
void RemoveNode(int row, const QModelIndex &parent=QModelIndex())
Remove a node from the scene tree.
SceneWindow(QWidget *parent=Q_NULLPTR, Qt::WindowFlags f=Qt::WindowFlags())
Construct the scene window widget.
void Save(const std::string &mFilename) const
Save the scene to a file.
void Open(const std::string &mFilename)
Open a scene file.
virtual ~SceneWindow()
Destructor.
void closeEvent(QCloseEvent *event) override
Handle window close events.
void SetNear(float aNear)
Set the near clipping plane distance.
void SetFieldOfView(float aFieldOfView)
Set the camera field of view.
void SetFar(float aFar)
Set the far clipping plane distance.
CRC-based compile-time string identifier.
constexpr const char * GetString() const
Get the underlying string pointer.
<- This is here just for the literals
DLL std::unique_ptr< Component > ConstructComponent(uint32_t aIdentifier)
Construct a component from a numeric identifier.
DLL void EnumerateComponentConstructors(const std::function< bool(const StringId &) > &aEnumerator)
Enumerates Component loader identifiers via an enumerator functor.
@ Info
General informational messages.