Using SFML 2.1 for Window, Input, ... Example(Working)

Anything and everything that's related to OGRE or the wider graphics field that doesn't fit into the other forums.
Post Reply
zester
Gnoblar
Posts: 21
Joined: Mon May 30, 2011 6:09 am
x 4

Using SFML 2.1 for Window, Input, ... Example(Working)

Post by zester »

Here is an example on how to use SFML v2.1 for Window, Input, ... using Ogre v1.9
Note: Currently this only works on linux, changes to this line of code maybe required for other platforms. "misc["currentGLContext"] = Ogre::String("true");"

Performance appears to be very good.

I tried briefly to draw 2D Graphics via SFML but I wasn't able to get anything to show-up, I will have to look further into it.

The SFML related code is actually very short and simple, I did however provide a full Ogre example with a frame-listener, etc. But 99% of the provided code in the example isn't needed.

Thanks to this Ogre/GLFW Example http://www.ogre3d.org/forums/viewtopic.php?f=2&t=69853 I was able to get this working.

I hope you find this useful.

Image

Code: Select all

// g++ main.cpp -o main `pkg-config --libs --cflags OGRE` -lsfml-window -lsfml-graphics -lsfml-system -lGL

// SFML v2.1 Includes
#include <SFML/Window.hpp>
#include <SFML/OpenGL.hpp>
#include <SFML/Graphics.hpp>

// Ogre v1.9 Includes
#include <Ogre.h>
#include <OgreFrameListener.h>

using namespace Ogre;
     
//
class MyFrameListener : public Ogre::FrameListener {
public:
  bool frameStarted (const FrameEvent &evt);
  bool frameEnded   (const FrameEvent &evt);
  bool frameRenderingQueued  (const FrameEvent &evt);
};
     
//
bool MyFrameListener::frameStarted(const FrameEvent &evt) {
  //std::cout << "Frame Started" << std::endl;
  return true;
}
     
//
bool MyFrameListener::frameEnded(const FrameEvent &evt) {
  //std::cout << "Frame Ended" << std::endl;
  return true;
}
     
//
bool MyFrameListener::frameRenderingQueued(const FrameEvent &evt) {
  //std::cout << "Frame Queued" << std::endl;
  return true;
}

int main()
{
  // create the window
  sf::RenderWindow window(sf::VideoMode(800, 600), "Ogre3D v1.9 and SFML v2.1", sf::Style::Default, sf::ContextSettings(32));
  
  // Create an instance of the OGRE Root Class
  Ogre::Root* ogreRoot = new Ogre::Root;
  
  // Configures the application
  if (!ogreRoot->restoreConfig())
    ogreRoot->showConfigDialog();
    ogreRoot->saveConfig();
  
  // Create Rendering System, but don't initialise it.
  ogreRoot->setRenderSystem(ogreRoot->getAvailableRenderers()[0]);
  ogreRoot->initialise(false);
  
  //
  Ogre::NameValuePairList misc;
  misc["currentGLContext"] = Ogre::String("true");
  
  // Create a render window | Note: Window Title and Size are not important here.
  Ogre::RenderWindow* ogreWindow = ogreRoot->createRenderWindow("Ogre Window", 800, 600, false, &misc);
  ogreWindow->setVisible(true);
  
  // Create Render Target
  Ogre::RenderTarget *ogreRenderTarget = ogreWindow;

  // Create Scene Manager
  Ogre::SceneManager* ogreSceneMgr = ogreRoot->createSceneManager(Ogre::ST_GENERIC);

  // Create a new camera
  Ogre::Camera* ogreCamera = ogreSceneMgr->createCamera("Camer0");
  ogreCamera->setPosition(Ogre::Vector3(0,0,10));
  ogreCamera->lookAt(Ogre::Vector3(0,0,-300));
  ogreCamera->setNearClipDistance(5);

  // Create OGRE Viewport and Set Background Colour
  Ogre::Viewport* vp = ogreWindow->addViewport(ogreCamera);
  vp->setBackgroundColour(Ogre::ColourValue(0,0,0));

  // Use the viewport to set the aspect ratio of the camera
  ogreCamera->setAspectRatio(Ogre::Real(vp->getActualWidth()) / Ogre::Real(vp->getActualHeight()));
  
  // Add our model to our resources and index it
  Ogre::ResourceGroupManager::getSingleton().addResourceLocation("media/packs/Sinbad.zip", "Zip");
  Ogre::ResourceGroupManager::getSingleton().addResourceLocation("media/models/", "FileSystem");
  Ogre::ResourceGroupManager::getSingleton().initialiseAllResourceGroups();
  
  // Set Scene Ambient Light.
  ogreSceneMgr->setAmbientLight(Ogre::ColourValue(0.5f, 0.5f, 0.5f));
  
  // Create a new light.
  Ogre::Light* light = ogreSceneMgr->createLight("Light0");
  light->setPosition(20.0f, 80.0f, 50.0f);

  // Create an instance of our model and add it to the scene
  Ogre::Entity* ent = ogreSceneMgr->createEntity("Sinbad.mesh");
  Ogre::SceneNode* entNode = ogreSceneMgr->createSceneNode("Character0");
  entNode->attachObject(ent);
  ogreSceneMgr->getRootSceneNode()->addChild(entNode);
  entNode->setPosition(0,0,0);
  
  // Create an instance of the MyFrameListener Class and add it to the root object
  MyFrameListener* myListener = new MyFrameListener();
  ogreRoot->addFrameListener(myListener);

  // run the main loop
  bool running = true;
  while (running)
  {
    //Ogre::WindowEventUtilities::messagePump();
    
    // handle events
    sf::Event event;
    while (window.pollEvent(event))
    {
      if (event.type == sf::Event::Closed)
      {
	// end the program
	running = false;
      }
      else if (event.type == sf::Event::Resized)
      {
	// adjust the viewport when the window is resized
	//glViewport(0, 0, event.size.width, event.size.height);
      }
    }
    
    // clear the buffers
    //glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    window.clear();
    
    // draw...
    ogreRoot->renderOneFrame();

    // end the current frame (internally swaps the front and back buffers)
    window.display();
  }
  
  // release resources...
  delete myListener;
  delete ogreRoot;
    
  return 0;
}
User avatar
Klaim
Old One
Posts: 2565
Joined: Sun Sep 11, 2005 1:04 am
Location: Paris, France
x 56
Contact:

