사용자 삽입 이미지
(원래 사진)
사용자 삽입 이미지

좀더 이해를 돕기 위해서
사용자 삽입 이미지
(원본)
사용자 삽입 이미지




아직 부족한건 많고 전진해야 한다. orz

소스와 원리는 http://rosagigantea.tistory.com/171 를 많이 참고

사용환경은 CImage를 사용해서 뿌렸기 때문에... ;; orz

게다가 단순 BackWard Mapping 방식이라 화상이 많이 쭈글거려진다... >_<

'알고리즘 > 이미지 처리' 카테고리의 다른 글

Perspective projection matrix  (0) 2008.03.05
다각형을 가져오기 위한 노력...  (0) 2008.03.04
ImageWarping Processing  (0) 2008.02.26
PNG 분석자료들  (0) 2008.02.24
이미지 와핑 소스(그나마 낳은거)  (0) 2008.02.20
이미지 와핑에 관해서  (0) 2008.02.19
어디서 가져온건데.. 어디지;; orz

'알고리즘 > 이미지 처리' 카테고리의 다른 글

다각형을 가져오기 위한 노력...  (0) 2008.03.04
ImageWarping Processing  (0) 2008.02.26
PNG 분석자료들  (0) 2008.02.24
이미지 와핑 소스(그나마 낳은거)  (0) 2008.02.20
이미지 와핑에 관해서  (0) 2008.02.19
GDI+에서의 투명색 처리...  (0) 2008.01.25

Morphing = Warping + Dissolving

Warping이란 이미지를 원하는 형태로 왜곡하는 것을 말합니다.
사용자 삽입 이미지

본 소스에서 사용된 기법은 그중에서 Mesh Warp라는 것으로 George Wolberg교수의
기법을 프로그램한 것입니다.
가장쉬운 방법은 line segment를 이용한 weight기법이 있고,
그 다음이 mesh warping입니다.
그 다음이 가장 직관적인 Surface generation기법이 있습니다.
아래에있는 morpro는 3차원 surface generation기법으로 구현한 것입니다만...
interpolation기법에 익숙치 않았던때라 결과물이 상당히 거칩니다.
그에 반해서 이 mesh warping은 catmull-rom의 spline interpolation을 통한
상당히 부드러운 결과물을 보여줍니다.

핵심 엔진은 마소에 연재되었던 이승준선배의 루틴입니다.


출처 : http://www.3dstudy.net/cgi-bin/ez2000/ezboard.cgi?db=download&action=read&dbf=6&page=1&depth=5

'알고리즘 > 이미지 처리' 카테고리의 다른 글

ImageWarping Processing  (0) 2008.02.26
PNG 분석자료들  (0) 2008.02.24
이미지 와핑 소스(그나마 낳은거)  (0) 2008.02.20
이미지 와핑에 관해서  (0) 2008.02.19
GDI+에서의 투명색 처리...  (0) 2008.01.25
이미지 회전 알고리즘  (0) 2008.01.18

HCI 과제 덕에 심심찮게 프로그래밍을 하게 되네요. 첫 과제 였던 3D rotation 관련을 구현하는 것도 상당히 흥미로웠지만, 두번째 과제인 Perspective Projection 를 구현하는 것은 정말 멋진 경험이었다고 생각합니다.

지난 며칠간 꽤나 재밌게 프로그래밍을 했던 관계로 블로그에도 살짝 정리해보는게 어떨까 하는 생각이 들었는데, 막상 쓸려니 내용이 잘 전해질지 의문이네요.

What is the Perspective Projection?

Perspective Projection 이란 아래의 왼쪽 이미지를 오른쪽 이미지 처럼 변화시키는 것을 얘기합니다. 꼭 저렇게 비뚜러진 이미지를 바로잡는것은 아니고, 이미지가 투영되는 면을 변화시키는 것이라고 생각하시면 됩니다.

사용자 삽입 이미지

