]> git.tdb.fi Git - libs/gui.git/commitdiff
Add DrawContext for 2D graphics
authorMikko Rasa <tdb@tdb.fi>
Tue, 5 Feb 2008 16:41:32 +0000 (16:41 +0000)
committerMikko Rasa <tdb@tdb.fi>
Tue, 5 Feb 2008 16:41:32 +0000 (16:41 +0000)
source/drawcontext.cpp [new file with mode: 0644]
source/drawcontext.h [new file with mode: 0644]

diff --git a/source/drawcontext.cpp b/source/drawcontext.cpp
new file mode 100644 (file)
index 0000000..44ecf21
--- /dev/null
@@ -0,0 +1,90 @@
+/* $Id$
+
+This file is part of libmspgbase
+Copyright © 2007 Mikko Rasa, Mikkosoft Productions
+Distributed under the LGPL
+*/
+
+#ifndef WIN32
+#include <sys/ipc.h>
+#include <sys/shm.h>
+#include <X11/Xutil.h>
+#endif
+#include <msp/core/except.h>
+#include "display.h"
+#include "drawcontext.h"
+#include "window.h"
+
+namespace Msp {
+namespace Graphics {
+
+DrawContext::DrawContext(Window &w):
+       display(w.get_display()),
+       window(w),
+       image(0)
+{
+#ifndef WIN32
+       ::Display *dpy=display.get_display();
+
+       use_shm=false; XShmQueryExtension(dpy);
+
+       XWindowAttributes wa;
+       XGetWindowAttributes(dpy, window.get_handle(), &wa);
+
+       if(use_shm)
+       {
+               image=XShmCreateImage(dpy, wa.visual, wa.depth, ZPixmap, 0, &shminfo, wa.width, wa.height);
+               if(!image)
+                       throw Exception("Could not create shared memory XImage");
+
+               shminfo.shmid=shmget(IPC_PRIVATE, image->bytes_per_line*image->height, IPC_CREAT|0666);
+               shminfo.shmaddr=image->data=reinterpret_cast<char *>(shmat(shminfo.shmid, 0, 0));
+               shminfo.readOnly=false;
+
+               XShmAttach(dpy, &shminfo);
+
+               XSync(dpy, false);
+               display.check_error();
+       }
+       else
+       {
+               image=XCreateImage(dpy, wa.visual, wa.depth, ZPixmap, 0, 0, wa.width, wa.height, 8, 0);
+               if(!image)
+                       throw Exception("Could not create XImage");
+               image->data=new char[image->bytes_per_line*image->height];
+       }
+#endif
+}
+
+DrawContext::~DrawContext()
+{
+#ifndef WIN32
+       if(use_shm)
+       {
+               XShmDetach(display.get_display(), &shminfo);
+               shmdt(shminfo.shmaddr);
+               shmctl(shminfo.shmid, IPC_RMID, 0);
+       }
+
+       XDestroyImage(image);
+#endif
+}
+
+void DrawContext::update()
+{
+#ifndef WIN32
+       ::Display *dpy=display.get_display();
+
+       GC gc=XCreateGC(dpy, window.get_handle(), 0, 0);
+
+       if(use_shm)
+               XShmPutImage(dpy, window.get_handle(), gc, image, 0, 0, 0, 0, image->width, image->height, false);
+       else
+               XPutImage(dpy, window.get_handle(), gc, image, 0, 0, 0, 0, image->width, image->height);
+
+       XFreeGC(dpy, gc);
+#endif
+}
+
+} // namespace Graphics
+} // namespace Msp
diff --git a/source/drawcontext.h b/source/drawcontext.h
new file mode 100644 (file)
index 0000000..15f66cb
--- /dev/null
@@ -0,0 +1,46 @@
+/* $Id$
+
+This file is part of libmspgbase
+Copyright © 2007 Mikko Rasa, Mikkosoft Productions
+Distributed under the LGPL
+*/
+
+#ifndef MSP_GBASE_DRAWCONTEXT_H_
+#define MSP_GBASE_DRAWCONTEXT_H_
+
+#ifndef WIN32
+#include <X11/Xlib.h>
+#include <X11/extensions/XShm.h>
+#endif
+
+namespace Msp {
+namespace Graphics {
+
+class Display;
+class Window;
+
+class DrawContext
+{
+private:
+       Display &display;
+       Window &window;
+#ifndef WIN32
+       XImage *image;
+       bool use_shm;
+       XShmSegmentInfo shminfo;
+#endif
+
+public:
+       DrawContext(Window &);
+       ~DrawContext();
+
+       Window &get_window() const { return window; }
+       unsigned get_depth() const { return image->depth; }
+       unsigned char *get_data() { return reinterpret_cast<unsigned char *>(image->data); }
+       void update();
+};
+
+} // namespace Graphics
+} // namespace Msp
+
+#endif