📄 display.c
字号:
/* display.c, X11 interface *//* Copyright (C) 1996, MPEG Software Simulation Group. All Rights Reserved. *//* * Disclaimer of Warranty * * These software programs are available to the user without any license fee or * royalty on an "as is" basis. The MPEG Software Simulation Group disclaims * any and all warranties, whether express, implied, or statuary, including any * implied warranties or merchantability or of fitness for a particular * purpose. In no event shall the copyright-holder be liable for any * incidental, punitive, or consequential damages of any kind whatsoever * arising from the use of these programs. * * This disclaimer of warranty extends to the user of these programs and user's * customers, employees, agents, transferees, successors, and assigns. * * The MPEG Software Simulation Group does not represent or warrant that the * programs furnished hereunder are free of infringement of any third-party * patents. * * Commercial implementations of MPEG-1 and MPEG-2 video, including shareware, * are subject to royalty fees to patent holders. Many of these patents are * general enough such that they are unavoidable regardless of implementation * design. * */#ifdef DISPLAY /* the Xlib interface is closely modeled after * mpeg_play 2.0 by the Berkeley Plateau Research Group */#include <stdio.h>#include <stdlib.h>#include <X11/Xlib.h>#include <X11/Xutil.h>#include "config.h"#include "global.h"/* private prototypes */static void Display_Image _ANSI_ARGS_((XImage *Ximage_Ptr, unsigned char *Dithered_Image));static void Dither_Frame _ANSI_ARGS_((unsigned char *src[]));static void Dither_Top_Field _ANSI_ARGS_((unsigned char *src[], unsigned char *dst));static void Dither_Bottom_Field _ANSI_ARGS_((unsigned char *src[], unsigned char *dst));static void Dither_Top_Field420 _ANSI_ARGS_((unsigned char *src[], unsigned char *dst));static void Dither_Bottom_Field420 _ANSI_ARGS_((unsigned char *src[], unsigned char *dst));/* local data */static unsigned char *Dithered_Image, *Dithered_Image2;static unsigned char Y_Table[256+16];static unsigned char Cb_Table[128+16];static unsigned char Cr_Table[128+16];/* X11 related variables */static Display *Display_Ptr;static Window Window_Instance;static GC GC_Instance;static XImage *Ximage_Ptr, *Ximage_Ptr2;static unsigned char Pixel[256];#ifdef SH_MEM#include <sys/ipc.h>#include <sys/shm.h>#include <X11/extensions/XShm.h>static int HandleXError _ANSI_ARGS_((Display *dpy, XErrorEvent *event));static void InstallXErrorHandler _ANSI_ARGS_((void));static void DeInstallXErrorHandler _ANSI_ARGS_((void));static int Shmem_Flag;static XShmSegmentInfo Shminfo1, Shminfo2;static int gXErrorFlag;static int CompletionType = -1;static int HandleXError(Dpy, Event)Display *Dpy;XErrorEvent *Event;{ gXErrorFlag = 1; return 0;}static void InstallXErrorHandler(){ XSetErrorHandler(HandleXError); XFlush(Display_Ptr);}static void DeInstallXErrorHandler(){ XSetErrorHandler(NULL); XFlush(Display_Ptr);}#endif/* connect to server, create and map window, * allocate colors and (shared) memory */void Initialize_Display_Process(name)char *name;{ int crv, cbu, cgu, cgv; int Y, Cb, Cr, R, G, B; int i; char dummy; int screen; Colormap cmap; int private; XColor xcolor; unsigned int fg, bg; char *hello = "MPEG-2 Display"; XSizeHints hint; XVisualInfo vinfo; XEvent xev; unsigned long tmp_pixel; XWindowAttributes xwa; Display_Ptr = XOpenDisplay(name); if (Display_Ptr == NULL) Error("Can not open display\n"); screen = DefaultScreen(Display_Ptr); hint.x = 200; hint.y = 200; hint.width = horizontal_size; hint.height = vertical_size; hint.flags = PPosition | PSize; /* Get some colors */ bg = WhitePixel (Display_Ptr, screen); fg = BlackPixel (Display_Ptr, screen); /* Make the window */ if (!XMatchVisualInfo(Display_Ptr, screen, 8, PseudoColor, &vinfo)) { if (!XMatchVisualInfo(Display_Ptr, screen, 8, GrayScale, &vinfo)) Error("requires 8 bit display\n"); } Window_Instance = XCreateSimpleWindow (Display_Ptr, DefaultRootWindow (Display_Ptr), hint.x, hint.y, hint.width, hint.height, 4, fg, bg); XSelectInput(Display_Ptr, Window_Instance, StructureNotifyMask); /* Tell other applications about this window */ XSetStandardProperties (Display_Ptr, Window_Instance, hello, hello, None, NULL, 0, &hint); /* Map window. */ XMapWindow(Display_Ptr, Window_Instance); /* Wait for map. */ do { XNextEvent(Display_Ptr, &xev); } while (xev.type != MapNotify || xev.xmap.event != Window_Instance); XSelectInput(Display_Ptr, Window_Instance, NoEventMask); /* matrix coefficients */ crv = Inverse_Table_6_9[matrix_coefficients][0]; cbu = Inverse_Table_6_9[matrix_coefficients][1]; cgu = Inverse_Table_6_9[matrix_coefficients][2]; cgv = Inverse_Table_6_9[matrix_coefficients][3]; /* allocate colors */ GC_Instance = DefaultGC(Display_Ptr, screen); cmap = DefaultColormap(Display_Ptr, screen); private = 0; /* color allocation: * i is the (internal) 8 bit color number, it consists of separate * bit fields for Y, U and V: i = (yyyyuuvv), we don't use yyyy=0000 * and yyyy=1111, this leaves 32 colors for other applications * * the allocated colors correspond to the following Y, U and V values: * Y: 24, 40, 56, 72, 88, 104, 120, 136, 152, 168, 184, 200, 216, 232 * U,V: -48, -16, 16, 48 * * U and V values span only about half the color space; this gives * usually much better quality, although highly saturated colors can * not be displayed properly * * translation to R,G,B is implicitly done by the color look-up table */ for (i=16; i<240; i++) { /* color space conversion */ Y = 16*((i>>4)&15) + 8; Cb = 32*((i>>2)&3) - 48; Cr = 32*(i&3) - 48; Y = 76309 * (Y - 16); /* (255/219)*65536 */ R = Clip[(Y + crv*Cr + 32768)>>16]; G = Clip[(Y - cgu*Cb - cgv*Cr + 32768)>>16]; B = Clip[(Y + cbu*Cb + 32786)>>16]; /* X11 colors are 16 bit */ xcolor.red = R << 8; xcolor.green = G << 8; xcolor.blue = B << 8; if (XAllocColor(Display_Ptr, cmap, &xcolor) != 0) Pixel[i] = xcolor.pixel; else { /* allocation failed, have to use a private colormap */ if (private) Error("Couldn't allocate private colormap"); private = 1; if (!Quiet_Flag) fprintf(stderr, "Using private colormap (%d colors were available).\n", i-16); /* Free colors. */ while (--i >= 16) { tmp_pixel = Pixel[i]; /* because XFreeColors expects unsigned long */ XFreeColors(Display_Ptr, cmap, &tmp_pixel, 1, 0); } /* i is now 15, this restarts the outer loop */ /* create private colormap */ XGetWindowAttributes(Display_Ptr, Window_Instance, &xwa); cmap = XCreateColormap(Display_Ptr, Window_Instance, xwa.visual, AllocNone); XSetWindowColormap(Display_Ptr, Window_Instance, cmap); } }#ifdef SH_MEM if (XShmQueryExtension(Display_Ptr)) Shmem_Flag = 1; else { Shmem_Flag = 0; if (!Quiet_Flag) fprintf(stderr, "Shared memory not supported\nReverting to normal Xlib\n"); } if (Shmem_Flag) CompletionType = XShmGetEventBase(Display_Ptr) + ShmCompletion; InstallXErrorHandler(); if (Shmem_Flag) { Ximage_Ptr = XShmCreateImage(Display_Ptr, None, 8, ZPixmap, NULL, &Shminfo1, Coded_Picture_Width, Coded_Picture_Height); if (!progressive_sequence) Ximage_Ptr2 = XShmCreateImage(Display_Ptr, None, 8, ZPixmap, NULL, &Shminfo2, Coded_Picture_Width, Coded_Picture_Height); /* If no go, then revert to normal Xlib calls. */ if (Ximage_Ptr==NULL || (!progressive_sequence && Ximage_Ptr2==NULL)) { if (Ximage_Ptr!=NULL) XDestroyImage(Ximage_Ptr); if (!progressive_sequence && Ximage_Ptr2!=NULL) XDestroyImage(Ximage_Ptr2); if (!Quiet_Flag) fprintf(stderr, "Shared memory error, disabling (Ximage error)\n"); goto shmemerror; } /* Success here, continue. */ Shminfo1.shmid = shmget(IPC_PRIVATE, Ximage_Ptr->bytes_per_line * Ximage_Ptr->height, IPC_CREAT | 0777); if (!progressive_sequence) Shminfo2.shmid = shmget(IPC_PRIVATE, Ximage_Ptr2->bytes_per_line * Ximage_Ptr2->height, IPC_CREAT | 0777); if (Shminfo1.shmid<0 || (!progressive_sequence && Shminfo2.shmid<0)) { XDestroyImage(Ximage_Ptr); if (!progressive_sequence) XDestroyImage(Ximage_Ptr2); if (!Quiet_Flag) fprintf(stderr, "Shared memory error, disabling (seg id error)\n"); goto shmemerror; } Shminfo1.shmaddr = (char *) shmat(Shminfo1.shmid, 0, 0); Shminfo2.shmaddr = (char *) shmat(Shminfo2.shmid, 0, 0); if (Shminfo1.shmaddr==((char *) -1) || (!progressive_sequence && Shminfo2.shmaddr==((char *) -1))) { XDestroyImage(Ximage_Ptr); if (Shminfo1.shmaddr!=((char *) -1)) shmdt(Shminfo1.shmaddr); if (!progressive_sequence) { XDestroyImage(Ximage_Ptr2); if (Shminfo2.shmaddr!=((char *) -1)) shmdt(Shminfo2.shmaddr); } if (!Quiet_Flag) { fprintf(stderr, "Shared memory error, disabling (address error)\n"); } goto shmemerror; } Ximage_Ptr->data = Shminfo1.shmaddr; Dithered_Image = (unsigned char *)Ximage_Ptr->data; Shminfo1.readOnly = False; XShmAttach(Display_Ptr, &Shminfo1); if (!progressive_sequence) { Ximage_Ptr2->data = Shminfo2.shmaddr; Dithered_Image2 = (unsigned char *)Ximage_Ptr2->data; Shminfo2.readOnly = False; XShmAttach(Display_Ptr, &Shminfo2); } XSync(Display_Ptr, False); if (gXErrorFlag) { /* Ultimate failure here. */ XDestroyImage(Ximage_Ptr); shmdt(Shminfo1.shmaddr); if (!progressive_sequence) { XDestroyImage(Ximage_Ptr2); shmdt(Shminfo2.shmaddr); } if (!Quiet_Flag) fprintf(stderr, "Shared memory error, disabling.\n"); gXErrorFlag = 0; goto shmemerror; } else { shmctl(Shminfo1.shmid, IPC_RMID, 0); if (!progressive_sequence) shmctl(Shminfo2.shmid, IPC_RMID, 0); } if (!Quiet_Flag) { fprintf(stderr, "Sharing memory.\n"); } } else {shmemerror: Shmem_Flag = 0;#endif Ximage_Ptr = XCreateImage(Display_Ptr,None,8,ZPixmap,0,&dummy, Coded_Picture_Width,Coded_Picture_Height,8,0); if (!(Dithered_Image = (unsigned char *)malloc(Coded_Picture_Width* Coded_Picture_Height))) Error("malloc failed"); if (!progressive_sequence) { Ximage_Ptr2 = XCreateImage(Display_Ptr,None,8,ZPixmap,0,&dummy, Coded_Picture_Width,Coded_Picture_Height,8,0); if (!(Dithered_Image2 = (unsigned char *)malloc(Coded_Picture_Width* Coded_Picture_Height))) Error("malloc failed"); }#ifdef SH_MEM } DeInstallXErrorHandler();#endif}void Terminate_Display_Process()
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -