chiark / gitweb /
Support for run-time icons in the GTK puzzles. This involved another
authorSimon Tatham <anakin@pobox.com>
Wed, 27 Dec 2006 15:10:59 +0000 (15:10 +0000)
committerSimon Tatham <anakin@pobox.com>
Wed, 27 Dec 2006 15:10:59 +0000 (15:10 +0000)
mkfiles.pl change (I don't seem to be planning ahead very well this
week), this time to provide a list of fallback options for an object
file. That way, I have a no-icon.c which quietly replaces
icons/foo-icon.c if the latter doesn't exist, and so again people
checking straight out from Subversion shouldn't have trouble.

[originally from svn r7021]

30 files changed:
blackbox.R
bridges.R
cube.R
dominosa.R
fifteen.R
flip.R
gtk.c
guess.R
icons/Makefile
icons/cicon.pl [new file with mode: 0755]
inertia.R
lightup.R
loopy.R
map.R
mines.R
mkfiles.pl
net.R
netslide.R
no-icon.c [new file with mode: 0644]
nullgame.R
pattern.R
pegs.R
rect.R
samegame.R
sixteen.R
slant.R
solo.R
tents.R
twiddle.R
untangle.R

index 884fe440ba63ded39324c5651d6cdb935fbf08af..423584004eda775438fbcfc60895b4564813b045 100644 (file)
@@ -1,6 +1,6 @@
 # -*- makefile -*-
 
-blackbox : [X] GTK COMMON blackbox
+blackbox : [X] GTK COMMON blackbox blackbox-icon|no-icon
 
 blackbox : [G] WINDOWS COMMON blackbox blackbox.res?
 
index f11fd4194d166fea2c83a6e1684d7329eab41563..75b9731e3a8e10f2a48c5b41f9ede88794797f34 100644 (file)
--- a/bridges.R
+++ b/bridges.R
@@ -2,7 +2,7 @@
 
 BRIDGES  = bridges dsf
 
-bridges  : [X] GTK COMMON BRIDGES
+bridges  : [X] GTK COMMON BRIDGES bridges-icon|no-icon
 
 bridges  : [G] WINDOWS COMMON BRIDGES bridges.res?
 
diff --git a/cube.R b/cube.R
index cc10fde33f112c4a4147d8ae9f76bc48e80f2e69..f08e0000de53c93a9cc7237b9e29c20fdf18d6fc 100644 (file)
--- a/cube.R
+++ b/cube.R
@@ -1,6 +1,6 @@
 # -*- makefile -*-
 
-cube     : [X] GTK COMMON cube
+cube     : [X] GTK COMMON cube cube-icon|no-icon
 
 cube     : [G] WINDOWS COMMON cube cube.res?
 
index 3bc8e34c87ac7ae61efdc2cabe4d5b3495314042..e243c43f3424a6b65951b19dc34f05e695e7db37 100644 (file)
@@ -1,6 +1,6 @@
 # -*- makefile -*-
 
-dominosa : [X] GTK COMMON dominosa
+dominosa : [X] GTK COMMON dominosa dominosa-icon|no-icon
 
 dominosa : [G] WINDOWS COMMON dominosa dominosa.res?
 
index fd371d71969eed9441af87097ec73331febb45e4..a9e2108ceef7aaccd99c08087dbe9e59e5919936 100644 (file)
--- a/fifteen.R
+++ b/fifteen.R
@@ -1,6 +1,6 @@
 # -*- makefile -*-
 
-fifteen  : [X] GTK COMMON fifteen
+fifteen  : [X] GTK COMMON fifteen fifteen-icon|no-icon
 
 fifteen  : [G] WINDOWS COMMON fifteen fifteen.res?
 
diff --git a/flip.R b/flip.R
index 91764de2e005760dcbfc7b2e60421be75f85483a..40ca546744166e290c1b75aa2cd708e04751d0fe 100644 (file)
--- a/flip.R
+++ b/flip.R
@@ -2,7 +2,7 @@
 
 FLIP     = flip tree234
 
