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

📄 ebcot_decoder.c

📁 JPEG2000实现的源码
💻 C
📖 第 1 页 / 共 5 页
字号:

static int
  construct_component_position_progression(ebcot_tile_ptr tile,
                                           ebcot_sequence_ptr seq,
                                           int first_level,
                                           int first_component,
                                           int max_layers, int max_levels,
                                           int max_components)
{
  ebcot_component_info_ptr comp_info;
  ebcot_level_info_ptr lev;
  ebcot_precinct_info_ptr precinct;
  canvas_dims dims;
  int new_packets;
  int n, c, p;
  int x_inc, y_inc, inc, x0, x1, y0, y1, x, y;

  /* Reset `next_precinct_idx' fields. */

  for (c=first_component; c < tile->num_components; c++)
    {
      comp_info = tile->components + c;
      for (n=first_level; n <= comp_info->num_levels; n++)
        {
          lev = comp_info->levels +n;
          lev->next_precinct_idx = 0;
        }
    }

  new_packets = 0;
  for (c=first_component; c < max_components; c++)
    {
      comp_info = tile->components + c;

      /* Determine spatial progression parameters. */

      x_inc = y_inc = 0;
      for (n=first_level; n < max_levels; n++)
        {
          if (n > comp_info->num_levels)
            continue;
          lev = comp_info->levels + n;
          if (lev->ppx >= 0)
            {
              /* SAIC General Decomp. Begin mods */
              int xfact = 0;
              int l;

              for (l=comp_info->num_levels; l>n; l--) {
                switch(comp_info->levels[l].decomp_sequence[0]) {
                  case 1:
                    xfact++;
                    break;
                  case 2:
                    xfact++;
                    break;
                  case 3:
                    break;
                }
              }
              inc = comp_info->hor_subsampling;
              inc <<= lev->ppx + xfact;
              /* SAIC General Decomp. End mods */

              if ((x_inc == 0) || (inc < x_inc))
                x_inc = inc;
            }
          if (lev->ppy >= 0)
            {
              /* SAIC General Decomp. Begin mods */
              int yfact = 0;
              int l;

              for (l=comp_info->num_levels; l>n; l--) {
                switch(comp_info->levels[l].decomp_sequence[0]) {
                  case 1:
                    yfact++;
                    break;
                  case 2:
                    break;
                  case 3:
                    yfact++;
                    break;
                }
              }
              inc = comp_info->vert_subsampling;
              inc <<= lev->ppy + yfact;
              /* SAIC General Decomp. End mods */

              if ((y_inc == 0) || (inc < y_inc))
                y_inc = inc;
            }
        }
      dims = tile->reference_dims;
      if (tile->overlapped)
        local_error("Spatially oriented packet progressions not defined "
                    "for overlapping tiles!");
      if (x_inc == 0)
        { /* Only one precinct horizontally. */
          x0 = 0; x1 = x_inc = 1;
        }
      else
        {
          x0 = dims.left_col; x1 = x0 + dims.cols;
          x0 &= ~(x_inc-1); /* Start on integer multiple of x_inc. */
        }
      if (y_inc == 0)
        { /* Only one precinct vertically. */
          y0 = 0; y1 = y_inc = 1;
        }
      else
        {
          y0 = dims.top_row; y1 = y0 + dims.rows;
          y0 &= ~(y_inc-1); /* Start on integer multiple of y_inc. */
        }


      /* Now walk through the component's progression. */

      for (y=y0; y < y1; y += y_inc)
        for (x=x0; x < x1; x += x_inc)
          for (n=first_level; n < max_levels; n++)
            {
              if (n > comp_info->num_levels)
                continue;
              lev = comp_info->levels + n;
              p = lev->next_precinct_idx;
              precinct = lev->precincts + p;
              if ((p < lev->total_precincts) &&
                  ((y==y0) || (y==precinct->yref)) &&
                  ((x==x0) || (x==precinct->xref)))
                {
                  lev->next_precinct_idx++;
                  while (precinct->sequenced_layers < max_layers)
                    {
                      seq->layer_idx = precinct->sequenced_layers;
                      seq->precinct = precinct;
                      new_packets++;
                      seq++;
                      precinct->sequenced_layers++;
                    }
                }
            }
    }
  return(new_packets);
}

/* Begin DST POC mod */
/*****************************************************************************/
/* STATIC                apply_progression_sequence_spec                     */
/*****************************************************************************/

static void
  apply_progression_sequence_spec(ebcot_tile_ptr tile,
                                  int first_level, int first_component,
                                  int max_levels, int max_components,
                                  int max_layers, int progression)

 /* Returns the number of new packets sequenced by the progression
    spec supplied here. */

{
  ebcot_sequence_ptr seq;
  int num_packets;

  if (max_layers > tile->num_layers)
    max_layers = tile->num_layers;
  if (max_levels > (tile->max_levels+1))
    max_levels = tile->max_levels+1;
  if (max_components > tile->num_components)
    max_components = tile->num_components;
  seq = tile->packet_sequence + tile->sequenced_packets;
  switch (progression) {
    case LAYER_PROGRESSIVE:
      num_packets =
        construct_layer_progression(tile,seq,first_level,first_component,
                                    max_layers,max_levels,max_components);
      break;
    case RESOLUTION_LAYER_PROGRESSIVE:
      num_packets =
        construct_resolution_layer_progression(tile,seq,first_level,
                                               first_component,max_layers,
                                               max_levels,max_components);
      break;
    case RESOLUTION_POSITION_PROGRESSIVE:
      num_packets =
        construct_resolution_position_progression(tile,seq,first_level,
                                                  first_component,max_layers,
                                                  max_levels,max_components);
      break;
    case POSITION_COMPONENT_PROGRESSIVE:
      num_packets =
        construct_position_component_progression(tile,seq,first_level,
                                                 first_component,max_layers,
                                                 max_levels,max_components);
      break;
    case COMPONENT_POSITION_PROGRESSIVE:
      num_packets =
        construct_component_position_progression(tile,seq,first_level,
                                                 first_component,max_layers,
                                                 max_levels,max_components);
      break;
    default: assert(0);
    }
  tile->sequenced_packets += num_packets;
  assert(tile->sequenced_packets <= tile->total_packets);
}

/*****************************************************************************/
/* STATIC              initialize_progression_sequence                       */
/*****************************************************************************/

static void
  initialize_progression_sequence(stream_in_ref stream, ebcot_tile_ptr tile)
{
  int tnum = tile->tnum;
  int first_level, first_component;
  int max_layers, max_levels, max_components;
  int progression;
  int num_poc_specs, n;

  /* Set up storage. */

  tile->packet_sequence = (ebcot_sequence_ptr)
    local_malloc(EBCOT_MEM_KEY,sizeof(ebcot_sequence)*tile->total_packets);

  /* Get default sequencing parameters based on relevant COD marker. */
  first_level = first_component = 0;
  max_layers = tile->num_layers;
  max_components = tile->num_components;
  max_levels = tile->max_levels+1;
  progression = (int)
    stream->get_marker_val(stream,tnum,MARKER_COD_PROG,0,0);
  
  /* Process all available sequencing information. */

  num_poc_specs = stream->size_marker_elt(stream,tnum,MARKER_POC_CHANGES,0);
  assert(!(num_poc_specs % 6));
  num_poc_specs /= 6;
  n = 0;
  do {
    if (num_poc_specs > 0)
      { /* Change the sequencing parameters. */
        first_level = (int)
          stream->get_marker_val(stream,tnum,MARKER_POC_CHANGES,0,6*n+0);
        first_component = (int)
          stream->get_marker_val(stream,tnum,MARKER_POC_CHANGES,0,6*n+1);
        max_layers = (int)
          stream->get_marker_val(stream,tnum,MARKER_POC_CHANGES,0,6*n+2);
        max_levels = (int)
          stream->get_marker_val(stream,tnum,MARKER_POC_CHANGES,0,6*n+3);
        max_components = (int)
          stream->get_marker_val(stream,tnum,MARKER_POC_CHANGES,0,6*n+4);
        progression = (int)
          stream->get_marker_val(stream,tnum,MARKER_POC_CHANGES,0,6*n+5);
        n++;
      }
    apply_progression_sequence_spec(tile,first_level,first_component,
                                    max_levels,max_components,max_layers,
                                    progression);
    num_poc_specs--;
  } while (num_poc_specs > 0);
}

/*****************************************************************************/
/* STATIC                 augment_packet_sequencing_info                     */
/*****************************************************************************/

static void
  augment_packet_sequencing_info(ebcot_tile_ptr tile,
                                 stream_in_ref stream)

 /* This function is called from within `retrieve_next_packet' when there
    is insufficient sequencing information available to identify the
    coordinates of the packet retrieved for the current tile.  The
    sequencing information must lie in a new POC marker which should have
    appeared in a tile-part header of the tile.  The function invokes the
    `stream_in__pop_tile_part_poc' function to get the next available POC
    marker and incorporate its sequencing information. */

{
  int tnum = tile->tnum;
  int first_level, first_component;
  int max_layers, max_levels, max_components;
  int progression;
  int num_poc_specs, n;

  /* Process next available sequencing identifier. */

  tile->current_poc_instance++;
  num_poc_specs = stream->size_marker_elt(stream,tnum,MARKER_POC_CHANGES,
                                          tile->current_poc_instance);
  if (num_poc_specs == 0)
    local_error("Insufficient tile-part specific POC markers supplied to "
                "sequence all packets for the tile!");
  assert(!(num_poc_specs % 6));
  num_poc_specs /= 6;
  for (n=0; n < num_poc_specs; n++)
    {
      first_level = (int)
        stream->get_marker_val(stream,tnum,MARKER_POC_CHANGES,
                               tile->current_poc_instance,6*n+0);
      first_component = (int)
        stream->get_marker_val(stream,tnum,MARKER_POC_CHANGES,
                               tile->current_poc_instance,6*n+1);
      max_layers = (int)
        stream->get_marker_val(stream,tnum,MARKER_POC_CHANGES,
                               tile->current_poc_instance,6*n+2);
      max_levels = (int)
        stream->get_marker_val(stream,tnum,MARKER_POC_CHANGES,
                               tile->current_poc_instance,6*n+3);
      max_components = (int)
        stream->get_marker_val(stream,tnum,MARKER_POC_CHANGES,
                               tile->current_poc_instance,6*n+4);
      progression = (int)
        stream->get_marker_val(stream,tnum,MARKER_POC_CHANGES,
                               tile->current_poc_instance,6*n+5);
      apply_progression_sequence_spec(tile,first_level,first_component,
                                      max_levels,max_components,max_layers,
                                      progression);
    }
}
/* End DST POC mod */

/*****************************************************************************/
/* STATIC                      build_partitions                              */
/*****************************************************************************/

static int
  build_partitions(ebcot_component_info_ptr comp_info)

 /* This function constructs the code-block partition and the precinct
    partition for all resolution levels and subbands in the tile-component
    referenced by `comp_info'.  The function returns the total number

⌨️ 快捷键说明

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