* See the included man page for more details.
*/
-#include <ctype.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
#include <math.h>
#include "screenhack.h"
-#include <X11/Xutil.h>
-
-
-
-/* parameters that are user configurable */
-
-/* delay (usec) between iterations */
-static int delay;
-
-static int scroll_p;
-
-
/* non-user-modifiable immutable definitions */
#define BARCODE_WIDTH (164)
#define BARCODE_HEIGHT (69)
-#define MAX_MAG (6)
-
-/* width and height of the window */
-static int windowWidth;
-static int windowHeight;
-
-static Display *display; /* the display to draw on */
-static Window window; /* the window to draw on */
-static Visual *visual; /* the visual to use */
-static Screen *screen; /* the screen to draw on */
-static Colormap cmap; /* the colormap of the window */
-
-static GC theGC; /* GC for drawing */
-
+#define MAX_MAG (7)
/* simple bitmap structure */
int width;
int height;
int widthBytes;
- unsigned char *buf;
+ char *buf;
}
Bitmap;
}
Barcode;
-static Barcode *barcodes; /* array of barcodes */
-static int barcode_count; /* how many barcodes are currently active */
-static int barcode_max; /* the maximum number of active barcodes */
+struct state {
+ Display *dpy;
+ Window window;
+
+ /* parameters that are user configurable */
+
+ /* delay (usec) between iterations */
+ int delay;
+
+ /* width and height of the window */
+ int windowWidth;
+ int windowHeight;
+
+ Visual *visual; /* the visual to use */
+ Colormap cmap; /* the colormap of the window */
-static XImage *theImage; /* ginormo image for drawing */
-static Bitmap *theBitmap; /* ginormo bitmap for drawing */
+ GC theGC; /* GC for drawing */
+ unsigned long fg_pixel, grid_pixel;
+ Bool button_down_p;
+ int grid_alloced_p;
+ char *strings[200];
+
+ Barcode *barcodes; /* array of barcodes */
+ int barcode_count; /* how many barcodes are currently active */
+ int barcode_max; /* the maximum number of active barcodes */
+
+ XImage *theImage; /* ginormo image for drawing */
+ Bitmap *theBitmap; /* ginormo bitmap for drawing */
+
+ enum { BC_SCROLL, BC_GRID, BC_CLOCK12, BC_CLOCK24 } mode;
+
+ int grid_w;
+ int grid_h;
+};
/* a bunch of words */
-static char *words[] =
+static const char *words[] =
{
- "abdomen",
- "abeyance",
- "abhorrent",
- "abrasive",
- "abstract",
- "acid",
- "addiction",
- "alertness",
- "Algeria",
- "anxiety",
- "aorta",
- "argyle socks",
- "attrition",
- "bamboo",
- "bangle",
- "bankruptcy",
- "baptism",
- "beer",
- "bellicose",
- "bells",
- "belly",
- "bread",
- "bubba",
- "burrito",
- "California",
- "capybara",
- "cardinality",
- "caribou",
- "carnage",
- "chocolate",
- "constriction",
- "contrition",
- "corpse",
- "cowboy",
- "cozy",
- "crabapple",
- "craziness",
- "Death",
- "Decker",
- "decoded",
- "decoy",
- "defenestration",
- "dependency",
- "despair",
- "desperation",
- "disease",
- "doberman",
- "dreams",
- "drench",
- "drugs",
- "easy",
- "ebony",
- "elliptic",
- "eloquence",
- "emergency",
- "eureka",
- "excommunicate",
- "fat",
- "fatherland",
- "Faust",
- "fear",
- "fever",
- "flatulence",
- "fluff",
- "fnord",
- "freedom",
- "fruit",
- "fruit",
- "gauche",
- "gawk",
- "gaze",
- "gerbils",
- "GOD",
- "goggles",
- "goobers",
- "gorilla",
- "halibut",
- "handmaid",
- "hapless",
- "happiness",
- "hate",
- "helplessness",
- "hermaphrodite",
- "Hindi",
- "hope",
- "hysteria",
- "icepick",
- "ignorance",
- "importance",
- "impossibility",
- "inkling",
- "insurrection",
- "intoxicant",
- "ire",
- "irritant",
- "jade",
- "jaundice",
- "Joyce",
- "kaput",
- "kitchenette",
- "kiwi",
- "lathe",
- "lattice",
- "lemming",
- "liquidation",
- "love",
- "lozenge",
- "magazine",
- "magnesium",
- "malfunction",
- "marmot",
- "marshmallow",
- "merit",
- "mescaline",
- "milk",
- "mischief",
- "mistrust",
- "money",
- "monkey",
- "monkeybutter",
- "multiple",
- "nature",
- "neuron",
- "noise",
- "nomenclature",
- "nutria",
- "obey",
- "ocelot",
- "offspring",
- "overseer",
- "pain",
- "pajamas",
- "passenger",
- "passion",
- "Passover",
- "Prozac",
- "peace",
- "penance",
- "persimmon",
- "petticoat",
- "pharmacist",
- "pitchfork",
- "plague",
- "Poindexter",
- "precept",
- "prison",
- "prophecy",
- "quadratic",
- "quagmire",
- "quarantine",
- "quartz",
- "rabies",
- "radish",
- "rage",
- "readout",
- "reality",
- "reject",
- "rejection",
- "respect",
- "revolution",
- "roadrunner",
- "rule",
- "sanguine",
- "savor",
- "scab",
- "scalar",
- "Scandinavia",
- "security",
- "sediment",
- "sickness",
- "silicone",
- "slack",
- "slander",
- "slavery",
- "sledgehammer",
- "smelly socks",
- "sorrow",
- "stamen",
- "standardization",
- "subversion",
- "suffering",
- "surrender",
- "surveilance",
- "synthesis",
- "tenant",
- "tendril",
- "terror",
- "terrorism",
- "terrorist",
- "the unknown",
- "toast",
- "topography",
- "truism",
- "turgid",
- "underbrush",
- "underling",
- "unguent",
- "unusual",
- "unworthy",
- "uplink",
- "urge",
- "valor",
- "variance",
- "vastness",
- "vaudeville",
- "vegetarian",
- "venom",
- "verifiability",
- "viagra",
- "vibrator",
- "victim",
- "vignette",
- "villainy",
- "W.A.S.T.E.",
- "wagon",
- "waiver",
- "warehouse",
- "waste",
- "waveform",
- "whiffle ball",
- "whorl",
- "windmill",
- "wistful",
- "worm",
- "worship",
- "worship",
- "Xanax",
- "Xerxes",
- "Xhosa",
- "xylophone",
- "yellow",
- "yesterday",
- "your nose",
- "Zanzibar",
- "zeal",
- "zebra",
- "zest",
- "zinc"
+ "abdomen",
+ "abeyance",
+ "abhorrence",
+ "abrasion",
+ "abstraction",
+ "acid",
+ "addiction",
+ "alertness",
+ "Algeria",
+ "anxiety",
+ "aorta",
+ "argyle socks",
+ "attrition",
+ "axis of evil",
+ "bamboo",
+ "bangle",
+ "bankruptcy",
+ "baptism",
+ "beer",
+ "bellicosity",
+ "bells",
+ "belly",
+ "bliss",
+ "bogosity",
+ "boobies",
+ "boobs",
+ "booty",
+ "bread",
+ "bubba",
+ "burrito",
+ "California",
+ "capybara",
+ "cardinality",
+ "caribou",
+ "carnage",
+ "children",
+ "chocolate",
+ "CLONE",
+ "cock",
+ "constriction",
+ "contrition",
+ "cop",
+ "corpse",
+ "cowboy",
+ "crabapple",
+ "craziness",
+ "cthulhu",
+ "Death",
+ "decepticon",
+ "deception",
+ "Decker",
+ "decoder",
+ "decoy",
+ "defenestration",
+ "democracy",
+ "dependency",
+ "despair",
+ "desperation",
+ "disease",
+ "disease",
+ "doberman",
+ "DOOM",
+ "dreams",
+ "dreams",
+ "drugs",
+ "easy",
+ "ebony",
+ "election",
+ "eloquence",
+ "emergency",
+ "eureka",
+ "excommunication",
+ "fat",
+ "fatherland",
+ "Faust",
+ "fear",
+ "fever",
+ "filth",
+ "flatulence",
+ "fluff",
+ "fnord",
+ "freedom",
+ "fruit",
+ "fruit",
+ "futility",
+ "gerbils",
+ "GOD",
+ "goggles",
+ "goobers",
+ "gorilla",
+ "halibut",
+ "handmaid",
+ "happiness",
+ "hate",
+ "helplessness",
+ "hemorrhoid",
+ "hermaphrodite",
+ "heroin",
+ "heroine",
+ "hope",
+ "hysteria",
+ "icepick",
+ "identity",
+ "ignorance",
+ "importance",
+ "individuality",
+ "inkling",
+ "insurrection",
+ "intoxicant",
+ "ire",
+ "irritant",
+ "jade",
+ "jaundice",
+ "Joyce",
+ "kidney stone",
+ "kitchenette",
+ "kiwi",
+ "lathe",
+ "lattice",
+ "lawyer",
+ "lemming",
+ "liquidation",
+ "lobbyist",
+ "love",
+ "lozenge",
+ "magazine",
+ "magnesium",
+ "malfunction",
+ "marmot",
+ "marshmallow",
+ "merit",
+ "merkin",
+ "mescaline",
+ "milk",
+ "mischief",
+ "mistrust",
+ "money",
+ "monkey",
+ "monkeybutter",
+ "nationalism",
+ "nature",
+ "neuron",
+ "noise",
+ "nomenclature",
+ "nutria",
+ "OBEY",
+ "ocelot",
+ "offspring",
+ "overseer",
+ "pain",
+ "pajamas",
+ "passenger",
+ "passion",
+ "Passover",
+ "peace",
+ "penance",
+ "persimmon",
+ "petticoat",
+ "pharmacist",
+ "PhD",
+ "pitchfork",
+ "plague",
+ "Poindexter",
+ "politician",
+ "pony",
+ "presidency",
+ "prison",
+ "prophecy",
+ "Prozac",
+ "punishment",
+ "punk rock",
+ "punk",
+ "pussy",
+ "quagmire",
+ "quarantine",
+ "quartz",
+ "rabies",
+ "radish",
+ "rage",
+ "readout",
+ "reality",
+ "rectum",
+ "reject",
+ "rejection",
+ "respect",
+ "revolution",
+ "roadrunner",
+ "rule",
+ "savor",
+ "scab",
+ "scalar",
+ "Scandinavia",
+ "schadenfreude",
+ "security",
+ "sediment",
+ "self worth",
+ "sickness",
+ "silicone",
+ "slack",
+ "slander",
+ "slavery",
+ "sledgehammer",
+ "smegma",
+ "smelly socks",
+ "sorrow",
+ "space program",
+ "stamen",
+ "standardization",
+ "stench",
+ "subculture",
+ "subversion",
+ "suffering",
+ "surrender",
+ "surveillance",
+ "synthesis",
+ "television",
+ "tenant",
+ "tendril",
+ "terror",
+ "terrorism",
+ "terrorist",
+ "the impossible",
+ "the unknown",
+ "toast",
+ "topography",
+ "truism",
+ "turgid",
+ "underbrush",
+ "underling",
+ "unguent",
+ "unusual",
+ "uplink",
+ "urge",
+ "valor",
+ "variance",
+ "vaudeville",
+ "vector",
+ "vegetarian",
+ "venom",
+ "verifiability",
+ "viagra",
+ "vibrator",
+ "victim",
+ "vignette",
+ "villainy",
+ "W.A.S.T.E.",
+ "wagon",
+ "waiver",
+ "warehouse",
+ "waste",
+ "waveform",
+ "whiffle ball",
+ "whorl",
+ "windmill",
+ "words",
+ "worm",
+ "worship",
+ "worship",
+ "Xanax",
+ "Xerxes",
+ "Xhosa",
+ "xylophone",
+ "yellow",
+ "yesterday",
+ "your nose",
+ "Zanzibar",
+ "zeal",
+ "zebra",
+ "zest",
+ "zinc"
};
#define WORD_COUNT (sizeof(words) / sizeof(char *))
*/
/* construct a new bitmap */
-Bitmap *makeBitmap (int width, int height)
+static Bitmap *makeBitmap (int width, int height)
{
Bitmap *result = malloc (sizeof (Bitmap));
result->width = width;
}
/* clear a bitmap */
-void bitmapClear (Bitmap *b)
+static void bitmapClear (Bitmap *b)
{
memset (b->buf, 0, b->widthBytes * b->height);
}
+#if 0
/* free a bitmap */
-void bitmapFree (Bitmap *b)
+static void bitmapFree (Bitmap *b)
{
free (b->buf);
free (b);
}
+#endif
+
/* get the byte value at the given byte-offset coordinates in the given
* bitmap */
-int bitmapGetByte (Bitmap *b, int xByte, int y)
+static int bitmapGetByte (Bitmap *b, int xByte, int y)
{
if ((xByte < 0) ||
(xByte >= b->widthBytes) ||
}
/* get the bit value at the given coordinates in the given bitmap */
-int bitmapGet (Bitmap *b, int x, int y)
+static int bitmapGet (Bitmap *b, int x, int y)
{
int xbyte = x >> 3;
int xbit = x & 0x7;
}
/* set the bit value at the given coordinates in the given bitmap */
-void bitmapSet (Bitmap *b, int x, int y, int value)
+static void bitmapSet (Bitmap *b, int x, int y, int value)
{
int xbyte = x >> 3;
int xbit = x & 0x7;
}
/* copy the given rectangle to the given destination from the given source. */
-void bitmapCopyRect (Bitmap *dest, int dx, int dy,
- Bitmap *src, int sx, int sy, int width, int height)
+static void bitmapCopyRect (Bitmap *dest, int dx, int dy,
+ Bitmap *src, int sx, int sy, int width, int height)
{
int x, y;
}
/* draw a vertical line in the given bitmap */
-void bitmapVlin (Bitmap *b, int x, int y1, int y2)
+static void bitmapVlin (Bitmap *b, int x, int y1, int y2)
{
while (y1 <= y2)
{
}
/* scale a bitmap into another bitmap */
-void bitmapScale (Bitmap *dest, Bitmap *src, int mag)
+static void bitmapScale (Bitmap *dest, Bitmap *src, int mag)
{
int x, y, x2, y2;
- for (y = 0; y < src->height; y++)
+ for (y = 0; y < BARCODE_HEIGHT; y++)
{
- for (x = 0; x < src->width; x++)
+ for (x = 0; x < BARCODE_WIDTH; x++)
{
int v = bitmapGet (src, x, y);
for (x2 = 0; x2 < mag; x2++)
0x0f, 0x0f, 0x0f, 0x00
};
-static Bitmap font5x8 = { 8, 1024, 1, font5x8Buf };
+static Bitmap font5x8 = { 8, 1024, 1, (char *) font5x8Buf };
/* draw the given 5x8 character at the given coordinates */
-void bitmapDrawChar5x8 (Bitmap *b, int x, int y, char c)
+static void bitmapDrawChar5x8 (Bitmap *b, int x, int y, char c)
{
bitmapCopyRect (b, x, y, &font5x8, 0, c * 8, 5, 8);
}
/* draw a string of 5x8 characters at the given coordinates */
-void bitmapDrawString5x8 (Bitmap *b, int x, int y, char *str)
+static void bitmapDrawString5x8 (Bitmap *b, int x, int y, char *str)
{
int origx = x;
UpcSet;
/* the Left A patterns */
-unsigned int upcLeftA[] = {
+static unsigned int upcLeftA[] = {
0x0d, 0x19, 0x13, 0x3d, 0x23, 0x31, 0x2f, 0x3b, 0x37, 0x0b
};
/* the Left B patterns */
-unsigned int upcLeftB[] = {
+static unsigned int upcLeftB[] = {
0x27, 0x33, 0x1b, 0x21, 0x1d, 0x39, 0x05, 0x11, 0x09, 0x17
};
/* the Right patterns */
-unsigned int upcRight[] = {
+static unsigned int upcRight[] = {
0x72, 0x66, 0x6c, 0x42, 0x5c, 0x4e, 0x50, 0x44, 0x48, 0x74
};
/* the EAN-13 first-digit patterns */
-unsigned int ean13FirstDigit[] = {
+static unsigned int ean13FirstDigit[] = {
0x00, 0x0b, 0x0d, 0x0e, 0x13, 0x19, 0x1c, 0x15, 0x16, 0x1a
};
/* the UPC-E last-digit patterns for first digit 0 (complement for
* digit 1); also used for 5-digit supplemental check patterns */
-unsigned int upcELastDigit[] = {
+static unsigned int upcELastDigit[] = {
0x38, 0x34, 0x32, 0x31, 0x2c, 0x26, 0x23, 0x2a, 0x29, 0x25
};
/* turn a character into an int representing its digit value; return
* 0 for things not in the range '0'-'9' */
-int charToDigit (char c)
+static int charToDigit (char c)
{
if ((c >= '0') && (c <= '9'))
{
/* draw the given digit character at the given coordinates; a '0' is
* used in place of any non-digit character */
-void drawDigitChar (Bitmap *b, int x, int y, char c)
+static void drawDigitChar (struct state *st, Bitmap *b, int x, int y, char c)
{
+ if (st->mode != BC_CLOCK24 &&
+ st->mode != BC_CLOCK12)
if ((c < '0') || (c > '9'))
- {
- c = '0';
- }
+ c = '0';
bitmapDrawChar5x8 (b, x, y, c);
}
/* draw a upc/ean digit at the given coordinates */
-void drawUpcEanDigit (Bitmap *upcBitmap, int x, int y1, int y2, char n,
- UpcSet set)
+static void drawUpcEanDigit (Bitmap *upcBitmap, int x, int y1, int y2, char n,
+ UpcSet set)
{
unsigned int bits;
int i;
/* report the width of the given supplemental code or 0 if it is a bad
* supplement form */
-int upcEanSupplementWidth (char *digits)
+static int upcEanSupplementWidth (char *digits)
{
switch (strlen (digits))
{
}
/* draw the given supplemental barcode, including the textual digits */
-void drawUpcEanSupplementalBars (Bitmap *upcBitmap, char *digits,
- int x, int y, int y2, int textAbove)
+static void drawUpcEanSupplementalBars (struct state *st,
+ Bitmap *upcBitmap, char *digits,
+ int x, int y, int y2, int textAbove)
{
int len = strlen (digits);
int i;
}
default:
{
- printf("Bad supplement\n");
+ fprintf (stderr, "%s: bad supplement (%d digits)\n",
+ progname, len);
exit(1);
break;
}
digits[i],
lset);
- drawDigitChar (upcBitmap, textX + i*6, textY, digits[i]);
+ drawDigitChar (st, upcBitmap, textX + i*6, textY, digits[i]);
}
}
/* draw the actual barcode part of a UPC-A barcode */
-void drawUpcABars (Bitmap *upcBitmap, char *digits, int x, int y,
- int barY2, int guardY2)
+static void drawUpcABars (Bitmap *upcBitmap, char *digits, int x, int y,
+ int barY2, int guardY2)
{
int i;
}
/* make and return a full-height UPC-A barcode */
-int makeUpcAFull (Bitmap *dest, char *digits, int y)
+static int makeUpcAFull (struct state *st, Bitmap *dest, char *digits, int y)
{
- static int baseWidth = 108;
- static int baseHeight = 60;
+ int baseWidth = 108;
+ int baseHeight = 60;
int height = baseHeight + y;
int i;
bitmapClear (dest);
drawUpcABars (dest, digits, 6, y, height - 10, height - 4);
- drawDigitChar (dest, 0, height - 14, digits[0]);
+ drawDigitChar (st, dest, 0, height - 14, digits[0]);
for (i = 0; i < 5; i++)
{
- drawDigitChar (dest, 18 + i*7, height - 7, digits[i+1]);
- drawDigitChar (dest, 57 + i*7, height - 7, digits[i+6]);
+ drawDigitChar (st, dest, 18 + i*7, height - 7, digits[i+1]);
+ drawDigitChar (st, dest, 57 + i*7, height - 7, digits[i+6]);
}
- drawDigitChar (dest, 103, height - 14, digits[11]);
+ drawDigitChar (st, dest, 103, height - 14, digits[11]);
return baseWidth;
}
/* make and return a UPC-A barcode */
-int makeUpcA (Bitmap *dest, char *digits, int y)
+static int makeUpcA (struct state *st, Bitmap *dest, char *digits, int y)
{
int i;
unsigned int mul = 3;
digits[11] = ((10 - (sum % 10)) % 10) + '0';
}
- return makeUpcAFull (dest, digits, y);
+ return makeUpcAFull (st, dest, digits, y);
}
/* draw the actual barcode part of a UPC-E barcode */
-void drawUpcEBars (Bitmap *upcBitmap, char *digits, int x, int y,
- int barY2, int guardY2)
+static void drawUpcEBars (struct state *st,
+ Bitmap *upcBitmap, char *digits, int x, int y,
+ int barY2, int guardY2)
{
int i;
int parityPattern = upcELastDigit[charToDigit(digits[7])];
+ int clockp = (st->mode == BC_CLOCK12 || st->mode == BC_CLOCK24);
+
if (digits[0] == '1')
{
parityPattern = ~parityPattern;
}
/* header */
- bitmapVlin (upcBitmap, x, y, guardY2);
+ bitmapVlin (upcBitmap, x, y, guardY2);
bitmapVlin (upcBitmap, x + 2, y, guardY2);
/* trailer */
- bitmapVlin (upcBitmap, x + 46, y, guardY2);
- bitmapVlin (upcBitmap, x + 48, y, guardY2);
- bitmapVlin (upcBitmap, x + 50, y, guardY2);
+ bitmapVlin (upcBitmap, x + 46 + (clockp?8:0), y, guardY2);
+ bitmapVlin (upcBitmap, x + 48 + (clockp?8:0), y, guardY2);
+ bitmapVlin (upcBitmap, x + 50 + (clockp?8:0), y, guardY2);
+
+ /* clock kludge -- this draws an extra set of dividers after
+ digits 2 and 4. This makes this *not* be a valid bar code,
+ but, it looks pretty for the clock dpy.
+ */
+ if (clockp)
+ {
+ bitmapVlin (upcBitmap, x + 18, y, guardY2);
+ bitmapVlin (upcBitmap, x + 18 + 2, y, guardY2);
+
+ bitmapVlin (upcBitmap, x + 36, y, guardY2);
+ bitmapVlin (upcBitmap, x + 36 + 2, y, guardY2);
+ }
for (i = 0; i < 6; i++)
{
UpcSet lset =
(parityPattern & (1 << (5 - i))) ? UPC_LEFT_B : UPC_LEFT_A;
-
+ int off = (clockp
+ ? (i < 2 ? 0 :
+ i < 4 ? 4 : /* extra spacing for clock bars */
+ 8)
+ : 0);
drawUpcEanDigit (upcBitmap,
- x + 3 + i*7,
+ x + 3 + i*7 + off,
y,
barY2,
digits[i + 1],
}
/* make and return a full-height UPC-E barcode */
-int makeUpcEFull (Bitmap *dest, char *digits, int y)
+static int makeUpcEFull (struct state *st, Bitmap *dest, char *digits, int y)
{
- static int baseWidth = 64;
- static int baseHeight = 60;
+ int baseWidth = 64;
+ int baseHeight = 60;
int height = baseHeight + y;
int i;
bitmapClear (dest);
- drawUpcEBars (dest, digits, 6, y, height - 10, height - 4);
+ drawUpcEBars (st, dest, digits, 6, y, height - 10, height - 4);
- drawDigitChar (dest, 0, height - 14, digits[0]);
+ drawDigitChar (st, dest, 0, height - 14, digits[0]);
for (i = 0; i < 6; i++)
{
- drawDigitChar (dest, 11 + i*7, height - 7, digits[i+1]);
+ drawDigitChar (st, dest, 11 + i*7, height - 7, digits[i+1]);
}
- drawDigitChar (dest, 59, height - 14, digits[7]);
+ drawDigitChar (st, dest, 59, height - 14, digits[7]);
return baseWidth;
}
* array, or just store '\0' into the first element, if the form factor
* is incorrect; this will also calculate the check digit, if it is
* specified as '?' */
-void expandToUpcADigits (char *compressed, char *expanded)
+static void expandToUpcADigits (char *compressed, char *expanded)
{
int i;
}
/* make and return a UPC-E barcode */
-int makeUpcE (Bitmap *dest, char *digits, int y)
+static int makeUpcE (struct state *st, Bitmap *dest, char *digits, int y)
{
char expandedDigits[13];
char compressedDigits[9];
compressedDigits[7] = expandedDigits[11];
- return makeUpcEFull (dest, compressedDigits, y);
+ return makeUpcEFull (st, dest, compressedDigits, y);
}
/* draw the actual barcode part of a EAN-13 barcode */
-void drawEan13Bars (Bitmap *upcBitmap, char *digits, int x, int y,
- int barY2, int guardY2)
+static void drawEan13Bars (Bitmap *upcBitmap, char *digits, int x, int y,
+ int barY2, int guardY2)
{
int i;
int leftPattern = ean13FirstDigit[charToDigit (digits[0])];
}
/* make and return a full-height EAN-13 barcode */
-int makeEan13Full (Bitmap *dest, char *digits, int y)
+static int makeEan13Full (struct state *st, Bitmap *dest, char *digits, int y)
{
- static int baseWidth = 102;
- static int baseHeight = 60;
+ int baseWidth = 102;
+ int baseHeight = 60;
int height = baseHeight + y;
int i;
bitmapClear (dest);
drawEan13Bars (dest, digits, 6, y, height - 10, height - 4);
- drawDigitChar (dest, 0, height - 7, digits[0]);
+ drawDigitChar (st, dest, 0, height - 7, digits[0]);
for (i = 0; i < 6; i++)
{
- drawDigitChar (dest, 11 + i*7, height - 7, digits[i+1]);
- drawDigitChar (dest, 57 + i*7, height - 7, digits[i+7]);
+ drawDigitChar (st, dest, 11 + i*7, height - 7, digits[i+1]);
+ drawDigitChar (st, dest, 57 + i*7, height - 7, digits[i+7]);
}
return baseWidth;
}
/* make and return an EAN-13 barcode */
-int makeEan13 (Bitmap *dest, char *digits, int y)
+static int makeEan13 (struct state *st, Bitmap *dest, char *digits, int y)
{
int i;
unsigned int mul = 1;
digits[12] = ((10 - (sum % 10)) % 10) + '0';
}
- return makeEan13Full (dest, digits, y);
+ return makeEan13Full (st, dest, digits, y);
}
/* draw the actual barcode part of an EAN-8 barcode */
-void drawEan8Bars (Bitmap *upcBitmap, char *digits, int x, int y,
- int barY2, int guardY2)
+static void drawEan8Bars (Bitmap *upcBitmap, char *digits, int x, int y,
+ int barY2, int guardY2)
{
int i;
}
/* make and return a full-height EAN-8 barcode */
-int makeEan8Full (Bitmap *dest, char *digits, int y)
+static int makeEan8Full (struct state *st, Bitmap *dest, char *digits, int y)
{
- static int baseWidth = 68;
- static int baseHeight = 60;
+ int baseWidth = 68;
+ int baseHeight = 60;
int height = baseHeight + y;
int i;
for (i = 0; i < 4; i++)
{
- drawDigitChar (dest, 5 + i*7, height - 7, digits[i]);
- drawDigitChar (dest, 37 + i*7, height - 7, digits[i+4]);
+ drawDigitChar (st, dest, 5 + i*7, height - 7, digits[i]);
+ drawDigitChar (st, dest, 37 + i*7, height - 7, digits[i+4]);
}
return baseWidth;
}
/* make and return an EAN-8 barcode */
-int makeEan8 (Bitmap *dest, char *digits, int y)
+static int makeEan8 (struct state *st, Bitmap *dest, char *digits, int y)
{
int i;
unsigned int mul = 3;
digits[7] = ((10 - (sum % 10)) % 10) + '0';
}
- return makeEan8Full (dest, digits, y);
+ return makeEan8Full (st, dest, digits, y);
}
/* Dispatch to the right form factor UPC/EAN barcode generator */
-void processUpcEan (char *str, Bitmap *dest)
+static void processUpcEan (struct state *st, char *str, Bitmap *dest)
{
char digits[16];
int digitCount = 0;
}
else
{
- printf ("Invalid supplement (must be 2 or 5 digits)\n");
+ fprintf (stderr, "%s: invalid supplement (must be 2 or 5 digits)\n",
+ progname);
exit (1);
}
{
case 7:
{
- width = makeUpcE (dest, digits, vstart);
+ width = makeUpcE (st, dest, digits, vstart);
break;
}
case 8:
{
- width = makeEan8 (dest, digits, vstart);
+ width = makeEan8 (st, dest, digits, vstart);
break;
}
case 12:
{
- width = makeUpcA (dest, digits, vstart);
+ width = makeUpcA (st, dest, digits, vstart);
break;
}
case 13:
{
- width = makeEan13 (dest, digits, vstart);
+ width = makeEan13 (st, dest, digits, vstart);
break;
}
default:
{
- printf("Bad barcode\n");
+ fprintf (stderr, "%s: bad barcode (%d digits)\n",
+ progname, digitCount);
exit(1);
}
}
if (supplement)
{
- drawUpcEanSupplementalBars (dest, supDigits,
+ drawUpcEanSupplementalBars (st, dest, supDigits,
width,
vstart + 1, dest->height - 4, 1);
}
*/
/* set up the system */
-static void setup (void)
+static void setup (struct state *st)
{
XWindowAttributes xgwa;
XGCValues gcv;
- XGetWindowAttributes (display, window, &xgwa);
-
- screen = xgwa.screen;
- visual = xgwa.visual;
- cmap = xgwa.colormap;
- windowWidth = xgwa.width;
- windowHeight = xgwa.height;
-
- gcv.background = get_pixel_resource ("background", "Background",
- display, xgwa.colormap);
- gcv.foreground = get_pixel_resource ("foreground", "Foreground",
- display, xgwa.colormap);
- theGC = XCreateGC (display, window, GCForeground|GCBackground, &gcv);
-
- theBitmap = makeBitmap(BARCODE_WIDTH * MAX_MAG, BARCODE_HEIGHT * MAX_MAG);
- theImage = XCreateImage(display, visual, 1, XYBitmap, 0, theBitmap->buf,
- theBitmap->width, theBitmap->height, 8,
- theBitmap->widthBytes);
+ XGetWindowAttributes (st->dpy, st->window, &xgwa);
+
+ st->visual = xgwa.visual;
+ st->cmap = xgwa.colormap;
+ st->windowWidth = xgwa.width;
+ st->windowHeight = xgwa.height;
+
+ gcv.background = get_pixel_resource (st->dpy, xgwa.colormap,
+ "background", "Background");
+ gcv.foreground = get_pixel_resource (st->dpy, xgwa.colormap,
+ "foreground", "Foreground");
+ st->fg_pixel = gcv.foreground;
+ st->theGC = XCreateGC (st->dpy, st->window, GCForeground|GCBackground, &gcv);
+
+ st->theBitmap = makeBitmap(BARCODE_WIDTH * MAX_MAG, BARCODE_HEIGHT * MAX_MAG);
+ st->theImage = XCreateImage(st->dpy, st->visual, 1, XYBitmap, 0, st->theBitmap->buf,
+ st->theBitmap->width, st->theBitmap->height, 8,
+ st->theBitmap->widthBytes);
+ st->theImage->bitmap_bit_order = LSBFirst;
+ st->theImage->byte_order = LSBFirst;
}
*/
/* set up the model */
-static void setupModel (void)
+static void setupModel (struct state *st)
{
int i;
- barcode_max = 20;
- barcode_count = 0;
- barcodes = malloc (sizeof (Barcode) * barcode_max);
+ st->barcode_max = 20;
+ st->barcode_count = 0;
+ st->barcodes = malloc (sizeof (Barcode) * st->barcode_max);
- for (i = 0; i < barcode_max; i++)
+ for (i = 0; i < st->barcode_max; i++)
{
- barcodes[i].bitmap = makeBitmap(BARCODE_WIDTH * MAX_MAG,
+ st->barcodes[i].bitmap = makeBitmap(BARCODE_WIDTH * MAX_MAG,
BARCODE_HEIGHT * MAX_MAG);
}
}
/* make a new barcode string */
-static void makeBarcodeString (char *str)
+static void makeBarcodeString (struct state *st, char *str)
{
int dig, i;
}
/* update the model for one iteration */
-static void scrollModel (void)
+static void scrollModel (struct state *st)
{
int i;
- for (i = 0; i < barcode_count; i++)
+ for (i = 0; i < st->barcode_count; i++)
{
- Barcode *b = &barcodes[i];
+ Barcode *b = &st->barcodes[i];
b->x--;
if ((b->x + BARCODE_WIDTH * b->mag) < 0)
{
/* fell off the edge */
- if (i != (barcode_count - 1)) {
+ if (i != (st->barcode_count - 1)) {
Bitmap *oldb = b->bitmap;
- memmove (b, b + 1, (barcode_count - i - 1) * sizeof (Barcode));
- barcodes[barcode_count - 1].bitmap = oldb;
+ memmove (b, b + 1, (st->barcode_count - i - 1) * sizeof (Barcode));
+ st->barcodes[st->barcode_count - 1].bitmap = oldb;
- XFreeColors (display, cmap, &b->pixel, 1, 0);
+ XFreeColors (st->dpy, st->cmap, &b->pixel, 1, 0);
}
i--;
- barcode_count--;
+ st->barcode_count--;
}
}
- while (barcode_count < barcode_max)
+ while (st->barcode_count < st->barcode_max)
{
- Barcode *barcode = &barcodes[barcode_count];
- barcode->x = (barcode_count == 0) ?
+ Barcode *barcode = &st->barcodes[st->barcode_count];
+ barcode->x = (st->barcode_count == 0) ?
0 :
- (barcodes[barcode_count - 1].x +
- barcodes[barcode_count - 1].mag * BARCODE_WIDTH);
+ (st->barcodes[st->barcode_count - 1].x +
+ st->barcodes[st->barcode_count - 1].mag * BARCODE_WIDTH);
barcode->x += RAND_FLOAT_01 * 100;
barcode->mag = RAND_FLOAT_01 * MAX_MAG;
barcode->y =
- RAND_FLOAT_01 * (windowHeight - BARCODE_HEIGHT * barcode->mag);
+ RAND_FLOAT_01 * (st->windowHeight - BARCODE_HEIGHT * barcode->mag);
if (barcode->y < 0)
{
barcode->y = 0;
}
- makeBarcodeString(barcode->code);
- processUpcEan (barcode->code, theBitmap);
- bitmapScale (barcode->bitmap, theBitmap, barcode->mag);
+ makeBarcodeString(st, barcode->code);
+ processUpcEan (st, barcode->code, st->theBitmap);
+ bitmapScale (barcode->bitmap, st->theBitmap, barcode->mag);
{
XColor c;
- int i, ok = 0;
- for (i = 0; i < 100; i++)
+ int ii, ok = 0;
+ for (ii = 0; ii < 100; ii++)
{
hsv_to_rgb (random() % 360, 1.0, 1.0, &c.red, &c.green, &c.blue);
- ok = XAllocColor (display, cmap, &c);
+ ok = XAllocColor (st->dpy, st->cmap, &c);
if (ok) break;
}
if (!ok)
{
c.red = c.green = c.blue = 0xFFFF;
- if (!XAllocColor (display, cmap, &c))
+ if (!XAllocColor (st->dpy, st->cmap, &c))
abort();
}
barcode->pixel = c.pixel;
}
- barcode_count++;
+ st->barcode_count++;
}
}
/* update the model for one iteration */
-static void updateGrid (void)
+static void updateGrid (struct state *st)
{
int i, x, y;
- static int grid_w = 0;
- static int grid_h = 0;
- static unsigned long pixel;
- static int alloced_p = 0;
-
- static char *strings[200] = { 0, };
-
- if (grid_w == 0 || grid_h == 0 ||
+ if (st->grid_w == 0 || st->grid_h == 0 ||
(! (random() % 400)))
{
- XClearWindow (display, window);
- grid_w = 1 + (random() % 3);
- grid_h = 1 + (random() % 4);
+ XClearWindow (st->dpy, st->window);
+ st->grid_w = 1 + (random() % 3);
+ st->grid_h = 1 + (random() % 4);
}
- if (!alloced_p || (! (random() % 100)))
+ if (!st->grid_alloced_p || (! (random() % 100)))
{
XColor c;
hsv_to_rgb (random() % 360, 1.0, 1.0, &c.red, &c.green, &c.blue);
- if (alloced_p)
- XFreeColors (display, cmap, &pixel, 1, 0);
- XAllocColor (display, cmap, &c);
- pixel = c.pixel;
- alloced_p = 1;
+ if (st->grid_alloced_p)
+ XFreeColors (st->dpy, st->cmap, &st->grid_pixel, 1, 0);
+ XAllocColor (st->dpy, st->cmap, &c);
+ st->grid_pixel = c.pixel;
+ st->grid_alloced_p = 1;
}
- barcode_count = grid_w * grid_h;
- if (barcode_count > barcode_max) abort();
+ st->barcode_count = st->grid_w * st->grid_h;
+ if (st->barcode_count > st->barcode_max) abort();
- for (i = 0; i < barcode_max; i++)
+ for (i = 0; i < st->barcode_max; i++)
{
- Barcode *b = &barcodes[i];
+ Barcode *b = &st->barcodes[i];
b->x = b->y = 999999;
}
i = 0;
- for (y = 0; y < grid_h; y++)
- for (x = 0; x < grid_w; x++, i++)
+ for (y = 0; y < st->grid_h; y++)
+ for (x = 0; x < st->grid_w; x++, i++)
{
- Barcode *b = &barcodes[i];
+ Barcode *b = &st->barcodes[i];
int digits = 12;
- int cell_w = (windowWidth / grid_w);
- int cell_h = (windowHeight / grid_h);
+ int cell_w = (st->windowWidth / st->grid_w);
+ int cell_h = (st->windowHeight / st->grid_h);
int mag_x = cell_w / BARCODE_WIDTH;
int mag_y = cell_h / BARCODE_HEIGHT;
int BW = 108 /*BARCODE_WIDTH*/;
b->x = (x * cell_w) + ((cell_w - b->mag * BW) / 2);
b->y = (y * cell_h) + ((cell_h - b->mag * BH) / 2);
- b->pixel = pixel;
+ b->pixel = st->grid_pixel;
- if (!strings[i])
+ if (!st->strings[i])
{
int j;
char *s = malloc (digits + 10);
- strings[i] = s;
+ st->strings[i] = s;
for (j = 0; j < digits; j++)
s[j] = (random() % 10) + '0';
s[j++] = '?';
s[j++] = ':';
- s[j++] = 0;
+ s[j] = 0;
}
/* change one digit in this barcode */
- strings[i][random() % digits] = (random() % 10) + '0';
+ st->strings[i][random() % digits] = (random() % 10) + '0';
- strcpy (b->code, strings[i]);
- processUpcEan (b->code, b->bitmap);
+ strcpy (b->code, st->strings[i]);
+ processUpcEan (st, b->code, b->bitmap);
}
}
+/* update the model for one iteration.
+ This one draws a clock. By jwz. */
+static void updateClock (struct state *st)
+{
+ Barcode *b = &st->barcodes[0];
+ int BW = 76 /* BARCODE_WIDTH */;
+ int BH = BARCODE_HEIGHT;
+ int mag_x, mag_y;
+ int i;
+ time_t now = time ((time_t *) 0);
+ struct tm *tm = localtime (&now);
+ XWindowAttributes xgwa;
+ int ow = st->windowWidth;
+ int oh = st->windowHeight;
+
+ XGetWindowAttributes (st->dpy, st->window, &xgwa);
+ st->windowWidth = xgwa.width;
+ st->windowHeight = xgwa.height;
+
+ mag_x = st->windowWidth / BW;
+ mag_y = st->windowHeight / BH;
+
+ st->barcode_count = 1;
+
+ b->mag = (mag_x < mag_y ? mag_x : mag_y);
+
+ if (b->mag > MAX_MAG) b->mag = MAX_MAG;
+ if (b->mag < 1) b->mag = 1;
+
+ b->x = (st->windowWidth - (b->mag * BW )) / 2;
+ b->y = (st->windowHeight - (b->mag * (BH + 9))) / 2;
+ b->pixel = st->fg_pixel;
+
+ if (!st->button_down_p)
+ sprintf (b->code, "0%02d%02d%02d?:",
+ (st->mode == BC_CLOCK24
+ ? tm->tm_hour
+ : (tm->tm_hour > 12
+ ? tm->tm_hour - 12
+ : (tm->tm_hour == 0
+ ? 12
+ : tm->tm_hour))),
+ tm->tm_min,
+ tm->tm_sec);
+ else
+ sprintf (b->code, "0%02d%02d%02d?:",
+ tm->tm_year % 100, tm->tm_mon+1, tm->tm_mday);
+
+ {
+ int vstart = 9;
+ int hh = BH + vstart;
+ char expandedDigits[13];
-/* render and display the current model */
-static void renderFrame (void)
+ expandedDigits[0] = '\0';
+
+ expandToUpcADigits (b->code, expandedDigits);
+ if (expandedDigits[0] != '\0')
+ b->code[7] = expandedDigits[11];
+
+ bitmapClear (st->theBitmap);
+ drawUpcEBars (st, st->theBitmap, b->code, 6, 9, 59, 65);
+ for (i = 0; i < 6; i++)
+ {
+ int off = (i < 2 ? 0 :
+ i < 4 ? 4 :
+ 8);
+ drawDigitChar (st, st->theBitmap, 11 + i*7 + off, hh - 16, b->code[i+1]);
+ }
+
+ if (!st->button_down_p)
+ {
+#if 0
+ char *days[] = { "SUN", "MON", "TUE", "WED", "THU", "FRI", "SAT" };
+ char *s = days[tm->tm_wday];
+ bitmapDrawString5x8 (st->theBitmap, (BW - strlen (s)*5) / 2, 0, s);
+#endif
+ drawDigitChar (st, st->theBitmap, 0, hh - 23, (tm->tm_hour < 12 ? 'A' : 'P'));
+ drawDigitChar (st, st->theBitmap, 68, hh - 23, 'M');
+ }
+ else
+ {
+ char s[20];
+ sprintf (s, "%03d", tm->tm_yday);
+ bitmapDrawString5x8 (st->theBitmap, (BW - strlen (s)*5) / 2, 0, s);
+ }
+ }
+
+ bitmapScale (b->bitmap, st->theBitmap, b->mag);
+
+ if (ow != st->windowWidth || oh != st->windowHeight)
+ XClearWindow (st->dpy, st->window);
+}
+
+
+
+/* render and dpy the current model */
+static void renderFrame (struct state *st)
{
int i;
- for (i = 0; i < barcode_count; i++)
+ for (i = 0; i < st->barcode_count; i++)
{
- Barcode *barcode = &barcodes[i];
+ Barcode *barcode = &st->barcodes[i];
- if (barcode->x > windowWidth) {
+ if (barcode->x > st->windowWidth) {
break;
}
- /* bitmapScale (theBitmap, barcode->bitmap, barcode->mag);*/
- theImage->data = barcode->bitmap->buf;
+ /* bitmapScale (st->theBitmap, barcode->bitmap, barcode->mag);*/
+ st->theImage->data = barcode->bitmap->buf;
- XSetForeground (display, theGC, barcode->pixel);
- XPutImage (display, window, theGC, theImage,
+ XSetForeground (st->dpy, st->theGC, barcode->pixel);
+ XPutImage (st->dpy, st->window, st->theGC, st->theImage,
0, 0, barcode->x, barcode->y,
BARCODE_WIDTH * barcode->mag,
BARCODE_HEIGHT * barcode->mag);
}
/* do one iteration */
-static void oneIteration (void)
+static unsigned long
+barcode_draw (Display *dpy, Window win, void *closure)
{
- if (scroll_p)
- scrollModel ();
+ struct state *st = (struct state *) closure;
+ if (st->mode == BC_SCROLL)
+ scrollModel (st);
+ else if (st->mode == BC_GRID)
+ updateGrid (st);
+ else if (st->mode == BC_CLOCK12 || st->mode == BC_CLOCK24)
+ updateClock (st);
else
- updateGrid ();
- renderFrame ();
+ abort();
+
+ renderFrame (st);
+
+ return st->delay;
}
+static Bool
+barcode_event (Display *dpy, Window window, void *closure, XEvent *event)
+{
+ struct state *st = (struct state *) closure;
+ int clockp = (st->mode == BC_CLOCK12 || st->mode == BC_CLOCK24);
+ if (clockp && event->xany.type == ButtonPress) {
+ st->button_down_p = True;
+ return True;
+ } else if (clockp && event->xany.type == ButtonRelease) {
+ st->button_down_p = False;
+ return True;
+ } else
+ return False;
+}
-/* main and options and stuff */
+static void
+barcode_reshape (Display *dpy, Window window, void *closure,
+ unsigned int w, unsigned int h)
+{
+ struct state *st = (struct state *) closure;
+ st->windowWidth = w;
+ st->windowHeight = h;
+}
-char *progclass = "Barcode";
+static void
+barcode_free (Display *dpy, Window window, void *closure)
+{
+}
+
+
+/* main and options and stuff */
-char *defaults [] = {
+static const char *barcode_defaults [] = {
".background: black",
- ".foreground: white",
+ ".foreground: green",
+ "*fpsSolid: true",
"*delay: 10000",
+ "*mode: scroll",
0
};
-XrmOptionDescRec options [] = {
+static XrmOptionDescRec barcode_options [] = {
{ "-delay", ".delay", XrmoptionSepArg, 0 },
+ { "-mode", ".mode", XrmoptionSepArg, 0 },
+ { "-scroll", ".mode", XrmoptionNoArg, "scroll" },
+ { "-grid", ".mode", XrmoptionNoArg, "grid" },
+ { "-clock", ".mode", XrmoptionNoArg, "clock" },
+ { "-clock12", ".mode", XrmoptionNoArg, "clock12" },
+ { "-clock24", ".mode", XrmoptionNoArg, "clock24" },
{ 0, 0, 0, 0 }
};
/* initialize the user-specifiable params */
-static void initParams (void)
+static void initParams (struct state *st)
{
int problems = 0;
+ char *s;
- delay = get_integer_resource ("delay", "Delay");
- if (delay < 0)
+ st->delay = get_integer_resource (st->dpy, "delay", "Delay");
+ if (st->delay < 0)
{
- fprintf (stderr, "error: delay must be at least 0\n");
+ fprintf (stderr, "%s: delay must be at least 0\n", progname);
problems = 1;
}
- scroll_p = 1;
+ s = get_string_resource (st->dpy, "mode", "Mode");
+ if (!s || !*s || !strcasecmp (s, "scroll"))
+ st->mode = BC_SCROLL;
+ else if (!strcasecmp (s, "grid"))
+ st->mode = BC_GRID;
+ else if (!strcasecmp (s, "clock") ||
+ !strcasecmp (s, "clock12"))
+ st->mode = BC_CLOCK12;
+ else if (!strcasecmp (s, "clock24"))
+ st->mode = BC_CLOCK24;
+ else
+ {
+ fprintf (stderr, "%s: unknown mode \"%s\"\n", progname, s);
+ problems = 1;
+ }
+ free (s);
+
+ if (st->mode == BC_CLOCK12 || st->mode == BC_CLOCK24)
+ st->delay = 10000; /* only update every 1/10th second */
if (problems)
{
}
}
-/* main function */
-void screenhack (Display *dpy, Window win)
+static void *
+barcode_init (Display *dpy, Window win)
{
- display = dpy;
- window = win;
+ struct state *st = (struct state *) calloc (1, sizeof(*st));
+ st->dpy = dpy;
+ st->window = win;
+
+ initParams (st);
+ setup (st);
+ setupModel (st);
+ return st;
+}
- initParams ();
- setup ();
- setupModel ();
- for (;;)
- {
- oneIteration ();
- XSync (dpy, False);
- screenhack_handle_events (dpy);
- usleep (delay);
- }
-}
+XSCREENSAVER_MODULE ("Barcode", barcode)