// Copyright (C) 2008-2012 Christian Stehno, Colin MacDonald // No rights reserved: this software is in the public domain. #include "testUtils.h" using namespace irr; namespace{ class MyEventReceiver : public IEventReceiver { public: // This is the one method that we have to implement virtual bool OnEvent(const SEvent& event) { // Remember whether each key is down or up if (event.EventType == EET_KEY_INPUT_EVENT) KeyIsDown[event.KeyInput.Key] = event.KeyInput.PressedDown; return false; } // This is used to check whether a key is being held down virtual bool IsKeyDown(EKEY_CODE keyCode) const { return KeyIsDown[keyCode]; } MyEventReceiver() { for (u32 i=0; i (160, 120)); if (!device) return true; // No error if device does not exist video::IVideoDriver* driver = device->getVideoDriver(); scene::ISceneManager* smgr = device->getSceneManager(); stabilizeScreenBackground(driver); scene::IMetaTriangleSelector * meta = smgr->createMetaTriangleSelector(); device->getFileSystem()->addFileArchive("../media/map-20kdm2.pk3"); scene::IAnimatedMesh* q3levelmesh = smgr->getMesh("20kdm2.bsp"); if (q3levelmesh) { scene::ISceneNode* q3node = smgr->addOctreeSceneNode(q3levelmesh->getMesh(0)); q3node->setPosition(core::vector3df(-1350,-130,-1400)); scene::ITriangleSelector * selector = smgr->createOctreeTriangleSelector(q3levelmesh->getMesh(0), q3node, 128); meta->addTriangleSelector(selector); selector->drop(); } scene::ICameraSceneNode* camera = smgr->addCameraSceneNode(); camera->setPosition(core::vector3df(-100,50,-150)); camera->updateAbsolutePosition(); camera->setTarget(camera->getAbsolutePosition() + core::vector3df(0, 0, 20)); device->getCursorControl()->setVisible(false); enum { MAX_TRIANGLES = 4096, // Large to test getting all the triangles BOX_SIZE1 = 300, BOX_SIZE2 = 50 }; core::triangle3df triangles[MAX_TRIANGLES]; core::vector3df boxPosition(camera->getAbsolutePosition()); video::SMaterial unlit; unlit.Lighting = false; unlit.Thickness = 3.f; unlit.PolygonOffsetSlopeScale= -1.f; unlit.PolygonOffsetDepthBias = -1.f; bool result = true; { camera->setPosition(core::vector3df(-620,-20,550)); driver->beginScene(video::ECBF_COLOR | video::ECBF_DEPTH, video::SColor(0)); smgr->drawAll(); core::aabbox3df box(boxPosition.X - BOX_SIZE1, boxPosition.Y - BOX_SIZE1, boxPosition.Z - BOX_SIZE1, boxPosition.X + BOX_SIZE1, boxPosition.Y + BOX_SIZE1, boxPosition.Z + BOX_SIZE1); driver->setTransform(video::ETS_WORLD, core::matrix4()); driver->setMaterial(unlit); driver->draw3DBox(box, video::SColor(255, 0, 255, 0)); if(meta) { s32 found; meta->getTriangles(triangles, MAX_TRIANGLES, found, box); while(--found >= 0) driver->draw3DTriangle(triangles[found], video::SColor(255, 255, 0, 0)); } driver->endScene(); result &= takeScreenshotAndCompareAgainstReference(driver, "-octree_select1.png"); } { camera->setPosition(core::vector3df(120,40,50)); driver->beginScene(video::ECBF_COLOR | video::ECBF_DEPTH, video::SColor(0)); smgr->drawAll(); core::aabbox3df box(boxPosition.X - BOX_SIZE2, boxPosition.Y - BOX_SIZE2, boxPosition.Z - BOX_SIZE2, boxPosition.X + BOX_SIZE2, boxPosition.Y + BOX_SIZE2, boxPosition.Z + BOX_SIZE2); driver->setTransform(video::ETS_WORLD, core::matrix4()); driver->setMaterial(unlit); driver->draw3DBox(box, video::SColor(255, 0, 255, 0)); if(meta) { s32 found; meta->getTriangles(triangles, MAX_TRIANGLES, found, box); while(--found >= 0) driver->draw3DTriangle(triangles[found], video::SColor(255, 255, 0, 0)); } driver->endScene(); result &= takeScreenshotAndCompareAgainstReference(driver, "-octree_select2.png"); } meta->drop(); device->closeDevice(); device->run(); device->drop(); return result; } //! Tests using triangle selector bool triangle() { IrrlichtDevice *device = createDevice (video::EDT_OPENGL, core::dimension2d < u32 > (160, 120)); if (!device) return true; // No error if device does not exist MyEventReceiver receiver; device->setEventReceiver(&receiver); video::IVideoDriver* driver = device->getVideoDriver(); scene::ISceneManager* smgr = device->getSceneManager(); stabilizeScreenBackground(driver); scene::IMetaTriangleSelector * meta = smgr->createMetaTriangleSelector(); scene::IAnimatedMesh * mesh = smgr->getMesh("../media/sydney.md2"); scene::IAnimatedMeshSceneNode * sydney = smgr->addAnimatedMeshSceneNode( mesh ); if (sydney) { sydney->setPosition(core::vector3df(15, -10, 15)); sydney->setMaterialFlag(video::EMF_LIGHTING, false); sydney->setMD2Animation ( scene::EMAT_STAND ); sydney->setAnimationSpeed(0.f); sydney->setMaterialTexture( 0, driver->getTexture("../media/sydney.bmp") ); scene::ITriangleSelector * selector = smgr->createTriangleSelector(sydney->getMesh()->getMesh(0), sydney); meta->addTriangleSelector(selector); selector->drop(); } scene::ICameraSceneNode* camera = smgr->addCameraSceneNodeFPS(); camera->setPosition(core::vector3df(70,0,-30)); camera->updateAbsolutePosition(); camera->setTarget(camera->getAbsolutePosition() + core::vector3df(-20, 0, 20)); device->getCursorControl()->setVisible(false); enum { MAX_TRIANGLES = 5000, // Large to test getting all the triangles BOX_SIZE = 30 }; core::triangle3df triangles[MAX_TRIANGLES]; core::vector3df boxPosition(0,0,0); video::SMaterial unlit; unlit.Lighting = false; unlit.Thickness = 3.f; unlit.PolygonOffsetSlopeScale= -1.f; unlit.PolygonOffsetDepthBias = -1.f; bool result = true; { driver->beginScene(video::ECBF_COLOR | video::ECBF_DEPTH, video::SColor(0xff00ffff)); smgr->drawAll(); core::aabbox3df box(boxPosition.X - BOX_SIZE, boxPosition.Y - BOX_SIZE, boxPosition.Z - BOX_SIZE, boxPosition.X + BOX_SIZE, boxPosition.Y + BOX_SIZE, boxPosition.Z + BOX_SIZE); driver->setTransform(video::ETS_WORLD, core::matrix4()); driver->setMaterial(unlit); driver->draw3DBox(box, video::SColor(255, 0, 255, 0)); if(meta) { s32 found; meta->getTriangles(triangles, MAX_TRIANGLES, found, box); while(--found >= 0) driver->draw3DTriangle(triangles[found], video::SColor(255, 255, 0, 0)); } driver->endScene(); result &= takeScreenshotAndCompareAgainstReference(driver, "-tri_select1.png"); } { boxPosition.Z -= 10.f; driver->beginScene(video::ECBF_COLOR | video::ECBF_DEPTH, video::SColor(0xff00ffff)); smgr->drawAll(); core::aabbox3df box(boxPosition.X - BOX_SIZE, boxPosition.Y - BOX_SIZE, boxPosition.Z - BOX_SIZE, boxPosition.X + BOX_SIZE, boxPosition.Y + BOX_SIZE, boxPosition.Z + BOX_SIZE); driver->setTransform(video::ETS_WORLD, core::matrix4()); driver->setMaterial(unlit); driver->draw3DBox(box, video::SColor(255, 0, 255, 0)); if(meta) { s32 found; meta->getTriangles(triangles, MAX_TRIANGLES, found, box); while(--found >= 0) driver->draw3DTriangle(triangles[found], video::SColor(255, 255, 0, 0)); } driver->endScene(); result &= takeScreenshotAndCompareAgainstReference(driver, "-tri_select2.png"); } { boxPosition.Z -= 20.f; driver->beginScene(video::ECBF_COLOR | video::ECBF_DEPTH, video::SColor(0xff00ffff)); smgr->drawAll(); core::aabbox3df box(boxPosition.X - BOX_SIZE, boxPosition.Y - BOX_SIZE, boxPosition.Z - BOX_SIZE, boxPosition.X + BOX_SIZE, boxPosition.Y + BOX_SIZE, boxPosition.Z + BOX_SIZE); driver->setTransform(video::ETS_WORLD, core::matrix4()); driver->setMaterial(unlit); driver->draw3DBox(box, video::SColor(255, 0, 255, 0)); if(meta) { s32 found; meta->getTriangles(triangles, MAX_TRIANGLES, found, box); while(--found >= 0) driver->draw3DTriangle(triangles[found], video::SColor(255, 255, 0, 0)); } driver->endScene(); result &= takeScreenshotAndCompareAgainstReference(driver, "-tri_select3.png"); } meta->drop(); device->closeDevice(); device->run(); device->drop(); return result; } } // Tests need not be accurate, as we just need to include at least // the triangles that match the criteria. But we try to be as close // as possible of course, to reduce the collision checks done afterwards bool triangleSelector(void) { bool result = true; result &= octree(); result &= triangle(); return result; }