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

📄 jpeg.c

📁 一个机器人开发的相关嵌入式开发源码
💻 C
📖 第 1 页 / 共 3 页
字号:
        {
        out[((by+iy)*o2)/2 + (bx/2) + (ix/2)] = (unsigned char)(((unsigned int)blockBase[(iy*16) + ix] + (unsigned int)blockBase[(iy*16) + ix+ 1])/2) + 0x7F;
         }
      }
      
      for (iy=0; iy<8; iy++)
      {
        for (ix=0; ix<8; ix++)
        {
        out[oo + ((by/2) +iy)*(o2) + (bx/2) + ix] = blockBase[256 + (iy*8) + ix] + 0x7F;
        }
      }

      for (iy=0; iy<8; iy++)
      {
        for (ix=0; ix<8; ix++)
        {
        out[(oo*2) + ((by/2) +iy)*(o2) + (bx/2) + ix] = blockBase[320 + (iy*8) + ix] + 0x7F;
        }
      }
            
      /*  YUV decode for 4:2:0 components
      unsigned int oo = outWidth * outHeight;
      unsigned int o2 = outWidth / 2;

      for (iy=0; iy<16; iy++)
      {
        for (ix=0; ix<16; ix++)
        {
        out[((by+iy)*outWidth) + bx + ix] = blockBase[(iy*16) + ix] + 0x7F;
         }
      }
      
      for (iy=0; iy<8; iy++)
      {
        for (ix=0; ix<8; ix++)
        {
        out[oo + ((by/2) +iy)*(o2) + (bx/2) + ix] = blockBase[256 + (iy*8) + ix] + 0x7F;
        }
      }


      for (iy=0; iy<8; iy++)
      {
        for (ix=0; ix<8; ix++)
        {
        out[(oo + (oo>>2)) + ((by/2) +iy)*(o2) + (bx/2) + ix] = blockBase[320 + (iy*8) + ix] + 0x7F;
        }
      }
      */

      
      /* Handle the restart interval. */
      if (decoder->restartInterval && --restartInterval == 0)
      {
        restartInterval = decoder->restartInterval;
        JPEG_BITS_REWIND ();
        if (((data [0] << 8) | data [1]) == JPEG_Marker_EOI)
          goto finish;
        for (c = 0; c < JPEG_MAXIMUM_COMPONENTS; c ++)
          dcLast [c] = 0;
        data += 2;
      }

    }
  }
   
finish:
  /* Make sure we read an EOI marker. */ 
  JPEG_BITS_REWIND ();
  data += 2;

  /* Clear up and return success. */
  *dataBase = data;
  return 1;
}

/* Read an JPEG_Marker_SOFn marker into frame.  This expects to start
 * processing immediately after the marker.
 */
int JPEG_FrameHeader_Read (JPEG_FrameHeader *frame, const unsigned char **dataBase, JPEG_Marker marker)
{
  const unsigned char *data = *dataBase;
  unsigned short length = (data [0] << 8) | data [1];
  int index;

  (void) length;
  data += 2; /* Skip the length. */
  frame->marker = marker;
  frame->encoding = (marker >= 0xFFC0 && marker <= 0xFFC7) ? 0 : 1;
  frame->differential = !(marker >= 0xFFC0 && marker <= 0xFFC3 && marker >= 0xFFC8 && marker <= 0xFFCB);
  
  frame->precision = *data ++;
  frame->height = (data [0] << 8) | data [1]; data += 2;
  frame->width = (data [0] << 8) | data [1]; data += 2;
  frame->componentCount = *data ++;
  
  /* Read the frame components. */
  for (index = 0; index < frame->componentCount; index ++)
  {
    JPEG_FrameHeader_Component *c = &frame->componentList [index];
    unsigned char pair;
    
    c->selector = *data ++;
    pair = *data ++;
    c->horzFactor = pair >> 4;
    c->vertFactor = pair & 15;
    c->quantTable = *data ++;
  }
  
  *dataBase = data;
  return 1;
}

/* Read a JPEG_Marker_SOS marker into scan.  This expects to start processing
 * immediately after the marker.
 */
int JPEG_ScanHeader_Read (JPEG_ScanHeader *scan, const unsigned char **dataBase)
{
  const unsigned char *data = *dataBase;
  unsigned short length = (data [0] << 8) | data [1];
  JPEG_ScanHeader_Component *c, *cEnd;
  unsigned char pair;
 
  (void) length;
  data += 2; /* Skip the length. */
  scan->componentCount = *data ++;
  
  /* Read the scan components. */  
  for (c = scan->componentList, cEnd = c + scan->componentCount; c < cEnd; c ++)
  {
    c->selector = *data ++;
    pair = *data ++;
    c->dcTable = pair >> 4;
    c->acTable = pair & 15;
  }
  
  /* Read the spectral and approximation footers, which are used for
   * progressive.
   */
   
  scan->spectralStart = *data ++;
  scan->spectralEnd = *data ++;
  pair = *data ++;
  scan->successiveApproximationBitPositionHigh = pair >> 4;
  scan->successiveApproximationBitPositionLow = pair & 15;
  
  *dataBase = data;
  return 1;
}

