37 #include <boost/thread.hpp>
39 #define ERR_GEN LOG_STREAM(err, lg::general)
97 if(
size_t(index) ==
handlers.size()) {
101 if(
handlers[
size_t(index)]->requires_event_focus()) {
113 if(i !=
handlers.end() && (**i).requires_event_focus()) {
131 pump_monitors.push_back(
this);
136 std::remove(pump_monitors.begin(), pump_monitors.end(),
this),
137 pump_monitors.end());
142 event_contexts.push_back(
context());
147 assert(event_contexts.empty() ==
false);
148 event_contexts.pop_back();
153 has_joined_global_(false)
157 assert(!event_contexts.empty());
158 event_contexts.back().add_handler(
this);
174 join(event_contexts.back());
188 if(!members.empty()) {
201 for(std::deque<context>::reverse_iterator
i = event_contexts.rbegin();
i != event_contexts.rend(); ++
i) {
202 std::vector<sdl_handler *> &handlers = (*i).handlers;
203 if (
std::find(handlers.begin(), handlers.end(), parent) != handlers.end()) {
208 join(global_context);
215 if(!members.empty()) {
220 assert(event_contexts.empty() ==
false);
222 for(std::deque<context>::reverse_iterator
i = event_contexts.rbegin();
i != event_contexts.rend(); ++
i) {
223 if(
i->remove_handler(
this)) {
241 if(!members.empty()) {
251 if(!members.empty()) {
253 (*i)->leave_global();
264 if(event_contexts.empty() ==
false) {
265 event_contexts.back().set_focus(ptr);
271 if(event_contexts.empty()) {
279 const int foc_i = event_contexts.back().focused_handler;
288 sdl_handler *
const foc_hand = event_contexts.back().handlers[foc_i];
289 if(foc_hand == hand){
294 int back_i = event_contexts.back().handlers.size() - 1;
295 for(
int i=back_i;
i>=0; --
i) {
296 sdl_handler *
const thief_hand = event_contexts.back().handlers[
i];
302 event_contexts.back().delete_handler_index(foc_i);
303 event_contexts.back().add_handler(foc_hand);
305 return thief_hand == hand;
324 if ((a.type == SDL_WINDOWEVENT) &&
325 (a.window.event == SDL_WINDOWEVENT_RESIZED ||
326 a.window.event == SDL_WINDOWEVENT_SIZE_CHANGED ||
327 a.window.event == SDL_WINDOWEVENT_EXPOSED)) {
347 static int last_mouse_down = -1;
348 static int last_click_x = -1, last_click_y = -1;
350 SDL_Event temp_event;
352 int begin_ignoring = 0;
353 std::vector< SDL_Event >
events;
354 while(SDL_PollEvent(&temp_event)) {
358 if(!begin_ignoring && temp_event.type == SDL_WINDOWEVENT
359 && (temp_event.window.event == SDL_WINDOWEVENT_ENTER
360 || temp_event.window.event == SDL_WINDOWEVENT_FOCUS_GAINED))
362 begin_ignoring = poll_count;
363 }
else if(begin_ignoring > 0 &&
is_input(temp_event)) {
367 events.push_back(temp_event);
371 for(
int i=1;
i < begin_ignoring; ++
i){
374 ev_it = events.erase(ev_it);
381 bool resize_found =
false;
382 for(ev_it = events.begin(); ev_it != ev_end; ++ev_it){
383 SDL_Event &
event = *ev_it;
384 if (
event.type == SDL_WINDOWEVENT &&
385 event.window.event == SDL_WINDOWEVENT_RESIZED) {
387 last_resize_event =
event;
388 last_resize_event_used =
false;
394 if (resize_found || SDL_GetTicks() <= last_resize_event.window.timestamp +
resize_timeout) {
395 events.erase(std::remove_if(events.begin(), events.end(),
remove_on_resize), events.end());
396 }
else if(SDL_GetTicks() > last_resize_event.window.timestamp + resize_timeout && !
last_resize_event_used) {
398 last_resize_event_used =
true;
401 ev_end = events.end();
403 for(ev_it = events.begin(); ev_it != ev_end; ++ev_it){
404 SDL_Event &
event = *ev_it;
407 case SDL_WINDOWEVENT:
408 switch(
event.window.event) {
409 case SDL_WINDOWEVENT_ENTER:
410 case SDL_WINDOWEVENT_FOCUS_GAINED:
414 case SDL_WINDOWEVENT_LEAVE:
415 case SDL_WINDOWEVENT_FOCUS_LOST:
419 case SDL_WINDOWEVENT_RESIZED:
427 const std::vector<sdl_handler*>& event_handlers = (*i).handlers;
428 for(
size_t i1 = 0, i2 = event_handlers.size(); i1 != i2 && i1 < event_handlers.size(); ++i1) {
429 event_handlers[i1]->handle_window_event(
event);
432 const std::vector<sdl_handler*>& event_handlers = global_context.
handlers;
433 for(
size_t i1 = 0, i2 = event_handlers.size(); i1 != i2 && i1 < event_handlers.size(); ++i1) {
434 event_handlers[i1]->handle_window_event(
event);
441 case SDL_MOUSEMOTION: {
449 case SDL_MOUSEBUTTONDOWN: {
453 if(
event.button.button == SDL_BUTTON_LEFT) {
454 static const int DoubleClickTime = 500;
455 static const int DoubleClickMaxMove = 3;
456 if(last_mouse_down >= 0 && info.
ticks() - last_mouse_down < DoubleClickTime &&
457 abs(
event.button.x - last_click_x) < DoubleClickMaxMove &&
458 abs(
event.button.y - last_click_y) < DoubleClickMaxMove) {
459 SDL_UserEvent user_event;
462 user_event.data1 =
reinterpret_cast<void*
>(
event.button.x);
463 user_event.data2 =
reinterpret_cast<void*
>(
event.button.y);
464 ::SDL_PushEvent(reinterpret_cast<SDL_Event*>(&user_event));
466 last_mouse_down = info.
ticks();
467 last_click_x =
event.button.x;
468 last_click_y =
event.button.y;
476 const std::vector<sdl_handler*>& event_handlers = (*i).handlers;
477 for( std::vector<sdl_handler*>::const_iterator i1 = event_handlers.begin(); i1 != event_handlers.end(); ++i1) {
478 (*i1)->handle_event(
event);
486 if(
event.key.keysym.sym == SDLK_F4 && (
event.key.keysym.mod == KMOD_RALT ||
event.key.keysym.mod == KMOD_LALT)) {
494 #if defined(_X11) && !defined(__APPLE__)
495 case SDL_SYSWMEVENT: {
503 case SDL_SYSWMEVENT: {
515 const std::vector<sdl_handler*>& event_handlers = global_context.
handlers;
516 for(
size_t i1 = 0, i2 = event_handlers.size(); i1 != i2 && i1 < event_handlers.size(); ++i1) {
517 event_handlers[i1]->handle_event(
event);
520 if(event_contexts.empty() ==
false) {
522 const std::vector<sdl_handler*>& event_handlers = event_contexts.back().handlers;
526 for(
size_t i1 = 0, i2 = event_handlers.size(); i1 != i2 && i1 < event_handlers.size(); ++i1) {
527 event_handlers[i1]->handle_event(
event);
534 for(
size_t i1 = 0, i2 = pump_monitors.size(); i1 != i2 && i1 < pump_monitors.size(); ++i1) {
535 pump_monitors[i1]->process(info);
541 if(event_contexts.empty() ==
false) {
543 const std::vector<sdl_handler*>& event_handlers = event_contexts.back().handlers;
547 for(
size_t i1 = 0, i2 = event_handlers.size(); i1 != i2 && i1 < event_handlers.size(); ++i1) {
548 event_handlers[i1]->process_event();
556 event.window.type = SDL_WINDOWEVENT;
557 event.window.event = SDL_WINDOWEVENT_RESIZED;
558 event.window.windowID = 0;
562 SDL_PushEvent(&event);
567 if(event_contexts.empty() ==
false) {
569 const std::vector<sdl_handler*>& event_handlers = event_contexts.back().handlers;
573 for(
size_t i1 = 0, i2 = event_handlers.size(); i1 != i2 && i1 < event_handlers.size(); ++i1) {
574 event_handlers[i1]->draw();
582 const std::vector<sdl_handler*>& event_handlers = (*i).handlers;
583 for(
size_t i1 = 0, i2 = event_handlers.size(); i1 != i2 && i1 < event_handlers.size(); ++i1) {
584 event_handlers[i1]->draw();
591 if(event_contexts.empty() ==
false) {
593 const std::vector<sdl_handler*>& event_handlers = event_contexts.back().handlers;
597 for(
size_t i1 = 0, i2 = event_handlers.size(); i1 != i2 && i1 < event_handlers.size(); ++i1) {
598 event_handlers[i1]->volatile_draw();
606 const std::vector<sdl_handler*>& event_handlers = (*i).handlers;
607 for(
size_t i1 = 0, i2 = event_handlers.size(); i1 != i2 && i1 < event_handlers.size(); ++i1) {
608 event_handlers[i1]->volatile_draw();
615 if(event_contexts.empty() ==
false) {
617 const std::vector<sdl_handler*>& event_handlers = event_contexts.back().handlers;
621 for(
size_t i1 = 0, i2 = event_handlers.size(); i1 != i2 && i1 < event_handlers.size(); ++i1) {
622 event_handlers[i1]->volatile_undraw();
629 if(event_contexts.empty() ==
false) {
631 const std::vector<sdl_handler*>& event_handlers = event_contexts.back().handlers;
633 for(
size_t i1 = 0, i2 = event_handlers.size(); i1 != i2 && i1 < event_handlers.size(); ++i1) {
634 event_handlers[i1]->process_help_string(mousex,mousey);
635 event_handlers[i1]->process_tooltip_string(mousex,mousey);
641 if(!
ticks_ && !(refresh_counter && ++*refresh_counter % refresh_rate)) {
642 ticks_ = ::SDL_GetTicks();
649 #define INPUT_MIN 0x300
650 #define INPUT_MAX 0x8FF
665 int num = SDL_PeepEvents(events, 100, SDL_PEEKEVENT, SDL_WINDOWEVENT, SDL_WINDOWEVENT);
666 for (
int i = 0;
i <
num; ++
i) {
667 if (events[
i].
type == SDL_WINDOWEVENT &&
668 events[
i].window.event == SDL_WINDOWEVENT_RESIZED) {
void raise_resize_event()
void raise_volatile_undraw_event()
void discard_input()
Discards all input events.
static thandler * handler
GLint GLint GLsizei GLsizei GLsizei depth
std::vector< events::sdl_handler * > sdl_handler_vector
bool last_resize_event_used
GLuint GLuint GLsizei GLenum type
int ticks(unsigned *refresh_counter=nullptr, unsigned refresh_rate=1)
virtual void leave_global()
static CVideo & get_singleton()
virtual void join_same(sdl_handler *parent)
const Uint32 resize_timeout
void raise_draw_all_event()
static bool remove_on_resize(const SDL_Event &a)
void focus_handler(const sdl_handler *ptr)
void set_focus(bool focus)
std::vector< sdl_handler * > handlers
void raise_volatile_draw_all_event()
GLboolean GLboolean GLboolean GLboolean a
void set_focus(const sdl_handler *ptr)
static const boost::thread::id main_thread
typedef int(WINAPI *PFNWGLRELEASEPBUFFERDCARBPROC)(HPBUFFERARB hPbuffer
void delete_handler_index(size_t handler)
#define DOUBLE_CLICK_EVENT
void raise_process_event()
static void quit_to_desktop()
#define SHOW_HELPTIP_EVENT
bool is_input(const SDL_Event &event)
Is the event an input event?
void raise_help_string_event(int mousex, int mousey)
void handle_system_event(const SDL_Event &)
virtual bool requires_event_focus(const SDL_Event *=nullptr) const
void raise_volatile_draw_event()
virtual std::vector< sdl_handler * > handler_members()
std::deque< context > event_contexts
Handling of system events.
std::vector< pump_monitor * > pump_monitors
sdl_handler(const bool auto_join=true)
bool find(E event, F functor)
Tests whether an event handler is available.
void add_handler(sdl_handler *ptr)
bool has_focus(const sdl_handler *hand, const SDL_Event *event)
Standard logging facilities (interface).
std::pair< int, int > resize_dimensions
const std::string remove
remove directive
SDL_Event last_resize_event
void update_framebuffer()
static void handle_system_event(const SDL_Event &event)
Frees resources when a notification disappears, switches user to the wesnoth window if the notificati...
bool remove_handler(sdl_handler *ptr)
virtual void join_global()
HOTKEY_COMMAND get_id(const std::string &command)
returns get_hotkey_command(command).id