#include <stdio.h>
#include <stdlib.h>
#include <jpeglib.h>
#include <memory.h>
int camera_W = 640;
int camera_H = 640;
int read_JPEG_file (char * filename, unsigned char *out_buf,int size)
{
struct jpeg_decompress_struct cinfo;
struct jpeg_error_mgr jerr;
/* More stuff */
FILE *infile; /* source file */
int row_stride; /* physical row width in output buffer */
unsigned char *rdata;
JSAMPROW row_pointer[1];
int image_size = 0 ;
if ((infile = fopen(filename, "rb")) == NULL)
{
fprintf(stderr, "can't open %s\n", filename);
return -1;
}
/* Step 1: allocate and initialize JPEG decompression object */
/* We set up the normal JPEG error routines, then override error_exit. */
cinfo.err = jpeg_std_error(&jerr);
/* Now we can initialize the JPEG decompression object. */
jpeg_create_decompress(&cinfo);
/* Step 2: specify data source (eg, a file) */
jpeg_stdio_src(&cinfo, infile);
/* Step 3: read file parameters with jpeg_read_header() */
(void) jpeg_read_header(&cinfo, TRUE);
/* 源信息 */
printf("image_width = %d\n", cinfo.image_width);
printf("image_height = %d\n", cinfo.image_height);
printf("num_components = %d\n", cinfo.num_components);
image_size = cinfo.image_width*cinfo.image_height*cinfo.num_components ;
//传进来的字符数组没有足够大的空间
if(size < image_size )
{
printf("buf size too small!\n") ;
return -2 ;
}
/* 分配内存存储字节 */
rdata=(unsigned char*)calloc(image_size,1);
/* Step 4: set parameters for decompression */
//设置输出的颜色类型
cinfo.out_color_space=JCS_RGB;
/* Step 5: Start decompressor */
(void) jpeg_start_decompress(&cinfo);
/* 输出的图象的信息 */
printf("output_width = %d\n", cinfo.output_width);
printf("output_height = %d\n", cinfo.output_height);
printf("output_components = %d\n", cinfo.output_components);//解压的是rgb,故为3元素
/* JSAMPLEs per row in output buffer */
row_stride = cinfo.output_width * cinfo.output_components;//一行的数据长度
/* Make a one-row-high sample array that will go away when done with image */
/* Step 6: while (scan lines remain to be read) */
/* jpeg_read_scanlines(...); */
while (cinfo.output_scanline < cinfo.output_height)
{
row_pointer[0] = & rdata[(cinfo.output_scanline)*cinfo.image_width*cinfo.num_components];
jpeg_read_scanlines(&cinfo,row_pointer ,1);
//(void) jpeg_read_scanlines(&cinfo, buffer, 1);
/* Assume put_scanline_someplace wants a pointer and sample count. */
//put_scanline_someplace(buffer[0], row_stride);
}
memcpy(out_buf, rdata, image_size) ;
free(rdata) ;
(void) jpeg_finish_decompress(&cinfo);
/* Step 8: Release JPEG decompression object */
/* This is an important step since it will release a good deal of memory. */
jpeg_destroy_decompress(&cinfo);
fclose(infile);
/* And we're done! */
return image_size;
}
int write_JPEG_file (char * filename,unsigned char *image_buffer, int image_width, int image_height, int quality )
{
struct jpeg_compress_struct cinfo;
struct jpeg_error_mgr jerr;
/* More stuff */
FILE * outfile; /* target file */
JSAMPROW row_pointer[1]; /* pointer to JSAMPLE row[s] */
int row_stride; /* physical row width in image buffer */
/* Step 1: allocate and initialize JPEG compression object */
cinfo.err = jpeg_std_error(&jerr);
/* Now we can initialize the JPEG compression object. */
jpeg_create_compress(&cinfo);
/* Step 2: specify data destination (eg, a file) */
/* Note: steps 2 and 3 can be done in either order. */
if ((outfile = fopen(filename, "w+")) == NULL) {
fprintf(stderr, "can't open %s\n", filename);
return -1;
}
jpeg_stdio_dest(&cinfo, outfile);
/* Step 3: set parameters for compression */
cinfo.image_width = image_width; /* image width and height, in pixels */
cinfo.image_height = image_height;
cinfo.input_components = 3; /* # of color components per pixel */
cinfo.in_color_space = JCS_RGB; /* colorspace of input image */
jpeg_set_defaults(&cinfo);
jpeg_set_quality(&cinfo, quality, TRUE /* limit to baseline-JPEG values */);
/* Step 4: Start compressor */
jpeg_start_compress(&cinfo, TRUE);
/* Step 5: while (scan lines remain to be written) */
row_stride = image_width * 3; /* JSAMPLEs per row in image_buffer */
while (cinfo.next_scanline < cinfo.image_height)
{
row_pointer[0] = & image_buffer[cinfo.next_scanline * row_stride];
(void) jpeg_write_scanlines(&cinfo, row_pointer, 1);
}
/* Step 6: Finish compression */
jpeg_finish_compress(&cinfo);
/* After finish_compress, we can close the output file. */
fclose(outfile);
/* Step 7: release JPEG compression object */
/* This is an important step since it will release a good deal of memory. */
jpeg_destroy_compress(&cinfo);
/* And we're done! */
return 0 ;
}
typedef struct _jpg_color_
{
unsigned char R;
unsigned char G;
unsigned char B;
}COLOR;
void Draw_square(COLOR *p , int start_x , int end_x , int start_y , int end_y , COLOR color={0, 255, 0}, int width = 5)
{
int x1,x2,y1,y2;
int x,y;
if(start_x==end_x || start_y==end_y)
return;//如果不符合就直接返回
/* start_x与end_x哪个大哪个赋值x2,小的赋值x1 */
if(start_x<end_x)
{
x1=start_x;
x2=end_x;
}
else
{
x2=start_x;
x1=end_x;
}
/* start_y与end_y哪个大哪个赋值y2,小的赋值y1 */
if(start_y<end_y)
{
y1=start_y;
y2=end_y;
}
else
{
y2=start_y;
y1=end_y;
}
//超出边界就取边界值
if(x1<0)x1=0;
if(x2>(camera_W-1))
x2=camera_W-1;
if(y1<0)
y1=0;
if(y2>(camera_H-1))
y2=camera_H-1;
//遍历通道
for(x=x1; x<x2; x++)
{
for (int i = 0; i < width; i++)
{
//p[(start_y * 3 + i)*camera_W+x]=color.value;
memcpy(&p[(start_y + i)*camera_W+x], &color, sizeof(COLOR));
memcpy(&p[(end_y - i)*camera_W+x], &color, sizeof(COLOR));
}
}
for(y=y1; y<y2; y++)
{
for (int i = 0; i < width; i++)
{
memcpy(&p[y*camera_W+(start_x + i)], &color, sizeof(COLOR));
memcpy(&p[y*camera_W+(end_x - i)], &color, sizeof(COLOR));
}
}
}
int main(int argc, char **argv)
{
int rv = -1 ;
int result = 0 ;
unsigned char buffer[640*640*3] ;
unsigned short rgb565_buf[640*640] ;
unsigned char rgb888_buf[640*640*3] ;
memset(buffer,0, sizeof(buffer)) ;
rv = read_JPEG_file((char*)"/data/ObjDetector/objectdetector/resource/640-640.jpg",buffer,sizeof(buffer)) ;//读取OV2640采集到的JPEG图像解码为RGB888数据
if(rv < 0)
{
printf("read_JPEG_file() failed\n") ;
return -1 ;
}
printf("jpeg decompress OK, after decompress size = %d\n",rv) ;
Draw_square((COLOR*)buffer , 100 , 200 , 100 , 200);
write_JPEG_file((char*)"new_test.jpg",buffer,640,640,75) ;//RGB888编码保存jpg图片文件
printf("rgb write jpeg compress finish!\n") ;
return 0 ;
}/* End Of Main */
使用libjpeg库在图片上画方框
最新推荐文章于 2024-07-10 15:00:55 发布