1
General discussions / SFML with gtkmm
« on: April 25, 2009, 07:58:04 pm »
I've been playing around with gtkmm and decided to create a SFML widget, after digging a lot through the documentation of both gtkmm and SFML and also looking at http://www.sfml-dev.org/forum/viewtopic.php?t=282 I managed to stitch something together.
However, I am fairly new to C++, gtkmm and SFML and I do not really understand the internals of SFML so I was wondering if there's any mistakes I've made. Basically I'm just looking for some constructive criticism.
Thank you.
SFMLWidget.h
SFMLWidget.cpp
However, I am fairly new to C++, gtkmm and SFML and I do not really understand the internals of SFML so I was wondering if there's any mistakes I've made. Basically I'm just looking for some constructive criticism.
Thank you.
SFMLWidget.h
Code: [Select]
#include <SFML/Graphics.hpp>
#include <gdk/gdkwin32.h>
#include <gdk/gdk.h>
#include <gdkmm/general.h>
#include <gtkmm.h>
class SFMLWidget : public Gtk::Widget, public sf::RenderWindow
{
private:
sf::VideoMode m_vMode;
virtual void on_size_request(Gtk::Requisition* requisition);
virtual void on_size_allocate(Gtk::Allocation& allocation);
virtual void on_map();
virtual void on_unmap();
virtual void on_realize();
virtual void on_unrealize();
virtual bool on_idle();
virtual bool on_expose_event(GdkEventExpose* event);
void DrawObjects();
Glib::RefPtr<Gdk::Window> m_refGdkWindow;
sf::Image m_tempImage;
sf::Sprite m_tempSprite;
public:
SFMLWidget(sf::VideoMode Mode);
virtual ~SFMLWidget();
};
SFMLWidget.cpp
Code: [Select]
#include "SFMLWidget.h"
void SFMLWidget::DrawObjects()
{
this->Draw(m_tempSprite);
}
bool SFMLWidget::on_idle()
{
if(m_refGdkWindow)
{
DrawObjects();
this->Display();
}
return true;
}
SFMLWidget::SFMLWidget(sf::VideoMode Mode)
: sf::RenderWindow(Mode, "")
{
set_flags(Gtk::NO_WINDOW);
m_tempImage.LoadFromFile("gtk_logo.png");
m_tempSprite.SetImage(m_tempImage);
m_tempSprite.SetPosition(50, 50);
Glib::signal_idle().connect( sigc::mem_fun(*this, &SFMLWidget::on_idle) );
}
SFMLWidget::~SFMLWidget()
{
}
void SFMLWidget::on_size_request(Gtk::Requisition* requisition)
{
*requisition = Gtk::Requisition();
requisition->width = this->GetWidth();
requisition->height = this->GetHeight();
}
void SFMLWidget::on_size_allocate(Gtk::Allocation& allocation)
{
//Do something with the space that we have actually been given:
//(We will not be given heights or widths less than we have requested, though
//we might get more)
this->set_allocation(allocation);
if(m_refGdkWindow)
{
m_refGdkWindow->move_resize(allocation.get_x(), allocation.get_y(), allocation.get_width(), allocation.get_height() );
this->SetSize(allocation.get_width(), allocation.get_height());
}
}
void SFMLWidget::on_map()
{
Gtk::Widget::on_map();
}
void SFMLWidget::on_unmap()
{
Gtk::Widget::on_unmap();
}
void SFMLWidget::on_realize()
{
Gtk::Widget::on_realize();
if(!m_refGdkWindow)
{
//Create the GdkWindow:
GdkWindowAttr attributes;
memset(&attributes, 0, sizeof(attributes));
Gtk::Allocation allocation = get_allocation();
//Set initial position and size of the Gdk::Window:
attributes.x = allocation.get_x();
attributes.y = allocation.get_y();
attributes.width = allocation.get_width();
attributes.height = allocation.get_height();
attributes.event_mask = get_events () | Gdk::EXPOSURE_MASK;
attributes.window_type = GDK_WINDOW_CHILD;
attributes.wclass = GDK_INPUT_OUTPUT;
m_refGdkWindow = Gdk::Window::create(get_window() /* parent */, &attributes,
GDK_WA_X | GDK_WA_Y);
unset_flags(Gtk::NO_WINDOW);
set_window(m_refGdkWindow);
//set colors
modify_bg(Gtk::STATE_NORMAL , Gdk::Color("red"));
modify_fg(Gtk::STATE_NORMAL , Gdk::Color("blue"));
//make the widget receive expose events
m_refGdkWindow->set_user_data(gobj());
///Reference: http://www.nabble.com/Win32-HWND-td20494257.html
///This is platform specific, compiling on Linux/MacOS will require a different Window Handle
this->sf::RenderWindow::Create(reinterpret_cast<HWND>(GDK_WINDOW_HWND(m_refGdkWindow->gobj())));
}
}
void SFMLWidget::on_unrealize()
{
m_refGdkWindow.clear();
//Call base class:
Gtk::Widget::on_unrealize();
}
bool SFMLWidget::on_expose_event(GdkEventExpose* event)
{
if(m_refGdkWindow)
{
DrawObjects();
this->Display();
}
return true;
}