📄 jpeg2yuv.c
字号:
jpeg_read_header(&dinfo, 1); switch (dinfo.jpeg_color_space) { case JCS_YCbCr: mjpeg_info("YUV colorspace detected.\n"); dinfo.out_color_space = JCS_YCbCr; break; case JCS_GRAYSCALE: mjpeg_info("Grayscale colorspace detected.\n"); dinfo.out_color_space = JCS_GRAYSCALE; break; default: mjpeg_error("Unsupported colorspace detected.\n"); break; } mjpeg_info("Starting decompression"); jpeg_start_decompress(&dinfo); if (dinfo.output_components != 3 && dinfo.out_color_space == JCS_YCbCr) mjpeg_error_exit1("Output components of color JPEG image = %d, must be 3.", dinfo.output_components); if (dinfo.output_components != 1 && dinfo.out_color_space == JCS_GRAYSCALE) mjpeg_error_exit1("Output components of grayscale JPEG image = %d, must be 1.", dinfo.output_components); mjpeg_info("Image dimensions are %dx%d", dinfo.image_width, dinfo.image_height); /* picture size check */ if ( (dinfo.image_width % 2) != 0 ) mjpeg_error_exit1("The image width has to be a even number, rescale the image"); if ( (dinfo.image_height % 2) != 0 ) mjpeg_error_exit1("The image height has to be even number, rescale the image"); param->width = dinfo.image_width; param->height = dinfo.image_height; param->colorspace = dinfo.jpeg_color_space; jpeg_destroy_decompress(&dinfo); fclose(jpegfile); mjpeg_info("Movie frame rate is: %f frames/second", Y4M_RATIO_DBL(param->framerate)); switch (param->interlace) { case Y4M_ILACE_NONE: mjpeg_info("Non-interlaced/progressive frames."); break; case Y4M_ILACE_BOTTOM_FIRST: mjpeg_info("Interlaced frames, bottom field first."); break; case Y4M_ILACE_TOP_FIRST: mjpeg_info("Interlaced frames, top field first."); break; default: mjpeg_error_exit1("Interlace has not been specified (use -I option)"); break; } if ((param->interlace != Y4M_ILACE_NONE) && (param->interleave == -1)) mjpeg_error_exit1("Interleave has not been specified (use -L option)"); if (!(param->interleave) && (param->interlace != Y4M_ILACE_NONE)) { param->height *= 2; mjpeg_info("Non-interleaved fields (image height doubled)"); } mjpeg_info("Frame size: %d x %d", param->width, param->height); return 0;}/** Rescales the YUV values from the range 0..255 to the range 16..235 @param yp: buffer for Y plane of decoded JPEG @param up: buffer for U plane of decoded JPEG @param vp: buffer for V plane of decoded JPEG */static void rescale_color_vals(int width, int height, uint8_t *yp, uint8_t *up, uint8_t *vp) { int x,y; for (y = 0; y < height; y++) for (x = 0; x < width; x++) yp[x+y*width] = (float)(yp[x+y*width]) * ((235.0 - 16.0)/255.0) + 16.0; for (y = 0; y < height/2; y++) for (x = 0; x < width/2; x++) { up[x+y*width/2] = (float)(up[x+y*width/2]) * ((240.0 - 16.0)/255.0) + 16.0; vp[x+y*width/2] = (float)(vp[x+y*width/2]) * ((240.0 - 16.0)/255.0) + 16.0; }}static int generate_YUV4MPEG(parameters_t *param){ uint32_t frame; int jpegsize; char jpegname[FILENAME_MAX]; FILE *jpegfile; int loops; /* number of loops to go */ uint8_t *yuv[3]; /* buffer for Y/U/V planes of decoded JPEG */ static uint8_t jpegdata[MAXPIXELS]; /* that ought to be enough */ y4m_stream_info_t streaminfo; y4m_frame_info_t frameinfo; loops = param->loop; mjpeg_info("Number of Loops %i", loops); mjpeg_info("Now generating YUV4MPEG stream."); y4m_init_stream_info(&streaminfo); y4m_init_frame_info(&frameinfo); y4m_si_set_width(&streaminfo, param->width); y4m_si_set_height(&streaminfo, param->height); y4m_si_set_interlace(&streaminfo, param->interlace); y4m_si_set_framerate(&streaminfo, param->framerate); y4m_si_set_sampleaspect(&streaminfo, param->aspect_ratio); yuv[0] = malloc(param->width * param->height * sizeof(yuv[0][0])); yuv[1] = malloc(param->width * param->height / 4 * sizeof(yuv[1][0])); yuv[2] = malloc(param->width * param->height / 4 * sizeof(yuv[2][0])); y4m_write_stream_header(STDOUT_FILENO, &streaminfo); do { for (frame = param->begin; (frame < param->numframes + param->begin) || (param->numframes == -1); frame++) { snprintf(jpegname, sizeof(jpegname), param->jpegformatstr, frame); jpegfile = fopen(jpegname, "rb"); if (jpegfile == NULL) { mjpeg_info("Read from '%s' failed: %s", jpegname, strerror(errno)); if (param->numframes == -1) { mjpeg_info("No more frames. Stopping."); break; /* we are done; leave 'while' loop */ } else { mjpeg_info("Rewriting latest frame instead."); } } else { mjpeg_debug("Preparing frame"); jpegsize = fread(jpegdata, sizeof(unsigned char), MAXPIXELS, jpegfile); fclose(jpegfile); /* decode_jpeg_raw:s parameters from 20010826 * jpeg_data: buffer with input / output jpeg * len: Length of jpeg buffer * itype: 0: Interleaved/Progressive * 1: Not-interleaved, Top field first * 2: Not-interleaved, Bottom field first * ctype Chroma format for decompression. * Currently always 420 and hence ignored. * raw0 buffer with input / output raw Y channel * raw1 buffer with input / output raw U/Cb channel * raw2 buffer with input / output raw V/Cr channel * width width of Y channel (width of U/V is width/2) * height height of Y channel (height of U/V is height/2) */ if ((param->interlace == Y4M_ILACE_NONE) || (param->interleave == 1)) { mjpeg_info("Processing non-interlaced/interleaved %s, size %d", jpegname, jpegsize); if (param->colorspace == JCS_GRAYSCALE) decode_jpeg_gray_raw(jpegdata, jpegsize, 0, 420, param->width, param->height, yuv[0], yuv[1], yuv[2]); else decode_jpeg_raw(jpegdata, jpegsize, 0, 420, param->width, param->height, yuv[0], yuv[1], yuv[2]); } else { switch (param->interlace) { case Y4M_ILACE_TOP_FIRST: mjpeg_info("Processing interlaced, top-first %s, size %d", jpegname, jpegsize); if (param->colorspace == JCS_GRAYSCALE) decode_jpeg_gray_raw(jpegdata, jpegsize, LAV_INTER_TOP_FIRST, 420, param->width, param->height, yuv[0], yuv[1], yuv[2]); else decode_jpeg_raw(jpegdata, jpegsize, LAV_INTER_TOP_FIRST, 420, param->width, param->height, yuv[0], yuv[1], yuv[2]); break; case Y4M_ILACE_BOTTOM_FIRST: mjpeg_info("Processing interlaced, bottom-first %s, size %d", jpegname, jpegsize); if (param->colorspace == JCS_GRAYSCALE) decode_jpeg_gray_raw(jpegdata, jpegsize, LAV_INTER_BOTTOM_FIRST, 420, param->width, param->height, yuv[0], yuv[1], yuv[2]); else decode_jpeg_raw(jpegdata, jpegsize, LAV_INTER_BOTTOM_FIRST, 420, param->width, param->height, yuv[0], yuv[1], yuv[2]); break; default: mjpeg_error_exit1("FATAL logic error?!?"); break; } } if (param->rescale_YUV) { mjpeg_info("Rescaling color values."); rescale_color_vals(param->width, param->height, yuv[0], yuv[1], yuv[2]); } mjpeg_debug("Frame decoded, now writing to output stream."); } y4m_write_frame(STDOUT_FILENO, &streaminfo, &frameinfo, yuv); } if (param->loop != -1) loops--; } while( loops >=1 || loops == -1 ); y4m_fini_stream_info(&streaminfo); y4m_fini_frame_info(&frameinfo); free(yuv[0]); free(yuv[1]); free(yuv[2]); return 0;}/* main * in: argc, argv: Classic commandline parameters. * returns: int: 0: success, !0: !success :-) */int main(int argc, char ** argv){ parameters_t param; parse_commandline(argc, argv, ¶m); mjpeg_default_handler_verbosity(param.verbose); mjpeg_info("Parsing & checking input files."); if (init_parse_files(¶m)) { mjpeg_error_exit1("* Error processing the JPEG input."); } if (generate_YUV4MPEG(¶m)) { mjpeg_error_exit1("* Error processing the input files."); } return 0;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -