У вас есть пара проблем, которые вам нужно исправить, чтобы использовать подключенные компоненты в Imagemagick.
Во-первых, ваше изображение в формате JPG и, возможно, сглажено и, следовательно, в оттенках серого. (JPG - сжатие с потерями и изменяет значения). Таким образом, его нужно сделать двоичным, иначе вы получите слишком много регионов для того, что вы хотите сделать.
Во-вторых, вам нужно использовать -define connected-components: mean-color = true, чтобы выходное изображение выглядело как входное изображение и не имело шкалы яркости, соответствующие номерам идентификаторов регионов.
Например, если я сделаю следующее для вашего входного изображения, я получу много областей в оттенках серого.
convert image.jpg \
-define connected-components:verbose=true \
-define connected-components:area-threshold=0 \
-define connected-components:mean-color=true \
-connected-components 4 \
null:
0: 818x687+0+0 420.4,339.2 393850 gray(255)
6405: 213x232+560+260 667.8,373.2 38867 gray(255)
1066: 212x197+46+61 145.7,161.0 32689 gray(255)
11470: 197x189+180+453 278.4,547.6 27921 gray(255)
4764: 259x279+536+236 667.8,372.1 14056 gray(0)
86: 258x261+22+21 144.0,156.7 13604 gray(0)
10418: 241x236+159+430 278.8,546.4 12060 gray(0)
8450: 4x40+538+304 539.5,323.5 160 gray(2)
14378: 2x57+158+496 158.5,523.8 113 gray(3)
10247: 31x6+260+425 278.7,427.6 98 gray(255)
5996: 32x5+106+257 121.2,259.2 89 gray(255)
15035: 43x3+656+514 676.8,515.5 85 gray(0)
14031: 41x4+659+490 678.3,492.3 81 gray(255)
9942: 2x41+795+407 795.5,427.2 81 gray(4)
3152: 2x32+22+144 22.5,159.5 64 gray(3)
11234: 29x6+264+449 279.1,451.8 64 gray(0)
15824: 4x16+378+568 379.5,575.5 64 gray(2)
284: 28x5+127+33 140.6,35.3 61 gray(255)
14375: 3x58+153+496 154.9,525.4 60 gray(254)
14374: 1x56+154+496 154.0,523.5 56 gray(252)
14377: 1x56+157+496 157.0,523.5 56 gray(0)
14376: 1x56+156+496 156.0,523.5 56 gray(252)
7795: 28x3+101+282 114.5,283.5 54 gray(0)
...
В приведенном выше полном списке более 3 черных областей.
Но если я установлю порог в 50%, чтобы сделать изображение чисто черно-белым с сохранением в формате PNG, тогда я получу
convert image.jpg -threshold 50% -type bilevel \
-define connected-components:verbose=true \
-define connected-components:area-threshold=0 \
-define connected-components:mean-color=true \
-connected-components 4 \
null:
Objects (id: bounding-box centroid area mean-color):
0: 818x687+0+0 419.2,339.3 401926 gray(255)
4: 215x236+560+258 668.0,373.6 41506 gray(255)
2: 215x202+44+60 145.1,161.4 34718 gray(255)
6: 197x192+180+452 278.1,547.3 29700 gray(255)
3: 262x283+536+234 666.8,372.5 19261 gray(0)
1: 262x265+20+20 143.2,155.8 18388 gray(0)
5: 243x239+157+428 277.3,546.1 16467 gray(0)
Обратите внимание, что теперь есть только 3 серых (0), то есть черных региона. Если бы было несколько крошечных черных пятен, вы могли бы увеличить порог области, чтобы удалить их.
Теперь, чтобы извлечь ваши регионы, я бы сделал следующее. Я бы выделил ограничивающую рамку и центроид с подчеркиванием между ними и поместил в массив. Я бы сохранил пороговое изображение как вывод связанных компонентов (это можно сделать с помощью -define connected-components: mean-color = true. Затем я бы зациклился на пороговом изображении, залил области заливки (предполагая, что они закрыты). ) после извлечения центроида и затем обрезки после извлечения ограничительной рамки.
Входной сигнал:
box_cent_Arr=(`convert image.jpg -threshold 50% -type bilevel \
-define connected-components:verbose=true \
-define connected-components:mean-color=true \
-connected-components 4 \
image_t50.png | grep "gray(0)" | awk 'BEGIN {OFS="_"} {print $2,$3}'`)
num=${#box_cent_Arr[*]}
for ((i=0; i<num; i++)); do
bbox=`echo "${box_cent_Arr[$i]}" | cut -d\_ -f1`
centroid=`echo "${box_cent_Arr[$i]}" | cut -d\_ -f2`
convert image_t50.png -fill black -draw "color $centroid floodfill" -alpha off -crop $bbox +repage image_$i.png
done
Пороговое изображение:
Три извлеченные заполненные области:
Что касается вашего второго изображения:
В этом случае вам не нужно их заполнять, поэтому просто используйте ограничивающий прямоугольник. Но вам нужно увеличить порог области, чтобы удалить небольшие пятна рядом с областью третьей строки / второго столбца. Поэтому здесь я бы сделал следующее:
bboxArr=(`convert image.png -threshold 50% -type bilevel \
-define connected-components:verbose=true \
-define connected-components:area-threshold=1000 \
-define connected-components:mean-color=true \
-connected-components 4 \
image_t50.png | grep "gray(0)" | awk '{print $2}'`)
num=${#bboxArr[*]}
for ((i=0; i<num; i++)); do
bbox=`echo "${bboxArr[$i]}" | cut -d\_ -f1`
convert image_t50.png -crop $bbox +repage image_$i.png
done
В результате извлекаются 22 региона (которые я пронумеровал от 0 до 21). Например, вот первые 3: