move playback on resize (snapWidgets), coding style ./etc/quality.sh

master
poikilos 2019-04-11 04:31:04 -04:00
parent d2aaced734
commit a3118c12e5
18 changed files with 653 additions and 526 deletions

118
.clang-format Normal file
View File

@ -0,0 +1,118 @@
---
Language: Cpp
# BasedOnStyle: WebKit
AccessModifierOffset: -4
AlignAfterOpenBracket: DontAlign
AlignConsecutiveAssignments: false
AlignConsecutiveDeclarations: false
AlignEscapedNewlines: Right
AlignOperands: false
AlignTrailingComments: false
AllowAllParametersOfDeclarationOnNextLine: true
AllowShortBlocksOnASingleLine: false
AllowShortCaseLabelsOnASingleLine: false
AllowShortFunctionsOnASingleLine: All
AllowShortIfStatementsOnASingleLine: false
AllowShortLoopsOnASingleLine: false
AlwaysBreakAfterDefinitionReturnType: None
AlwaysBreakAfterReturnType: None
AlwaysBreakBeforeMultilineStrings: false
AlwaysBreakTemplateDeclarations: MultiLine
BinPackArguments: true
BinPackParameters: true
BraceWrapping:
AfterClass: false
AfterControlStatement: false
AfterEnum: false
AfterFunction: true
AfterNamespace: false
AfterObjCDeclaration: false
AfterStruct: false
AfterUnion: false
AfterExternBlock: false
BeforeCatch: false
BeforeElse: false
IndentBraces: false
SplitEmptyFunction: true
SplitEmptyRecord: true
SplitEmptyNamespace: true
BreakBeforeBinaryOperators: All
BreakBeforeBraces: WebKit
BreakBeforeInheritanceComma: false
BreakInheritanceList: BeforeColon
BreakBeforeTernaryOperators: true
BreakConstructorInitializersBeforeComma: false
BreakConstructorInitializers: BeforeComma
BreakAfterJavaFieldAnnotations: false
BreakStringLiterals: true
ColumnLimit: 0
CommentPragmas: '^ IWYU pragma:'
CompactNamespaces: false
ConstructorInitializerAllOnOneLineOrOnePerLine: false
ConstructorInitializerIndentWidth: 4
ContinuationIndentWidth: 4
Cpp11BracedListStyle: false
DerivePointerAlignment: false
DisableFormat: false
ExperimentalAutoDetectBinPacking: false
FixNamespaceComments: false
ForEachMacros:
- foreach
- Q_FOREACH
- BOOST_FOREACH
IncludeBlocks: Preserve
IncludeCategories:
- Regex: '^"(llvm|llvm-c|clang|clang-c)/'
Priority: 2
- Regex: '^(<|"(gtest|gmock|isl|json)/)'
Priority: 3
- Regex: '.*'
Priority: 1
IncludeIsMainRegex: '(Test)?$'
IndentCaseLabels: false
IndentPPDirectives: None
IndentWidth: 4
IndentWrappedFunctionNames: false
JavaScriptQuotes: Leave
JavaScriptWrapImports: true
KeepEmptyLinesAtTheStartOfBlocks: true
MacroBlockBegin: ''
MacroBlockEnd: ''
MaxEmptyLinesToKeep: 1
NamespaceIndentation: Inner
ObjCBinPackProtocolList: Auto
ObjCBlockIndentWidth: 4
ObjCSpaceAfterProperty: true
ObjCSpaceBeforeProtocolList: true
PenaltyBreakAssignment: 2
PenaltyBreakBeforeFirstCallParameter: 19
PenaltyBreakComment: 300
PenaltyBreakFirstLessLess: 120
PenaltyBreakString: 1000
PenaltyBreakTemplateDeclaration: 10
PenaltyExcessCharacter: 1000000
PenaltyReturnTypeOnItsOwnLine: 60
PointerAlignment: Left
ReflowComments: true
SortIncludes: true
SortUsingDeclarations: true
SpaceAfterCStyleCast: false
SpaceAfterTemplateKeyword: true
SpaceBeforeAssignmentOperators: true
SpaceBeforeCpp11BracedList: true
SpaceBeforeCtorInitializerColon: true
SpaceBeforeInheritanceColon: true
SpaceBeforeParens: ControlStatements
SpaceBeforeRangeBasedForLoopColon: true
SpaceInEmptyParentheses: false
SpacesBeforeTrailingComments: 1
SpacesInAngles: false
SpacesInContainerLiterals: true
SpacesInCStyleCastParentheses: false
SpacesInParentheses: false
SpacesInSquareBrackets: false
Standard: Cpp11
TabWidth: 8
UseTab: Never
...

3
.gitignore vendored
View File

@ -35,4 +35,7 @@ Makefile*
# QtCtreator CMake # QtCtreator CMake
CMakeLists.txt.user CMakeLists.txt.user
# dev generated files
nohup.out nohup.out
*.tmp

View File

@ -3,11 +3,11 @@
using std::cout; using std::cout;
using std::endl; using std::endl;
using std::ostream; using std::ostream;
using std::wcout;
using std::wcerr; using std::wcerr;
using std::wcout;
ostream & debug() ostream& debug()
{ {
std::flush( cout ); std::flush(cout);
return cout; return cout;
} }

View File

@ -3,6 +3,6 @@
#include <iostream> #include <iostream>
std::ostream & debug(); std::ostream& debug();
#endif // DEBUG_H #endif // DEBUG_H

View File

