C++Builder Programming Forum
C++Builder  |  Delphi  |  FireMonkey  |  C/C++  |  Free Pascal  |  Firebird
볼랜드포럼 BorlandForum
 경고! 게시물 작성자의 사전 허락없는 메일주소 추출행위 절대 금지
C++빌더 포럼
Q & A
FAQ
팁&트릭
강좌/문서
자료실
컴포넌트/라이브러리
메신저 프로젝트
볼랜드포럼 홈
헤드라인 뉴스
IT 뉴스
공지사항
자유게시판
해피 브레이크
공동 프로젝트
구인/구직
회원 장터
건의사항
운영진 게시판
회원 메뉴
북마크
볼랜드포럼 광고 모집

C++빌더 Q&A
C++Builder Programming Q&A
[43727] Re:string grid 의 checkbox 가운데 정렬과 이벤트 함수 선언 방법
박지훈.임프 [cbuilder] 3302 읽음    2006-02-17 02:24
그리드에 체크박스 넣기...라는 것은 꽤 여러번 답변을 하는데... 의외로, 질문하시는 거의 모든 분들이 TCheckBox를
집어넣으려고 시도하시는군요. 물론 그렇게 할 수도 있긴 하지만, 오히려 일이 더 번거롭게 되고 버그 가능성도 더 높습니다.

가만히 조금만 생각해보시면, TCheckBox를 생성해서 넣는 것보단 그냥 해당 셀에다가 체크박스 형태의 그림만 그려주는
것이 훨씬 쉽고 문제의 가능성도 적다는 것을 아실 수 있을 겁니다. 체크박스는 무슨 복잡한 입력을 받는 것도 아니고,
단지 현재 상태에 따라 체크가 있는 그림이거나 체크가 없는 그림 두가지중의 하나만 그려주면 끝이니까요. 게다가 입력을
받는 경우도, 클릭 혹은 더블클릭(체크박스 토글을 클릭이나 더블클릭 둘중의 어떤 쪽으로 할지는 직접 정하시면 되죠)
핸들러를 만들고 거기서 데이터값을 바꿔주면 되죠.

체크박스를 그리려한다고 해서 일일이 다 그릴 필요도 없고, Win32 API 함수 하나면 땡입니다.
DrawFrameControl(HDC hdc, LPRECT lprc, UINT uType, UINT uState);

이 함수의 세번째 인자로 DFC_BUTTON를 넘기고 동시에 마지막 인자로 DFCS_BUTTONCHECK이라는 값을 넘겨주면
체크가 안된 체크박스 모양이 그려집니다. 함께 DFCS_CHECKED를 넘겨주면 체크표시가 된 체크박스가 그려지고요.
짐작하시겠지만 첫번째 인자로는 DC를 넘기면 되는데, 스트링그리드의 Canvas->Handle을 넘기면 되구요.
두번째 인자는 TRect 값을 넘겨주면 되므로 체크가 그려질 영역을 넘기면 됩니다.

만약 OnDrawCell 핸들러에서 넘어오는 Rect 값을 그대로 넘겨줘버리면 셀 전체를 꽉채우는 거대한(?) 체크가 그러지겠죠.
그러니까 Rect 크기를 일반적으로 우리가 흔히 보는 체크박스 크기로 줄여줘야 하는데, 그것은 현재 윈도우에 정의되어
있으므로 그걸 읽어오면 됩니다. 현재 윈도우 시스템의 기본 체크박스 크기는 GetSystemMetrics(SM_CXMENUCHECK)
으로 너비를, GetSystemMetrics(SM_CYMENUCHECK)으로 높이를 알 수 있습니다.

따라서, OnDrawCell의 인자인 Rect를 줄여서 위에서 얻은 체크 크기로 줄여주면 됩니다.
아래와 같이 될 겁니다.

TPoint PtCheckSize;
TRect RtCheck;
PtCheckSize = Point(GetSystemMetrics(SM_CXMENUCHECK), GetSystemMetrics(SM_CYMENUCHECK));
RtCheck.Left   = Rect.Left + ((Rect.Right-Rect.Left)-PtCheckSize.X) / 2;
RtCheck.Top    = Rect.Top + ((Rect.Bottom-Rect.Top)-PtCheckSize.Y) / 2;
RtCheck.Right  = RtCheck.Left + PtCheckSize.X;
RtCheck.Bottom = RtCheck.Top + PtCheckSize.Y;

그리고 OnClick 혹은 OnDblClick에서 값을 토글하는 건 어렵지 않으니까 혼자 해보실 수 있으실 거구요.

이 정도의 코드는 컴포넌트 자료실에 올려놓은 ImpStringGrid에 거의 그대로 구현되어 있으니까 파스칼 코드를 보실 수
있으시다면 소스를 참고하시면 되겠고요. C++빌더용으로 설치할 수도 있으니까 TStringGrid 대신에 쓰셔도 되겠습니다.
http://cbuilder.borlandforum.com/impboard/impboard.dll?action=read&db=component&no=439

그럼...


김도훈 님이 쓰신 글 :
: void __fastcall TfrParaSet::sgCalDrawCell(TObject *Sender, int ACol,
:       int ARow, TRect &Rect, TGridDrawState State)
: {
:         if(ARow != 0)
:         {
:                 if(ARow %2 == 0)
:                 {
:                         sgCal->Canvas->Brush->Color = 0xcaffca;
:                         sgCal->Canvas->TextRect(Rect,Rect.Left+2,Rect.Top+2,sgCal->Cells[ACol][ARow]);
:                 }
:
:                 if(ACol==0)
:                 {
:                  // 체크 박스 그리기
:                 }
:        }
: }
:
: 이렇게 해서 그리드에 색을 넣고 체크 박스를 가운데 정렬을 하고 싶은데 어떻게 해야 하는지 알려 주시면 감사 하겠습니다,
:
: TCheckBox* t = new TCheckBox(frParaSet);
:         frParaSet->sgCal->Objects[0][0] = t;
:         t->Parent = frParaSet->sgCal;
:         t->BoundsRect = frParaSet->sgCal->CellRect(0,1);
:         t->Width = 15;
:         t->Height = 15;
:         t->OnMouseUp = CheckBoxMouseUp;   <====요기
:
:
: 체크 박스는 예제를 보고 저렇게 만들었는데 1 col에 체크 박스를 다 넣고 싶은데 다른 방법이 있나요? row 의 개수는   15개 입니다.
:
: 그리고 표시한 저부분이 이벤트 함수를 만드는 부분 같은데 어떻게 선언 해야 하는 지를 알려 주시면 감사하겠습니다.
: 링크된 문서도 상관 없구요....헤더 파일과 함수 구현 부분에 대해 자세히 부탁 드리겠습니다....

+ -

관련 글 리스트
43725 string grid 의 checkbox 가운데 정렬과 이벤트 함수 선언 방법 김도훈 1510 2006/02/16
43727     Re:string grid 의 checkbox 가운데 정렬과 이벤트 함수 선언 방법 박지훈.임프 3302 2006/02/17
Google
Copyright © 1999-2015, borlandforum.com. All right reserved.