/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ /*************************************************************************** * window.cc * * Sun Oct 9 13:11:53 CEST 2011 * Copyright 2011 Bent Bisballe Nyeng * deva@aasimon.org ****************************************************************************/ /* * This file is part of DrumGizmo. * * DrumGizmo is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * DrumGizmo is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with DrumGizmo; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. */ #include "window.h" #include "painter.h" #include #include #include #include #ifndef PUGL #ifdef X11 #include "nativewindow_x11.h" #endif/*X11*/ #ifdef WIN32 #include "nativewindow_win32.h" #endif/*WIN32*/ #else #include "nativewindow_pugl.h" #endif GUI::Window::Window() : Widget(NULL), wpixbuf(100, 100), back(":bg.png"), logo(":logo.png") { _x = _y = 100; _width = wpixbuf.width; _height = wpixbuf.height; refcount = 0; max_refcount = 0; _keyboardFocus = this; _buttonDownFocus = NULL; _mouseFocus = NULL; #ifndef PUGL #ifdef X11 native = new NativeWindowX11(this); #endif/*X11*/ #ifdef WIN32 native = new NativeWindowWin32(this); #endif/*WIN32*/ #else/*Use pugl*/ native = new NativeWindowPugl(this); #endif eventhandler = new GUI::EventHandler(native, this); } GUI::Window::~Window() { delete native; delete eventhandler; } GUI::EventHandler *GUI::Window::eventHandler() { return eventhandler; } void GUI::Window::setCaption(std::string caption) { native->setCaption(caption); } void GUI::Window::repaintEvent(GUI::RepaintEvent *e) { if(!visible()) return; Painter p(this); p.drawImageStretched(0,0, &back, width(), height()); p.drawImage(width() - logo.width(), height() - logo.height(), &logo); } void GUI::Window::setFixedSize(int w, int h) { native->setFixedSize(w, h); resize(w,h); } void GUI::Window::resize(int width, int height) { if(width < 1 || height < 1) return; // This needs to be done on all platoforms when setFixedSize is introduced. //#ifdef WIN32 // Fix to force buffer size reallocation // FIXME: This should've been done indirectly through a WM_SIZE message in the // EventHandler... resized(width, height); //#endif Widget::resize(width, height); native->resize(width, height); } void GUI::Window::move(size_t x, size_t y) { native->move(x, y); // Make sure widget corrds are updated. Widget::move(x, y); } size_t GUI::Window::x() { return _x; } size_t GUI::Window::y() { return _y; } size_t GUI::Window::width() { return _width; } size_t GUI::Window::height() { return _height; } size_t GUI::Window::windowX() { return 0; } size_t GUI::Window::windowY() { return 0; } void GUI::Window::show() { repaint_r(NULL); native->show(); } void GUI::Window::hide() { native->hide(); } GUI::Window *GUI::Window::window() { return this; } void GUI::Window::beginPaint() { refcount++; if(refcount > max_refcount) max_refcount = refcount; } void GUI::Window::endPaint() { if(refcount) refcount--; if(!refcount) { if(max_refcount > 1) { // Did we go deep enough for a buffer update? updateBuffer(); redraw(); } max_refcount = 0; } } void GUI::Window::updateBuffer() { DEBUG(window, "Updating buffer\n"); memset(wpixbuf.buf, 0, wpixbuf.width * wpixbuf.height * 3); std::vector pl = getPixelBuffers(); std::vector::iterator pli = pl.begin(); while(pli != pl.end()) { PixelBufferAlpha *pb = *pli; for(size_t x = 0; x < pb->width; x++) { for(size_t y = 0; y < pb->height; y++) { unsigned char r,g,b,a; pb->pixel(x,y,&r,&g,&b,&a); wpixbuf.setPixel(x + pb->x, y + pb->y, r, g, b, a); } } pli++; } native->handleBuffer(); } void GUI::Window::resized(size_t w, size_t h) { if(_width == w && _height == h) return; _width = w; _height = h; wpixbuf.realloc(w, h); updateBuffer(); pixbuf.realloc(w, h); repaintEvent(NULL); } void GUI::Window::redraw() { native->redraw(); } GUI::Widget *GUI::Window::keyboardFocus() { return _keyboardFocus; } void GUI::Window::setKeyboardFocus(GUI::Widget *widget) { GUI::Widget *old_focus = _keyboardFocus; _keyboardFocus = widget; if(old_focus) old_focus->repaintEvent(NULL); if(_keyboardFocus) _keyboardFocus->repaintEvent(NULL); } GUI::Widget *GUI::Window::buttonDownFocus() { return _buttonDownFocus; } void GUI::Window::setButtonDownFocus(GUI::Widget *widget) { _buttonDownFocus = widget; native->grabMouse(widget != NULL); } GUI::Widget *GUI::Window::mouseFocus() { return _mouseFocus; } void GUI::Window::setMouseFocus(GUI::Widget *widget) { _mouseFocus = widget; }