-flip     : [X] GTK COMMON FLIP
+flip     : [X] GTK COMMON FLIP flip-icon|no-icon
 
 flip     : [G] WINDOWS COMMON FLIP flip.res?
 
diff --git a/gtk.c b/gtk.c
index d9b9a276715421ef410d538aaa023980af4663c4..35e74662fd7528bb0df2b39946f1dc52ed4ae200 100644 (file)
--- a/gtk.c
+++ b/gtk.c
@@ -15,6 +15,8 @@
 #include <gtk/gtk.h>
 #include <gdk/gdkkeysyms.h>
 
+#include <gdk-pixbuf/gdk-pixbuf.h>
+
 #include <gdk/gdkx.h>
 #include <X11/Xlib.h>
 #include <X11/Xutil.h>
@@ -1458,8 +1460,12 @@ static frontend *new_window(char *arg, int argtype, char **error)
     frontend *fe;
     GtkBox *vbox;
     GtkWidget *menubar, *menu, *menuitem;
+    GdkPixmap *iconpm;
+    GList *iconlist;
     int x, y, n;
     char errbuf[1024];
+    extern char *const *const xpm_icons[];
+    extern const int n_xpm_icons;
 
     fe = snew(frontend);
 
@@ -1745,6 +1751,21 @@ static frontend *new_window(char *arg, int argtype, char **error)
                           GDK_BUTTON_RELEASE_MASK |
                          GDK_BUTTON_MOTION_MASK);
 
+    if (n_xpm_icons) {
+       gtk_widget_realize(fe->window);
+       iconpm = gdk_pixmap_create_from_xpm_d(fe->window->window, NULL,
+                                             NULL, (gchar **)xpm_icons[0]);
+       gdk_window_set_icon(fe->window->window, NULL, iconpm, NULL);
+       iconlist = NULL;
+       for (n = 0; n < n_xpm_icons; n++) {
+           iconlist =
+               g_list_append(iconlist,
+                             gdk_pixbuf_new_from_xpm_data((const gchar **)
+                                                          xpm_icons[n]));
+       }
+       gdk_window_set_icon_list(fe->window->window, iconlist);
+    }
+
     gtk_widget_show(fe->area);
     gtk_widget_show(fe->window);
 
diff --git a/guess.R b/guess.R
index fa98337ea3004ccf65de750e42755aa01e03eeea..0956e6583893723687c54dd309f64266127d8782 100644 (file)
--- a/guess.R
+++ b/guess.R
@@ -1,6 +1,6 @@
 # -*- makefile -*-
 
-guess    : [X] GTK COMMON guess
+guess    : [X] GTK COMMON guess guess-icon|no-icon
 
 guess    : [G] WINDOWS COMMON guess guess.res?
 
index 233f7679a1d865cf66eb10ffc645bb4b494f4561..bec2a4a6f613bf5b2c1a5bf33e3969facc7e0b3f 100644 (file)
@@ -19,6 +19,7 @@ P16D24 = $(patsubst %,%-16d24.png,$(PUZZLES))
 P16D8 = $(patsubst %,%-16d8.png,$(PUZZLES))
 P16D4 = $(patsubst %,%-16d4.png,$(PUZZLES))
 ICONS = $(patsubst %,%.ico,$(PUZZLES))
+CICONS = $(patsubst %,%-icon.c,$(PUZZLES))
 RC = $(patsubst %,%.rc,$(PUZZLES))
 
 BIN = ../
@@ -28,6 +29,7 @@ base: $(BASE)
 web: $(WEB)
 pngicons: $(P48D24) $(P32D24) $(P16D24)
 winicons: $(ICONS) $(RC)
+gtkicons: $(CICONS)
 
 # Build the base puzzle screenshots from which all the other images
 # are derived. Some of them involve showing a move animation
@@ -120,5 +122,9 @@ $(ICONS): %.ico: %-48d24.png %-48d8.png %-48d4.png \
 $(RC): %.rc:
        echo '200 ICON "$*.ico"' > $@
 
+# Build the GTK icon source files.
+$(CICONS): %-icon.c: %-16d24.png %-32d24.png %-48d24.png
+       $(PIC)cicon.pl $^ > $@  
+
 clean:
