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

📄 jctrans.pas

📁 用pascal寫的jpeg codec, 測試過的
💻 PAS
📖 第 1 页 / 共 2 页
字号:
Unit JcTrans;

{ This file contains library routines for transcoding compression,
  that is, writing raw DCT coefficient arrays to an output JPEG file.
  The routines in jcapimin.c will also be needed by a transcoder. }

{ Original : jctrans.c ;  Copyright (C) 1995-1996, Thomas G. Lane. }

interface

{$I jconfig.inc}

uses
  jmorecfg,
  jinclude,
  jdeferr,
  jerror,
  jutils,
  jpeglib,
  jcapimin, jcparam, jcomapi, jcmaster, jchuff, jcmarker;

{ Compression initialization for writing raw-coefficient data.
  Before calling this, all parameters and a data destination must be set up.
  Call jpeg_finish_compress() to actually write the data.

  The number of passed virtual arrays must match cinfo^.num_components.
  Note that the virtual arrays need not be filled or even realized at
  the time write_coefficients is called; indeed, if the virtual arrays
  were requested from this compression object's memory manager, they
  typically will be realized during this routine and filled afterwards. }

{GLOBAL}
procedure jpeg_write_coefficients (cinfo : j_compress_ptr;
                                   coef_arrays : jvirt_barray_tbl_ptr);

{ Initialize the compression object with default parameters,
  then copy from the source object all parameters needed for lossless
  transcoding.  Parameters that can be varied without loss (such as
  scan script and Huffman optimization) are left in their default states. }

{GLOBAL}
procedure jpeg_copy_critical_parameters (srcinfo : j_decompress_ptr;
			                 dstinfo : j_compress_ptr);


implementation

{ Forward declarations }
{LOCAL}
procedure  transencode_master_selection(cinfo : j_compress_ptr;
                                        coef_arrays : jvirt_barray_tbl_ptr);
                                        forward;
{LOCAL}
procedure  transencode_coef_controller(cinfo : j_compress_ptr;
                                       coef_arrays : jvirt_barray_tbl_ptr);
                                       forward;


{ Compression initialization for writing raw-coefficient data.
  Before calling this, all parameters and a data destination must be set up.
  Call jpeg_finish_compress() to actually write the data.

  The number of passed virtual arrays must match cinfo^.num_components.
  Note that the virtual arrays need not be filled or even realized at
  the time write_coefficients is called; indeed, if the virtual arrays
  were requested from this compression object's memory manager, they
  typically will be realized during this routine and filled afterwards. }

{GLOBAL}
procedure jpeg_write_coefficients (cinfo : j_compress_ptr;
                                   coef_arrays : jvirt_barray_tbl_ptr);
begin
  if (cinfo^.global_state <> CSTATE_START) then
    ERREXIT1(j_common_ptr(cinfo), JERR_BAD_STATE, cinfo^.global_state);
  { Mark all tables to be written }
  jpeg_suppress_tables(cinfo, FALSE);
  { (Re)initialize error mgr and destination modules }
  cinfo^.err^.reset_error_mgr (j_common_ptr(cinfo));
  cinfo^.dest^.init_destination (cinfo);
  { Perform master selection of active modules }
  transencode_master_selection(cinfo, coef_arrays);
  { Wait for jpeg_finish_compress() call }
  cinfo^.next_scanline := 0;	{ so jpeg_write_marker works }
  cinfo^.global_state := CSTATE_WRCOEFS;
end;


{ Initialize the compression object with default parameters,
  then copy from the source object all parameters needed for lossless
  transcoding.  Parameters that can be varied without loss (such as
  scan script and Huffman optimization) are left in their default states. }

{GLOBAL}
procedure jpeg_copy_critical_parameters (srcinfo : j_decompress_ptr;
			                 dstinfo : j_compress_ptr);
var
  qtblptr : ^JQUANT_TBL_PTR;
  incomp, outcomp : jpeg_component_info_ptr;
  c_quant, slot_quant : JQUANT_TBL_PTR;
  tblno, ci, coefi : int;
