
    i"                     N    d Z ddlZddlZddZ	 ddZd Zd Zd Zd Z	d	 Z
d
 Zy)zpFunctions useful for detecting graphical elements from the image to using OpenCV to reconstruct / detect tables.    Nc                    t        j                  |       }t        j                  |t         j                        }|st	        j
                  |      }t        j                  |dt         j                  t         j                  ||      }||fS )ak  Thresholds an image using OpenCV's adaptiveThreshold.

    Parameters
    ----------
    imagename : string
        Path to image file.
    process_background : bool, optional (default: False)
        Whether or not to process lines that are in background.
    blocksize : int, optional (default: 15)
        Size of a pixel neighborhood that is used to calculate a
        threshold value for the pixel: 3, 5, 7, and so on.

        For more information, refer `OpenCV's adaptiveThreshold
        <https://docs.opencv.org/2.4/modules/imgproc/doc/miscellaneous_transformations.html#adaptivethreshold>`_.
    c : int, optional (default: -2)
        Constant subtracted from the mean or weighted mean.
        Normally, it is positive but may be zero or negative as well.

        For more information, refer `OpenCV's adaptiveThreshold
        <https://docs.opencv.org/2.4/modules/imgproc/doc/miscellaneous_transformations.html#adaptivethreshold>`_.

    Returns
    -------
    img : object
        numpy.ndarray representing the original image.
    threshold : object
        numpy.ndarray representing the thresholded image.
       )	cv2imreadcvtColorCOLOR_BGR2GRAYnpinvertadaptiveThresholdADAPTIVE_THRESH_GAUSSIAN_CTHRESH_BINARY)	imagenameprocess_background	blocksizecimggray	thresholds          K/home/agent/.local/lib/python3.12/site-packages/camelot/image_processing.pyadaptive_thresholdr      sn    : **Y
C<<S//0Dyy%%c31133D3DiQRI 	>    c                 8   |dvrt        d      t        | ||      \  }}t        | |      } t        | ||      }t	        j
                  |j                  t        j                        t        j                  t        j                        \  }}	t        ||      }
||
fS )ae  
    Finds horizontal and vertical lines by applying morphological transformations on an image.

    Parameters
    ----------
    threshold : object
        numpy.ndarray representing the thresholded image.
    regions : list, optional (default: None)
        List of page regions that may contain tables of the form x1,y1,x2,y2
        where (x1, y1) -> left-top and (x2, y2) -> right-bottom
        in image coordinate space.
    direction : string, optional (default: 'horizontal')
        Specifies whether to find vertical or horizontal lines.
    line_scale : int, optional (default: 40)
        Factor by which the page dimensions will be divided to get
        smallest length of lines that should be detected.
    iterations : int, optional (default: 0)
        Number of times for erosion/dilation is applied.

    Returns
    -------
    dmask : object
        numpy.ndarray representing pixels where vertical/horizontal
        lines lie.
    lines : list
        List of tuples representing vertical/horizontal lines with
        coordinates relative to a left-top origin in
        image coordinate space.
    )vertical
horizontalz6Specify direction as either 'vertical' or 'horizontal')
ValueErrorcreate_structuring_elementapply_region_maskprocess_imager   findContoursastyper	   uint8RETR_EXTERNALCHAIN_APPROX_SIMPLEextract_lines_from_contours)r   regions	direction
line_scale
iterationselsizeprocessed_thresholdcontours_liness              r   
find_linesr/   .   s    @ 22QRR))Y
KHB!)W5I'	2zB""""288,c.?.?AXAXKHa ()<E%%r   c                     |dk(  r<| j                   d   |z  }t        j                  t        j                  d|f      }||fS | j                   d   |z  }t        j                  t        j                  |df      }||fS )a  
    Create a structuring element based on the specified direction.

    Parameters
    ----------
    threshold : object
        numpy.ndarray representing the thresholded image.
    direction : string
        Direction to create the structuring element.
    line_scale : int
        Factor for scaling the size of the structuring element.

    Returns
    -------
    tuple
        The structuring element and its size.
    r   r      )shaper   getStructuringElement
