Initial commit master
authorFrancois Fleuret <francois@fleuret.org>
Sun, 7 Nov 2010 17:14:32 +0000 (18:14 +0100)
committerFrancois Fleuret <francois@fleuret.org>
Sun, 7 Nov 2010 17:14:32 +0000 (18:14 +0100)
Makefile [new file with mode: 0644]
example.cc [new file with mode: 0644]
simple_window.cc [new file with mode: 0644]
simple_window.h [new file with mode: 0644]

diff --git a/Makefile b/Makefile
new file mode 100644 (file)
index 0000000..44f310b
--- /dev/null
+++ b/Makefile
@@ -0,0 +1,34 @@
+
+#########################################################################
+# This program is free software: you can redistribute it and/or modify  #
+# it under the terms of the version 3 of the GNU General Public License #
+# as published by the Free Software Foundation.                                #
+#                                                                      #
+# This program 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 this program. If not, see <http://www.gnu.org/licenses/>.  #
+#                                                                      #
+# Written by and Copyright (C) Francois Fleuret                                #
+# Contact <francois.fleuret@idiap.ch> for comments & bug reports        #
+#########################################################################
+
+CXXFLAGS = -Wall
+
+LDFLAGS=-lX11
+
+all:   example
+
+example: example.cc simple_window.o
+       $(CXX) $(OPTIONS) -o $@ $^ $(LDFLAGS)
+
+Makefile.depend: *.h *.cc Makefile
+       $(CC) -M *.cc > Makefile.depend
+
+clean:
+       rm -f *.o example Makefile.depend
+
+-include Makefile.depend
diff --git a/example.cc b/example.cc
new file mode 100644 (file)
index 0000000..7a91406
--- /dev/null
@@ -0,0 +1,59 @@
+
+///////////////////////////////////////////////////////////////////////////
+// This program is free software: you can redistribute it and/or modify  //
+// it under the terms of the version 3 of the GNU General Public License //
+// as published by the Free Software Foundation.                         //
+//                                                                       //
+// This program 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 this program. If not, see <http://www.gnu.org/licenses/>.  //
+//                                                                       //
+// Written by and Copyright (C) Francois Fleuret                         //
+// Contact <francois.fleuret@idiap.ch> for comments & bug reports        //
+///////////////////////////////////////////////////////////////////////////
+
+#include <iostream>
+
+#include "simple_window.h"
+
+using namespace std;
+
+int main() {
+  SimpleWindow window("Mandelbrot", 600, 600);
+  int n;
+  int depth = 100;
+
+  const int width = window.get_width();
+  const int height = window.get_height();
+
+  window.map();
+
+  for(int i = 0; i < width; i++)
+    for(int j = 0; j < height; j++) {
+      double cr = -2.0 + 3.0 * (double(i)/double(width));
+      double ci = -1.5 + 3.0 * (double(j)/double(height));
+      double zr = 0, zi = 0;
+      for(n = 0; (n < depth) && (zr*zr + zi*zi < 100); n++) {
+       double t = zr*zr -zi*zi + cr;
+       zi = 2*zr*zi + ci;
+       zr = t;
+      }
+
+      float a = float(n)/float(depth);
+
+      if(a < 0.5) window.color(0, 0, a*2);
+      else        window.color((a-0.5)*2, (a-0.5)*2, 1.0);
+
+      window.draw_point(i, j);
+    }
+
+  window.show();
+
+  cout << "Press [ENTER] to close the window.\n";
+
+  cin.get();
+}
diff --git a/simple_window.cc b/simple_window.cc
new file mode 100644 (file)
index 0000000..5dd0aca
--- /dev/null
@@ -0,0 +1,152 @@
+
+///////////////////////////////////////////////////////////////////////////
+// This program is free software: you can redistribute it and/or modify  //
+// it under the terms of the version 3 of the GNU General Public License //
+// as published by the Free Software Foundation.                         //
+//                                                                       //
+// This program 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 this program. If not, see <http://www.gnu.org/licenses/>.  //
+//                                                                       //
+// Written by and Copyright (C) Francois Fleuret                         //
+// Contact <francois.fleuret@idiap.ch> for comments & bug reports        //
+///////////////////////////////////////////////////////////////////////////
+
+#include "simple_window.h"
+
+SimpleWindow::SimpleWindow(const char *name, int w, int h) {
+
+  width = w; height = h;
+
+  dpy = XOpenDisplay(0);
+
+  if (dpy) {
+
+      Visual *v = XDefaultVisual(dpy, DefaultScreen(dpy));
+
+      blue_mask = v->blue_mask;
+      green_mask = v->green_mask;
+      red_mask = v->red_mask;
+
+      if(blue_mask == 0 || green_mask == 0 || red_mask == 0) {
+        std::cerr << "Can not deal with the colors on that display.\n";
+      }
+
+      // We compute how many bits we have for each component, and
+      // compute the corresponding mask
+      red_shift = 1;
+      while(!(red_mask & 1)) {
+        red_mask = red_mask >> 1;
+        red_shift = red_shift << 1;
+      }
+
+      green_shift = 1;
+      while(!(green_mask & 1)) {
+        green_mask = green_mask >> 1;
+        green_shift = green_shift << 1;
+      }
+
+      blue_shift = 1;
+      while(!(blue_mask & 1)) {
+        blue_mask = blue_mask >> 1;
+        blue_shift = blue_shift << 1;
+      }
+
+      gc = DefaultGC(dpy, DefaultScreen(dpy));
+
+      XSetWindowAttributes xswa;
+
+      pixmap = XCreatePixmap(dpy, DefaultRootWindow(dpy),
+                            width, height, DisplayPlanes(dpy, DefaultScreen(dpy)));
+
+      xswa.background_pixmap = pixmap;
+      xswa.event_mask = NoEventMask;
+      xswa.backing_store = Always;
+
+      window = XCreateWindow(dpy, DefaultRootWindow(dpy), 0, 0, width, height,
+                            0, 0, InputOutput, CopyFromParent,
+                            CWBackPixmap | CWEventMask | CWBackingStore,
+                            &xswa);
+
+      XSizeHints size_hints;
+      size_hints.flags = PMinSize | PMaxSize;
+      size_hints.min_width = width;
+      size_hints.min_height = height;
+      size_hints.max_width = width;
+      size_hints.max_height = height;
+      XSetNormalHints(dpy, window, &size_hints);
+
+      XStoreName(dpy, window, name);
+
+      XSetState(dpy, gc, 0, 0, GXcopy, AllPlanes);
+      XFillRectangle(dpy, pixmap, gc, 0, 0, width, height);
+      XFlush(dpy);
+    } else abort();
+}
+
+SimpleWindow::~SimpleWindow() {
+  XUnmapWindow(dpy, window);
+  XDestroyWindow(dpy, window);
+  XCloseDisplay(dpy);
+}
+
+int SimpleWindow::get_width() {
+  return width;
+}
+
+int SimpleWindow::get_height() {
+  return height;
+}
+
+void SimpleWindow::map() {
+  XMapWindow(dpy, window);
+  XFlush(dpy);
+}
+
+void SimpleWindow::unmap() {
+  XUnmapWindow(dpy, window);
+  XFlush(dpy);
+}
+
+void SimpleWindow::color(float red, float green, float blue) {
+  // We work under the assumption that the bits come in the
+  // red/green/blue order with the corresponding masks
+  XSetState(dpy, gc,
+              ((unsigned int) (  red *   red_mask)) *   red_shift
+           + ((unsigned int) (green * green_mask)) * green_shift
+           + ((unsigned int) ( blue *  blue_mask)) *  blue_shift,
+           0, GXcopy, AllPlanes);
+}
+
+void SimpleWindow::draw_point(int x, int y) {
+  XDrawPoint(dpy, pixmap, gc, x, y);
+}
+
+void SimpleWindow::draw_line(int x1, int y1, int x2, int y2) {
+  XDrawLine(dpy, pixmap, gc, x1, y1, x2, y2);
+}
+
+void SimpleWindow::draw_circle(int x, int y, int r) {
+  XDrawArc(dpy, pixmap, gc, x-r, y-r, 2*r, 2*r, 0, 360*64);
+}
+
+void SimpleWindow::draw_text(char *s, int x, int y) {
+  XDrawString(dpy, pixmap, gc, x, y, s, strlen(s));
+}
+
+void SimpleWindow::fill_rectangle(int x, int y, int w, int h) {
+  XFillRectangle(dpy, pixmap, gc, x, y, w, h);
+}
+
+void SimpleWindow::show() {
+  XCopyArea(dpy, pixmap, window, gc, 0, 0, width, height, 0, 0);
+  XFlush(dpy);
+}
+
+void SimpleWindow::fill() {
+  XFillRectangle(dpy, pixmap, gc, 0, 0, width, height);
+}
diff --git a/simple_window.h b/simple_window.h
new file mode 100644 (file)
index 0000000..0732847
--- /dev/null
@@ -0,0 +1,64 @@
+
+///////////////////////////////////////////////////////////////////////////
+// This program is free software: you can redistribute it and/or modify  //
+// it under the terms of the version 3 of the GNU General Public License //
+// as published by the Free Software Foundation.                         //
+//                                                                       //
+// This program 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 this program. If not, see <http://www.gnu.org/licenses/>.  //
+//                                                                       //
+// Written by and Copyright (C) Francois Fleuret                         //
+// Contact <francois.fleuret@idiap.ch> for comments & bug reports        //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef SIMPLE_WINDOW_H
+#define SIMPLE_WINDOW_H
+
+#include <iostream>
+#include <cmath>
+#include <stdlib.h>
+#include <string.h>
+
+#include <stdio.h>
+#include <unistd.h>
+#include <X11/Xlib.h>
+#include <X11/Xutil.h>
+#include <X11/Xresource.h>
+#include <X11/cursorfont.h>
+
+class SimpleWindow {
+  Display *dpy;
+  Window window;
+  Pixmap pixmap;
+  GC gc;
+
+protected:
+  int red_mask, green_mask, blue_mask;
+  int red_shift, green_shift, blue_shift;
+  int width, height;
+
+public:
+  SimpleWindow(const char *name, int w, int h);
+  virtual ~SimpleWindow();
+
+  virtual int get_width();
+  virtual int get_height();
+
+  virtual void map();
+  virtual void unmap();
+  virtual void color(float red, float green, float blue);
+  virtual void draw_point(int x, int y);
+  virtual void draw_line(int x1, int y1, int x2, int y2);
+  virtual void draw_circle(int x, int y, int r);
+  virtual void draw_text(char *s, int x, int y);
+  virtual void fill_rectangle(int x, int y, int w, int h);
+  virtual void show();
+  virtual void fill();
+};
+
+#endif