// file: $USFS/class/image_analysis/v6.1/imaga_edge_13.cc
//

// system include files
//
#include <string.h>
#include <math.h>

// isip include files
//
#include "image_analysis.h"
#include "image_analysis_constants.h"

// method: edge_lines_cc
//
// arguments:
//  int_4* num_lines: buffer for the number of lines
//  float_4* edge_data: (input) edge detected data
//  int_4 width: width of the image
//  int_4 height: height of the image
//
// this method counts the number and the length of each of the vertical lines
//
logical_1 Image_analysis::edge_lines_cc(int_4* num_lines_a,
					float_4* edge_data_a,
					int_4 width_a, int_4 height_a) {
  
  // initialize the variables
  //
  int_4 max_pixel = 0;
  int_4 max_line = 0;
  
  // initializing the number of lines to zeros
  //
  memset((void*)num_lines_a, (int)0, (width_a * height_a));
  
  for (int_4 i=0; i<height_a; i++) {
    for (int_4 j=0; j<width_a; j++) {
      
      // initializing the number of pixels and the deviations in the horizontal
      // and vertical direction
      //
      int_4 pixel_num = 0;
      int_4 h_dev = 0;
      int_4 v_dev = 0;
      
      // storing the row and the column numbers
      //
      int_4 row_num = i;
      int_4 col_num = j;
      
      // checking for the edge
      //
      while (((uint_2)edge_data_a[i * width_a + j]) == IMAGA_EDGE_COLMAX) {
	
	edge_data_a[i * width_a + j] = 0;
	pixel_num++;
	
	h_dev = col_num - j;
	v_dev = 0;
	
	// if the pixel is an edge, increment the row to check for the
	// next vertical pixel
	//
	if ((i + 1) < height_a) {
	  if (((uint_2)edge_data_a[(i + 1) * width_a + j])
	      == IMAGA_EDGE_COLMAX) {
	    i++;
	  }
	}
	
	// if the immediate veritcal pixel does not correspond to the line,
	// increment the row number until the vertical deviation limit
	//
	else {
	  
	  while ((v_dev < IMAGA_EDGE_VDEV) && ((i + v_dev) < height_a)
		 && ((uint_2)edge_data_a[(i + v_dev) * width_a + j])
		 != IMAGA_EDGE_COLMAX) {
	    v_dev++;
	  }
	  
	  // if the vertical deviation is within the limit
	  //
	  if ((v_dev < IMAGA_EDGE_VDEV) && ((i + v_dev) < height_a)) {
	    i = v_dev + i;
	    pixel_num = pixel_num + IMAGA_EDGE_PINCR;
	  }
	  
	  // if there is no line in the vertical direction check to see
	  // if there is any by assuming a limit in the horizontal direction
	  //
	  else if (((i + 1) < height_a) && ((j + 1) < width_a) &&
		   (((uint_2)edge_data_a[(i + 1) * width_a + j + 1])
		    == IMAGA_EDGE_COLMAX) && (abs(h_dev) < IMAGA_EDGE_HDEV)) {
	    j++;
	    i++;
	    h_dev++;
	  }
	  
	  // checking the limit in the deviation in the horizontal direction
	  //
	  else if (((i + 1) < height_a) && (j > 0) &&
		   (((uint_2)edge_data_a[(i + 1) * width_a + j -1])
		    == IMAGA_EDGE_COLMAX) && (abs(h_dev) < IMAGA_EDGE_HDEV)) {
	    j--;
	    i++;
	    h_dev++;
	  }
	}
      }
      
      // checking if the pixel count is large enough to treat it as a line
      //
      if (pixel_num >= IMAGA_EDGE_PIXEL) {
	if (pixel_num > max_pixel) {
	  max_pixel = pixel_num;
	}
	max_line = max_line + 1;
	edge_t_tlines_d = edge_t_tlines_d + 1;
	num_lines_a[pixel_num] = num_lines_a[pixel_num] + 1;

	// assigning the pixel_num to the particular bin
	//
	if (edge_assign_cc(pixel_num) == ISIP_FALSE) {
	  error_handler_cc((char_1*)"edge_lines_cc",
			   (char_1*)"error while computing the bins");
	  return ISIP_FALSE;
	  
	}
      }
      i = row_num;
      j = col_num;
    }
  }

  // for debugging
  //
  //fprintf(stdout, "%ld\t", edge_t_tlines_d);
  
  // initializing the number of lines
  //
  int_4 small_lines = 0;
  int_4 long_lines = 0;
  
  // calculating the percentage of small and long lines
  //
  for (int_4 m=0; m<IMAGA_EDGE_SLIM; m++) {
    small_lines = small_lines + num_lines_a[m];
  }
  
  for (int_4 n=IMAGA_EDGE_LLIM; n<height_a; n++) {
    long_lines = long_lines + num_lines_a[n];
  }

  if (max_line != 0) {
    edge_pershrt_t_lines_d = (float_8)small_lines / max_line;
    edge_perlong_t_lines_d = (float_8)long_lines / max_line;
  }
  
  // print the mean value of each of the color
  //
  //fprintf(stdout, "%3.3f\t%3.3f\n", edge_perlong_t_lines_d, edge_pershrt_t_lines_d);
  
  // providing the debugging information
  //
  if (debug_level_d > ISIP_DEBUG_NONE) {
    fprintf(stdout, "<%s> %s:\n", "Image_analysis::edge_lines_cc",
	    "distribution of lines");

    for (int_4 i=0; i < height_a; i++) {
      if (num_lines_a[i] != (int)0) {
	fprintf(stdout, "%ld: %ld\n", i, num_lines_a[i]);
      }
    }
  }
  
  // exit gracefully
  //
  return ISIP_TRUE;
}


































































