@ -3,12 +3,12 @@
#include "Engine.h" #include "Engine.h"
#include "UserInterface.h" #include "UserInterface.h"
#include "View.h"
#include "Utility.h" #include "Utility.h"
#include "View.h"
using std::cout; using std::cout;
using std::wcerr;
using std::endl; using std::endl;
using std::wcerr;
using std::wstring; using std::wstring;
using std::wstringstream; using std::wstringstream;
@ -26,61 +26,61 @@ void Engine::setupScene()
{ {
// Setup Light // Setup Light
m_SceneLight = m_Scene->addLightSceneNode(); m_SceneLight = m_Scene->addLightSceneNode();
m_SceneLight->setID( SIID_LIGHT ); m_SceneLight->setID(SIID_LIGHT);
m_SceneLight->setLightType( ELT_DIRECTIONAL ); m_SceneLight->setLightType(ELT_DIRECTIONAL);
m_SceneLight->getLightData().AmbientColor = SColorf( 0.2f, 0.2f, 0.2f ); m_SceneLight->getLightData().AmbientColor = SColorf(0.2f, 0.2f, 0.2f);
m_SceneLight->getLightData().DiffuseColor = SColorf( 0.8f, 0.8f, 0.8f ); m_SceneLight->getLightData().DiffuseColor = SColorf(0.8f, 0.8f, 0.8f);
m_Scene->setAmbientLight( SColorf( 0.2f, 0.2f, 0.2f )); m_Scene->setAmbientLight(SColorf(0.2f, 0.2f, 0.2f));
// Setup Camera // Setup Camera
// (so z-forward characters face camera partially (formerly vector3df( 0, 0, -10 ), vector3df()) // (so z-forward characters face camera partially (formerly vector3df(0, 0, -10), vector3df())
m_CamPos = vector3df( 4.5, 3, 9 ); m_CamPos = vector3df(4.5, 3, 9);
m_CamTarget = vector3df(0, 3, 0); m_CamTarget = vector3df(0, 3, 0);
ICameraSceneNode *camera = m_Scene->addCameraSceneNode(nullptr, m_CamPos, m_CamTarget); // this will be overridden by View m_Yaw and m_Pitch--see "calculate m_Yaw" further down ICameraSceneNode* camera = m_Scene->addCameraSceneNode(nullptr, m_CamPos, m_CamTarget); // this will be overridden by View m_Yaw and m_Pitch--see "calculate m_Yaw" further down
camera->setAspectRatio(static_cast<f32>(m_Driver->getScreenSize().Width) / static_cast<f32>(m_Driver->getScreenSize().Height)); camera->setAspectRatio(static_cast<f32>(m_Driver->getScreenSize().Width) / static_cast<f32>(m_Driver->getScreenSize().Height));
} }
IGUIEnvironment * Engine::getGUIEnvironment() const IGUIEnvironment* Engine::getGUIEnvironment() const
{ {
return m_Device->getGUIEnvironment(); return m_Device->getGUIEnvironment();
} }
void Engine::drawAxisLines() void Engine::drawAxisLines()
{ {
SMaterial *lineX = new SMaterial(); SMaterial* lineX = new SMaterial();
lineX->Lighting = false; lineX->Lighting = false;
lineX->EmissiveColor = SColor( 255, 255, 0, 0 ); lineX->EmissiveColor = SColor(255, 255, 0, 0);
lineX->Thickness = 1.0f; lineX->Thickness = 1.0f;
SMaterial *lineY = new SMaterial( *lineX ); SMaterial* lineY = new SMaterial(*lineX);
lineY->EmissiveColor = SColor( 255, 0, 255, 0 ); lineY->EmissiveColor = SColor(255, 0, 255, 0);
SMaterial *lineZ = new SMaterial( *lineX ); SMaterial* lineZ = new SMaterial(*lineX);
lineZ->EmissiveColor = SColor( 255, 0, 0, 255 ); lineZ->EmissiveColor = SColor(255, 0, 0, 255);
m_Driver->setTransform( ETS_WORLD, matrix4() ); m_Driver->setTransform(ETS_WORLD, matrix4());
m_Driver->setMaterial( *lineX ); m_Driver->setMaterial(*lineX);
m_Driver->draw3DLine( vector3df(), vector3df( 5, 0, 0 ), SColor( 255, 255, 0, 0 )); m_Driver->draw3DLine(vector3df(), vector3df(5, 0, 0), SColor(255, 255, 0, 0));
position2d<s32> textPos = m_Scene->getSceneCollisionManager()->getScreenCoordinatesFrom3DPosition( vector3df( 5.2f, 0, 0 )); position2d<s32> textPos = m_Scene->getSceneCollisionManager()->getScreenCoordinatesFrom3DPosition(vector3df(5.2f, 0, 0));
dimension2d<u32> textSize; dimension2d<u32> textSize;
if (m_AxisFont != nullptr) { if (m_AxisFont != nullptr) {
textSize = m_AxisFont->getDimension( L"X+" ); textSize = m_AxisFont->getDimension(L"X+");
m_AxisFont->draw( L"X+", rect<s32>( textPos, textSize ), SColor( 255, 255, 0, 0 ), true, true ); m_AxisFont->draw(L"X+", rect<s32>(textPos, textSize), SColor(255, 255, 0, 0), true, true);
} }
m_Driver->setMaterial( *lineY ); m_Driver->setMaterial(*lineY);
m_Driver->draw3DLine( vector3df(), vector3df( 0, 5, 0 ), SColor( 255, 0, 255, 0 )); m_Driver->draw3DLine(vector3df(), vector3df(0, 5, 0), SColor(255, 0, 255, 0));
textPos = m_Scene->getSceneCollisionManager()->getScreenCoordinatesFrom3DPosition( vector3df( 0, 5.2f, 0 )); textPos = m_Scene->getSceneCollisionManager()->getScreenCoordinatesFrom3DPosition(vector3df(0, 5.2f, 0));
if (m_AxisFont != nullptr) { if (m_AxisFont != nullptr) {
textSize = m_AxisFont->getDimension( L"Y+" ); textSize = m_AxisFont->getDimension(L"Y+");
m_AxisFont->draw( L"Y+", rect<s32>( textPos, textSize ), SColor( 255, 0, 255, 0 ), true, true ); m_AxisFont->draw(L"Y+", rect<s32>(textPos, textSize), SColor(255, 0, 255, 0), true, true);
} }
m_Driver->setMaterial( *lineZ ); m_Driver->setMaterial(*lineZ);
m_Driver->draw3DLine( vector3df(), vector3df( 0, 0, 5 ), SColor( 255, 0, 0, 255 )); m_Driver->draw3DLine(vector3df(), vector3df(0, 0, 5), SColor(255, 0, 0, 255));
textPos = m_Scene->getSceneCollisionManager()->getScreenCoordinatesFrom3DPosition( vector3df( 0, 0, 5.2f )); textPos = m_Scene->getSceneCollisionManager()->getScreenCoordinatesFrom3DPosition(vector3df(0, 0, 5.2f));
if (m_AxisFont != nullptr) { if (m_AxisFont != nullptr) {
textSize = m_AxisFont->getDimension( L"Z+" ); textSize = m_AxisFont->getDimension(L"Z+");
m_AxisFont->draw( L"Z+", rect<s32>( textPos, textSize ), SColor( 255, 0, 0, 255 ), true, true ); m_AxisFont->draw(L"Z+", rect<s32>(textPos, textSize), SColor(255, 0, 0, 255), true, true);
} }
delete lineX; delete lineX;
delete lineY; delete lineY;
@ -90,38 +90,37 @@ void Engine::drawAxisLines()
void Engine::drawBackground() void Engine::drawBackground()
{ {
dimension2d<u32> screenSize = m_Driver->getScreenSize(); dimension2d<u32> screenSize = m_Driver->getScreenSize();
m_Driver->draw2DRectangle( rect<s32>( 0, 0, static_cast<s32>(screenSize.Width), static_cast<s32>(screenSize.Height) ), m_Driver->draw2DRectangle(rect<s32>(0, 0, static_cast<s32>(screenSize.Width), static_cast<s32>(screenSize.Height)),
SColor( 255, 128, 128, 255 ), SColor(255, 128, 128, 255),
SColor( 255, 128, 128, 255 ), SColor(255, 128, 128, 255),
SColor( 255, 224, 224, 255 ), SColor(255, 224, 224, 255),
SColor( 255, 224, 224, 255 )); SColor(255, 224, 224, 255));
} }
void Engine::checkResize() void Engine::checkResize()
{ {
if(( m_WindowSize->Width != m_Driver->getScreenSize().Width ) || ( m_WindowSize->Height != m_Driver->getScreenSize().Height )) if ((m_WindowSize.Width != m_Driver->getScreenSize().Width) || (m_WindowSize.Height != m_Driver->getScreenSize().Height)) {
{ m_WindowSize.Width = m_Driver->getScreenSize().Width;
m_WindowSize->Width = m_Driver->getScreenSize().Width; m_WindowSize.Height = m_Driver->getScreenSize().Height;
m_WindowSize->Height = m_Driver->getScreenSize().Height;
// Send custom event // Send custom event
IEventReceiver *eventReceiver = m_Device->getEventReceiver(); IEventReceiver* eventReceiver = m_Device->getEventReceiver();
SEvent event; SEvent event;
event.EventType = EET_USER_EVENT; event.EventType = EET_USER_EVENT;
event.UserEvent.UserData1 = UEI_WINDOWSIZECHANGED; event.UserEvent.UserData1 = UEI_WINDOWSIZECHANGED;
eventReceiver->OnEvent( event ); eventReceiver->OnEvent(event);
//m_UserInterface-> //m_UserInterface->
} }
} }
s32 Engine::getNumberOfVertices() s32 Engine::getNumberOfVertices()
{ {
IMesh *mesh = m_LoadedMesh->getMesh()->getMesh( 0, 255, -1, -1 ); IMesh* mesh = m_LoadedMesh->getMesh()->getMesh(0, 255, -1, -1);
int vertices = 0; int vertices = 0;
for( irr::u32 bufferIndex = 0; bufferIndex < mesh->getMeshBufferCount(); bufferIndex ++ ) for (irr::u32 bufferIndex = 0; bufferIndex < mesh->getMeshBufferCount(); bufferIndex++)
vertices += mesh->getMeshBuffer( bufferIndex )->getVertexCount(); vertices += mesh->getMeshBuffer(bufferIndex)->getVertexCount();
cout << vertices << endl; cout << vertices << endl;
@ -136,9 +135,9 @@ Engine::Engine()
{ {
// For monitoring single press: see // For monitoring single press: see
// <http://irrlicht.sourceforge.net/forum/viewtopic.php?p=210744> // <http://irrlicht.sourceforge.net/forum/viewtopic.php?p=210744>
for (u32 i=0; i<KEY_KEY_CODES_COUNT; ++i) for (u32 i = 0; i < KEY_KEY_CODES_COUNT; ++i)
KeyIsDown[i] = false; KeyIsDown[i] = false;
for (u32 i=0; i<KEY_KEY_CODES_COUNT; ++i) for (u32 i = 0; i < KEY_KEY_CODES_COUNT; ++i)
keyState[i] = 0; keyState[i] = 0;
LMouseState = 0; LMouseState = 0;
RMouseState = 0; RMouseState = 0;
@ -149,41 +148,40 @@ Engine::Engine()
this->textureExtensions.push_back(L"jpg"); this->textureExtensions.push_back(L"jpg");
this->textureExtensions.push_back(L"bmp"); this->textureExtensions.push_back(L"bmp");
#if WIN32 #if WIN32
m_Device = createDevice( EDT_DIRECT3D9, dimension2d<u32>( 1024, 768 ), 32, false, false, false, nullptr ); m_Device = createDevice(EDT_DIRECT3D9, dimension2d<u32>(1024, 768), 32, false, false, false, nullptr);
#else #else
m_Device = createDevice( EDT_OPENGL, dimension2d<u32>( 1024, 768 ), 32, false, false, false, nullptr ); m_Device = createDevice(EDT_OPENGL, dimension2d<u32>(1024, 768), 32, false, false, false, nullptr);
#endif #endif
m_Device->setResizable( true ); m_Device->setResizable(true);
m_EventHandler = new EventHandler( m_Device ); m_EventHandler = new EventHandler(m_Device);
m_Device->setEventReceiver( m_EventHandler ); m_Device->setEventReceiver(m_EventHandler);
m_Driver = m_Device->getVideoDriver(); m_Driver = m_Device->getVideoDriver();
m_Scene = m_Device->getSceneManager(); m_Scene = m_Device->getSceneManager();
wstringstream windowTitle; wstringstream windowTitle;
windowTitle << L"b3view (Blitz3D/Irrlicht Viewer) [" << m_Driver->getName() << L"]"; windowTitle << L"b3view (Blitz3D/Irrlicht Viewer) [" << m_Driver->getName() << L"]";
m_Device->setWindowCaption( windowTitle.str().c_str() ); m_Device->setWindowCaption(windowTitle.str().c_str());
setupScene(); setupScene();
// Setup User Interface // Setup User Interface
m_UserInterface = new UserInterface( this ); m_UserInterface = new UserInterface(this);
m_EventHandler->addEventReceiver( ERT_USERINTERFACE, m_UserInterface ); m_EventHandler->addEventReceiver(ERT_USERINTERFACE, m_UserInterface);
// Setup 3D View // Setup 3D View
m_View = new View( this ); m_View = new View(this);
m_EventHandler->addEventReceiver( ERT_3DVIEW, m_View ); m_EventHandler->addEventReceiver(ERT_3DVIEW, m_View);
// Load font for displaying Axis names // Load font for displaying Axis names
m_AxisFontFace = new CGUITTFace(); m_AxisFontFace = new CGUITTFace();
// NOTE: m_FontPath is modified y UserInterface constructor above if font was missing // NOTE: m_FontPath is modified y UserInterface constructor above if font was missing
if (m_AxisFontFace->load(m_FontPath.c_str())) { if (m_AxisFontFace->load(m_FontPath.c_str())) {
m_AxisFont = new CGUITTFont( m_UserInterface->getGUIEnvironment() ); m_AxisFont = new CGUITTFont(m_UserInterface->getGUIEnvironment());
m_AxisFont->attach( m_AxisFontFace, 14 ); m_AxisFont->attach(m_AxisFontFace, 14);
m_AxisFont->AntiAlias = false; m_AxisFont->AntiAlias = false;
} } else {
else {
delete m_AxisFontFace; delete m_AxisFontFace;
m_AxisFontFace = nullptr; m_AxisFontFace = nullptr;
} }
@ -192,9 +190,8 @@ Engine::Engine()
m_LoadedMesh = nullptr; m_LoadedMesh = nullptr;
// Store actual window size // Store actual window size
m_WindowSize = new dimension2d<u32>(); m_WindowSize.Width = m_Driver->getScreenSize().Width;
m_WindowSize->Width = m_Driver->getScreenSize().Width; m_WindowSize.Height = m_Driver->getScreenSize().Height;
m_WindowSize->Height = m_Driver->getScreenSize().Height;
// (do not calculate m_Yaw and m_Pitch here--see View constructor) // (do not calculate m_Yaw and m_Pitch here--see View constructor)
@ -204,37 +201,35 @@ Engine::Engine()
Engine::~Engine() Engine::~Engine()
{ {
m_Device->drop(); m_Device->drop();
delete m_WindowSize;
delete m_AxisFont; delete m_AxisFont;
delete m_AxisFontFace; delete m_AxisFontFace;
} }
void Engine::loadMesh( const wstring &fileName ) void Engine::loadMesh(const wstring& fileName)
{ {
this->m_PreviousPath = fileName; // even if bad, set this this->m_PreviousPath = fileName; // even if bad, set this
// to allow F5 to reload // to allow F5 to reload
if( m_LoadedMesh != nullptr ) if (m_LoadedMesh != nullptr)
m_LoadedMesh->remove(); m_LoadedMesh->remove();
irr::scene::IAnimatedMesh* mesh = m_Scene->getMesh( fileName.c_str()); irr::scene::IAnimatedMesh* mesh = m_Scene->getMesh(fileName.c_str());
if (mesh != nullptr) { if (mesh != nullptr) {
m_LoadedMesh = m_Scene->addAnimatedMeshSceneNode( mesh ); m_LoadedMesh = m_Scene->addAnimatedMeshSceneNode(mesh);
Utility::dumpMeshInfoToConsole( m_LoadedMesh ); Utility::dumpMeshInfoToConsole(m_LoadedMesh);
if (Utility::toLower(Utility::extensionOf(fileName)) == L"3ds") { if (Utility::toLower(Utility::extensionOf(fileName)) == L"3ds") {
m_View->setZUp(true); m_View->setZUp(true);
} } else {
else {
m_View->setZUp(false); m_View->setZUp(false);
} }
if (m_LoadedMesh != nullptr) { if (m_LoadedMesh != nullptr) {
ICameraSceneNode *camera = this->m_Scene->getActiveCamera(); ICameraSceneNode* camera = this->m_Scene->getActiveCamera();
aabbox3d<f32> box = m_LoadedMesh->getTransformedBoundingBox(); aabbox3d<f32> box = m_LoadedMesh->getTransformedBoundingBox();
//vector3d<float> extents = box.getExtent(); //vector3d<float> extents = box.getExtent();
if (m_View->zUp()) { if (m_View->zUp()) {
float oldDist = m_CamPos.getDistanceFrom(m_CamTarget); float oldDist = m_CamPos.getDistanceFrom(m_CamTarget);
float newDist = oldDist; float newDist = oldDist;
if (oldDist != 0) { if (Utility::equalsApprox(oldDist, 0.0f)) {
vector3d<float> center = box.getCenter(); vector3d<float> center = box.getCenter();
vector3df edges[8]; vector3df edges[8];
box.getEdges(edges); box.getEdges(edges);
@ -249,13 +244,14 @@ void Engine::loadMesh( const wstring &fileName )
0---------4/ 0---------4/
*/ */
newDist = 0; newDist = 0;
for (int i=0; i<8; i++) { for (int i = 0; i < 8; i++) {
float tryDist = center.getDistanceFrom(edges[i]); float tryDist = center.getDistanceFrom(edges[i]);
if (tryDist>newDist) newDist = tryDist; if (tryDist > newDist)
newDist = tryDist;
} }
newDist *= 2; // so camera doesn't touch model newDist *= 2; // so camera doesn't touch model
if (!Utility::equalsApprox<float>(newDist, oldDist)) { if (!Utility::equalsApprox<float>(newDist, oldDist)) {
float scale = newDist / oldDist; // already checked 0 float scale = newDist / oldDist; // already checked 0
vector3df oldCamPos = camera->getPosition(); vector3df oldCamPos = camera->getPosition();
m_CamPos = oldCamPos; m_CamPos = oldCamPos;
m_CamPos.X = m_CamPos.X * scale; m_CamPos.X = m_CamPos.X * scale;
@ -290,7 +286,7 @@ void Engine::reloadTexture()
} }
} }
bool Engine::loadTexture(const wstring &fileName) bool Engine::loadTexture(const wstring& fileName)
{ {
ITexture* texture = this->m_Driver->getTexture(fileName.c_str()); ITexture* texture = this->m_Driver->getTexture(fileName.c_str());
bool ret = false; bool ret = false;
@ -303,32 +299,27 @@ bool Engine::loadTexture(const wstring &fileName)
return ret; return ret;
} }
void Engine::setMeshDisplayMode( bool wireframe, bool lighting, bool textureInterpolation) void Engine::setMeshDisplayMode(bool wireframe, bool lighting, bool textureInterpolation)
{ {
if (m_LoadedMesh != nullptr) { if (m_LoadedMesh != nullptr) {
for( u32 materialIndex = 0; materialIndex < m_LoadedMesh->getMaterialCount(); materialIndex ++ ) for (u32 materialIndex = 0; materialIndex < m_LoadedMesh->getMaterialCount(); materialIndex++) {
{
// Set Wireframe display // Set Wireframe display
m_LoadedMesh->getMaterial(materialIndex).Wireframe = wireframe; m_LoadedMesh->getMaterial(materialIndex).Wireframe = wireframe;
// Set Lighting // Set Lighting
if( ! lighting ) if (!lighting) {
{
m_LoadedMesh->getMaterial(materialIndex).Lighting = false; m_LoadedMesh->getMaterial(materialIndex).Lighting = false;
m_LoadedMesh->getMaterial(materialIndex).EmissiveColor = SColor( 255, 255, 255, 255 ); m_LoadedMesh->getMaterial(materialIndex).EmissiveColor = SColor(255, 255, 255, 255);
} } else {
else
{
m_LoadedMesh->getMaterial(materialIndex).Lighting = true; m_LoadedMesh->getMaterial(materialIndex).Lighting = true;
m_LoadedMesh->getMaterial(materialIndex).EmissiveColor = SColor( 255, 0, 0, 0 ); m_LoadedMesh->getMaterial(materialIndex).EmissiveColor = SColor(255, 0, 0, 0);
} }
// m_LoadedMesh->setMaterialType(video::EMT_TRANSPARENT_ALPHA_CHANNEL); //already done on load // m_LoadedMesh->setMaterialType(video::EMT_TRANSPARENT_ALPHA_CHANNEL); //already done on load
// m_LoadedMesh->setMaterialFlag(video::E_ALPHA_SOURCE, true); // requires EMT_ONETEXTURE // m_LoadedMesh->setMaterialFlag(video::E_ALPHA_SOURCE, true); // requires EMT_ONETEXTURE
if (textureInterpolation) { if (textureInterpolation) {
m_LoadedMesh->setMaterialFlag(video::EMF_BILINEAR_FILTER, true); m_LoadedMesh->setMaterialFlag(video::EMF_BILINEAR_FILTER, true);
m_LoadedMesh->setMaterialFlag(video::EMF_TRILINEAR_FILTER, true); m_LoadedMesh->setMaterialFlag(video::EMF_TRILINEAR_FILTER, true);
} } else {
else {
m_LoadedMesh->setMaterialFlag(video::EMF_BILINEAR_FILTER, false); m_LoadedMesh->setMaterialFlag(video::EMF_BILINEAR_FILTER, false);
m_LoadedMesh->setMaterialFlag(video::EMF_TRILINEAR_FILTER, false); m_LoadedMesh->setMaterialFlag(video::EMF_TRILINEAR_FILTER, false);
//m_LoadedMesh->setMaterialFlag(video::E_ALPHA_SOURCE, true); //m_LoadedMesh->setMaterialFlag(video::E_ALPHA_SOURCE, true);
@ -341,11 +332,11 @@ void Engine::setMeshDisplayMode( bool wireframe, bool lighting, bool textureInte
// below would require patching Irrlicht: // below would require patching Irrlicht:
// GLint filteringMipMaps = GL_NEAREST_MIPMAP_NEAREST // GLint filteringMipMaps = GL_NEAREST_MIPMAP_NEAREST
// // above is used by glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, filteringMipMaps); // // above is used by glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, filteringMipMaps);
} }
} }
} } else
else debug() << "WARNING in setMeshDisplayMode: No mesh is loaded " << endl; debug() << "WARNING in setMeshDisplayMode: No mesh is loaded " << endl;
} }
bool Engine::isAnimating() bool Engine::isAnimating()
@ -360,7 +351,8 @@ void Engine::playAnimation()
} }
if (!this->isAnimating()) { if (!this->isAnimating()) {
if (this->m_LoadedMesh != nullptr) { if (this->m_LoadedMesh != nullptr) {
if (this->prevFPS < 1) this->prevFPS = 5; if (this->prevFPS < 1)
this->prevFPS = 5;
this->m_LoadedMesh->setAnimationSpeed(this->prevFPS); this->m_LoadedMesh->setAnimationSpeed(this->prevFPS);
} }
} }
@ -384,12 +376,10 @@ void Engine::toggleAnimation()
if (this->isAnimating()) { if (this->isAnimating()) {
this->pauseAnimation(); this->pauseAnimation();
debug() << "paused " << this->animationFPS() << "fps" << endl; debug() << "paused " << this->animationFPS() << "fps" << endl;
} } else {
else {
this->playAnimation(); this->playAnimation();
debug() << "unpaused " << this->animationFPS() << "fps" << endl; debug() << "unpaused " << this->animationFPS() << "fps" << endl;
} }
} }
void Engine::setAnimationFPS(u32 animationFPS) void Engine::setAnimationFPS(u32 animationFPS)
@ -419,13 +409,12 @@ void Engine::run()
{ {
u32 timePerFrame = 1000.0f; u32 timePerFrame = 1000.0f;
if (this->worldFPS > 0) { if (this->worldFPS > 0) {
timePerFrame = static_cast<u32>( 1000.0f / this->worldFPS ); timePerFrame = static_cast<u32>(1000.0f / this->worldFPS);
} }
ITimer *timer = m_Device->getTimer(); ITimer* timer = m_Device->getTimer();
// Run the Device with fps frames/sec // Run the Device with fps frames/sec
while( m_Device->run() && m_RunEngine ) while (m_Device->run() && m_RunEngine) {
{
u32 startTime = timer->getRealTime(); u32 startTime = timer->getRealTime();
checkResize(); checkResize();
@ -433,23 +422,22 @@ void Engine::run()
if (isPlaying) { if (isPlaying) {
this->m_LoadedMesh->setLoopMode(true); this->m_LoadedMesh->setLoopMode(true);
this->m_UserInterface->playbackSetFrameEditBox->setText(Utility::toWstring(this->m_LoadedMesh->getFrameNr()).c_str()); this->m_UserInterface->playbackSetFrameEditBox->setText(Utility::toWstring(this->m_LoadedMesh->getFrameNr()).c_str());
} } else {
else {
this->m_LoadedMesh->setLoopMode(false); this->m_LoadedMesh->setLoopMode(false);
} }
} }
m_Driver->beginScene(); m_Driver->beginScene();
drawBackground(); // Draw Background drawBackground(); // Draw Background
drawAxisLines(); // Draw XYZ Axis drawAxisLines(); // Draw XYZ Axis
m_Scene->drawAll(); // Draw Scenegraph m_Scene->drawAll(); // Draw Scenegraph
m_UserInterface->getGUIEnvironment()->drawAll(); m_UserInterface->getGUIEnvironment()->drawAll();
m_UserInterface->drawStatusLine(); m_UserInterface->drawStatusLine();
m_Driver->endScene(); m_Driver->endScene();
u32 sleepTime = timePerFrame - ( timer->getRealTime() - startTime ); u32 sleepTime = timePerFrame - (timer->getRealTime() - startTime);
if( sleepTime > 0 && sleepTime < timePerFrame ) if (sleepTime > 0 && sleepTime < timePerFrame)
m_Device->sleep( sleepTime, false ); m_Device->sleep(sleepTime, false);
} }
} }

View File

@ -5,81 +5,78 @@
class UserInterface; class UserInterface;
class View; class View;
#include <string>
#include <sstream>
#include <iostream> #include <iostream>
#include <sstream>
#include <string>
#include <vector> #include <vector>
#include <irrlicht/irrlicht.h>
#include "EventHandler.h" #include "EventHandler.h"
#include "extlib/CGUITTFont.h" #include "extlib/CGUITTFont.h"
#include <irrlicht/irrlicht.h>
enum SceneItemID enum SceneItemID {
{ SIID_LIGHT = 1,
SIID_LIGHT = 1, SIID_CAMERA = 2,
SIID_CAMERA = 2, SIID_MODEL = 3
SIID_MODEL = 3
}; };
class Engine class Engine {
{
friend class UserInterface; friend class UserInterface;
friend class View; friend class View;
private: private:
std::wstring m_NextPath; std::wstring m_NextPath;
irr::IrrlichtDevice *m_Device; irr::IrrlichtDevice* m_Device;
irr::video::IVideoDriver *m_Driver; irr::video::IVideoDriver* m_Driver;
irr::scene::ISceneManager *m_Scene; irr::scene::ISceneManager* m_Scene;
irr::scene::IAnimatedMeshSceneNode *m_LoadedMesh; irr::scene::IAnimatedMeshSceneNode* m_LoadedMesh;
irr::scene::ILightSceneNode *m_SceneLight; irr::scene::ILightSceneNode* m_SceneLight;
irr::gui::CGUITTFont *m_AxisFont; irr::gui::CGUITTFont* m_AxisFont;
irr::gui::CGUITTFace *m_AxisFontFace; irr::gui::CGUITTFace* m_AxisFontFace;
irr::core::dimension2d<irr::u32> *m_WindowSize; irr::core::dimension2d<irr::u32> m_WindowSize;
bool m_RunEngine; bool m_RunEngine;
EventHandler *m_EventHandler; EventHandler* m_EventHandler;
UserInterface *m_UserInterface; UserInterface* m_UserInterface;
View *m_View; View* m_View;
void setupScene(); void setupScene();
void drawAxisLines(); void drawAxisLines();
void drawBackground(); void drawBackground();
void checkResize(); void checkResize();
irr::gui::IGUIEnvironment *getGUIEnvironment() const; irr::gui::IGUIEnvironment* getGUIEnvironment() const;
irr::s32 getNumberOfVertices(); irr::s32 getNumberOfVertices();
bool isPlaying; bool isPlaying;
irr::u32 worldFPS; irr::u32 worldFPS;
irr::u32 prevFPS; irr::u32 prevFPS;
std::vector<std::wstring> textureExtensions; std::vector<std::wstring> textureExtensions;
// Making materials in contructor or setupScene causes segfault at // Making materials in contructor or setupScene causes segfault at
// `m_Driver->setMaterial( *lineX );` in // `m_Driver->setMaterial(*lineX);` in
// `Engine::drawAxisLines` for unknown reason: // `Engine::drawAxisLines` for unknown reason:
// irr::video::SMaterial *lineX; // irr::video::SMaterial *lineX;
// irr::video::SMaterial *lineY; // irr::video::SMaterial *lineY;
// irr::video::SMaterial *lineZ; // irr::video::SMaterial *lineZ;
irr::core::vector3df m_CamPos; irr::core::vector3df m_CamPos;
irr::core::vector3df m_CamTarget; irr::core::vector3df m_CamTarget;
std::wstring m_FontPath = L"ClearSansRegular.ttf"; // core::stringc has implicit conversion to io::path std::wstring m_FontPath = L"ClearSansRegular.ttf"; // core::stringc has implicit conversion to io::path
bool KeyIsDown[irr::KEY_KEY_CODES_COUNT]; bool KeyIsDown[irr::KEY_KEY_CODES_COUNT];
irr::s32 keyState[irr::KEY_KEY_CODES_COUNT]; irr::s32 keyState[irr::KEY_KEY_CODES_COUNT];
irr::s32 LMouseState,RMouseState; irr::s32 LMouseState, RMouseState;
public: public:
std::wstring m_PreviousPath; std::wstring m_PreviousPath;
std::wstring m_PrevTexturePath; std::wstring m_PrevTexturePath;
Engine(); Engine();
~Engine(); ~Engine();
void run(); void run();
void loadMesh( const std::wstring &fileName ); void loadMesh(const std::wstring& fileName);
void reloadMesh(); void reloadMesh();
void reloadTexture(); void reloadTexture();
bool loadTexture( const std::wstring &fileName ); bool loadTexture(const std::wstring& fileName);
void setMeshDisplayMode(bool wireframe = false, bool lighting = true, bool textureInterpolation = true); void setMeshDisplayMode(bool wireframe = false, bool lighting = true, bool textureInterpolation = true);
bool isAnimating(); bool isAnimating();
void playAnimation(); void playAnimation();

View File

@ -1,18 +1,18 @@
#include "EventHandler.h" #include "EventHandler.h"
#include <sys/types.h>
#include <sys/stat.h>
#include <string.h>
#include <Utility.h> #include <Utility.h>
#include <string.h>
#include <sys/stat.h>
#include <sys/types.h>
using namespace irr; using namespace irr;
using namespace irr::video; using namespace irr::video;
using namespace irr::gui; using namespace irr::gui;
// Public // Public
EventHandler::EventHandler( IrrlichtDevice *device ) EventHandler::EventHandler(IrrlichtDevice* device)
{ {
m_Device = device; m_Device = device;
m_EventReceivers = new map<EventReceiverType, IEventReceiver *>(); m_EventReceivers = new map<EventReceiverType, IEventReceiver*>();
} }
EventHandler::~EventHandler() EventHandler::~EventHandler()
@ -20,37 +20,31 @@ EventHandler::~EventHandler()
delete m_EventReceivers; delete m_EventReceivers;
} }
bool EventHandler::addEventReceiver( EventReceiverType type, IEventReceiver *receiver ) bool EventHandler::addEventReceiver(EventReceiverType type, IEventReceiver* receiver)
{ {
m_EventReceivers->insert( make_pair( type, receiver )); m_EventReceivers->insert(make_pair(type, receiver));
return true; return true;
} }
// IEventReceiver // IEventReceiver
bool EventHandler::OnEvent( const SEvent &event ) bool EventHandler::OnEvent(const SEvent& event)
{ {
if (event.EventType == EET_GUI_EVENT) if (event.EventType == EET_GUI_EVENT) {
{
// Pass to User Interface Handler // Pass to User Interface Handler
map<EventReceiverType,IEventReceiver *>::iterator iter = m_EventReceivers->find( ERT_USERINTERFACE ); map<EventReceiverType, IEventReceiver*>::iterator iter = m_EventReceivers->find(ERT_USERINTERFACE);
iter->second->OnEvent( event ); iter->second->OnEvent(event);
} } else if (event.EventType == EET_MOUSE_INPUT_EVENT) {
else if (event.EventType == EET_MOUSE_INPUT_EVENT) map<EventReceiverType, IEventReceiver*>::iterator iter = m_EventReceivers->find(ERT_3DVIEW);
{ iter->second->OnEvent(event);
map<EventReceiverType,IEventReceiver *>::iterator iter = m_EventReceivers->find( ERT_3DVIEW ); } else if (event.EventType == EET_KEY_INPUT_EVENT) {
iter->second->OnEvent( event ); map<EventReceiverType, IEventReceiver*>::iterator iter = m_EventReceivers->find(ERT_USERINTERFACE);
} iter->second->OnEvent(event);
else if (event.EventType == EET_KEY_INPUT_EVENT) { } else if (event.EventType == EET_USER_EVENT) {
map<EventReceiverType,IEventReceiver *>::iterator iter = m_EventReceivers->find( ERT_USERINTERFACE );
iter->second->OnEvent( event );
}
else if (event.EventType == EET_USER_EVENT)
{
if (event.UserEvent.UserData1 == UEI_WINDOWSIZECHANGED) { if (event.UserEvent.UserData1 == UEI_WINDOWSIZECHANGED) {
// Window resize handling - send to all subscribers // Window resize handling - send to all subscribers
map<EventReceiverType,IEventReceiver *>::iterator iter; map<EventReceiverType, IEventReceiver*>::iterator iter;
for( iter = m_EventReceivers->begin(); iter != m_EventReceivers->end(); iter ++ ) for (iter = m_EventReceivers->begin(); iter != m_EventReceivers->end(); iter++)
iter->second->OnEvent( event ); iter->second->OnEvent(event);
} }
} }

View File

@ -5,38 +5,36 @@
#include <map> #include <map>
#include <utility> #include <utility>
#include <irrlicht/irrlicht.h>
#include "Debug.h" #include "Debug.h"
#include <irrlicht/irrlicht.h>
using std::cout; using std::cout;
using std::endl; using std::endl;
using std::map;
using std::make_pair; using std::make_pair;
using std::map;
enum EventReceiverType enum EventReceiverType {
{
ERT_USERINTERFACE = 1, ERT_USERINTERFACE = 1,
ERT_3DVIEW = 2 ERT_3DVIEW = 2
}; };
enum UserEventIdentifier enum UserEventIdentifier {
{
UEI_WINDOWSIZECHANGED = 1 UEI_WINDOWSIZECHANGED = 1
}; };
class EventHandler : public irr::IEventReceiver class EventHandler : public irr::IEventReceiver {
{
private: private:
irr::IrrlichtDevice *m_Device; irr::IrrlichtDevice* m_Device;
map<EventReceiverType, IEventReceiver*> *m_EventReceivers; map<EventReceiverType, IEventReceiver*>* m_EventReceivers;
public: public:
EventHandler( irr::IrrlichtDevice *device ); EventHandler(irr::IrrlichtDevice* device);
~EventHandler(); ~EventHandler();
bool addEventReceiver(EventReceiverType type, irr::IEventReceiver *receiver ); bool addEventReceiver(EventReceiverType type, irr::IEventReceiver* receiver);
// IEventReceiver // IEventReceiver
virtual bool OnEvent( const irr::SEvent &event ); virtual bool OnEvent(const irr::SEvent& event);
}; };
#endif // EVENTHANDLER_H #endif // EVENTHANDLER_H

View File

@ -1,12 +1,12 @@
#include "UserInterface.h" #include "UserInterface.h"
#include <string>
#include <iostream>
#include <algorithm> #include <algorithm>
#include <iostream>
#include <string>
// NOTE: to use filesystem, you must also include the fs library such // NOTE: to use filesystem, you must also include the fs library such
// as via the `-lstdc++fs` linker option -- see b3view.pro // as via the `-lstdc++fs` linker option -- see b3view.pro
// #include <filesystem> // requires C++17 // #include <filesystem> // requires C++17
#include <experimental/filesystem> // requires C++14 such as gcc 8.2.1 #include <experimental/filesystem> // requires C++14 such as gcc 8.2.1
#include "Debug.h" #include "Debug.h"
#include "Engine.h" #include "Engine.h"
@ -30,87 +30,81 @@ void UserInterface::setupUserInterface()
{ {
// Menu // Menu
menu = m_Gui->addMenu(); menu = m_Gui->addMenu();
menu->addItem( L"File", UIE_FILEMENU, true, true ); menu->addItem(L"File", UIE_FILEMENU, true, true);
menu->addItem( L"View", UIE_VIEWMENU, true, true ); menu->addItem(L"View", UIE_VIEWMENU, true, true);
// File Menu // File Menu
fileMenu = menu->getSubMenu( 0 ); fileMenu = menu->getSubMenu(0);
fileMenu->addItem( L"Load", UIC_FILE_LOAD ); fileMenu->addItem(L"Load", UIC_FILE_LOAD);
fileMenu->addItem( L"LoadTexture", UIC_FILE_LOAD_TEXTURE ); fileMenu->addItem(L"LoadTexture", UIC_FILE_LOAD_TEXTURE);
fileMenu->addItem( L"Quit", UIC_FILE_QUIT ); fileMenu->addItem(L"Quit", UIC_FILE_QUIT);
// View Menu // View Menu
viewMenu = menu->getSubMenu( 1 ); viewMenu = menu->getSubMenu(1);
INDEX_VIEW_WIREFRAME_MESH = viewMenu->addItem(L"Wireframe Mesh", UIC_VIEW_WIREFRAME, true, false, this->m_WireframeDisplay, true); INDEX_VIEW_WIREFRAME_MESH = viewMenu->addItem(L"Wireframe Mesh", UIC_VIEW_WIREFRAME, true, false, this->m_WireframeDisplay, true);
INDEX_VIEW_LIGHTING = viewMenu->addItem(L"Lighting", UIC_VIEW_LIGHTING, true, false, this->m_Lighting, true ); INDEX_VIEW_LIGHTING = viewMenu->addItem(L"Lighting", UIC_VIEW_LIGHTING, true, false, this->m_Lighting, true);
INDEX_VIEW_TEXTURE_INTERPOLATION = viewMenu->addItem(L"Texture Interpolation", UIC_VIEW_TEXTURE_INTERPOLATION, true, false, this->m_TextureInterpolation, true); INDEX_VIEW_TEXTURE_INTERPOLATION = viewMenu->addItem(L"Texture Interpolation", UIC_VIEW_TEXTURE_INTERPOLATION, true, false, this->m_TextureInterpolation, true);
// Playback Control Window // Playback Control Window
dimension2d<u32> windowSize = m_Engine->m_Driver->getScreenSize(); dimension2d<u32> windowSize = m_Engine->m_Driver->getScreenSize();
playbackWindow = m_Gui->addWindow( playbackWindow = m_Gui->addWindow(
rect<s32>( vector2d<s32>( windowSize.Width - 4 - 160, 28 ), dimension2d<s32>( 160, 300 )), false, L"Playback", nullptr, UIE_PLAYBACKWINDOW ); rect<s32>(vector2d<s32>(windowSize.Width - 4 - 160, 28), dimension2d<s32>(160, 300)), false, L"Playback", nullptr, UIE_PLAYBACKWINDOW);
playbackWindow->getCloseButton()->setVisible( false ); playbackWindow->getCloseButton()->setVisible(false);
s32 spacing_x = 4; s32 spacing_x = 4;
s32 spacing_y = 4; spacing_y = 4;
s32 size_x = playbackWindow->getClientRect().getWidth() - 8; s32 size_x = playbackWindow->getClientRect().getWidth() - 8;
s32 size_y = 24; s32 size_y = 24;
s32 y = 24; s32 y = 24;
playbackStartStopButton = m_Gui->addButton( playbackStartStopButton = m_Gui->addButton(
rect<s32>( vector2d<s32>( spacing_x, y ), dimension2d<s32>( size_x, size_y )), rect<s32>(vector2d<s32>(spacing_x, y), dimension2d<s32>(size_x, size_y)),
playbackWindow, playbackWindow,
UIE_PLAYBACKSTARTSTOPBUTTON, UIE_PLAYBACKSTARTSTOPBUTTON,
L"Start/Stop", L"Start/Stop",
nullptr nullptr);
);
y += size_y + spacing_y; y += size_y + spacing_y;
playbackIncreaseButton = m_Gui->addButton( playbackIncreaseButton = m_Gui->addButton(
rect<s32>( vector2d<s32>( spacing_x, y ), dimension2d<s32>( size_x, size_y )), rect<s32>(vector2d<s32>(spacing_x, y), dimension2d<s32>(size_x, size_y)),
playbackWindow, playbackWindow,
UIE_PLAYBACKINCREASEBUTTON, UIE_PLAYBACKINCREASEBUTTON,
L"Faster", L"Faster",
nullptr nullptr);
);
y += size_y + spacing_y; y += size_y + spacing_y;
playbackDecreaseButton = m_Gui->addButton( playbackDecreaseButton = m_Gui->addButton(
rect<s32>( vector2d<s32>( spacing_x, y ), dimension2d<s32>( size_x, size_y )), rect<s32>(vector2d<s32>(spacing_x, y), dimension2d<s32>(size_x, size_y)),
playbackWindow, playbackWindow,
UIE_PLAYBACKDECREASEBUTTON, UIE_PLAYBACKDECREASEBUTTON,
L"Slower", L"Slower",
nullptr nullptr);
);
y += size_y + spacing_y; y += size_y + spacing_y;
playbackSetFrameEditBox = m_Gui->addEditBox( playbackSetFrameEditBox = m_Gui->addEditBox(
L"", L"",
rect<s32>( vector2d<s32>( spacing_x, y ), dimension2d<s32>( size_x, size_y )), rect<s32>(vector2d<s32>(spacing_x, y), dimension2d<s32>(size_x, size_y)),
true, true,
playbackWindow, playbackWindow,
UIE_PLAYBACKSETFRAMEEDITBOX UIE_PLAYBACKSETFRAMEEDITBOX);
);
y += size_y + spacing_y; y += size_y + spacing_y;
texturePathStaticText = m_Gui->addStaticText( texturePathStaticText = m_Gui->addStaticText(
L"Texture Path:", L"Texture Path:",
rect<s32>( vector2d<s32>( spacing_x, y ), dimension2d<s32>( size_x, size_y )), rect<s32>(vector2d<s32>(spacing_x, y), dimension2d<s32>(size_x, size_y)),
true, true,
true, true,
playbackWindow, playbackWindow,
UIE_TEXTUREPATHSTATICTEXT, UIE_TEXTUREPATHSTATICTEXT,
false false);
);
y += size_y + spacing_y; y += size_y + spacing_y;
texturePathEditBox = m_Gui->addEditBox( texturePathEditBox = m_Gui->addEditBox(
L"", L"",
rect<s32>( vector2d<s32>( spacing_x, y ), dimension2d<s32>( size_x, size_y )), rect<s32>(vector2d<s32>(spacing_x, y), dimension2d<s32>(size_x, size_y)),
true, true,
playbackWindow, playbackWindow,
UIE_TEXTUREPATHEDITBOX UIE_TEXTUREPATHEDITBOX);
);
// Set Font for UI Elements // Set Font for UI Elements
m_GuiFontFace = new CGUITTFace(); m_GuiFontFace = new CGUITTFace();
// irrString defines stringc as string<c8> // irrString defines stringc as string<c8>
// if (QFile(fontPath).exists()) {} // if (QFile(fontPath).exists()) {
if (!Utility::isFile(m_Engine->m_FontPath)) { if (!Utility::isFile(m_Engine->m_FontPath)) {
m_Engine->m_FontPath = L"C:\\Windows\\Fonts\\calibrib.ttf"; m_Engine->m_FontPath = L"C:\\Windows\\Fonts\\calibrib.ttf";
} }
@ -130,12 +124,11 @@ void UserInterface::setupUserInterface()
m_Engine->m_FontPath = L"/usr/share/fonts/google-droid/DroidSans-Bold.ttf"; m_Engine->m_FontPath = L"/usr/share/fonts/google-droid/DroidSans-Bold.ttf";
} }
if (m_GuiFontFace->load(m_Engine->m_FontPath.c_str())) { // actually takes `const io::path &` if (m_GuiFontFace->load(m_Engine->m_FontPath.c_str())) { // actually takes `const io::path &`
m_GuiFont = new CGUITTFont( m_Gui ); m_GuiFont = new CGUITTFont(m_Gui);
m_GuiFont->attach( m_GuiFontFace, 14 ); m_GuiFont->attach(m_GuiFontFace, 14);
m_Gui->getSkin()->setFont( m_GuiFont ); m_Gui->getSkin()->setFont(m_GuiFont);
} } else {
else {
std::wcerr << L"WARNING: Missing '" << m_Engine->m_FontPath << L"'" << endl; std::wcerr << L"WARNING: Missing '" << m_Engine->m_FontPath << L"'" << endl;
delete m_GuiFontFace; delete m_GuiFontFace;
m_GuiFontFace = nullptr; m_GuiFontFace = nullptr;
@ -148,22 +141,21 @@ void UserInterface::setupUserInterface()
void UserInterface::displayLoadFileDialog() void UserInterface::displayLoadFileDialog()
{ {
m_Gui->addFileOpenDialog( L"Select file to load", true, nullptr, UIE_LOADFILEDIALOG ); m_Gui->addFileOpenDialog(L"Select file to load", true, nullptr, UIE_LOADFILEDIALOG);
} }
void UserInterface::displayLoadTextureDialog() void UserInterface::displayLoadTextureDialog()
{ {
m_Gui->addFileOpenDialog( L"Select file to load", true, nullptr, UIE_LOADTEXTUREDIALOG ); m_Gui->addFileOpenDialog(L"Select file to load", true, nullptr, UIE_LOADTEXTUREDIALOG);
} }
void UserInterface::handleMenuItemPressed( IGUIContextMenu *menu ) void UserInterface::handleMenuItemPressed(IGUIContextMenu* menu)
{ {
s32 selected = menu->getSelectedItem(); s32 selected = menu->getSelectedItem();
if (selected > -1) { if (selected > -1) {
s32 id = menu->getItemCommandId(static_cast<u32>(selected)); s32 id = menu->getItemCommandId(static_cast<u32>(selected));
switch( id ) switch (id) {
{
case UIC_FILE_LOAD: case UIC_FILE_LOAD:
displayLoadFileDialog(); displayLoadFileDialog();
break; break;
@ -190,14 +182,33 @@ void UserInterface::handleMenuItemPressed( IGUIContextMenu *menu )
m_TextureInterpolation = viewMenu->isItemChecked(INDEX_VIEW_TEXTURE_INTERPOLATION); m_TextureInterpolation = viewMenu->isItemChecked(INDEX_VIEW_TEXTURE_INTERPOLATION);
m_Engine->setMeshDisplayMode(m_WireframeDisplay, m_Lighting, m_TextureInterpolation); m_Engine->setMeshDisplayMode(m_WireframeDisplay, m_Lighting, m_TextureInterpolation);
break; break;
} }
} }
}
void UserInterface::snapWidgets()
{
dimension2d<u32> screenSize = m_Engine->m_Driver->getScreenSize();
rect<s32> newRect;
//newRect.LowerRightCorner.X = static_cast<s32>(size.Width);
//newRect.LowerRightCorner.Y = static_cast<s32>(size.Height);
rect<s32> prevRect = playbackWindow->getRelativePosition();
newRect.UpperLeftCorner.X = static_cast<s32>(screenSize.Width) - prevRect.getWidth() - spacing_y;
//debug() << "screen size: " << screenSize.Width << "x" << screenSize.Height;
//debug() << " prevRect: "
// << prevRect.UpperLeftCorner.X << "," << prevRect.UpperLeftCorner.Y << ","
// << prevRect.LowerRightCorner.X << "," << prevRect.LowerRightCorner.Y
// << " size=(" << prevRect.getWidth() << "," <<prevRect.getHeight() << ")" << endl;
newRect.UpperLeftCorner.Y = prevRect.UpperLeftCorner.Y;
newRect.LowerRightCorner.X = newRect.UpperLeftCorner.X + prevRect.getWidth();
newRect.LowerRightCorner.Y = newRect.UpperLeftCorner.Y + prevRect.getHeight();
playbackWindow->setRelativePosition(newRect);
m_WindowSize.Width = m_Engine->m_Driver->getScreenSize().Width;
m_WindowSize.Height = m_Engine->m_Driver->getScreenSize().Height;
} }
// PUBLIC // PUBLIC
UserInterface::UserInterface( Engine *engine ) UserInterface::UserInterface(Engine* engine)
{ {
INDEX_VIEW_TEXTURE_INTERPOLATION = 0; INDEX_VIEW_TEXTURE_INTERPOLATION = 0;
INDEX_VIEW_WIREFRAME_MESH = 0; INDEX_VIEW_WIREFRAME_MESH = 0;
@ -221,7 +232,7 @@ UserInterface::~UserInterface()
delete m_GuiFontFace; delete m_GuiFontFace;
} }
IGUIEnvironment * UserInterface::getGUIEnvironment() const IGUIEnvironment* UserInterface::getGUIEnvironment() const
{ {
return m_Gui; return m_Gui;
} }
@ -242,21 +253,19 @@ bool UserInterface::loadNextTexture(int direction)
std::wstring dirSeparator = Utility::delimiter(this->m_Engine->m_PreviousPath); std::wstring dirSeparator = Utility::delimiter(this->m_Engine->m_PreviousPath);
std::wstring texturesPath = parentPath + dirSeparator + L"textures"; std::wstring texturesPath = parentPath + dirSeparator + L"textures";
std::wstring tryTexPath = texturesPath + dirSeparator + Utility::withoutExtension(lastName) + L".png"; std::wstring tryTexPath = texturesPath + dirSeparator + Utility::withoutExtension(lastName) + L".png";
if (direction==0 && Utility::isFile(tryTexPath)) { if (direction == 0 && Utility::isFile(tryTexPath)) {
this->m_Engine->m_NextPath = tryTexPath; this->m_Engine->m_NextPath = tryTexPath;
this->m_Engine->loadTexture(this->m_Engine->m_NextPath); this->m_Engine->loadTexture(this->m_Engine->m_NextPath);
} } else {
else {
tryTexPath = lastDirPath + dirSeparator + Utility::withoutExtension(lastName) + L".png"; tryTexPath = lastDirPath + dirSeparator + Utility::withoutExtension(lastName) + L".png";
if (direction==0 && Utility::isFile(tryTexPath)) { if (direction == 0 && Utility::isFile(tryTexPath)) {
this->m_Engine->m_NextPath = tryTexPath; this->m_Engine->m_NextPath = tryTexPath;
ret = this->m_Engine->loadTexture(this->m_Engine->m_NextPath); ret = this->m_Engine->loadTexture(this->m_Engine->m_NextPath);
} } else {
else {
std::wstring path = texturesPath; std::wstring path = texturesPath;
if (!fs::is_directory(fs::status(path))) if (!fs::is_directory(fs::status(path)))
path = lastDirPath; // cycle textures in model's directory instead path = lastDirPath; // cycle textures in model's directory instead
fs::directory_iterator end_itr; // default construction yields past-the-end fs::directory_iterator end_itr; // default construction yields past-the-end
@ -269,7 +278,7 @@ bool UserInterface::loadNextTexture(int direction)
wstring tryPath; wstring tryPath;
if (fs::is_directory(fs::status(path))) { if (fs::is_directory(fs::status(path))) {
if (this->m_Engine->m_PrevTexturePath.length() == 0) { if (this->m_Engine->m_PrevTexturePath.length() == 0) {
if (this->m_Engine->m_PreviousPath.length() > 0 ) { if (this->m_Engine->m_PreviousPath.length() > 0) {
//debug() << "tryPath..." << endl; //debug() << "tryPath..." << endl;
tryPath = texturesPath + dirSeparator + Utility::withoutExtension(Utility::basename(this->m_Engine->m_PreviousPath)) + L".png"; tryPath = texturesPath + dirSeparator + Utility::withoutExtension(Utility::basename(this->m_Engine->m_PreviousPath)) + L".png";
// debug() << "tryPath 1a " << Utility::toString(tryPath) << "..." << endl; // debug() << "tryPath 1a " << Utility::toString(tryPath) << "..." << endl;
@ -289,8 +298,7 @@ bool UserInterface::loadNextTexture(int direction)
found = true; found = true;
force = true; force = true;
} }
} } else {
else {
nextPath = tryPath; nextPath = tryPath;
found = true; found = true;
force = true; force = true;
@ -299,24 +307,28 @@ bool UserInterface::loadNextTexture(int direction)
} }
//debug() << "tryPath: " << Utility::toString(tryPath) << endl; //debug() << "tryPath: " << Utility::toString(tryPath) << endl;
//debug() << "nextPath: " << Utility::toString(nextPath) << endl; //debug() << "nextPath: " << Utility::toString(nextPath) << endl;
for (const auto & itr : fs::directory_iterator(path)) { for (const auto& itr : fs::directory_iterator(path)) {
std::wstring ext = Utility::extensionOf(itr.path().wstring()); // no dot! std::wstring ext = Utility::extensionOf(itr.path().wstring()); // no dot!
if (!is_directory(itr.status()) if (!is_directory(itr.status())
&& std::find(m_Engine->textureExtensions.begin(), m_Engine->textureExtensions.end(), ext) != m_Engine->textureExtensions.end()) { && std::find(m_Engine->textureExtensions.begin(), m_Engine->textureExtensions.end(), ext) != m_Engine->textureExtensions.end()) {
// cycle through files (go to next after m_PrevTexturePath // cycle through files (go to next after m_PrevTexturePath
// if any previously loaded, otherwise first) // if any previously loaded, otherwise first)
if (nextPath.length() == 0) nextPath = itr.path().wstring(); if (nextPath.length() == 0)
nextPath = itr.path().wstring();
lastPath = itr.path().wstring(); lastPath = itr.path().wstring();
if (found && direction > 0) { if (found && direction > 0) {
if (!force) nextPath = itr.path().wstring(); if (!force)
nextPath = itr.path().wstring();
break; break;
} }
if (itr.path().wstring() == this->m_Engine->m_PrevTexturePath) found = true; if (itr.path().wstring() == this->m_Engine->m_PrevTexturePath)
if (!found) retroPath = itr.path().wstring(); found = true;
if (!found)
retroPath = itr.path().wstring();
} }
} }
if (retroPath.length() == 0) if (retroPath.length() == 0)
retroPath = lastPath; // previous is last if at beginning retroPath = lastPath; // previous is last if at beginning
if (direction < 0) if (direction < 0)
nextPath = retroPath; nextPath = retroPath;
if (nextPath.length() > 0) { if (nextPath.length() > 0) {
@ -325,65 +337,63 @@ bool UserInterface::loadNextTexture(int direction)
} }
} }
} }
} } else
else debug() << "Can't cycle texture since no file was opened" << endl; debug() << "Can't cycle texture since no file was opened" << endl;
return ret; return ret;
} }
// IEventReceiver // IEventReceiver
bool UserInterface::OnEvent( const SEvent &event ) bool UserInterface::OnEvent(const SEvent& event)
{ {
// Events arriving here should be destined for us // Events arriving here should be destined for us
if (event.EventType == EET_KEY_INPUT_EVENT) { if (event.EventType == EET_USER_EVENT) {
if (event.UserEvent.UserData1 == UEI_WINDOWSIZECHANGED) {
if ((m_WindowSize.Width != m_Engine->m_Driver->getScreenSize().Width) || (m_WindowSize.Height != m_Engine->m_Driver->getScreenSize().Height)) {
snapWidgets();
}
}
return true;
} else if (event.EventType == EET_KEY_INPUT_EVENT) {
if (event.KeyInput.PressedDown && !m_Engine->KeyIsDown[event.KeyInput.Key]) { if (event.KeyInput.PressedDown && !m_Engine->KeyIsDown[event.KeyInput.Key]) {
if (event.KeyInput.Key == irr::KEY_F5) { if (event.KeyInput.Key == irr::KEY_F5) {
m_Engine->reloadMesh(); m_Engine->reloadMesh();
} } else if (event.KeyInput.Key == irr::KEY_KEY_T) {
else if (event.KeyInput.Key == irr::KEY_KEY_T) {
loadNextTexture(1); loadNextTexture(1);
} } else if (event.KeyInput.Key == irr::KEY_KEY_E) {
else if (event.KeyInput.Key == irr::KEY_KEY_E) {
loadNextTexture(-1); loadNextTexture(-1);
} } else if (event.KeyInput.Key == irr::KEY_KEY_R) {
else if (event.KeyInput.Key == irr::KEY_KEY_R) {
m_Engine->reloadTexture(); m_Engine->reloadTexture();
} } else if (event.KeyInput.Key == irr::KEY_KEY_Z) {
else if (event.KeyInput.Key == irr::KEY_KEY_Z) {
m_Engine->setZUp(true); m_Engine->setZUp(true);
} } else if (event.KeyInput.Key == irr::KEY_KEY_Y) {
else if (event.KeyInput.Key == irr::KEY_KEY_Y) {
m_Engine->setZUp(false); m_Engine->setZUp(false);
} } else if (event.KeyInput.Key == irr::KEY_KEY_X) {
else if (event.KeyInput.Key == irr::KEY_KEY_X) {
// IGUIContextMenu* textureInterpolationElement = dynamic_cast<IGUIContextMenu*>(viewMenu->getElementFromId(UIC_VIEW_TEXTURE_INTERPOLATION)); // IGUIContextMenu* textureInterpolationElement = dynamic_cast<IGUIContextMenu*>(viewMenu->getElementFromId(UIC_VIEW_TEXTURE_INTERPOLATION));
//m_TextureInterpolation = textureInterpolationElement->isItemChecked(UIC_VIEW_TEXTURE_INTERPOLATION); //m_TextureInterpolation = textureInterpolationElement->isItemChecked(UIC_VIEW_TEXTURE_INTERPOLATION);
m_TextureInterpolation = m_TextureInterpolation ? false : true; m_TextureInterpolation = m_TextureInterpolation ? false : true;
//doesn't work: m_TextureInterpolation = viewMenu->isItemChecked(UIC_VIEW_TEXTURE_INTERPOLATION); //doesn't work: m_TextureInterpolation = viewMenu->isItemChecked(UIC_VIEW_TEXTURE_INTERPOLATION);
m_Engine->setMeshDisplayMode(m_WireframeDisplay, m_Lighting, m_TextureInterpolation); m_Engine->setMeshDisplayMode(m_WireframeDisplay, m_Lighting, m_TextureInterpolation);
viewMenu->setItemChecked(INDEX_VIEW_TEXTURE_INTERPOLATION, m_TextureInterpolation); viewMenu->setItemChecked(INDEX_VIEW_TEXTURE_INTERPOLATION, m_TextureInterpolation);
} } else if (event.KeyInput.Char == L'+' || event.KeyInput.Char == L'=') {
else if (event.KeyInput.Char == L'+' || event.KeyInput.Char == L'=') {
m_Engine->setAnimationFPS(m_Engine->animationFPS() + 5); m_Engine->setAnimationFPS(m_Engine->animationFPS() + 5);
} } else if (event.KeyInput.Char == L'-') {
else if (event.KeyInput.Char == L'-') {
if (m_Engine->animationFPS() > 0) { if (m_Engine->animationFPS() > 0) {
m_Engine->setAnimationFPS(m_Engine->animationFPS() - 5); m_Engine->setAnimationFPS(m_Engine->animationFPS() - 5);
} }
} } else if (event.KeyInput.Char == L' ') {
else if (event.KeyInput.Char == L' ') {
m_Engine->toggleAnimation(); m_Engine->toggleAnimation();
} } else if (event.KeyInput.Key == irr::KEY_LEFT) {
else if (event.KeyInput.Key == irr::KEY_LEFT) {
if (this->m_Engine->m_LoadedMesh != nullptr) { if (this->m_Engine->m_LoadedMesh != nullptr) {
if (m_Engine->isPlaying) m_Engine->toggleAnimation(); if (m_Engine->isPlaying)
this->m_Engine->m_LoadedMesh->setCurrentFrame(round(this->m_Engine->m_LoadedMesh->getFrameNr())-1); m_Engine->toggleAnimation();
this->m_Engine->m_LoadedMesh->setCurrentFrame(round(this->m_Engine->m_LoadedMesh->getFrameNr()) - 1);
this->playbackSetFrameEditBox->setText(Utility::toWstring(this->m_Engine->m_LoadedMesh->getFrameNr()).c_str()); this->playbackSetFrameEditBox->setText(Utility::toWstring(this->m_Engine->m_LoadedMesh->getFrameNr()).c_str());
} }
} } else if (event.KeyInput.Key == irr::KEY_RIGHT) {
else if (event.KeyInput.Key == irr::KEY_RIGHT) {
if (this->m_Engine->m_LoadedMesh != nullptr) { if (this->m_Engine->m_LoadedMesh != nullptr) {
if (m_Engine->isPlaying) m_Engine->toggleAnimation(); if (m_Engine->isPlaying)
this->m_Engine->m_LoadedMesh->setCurrentFrame(round(this->m_Engine->m_LoadedMesh->getFrameNr())+1); m_Engine->toggleAnimation();
this->m_Engine->m_LoadedMesh->setCurrentFrame(round(this->m_Engine->m_LoadedMesh->getFrameNr()) + 1);
this->playbackSetFrameEditBox->setText(Utility::toWstring(this->m_Engine->m_LoadedMesh->getFrameNr()).c_str()); this->playbackSetFrameEditBox->setText(Utility::toWstring(this->m_Engine->m_LoadedMesh->getFrameNr()).c_str());
} }
} }
@ -392,87 +402,80 @@ bool UserInterface::OnEvent( const SEvent &event )
m_Engine->KeyIsDown[event.KeyInput.Key] = event.KeyInput.PressedDown; m_Engine->KeyIsDown[event.KeyInput.Key] = event.KeyInput.PressedDown;
return true; return true;
} } else if (event.EventType == EET_MOUSE_INPUT_EVENT) {
else if (event.EventType == EET_MOUSE_INPUT_EVENT)
{
// TODO: improve this copypasta // TODO: improve this copypasta
switch ( event.MouseInput.Event) switch (event.MouseInput.Event) {
{
case EMIE_LMOUSE_LEFT_UP: case EMIE_LMOUSE_LEFT_UP:
if ( m_Engine->LMouseState == 2) { if (m_Engine->LMouseState == 2) {
m_Engine->LMouseState = 3; m_Engine->LMouseState = 3;
} }
break; break;
case EMIE_LMOUSE_PRESSED_DOWN: case EMIE_LMOUSE_PRESSED_DOWN:
if ( m_Engine->LMouseState == 0) { if (m_Engine->LMouseState == 0) {
m_Engine->LMouseState = 1; m_Engine->LMouseState = 1;
} }
break; break;
case EMIE_RMOUSE_LEFT_UP: case EMIE_RMOUSE_LEFT_UP:
if ( m_Engine->RMouseState == 2) { if (m_Engine->RMouseState == 2) {
m_Engine->RMouseState = 3; m_Engine->RMouseState = 3;
} }
break; break;
case EMIE_RMOUSE_PRESSED_DOWN: case EMIE_RMOUSE_PRESSED_DOWN:
if ( m_Engine->RMouseState == 0) { if (m_Engine->RMouseState == 0) {
m_Engine->RMouseState = 1; m_Engine->RMouseState = 1;
} }
break; break;
} }
} } else if (!(event.EventType == EET_GUI_EVENT))
else if (!(event.EventType == EET_GUI_EVENT))
return false; return false;
const SEvent::SGUIEvent *ge = &( event.GUIEvent ); const SEvent::SGUIEvent* ge = &(event.GUIEvent);
switch( ge->Caller->getID() ) switch (ge->Caller->getID()) {
{
case UIE_FILEMENU: case UIE_FILEMENU:
case UIE_VIEWMENU: case UIE_VIEWMENU:
// call handler for all menu related actions // call handler for all menu related actions
handleMenuItemPressed( static_cast<IGUIContextMenu *>( ge->Caller )); handleMenuItemPressed(static_cast<IGUIContextMenu*>(ge->Caller));
break; break;
case UIE_LOADFILEDIALOG: case UIE_LOADFILEDIALOG:
if( ge->EventType == EGET_FILE_SELECTED ) if (ge->EventType == EGET_FILE_SELECTED) {
{ IGUIFileOpenDialog* fileOpenDialog = static_cast<IGUIFileOpenDialog*>(ge->Caller);
IGUIFileOpenDialog *fileOpenDialog = static_cast<IGUIFileOpenDialog *>( ge->Caller ); m_Engine->loadMesh(fileOpenDialog->getFileName());
m_Engine->loadMesh( fileOpenDialog->getFileName() );
} }
break; break;
case UIE_LOADTEXTUREDIALOG: case UIE_LOADTEXTUREDIALOG:
if( ge->EventType == EGET_FILE_SELECTED ) if (ge->EventType == EGET_FILE_SELECTED) {
{ IGUIFileOpenDialog* fileOpenDialog = static_cast<IGUIFileOpenDialog*>(ge->Caller);
IGUIFileOpenDialog *fileOpenDialog = static_cast<IGUIFileOpenDialog *>( ge->Caller ); m_Engine->loadTexture(fileOpenDialog->getFileName());
m_Engine->loadTexture( fileOpenDialog->getFileName() );
} }
break; break;
case UIE_PLAYBACKSTARTSTOPBUTTON: case UIE_PLAYBACKSTARTSTOPBUTTON:
if ( ge->EventType == EGET_BUTTON_CLICKED) { if (ge->EventType == EGET_BUTTON_CLICKED) {
this->m_Engine->toggleAnimation(); this->m_Engine->toggleAnimation();
} }
break; break;
case UIE_PLAYBACKINCREASEBUTTON: case UIE_PLAYBACKINCREASEBUTTON:
if ( ge->EventType == EGET_BUTTON_CLICKED) { if (ge->EventType == EGET_BUTTON_CLICKED) {
this->m_Engine->setAnimationFPS(this->m_Engine->animationFPS() + 5); this->m_Engine->setAnimationFPS(this->m_Engine->animationFPS() + 5);
} }
break; break;
case UIE_PLAYBACKDECREASEBUTTON: case UIE_PLAYBACKDECREASEBUTTON:
if ( ge->EventType == EGET_BUTTON_CLICKED) { if (ge->EventType == EGET_BUTTON_CLICKED) {
if (this->m_Engine->animationFPS() >= 5) { if (this->m_Engine->animationFPS() >= 5) {
this->m_Engine->setAnimationFPS(this->m_Engine->animationFPS() - 5); this->m_Engine->setAnimationFPS(this->m_Engine->animationFPS() - 5);
} }
} }
break; break;
case UIE_PLAYBACKSETFRAMEEDITBOX: case UIE_PLAYBACKSETFRAMEEDITBOX:
if ( ge->EventType == EGET_EDITBOX_ENTER) { if (ge->EventType == EGET_EDITBOX_ENTER) {
if (this->m_Engine->m_LoadedMesh != nullptr) { if (this->m_Engine->m_LoadedMesh != nullptr) {
this->m_Engine->m_LoadedMesh->setCurrentFrame(Utility::toF32(this->playbackSetFrameEditBox->getText())); this->m_Engine->m_LoadedMesh->setCurrentFrame(Utility::toF32(this->playbackSetFrameEditBox->getText()));
} }

View File

@ -1,14 +1,13 @@
#ifndef USERINTERFACE_H #ifndef USERINTERFACE_H
#define USERINTERFACE_H #define USERINTERFACE_H
#include <irrlicht/irrlicht.h>
#include "extlib/CGUITTFont.h" #include "extlib/CGUITTFont.h"
#include <irrlicht/irrlicht.h>
// Forward declaration of class Engine // Forward declaration of class Engine
class Engine; class Engine;
enum UserInterfaceElements enum UserInterfaceElements {
{
UIE_FILEMENU = 1003, UIE_FILEMENU = 1003,
UIE_LOADFILEDIALOG = 1100, UIE_LOADFILEDIALOG = 1100,
// UIE_LOADBUTTON = 1101, // UIE_LOADBUTTON = 1101,
@ -25,8 +24,7 @@ enum UserInterfaceElements
UIE_TEXTUREPATHEDITBOX = 3006 UIE_TEXTUREPATHEDITBOX = 3006
}; };
enum UserInterfaceCommands enum UserInterfaceCommands {
{
UIC_FILE_LOAD = 1000, UIC_FILE_LOAD = 1000,
UIC_FILE_QUIT = 1001, UIC_FILE_QUIT = 1001,
UIC_FILE_LOAD_TEXTURE = 1002, UIC_FILE_LOAD_TEXTURE = 1002,
@ -35,46 +33,48 @@ enum UserInterfaceCommands
UIC_VIEW_TEXTURE_INTERPOLATION = 2003 UIC_VIEW_TEXTURE_INTERPOLATION = 2003
}; };
class UserInterface : public irr::IEventReceiver class UserInterface : public irr::IEventReceiver {
{
private: private:
Engine *m_Engine; irr::s32 spacing_y;
irr::gui::IGUIEnvironment *m_Gui; Engine* m_Engine;
irr::gui::CGUITTFont *m_GuiFont; irr::gui::IGUIEnvironment* m_Gui;
irr::gui::CGUITTFace *m_GuiFontFace; irr::gui::CGUITTFont* m_GuiFont;
irr::gui::CGUITTFace* m_GuiFontFace;
void setupUserInterface(); void setupUserInterface();
void displayLoadFileDialog(); void displayLoadFileDialog();
void displayLoadTextureDialog(); void displayLoadTextureDialog();
void handleMenuItemPressed(irr::gui::IGUIContextMenu *menu); void handleMenuItemPressed(irr::gui::IGUIContextMenu* menu);
bool m_WireframeDisplay; bool m_WireframeDisplay;
bool m_Lighting; bool m_Lighting;
bool m_TextureInterpolation; bool m_TextureInterpolation;
irr::gui::IGUIWindow *playbackWindow; irr::gui::IGUIWindow* playbackWindow;
irr::core::dimension2d<irr::u32> m_WindowSize; // previous size
public: public:
irr::gui::IGUIContextMenu *menu; irr::gui::IGUIContextMenu* menu;
irr::gui::IGUIContextMenu *fileMenu; irr::gui::IGUIContextMenu* fileMenu;
irr::gui::IGUIContextMenu *viewMenu; irr::gui::IGUIContextMenu* viewMenu;
irr::gui::IGUIButton *playbackStartStopButton; irr::gui::IGUIButton* playbackStartStopButton;
irr::gui::IGUIButton *playbackIncreaseButton; irr::gui::IGUIButton* playbackIncreaseButton;
irr::gui::IGUIButton *playbackDecreaseButton; irr::gui::IGUIButton* playbackDecreaseButton;
irr::gui::IGUIEditBox *playbackSetFrameEditBox; irr::gui::IGUIEditBox* playbackSetFrameEditBox;
irr::gui::IGUIStaticText *texturePathStaticText; irr::gui::IGUIStaticText* texturePathStaticText;
irr::gui::IGUIEditBox *texturePathEditBox; irr::gui::IGUIEditBox* texturePathEditBox;
irr::u32 INDEX_VIEW_TEXTURE_INTERPOLATION; irr::u32 INDEX_VIEW_TEXTURE_INTERPOLATION;
irr::u32 INDEX_VIEW_WIREFRAME_MESH; irr::u32 INDEX_VIEW_WIREFRAME_MESH;
irr::u32 INDEX_VIEW_LIGHTING; irr::u32 INDEX_VIEW_LIGHTING;
void snapWidgets();
UserInterface( Engine *device ); UserInterface(Engine* device);
~UserInterface(); ~UserInterface();
irr::gui::IGUIEnvironment *getGUIEnvironment() const; irr::gui::IGUIEnvironment* getGUIEnvironment() const;
void drawStatusLine() const; void drawStatusLine() const;
bool loadNextTexture(int direction); bool loadNextTexture(int direction);
// IEventReceiver // IEventReceiver
virtual bool OnEvent( const irr::SEvent &event ); virtual bool OnEvent(const irr::SEvent& event);
}; };
#endif // USERINTERFACE_H #endif // USERINTERFACE_H

View File

@ -1,13 +1,13 @@
#include "Utility.h" #include "Utility.h"
#include <string>
#include <iostream>
#include <clocale>
#include <locale>
#include <vector>
#include <cmath>
#include <cwctype> // #include <cwtype>
#include <algorithm> #include <algorithm>
#include <clocale>
#include <cmath>
#include <cwctype> // #include <cwtype>
#include <iostream>
#include <locale>
#include <sstream> #include <sstream>
#include <string>
#include <vector>
#include "Debug.h" #include "Debug.h"
@ -16,13 +16,12 @@ using namespace irr::scene;
using namespace irr::video; using namespace irr::video;
using namespace std; using namespace std;
void Utility::dumpVectorToConsole(const vector3df& vector)
void Utility::dumpVectorToConsole( const vector3df &vector )
{ {
debug() << "X: " << vector.X << " Y: " << vector.Y << " Z: " << vector.Z << endl; debug() << "X: " << vector.X << " Y: " << vector.Y << " Z: " << vector.Z << endl;
} }
void Utility::dumpMeshInfoToConsole( IAnimatedMeshSceneNode *node ) void Utility::dumpMeshInfoToConsole(IAnimatedMeshSceneNode* node)
{ {
if (node == nullptr) { if (node == nullptr) {
debug() << "[MESH]: # node: nullptr" << endl; debug() << "[MESH]: # node: nullptr" << endl;
@ -33,33 +32,32 @@ void Utility::dumpMeshInfoToConsole( IAnimatedMeshSceneNode *node )
return; return;
} }
// Dump some information about the mesh to the console // Dump some information about the mesh to the console
IAnimatedMesh *mesh = node->getMesh(); IAnimatedMesh* mesh = node->getMesh();
debug() << "[MESH]: # of frames : " << mesh->getFrameCount() << endl; debug() << "[MESH]: # of frames : " << mesh->getFrameCount() << endl;
debug() << "[MESH]: # of materials : " << node->getMaterialCount() << endl; debug() << "[MESH]: # of materials : " << node->getMaterialCount() << endl;
for( irr::u32 matIndex = 0; matIndex < node->getMaterialCount(); matIndex ++ ) for (irr::u32 matIndex = 0; matIndex < node->getMaterialCount(); matIndex++) {
{
debug() << "[MESH]: Material # " << matIndex << endl; debug() << "[MESH]: Material # " << matIndex << endl;
const SMaterial &material = node->getMaterial( matIndex ); const SMaterial& material = node->getMaterial(matIndex);
debug() << "[MESH]: Diffuse Color : A" << material.DiffuseColor.getAlpha() << " R" << material.DiffuseColor.getRed() << " G" << material.DiffuseColor.getGreen() << " B" << material.DiffuseColor.getBlue() << endl; debug() << "[MESH]: Diffuse Color : A" << material.DiffuseColor.getAlpha() << " R" << material.DiffuseColor.getRed() << " G" << material.DiffuseColor.getGreen() << " B" << material.DiffuseColor.getBlue() << endl;
debug() << "[MESH]: Specular Color : A" << material.SpecularColor.getAlpha() << " R" << material.SpecularColor.getRed() << " G" << material.SpecularColor.getGreen() << " B" << material.SpecularColor.getBlue() << endl; debug() << "[MESH]: Specular Color : A" << material.SpecularColor.getAlpha() << " R" << material.SpecularColor.getRed() << " G" << material.SpecularColor.getGreen() << " B" << material.SpecularColor.getBlue() << endl;
debug() << "[MESH]: Specular Shininess : " << material.Shininess << endl; debug() << "[MESH]: Specular Shininess : " << material.Shininess << endl;
// check for # textures // check for # textures
int textures = 0; int textures = 0;
for( irr::u32 ti = 0; ti < MATERIAL_MAX_TEXTURES; ti ++ ) for (irr::u32 ti = 0; ti < MATERIAL_MAX_TEXTURES; ti++)
if( material.getTexture( ti ) != nullptr ) textures ++; if (material.getTexture(ti) != nullptr)
textures++;
debug() << "[MESH]: # of textures : " << textures << endl; debug() << "[MESH]: # of textures : " << textures << endl;
} }
} }
std::wstring Utility::parentOfPath(const wstring &path) std::wstring Utility::parentOfPath(const wstring& path)
{ {
std::wstring ret = L"."; std::wstring ret = L".";
if (path == L".") { if (path == L".") {
ret = L".."; ret = L"..";
} } else {
else {
std::wstring::size_type lastSlashPos = path.find_last_of(L"/"); std::wstring::size_type lastSlashPos = path.find_last_of(L"/");
if (lastSlashPos == std::wstring::npos) { if (lastSlashPos == std::wstring::npos) {
lastSlashPos = path.find_last_of(L"\\"); lastSlashPos = path.find_last_of(L"\\");
@ -71,7 +69,7 @@ std::wstring Utility::parentOfPath(const wstring &path)
return ret; return ret;
} }
wstring Utility::basename(const wstring &path) wstring Utility::basename(const wstring& path)
{ {
std::wstring ret = path; std::wstring ret = path;
std::wstring::size_type lastSlashPos = path.find_last_of(L"/"); std::wstring::size_type lastSlashPos = path.find_last_of(L"/");
@ -79,12 +77,12 @@ wstring Utility::basename(const wstring &path)
lastSlashPos = path.find_last_of(L"\\"); lastSlashPos = path.find_last_of(L"\\");
} }
if (lastSlashPos != std::wstring::npos) { if (lastSlashPos != std::wstring::npos) {
ret = path.substr(lastSlashPos+1); ret = path.substr(lastSlashPos + 1);
} }
return ret; return ret;
} }
wstring Utility::withoutExtension(const wstring &path) wstring Utility::withoutExtension(const wstring& path)
{ {
std::wstring ret = path; std::wstring ret = path;
std::wstring::size_type lastDotPos = path.find_last_of(L"."); std::wstring::size_type lastDotPos = path.find_last_of(L".");
@ -94,14 +92,15 @@ wstring Utility::withoutExtension(const wstring &path)
lastSlashPos = path.find_last_of(L"\\"); lastSlashPos = path.find_last_of(L"\\");
} }
if (lastSlashPos != std::wstring::npos) { if (lastSlashPos != std::wstring::npos) {
if (lastDotPos > lastSlashPos) ret = path.substr(0, lastDotPos); if (lastDotPos > lastSlashPos)
} ret = path.substr(0, lastDotPos);
else ret = path.substr(0, lastDotPos); } else
ret = path.substr(0, lastDotPos);
} }
return ret; return ret;
} }
wstring Utility::extensionOf(const wstring &path) wstring Utility::extensionOf(const wstring& path)
{ {
std::wstring ret = L""; std::wstring ret = L"";
std::wstring::size_type lastDotPos = path.find_last_of(L"."); std::wstring::size_type lastDotPos = path.find_last_of(L".");
@ -111,21 +110,21 @@ wstring Utility::extensionOf(const wstring &path)
lastSlashPos = path.find_last_of(L"\\"); lastSlashPos = path.find_last_of(L"\\");
} }
if (lastSlashPos != std::wstring::npos) { if (lastSlashPos != std::wstring::npos) {
if (lastDotPos > lastSlashPos) ret = path.substr(lastDotPos + 1); if (lastDotPos > lastSlashPos)
} ret = path.substr(lastDotPos + 1);
else ret = path.substr(lastDotPos + 1); } else
ret = path.substr(lastDotPos + 1);
} }
return ret; return ret;
} }
wstring Utility::delimiter(const wstring &path) wstring Utility::delimiter(const wstring& path)
{ {
std::wstring ret = L"/"; std::wstring ret = L"/";
std::wstring::size_type lastSlashPos = path.find_last_of(L"/"); std::wstring::size_type lastSlashPos = path.find_last_of(L"/");
if (lastSlashPos == std::wstring::npos) { if (lastSlashPos == std::wstring::npos) {
// ret = L"/"; // ret = L"/";
} } else {
else {
std::wstring::size_type lastSlashPos = path.find_last_of(L"\\"); std::wstring::size_type lastSlashPos = path.find_last_of(L"\\");
if (lastSlashPos != std::wstring::npos) { if (lastSlashPos != std::wstring::npos) {
ret = L"\\"; ret = L"\\";
@ -134,8 +133,9 @@ wstring Utility::delimiter(const wstring &path)
return ret; return ret;
} }
bool Utility::isFile(const std::string& name) { bool Utility::isFile(const std::string& name)
if (FILE *file = fopen(name.c_str(), "r")) { {
if (FILE* file = fopen(name.c_str(), "r")) {
fclose(file); fclose(file);
return true; return true;
} else { } else {
@ -143,7 +143,8 @@ bool Utility::isFile(const std::string& name) {
} }
} }
std::string Utility::toString(const std::wstring& ws) { std::string Utility::toString(const std::wstring& ws)
{
std::string ret; std::string ret;
if (ws.length() > 0) { if (ws.length() > 0) {
// std::string str = "Hello"; // std::string str = "Hello";
@ -154,37 +155,36 @@ std::string Utility::toString(const std::wstring& ws) {
return ret; return ret;
//below sometimes results in "internal_utf8_loop_single: Assertion `inptr - bytebuf > (state->__count & 7)' failed." on the converter.out call: //below sometimes results in "internal_utf8_loop_single: Assertion `inptr - bytebuf > (state->__count & 7)' failed." on the converter.out call:
// if (ws.length() > 0) { //if (ws.length() > 0) {
// // convert to w_string using locale: see Phillipp on <https://stackoverflow.com/questions/4804298/how-to-convert-wstring-into-string> // // convert to w_string using locale: see Phillipp on <https://stackoverflow.com/questions/4804298/how-to-convert-wstring-into-string>
// std::setlocale(LC_ALL, ""); // std::setlocale(LC_ALL, "");
// const std::locale locale(""); // const std::locale locale("");
// typedef std::codecvt<wchar_t, char, std::mbstate_t> converter_type; // typedef std::codecvt<wchar_t, char, std::mbstate_t> converter_type;
// const converter_type& converter = std::use_facet<converter_type>(locale); // const converter_type& converter = std::use_facet<converter_type>(locale);
// std::vector<char> to(ws.length() * converter.max_length()); // std::vector<char> to(ws.length() * converter.max_length());
// std::mbstate_t state; // std::mbstate_t state;
// const wchar_t* from_next = nullptr; // const wchar_t* from_next = nullptr;
// char* to_next = nullptr; // char* to_next = nullptr;
// const converter_type::result result = converter.out(state, ws.data(), ws.data() + ws.length(), from_next, &to[0], &to[0] + to.size(), to_next); // const converter_type::result result = converter.out(state, ws.data(), ws.data() + ws.length(), from_next, &to[0], &to[0] + to.size(), to_next);
// if (result == converter_type::ok or result == converter_type::noconv) { // if (result == converter_type::ok or result == converter_type::noconv) {
// const std::string s(&to[0], to_next); // const std::string s(&to[0], to_next);
// //std::cout <<"std::string = "<<s<<std::endl; // //std::cout <<"std::string = "<<s<<std::endl;
// ret = s; // ret = s;
// } // }
// } //return ret;
// return ret;
} }
std::string Utility::toLower(const std::string &s) std::string Utility::toLower(const std::string& s)
{ {
std::string ret = s; std::string ret = s;
std::transform( ret.begin(), ret.end(), ret.begin(), ::tolower); std::transform(ret.begin(), ret.end(), ret.begin(), ::tolower);
return ret; return ret;
} }
wstring Utility::toLower(const wstring &s) wstring Utility::toLower(const wstring& s)
{ {
wstring ret = s; wstring ret = s;
std::transform( ret.begin(), ret.end(), ret.begin(), towlower); std::transform(ret.begin(), ret.end(), ret.begin(), towlower);
return ret; return ret;
} }
@ -198,7 +198,7 @@ wstring Utility::toWstring(int val)
return std::to_wstring(val); return std::to_wstring(val);
} }
wstring Utility::toWstring(const std::string &str) wstring Utility::toWstring(const std::string& str)
{ {
std::wstring ret; std::wstring ret;
if (str.length() > 0) { if (str.length() > 0) {
@ -218,9 +218,10 @@ irr::f32 Utility::toF32(wstring val)
return ret; return ret;
} }
bool Utility::isFile(const std::wstring& name) { bool Utility::isFile(const std::wstring& name)
{
std::string name_s = toString(name); std::string name_s = toString(name);
if (FILE *file = fopen(name_s.c_str(), "r")) { if (FILE* file = fopen(name_s.c_str(), "r")) {
fclose(file); fclose(file);
return true; return true;
} else { } else {
@ -233,7 +234,6 @@ std::string Utility::toString(irr::f32 val)
return std::to_string(val); return std::to_string(val);
} }
//don't do late instantiation (see header file) //don't do late instantiation (see header file)
//template<typename T> //template<typename T>
//bool Utility::equalsApprox(T f1, T f2) //bool Utility::equalsApprox(T f1, T f2)

View File

@ -5,31 +5,31 @@
#include <irrlicht/irrlicht.h> #include <irrlicht/irrlicht.h>
class Utility class Utility {
{
public: public:
static void dumpVectorToConsole( const irr::core::vector3df &vector ); static void dumpVectorToConsole(const irr::core::vector3df& vector);
static void dumpMeshInfoToConsole( irr::scene::IAnimatedMeshSceneNode *node ); static void dumpMeshInfoToConsole(irr::scene::IAnimatedMeshSceneNode* node);
static std::wstring parentOfPath(const std::wstring &path); static std::wstring parentOfPath(const std::wstring& path);
static std::wstring basename(const std::wstring &path); static std::wstring basename(const std::wstring& path);
static std::wstring withoutExtension(const std::wstring &path); static std::wstring withoutExtension(const std::wstring& path);
static std::wstring extensionOf(const std::wstring &path); static std::wstring extensionOf(const std::wstring& path);
static std::wstring delimiter(const std::wstring &path); static std::wstring delimiter(const std::wstring& path);
static bool isFile(const std::string &name); static bool isFile(const std::string& name);
static bool isFile(const std::wstring &name); static bool isFile(const std::wstring& name);
static std::string toString(irr::f32 val); static std::string toString(irr::f32 val);
static std::string toString(const std::wstring &name); static std::string toString(const std::wstring& name);
static std::string toLower(const std::string &s); static std::string toLower(const std::string& s);
static std::wstring toLower(const std::wstring &s); static std::wstring toLower(const std::wstring& s);
static std::wstring toWstring(irr::f32 val); static std::wstring toWstring(irr::f32 val);
static std::wstring toWstring(int val); static std::wstring toWstring(int val);
static std::wstring toWstring(const std::string &str); static std::wstring toWstring(const std::string& str);
static irr::f32 toF32(std::wstring val); static irr::f32 toF32(std::wstring val);
// compiler doesn't like template function when class is not a template--instantiate immediately // compiler doesn't like template function when class is not a template--instantiate immediately
// see http://processors.wiki.ti.com/index.php/C%2B%2B_Template_Instantiation_Issues // see http://processors.wiki.ti.com/index.php/C%2B%2B_Template_Instantiation_Issues
template <typename T> template <typename T>
static bool equalsApprox(T f1, T f2) { static bool equalsApprox(T f1, T f2)
return abs(f2-f1) < .00000001; // TODO: kEpsilon? (see also <https://en.wikipedia.org/wiki/Machine_epsilon#How_to_determine_machine_epsilon>) {
return abs(f2 - f1) < .00000001; // TODO: kEpsilon? (see also <https://en.wikipedia.org/wiki/Machine_epsilon#How_to_determine_machine_epsilon>)
} }
}; };

109
View.cpp
View File

@ -1,6 +1,6 @@
#include "View.h" #include "View.h"
#include <iostream>
#include "Engine.h" #include "Engine.h"
#include <iostream>
using namespace irr; using namespace irr;
using namespace irr::core; using namespace irr::core;
@ -14,12 +14,11 @@ void View::setNewCameraPosition()
void View::setNewCameraPosition(bool zUp) void View::setNewCameraPosition(bool zUp)
{ {
vector3d<f32> newCameraPosition; vector3d<f32> newCameraPosition;
ICameraSceneNode *camera = m_Engine->m_Scene->getActiveCamera(); ICameraSceneNode* camera = m_Engine->m_Scene->getActiveCamera();
if (zUp) { if (zUp) {
camera->setUpVector(vector3df(0, 0, 1)); camera->setUpVector(vector3df(0, 0, 1));
} } else {
else {
camera->setUpVector(vector3df(0, 1, 0)); camera->setUpVector(vector3df(0, 1, 0));
} }
@ -47,11 +46,10 @@ void View::setNewCameraPosition(bool zUp)
newCameraPosition.Y = m_CameraDistance * cos(m_Pitch); newCameraPosition.Y = m_CameraDistance * cos(m_Pitch);
newCameraPosition.Z = m_CameraDistance * sin(m_Pitch); newCameraPosition.Z = m_CameraDistance * sin(m_Pitch);
yawMatrix.setRotationRadians(vector3df(0, 0, m_Yaw)); yawMatrix.setRotationRadians(vector3df(0, 0, m_Yaw));
} } else {
else {
newCameraPosition.X = 0; newCameraPosition.X = 0;
newCameraPosition.Y = m_CameraDistance * sin( m_Pitch ); newCameraPosition.Y = m_CameraDistance * sin(m_Pitch);
newCameraPosition.Z = m_CameraDistance * cos( m_Pitch ); newCameraPosition.Z = m_CameraDistance * cos(m_Pitch);
yawMatrix.setRotationRadians(vector3df(0, m_Yaw, 0)); yawMatrix.setRotationRadians(vector3df(0, m_Yaw, 0));
} }
@ -60,33 +58,32 @@ void View::setNewCameraPosition(bool zUp)
if (zUp) { if (zUp) {
//camera->setUpVector(vector3df(0, 0, 1)); //camera->setUpVector(vector3df(0, 0, 1));
//newCameraPosition.Z = oldCamPos.Z; //newCameraPosition.Z = oldCamPos.Z;
} } else {
else {
//camera->setUpVector(vector3df(0, 1, 0)); //camera->setUpVector(vector3df(0, 1, 0));
//newCameraPosition.Y = oldCamPos.Y; //newCameraPosition.Y = oldCamPos.Y;
} }
camera->setPosition( newCameraPosition ); camera->setPosition(newCameraPosition);
// vector3df newRotation(); // vector3df newRotation();
// camera->setRotation(); // camera->setRotation();
camera->setTarget(m_Engine->m_CamTarget); camera->setTarget(m_Engine->m_CamTarget);
// Set Light direction // Set Light direction
setNewLightDirection( newCameraPosition ); setNewLightDirection(newCameraPosition);
m_zUp = zUp; m_zUp = zUp;
// std::wcerr << L" setCameraPosition pitch: " << m_Pitch << endl; // std::wcerr << L" setCameraPosition pitch: " << m_Pitch << endl;
} }
void View::setNewLightDirection( const vector3df &cameraPosition ) void View::setNewLightDirection(const vector3df& cameraPosition)
{ {
ILightSceneNode *light = static_cast<ILightSceneNode *>( m_Engine->m_Scene->getSceneNodeFromId( SIID_LIGHT )); ILightSceneNode* light = static_cast<ILightSceneNode*>(m_Engine->m_Scene->getSceneNodeFromId(SIID_LIGHT));
matrix4 m; matrix4 m;
m.buildRotateFromTo( vector3df( 0, 0, 1 ), vector3df( cameraPosition ).invert().normalize() ); m.buildRotateFromTo(vector3df(0, 0, 1), vector3df(cameraPosition).invert().normalize());
light->setRotation( m.getRotationDegrees() ); light->setRotation(m.getRotationDegrees());
} }
View::View( Engine *engine ) View::View(Engine* engine)
{ {
m_zUp = false; m_zUp = false;
m_Engine = engine; m_Engine = engine;
@ -101,10 +98,9 @@ View::View( Engine *engine )
// Calculate offsetVec3 manually, since the object is needed later // Calculate offsetVec3 manually, since the object is needed later
// (Vectors for angle are opposite, since camera revolves around center): // (Vectors for angle are opposite, since camera revolves around center):
vector3df offsetVec3( vector3df offsetVec3(
engine->m_CamPos.X-engine->m_CamTarget.X, engine->m_CamPos.X - engine->m_CamTarget.X,
engine->m_CamPos.Y-engine->m_CamTarget.Y, engine->m_CamPos.Y - engine->m_CamTarget.Y,
engine->m_CamPos.Z-engine->m_CamTarget.Z engine->m_CamPos.Z - engine->m_CamTarget.Z);
);
m_CameraDistance = offsetVec3.getLength(); m_CameraDistance = offsetVec3.getLength();
// NOTE: rotationToDirection converts a rotation to a vec3 direction // NOTE: rotationToDirection converts a rotation to a vec3 direction
@ -147,45 +143,36 @@ bool View::zUp()
} }
// IEventReceiver // IEventReceiver
bool View::OnEvent( const SEvent &event ) bool View::OnEvent(const SEvent& event)
{ {
// If it's not a mouse event or window resize event, return // If it's not a mouse event or window resize event, return
if( event.EventType != EET_MOUSE_INPUT_EVENT && !( event.EventType == EET_USER_EVENT && event.UserEvent.UserData1 == UEI_WINDOWSIZECHANGED )) if (event.EventType != EET_MOUSE_INPUT_EVENT && !(event.EventType == EET_USER_EVENT && event.UserEvent.UserData1 == UEI_WINDOWSIZECHANGED))
return false; return false;
// Handle window resize // Handle window resize
if( event.EventType == EET_USER_EVENT && event.UserEvent.UserData1 == UEI_WINDOWSIZECHANGED ) if (event.EventType == EET_USER_EVENT && event.UserEvent.UserData1 == UEI_WINDOWSIZECHANGED) {
{
dimension2d<u32> windowSize = m_Engine->m_Driver->getScreenSize(); dimension2d<u32> windowSize = m_Engine->m_Driver->getScreenSize();
f32 aspectRatio = static_cast<f32>(windowSize.Width) / static_cast<f32>(windowSize.Height); f32 aspectRatio = static_cast<f32>(windowSize.Width) / static_cast<f32>(windowSize.Height);
debug() << "Setting aspect to: " << aspectRatio << endl; debug() << "Setting aspect to: " << aspectRatio << endl;
m_Engine->m_Scene->getActiveCamera()->setAspectRatio( aspectRatio ); m_Engine->m_Scene->getActiveCamera()->setAspectRatio(aspectRatio);
} }
// Handle mouse event // Handle mouse event
const SEvent::SMouseInput *mouseEvent = &( event.MouseInput ); const SEvent::SMouseInput* mouseEvent = &(event.MouseInput);
if( mouseEvent->Event == EMIE_MMOUSE_PRESSED_DOWN ) if (mouseEvent->Event == EMIE_MMOUSE_PRESSED_DOWN) {
{
m_RotMouse = true; m_RotMouse = true;
m_LastMousePosition->X = mouseEvent->X; m_LastMousePosition->X = mouseEvent->X;
m_LastMousePosition->Y = mouseEvent->Y; m_LastMousePosition->Y = mouseEvent->Y;
} } else if (mouseEvent->Event == EMIE_MMOUSE_LEFT_UP) {
else if( mouseEvent->Event == EMIE_MMOUSE_LEFT_UP )
{
m_RotMouse = false; m_RotMouse = false;
} } else if (mouseEvent->Event == EMIE_MOUSE_WHEEL) {
else if( mouseEvent->Event == EMIE_MOUSE_WHEEL )
{
f32 distanceDelta = mouseEvent->Wheel / 2.5f; f32 distanceDelta = mouseEvent->Wheel / 2.5f;
if( m_CameraDistance - distanceDelta > 0.1f ) if (m_CameraDistance - distanceDelta > 0.1f)
m_CameraDistance -= distanceDelta; m_CameraDistance -= distanceDelta;
setNewCameraPosition(); setNewCameraPosition();
} } else if (m_RotMouse) {
else if( m_RotMouse )
{
int dx = mouseEvent->X - m_LastMousePosition->X; int dx = mouseEvent->X - m_LastMousePosition->X;
int dy = mouseEvent->Y - m_LastMousePosition->Y; int dy = mouseEvent->Y - m_LastMousePosition->Y;
@ -194,7 +181,7 @@ bool View::OnEvent( const SEvent &event )
if (m_Engine->KeyIsDown[irr::KEY_RSHIFT] || m_Engine->KeyIsDown[irr::KEY_LSHIFT]) { if (m_Engine->KeyIsDown[irr::KEY_RSHIFT] || m_Engine->KeyIsDown[irr::KEY_LSHIFT]) {
// Pan camera. // Pan camera.
float yDelta = (dy / 400.0f) * m_CameraDistance; float yDelta = (dy / 400.0f) * m_CameraDistance;
ICameraSceneNode *camera = m_Engine->m_Scene->getActiveCamera(); ICameraSceneNode* camera = m_Engine->m_Scene->getActiveCamera();
vector3df rotationVec3; vector3df rotationVec3;
rotationVec3 = camera->getRotation(); rotationVec3 = camera->getRotation();
vector3df forwards(0, 0, 1); vector3df forwards(0, 0, 1);
@ -208,17 +195,16 @@ bool View::OnEvent( const SEvent &event )
forwards = vector3df(0, 1, 0); forwards = vector3df(0, 1, 0);
dirVec3.rotateYZBy(camRot.X); dirVec3.rotateYZBy(camRot.X);
dirVec3.rotateXYBy(camRot.Z); dirVec3.rotateXYBy(camRot.Z);
} } else {
else {
camRot.Z = m_Pitch; camRot.Z = m_Pitch;
dirVec3.rotateYZBy(camRot.X); dirVec3.rotateYZBy(camRot.X);
dirVec3.rotateXYBy(camRot.Y); dirVec3.rotateXYBy(camRot.Y);
} }
// vector3df dirVec3 = rotationVec3.rotationToDirection(forwards); // vector3df dirVec3 = rotationVec3.rotationToDirection(forwards);
// // move up and down, not in and out: // // move up and down, not in and out:
// float z = dirVec3.Z; // float z = dirVec3.Z;
// dirVec3.Z = dirVec3.Y; // dirVec3.Z = dirVec3.Y;
// dirVec3.Z = z; // dirVec3.Z = z;
dirVec3.X *= yDelta; dirVec3.X *= yDelta;
dirVec3.Y *= yDelta; dirVec3.Y *= yDelta;
dirVec3.Z *= yDelta; dirVec3.Z *= yDelta;
@ -231,36 +217,35 @@ bool View::OnEvent( const SEvent &event )
if (m_zUp) { if (m_zUp) {
//m_Engine->m_CamPos.Z += yDelta; //m_Engine->m_CamPos.Z += yDelta;
//m_Engine->m_CamTarget.Z += yDelta; //m_Engine->m_CamTarget.Z += yDelta;
} } else {
else {
//m_Engine->m_CamPos.Y += yDelta; //m_Engine->m_CamPos.Y += yDelta;
//m_Engine->m_CamTarget.Y += yDelta; //m_Engine->m_CamTarget.Y += yDelta;
} }
camera->setPosition(m_Engine->m_CamPos); camera->setPosition(m_Engine->m_CamPos);
camera->setTarget(m_Engine->m_CamTarget); camera->setTarget(m_Engine->m_CamTarget);
vector3df offsetVec3( vector3df offsetVec3(
m_Engine->m_CamPos.X-m_Engine->m_CamTarget.X, m_Engine->m_CamPos.X - m_Engine->m_CamTarget.X,
m_Engine->m_CamPos.Y-m_Engine->m_CamTarget.Y, m_Engine->m_CamPos.Y - m_Engine->m_CamTarget.Y,
m_Engine->m_CamPos.Z-m_Engine->m_CamTarget.Z m_Engine->m_CamPos.Z - m_Engine->m_CamTarget.Z);
);
m_CameraDistance = offsetVec3.getLength(); m_CameraDistance = offsetVec3.getLength();
m_Yaw = atan2(offsetVec3.X, offsetVec3.Z); m_Yaw = atan2(offsetVec3.X, offsetVec3.Z);
m_Pitch = asin(-offsetVec3.Y); m_Pitch = asin(-offsetVec3.Y);
setNewCameraPosition(); setNewCameraPosition();
} } else {
else {
// Revolve camera around object. // Revolve camera around object.
// increments of 120 pixels * PI are equal to 180 deg (PI radians): // increments of 120 pixels * PI are equal to 180 deg (PI radians):
f32 pitchDelta = dy / 120.0f; f32 pitchDelta = dy / 120.0f;
// (This old code which may make assumptions about view tends to lock on min/max) // (This old code which may make assumptions about view tends to lock on min/max)
// if(( m_Pitch - pitchDelta > ( PI - ( PI / 2 ))) && ( m_Pitch - pitchDelta < PI + ( PI/2 ))) // if ((m_Pitch - pitchDelta > (PI - (PI / 2))) && (m_Pitch - pitchDelta < PI + (PI/2)))
// m_Pitch -= dy / 120.0f; // m_Pitch -= dy / 120.0f;
m_Pitch += pitchDelta; m_Pitch += pitchDelta;
float minPitch = -PI/2.0f + PI/1000.0f; float minPitch = -PI / 2.0f + PI / 1000.0f;
float maxPitch = PI/2.0f - PI/1000.0f; float maxPitch = PI / 2.0f - PI / 1000.0f;
if (m_Pitch < minPitch) m_Pitch = minPitch; if (m_Pitch < minPitch)
else if (m_Pitch > maxPitch) m_Pitch = maxPitch; m_Pitch = minPitch;
else if (m_Pitch > maxPitch)
m_Pitch = maxPitch;
// std::wcerr << "pitch = " << m_Pitch << endl; // std::wcerr << "pitch = " << m_Pitch << endl;
m_Yaw += dx / 120.0f; m_Yaw += dx / 120.0f;

15
View.h
View File

@ -5,21 +5,20 @@
class Engine; class Engine;
class View : public irr::IEventReceiver class View : public irr::IEventReceiver {
{
private: private:
Engine *m_Engine; Engine* m_Engine;
irr::f32 m_Yaw, m_Pitch, m_CameraDistance; irr::f32 m_Yaw, m_Pitch, m_CameraDistance;
irr::core::vector2d<int> *m_LastMousePosition; irr::core::vector2d<int>* m_LastMousePosition;
bool m_RotMouse; bool m_RotMouse;
bool m_zUp; bool m_zUp;
void setNewCameraPosition(); void setNewCameraPosition();
void setNewCameraPosition(bool zUp); void setNewCameraPosition(bool zUp);
void setNewLightDirection( const irr::core::vector3df &cameraPosition ); void setNewLightDirection(const irr::core::vector3df& cameraPosition);
public: public:
View( Engine *engine ); View(Engine* engine);
~View(); ~View();
void setZUp(bool zUp); void setZUp(bool zUp);
void setCameraDistance(float cameraDistance); void setCameraDistance(float cameraDistance);
@ -27,7 +26,7 @@ public:
bool m_Shift; bool m_Shift;
// IEventReceiver // IEventReceiver
virtual bool OnEvent( const irr::SEvent &event ); virtual bool OnEvent(const irr::SEvent& event);
}; };
#endif // VIEW_H #endif // VIEW_H

2
etc/pushtmp.sh Executable file
View File

@ -0,0 +1,2 @@
#!/bin/bash
clang-format -style=file $1 > $2/$1

43
etc/quality.sh Executable file
View File

@ -0,0 +1,43 @@
#!/bin/sh
customDie() {
echo
echo "ERROR:"
echo "$1"
echo
echo
exit 1
}
project_dir_name=b3view
flag_file=b3view.pro
if [ ! -f $flag_file ]; then
if [ -f ../$flag_file ]; then
cd ..
fi
fi
if [ ! -f $flag_file ]; then
echo "ERROR: There was no $flag_file in working or parent directory."
exit 1
fi
echo "* rewriting .clang-format to avoid clang-format version issues..."
#rewriting avoids the following error:
#YAML:94:22: error: unknown key 'Delimiter'
# - Delimiter: pb
clang-format -style=WebKit -dump-config > .clang-format
dump_dest=/tmp/$project_dir_name
if [ -d "$dump_dest" ]; then
rm -Rf "$dump_dest" || customDie "Cannot remove old $dump_dest"
fi
mkdir "$dump_dest" || customDie "Cannot mkdir $dump_dest"
chmod +x ./etc/pushtmp.sh
echo "* writing $dump_dest using .clang-format..."
find -maxdepth 1 -name "*.cpp" -exec ./etc/pushtmp.sh {} "$dump_dest" \;
find -maxdepth 1 -name "*.h" -exec ./etc/pushtmp.sh {} "$dump_dest" \;
if [ -f "`command -v meld`" ]; then
meld `pwd` "$dump_dest"
else
echo "You do not have meld installed, so you'll have to diff"
echo "against manually to see style issues, such as:"
echo "diff -r \"`pwd`\" \"$dump_dest\""
fi
echo "Done."

View File

@ -298,7 +298,7 @@ Environment(env), Driver(nullptr), tt_face(nullptr), GlobalKerningWidth(0), Glob
if (Driver) if (Driver)
Driver->grab(); Driver->grab();
setInvisibleCharacters ( L" " ); setInvisibleCharacters (L" ");
// Glyphs isn't reference counted, so don't try to delete when we free the array. // Glyphs isn't reference counted, so don't try to delete when we free the array.
Glyphs.set_free_when_destroyed(false); Glyphs.set_free_when_destroyed(false);
@ -659,7 +659,7 @@ core::vector2di CGUITTFont::getKerning(const wchar_t thisLetter, const wchar_t p
return ret; return ret;
} }
void CGUITTFont::setInvisibleCharacters( const wchar_t *s ) void CGUITTFont::setInvisibleCharacters(const wchar_t *s)
{ {
Invisible = s; Invisible = s;
} }

View File

@ -1,6 +1,6 @@
#include <string.h>
#include <malloc.h> #include <malloc.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h>
#include "Engine.h" #include "Engine.h"
@ -9,58 +9,56 @@ using std::wstring;
using namespace irr; using namespace irr;
using namespace irr::core; using namespace irr::core;
wchar_t * getWideCharString( char *str ); wchar_t* getWideCharString(char* str);
#ifdef WIN32 #ifdef WIN32
#include <Windows.h> #include <Windows.h>
int WINAPI WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow ) int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
#else #else
int main( int argc, char **argv ) int main(int argc, char** argv)
#endif #endif
{ {
// Parse commandline to check if a filename argument has been passed // Parse commandline to check if a filename argument has been passed
#ifdef WIN32 #ifdef WIN32
int argc; int argc;
char **argv; char** argv;
LPWSTR *args; LPWSTR* args;
args = CommandLineToArgvW( GetCommandLineW(), &argc ); args = CommandLineToArgvW(GetCommandLineW(), &argc);
argv = ( char ** ) malloc( sizeof( char * ) * argc ); argv = (char**)malloc(sizeof(char*) * argc);
for( int index = 0; index < argc; index ++ ) for (int index = 0; index < argc; index++) {
{ int argumentBufferLength = wcslen(args[index]) + 1;
int argumentBufferLength = wcslen( args[index] ) + 1; argv[index] = (char*)malloc(sizeof(char) * argumentBufferLength);
argv[index] = ( char * ) malloc( sizeof( char ) * argumentBufferLength ); sprintf_s(argv[index], argumentBufferLength, "%ws", args[index]);
sprintf_s( argv[index], argumentBufferLength, "%ws", args[index] );
} }
LocalFree( args ); LocalFree(args);
#endif #endif
Engine *engine = new Engine(); Engine* engine = new Engine();
if( argc >= 2 ) if (argc >= 2) {
{ wchar_t* initialFileName = getWideCharString(argv[1]);
wchar_t *initialFileName = getWideCharString( argv[1] ); engine->loadMesh(wstring(initialFileName));
engine->loadMesh( wstring( initialFileName )); free(initialFileName);
free( initialFileName );
} }
// else //else
// engine->loadMesh( L"test.b3d" ); // engine->loadMesh(L"test.b3d");
engine->run(); engine->run();
delete engine; delete engine;
#ifdef WIN32 #ifdef WIN32
for( int index = 0; index < argc; index ++ ) for (int index = 0; index < argc; index++)
free( argv[index] ); free(argv[index]);
free( argv ); free(argv);
#endif #endif
} }
wchar_t * getWideCharString( char *str ) wchar_t* getWideCharString(char* str)
{ {
wchar_t *dest = static_cast<wchar_t *>(malloc(sizeof(wchar_t) * (strlen(str) + 1))); wchar_t* dest = static_cast<wchar_t*>(malloc(sizeof(wchar_t) * (strlen(str) + 1)));
size_t resultSize = mbstowcs(nullptr, str, strlen(str)); size_t resultSize = mbstowcs(nullptr, str, strlen(str));
mbstowcs(dest, str, strlen(str)); mbstowcs(dest, str, strlen(str));
@ -69,4 +67,3 @@ wchar_t * getWideCharString( char *str )
return dest; return dest;
} }