-       rm -f *.png *.ico *.rc
+       rm -f *.png *.ico *.rc *-icon.c
diff --git a/icons/cicon.pl b/icons/cicon.pl
new file mode 100755 (executable)
index 0000000..3578bd3
--- /dev/null
@@ -0,0 +1,27 @@
+#!/usr/bin/perl 
+
+# Given a list of input PNGs, create a C source file file
+# containing a const array of XPMs, under the name `xpm_icon'.
+
+$k = 0;
+@xpms = ();
+foreach $f (@ARGV) {
+  # XPM format is generated directly by ImageMagick, so that's easy
+  # enough. We just have to adjust the declaration line so that it
+  # has the right name, linkage and storage class.
+  @lines = ();
+  open XPM, "convert $f xpm:- |";
+  push @lines, $_ while <XPM>;
+  close XPM;
+  die "XPM from $f in unexpected format\n" unless $lines[1] =~ /^static.*\{$/;
+  $lines[1] = "static const char *const xpm_icon_$k"."[] = {\n";
+  $k++;
+  push @xpms, @lines, "\n";
+}
+
+# Now output.
+foreach $line (@xpms) { print $line; }
+print "const char *const *const xpm_icons[] = {\n";
+for ($i = 0; $i < $k; $i++) { print "    xpm_icon_$i,\n"; }
+print "};\n";
+print "const int n_xpm_icons = $k;\n";
index 33e1841e0ca5c8f842bfe8c229d41bd1747f0b4c..867484e977101de3cab2de97241b19f00ae36265 100644 (file)
--- a/inertia.R
+++ b/inertia.R
@@ -1,6 +1,6 @@
 # -*- makefile -*-
 
-inertia  : [X] GTK COMMON inertia
+inertia  : [X] GTK COMMON inertia inertia-icon|no-icon
 
 inertia  : [G] WINDOWS COMMON inertia inertia.res?
 
index 17a2c6cc4b5a75366d9bedf5e687ae063dab9411..b4c4a3dfb17f9d30b6aa2d9b0b78dc4c138f0629 100644 (file)
--- a/lightup.R
+++ b/lightup.R
@@ -2,7 +2,7 @@
 
 LIGHTUP  = lightup combi
 
-lightup  : [X] GTK COMMON LIGHTUP
+lightup  : [X] GTK COMMON LIGHTUP lightup-icon|no-icon
 
 lightup  : [G] WINDOWS COMMON LIGHTUP lightup.res?
 
diff --git a/loopy.R b/loopy.R
index 37e64b66a54a84263f60e9312b83f6b763869940..1856d5309aab0895d1ad8b87c49e912bc9902407 100644 (file)
--- a/loopy.R
+++ b/loopy.R
@@ -2,7 +2,7 @@
 
 LOOPY    = loopy tree234 dsf
 
-loopy    : [X] GTK COMMON LOOPY
+loopy    : [X] GTK COMMON LOOPY loopy-icon|no-icon
 
 loopy    : [G] WINDOWS COMMON LOOPY loopy.res?
 
diff --git a/map.R b/map.R
index 7752ec2d1544754cc50d312a2ad32e934114bd75..20e6706a736b97f03651af002edf8318f2314b88 100644 (file)
--- a/map.R
+++ b/map.R
@@ -2,7 +2,7 @@
 
 MAP      = map dsf
 
-map      : [X] GTK COMMON MAP
+map      : [X] GTK COMMON MAP map-icon|no-icon
 
 map      : [G] WINDOWS COMMON MAP map.res?
 
diff --git a/mines.R b/mines.R
index 46913de62913ecb72365abf1d2ce0ee855092499..bc7e3a9b093185d2e520fa740a29a80155097341 100644 (file)
--- a/mines.R
+++ b/mines.R
@@ -2,7 +2,7 @@
 
 MINES    = mines tree234
 
-mines    : [X] GTK COMMON MINES
+mines    : [X] GTK COMMON MINES mines-icon|no-icon
 
 mines    : [G] WINDOWS COMMON MINES mines.res?
 
index c81d64d51f538c1a8abb305223755f5a7b65cc9e..165f796beb4024227880d1a5fc87ee4b397283cd 100755 (executable)
@@ -131,11 +131,22 @@ readinput: while (1) {
       $type = substr($i,1,(length $i)-2);
     } else {
       if ($i =~ /\?$/) {
-       # Source files with a trailing question mark are optional:
+       # Object files with a trailing question mark are optional:
        # the build can proceed fine without them, so we only use
-       # them if they're present.
+       # them if their primary source files are present.
        $i =~ s/\?$//;
        $i = undef unless defined &finddep($i);
+      } elsif ($i =~ /\|/) {
+       # Object file descriptions containing a vertical bar are
+       # lists of choices: we use the _first_ one whose primary
+       # source file is present.
+       @options = split /\|/, $i;
+       $j = undef;
+       foreach $k (@options) {
+         $j=$k, last if defined &finddep($k);
+       }
+       die "no alternative found for $i\n" unless defined $j;
+       $i = $j;
       }
       if (defined $i) {
        push @$listref, $i;
diff --git a/net.R b/net.R
index ec7c8a3484f8d5489009a4746662853570dcf92c..5edddb57de49a70757e003e1434f9e4cc4e7bbce 100644 (file)
--- a/net.R
+++ b/net.R
@@ -2,7 +2,7 @@
 
 NET      = net tree234 dsf
 
-net      : [X] GTK COMMON NET
+net      : [X] GTK COMMON NET net-icon|no-icon
 
 # The Windows Net shouldn't be called `net.exe' since Windows
 # already has a reasonably important utility program by that name!
index 69e643dbcb8098db0314f10b69680fe241aa55ef..b558de992991ec074a609e6395d5a9067774ea6c 100644 (file)
@@ -2,7 +2,7 @@
 
 NETSLIDE = netslide tree234
 
-netslide : [X] GTK COMMON NETSLIDE
+netslide : [X] GTK COMMON NETSLIDE netslide-icon|no-icon
 
 netslide : [G] WINDOWS COMMON NETSLIDE netslide.res?
 
diff --git a/no-icon.c b/no-icon.c
new file mode 100644 (file)
index 0000000..8a1de91
--- /dev/null
+++ b/no-icon.c
@@ -0,0 +1,9 @@
+#include <X11/Intrinsic.h>
+
+/*
+ * Dummy source file which replaces the files generated in the
+ * `icons' subdirectory, when they're absent.
+ */
+
+const char *const *const xpm_icons[] = { 0 };
+const int n_xpm_icons = 0;
index 993f1ef27770025509f8c079e10a9873309a2d61..941623c92658324fd6e42bdb1ab6bd50729733ca 100644 (file)
@@ -8,5 +8,5 @@
 # it in the Makefile because it will be worse than useless if it
 # ever fails to compile, so it's important that it should actually
 # be built on a regular basis.
-nullgame : [X] GTK COMMON nullgame
+nullgame : [X] GTK COMMON nullgame nullgame-icon|no-icon
 nullgame : [G] WINDOWS COMMON nullgame
index 13dbfe2aad859e8d6987f60770489c7fffb5d98b..0b96d46fb78f0572bf1e04d0003c749a2c93eba4 100644 (file)
--- a/pattern.R
+++ b/pattern.R
@@ -1,6 +1,6 @@
 # -*- makefile -*-
 
-pattern  : [X] GTK COMMON pattern
+pattern  : [X] GTK COMMON pattern pattern-icon|no-icon
 
 pattern  : [G] WINDOWS COMMON pattern pattern.res?
 
diff --git a/pegs.R b/pegs.R
index a1ab945c139a59708cd5523d9ec6d4351c9d6710..97a175073d683e2c8e2f1a585dd914e9c65ccf22 100644 (file)
--- a/pegs.R
+++ b/pegs.R
@@ -2,7 +2,7 @@
 
 PEGS     = pegs tree234
 
-pegs     : [X] GTK COMMON PEGS
+pegs     : [X] GTK COMMON PEGS pegs-icon|no-icon
 
 pegs     : [G] WINDOWS COMMON PEGS pegs.res?
 
diff --git a/rect.R b/rect.R
index 20d3b49553dc1f52531ea53a8bfbc29989fc5b1d..e050b40d52d9839b6b0f0ae841fe8136cb92f68e 100644 (file)
--- a/rect.R
+++ b/rect.R
@@ -1,6 +1,6 @@
 # -*- makefile -*-
 
-rect     : [X] GTK COMMON rect
+rect     : [X] GTK COMMON rect rect-icon|no-icon
 
 rect     : [G] WINDOWS COMMON rect rect.res?
 
index c3905bda3ef3c0b9cdc2a1a43788f5209097874a..fa1f2cadcf79785533bc2b9bf8ad0d1424a7bdeb 100644 (file)
@@ -1,6 +1,6 @@
 # -*- makefile -*-
 
-samegame : [X] GTK COMMON samegame
+samegame : [X] GTK COMMON samegame samegame-icon|no-icon
 
 samegame : [G] WINDOWS COMMON samegame samegame.res?
 
index 46147afd09746e295e37f1bdb97913537c7edcb4..4a699618ab54a24882b0662ca4c7486d3e3db3e4 100644 (file)
--- a/sixteen.R
+++ b/sixteen.R
@@ -1,6 +1,6 @@
 # -*- makefile -*-
 
-sixteen  : [X] GTK COMMON sixteen
+sixteen  : [X] GTK COMMON sixteen sixteen-icon|no-icon
 
 sixteen  : [G] WINDOWS COMMON sixteen sixteen.res?
 
diff --git a/slant.R b/slant.R
index b735ec47c33396436e1de58a8ebeb4c23668839f..b615a9fc6b6c00888ade0f445c9eca01844a7853 100644 (file)
--- a/slant.R
+++ b/slant.R
@@ -2,7 +2,7 @@
 
 SLANT    = slant dsf
 
-slant    : [X] GTK COMMON SLANT
+slant    : [X] GTK COMMON SLANT slant-icon|no-icon
 
 slant    : [G] WINDOWS COMMON SLANT slant.res?
 
diff --git a/solo.R b/solo.R
index 6fe4ea07abfa919f57b0e6d8cb776e8f655748aa..126e338bc1c4cf145c97c69a86bcf4e16554ff33 100644 (file)
--- a/solo.R
+++ b/solo.R
@@ -1,6 +1,6 @@
 # -*- makefile -*-
 
-solo     : [X] GTK COMMON solo
+solo     : [X] GTK COMMON solo solo-icon|no-icon
 
 solo     : [G] WINDOWS COMMON solo solo.res?
 
diff --git a/tents.R b/tents.R
index ab6066f4c11493c61993258f96228a4c637677ee..c875289500cd837a5b1e06ab017775efa085e973 100644 (file)
--- a/tents.R
+++ b/tents.R
@@ -2,7 +2,7 @@
 
 TENTS    = tents maxflow
 
-tents    : [X] GTK COMMON TENTS
+tents    : [X] GTK COMMON TENTS tents-icon|no-icon
 
 tents    : [G] WINDOWS COMMON TENTS tents.res?
 
index c525953890234f0e9b252afed67dbda28edea9f5..6b23df16f5171888b2070202317ced3cf2f220cb 100644 (file)
--- a/twiddle.R
+++ b/twiddle.R
@@ -1,6 +1,6 @@
 # -*- makefile -*-
 
-twiddle  : [X] GTK COMMON twiddle
+twiddle  : [X] GTK COMMON twiddle twiddle-icon|no-icon
 
 twiddle  : [G] WINDOWS COMMON twiddle twiddle.res?
 
index 8c467d6f17d2b1c9c603b490140623fb1bc6e0f2..fd74f319c053c6a5cd95986cc6c882d067f495c6 100644 (file)
@@ -2,7 +2,7 @@
 
 UNTANGLE = untangle tree234
 
-untangle : [X] GTK COMMON UNTANGLE
+untangle : [X] GTK COMMON UNTANGLE untangle-icon|no-icon
 
 untangle : [G] WINDOWS COMMON UNTANGLE untangle.res?