Алгоритм автофокуса для USB-микроскопа

Я пытаюсь разработать систему автофокусировки для недорогого USB-микроскопа. Я разрабатывал аппаратную сторону с прецизионным двигателем PAP, который может регулировать ручку фокусировки в микроскоп, и теперь самое сложное.

Я думал о том, как реализовать программное обеспечение. Аппаратное обеспечение имеет два USB-порта, один для камеры микроскопа, а другой для мотора. Моя первоначальная идея — написать приложение на C#, способное получать изображение с микроскопа и двигать двигатель вперед и назад, пока все хорошо :)

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

Я гуглил, но безуспешно... Буду признателен за любую помощь/идею/рекомендацию!

Большое спасибо :)

РЕДАКТИРОВАНИЕ: Спасибо, ребята, за ваши ответы, я попробую все варианты и вернусь сюда с результатами (или, может быть, с другими вопросами).


person SubniC    schedule 19.11.2010    source источник
comment
Это звучит похоже на этот вопрос - stackoverflow.com/questions/2134934/image-focus- расчет   -  person Graham Clark    schedule 19.11.2010
comment
Правильно, я не показывал этот пост раньше. благодаря.   -  person SubniC    schedule 19.11.2010
comment
@SubniC См. также stackoverflow.com/a/32951113/15485   -  person Alessandro Jacopson    schedule 05.10.2015
comment
@AlessandroJacopson, спасибо, приятно читать, я бы хотел попробовать этот метод :)   -  person SubniC    schedule 12.10.2015


Ответы (4)


Самая важная часть — это код, который сообщает вам, насколько изображение не в фокусе. Поскольку несфокусированное изображение теряет высокочастотные данные, я бы попробовал что-то вроде следующего:

long CalculateFocusQuality(byte[,] pixels)
{
  long sum = 0;
  for(int y = 0; y<height-1; y++)
    for(int x=0; x<width-1; x++)
    {
      sum += Square(pixels[x+1, y] - pixels[x, y]);
      sum += Square(pixels[x, y] - pixels[x, y+1]);
    }
  return sum;
}

int Square(int x)
{
  return x*x;
}

Этот алгоритм не работает, если изображение зашумлено. В этом случае вы можете уменьшить его или использовать более сложный алгоритм.

Или другая идея - вычислить вариацию значений пикселей:

long CalculateFocusQuality(byte[,] pixels)
{
  long sum = 0;
  long sumOfSquares = 0;
  for(int y=0; y<height; y++)
    for(int x=0; x<width; x++)
    {
      byte pixel=pixels[x,y];
      sum+=pixel;
      sumofSquares+=pixel*pixel;
    }
  return sumOfSquares*width*height - sum*sum;
}

Эти функции работают с монохроматическими изображениями, для изображений RGB просто суммируются значения для каналов.

Используя эту функцию, измените фокус, пытаясь максимизировать CalculateFocusQuality. Увеличьте размер шага, если несколько попыток подряд улучшили качество, и уменьшите его и измените направление, если шаг снизил качество.

person CodesInChaos    schedule 19.11.2010
comment
Спасибо CodeInChaos, я попробую ваш фрагмент и расскажу, как он работает :) - person SubniC; 21.11.2010
comment
В ваших алгоритмах есть небольшая опечатка: ваш цикл y сравнивает x с высотой. Кроме того, не даст ли второй алгоритм более высокую оценку полностью белому изображению, чем чередующемуся бело-черному рисунку шахматной доски? Это кажется неправильным, так как шахматная доска больше в фокусе. - person Mike; 07.11.2012
comment
@noroom Спасибо. Ни один из алгоритмов не делал того, что я намеревался сделать. Должно быть исправлено сейчас. Пожалуйста, дайте мне знать, если вы найдете другую ошибку. - person CodesInChaos; 08.11.2012

Автофокусировка микроскопа — давняя тема в оптических исследованиях.
Вы можете немного узнать об используемых алгоритмах здесь.

Проблема заключается не только в том, как измерить расфокусировку, но и в том, как оптимально перемещать оптическую ось и как алгоритмически корректировать остаточные аберрации.

ХТХ!

person Dr. belisarius    schedule 19.11.2010
comment
Привет, Велизарий, очень интересная статья, я постараюсь получить некоторую информацию, которая может мне помочь. С уважением. - person SubniC; 19.11.2010

просто некоторые из моих опытов, пытаясь решить подобную задачу. В моей системе используется 200-кратное увеличение. Разрешение шагового двигателя в направлении Z 0,001 мкм.

Проблемы с которыми я столкнулся: -Тряска. Изображение в теоретически лучшем положении могло быть оценено хуже из-за внезапной тряски. Поскольку API моей системы не позволял перемещать ось z и делать изображения параллельно, мне пришлось двигаться поэтапно и захватывать последовательно. Каждый ход-стоп вызывал тряску. Интересно, что тряска была сильнее при движении вниз, чем при движении вверх.

-Механическая неточность. Сканирование и перемещение в теоретически наилучшее положение может привести к ошибке, поскольку положение шагового двигателя в контроллере может не совпадать с механическим положением.

-Экспозиция: в зависимости от приложения яркость изображения может различаться, поэтому экспозицию необходимо отрегулировать. В зависимости от алгоритма оценки фокуса (учитывается ли яркость в расчете или нет) может потребоваться фиксация экспозиции. Это приводит к проблеме куриного яйца - как настроить экспозицию, если неизвестна яркость изображения и как сфокусироваться, если неизвестна требуемая экспозиция.

Наконец, чтобы избежать механических проблем, я (пере)сохранил лучшее изображение, найденное во время фокусировки, и вернул его в конце. Что касается алгоритма значения фокуса, то лучше всего он искал края в сочетании с полным количеством цветов (шириной гистограммы). Но, конечно, это зависит от типа изображения, которое вы обрабатываете.

С уважением, Валентин Хайниц.

person Community    schedule 29.05.2012

Некоторая информация содержится в Википедии.

Технически это может быть реализовано как фильтр верхних частот и некоторая система, которая сознательно перемещает объектив вокруг точки, где выходной сигнал фильтра является максимальным. Цифровая обработка не требуется

Кроме того, 5 из первых 6 совпадений, которые я получаю в Google для «алгоритма автофокуса», кажутся релевантными и полезными (хотя в одном или двух случаях полная информация о документах требует оплаты).

person The Archetypal Paul    schedule 19.11.2010
comment
Здравствуйте, Пол, спасибо, что уделили время, я уже знаю страницу в Википедии, никогда не спрашивайте перед поиском. Может быть, я не так хорошо разбираюсь в Google :) я искал его, но не нашел алгоритма, который мог бы понять, мой математический фон не так силен, поэтому я прошу здесь о помощи. - person SubniC; 19.11.2010
comment
Я постараюсь научиться этому, если я не могу, я найду кого-нибудь, кто мне поможет. Но для начала очень приятно, что люди здесь, чтобы направить вас в правильном направлении :) - person SubniC; 19.11.2010
comment
Меня сбивает с толку, как реализовать фильтр верхних частот без «цифровой обработки». Конденсатор на USB-сигнал вроде не повесишь. - person Hans Passant; 19.11.2010
comment
@Hans Passant: Это цитата из статьи в Википедии, которая, конечно, не ограничивается USB. В нем говорится, что вы можете использовать аналоговый фильтр высоких частот на выходе аналоговой камеры для реализации автофокусировки. - person CodesInChaos; 19.11.2010
comment
Хе-хе, ворваться в музей, чтобы забрать камеру, у него будут проблемы :) - person Hans Passant; 19.11.2010