Re: Using SFML 2.1 for Window, Input, ... Example(Working)

Post by Klaim »

Nice!

The SFML display problem might be because the transforms are all relative so you might display SFML things in a space that is not the camera space.

By the way, you might want to read this if you didn't already: http://www.ogre3d.org/forums/viewtopic.php?f=4&t=79237
zester
Gnoblar
Posts: 21
Joined: Mon May 30, 2011 6:09 am
x 4

Re: Using SFML 2.1 for Window, Input, ... Example(Working)

Post by zester »

Klaim wrote:Nice!

The SFML display problem might be because the transforms are all relative so you might display SFML things in a space that is not the camera space.

By the way, you might want to read this if you didn't already: http://www.ogre3d.org/forums/viewtopic.php?f=4&t=79237
Thanks, I will have to check, you might be right that the SFML stuff is there just not in camera space. I have seen the SDL2 post and completely agree with the OP, Ogre needs to be just a Rendering Engine and not handle Windowing.


I wrote the following snippet, to do away with the "Ogre Config Dialog" I will have to modify this and test it with the SFML example I posted to make sure there is no problems.

Code: Select all

#if defined OIS_LINUX_PLATFORM
  mRoot->loadPlugin("/usr/lib/OGRE/Plugin_ParticleFX");
  mRoot->loadPlugin("/usr/lib/OGRE/Plugin_CgProgramManager");
  mRoot->loadPlugin("/usr/lib/OGRE/Plugin_OctreeSceneManager");
  mRoot->loadPlugin("/usr/lib/OGRE/Plugin_PCZSceneManager");
  mRoot->loadPlugin("/usr/lib/OGRE/Plugin_OctreeZone");
  mRoot->loadPlugin("/usr/lib/OGRE/Plugin_BSPSceneManager");
  mRoot->loadPlugin("/usr/lib/OGRE/RenderSystem_GL");
  #endif

  Ogre::RenderSystemList::const_iterator renderers = mRoot->getAvailableRenderers().begin();

  while(renderers != mRoot->getAvailableRenderers().end())
  {
    Ogre::String rName = (*renderers)->getName();

    if (rName == "OpenGL Rendering Subsystem")
      break;

    renderers++;
  }

  Ogre::RenderSystem *renderSystem = *renderers;
  renderSystem->setConfigOption("Full Screen","No");
  renderSystem->setConfigOption("Video Mode","1024 x 768 @ 32-bit colour");
  renderSystem->setConfigOption("Display Frequency","50 Hz");
  renderSystem->setConfigOption("FSAA","16");
  renderSystem->setConfigOption("Fixed Pipeline Enabled","Yes");
  renderSystem->setConfigOption("RTT Preferred Mode","FBO");
  renderSystem->setConfigOption("VSync","No");
  renderSystem->setConfigOption("sRGB Gamma Conversion","No");

  mRoot->setRenderSystem(renderSystem); 

  // Create a render window
  mWindow =  mRoot->initialise(true, "MyGame v0.0.1");
