Один из подходов заключается в выполнении кластеризации черных пикселей изображения. Кластеры являются полками. Если полки параллельны оси, вы можете найти прямоугольники, просто взяв мин / макс в каждом направлении. Это работает довольно хорошо:
Пример кода (я преобразовал изображение в PNG, так как его легче читать, чем gif):
library(png)
library(dbscan)
library(tidyverse)
library(RColorBrewer)
img <- readPNG("G18JU.png")
is_black <-
img %>%
apply(c(1, 2), sum) %>% #sum all color channels
{. < 2.5} %>% # we assume black if the sum is lower than 2.5 (max value is 3)
which(arr.ind=TRUE) # the indices of the black pixels
clust <- dbscan(is_black, 2) # identify clusters
rects <-
as.tibble(is_black) %>%
mutate(cluster = clust$cluster) %>% # add cluster information
group_by(cluster) %>%
## find corner points of rectangles normalized to [0, 1]
summarise(xleft = max(col) / dim(img)[2],
ybottom = 1 - min(row) / dim(img)[1],
xright = min(col) / dim(img)[2],
ytop = 1 - max(row) / dim(img)[1])
## plot the image and the rectangles
plot(c(0, 1), c(0, 1), type="n")
rasterImage(img, 0, 0, 1, 1)
for (i in seq_len(nrow(rects))) {
rect(rects$xleft[i], rects$ybottom[i], rects$xright[i], rects$ytop[i],
border = brewer.pal(nrow(rects), "Paired")[i], lwd = 2)
}
Конечно, этот подход также обнаруживает другие черные линии как «прямоугольники» (например, черная граница). Но я думаю, вы легко можете создать «чистое» изображение.
Редактировать: метод расширения для поиска полок с черной линией
Чтобы расширить метод так, чтобы он мог отделить полки, которые разделяют черную линию:
Сначала определите прямоугольники, как описано выше.
Затем извлеките каждый прямоугольник из изображения и вычислите рядные значения. Это дает вам 1d изображение (= линия) для каждого прямоугольника. В этой строке примените порог и кластеризацию, как и раньше. Кластеры теперь являются сегментами черных линий, а среднее значение каждого кластера соответствует вертикальной линии, разделяемой двумя полками.
Чтобы найти горизонтальные общие линии, можно применить ту же процедуру, но с использованием столбцов вместо строк.