Я работаю над школьным проектом для класса графики. Моя задача — выделение краев на цветном изображении, поступило предложение использовать алгоритм обнаружения краев Канни.
Я решил написать всю программу сам на Java, потому что с приведенными формулами это выглядит легко. Я создал окно с Java Swing, я читаю входное изображение как изображение sRGB, преобразовывая его в CIELab* (потому что это часть задачи). Мне удалось применить ядра Собеля (Cx, Cy), которые определяют частную производную. Однако я застрял с формулой направления и кодирую ее.
Моя первая проблема заключается в том, что я не знаю, должен ли я вычислять направления в каждом отдельном цветовом канале или делать это одним куском.
Вот формулы для расчетов (сначала это направление, с которым я застрял, а на правильном размере есть величина, которая требует направления -тета)
Вот исходный код для расчета направления:
//Returns the gradients direction from Cx,Cy
public LabImg direction(LabImg Cx, LabImg Cy) {
LabImg result = new LabImg(Cx.getWidth(),Cx.getHeight());
for(int x = 0; x < result.getWidth(); x++) {
for(int y = 0; y < result.getHeight(); y++) {
float CxL = Cx.getPixel(x, y).getL();
float Cxa = Cx.getPixel(x, y).getA();
float Cxb = Cx.getPixel(x, y).getB();
float CyL = Cy.getPixel(x, y).getL();
float Cya = Cy.getPixel(x, y).getA();
float Cyb = Cy.getPixel(x, y).getB();
float dirL = (float) ((2*CxL*CyL)/((CxL*CxL)-(CyL*CyL)));
float dira = (float) ((2*Cxa*Cya)/((Cxa*Cxa)-(Cya*Cya)));
float dirb = (float) ((2*Cxb*Cyb)/((Cxb*Cxb)-(Cyb*Cyb)));
//float dir = (2*CxL*CyL+Cxa*Cya+Cxb*Cyb)/((CxL*CxL+Cxa*Cxa+Cxb*Cxb)-(CyL*CyL+Cya*Cya+Cyb*Cyb));
result.setLab(x, y, dirL, dira, dirb);
}
}
return result;
}
LabImg
— это тип данных, который содержит размер изображения, двумерный массив значений пикселей и буферизованное изображение.
hypot
иatan2
. - person Cris Luengo   schedule 24.04.2018