mfc-imageProcessing 다양한 이미지 작업을 알아보자
2018, May 28
이전까지 칼라이미지와 흑백이미지를 함께 출력하는 작업을 했다.
다양한 이미지 작업을 해보자. 작업 목록은 아래와 같다.
픽셀 단위 작업
- 밝기 조절
- 콘트라스트 조절
- 흑백이미지를 바이너리화
영역 단위 작업
- 이진 이미지 침식
- 이진 이미지 팽창
이 포스트에서는 밝기 조절과 콘트라스트 조절 작업에 대해 알아볼 것이다.
밝기조절
ImageProc.h, ImageProc.cpp 에 다음과 같은 밝기 조절 함수를 추가한다.
ImageProc.h
class ImageProc{
...
public:
static void AdjustBright(unsigned char* image,
const int width, const int height, const int bright );
}
ImageProc.cpp
void ImageProc::AdjustBright(unsigned char* image,
const int width, const int height, const int bright )
{
// 255 보다 크면 255 0보다 작으면 0을 저장한다.
for(int i=0; i<width*height; i++)
{
image[i*4 + 0] = static_cast<char>(min(255,(max(0,(image[i*4 + 0] + bright)))));
image[i*4 + 1] = static_cast<char>(min(255,(max(0,(image[i*4 + 1] + bright)))));
image[i*4 + 2] = static_cast<char>(min(255,(max(0,(image[i*4 + 2] + bright)))));
}
}
이제 이벤트를 처리하는 함수를 정의한다.
ImageProcessingDoc.h
class CImageProcessingDoc::public CDocument
{
...
public :
afx_msg void OnPixelProcessingAdjustbright();
}
ImageProcessingDoc.cpp
...
void OnPixelProcessingAdjustbright()
{
ImageProc::AdjustBright(m_Images[cur_index].image_color,
m_Images[cur_index].width, m_Images[cur_index].height, 34);
// 흑백 이미지 밝기도 조절 한다.
ImageProc::MergeChannels(m_Images[cur_index].image_color,
m_Images[cur_index].image_gray, m_Images[cur_index].width, m_Images[cur_index].height);
// View 포인터를 얻어오고 이미지를 세팅한다.
CImageProcessingView* pView = (CImageProcessingView*)((CMainFrame*)(AfxGetApp()->m_pMainWnd))->GetActiveView();
pView->SetDrawImage(m_Images[cur_index].image_color, m_Images[cur_index].image_gray,
m_Images[cur_index].width, m_Images[cur_index].height);
// 화면을 업데이트 한다.
pView->OnInitialUpdate();
}
...
이를 실행하면 위의 이미지가
이와 같이 밝아진다.
콘트라스트(contrast) 조절
콘트라스트 기능 구현만 밝기 조절과 다르고 다른 부분은 같다.
ImageProc.h, ImageProc.cpp 에 다음과 같은 contrast 조절 함수를 추가한다.
ImageProc.h
class ImageProc{
...
public:
static void AdjustContrast(unsigned char* image,
const int width, const int height, const int contrast );
}
ImageProc.cpp
void ImageProc::AdjustContrast(unsigned char* image,
const int width, const int height, const int contrast )
{
// 255 보다 크면 255 0보다 작으면 0을 저장한다.
// 밝기와 다른 유일한 부분은 (* contrast) 이다.
for(int i=0; i<width*height; i++)
{
image[i*4 + 0] = static_cast<char>(min(255,(max(0,(image[i*4 + 0] * contrast)))));
image[i*4 + 1] = static_cast<char>(min(255,(max(0,(image[i*4 + 1] * contrast)))));
image[i*4 + 2] = static_cast<char>(min(255,(max(0,(image[i*4 + 2] * contrast)))));
}
}
이제 contrast 조절 이벤트를 추가한다.
ImageProcessingDoc.h
class CImageProcessingDoc::public CDocument
{
...
public :
afx_msg void OnPixelProcessingAdjustcontrast();
}
ImageProcessingDoc.cpp
...
void OnPixelProcessingAdjustcontrast()
{
ImageProc::AdjustContrast(m_Images[cur_index].image_color,
m_Images[cur_index].width, m_Images[cur_index].height, 3);
// 작업완료된 이미지로 흑백 이미지를 만든다
ImageProc::MergeChannels(m_Images[cur_index].image_color,
m_Images[cur_index].image_gray, m_Images[cur_index].width, m_Images[cur_index].height);
// View 포인터를 얻어오고 이미지를 세팅한다.
CImageProcessingView* pView = (CImageProcessingView*)((CMainFrame*)(AfxGetApp()->m_pMainWnd))->GetActiveView();
pView->SetDrawImage(m_Images[cur_index].image_color, m_Images[cur_index].image_gray,
m_Images[cur_index].width, m_Images[cur_index].height);
// 화면을 업데이트 한다.
pView->OnInitialUpdate();
}
...
실행하면 다음과 그림과 같이 보인다.