⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 nxroach.x

📁 神龙卡开发原代码
💻 X
字号:
/*    Xroach - A game of skill.  Try to find the roaches under your windows.        Copyright 1991 by J.T. Anderson    jta@locus.com        This program may be freely distributed provided that all    copyright notices are retained.    To build:      cc -o xroach roach.c -lX11 [-lsocketorwhatever] [-lm] [-l...]    Dedicated to Greg McFarlane.   (gregm@otc.otca.oz.au)*///#include <X11/Xlib.h>//#include <X11/Xutil.h>//#include <X11/Xos.h>#include <stdio.h>#include <math.h>#include <signal.h>#include <stdlib.h>#include <time.h>#define MWINCLUDECOLORS#include "nano-X.h"#include "XtoNX.h"char Copyright[] = "Xroach\nCopyright 1991 J.T. Anderson";#include "roachmap.h"typedef unsigned long Pixel;typedef int ErrorHandler();#define SCAMPER_EVENT	99		// LASTEvent+1?#if !defined(GRAB_SERVER)#define GRAB_SERVER	0#endifSTATIC_FUNCTIONS;Display *display;int screen;Window rootWin;unsigned int display_width, display_height;int center_x, center_y;GC gc;char *display_name = NULL;Pixel black, white;int done = 0;int eventBlock = 0;int errorVal = 0;typedef struct Roach {    RoachMap *rp;    int index;    float x;    float y;    int intX;    int intY;    int hidden;    int turnLeft;    int steps;} Roach;Roach *roaches;int maxRoaches = 10;int curRoaches = 0;float roachSpeed = 20.0;Region rootVisible = 0;void Usage(void);void SigHandler(int sig);void AddRoach(void);void MoveRoach(int Rx);void DrawRoaches(void);void CoverRoot(void);int CalcRootVisible(void);int MarkHiddenRoaches(void);//Pixel AllocNamedColor();intmain(int ac, char **av){    //XGCValues xgcv;    int ax;    char *arg;    RoachMap *rp;    int rx;    float angle;    XEvent ev;    char *roachColor = "black";    int nVis;    int needCalc;        /*       Process command line options.    */    for (ax=1; ax<ac; ax++) {	arg = av[ax];	if (strcmp(arg, "-display") == 0) {	    display_name = av[++ax];	}	else if (strcmp(arg, "-rc") == 0) {	    roachColor = av[++ax];	}	else if (strcmp(arg, "-speed") == 0) {	    roachSpeed = atof(av[++ax]);	}	else if (strcmp(arg, "-roaches") == 0) {	    maxRoaches = strtol(av[++ax], (char **)NULL, 0);	}	else {	    Usage();	}    }    srand((int)time((long *)NULL));        /*       Catch some signals so we can erase any visible roaches.    */    signal(SIGKILL, SigHandler);    signal(SIGINT, SigHandler);    signal(SIGTERM, SigHandler);    signal(SIGHUP, SigHandler);    display = XOpenDisplay(display_name);    if (display == NULL) {	if (display_name == NULL) display_name = getenv("DISPLAY");	(void) fprintf(stderr, "%s: cannot connect to server %s\n", av[0],	    display_name ? display_name : "(default)");	exit(1);    }    screen = DefaultScreen(display);    rootWin = RootWindow(display, screen);    black = BlackPixel(display, screen);    white = WhitePixel(display, screen);    display_width = DisplayWidth(display, screen);    display_height = DisplayHeight(display, screen);    center_x = display_width / 2;    center_y = display_height / 2;        /*       Create roach pixmaps at several orientations.    */    for (ax=0; ax<360; ax+=ROACH_ANGLE) {	rx = ax / ROACH_ANGLE;	angle = rx * 0.261799387799;	rp = &roachPix[rx];	//rp->pixmap = XCreateBitmapFromData(display, rootWin,	    //rp->roachBits, rp->width, rp->height);	rp->pixmap = XCreatePixmapFromBitmapData(display, rootWin,	    rp->roachBits, rp->width, rp->height, BLACK, CYAN, 1);	//FIXME	rp->sine = sin(angle);	rp->cosine = cos(angle);    }    roaches = (Roach *)malloc(sizeof(Roach) * maxRoaches);    gc = XCreateGC(display, rootWin, 0L, &xgcv);    //XSetForeground(display, gc, AllocNamedColor(roachColor, black));    //XSetFillStyle(display, gc, FillStippled);        while (curRoaches < maxRoaches)	AddRoach();        XSelectInput(display, rootWin, ExposureMask | SubstructureNotifyMask);        needCalc = 1;    while (!done) {	if (XPending(display)) {	    XNextEvent(display, &ev);	}	else {	    if (needCalc) {		needCalc = CalcRootVisible();	    }	    nVis = MarkHiddenRoaches();	    if (nVis) {		ev.type = SCAMPER_EVENT;	    }	    else {		DrawRoaches();		GrDelay(100);		eventBlock = 1;		XNextEvent(display, &ev);		eventBlock = 0;	    }	}		switch (ev.type) {	    	    case SCAMPER_EVENT:		for (rx=0; rx<curRoaches; rx++) {		    if (!roaches[rx].hidden)			MoveRoach(rx);		}		DrawRoaches();		GrDelay(100);		XSync(display, False);		break;			    case Expose:	    //case MapNotify:	    //case UnmapNotify:	    case ConfigureNotify:		needCalc = 1;		break;			}    }        CoverRoot();        XCloseDisplay(display);    return 0;}#define USEPRT(msg) fprintf(stderr, msg)voidUsage(void){    USEPRT("Usage: nxroach [options]\n\n");    USEPRT("Options:\n");    USEPRT("       -display displayname\n");    USEPRT("       -rc      roachcolor\n");    USEPRT("       -roaches numroaches\n");    USEPRT("       -speed   roachspeed\n");        exit(1);}voidSigHandler(int sig){           /*       If we are blocked, no roaches are visible and we can just bail       out.  If we are not blocked, then let the main procedure clean       up the root window.    */    if (eventBlock) {	XCloseDisplay(display);	exit(0);    }    else {	done = 1;    }}/*   Generate random integer between 0 and maxVal-1.*/intRandInt(int maxVal){	return rand() % maxVal;}/*   Check for roach completely in specified rectangle.*/intRoachInRect(roach, rx, ry, x, y, width, height)Roach *roach;int rx;int ry;int x;int y;unsigned int width;unsigned int height;{    if (rx < x) return 0;    if ((rx + roach->rp->width) > (x + width)) return 0;    if (ry < y) return 0;    if ((ry + roach->rp->height) > (y + height)) return 0;        return 1;}/*   Check for roach overlapping specified rectangle.*/intRoachOverRect(roach, rx, ry, x, y, width, height)Roach *roach;int rx;int ry;int x;int y;unsigned int width;unsigned int height;{    if (rx >= (x + width)) return 0;    if ((rx + roach->rp->width) <= x) return 0;    if (ry >= (y + height)) return 0;    if ((ry + roach->rp->height) <= y) return 0;        return 1;}/*   Give birth to a roach.*/voidAddRoach(void){    Roach *r;        if (curRoaches < maxRoaches) {	r = &roaches[curRoaches++];	r->index = RandInt(ROACH_HEADINGS);	r->rp = &roachPix[r->index];	r->x = RandInt(display_width - r->rp->width);	r->y = RandInt(display_height - r->rp->height);	r->intX = -1;	r->intY = -1;	r->hidden = 0;	r->steps = RandInt(200);	r->turnLeft = RandInt(100) >= 50;    }}/*   Turn a roach.*/voidTurnRoach(roach)Roach *roach;{    if (roach->index != (roach->rp - roachPix)) return;    if (roach->turnLeft) {	roach->index += (RandInt(30) / 10) + 1;	if (roach->index >= ROACH_HEADINGS)	    roach->index -= ROACH_HEADINGS;    }    else {	roach->index -= (RandInt(30) / 10) + 1;	if (roach->index < 0)	    roach->index += ROACH_HEADINGS;    }}/*   Move a roach.*/voidMoveRoach(int rx){    Roach *roach;    Roach *r2;    float newX;    float newY;    int ii;        roach = &roaches[rx];    newX = roach->x + (roachSpeed * roach->rp->cosine);    newY = roach->y - (roachSpeed * roach->rp->sine);        if (RoachInRect(roach, (int)newX, (int)newY, 			    0, 0, display_width, display_height)) {		roach->x = newX;	roach->y = newY;	if (roach->steps-- <= 0) {	    TurnRoach(roach);	    roach->steps = RandInt(200);	}	for (ii=rx+1; ii<curRoaches; ii++) {	    r2 = &roaches[ii];	    if (RoachOverRect(roach, (int)newX, (int)newY,		r2->intX, r2->intY, r2->rp->width, r2->rp->height)) {			TurnRoach(roach);	    }	}    }    else {	TurnRoach(roach);    }}    /*   Draw all roaches.*/voidDrawRoaches(void){    Roach *roach;    int rx;        for (rx=0; rx<curRoaches; rx++) {	roach = &roaches[rx];		if (roach->intX >= 0) {	    XClearArea(display, rootWin, roach->intX, roach->intY,		roach->rp->width, roach->rp->height, False);	}    }        for (rx=0; rx<curRoaches; rx++) {	roach = &roaches[rx];		if (!roach->hidden) {	    roach->intX = roach->x;	    roach->intY = roach->y;	    roach->rp = &roachPix[roach->index];    	    //XSetStipple(display, gc, roach->rp->pixmap);	    //XSetTSOrigin(display, gc, roach->intX, roach->intY);	    //XFillRectangle(display, rootWin, gc,		//roach->intX, roach->intY, roach->rp->width, roach->rp->height);	    GrCopyArea(GR_ROOT_WINDOW_ID, gc, roach->intX, roach->intY,		roach->rp->width, roach->rp->height, roach->rp->pixmap, 0, 0,		MWROP_SRCCOPY);	}	else {	    roach->intX = -1;	}    }}/*   Cover root window to erase roaches.*/voidCoverRoot(void){    //XSetWindowAttributes xswa;    //long wamask;    Window roachWin;    #define CopyFromParent	0#define InputOutput	0    //xswa.background_pixmap = ParentRelative;    //xswa.override_redirect = True;    //wamask = CWBackPixmap | CWOverrideRedirect;    roachWin = XCreateWindow(display, rootWin, 0, 0,		    display_width, display_height, 0, CopyFromParent,		    InputOutput, CopyFromParent, wamask, &xswa);    XLowerWindow(display, roachWin);    XMapWindow(display, roachWin);    XFlush(display);}    #if !GRAB_SERVER#if 0intRoachErrors(dpy, err)Display *dpy;XErrorEvent *err;{    errorVal = err->error_code;        return 0;}#endif#endif /* GRAB_SERVER *//*   Calculate Visible region of root window.*/intCalcRootVisible(void){    Region covered;    Region visible;    Window *children;    int nChildren;    Window dummy;    //XWindowAttributes wa;    int wx;    XRectangle rect;    int winX, winY;    unsigned int winHeight, winWidth;    unsigned int borderWidth;    unsigned int depth;    GR_WINDOW_INFO info;        /*       If we don't grab the server, the XGetWindowAttribute or XGetGeometry       calls can abort us.  On the other hand, the server grabs can make for       some annoying delays.    */#if GRAB_SERVER    //XGrabServer(display);#else    //XSetErrorHandler(RoachErrors);#endif    /*       Get children of root.    */    XQueryTree(display, rootWin, &dummy, &dummy, &children, &nChildren);        /*       For each mapped child, add the window rectangle to the covered       region.    */    covered = XCreateRegion();    for (wx=0; wx<nChildren; wx++) {	//if (XEventsQueued(display, QueuedAlready)) return 1;	//errorVal = 0;	//XGetWindowAttributes(display, children[wx], &wa);	//if (errorVal) continue;	GrGetWindowInfo(children[wx], &info);	//if (wa.map_state == IsViewable) {	if (info.unmapcount == 0) {	    //XGetGeometry(display, children[wx], &dummy, &winX, &winY,		//&winWidth, &winHeight, &borderWidth, &depth);	    //if (errorVal) continue;	    rect.x = info.x;	    rect.y = info.y;	    //rect.width = winWidth + (borderWidth * 2);	    //rect.height = winHeight + (borderWidth * 2);	    rect.width = info.width;	    rect.height = info.height;	    XUnionRectWithRegion(&rect, covered, covered);	}    }    XFree((char *)children);#if GRAB_SERVER    //XUngrabServer(display);#else    //XSetErrorHandler((ErrorHandler *)NULL);#endif        /*       Subtract the covered region from the root window region.    */    visible = XCreateRegion();    rect.x = 0;    rect.y = 0;    rect.width = display_width;    rect.height = display_height;    XUnionRectWithRegion(&rect, visible, visible);    XSubtractRegion(visible, covered, visible);    XDestroyRegion(covered);        /*       Save visible region globally.    */    if (rootVisible)	XDestroyRegion(rootVisible);    rootVisible = visible;            /*       Mark all roaches visible.    */    for (wx=0; wx<curRoaches; wx++) 	roaches[wx].hidden = 0;    return 0;}/*   Mark hidden roaches.*/intMarkHiddenRoaches(void){    int rx;    Roach *r;    int nVisible;        nVisible = 0;    for (rx=0; rx<curRoaches; rx++) {	r = &roaches[rx];		if (!r->hidden) {	    if (r->intX > 0 && XRectInRegion(rootVisible, r->intX, r->intY,			    r->rp->width, r->rp->height) == RectangleOut) {		r->hidden = 1;	    }	    else {		nVisible++;	    }	}    }        return nVisible;}#if 0/*   Allocate a color by name.*/PixelAllocNamedColor(colorName, dfltPix)char *colorName;Pixel dfltPix;{	Pixel pix;	XColor scrncolor;	XColor exactcolor;	if (XAllocNamedColor(display, DefaultColormap(display, screen),		colorName, &scrncolor, &exactcolor)) {		pix = scrncolor.pixel;	}	else {		pix = dfltPix;	}	return pix;}#endif

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -