cellCoords :: Img -> (Int,Int) -> CellCoords
cellCoords img topLeftCoord = (xcentres, ycentres, cellMinLength)
  where
    h = imageHeight img
    w = imageWidth img
    coords = iterate belowRight topLeftCoord
    afterEdge = dropWhile (pixAtIsEdge img) coords
    topLeftNonEdge = head afterEdge
    nextOne = belowRight topLeftNonEdge
    row = map (\c -> (c, pixAt img c)) (takeWhile ((<w) . fst) (iterate right nextOne))
    grow = map (head &&& length) . groupBy ((==) `on` snd) $ row
    cellMinLength = round (0.8 * fromIntegral (snd (head grow)))
    cellMaxLength = round (1.2 * fromIntegral (snd (head grow)))
    rowcells = filter (\ (_,l) -> cellMinLength <= l) (takeWhile ((<= cellMaxLength) . snd) grow)
    xcentres = map (\ (((x,_),_p), l) -> x + (l `div` 2)) rowcells

    col = map (\c -> (c, pixAt img c)) (takeWhile ((<h) . snd) (iterate below nextOne))
    gcol = map (head &&& length) . groupBy ((==) `on` snd) $ col
    colcells = filter (\ (_,l) -> cellMinLength <= l) (takeWhile ((<= cellMaxLength) . snd) gcol)
    ycentres = map (\ (((_,y),_p), l) -> y + (l `div` 2)) colcells
cellCoords :: Img -> (Int,Int) -> CellCoords
cellCoords img topLeftCoord = (xcentres, ycentres, cellMinLength)
  where
    h = imageHeight img
    w = imageWidth img
    coords = iterate belowRight topLeftCoord
    afterEdge = dropWhile (pixAtIsEdge img) coords
    topLeftNonEdge = head afterEdge
    nextOne = belowRight topLeftNonEdge
    row = map (\c -> (c, pixAt img c)) (takeWhile ((<w) . fst) (iterate right nextOne))
    grow = map (head &&& length) . groupBy ((==) `on` snd) $ row
    cellMinLength = round (0.8 * fromIntegral (snd (head grow)))
    cellMaxLength = round (1.2 * fromIntegral (snd (head grow)))
    rowcells = filter (\ (_,l) -> cellMinLength <= l) (takeWhile ((<= cellMaxLength) . snd) grow)
    xcentres = map (\ (((x,_),_p), l) -> x + (l `div` 2)) rowcells

    col = map (\c -> (c, pixAt img c)) (takeWhile ((<h) . snd) (iterate below nextOne))
    gcol = map (head &&& length) . groupBy ((==) `on` snd) $ col
    colcells = filter (\ (_,l) -> cellMinLength <= l) (takeWhile ((<= cellMaxLength) . snd) gcol)
    ycentres = map (\ (((_,y),_p), l) -> y + (l `div` 2)) colcells
cellCoords img topLeftCoord = (xcentres, ycentres, cellMinLength)
  where
    h = imageHeight img
    w = imageWidth img
    coords = iterate belowRight topLeftCoord
    afterEdge = dropWhile (pixAtIsEdge img) coords
    topLeftNonEdge = head afterEdge
    nextOne = belowRight topLeftNonEdge
    row = map (\c -> (c, pixAt img c)) (takeWhile ((<w) . fst) (iterate right nextOne))
    grow = map (head &&& length) . groupBy ((==) `on` snd) $ row
    cellMinLength = round (0.8 * fromIntegral (snd (head grow)))
    cellMaxLength = round (1.2 * fromIntegral (snd (head grow)))
    rowcells = filter (\ (_,l) -> cellMinLength <= l) (takeWhile ((<= cellMaxLength) . snd) grow)
    xcentres = map (\ (((x,_),_p), l) -> x + (l `div` 2)) rowcells

    col = map (\c -> (c, pixAt img c)) (takeWhile ((<h) . snd) (iterate below nextOne))
    gcol = map (head &&& length) . groupBy ((==) `on` snd) $ col
    colcells = filter (\ (_,l) -> cellMinLength <= l) (takeWhile ((<= cellMaxLength) . snd) gcol)
    ycentres = map (\ (((_,y),_p), l) -> y + (l `div` 2)) colcells