begin

  { Safety check to ensure start_compress not called yet. }
  if (dstinfo^.global_state <> CSTATE_START) then
    ERREXIT1(j_common_ptr(dstinfo), JERR_BAD_STATE, dstinfo^.global_state);
  { Copy fundamental image dimensions }
  dstinfo^.image_width := srcinfo^.image_width;
  dstinfo^.image_height := srcinfo^.image_height;
  dstinfo^.input_components := srcinfo^.num_components;
  dstinfo^.in_color_space := srcinfo^.jpeg_color_space;
  { Initialize all parameters to default values }
  jpeg_set_defaults(dstinfo);
  { jpeg_set_defaults may choose wrong colorspace, eg YCbCr if input is RGB.
    Fix it to get the right header markers for the image colorspace. }

  jpeg_set_colorspace(dstinfo, srcinfo^.jpeg_color_space);
  dstinfo^.data_precision := srcinfo^.data_precision;
  dstinfo^.CCIR601_sampling := srcinfo^.CCIR601_sampling;
  { Copy the source's quantization tables. }
  for tblno := 0 to pred(NUM_QUANT_TBLS) do
  begin
    if (srcinfo^.quant_tbl_ptrs[tblno] <> NIL) then
    begin
      qtblptr := @dstinfo^.quant_tbl_ptrs[tblno];
      if (qtblptr^ = NIL) then
	qtblptr^ := jpeg_alloc_quant_table(j_common_ptr(dstinfo));
      MEMCOPY(@(qtblptr^)^.quantval,
	      @srcinfo^.quant_tbl_ptrs[tblno]^.quantval,
	      SIZEOF((qtblptr^)^.quantval));
      (qtblptr^)^.sent_table := FALSE;
    end;
  end;
  { Copy the source's per-component info.
    Note we assume jpeg_set_defaults has allocated the dest comp_info array. }

  dstinfo^.num_components := srcinfo^.num_components;
  if (dstinfo^.num_components < 1) or
     (dstinfo^.num_components > MAX_COMPONENTS) then
    ERREXIT2(j_common_ptr(dstinfo), JERR_COMPONENT_COUNT,
        dstinfo^.num_components,   MAX_COMPONENTS);
  incomp := srcinfo^.comp_info;
  outcomp := dstinfo^.comp_info;
  for ci := 0 to pred(dstinfo^.num_components) do
  begin
  
    outcomp^.component_id := incomp^.component_id;
    outcomp^.h_samp_factor := incomp^.h_samp_factor;
    outcomp^.v_samp_factor := incomp^.v_samp_factor;
    outcomp^.quant_tbl_no := incomp^.quant_tbl_no;
    { Make sure saved quantization table for component matches the qtable
      slot.  If not, the input file re-used this qtable slot.
      IJG encoder currently cannot duplicate this. }

    tblno := outcomp^.quant_tbl_no;
    if (tblno < 0) or (tblno >= NUM_QUANT_TBLS) or
       (srcinfo^.quant_tbl_ptrs[tblno] = NIL) then
      ERREXIT1(j_common_ptr(dstinfo), JERR_NO_QUANT_TABLE, tblno);
    slot_quant := srcinfo^.quant_tbl_ptrs[tblno];
    c_quant := incomp^.quant_table;
    if (c_quant <> NIL) then
    begin
      for coefi := 0 to pred(DCTSIZE2) do
      begin
	if (c_quant^.quantval[coefi] <> slot_quant^.quantval[coefi]) then
	  ERREXIT1(j_common_ptr(dstinfo), JERR_MISMATCHED_QUANT_TABLE, tblno);
      end;
    end;
    { Note: we do not copy the source's Huffman table assignments;
      instead we rely on jpeg_set_colorspace to have made a suitable choice. }
    Inc(incomp);
    Inc(outcomp);
  end;
end;


{ Master selection of compression modules for transcoding.
  This substitutes for jcinit.c's initialization of the full compressor. }

{LOCAL}
procedure transencode_master_selection (cinfo : j_compress_ptr;
			                coef_arrays : jvirt_barray_tbl_ptr);
begin
  { Although we don't actually use input_components for transcoding,
    jcmaster.c's initial_setup will complain if input_components is 0. }

  cinfo^.input_components := 1;
  { Initialize master control (includes parameter checking/processing) }
  jinit_c_master_control(cinfo, TRUE { transcode only });

  { Entropy encoding: either Huffman or arithmetic coding. }
  if (cinfo^.arith_code) then
  begin
    ERREXIT(j_common_ptr(cinfo), JERR_ARITH_NOTIMPL);
  end
  else
  begin
    if (cinfo^.progressive_mode) then
    begin
{$ifdef C_PROGRESSIVE_SUPPORTED}
      jinit_phuff_encoder(cinfo);
{$else}
      ERREXIT(j_common_ptr(cinfo), JERR_NOT_COMPILED);
{$endif}
    end
    else
      jinit_huff_encoder(cinfo);
  end;

  { We need a special coefficient buffer controller. }
  transencode_coef_controller(cinfo, coef_arrays);

  jinit_marker_writer(cinfo);

  { We can now tell the memory manager to allocate virtual arrays. }
  cinfo^.mem^.realize_virt_arrays (j_common_ptr(cinfo));

  { Write the datastream header (SOI) immediately.
    Frame and scan headers are postponed till later.
    This lets application insert special markers after the SOI. }

⌨️ 快捷键说明

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