MORPH_RECT)r   r&   r'   r*   r)   s        r   r   r   ^   s|    $ Jq!Z/&&s~~4yA
 t8O q!Z/&&s~~ayAt8Or   c                     |dt        j                  | j                  t         j                        }|D ]  }|\  }}}}d||||z   |||z   f<    t        j                  | |      } | S )aF  
    Apply a mask to the threshold image based on specified regions.

    Parameters
    ----------
    threshold : object
        numpy.ndarray representing the thresholded image.
    regions : list
        List of regions to apply the mask.

    Returns
    -------
    numpy.ndarray
        The masked threshold image.
    )dtyper1   )r	   zerosr2   r!   multiply)r   r%   region_maskregionxywhs           r   r   r   z   su      hhybhh? 	2FJAq!Q01KAE	1q1u9,-	2 KK	;7	r   c                     t        j                  | |      } t        j                  | |      } t        j                  | ||      }|S )a  
    Apply morphological operations to the threshold image.

    Parameters
    ----------
    threshold : object
        numpy.ndarray representing the thresholded image.
    el : object
        Structuring element for morphological operations.
    iterations : int
        Number of iterations for dilation.

    Returns
    -------
    numpy.ndarray
        The processed threshold image.
    )r(   )r   erodedilate)r   r)   r(   dmasks       r   r   r      s;    $ 		)R(I

9b)IJJy"<ELr   c                    g }| D ]x  }t        j                  |      \  }}}}|||z   }	}|||z   }}
|dk(  r"|j                  ||	z   dz  |||	z   dz  |
f       R|dk(  sX|j                  ||
|z   dz  |	|
|z   dz  f       z |S )ae  
    Extract lines from contours based on the specified direction.

    Parameters
    ----------
    contours : list
        List of contours found in the image.
    direction : string
        Specifies whether to extract vertical or horizontal lines.

    Returns
    -------
    list
        List of tuples representing the coordinates of the lines.
    r      r   )r   boundingRectappend)r,   r&   r.   r   r;   r<   r=   r>   x1x2y1y2s               r   r$   r$      s      E C%%a(
1aAEBAEB
"LL27q."rBw1nbAB,&LL"rBw1nb27q.ABC Lr   c                    | |z   }t        j                  |j                  t        j                        t         j
                  t         j                        \  }}t        |t         j                  d      dd }g }|D ]H  }t        j                  |dd      }t        j                  |      \  }}	}
}|j                  ||	|
|f       J |S )a  Find table boundaries using OpenCV's findContours.

    Parameters
    ----------
    vertical : object
        numpy.ndarray representing pixels where vertical lines lie.
    horizontal : object
        numpy.ndarray representing pixels where horizontal lines lie.

    Returns
    -------
    cont : list
        List of tuples representing table boundaries. Each tuple is of
        the form (x, y, w, h) where (x, y) -> left-top, w -> width and
        h -> height in image coordinate space.

    T)keyreverseN
      )r   r   r    r	   r!   r"   r#   sortedcontourAreaapproxPolyDPrE   rF   )r   r   maskr,   __contr   c_polyr;   r<   r=   r>   s               r   find_contoursrW      s    $ j D##BHHs00#2I2ILHb hCOOTB3BGHD "!!!Q-%%f-
1aQ1aL!" Kr   c                    t        j                  ||      }i }| D ]  }|\  }}}}	||||	z   |||z   f   }
t        j                  |
j	                  t         j
                        t        j                  t        j                        \  }}t        |      dk  r}g }|D ]K  }t        j                  |      \  }}}}|d|z  |z   dz  z   |d|z  |z   dz  z   }}|j                  ||f       M |||||	z   ||z   |f<    |S )a  Find joints/intersections present inside each table boundary.

    Parameters
    ----------
    contours : list
        List of tuples representing table boundaries. Each tuple is of
        the form (x, y, w, h) where (x, y) -> left-top, w -> width and
        h -> height in image coordinate space.
    vertical : object
        numpy.ndarray representing pixels where vertical lines lie.
    horizontal : object
        numpy.ndarray representing pixels where horizontal lines lie.

    Returns
    -------
    tables : dict
        Dict with table boundaries as keys and list of intersections
        in that boundary as their value.
        Keys are of the form (x1, y1, x2, y2) where (x1, y1) -> lb
        and (x2, y2) -> rt in image coordinate space.

       rD   )r	   r8   r   r   r    r!   
RETR_CCOMPr#   lenrE   rF   )r,   r   r   jointstablesr   r;   r<   r=   r>   roijcrT   joint_coordsjjxjyjwjhc1c2s                        r   find_jointsrh      s%   . [[:.FF 4
1aQQYAE	)*!!JJrxx #..#2I2I
B r7a< 	*A --a0NBB!b&2+!++Q!b&2+!1C-CBR)	* (41q5!a%#$4 Mr   )F   )Nr   (   r   )__doc__r   numpyr	   r   r/   r   r   r   r$   rW   rh    r   r   <module>ro      s@    v 
 $P PQ-&`842:D(r   