4

Я пытаюсь найти способ, чтобы найти угловые точки на этом бинарного изображения в MatLabMatLab: Угол обнаружения на бинарном изображении

Binary Image

Я пытался найти способ, чтобы соответствовать треугольник над это изображение и поиск вершин. Я попытался найти углы, но возвращаемые значения не всегда верны.
Есть ли способ, чтобы я мог затачивать края так, чтобы функция угла могла возвращать лучшие результаты?

Я ценю любой ввод! Благодаря!

enter image description here

Какая стратегия кажется проще и эффективнее? Какие существующие функции MatLab можно использовать?

+1

сколько/какие углы вы хотите обнаружить? можете ли вы добавить изображение с обрисованными углами? –

+0

Должно быть 3 угла, и я добавил приложение к исходному вопросу. – user3315340

+0

Кто-нибудь знает, как мне обнаружить три угла? Я смотрел в houghline, но я не уверен, как правильно его использовать. – user3315340

ответ

2

Вместо подхода обработки изображений, давайте попробуем более алгебраический подход.

У вас есть белые пиксели - 2D-точки на плоскости, и вы хотите найти три полуплоскости (прямые линии), которые лучше всего отделяют эти точки от остальной части плоскости.

Итак, давайте начнем

img=imread('http://i.stack.imgur.com/DL2Cq.png'); %// read the image 
bw = img(:,:,1) > 128; %// convert to binary mask 
[y x] = find(bw); %// get the x-y coordinates of white pixels 
n=numel(x); %// how many do we have 

Для устойчивости вычесть среднее всех точек - центровка белые пиксели вокруг происхождения:

mm = mean([x y],1); 
mA = bsxfun(@minus, [x y], mm); 

Теперь, линия может быть описана двумя параметрами , все точки (x, y), которые удовлетворяют L(1)*x + L(2)*y = 1. Чтобы найти прямую, что все точки строго соответствуют одной ее стороне, это неравенство должно выполняться для всех точек (x,y) набора: L(1)*x + L(2)*y <= 1. Мы можем заставить эти неравенства и поиск наиболее плотно полуплоскость L, что выполнить это ограничение с помощью quadprog:

L1 = quadprog(eye(2), -ones(2,1), mA, ones(n,1)); 
L2 = quadprog(eye(2), ones(2,1), mA, ones(n,1)); 
L3 = quadprog(eye(2), [1; -1], mA, ones(n,1)); 

Обратите внимание, как за счет изменения квадратичной цели оптимизации f, мы можем получить разные половины плоскости, разделяющие белые пиксели ,

После того, как у нас есть три линии, мы можем получить точки пересечения (сдвигающие их от начала координат mm):

x12=inv([L1';L2'])*ones(2,1)+mm'; 
x23=inv([L3';L2'])*ones(2,1)+mm'; 
x13=inv([L3';L1'])*ones(2,1)+mm'; 

Вы можете использовать увидеть результаты

imshow(bw,'border','tight'); 
hold all; 
%// plot the lines 
ezplot(gca, @(x,y) L1(1)*(x-mm(1))+L1(2)*(y-mm(2))-1, [1 340 1 352]); 
ezplot(gca, @(x,y) L2(1)*(x-mm(1))+L2(2)*(y-mm(2))-1, [1 340 1 352]); 
ezplot(gca, @(x,y) L3(1)*(x-mm(1))+L3(2)*(y-mm(2))-1, [1 340 1 352]); 
%// plot the intersection points 
scatter([x12(1) x23(1) x13(1)],[x12(2) x23(2) x13(2)],50,'+r'); 

enter image description here

+0

Этот код отлично работает на некоторых изображениях, которые у меня есть, но, похоже, некоторые проблемы возникают, если я даю ему определенные изображения, подобные этому: http://imgur.com/qqg3cKS. Есть ли способ исправить это? – user3315340

+0

@ user3315340, бит с термином 'f' в' quadprog' (второй аргумент), приводит к различным решениям, для изображения, которое вы отправили 'L3 = quadprog (eye (2), [-1; 1], mA, (n, 1)), дает требуемое решение. – Shai

0

Вы можете найти минимальную площадь, описанную в треугольнике.

Сначала вычислите выпуклую оболочку капли.

Затем попробуйте все различные варианты трех сторон корпуса, протяните стороны, вычислив попарные пересечения и сохраните треугольник с наименьшей положительной областью.

enter image description here