zester
Gnoblar
Posts: 21
Joined: Mon May 30, 2011 6:09 am
x 4

Re: Using SFML 2.1 for Window, Input, ... Example(Working)

Post by zester »

I wasn't able to solve the problem with SFML Graphics and Ogre, I am positive its a bug in SFML as many others are having the same problem with "Irrlicht, Horde3D, ...",
instead, I just used MyGUI. There is a slight,dim,rapid flickering of the text that's slightly noticeable. Other than that everything seams to work really well.

Image

Includes

Code: Select all

#include "MyGUI.h"
#include "MyGUI_OgrePlatform.h"
For the GUI Elements (Note: add this after setting up your viewport)

Code: Select all

  //Ui Code
  MyGUI::Gui* mGUI;
  
  MyGUI::OgrePlatform* mPlatform = new MyGUI::OgrePlatform();
  mPlatform->initialise(ogreWindow, ogreSceneMgr);
  
  mGUI = new MyGUI::Gui();
  mGUI->initialise();

  MyGUI::ButtonPtr button = mGUI->createWidget<MyGUI::Button>("Button", 30, 30, 100, 26, MyGUI::Align::Default, "Main");
  button->setCaption("exit");
  
  // create an empty menu bar 
  MyGUI::MenuBar * menuBar = mGUI->createWidget<MyGUI::MenuBar>("MenuBar", 0, 0, mGUI->getViewWidth(), 25, MyGUI::Align::Default, "Overlapped");

  // add the "File" menu item (this is a button)
  MyGUI::MenuItem * fileItem = menuBar->addItem("File", MyGUI::MenuItemType::Popup);
  MyGUI::MenuItem * editItem = menuBar->addItem("Edit", MyGUI::MenuItemType::Popup);
  MyGUI::MenuItem * assetsItem = menuBar->addItem("Assets", MyGUI::MenuItemType::Popup);
  MyGUI::MenuItem * gameObjectItem = menuBar->addItem("GameObject", MyGUI::MenuItemType::Popup);
  MyGUI::MenuItem * componentItem = menuBar->addItem("Component", MyGUI::MenuItemType::Popup);
  MyGUI::MenuItem * windowItem = menuBar->addItem("Window", MyGUI::MenuItemType::Popup);
  MyGUI::MenuItem * helpItem = menuBar->addItem("Help", MyGUI::MenuItemType::Popup);

  // add a PopupMenu (which is a MenuCtrl) to the MenuItem (only one MenuCtrl per MenuItem)
  MyGUI::PopupMenu * popupMenu = fileItem->createItemChildT<MyGUI::PopupMenu>();

  // add MenuItems to the PopupMenu
  popupMenu->addItem("Open");
  popupMenu->addItem("",MyGUI::MenuItemType::Separator);
  popupMenu->addItem("Quit");

  MyGUI::PointerManager::getInstance().setVisible(false);
And for mouse handling

Code: Select all

if(event.type == sf::Event::MouseMoved)
{
    MyGUI::InputManager::getInstance().injectMouseMove(event.mouseMove.x, event.mouseMove.y, 0);
}
Release Resources

Code: Select all

mGUI->shutdown();
delete mGUI;
mGUI = 0;   
mPlatform->shutdown();
delete mPlatform;
mPlatform = 0;
cfn
Gnoblar
Posts: 9
Joined: Mon May 28, 2012 5:29 pm

Re: Using SFML 2.1 for Window, Input, ... Example(Working)

Post by cfn »

The example was quite useful to me, thanks.

Unfortunately the code you presented didn't work on Windows. The "currentGLContext" option seems to be ignored. This can be fixed by retrieving the context manually and set options accordingly. The code below works for me on Windows.

Code: Select all

	Ogre::NameValuePairList misc;
#ifdef _WIN32
	unsigned long winHandle = reinterpret_cast<unsigned long>(window.getSystemHandle());
	unsigned long winGlContext = reinterpret_cast<unsigned long>(wglGetCurrentContext());

	misc["externalWindowHandle"] = StringConverter::toString(winHandle);
	misc["externalGLContext"] = StringConverter::toString(winGlContext);
	misc["externalGLControl"] = String("True");
#else
	misc["currentGLContext"] = String("True");
#endif

	Ogre::RenderWindow* ogreWindow = ogreRoot->createRenderWindow("Ogre Window", 800, 600, false, &misc);
Also, I found out how to handle the resize events correctly.

Code: Select all

if (event.type == sf::Event::Resized) {
    ogreWindow->windowMovedOrResized();
    ogreCamera->setAspectRatio(Ogre::Real(event.size.width) / Ogre::Real(event.size.height));
}
scrawl
OGRE Expert User
OGRE Expert User
Posts: 1119
Joined: Sat Jan 01, 2011 7:57 pm
x 216

Re: Using SFML 2.1 for Window, Input, ... Example(Working)

Post by scrawl »

Also, I found out how to handle the resize events correctly.
Note that this is inconsistent in 1.8. On Windows, you need to use RenderWindow::windowMovedOrResized, while on linux, you need to use RenderWindow::resize.
This inconsistency has been fixed in 1.9, where RenderWindow::resize now works properly on all platforms.
oiram
Halfling
Posts: 87
Joined: Sun Dec 13, 2009 5:06 am
x 6

Re: Using SFML 2.1 for Window, Input, ... Example(Working)

Post by oiram »

Great work!
Could you post it to ogre wiki when it's done?
:mrgreen:
cfn
Gnoblar
Posts: 9
Joined: Mon May 28, 2012 5:29 pm

Re: Using SFML 2.1 for Window, Input, ... Example(Working)

Post by cfn »

scrawl wrote:
Also, I found out how to handle the resize events correctly.
Note that this is inconsistent in 1.8. On Windows, you need to use RenderWindow::windowMovedOrResized, while on linux, you need to use RenderWindow::resize.
This inconsistency has been fixed in 1.9, where RenderWindow::resize now works properly on all platforms.
Good to know that it should work with RenderWindow::resize, because it doesn't. :shock:

I'm using Ogre 1.9 (stable) and sfml 2.1 (stable). When calling ogre::RenderWindow::resize with the parameters of the sfml resize event the rendering window collapses to nothing. Ogre resizes the native window inside the resize method by calling the Windows api. This again triggers a sfml resize event with smaller dimensions than the previous. This seems to be caused by a different meaning of the render windows "size" in sfml and ogre. Ogre seems to use the size of the real window while sfml uses the size of the rendering area in the window.

However even if I adjust the size passed by sfml and pass those values, ogre doesn't react properly.
Resize.png
Resize.png (91.68 KiB) Viewed 4856 times
From top to bottom: Initial size; resized using RenderWindow::resize; resized using RenderWindow::windowMovedOrResized.
Nothing else than the single line that passes the new size to ogre was changed between those screenshots.
scrawl
OGRE Expert User
OGRE Expert User
Posts: 1119
Joined: Sat Jan 01, 2011 7:57 pm
x 216

Re: Using SFML 2.1 for Window, Input, ... Example(Working)

Post by scrawl »

Hm, what you're describing is exactly the problem that I've faced in 1.8, but should be fixed in 1.9.
Take a look at the code. It no longer resizes the window if mIsExternal is true. So this really shouldn't be happening anymore.
cfn
Gnoblar
Posts: 9
Joined: Mon May 28, 2012 5:29 pm

Re: Using SFML 2.1 for Window, Input, ... Example(Working)

Post by cfn »

Thanks for pointing to the code. It is in fact fixed and working with the OpenGL Rendering Subsystem, but the fix is not yet applied to the GL3+ renderer.
scrawl
OGRE Expert User
OGRE Expert User
Posts: 1119
Joined: Sat Jan 01, 2011 7:57 pm
x 216

Re: Using SFML 2.1 for Window, Input, ... Example(Working)

Post by scrawl »

Ah, that's a good point. Check if its fixed in the GL3 GSOC repo and otherwise feel free to make a pull request.
RaptorStudios
Gnoblar
Posts: 6
Joined: Mon Mar 31, 2014 8:12 pm

Re: Using SFML 2.1 for Window, Input, ... Example(Working)

Post by RaptorStudios »

Did you ever get the flickering to stop? It would really help out my game.
Post Reply