/* Read all headers from the very start of the JFIF stream to right after the
 * SOS marker.
 */
 
int JPEG_Decoder_ReadHeaders (JPEG_Decoder *decoder, const unsigned char **dataBase)
{
  const unsigned char *data = *dataBase;
  JPEG_Marker marker;
  int c;
 
  /* Initialize state and assure that this is a JFIF file. */   
  decoder->restartInterval = 0;
  data += 2;
  
  /* Start reading every marker as it comes in. */
  while (1)
  {
    marker = (JPEG_Marker) ((data [0] << 8) | data [1]);
    data += 2;
    
    switch (marker)
    {
      /* This block is just skipped over. */
      case JPEG_Marker_APP0:
      case JPEG_Marker_APP1:
      case JPEG_Marker_APP2:
      case JPEG_Marker_APP3:
      case JPEG_Marker_APP4:
      case JPEG_Marker_APP5:
      case JPEG_Marker_APP6:
      case JPEG_Marker_APP7:
      case JPEG_Marker_APP8:
      case JPEG_Marker_APP9:
      case JPEG_Marker_APP10:
      case JPEG_Marker_APP11:
      case JPEG_Marker_APP12:
      case JPEG_Marker_APP13:
      case JPEG_Marker_APP14:
      case JPEG_Marker_APP15:
      case JPEG_Marker_COM:
        data += (data [0] << 8) | data [1];
        break;
      
      case JPEG_Marker_DHT: /* Define Huffman table.  We just skip it for later decompression. */
      {
        unsigned short length = (data [0] << 8) | data [1];
        const unsigned char *end = data + length;
        
        data += 2;
        while (data < end)
        {
          unsigned char pair, type, slot;
          
          pair = *data ++;
          type = pair >> 4;
          slot = pair & 15;
          
          if (type == 0)
            decoder->dcTables [slot] = data;
          else
            decoder->acTables [slot] = data;
            
          if (!JPEG_HuffmanTable_Skip (&data))
            return 0;
        }
        break;
      }
      
      case JPEG_Marker_DQT: /* Define quantization table. */
      {
        unsigned short length = (data [0] << 8) | data [1];
        const unsigned char *end = data + length;
        int col, row;
        JPEG_FIXED_TYPE *s;
        
        data += 2;
        
        while (data < end)
        {
          int pair, slot, precision;
          
          pair = *data ++;
          precision = pair >> 4;
          slot = pair & 15;
          
          s = decoder->quantTables [slot];
           
          for (c = 0; c < JPEG_DCTSIZE2; c ++)
            s [c] = JPEG_ITOFIX (*data ++);
          
          /* Multiply against the AAN factors. */
          for (row = 0; row < JPEG_DCTSIZE; row ++)
            for (col = 0; col < JPEG_DCTSIZE; col ++)
            {
              JPEG_FIXED_TYPE *item = &s [col + row * JPEG_DCTSIZE];
              
              *item = JPEG_FIXMUL (*item, JPEG_AANScaleFactor [JPEG_ToZigZag [row * JPEG_DCTSIZE + col]]);
            }
        }
        
        break;
      }
    
      case JPEG_Marker_DRI: /* Define restart interval. */
        decoder->restartInterval = (data [2] << 8) | data [3];
        data += 4;
        break;
      
      case JPEG_Marker_SOF0: /* Start of Frame: Baseline Sequential Huffman. */
        if (!JPEG_FrameHeader_Read (&decoder->frame, &data, marker))
          return 0;
        break;
      
      case JPEG_Marker_SOS: /* Start of scan, immediately followed by the image. */
        if (!JPEG_ScanHeader_Read (&decoder->scan, &data))
          return 0;
        *dataBase = data;
        return 1;
        
      default: /* No known marker of this type. */
        break;
    }
  }
}

/* Perform the two steps necessary to decompress a JPEG image.
 * Nothing fancy about it.
 */
int JPEG_DecompressImage (const unsigned char *data, signed char *out, int outWidth, int outHeight)
{
  static JPEG_Decoder decoder;

  if (!JPEG_Decoder_ReadHeaders (&decoder, &data))
    return 0;
  if (!JPEG_Decoder_ReadImage (&decoder, &data, out, outWidth, outHeight))
    return 0;
  return 1;
}

/* Return whether this code is a JPEG file.  Unfortunately it will incorrectly
 * match variants such as JPEG 2000 and JPEG-LS.  A better function would
 * skip known markers until it reaches an unknown marker or a handled
 * SOFn.
 */
 
int JPEG_Match (const unsigned char *data, int length)
{
  if (length == 0) return 0;
  if (data [0] != 0xFF) return 0;
  if (length == 1) return 1;
  if (data [1] != 0xD8) return 0;
  if (length == 2) return 1;
  return 1;
  if (data [2] != 0xFF) return 0;
  if (length == 3) return 1;
  if (data [3] < 0xC0 || data [3] > 0xCF) return 0;
  if (data [3] == 0xC0) return 1;
  return 0;
}


⌨️ 快捷键说明

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