/* (c) Copyright 1991-7 Parallax Graphics Inc, All Rights Reserved */ #include #include #include #include #include #include #include #include #include #include #include #define VIDEO 1 #define GRAPHICS 2 plx_IO *XPlxQueryConfig(); plx_signal *XPlxQueryVideo(); plx_IO *plxio = NULL; plx_signal *plxsignal = NULL; static Arg args[25]; static unsigned int n; int videowidth = 640; int videoheight = 480; static XColor this_red, exact_red, this_blue, exact_blue, this_green, exact_green, this_black, exact_black; static XWindowAttributes win_atts; struct time_t *now; struct time_t *before; int first = 1; XGCValues values; GC gcBackground; GC gcForeground; typedef struct VideoWindow { int Width; int Height; } VideoWindow; XVisualInfo* GetTrueColorVisual(int screenNumber, Display* display) { int i; long visualInfoMask; int visualsMatched; XVisualInfo visualHints; static XVisualInfo* visualList = (XVisualInfo*)NULL; XVisualInfo* theVisual; if (visualList != (XVisualInfo*)NULL) /* Was data saved by a previous call to this function? */ XFree((void*)visualList); /* Yes, release the data since it is no longer needed */ visualHints.class = TrueColor; /* Set up hints to determine the type of visual needed... */ visualHints.screen = screenNumber; /* ...to create a window that can display video */ visualInfoMask = (VisualClassMask | VisualScreenMask); /* For Sun, need to get real TrueColor class */ visualList = XGetVisualInfo(display, /* Try to find a visual that matches what is needed for... */ visualInfoMask, /* ... a window that will display video or TrueColor... */ &visualHints, /* ...graphics. */ &visualsMatched); if (visualsMatched == 0) /* Did the search for a TrueColor visual fail? */ return((XVisualInfo*)NULL); /* Yes, return a NULL structure to represent failure */ for (theVisual = visualList, i = 0; /* Look at all the visuals returned by XGetVisualInfo... */ i < visualsMatched; /* ...to find the best match. The idea match would be... */ i++, theVisual++) /* ...a 24-bit depth Visual. */ { if (theVisual->depth == 24) /* Was an ideal match found? */ return(theVisual); /* Yes, return this Visual */ } for (theVisual = visualList, i = 0; /* If this statement is reached, no 24-bit TrueColor... */ i < visualsMatched; /* ...Visual was found; in this case, fallback and try... */ i++, theVisual++) /* ...to find the next best thing: any TrueColor visual... */ { /* ...of depth >= 24 bits (probably a 32-bit is what will... */ if (theVisual->depth >= 24) /* ...be found). */ return(theVisual); /* Was a good fallback Visual found? If so, return it. */ } return(visualList); /* If this statement was reached, no good fallback was... */ /* ...found. In this case, simply return the first... */ /* ...TrueColor visual found. */ } /* end function GetTrueColorVisual */ GetVideoSignal(disp, win, gc, channel) Display *disp; Window win; GC gc; int channel; { plxio = XPlxQueryConfig(disp, win, gc); /* Query the hardware for configuration parameters */ XPlxVideoInputSelect(disp, win, gc, /* Ask for input on channel 0, with the following... */ channel, /* ...characteristics: */ PLX_NTSC, /* Standard = NTSC */ PLX_COMP, /* Format = Composite */ PLX_RGB24); /* Type = RGB24 */ plxsignal = XPlxQueryVideo(disp, win, gc); /* Query the Video to see if sync is there */ while ( !plxsignal->sync_ok ) /* Wait until a signal is input into the board */ { printf(" Sync Absent - Hook up an input source\n"); plxsignal = XPlxQueryVideo(disp, win, gc); /* Query the Video again to check sync */ } videowidth = plxsignal->w; videoheight = plxsignal->h - plxsignal->b; } DrawTime(disp, win, gcBackground, videowindow) Display *disp; Window win; GC gcBackground; VideoWindow videowindow; { char* string; if (first) { time(&before); /* set up "has time changed?" timer */ first = 0; } time(&now); if (now != before) /* time has changed */ { /* Overwrite string with black in order to update it cleanly */ string = ctime(&before); values.foreground = this_black.pixel; XChangeGC(disp,gcBackground,GCForeground|GCBackground|GCPlaneMask,&values); XDrawString(disp, win, gcBackground, 20, videowindow.Height-20, string, strlen(string)-1); /* write string now that time has incremented by one second */ before = now; string = ctime(&now); values.foreground = this_blue.pixel; XChangeGC(disp,gcBackground,GCForeground|GCBackground|GCPlaneMask,&values); XDrawString(disp, win, gcBackground, 20, videowindow.Height-20, string, strlen(string)-1); sleep(1); } } void main(argc, argv) int argc; char **argv; { Window win; Display *disp; int scr, mask; XEvent event; XSetWindowAttributes attr; XVisualInfo vinfo; int depth = 32; XVisualInfo* visualInfo; VideoWindow videowindow; int i; int borderwidth; int Background = 0; int Foreground = 0; int text = False; /* default: do not print text */ XFontStruct *font; char fontname[] = "-adobe-times-medium-r-normal--34-240-100-100-p-170-iso8859-1"; disp = XOpenDisplay(getenv("DISPLAY")); /* Connect your client program with the X server */ scr = (int) XDefaultScreen(disp); /* Get a default screen */ visualInfo = GetTrueColorVisual(scr, disp); /* Get a proper Visual for using 24-bit video in a window */ depth = visualInfo->depth; mask = CWBackPixel | /* WARNING!!! Must set up the colormap, the... */ CWColormap | /* ...background_pixel and the border_pixel to make it... */ CWBorderPixel; /* ...work when the window depth is diff. from root depth. */ attr.colormap = XCreateColormap(disp, XRootWindow(disp, scr), visualInfo->visual, AllocNone); attr.background_pixel = BlackPixel(disp, DefaultScreen(disp)); attr.border_pixel = WhitePixel(disp, DefaultScreen(disp)); win = XCreateWindow(disp, RootWindow(disp, scr), /* Create the drawable for the XPlx calls */ 0, 0, videowidth, videoheight, 1, depth, InputOutput, visualInfo->visual, mask, &attr); XSelectInput(disp, win, ExposureMask | /* Catch exposure events */ ButtonPressMask | /* and button press events */ StructureNotifyMask); /* and window parameter change events */ values.line_width = 3; values.foreground = 0x01; gcBackground = XCreateGC(disp, win, GCForeground | GCLineWidth, &values); /* the foreground gc defalts to video */ gcForeground = XCreateGC(disp, win, 0, NULL); XGetWindowAttributes(disp,win,&win_atts); GetColors(disp); values.foreground = this_blue.pixel; /* blue is a nice color, isn't it? */ /* values.foreground = this_red.pixel; /* values.foreground = this_green.pixel; */ values.background = this_black.pixel; values.plane_mask = -1; XChangeGC(disp,gcBackground,GCForeground|GCBackground|GCPlaneMask,&values); videowindow.Width = videowidth; videowindow.Height = videoheight; borderwidth = 3; GetVideoSignal(disp, win, gcForeground, PLX_INPUT_0); font = XLoadQueryFont(disp, fontname); /* setup to display text */ XSetFont(disp, gcForeground, font->fid); XFlush(disp); XResizeWindow(disp, win, videowidth, videoheight); /* Map windows */ XMapWindow(disp, win); XPlxVideoSqueezeLive(disp, win, gcForeground, 0, 0, videowidth, videoheight, 0, 0, videowindow.Width, videowindow.Height); while (1) /* Show live video with std signal width and height */ { if(XPending(disp)) { XNextEvent(disp, &event); if(event.type == Expose) /* if exposed, have to refresh the Graphics Over Video */ { XPlxVideoSqueezeLive(disp, win, gcForeground, 0, 0, videowidth, videoheight, 0, 0, videowindow.Width, videowindow.Height); DrawTime(disp, win, gcBackground, videowindow); } if(event.type == ButtonPress) { XPlxVideoStop(disp, win, gcForeground); /* Stop video in the window and digitization of the video signal */ XFreeGC(disp, gcForeground); XFreeGC(disp, gcBackground); XCloseDisplay(disp); exit(1); } if(event.type == ConfigureNotify) { int resize = 0; if(event.xconfigure.width != videowindow.Width) { if(event.xconfigure.width > videowidth) { videowindow.Width = videowidth; resize = 1; } else { videowindow.Width = event.xconfigure.width; } } if(event.xconfigure.height != videowindow.Height) { if(event.xconfigure.height > videoheight) { videowindow.Height = videoheight; resize = 1; } else { videowindow.Height = event.xconfigure.height; } } if(resize) { XResizeWindow(disp, win, videowindow.Width, videowindow.Height); } } } DrawTime(disp, win, gcBackground, videowindow); } } /* end program */ static void GetColors(d) Display *d; { XAllocNamedColor(d,win_atts.colormap,"red", &this_red,&exact_red); XAllocNamedColor(d,win_atts.colormap,"blue", &this_blue, &exact_blue); XAllocNamedColor(d,win_atts.colormap,"green", &this_green, &exact_green); XAllocNamedColor(d,win_atts.colormap, "black",&this_black, &exact_black); }