Страница 3 из 3

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 28.11.2010 (Вс) 15:52
arthur2
Хакер писал(а):Вот. Это явное свидетельство, что делаешь ты совершенно что-то своё.
Это свидетельствует о том, что у нас нет договоренности в терминах. Фигуры типа X я и назвал разветвляющимися. Можешь назвать по-другому - суть не изменится. Нигде я не говорил о разветвляющихся контурах.
Хакер писал(а):По два на каждый растущий контур.
На контур вокруг фигуры типа X после середины нужно не два, а четыре массива, или я чего-то опять не понимаю в твоем предложении

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 28.11.2010 (Вс) 17:05
Хакер
Если говорить об иксе: на первой строке возникнет два контура.
Они будут расти и на верхней части перекрестия объединяться в один.
На нижней части перекрестия возникнет новый контур (который рискует стать внутренним, но не станет).
На самой нижней строке первый и последний контуры объединятся в один.

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 28.11.2010 (Вс) 17:40
arthur2
Хакер писал(а):На нижней части перекрестия возникнет новый контур (который рискует стать внутренним, но не станет).
Ага, вот в этом месте мой алгоритм отличается от твоего. Пойду подумаю :)

Хакер писал(а):делаешь ты совершенно что-то своё.
Кстати, я свой алгоритм подробно описал, обидно, что ты даже не прочитал, а то бы давно уже сказал, что не так :oops:

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 28.11.2010 (Вс) 17:48
Хакер
arthur2 писал(а):Ага, вот в этом месте мой алгоритм отличается от твоего.

А как он может отличаться? «Пах» буквы X в плане «островковости» ничем не лучше верхушек буквы X. С какой стати твой алгоритм хоть на долю процента различает два эти островка и по разному обрабатывает? Как хоть сколько-нибудь здравый принцип логический лежит в таком разделении.

Как ещё можно поступать, кроме как создать из нового островка контур и ждать, пока он не замкнётся либо сам с собой (CCW с CW), либо не соединится с другим контуром (любая ветка (CW/CCW) с любой).

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 28.11.2010 (Вс) 18:59
Хакер
Ты на Си или на VB пишешь?

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 28.11.2010 (Вс) 19:57
arthur2
Хакер писал(а):А как он может отличаться?
тем не менее, он отличался, и в описании это есть :) Мой алгоритм был построен на строгом чередовании лево-право, поэтому внутренний контур обрабатывался не так же, как внешний.

В общем, твой вариант мне нравится больше, я переделываю :D

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 28.11.2010 (Вс) 20:45
arthur2
сейчас попробую на си :)

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 13.12.2010 (Пн) 22:27
arthur2
В общем, пришел пока к следующему:

1. После обхода контура на выходе каждая фигура описана координатами первой точки и массивом байт, каждый из которых описывает следующую точку. В байте четыре значимых бита: влево, вправо, вниз, вверх. То есть, если следующая точка по диагонали вверх и влево, то установлены биты "вверх" и "влево".
Код: Выделить всё
Private Enum V_UDLR
    V_U = &H1 'up
    V_L = &H2 'left
    V_D = &H4 'down
    V_R = &H8 'right
    V_UL = V_U Or V_L
    V_LD = V_L Or V_D
    V_DR = V_D Or V_R
    V_RU = V_R Or V_U
End Enum
То есть, каждая точка описана одним из восьми байтов. При таком подходе легко сравнивать участки контура с эталонами.

2. Теперь поиск вершин. Есть несколько сочетаний, которые заведомо вершины. Их совсем немного: U-D, UR-DR, R-D и ещё девять, им симметричных. Обычным InStrB ищу вхождение этих сочетаний в массив, описывающий фигуру. Несколько вершин у меня уже есть.

3. Если ни одной вершины не найдено, то значит контур довольно-таки округлый, плавный. Сравниваю с другими эталонами, которые могут быть вершинами, а могут и не быть. Получаю несколько точек с подозрением на вершины.

3. По алгоритму Брезенхэма строю эталонные отрезки между вершинами или подозреваемыми вершинами. При сбое алгоритма добавляю сбойную точку в список вершин и рекурсионно перепроверяю участок от точки до точки.

4. Если участок контура распадается на отрезки короче пяти точек, то считаю этот участок плавно изогнутым и добавляю в список вершин все точки, на которых изменилось направление.

Пока что контур масштабируется довольно угловато :( И есть ещё несколько неучтенных вариантов.

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 13.12.2010 (Пн) 22:51
Хакер
Не понял большей части написанного. Почему сделано не так, как я велел?

arthur2 писал(а):Пока что контур масштабируется довольно угловато :(

Ничего не поделаешь.

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 13.12.2010 (Пн) 23:27
arthur2
Хакер писал(а):Почему сделано не так, как я велел?
:lol:
Как ты посоветовал. Я, в общем-то, сделал как раз так - алгоритм тот, просто реализация своя (а ты реализации и не описывал).
А что не понятно-то? Каждая точка контура описана не координатами, а положением относительно предыдущей точки. Эта мысль мне очень нравится: удобно сравнивать участки контура с эталонами и между собой.

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 23.12.2010 (Чт) 1:29
arthur2
Передал контур в функцию Poligon. Сначала передавал "оптимизированные" вершины, но вылез косяк - контуры не совпали. Тогда передал просто тупо все найденные точки контура:
Изображение
Круг изначально был красным. Белый контур - нарисован по алгоритму. Черный - нарисован Poligon-ом по ВСЕМ точкам контура (без пропусков). Почему они не совпали? И что делать?

Причем, справа и снизу контуры совпали полностью, а слева и сверху разошлись на один пиксель. Ну а в левом верхнем углу - на все два пикселя.

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 23.12.2010 (Чт) 1:32
Хакер
Чёрный с зелёным — потому что ты где-то в коде допустим ошибку (возможно очень глобоко), пропустив концептуальную единицу.

Чёрное с красным —, скорее всего, из разницы в реализации растеризующих алгоритмов.

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 23.12.2010 (Чт) 1:37
arthur2
Белый контур - тот, который по алгоритму - совпал и с иходной фигурой полностью. Так что в алгоритме ошибки нет.

В полигон я передал ВСЕ ТОЧКИ, по которым был построен белый контур. Без пропусков. Почему в левом верхнем углу полигон отошел от переданных точек аж на два пикселя?

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 23.12.2010 (Чт) 1:40
Хакер
arthur2 писал(а):Белый контур - тот, который по алгоритму - совпал и с иходной фигурой полностью. Так что в алгоритме ошибки нет.


Тогда причём тут я?

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 23.12.2010 (Чт) 1:41
arthur2
Ты-то тут причем? :shock:

Вопрос в том, почему полигон, построенный по заданным точкам функцией Poligon, не проходит через эти точки.

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 23.12.2010 (Чт) 2:04
Хакер
arthur2 писал(а):почему полигон, построенный по заданным точкам функцией Poligon, не проходит через эти точки.

Хакер писал(а):скорее всего, из разницы в реализации растеризующих алгоритмов.

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 23.12.2010 (Чт) 2:21
arthur2
А что делать? :oops:

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 23.12.2010 (Чт) 2:32
arthur2
Хакер писал(а):из разницы в реализации растеризующих алгоритмов.
Я передал в функцию набор точек. Просто набор точек. И попросил по ним построить линию. И эта построенная линия отошла от некоторых предложенных точек аж на два пикселя. По какому тогда принципу работает Poligon()?

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 23.12.2010 (Чт) 2:33
Хакер
Оффтопик.

Re: Векторизация контура. Как масштабировать картинку?

СообщениеДобавлено: 23.12.2010 (Чт) 4:15
arthur2
так-с, косяк-таки мой :oops: Контур выводился со смещением в один пиксель. Всё совпало! Убейте меня кто-нибудь! (или как там в автозамене?)