display.c
上传用户:sunbaby
上传日期:2013-05-31
资源大小:242k
文件大小:17k
源码类别:

mpeg/mp3

开发平台:

Visual C++

  1. /************************************************************************
  2.  *
  3.  *  display.c, X11 interface for tmndecode (H.263 decoder)
  4.  *  Copyright (C) 1995, 1996  Telenor R&D, Norway
  5.  *
  6.  *  Contacts:
  7.  *  Robert Danielsen                  <Robert.Danielsen@nta.no>
  8.  *
  9.  *  Telenor Research and Development  http://www.nta.no/brukere/DVC/
  10.  *  P.O.Box 83                        tel.:   +47 63 84 84 00
  11.  *  N-2007 Kjeller, Norway            fax.:   +47 63 81 00 76
  12.  *
  13.  *  Copyright (C) 1997  University of BC, Canada
  14.  *  Modified by: Michael Gallant <mikeg@ee.ubc.ca>
  15.  *               Guy Cote <guyc@ee.ubc.ca>
  16.  *               Berna Erol <bernae@ee.ubc.ca>
  17.  *               
  18.  *  Contacts:
  19.  *  Michael Gallant                   <mikeg@ee.ubc.ca>
  20.  *
  21.  *  UBC Image Processing Laboratory   http://www.ee.ubc.ca/image
  22.  *  2356 Main Mall                    tel.: +1 604 822 4051
  23.  *  Vancouver BC Canada V6T1Z4        fax.: +1 604 822 5949
  24.  *
  25.  ************************************************************************/
  26. /* Disclaimer of Warranty
  27.  * 
  28.  * These software programs are available to the user without any license fee
  29.  * or royalty on an "as is" basis. The University of British Columbia
  30.  * disclaims any and all warranties, whether express, implied, or
  31.  * statuary, including any implied warranties or merchantability or of
  32.  * fitness for a particular purpose.  In no event shall the
  33.  * copyright-holder be liable for any incidental, punitive, or
  34.  * consequential damages of any kind whatsoever arising from the use of
  35.  * these programs.
  36.  * 
  37.  * This disclaimer of warranty extends to the user of these programs and
  38.  * user's customers, employees, agents, transferees, successors, and
  39.  * assigns.
  40.  * 
  41.  * The University of British Columbia does not represent or warrant that the
  42.  * programs furnished hereunder are free of infringement of any
  43.  * third-party patents.
  44.  * 
  45.  * Commercial implementations of H.263, including shareware, are subject to
  46.  * royalty fees to patent holders.  Many of these patents are general
  47.  * enough such that they are unavoidable regardless of implementation
  48.  * design.
  49.  * 
  50.  */
  51. /* based on mpeg2decode, (C) 1994, MPEG Software Simulation Group and
  52.  * mpeg2play, (C) 1994 Stefan Eckart <stefan@lis.e-technik.tu-muenchen.de>
  53.  * 
  54.  */
  55. /* the Xlib interface is closely modeled after mpeg_play 2.0 by the
  56.  * Berkeley Plateau Research Group */
  57. #include <stdio.h>
  58. #include <stdlib.h>
  59. #include <X11/Xlib.h>
  60. #include <X11/Xutil.h>
  61. #include "display.h"
  62. #ifdef USE_DISPLAY
  63. /* private prototypes */
  64. static void display_image _ANSI_ARGS_ ((XImage * ximage, unsigned char *dithered_image));
  65. /* display related data */
  66. unsigned long wpixel[3];
  67. static unsigned char *dithered_image;
  68. int expand = 0;
  69. int quiet = 1;
  70. int horizontal_size = 176;
  71. int vertical_size = 144;
  72. int coded_picture_width = 176;
  73. int coded_picture_height = 144;
  74. int ref_coded_picture_width = 176, ref_coded_picture_height = 144;
  75. int chrom_width = 88, chrom_height = 72;//, blk_cnt;
  76. int ref_chrom_width = 88, ref_chrom_height = 72;
  77. int matrix_coefficients = 5;
  78. unsigned char * clp = NULL;
  79. unsigned char * clp1 = NULL;
  80. int convmat[8][4]
  81. =
  82. {
  83.   {117504, 138453, 13954, 34903}, /* no sequence_display_extension */
  84.   {117504, 138453, 13954, 34903}, /* ITU-R Rec. 709 (1990) */
  85.   {104597, 132201, 25675, 53279}, /* unspecified */
  86.   {104597, 132201, 25675, 53279}, /* reserved */
  87.   {104448, 132798, 24759, 53109}, /* FCC */
  88.   {104597, 132201, 25675, 53279}, /* ITU-R Rec. 624-4 System B, G */
  89.   {104597, 132201, 25675, 53279}, /* SMPTE 170M */
  90.   {117579, 136230, 16907, 35559}/* SMPTE 240M (1987) */
  91. }  ;
  92. /* X11 related variables */
  93. static Display *display;
  94. static Window window;
  95. static GC gc;
  96. static int dpy_depth;
  97. XImage *ximage;
  98. unsigned char pixel[256];
  99. #define SH_MEM
  100. #ifdef SH_MEM
  101. #include <sys/ipc.h>
  102. #include <sys/shm.h>
  103. #include <X11/extensions/XShm.h>
  104. extern int XShmQueryExtension _ANSI_ARGS_ ((Display * dpy));
  105. extern int XShmGetEventBase _ANSI_ARGS_ ((Display * dpy));
  106. static int HandleXError _ANSI_ARGS_ ((Display * dpy, XErrorEvent * event));
  107. static void InstallXErrorHandler _ANSI_ARGS_ ((void));
  108. static void DeInstallXErrorHandler _ANSI_ARGS_ ((void));
  109. static int shmem_flag;
  110. static XShmSegmentInfo shminfo1, shminfo2;
  111. static int gXErrorFlag;
  112. static int CompletionType = -1;
  113. static int HandleXError (dpy, event)
  114.   Display *dpy;
  115.   XErrorEvent *event;
  116. {
  117.   gXErrorFlag = 1;
  118.   return 0;
  119. }
  120. static void InstallXErrorHandler ()
  121. {
  122.   XSetErrorHandler (HandleXError);
  123.   XFlush (display);
  124. }
  125. static void DeInstallXErrorHandler ()
  126. {
  127.   XSetErrorHandler (NULL);
  128.   XFlush (display);
  129. }
  130. #endif
  131. /* connect to server, create and map window, allocate colors and (shared)
  132.  * memory */
  133. void init_display (char *name, int width, int height)
  134. {
  135.   int crv, cbu, cgu, cgv;
  136.   int y, u, v, r, g, b;
  137.   int i;
  138.   char dummy;
  139.   int screen;
  140.   Visual *visual;
  141.   int dpy_class;
  142.   Colormap cmap;
  143.   int private;
  144.   XColor xcolor;
  145.   unsigned int fg, bg;
  146.   XSizeHints hint;
  147.   XEvent xev;
  148.   XSetWindowAttributes xswa;
  149.   unsigned long tmp_pixel;
  150.   unsigned int mask;
  151.   char *hello = "H.264 Display";
  152.   horizontal_size = width;
  153.   vertical_size = height;
  154.   coded_picture_width = width;
  155.   coded_picture_height = height;
  156.   ref_coded_picture_width = width;
  157.   ref_coded_picture_height = height;
  158.   chrom_width = (width >> 1);
  159.   chrom_height = (height >> 1);
  160.   ref_chrom_width = (width >> 1);
  161.   ref_chrom_height = (height >> 1);
  162.   
  163.   display = XOpenDisplay (name);
  164.   if (display == NULL)
  165.     perror ("Can not open displayn");
  166.   init_dither_tab();
  167.   screen = DefaultScreen (display);
  168.   visual = DefaultVisual (display, screen);
  169.   dpy_depth = DefaultDepth (display, screen);
  170.   dpy_class = visual->class;
  171.   if (!((dpy_class == TrueColor && dpy_depth == 32)
  172.         || (dpy_class == TrueColor && dpy_depth == 24)
  173.         || (dpy_class == TrueColor && dpy_depth == 16)
  174.         || (dpy_class == PseudoColor && dpy_depth == 8)))
  175.     perror ("requires 8 bit PseudoColor or 16/24/32 bit TrueColor displayn");
  176.   if (dpy_class == TrueColor && dpy_depth == 32)
  177.     perror("TrueColor : 32 bit colordepthn");
  178.   if (dpy_class == TrueColor && dpy_depth == 24)
  179.     perror ("TrueColor : 24 bit colordepthn");
  180.   if (dpy_class == TrueColor && dpy_depth == 16)
  181.     perror ("TrueColor : 16 bit colordepthn");
  182.   if (dpy_class == PseudoColor && dpy_depth == 8)
  183.     perror ("PseudoColor : 8 bit colordepth, 4x4 ordered dithern");
  184.   /* width and height of the display window */
  185.   if (expand)
  186.   {
  187.     hint.min_width = hint.max_width = hint.width = 2 * horizontal_size;
  188.     hint.min_height = hint.max_height = hint.height = 2 * vertical_size;
  189.   } else
  190.   {
  191.     hint.min_width = hint.max_width = hint.width = horizontal_size;
  192.     hint.min_height = hint.max_height = hint.height = vertical_size;
  193.   }
  194.   hint.flags = PSize | PMinSize | PMaxSize;
  195.   /* Get some colors */
  196.   bg = WhitePixel (display, screen);
  197.   fg = BlackPixel (display, screen);
  198.   /* Make the window */
  199.   mask = CWBackPixel | CWBorderPixel;
  200.   if (dpy_depth == 32 || dpy_depth == 24 || dpy_depth == 16)
  201.   {
  202.     mask |= CWColormap;
  203.     xswa.colormap = XCreateColormap (display, DefaultRootWindow (display),
  204.                                      visual, AllocNone);
  205.   }
  206.   xswa.background_pixel = bg;
  207.   xswa.border_pixel = fg;
  208.   window = XCreateWindow (display, DefaultRootWindow (display),
  209.                           hint.x, hint.y, hint.width, hint.height,
  210.                           1, dpy_depth, InputOutput, visual, mask, &xswa);
  211.   XSelectInput (display, window, StructureNotifyMask);
  212.   /* Tell other applications about this window */
  213.   XSetStandardProperties (display, window, hello, hello, None, NULL, 0, &hint);
  214.   /* Map window. */
  215.   XMapWindow (display, window);
  216.   /* Wait for map. */
  217.   do
  218.   {
  219.     XNextEvent (display, &xev);
  220.   }
  221.   while (xev.type != MapNotify || xev.xmap.event != window);
  222.   XSelectInput (display, window, NoEventMask);
  223.   /* allocate colors */
  224.   gc = DefaultGC (display, screen);
  225.   if (dpy_depth == 8)
  226.   {
  227.     XWindowAttributes xwa;
  228.     cmap = DefaultColormap (display, screen);
  229.     private = 0;
  230.     /* matrix coefficients */
  231.     crv = convmat[matrix_coefficients][0];
  232.     cbu = convmat[matrix_coefficients][1];
  233.     cgu = convmat[matrix_coefficients][2];
  234.     cgv = convmat[matrix_coefficients][3];
  235.     /* color allocation: i is the (internal) 8 bit color number, it
  236.      * consists of separate bit fields for Y, U and V: i = (yyyyuuvv), we
  237.      * don't use yyyy=0000 yyyy=0001 and yyyy=1111, this leaves 48 colors
  238.      * for other applications
  239.      * 
  240.      * the allocated colors correspond to the following Y, U and V values: Y:
  241.      * 40, 56, 72, 88, 104, 120, 136, 152, 168, 184, 200, 216, 232 U,V:
  242.      * -48, -16, 16, 48
  243.      * 
  244.      * U and V values span only about half the color space; this gives
  245.      * usually much better quality, although highly saturated colors can
  246.      * not be displayed properly
  247.      * 
  248.      * translation to R,G,B is implicitly done by the color look-up table */
  249.     for (i = 32; i < 240; i++)
  250.     {
  251.       /* color space conversion */
  252.       y = 16 * ((i >> 4) & 15) + 8;
  253.       u = 32 * ((i >> 2) & 3) - 48;
  254.       v = 32 * (i & 3) - 48;
  255.       y = 76309 * (y - 16);     /* (255/219)*65536 */
  256.       r = clp[(y + crv * v + 32768) >> 16];
  257.       g = clp[(y - cgu * u - cgv * v + 32768) >> 16];
  258.       b = clp[(y + cbu * u + 32786) >> 16];
  259.       /* X11 colors are 16 bit */
  260.       xcolor.red = r << 8;
  261.       xcolor.green = g << 8;
  262.       xcolor.blue = b << 8;
  263.       if (XAllocColor (display, cmap, &xcolor) != 0)
  264.         pixel[i] = xcolor.pixel;
  265.       else
  266.       {
  267.         /* allocation failed, have to use a private colormap */
  268.         if (private)
  269.           perror ("Couldn't allocate private colormap");
  270.         private = 1;
  271.         if (!quiet)
  272.         {
  273.           char tmp[256];
  274.           sprintf(tmp,"nerror: Using private colormap (%d colors were "
  275.                    "available).n", i - 32);
  276.           perror(tmp);
  277.         }
  278.         /* Free colors. */
  279.         while (--i >= 32)
  280.         {
  281.           tmp_pixel = pixel[i]; /* because XFreeColors expects unsigned
  282.                                  * long */
  283.           XFreeColors (display, cmap, &tmp_pixel, 1, 0);
  284.         }
  285.         /* i is now 31, this restarts the outer loop */
  286.         /* create private colormap */
  287.         XGetWindowAttributes (display, window, &xwa);
  288.         cmap = XCreateColormap (display, window, xwa.visual, AllocNone);
  289.         XSetWindowColormap (display, window, cmap);
  290.       }
  291.     }
  292.   }
  293. #ifdef SH_MEM
  294.   if (XShmQueryExtension (display))
  295.     shmem_flag = 1;
  296.   else
  297.   {
  298.     shmem_flag = 0;
  299.     if (!quiet)
  300.       perror("nerror: Shared memory not supportednReverting to normal "
  301.                "Xlibn");
  302.   }
  303.   if (shmem_flag)
  304.     CompletionType = XShmGetEventBase (display) + ShmCompletion;
  305.   InstallXErrorHandler ();
  306.   if (shmem_flag)
  307.   {
  308.     if (expand)
  309.       ximage = XShmCreateImage (display, visual, dpy_depth, ZPixmap, NULL,
  310.                                 &shminfo1,
  311.                       2 * coded_picture_width, 2 * coded_picture_height);
  312.     else
  313.       ximage = XShmCreateImage (display, visual, dpy_depth, ZPixmap, NULL,
  314.                                 &shminfo1,
  315.                               coded_picture_width, coded_picture_height);
  316.     /* If no go, then revert to normal Xlib calls. */
  317.     if (ximage == NULL)
  318.     {
  319.       if (ximage != NULL)
  320.         XDestroyImage (ximage);
  321.       if (!quiet)
  322.         perror("nerror: Shared memory error, disabling (Ximage error)n");
  323.       goto shmemerror;
  324.     }
  325.     /* Success here, continue. */
  326.     shminfo1.shmid = shmget (IPC_PRIVATE,
  327.                              ximage->bytes_per_line * ximage->height,
  328.                              IPC_CREAT | 0777);
  329.     if (shminfo1.shmid < 0)
  330.     {
  331.       XDestroyImage (ximage);
  332.       if (!quiet)
  333.         perror("nerror: Shared memory error, disabling (seg id error)n");
  334.       goto shmemerror;
  335.     }
  336.     shminfo1.shmaddr = (char *) shmat (shminfo1.shmid, 0, 0);
  337.     shminfo2.shmaddr = (char *) shmat (shminfo2.shmid, 0, 0);
  338.     if (shminfo1.shmaddr == ((char *) -1))
  339.     {
  340.       XDestroyImage (ximage);
  341.       if (shminfo1.shmaddr != ((char *) -1))
  342.         shmdt (shminfo1.shmaddr);
  343.       if (!quiet)
  344.       {
  345.         perror("nerror: Shared memory error, disabling (address error)n");
  346.       }
  347.       goto shmemerror;
  348.     }
  349.     ximage->data = shminfo1.shmaddr;
  350.     dithered_image = (unsigned char *) ximage->data;
  351.     shminfo1.readOnly = False;
  352.     XShmAttach (display, &shminfo1);
  353.     XSync (display, False);
  354.     if (gXErrorFlag)
  355.     {
  356.       /* Ultimate failure here. */
  357.       XDestroyImage (ximage);
  358.       shmdt (shminfo1.shmaddr);
  359.       if (!quiet)
  360.         perror("nerror: Shared memory error, disabling.n");
  361.       gXErrorFlag = 0;
  362.       goto shmemerror;
  363.     } else
  364.     {
  365.       shmctl (shminfo1.shmid, IPC_RMID, 0);
  366.     }
  367.     if (!quiet)
  368.     {
  369.       perror("nerror: Sharing memory.n");
  370.     }
  371.   } else
  372.   {
  373. shmemerror:
  374.     shmem_flag = 0;
  375. #endif
  376.     if (expand)
  377.     {
  378.       ximage = XCreateImage (display, visual, dpy_depth, ZPixmap, 0, &dummy,
  379.                 2 * coded_picture_width, 2 * coded_picture_height, 8, 0);
  380.       if (!(dithered_image =
  381.             (unsigned char *) malloc (coded_picture_width * coded_picture_height *
  382.                                       (dpy_depth > 8 ? sizeof (int) * 4 :
  383.                                        sizeof (unsigned char)) * 4)))
  384.         perror ("malloc failed");
  385.     } else
  386.     {
  387.       ximage = XCreateImage (display, visual, dpy_depth, ZPixmap, 0, &dummy,
  388.                         coded_picture_width, coded_picture_height, 8, 0);
  389.       if (!(dithered_image =
  390.             (unsigned char *) malloc (coded_picture_width * coded_picture_height *
  391.                                       (dpy_depth > 8 ? sizeof (int) :
  392.                                        sizeof (unsigned char)))))
  393.         perror ("malloc failed");
  394.     }
  395. #ifdef SH_MEM
  396.   }
  397.   DeInstallXErrorHandler ();
  398. #endif
  399.   if (dpy_depth == 32 || dpy_depth == 24 || dpy_depth == 16)
  400.   {
  401.     XWindowAttributes xwa;
  402.     XGetWindowAttributes (display, window, &xwa);
  403.     wpixel[0] = xwa.visual->red_mask;
  404.     wpixel[1] = xwa.visual->green_mask;
  405.     wpixel[2] = xwa.visual->blue_mask;
  406.     /* If the colors in 16/24/32-bit mode are wrong, try this instead of
  407.      * the above three lines */
  408.     /* wpixel[2] = xwa.visual->red_mask; wpixel[1] =
  409.      * xwa.visual->green_mask; wpixel[0] = xwa.visual->blue_mask; */
  410.     InitColorDither (dpy_depth == 24 || dpy_depth == 32);
  411.   } else
  412.   {
  413.     ord4x4_dither_init ();
  414.   }
  415. }
  416. void exit_display ()
  417. {
  418. #ifdef SH_MEM
  419.   if (shmem_flag)
  420.   {
  421.     XShmDetach (display, &shminfo1);
  422.     XDestroyImage (ximage);
  423.     shmdt (shminfo1.shmaddr);
  424.   }
  425. #endif
  426.   if(clp1 != NULL)
  427.   {
  428.     free(clp1);
  429.     clp1 = NULL;
  430.   }
  431. }
  432. static void display_image (ximage, dithered_image)
  433.   XImage *ximage;
  434.   unsigned char *dithered_image;
  435. {
  436.   int t = 1;
  437.   /* Always work in native bit and byte order. This tells Xlib to reverse
  438.    * bit and byte order if necessary when crossing a network. Frankly,
  439.    * this part of XImages is somewhat underdocumented, so this may not be
  440.    * exactly correct.  */
  441.   if (*(char *) &t == 1)
  442.   {
  443.     ximage->byte_order = LSBFirst;
  444.     ximage->bitmap_bit_order = LSBFirst;
  445.   } else
  446.   {
  447.     ximage->byte_order = MSBFirst;
  448.     ximage->bitmap_bit_order = MSBFirst;
  449.   }
  450.   /* display dithered image */
  451. #ifdef SH_MEM
  452.   if (shmem_flag)
  453.   {
  454.     XShmPutImage (display, window, gc, ximage,
  455.                   0, 0, 0, 0, ximage->width, ximage->height, True);
  456.     XFlush (display);
  457.     while (1)
  458.     {
  459.       XEvent xev;
  460.       XNextEvent (display, &xev);
  461.       if (xev.type == CompletionType)
  462.         break;
  463.     }
  464.   } else
  465. #endif
  466.   {
  467.     ximage->data = (char *) dithered_image;
  468.     XPutImage (display, window, gc, ximage, 0, 0, 0, 0, ximage->width, ximage->height);
  469.   }
  470. }
  471. void dither (src)
  472.   unsigned char *src[];
  473. {
  474.   if (dpy_depth == 24 || dpy_depth == 32)
  475.   {
  476.     if (ximage->bits_per_pixel == 24)
  477.       ConvertYUVtoRGB (src[0], src[1], src[2], dithered_image,
  478.                        coded_picture_width,
  479.                        coded_picture_height);
  480.     else
  481.       Color32DitherImage (src, dithered_image);
  482.   } else if (dpy_depth == 16)
  483.   {
  484.     Color16DitherImage (src, dithered_image);
  485.   } else
  486.   {
  487.     ord4x4_dither_frame (src, dithered_image);
  488.   }
  489.   display_image (ximage, dithered_image);
  490. }
  491. #endif