이해를 돕기 위해 wikipedia 에서 이미지를 하나 가져왔습니다. 아래 이미지의 연보라색 면이 상이 맺히는 곳이라고 할 때, perspective transform 은 그 보라색 면을 이동시킨 것 같은 효과를 주기 위해 사용합니다.

사용자 삽입 이미지

How to get a projection matrix.

기본 적으로 Perspective Transform 을 위한 식은 다음과 같습니다.

사용자 삽입 이미지


homogenious coordinate 를 사용하고 있으니 x’ 와 y’ 에 관한 식은 아래와 같이 바꿔쓸 수 있습니다.

사용자 삽입 이미지


이를 정리하면 다음과 같은 꼴로 만들 수 있고,

사용자 삽입 이미지


우리가 값을 알고 싶은 변수들은 a, b, c, d, e, f, g, h 이렇게 8 개이므로, (x, y) 와 그에 대응되는 (x’, y’) 쌍을 4개만 알고 있으면 projection matrix 를 구할 수 있습니다. 이를 구하기 위한 매트릭스는 아래와 같습니다.

사용자 삽입 이미지


남은 건 8×8 matrix 의 inverse matrix 를 구한 뒤 뒤 쪽의 매트릭스에 곱해주는 것 뿐이군요.

Implementation of Perspective projection

이제까지 Perspective Transform 을 위한 매트릭스에 대해 알아봤습니다. 이제는 실제 구현을 해보는 것만 남았네요. 위에서 알아봤듯이 Perspective matrix 를 구하려면 matrix multiplication 과 inverse 를 위한 인터페이스가 필요합니다.

matrix multiplication 의 경우 서로 곱할 수 있는 형식인지를 체크한 뒤 단순한 계산을 하면 되고, inverse 는 gauss elimination 을 이용 reduced row echelon form 으로 만들어주는 것을 통해 쉽게(?) 구해낼 수 있습니다.

위의 두 가지까지 구현했다면, 이제 warping 만을 구현하면 되겠습니다. 이 warping 은 크게 두가지 방법을 통해 구현할 수 있습니다.

forward mapping

forward mapping 은 말 그대로 src 의 x, y 좌표에 대하 dst 의 x’, y’ 를 계산 한 뒤 값을 채워주는 방식입니다. 간단히 pseudo code 로 표현하면 다음과 같이 표현할 수 있겠네요.

for( y = 0 ; y < height ; y++ ){
    for( x = 0 ; x < width ; x++ ){
        x' = (ax+by+c) / (gx+hy+1);
        y' = (dx+ey+f) / (gx+hy+1);

        dst[y'][x'] = src[y][x];
    }
}

근데 막상 구현을 해놓고 보면 pixel 이 정수단위이기 때문에 아래와 같이 hole 이 발생하는 것을 확인할 수 있습니다.

사용자 삽입 이미지

backward mapping

위에서 얘기한 hole 을 방지하기 위한 방법 중 하나로 backward warping 이란 것이 있습니다. forward warping 에서 src 의 좌표를 기준으로 dst 의 좌표를 계산했다면, backward warping 에서는 dst 의 좌표를 기준으로 src 의 좌표를 계산하게 됩니다.

간단하게 pseudo code 로 표현하면 아래와 같이 되겠습니다.

for( y' = 0 ; y' < height ; y'++ ){
    for( x' = 0 ; x' < width ; x'++ ){
        x = (ax'+by'+c) / (gx'+hy'+1);
        y = (dx'+ey'+f) / (gx'+hy'+1);

        dst[y'][x'] = src[y][x];
    }
}

간단히 코드만 봐도 예상할 수 있겠지만 backward_warping 을 해주게 되면 hole 은 확실하게 없앨 수 있습니다. 결과 이미지는 아래와 같은데, 아주 깔끔한 결과가 나오지는 않았습니다.

사용자 삽입 이미지

forward (or backward) warping with interpolation

forward warping 을 하게 되면 hole 이 생기게 되고, 단순한 backward warping 을 하게 되면 이미지의 화질 저하가 발생하게 되는데, interpolation 을 사용하게 되면 이를 조금 더 개선할 수 있습니다.

전 linear-interpolation 을 사용해보았는데, 설명하기는 복잡하니 관심있으신 분은 저 아래 첨부할 소스를 참고해보시면 좋겠습니다. 결과는 아래와 같이 나옵니다.

우선 interpolation 을 이용한 forward warping 입니다. 복잡하게 하기는 귀찮고 해서 대강 구현했더니, hole 이 줄기는 했지만 여전히 존재하고 있습니다.

사용자 삽입 이미지

다음은 backward warping 에 linear interpolation 을 적용한 결과입니다. hole 도 없고, 보기에 상당히 괜찮아진 것을 확인할 수 있습니다.

사용자 삽입 이미지

소스코드:
http://trac.unfix.net/browser/snippet/image_projection/

참고자료:
http://en.wikipedia.org/wiki/Perspective_%28graphical%29
http://en.wikipedia.org/wiki/Gaussian_elimination

p.s) 부동 소숫점 연산에서 x - x/x*x = 0 이라는 것이 보장되질 않더군요. 코드 한 줄 줄일려다가 디버깅을 30분동안 해야했습니다. -_ㅜ

출처 : http://b.mytears.org/2007/10/599

'알고리즘 > 이미지 처리' 카테고리의 다른 글

PNG 분석자료들  (0) 2008.02.24
이미지 와핑 소스(그나마 낳은거)  (0) 2008.02.20
이미지 와핑에 관해서  (0) 2008.02.19
GDI+에서의 투명색 처리...  (0) 2008.01.25
이미지 회전 알고리즘  (0) 2008.01.18
Image Processing  (0) 2008.01.18

사용자 삽입 이미지


위에가 원본 bitmap 밑이 투명처리와 색 변환을 적용한 CachedBitmap.
자주색은 투명처리, 파란색은 노란색으로 변환.

투명처리 및 색 변화 모두 ImageAttributes 라는 객체에 값을 설정해서 Graphics객체의 DrawImage 등을 호출할때 인자로 넣어주면 된다.

[CODE] CachedBitmap* MarkTemplate::CreateCachedBitmap( Graphics* g, Color innerColor )
{
 Bitmap tmpBit( markTp_.GetWidth(), markTp_.GetHeight(), PixelFormat32bppARGB );
 Graphics* pMemGraphics = Graphics::FromImage(&tmpBit);

 ColorMap tplToinner;
 tplToinner.oldColor = tplColor_;
 tplToinner.newColor = innerColor;

 ImageAttributes imgAttr;
 imgAttr.SetRemapTable(1, &tplToinner,ColorAdjustTypeBitmap);
 imgAttr.SetColorKey(transColor_, transColor_,ColorAdjustTypeBitmap );
 pMemGraphics->DrawImage(&markTp_, Rect(0,0,tmpBit.GetWidth(),tmpBit.GetHeight()), 0.0,0.0,markTp_.GetWidth(), markTp_.GetHeight(), UnitPixel, &imgAttr, NULL, NULL);

 delete pMemGraphics;
 CachedBitmap* ccBit = new CachedBitmap(&tmpBit, g);

 return ccBit;
}
[/CODE]


코드는 대략 이런 느낌.
주의할 점은 Bitmap->CachedBitmap으로 바꾸면서 위의 내용을 적용할수가 없기때문에 Bitmap -> 변환된 Bitmap -> CachedBitmap 으로 간다. Bitmap의 변환에는 Graphics객체를 따로 생성해서 그려주는 수밖에 없는듯하다.

'알고리즘 > 이미지 처리' 카테고리의 다른 글

이미지 와핑 소스(그나마 낳은거)  (0) 2008.02.20
이미지 와핑에 관해서  (0) 2008.02.19
GDI+에서의 투명색 처리...  (0) 2008.01.25
이미지 회전 알고리즘  (0) 2008.01.18
Image Processing  (0) 2008.01.18
그림 띄우기  (0) 2008.01.07

+ Recent posts