ListCtrl


==========================================


1. 특정 ROW 포커스 주기
2. 특정 ROW로 가기
3. 헤더 컬럼수 얻어오기
4. 컬럼의 너비를 이쁘게 주기
5. 한줄 쭉 선택되게 하기, 그리드 라인 주기
6. 선택한 아이템(ROW)를 지우기
7. 두 아이템을 스왑 하기
8. 기존에 선택되어있는 것을 해체하기


9. List Control의 0번째 컬럼 사이즈 변경하지 못 하도록 프로그래밍


10. List Control 에 다른 Control 넣기


11. List Control 행크기 늘리기


12. List Control 에서 시스템 아이콘 사용하기


 


1. 특정 ROW 포커스 주기
—————————————————
리스트 컨트롤에서 어떤 특정 Row를 선택하게 하고 싶을때
( 이때 선택뿐아니라 포커스도 가야 한다.
포커스가 간다는 의미는 다음에 키다운을 하면 바로 부드럽게
다음 아이템을 가리키도록 하는 것이다 )


ListView_SetItemState (pListCtrl->GetSafeHwnd(), // handle to listview
10, // index to listview item
LVIS_FOCUSED | LVIS_SELECTED, // item state
0x000F); //mask


위와 같이 코딩하면 된다.



2. 특정 ROW로 가기
—————————————————
만일 원하는 Row를 스크롤을 하던 어떻게 하든 화면에 보이게
하고 싶을때


pListCtrl->EnsureVisible(15, TRUE);


이렇게 하면 된다.



3. 헤더 컬럼수 얻어오기
—————————————————
헤더 컬럼의 갯수를 알고 싶을때
CHeaderCtrl* pHeader = (CHeaderCtrl*)GetDlgItem(0);
int nColumnCount = pHeader->GetItemCount();


또는 pList->GetHeaderCtrl()을 통해서 얻어올수 도 있다.



4. 컬럼의 너비를 이쁘게 주기
—————————————————
공백없이 잘 채워 준다.


부모 다이얼로그의 OnSize에서
void CAttrListDlg::OnSize(UINT nType, int cx, int cy)
{
CDialog::OnSize(nType, cx, cy);


// TODO: Add your message handler code here
if( IsWindow( z_AttrList.m_hWnd ))
{
z_AttrList.MoveWindow( 0, 0, cx, cy );
z_AttrList.SetColumnWidth(1 , LVSCW_AUTOSIZE_USEHEADER);
}
}



5. 한줄 쭉 선택되게 하기, 그리드 라인 주기
—————————————————
z_AttrList.SetExtendedStyle(LVS_EX_GRIDLINES | LVS_EX_FULLROWSELECT);



6. 선택한 아이템(ROW)를 지우기
—————————————————


CDWordArray m_anDragIndexes; // 선택한 아이템을 기억하는
배열


int CAttrList::fnRemoveItem()
{


m_anDragIndexes.RemoveAll();
POSITION pos = GetFirstSelectedItemPosition();
while (pos)
{
m_anDragIndexes.Add(GetNextSelectedItem(pos));
}


int nSize = m_anDragIndexes.GetSize();
int nRet = -1;
if( nSize )
nRet = m_anDragIndexes[0];


while( nSize– )
DeleteItem( m_anDragIndexes[nSize] );


m_anDragIndexes.RemoveAll();
return nRet;
}



7. 두 아이템을 스왑 하기
—————————————————
void CAttrList::fnSwapItem( int nItem1, int nItem2 )
{
int hi = nItem2;
int lo = nItem1;
CStringArray rowText;


LV_ITEM lvitemlo, lvitemhi;
CHeaderCtrl* pHeaderCtrl = GetHeaderCtrl();
int nColCount =pHeaderCtrl->GetItemCount();


rowText.SetSize( nColCount );
int i;
for( i=0; i<nColCount; i++)
rowText[i] = GetItemText(lo, i);
lvitemlo.mask = LVIF_IMAGE | LVIF_PARAM | LVIF_STATE;
lvitemlo.iItem = lo;
lvitemlo.iSubItem = 0;
lvitemlo.stateMask = LVIS_CUT | LVIS_DROPHILITED |
LVIS_FOCUSED | LVIS_SELECTED |
LVIS_OVERLAYMASK | LVIS_STATEIMAGEMASK;


lvitemhi = lvitemlo;
lvitemhi.iItem = hi;


GetItem( &lvitemlo );
GetItem( &lvitemhi );


for( i=0; i<nColCount; i++)
SetItemText(lo, i, GetItemText(hi, i));


lvitemhi.iItem = lo;
SetItem( &lvitemhi );


for( i=0; i<nColCount; i++)
SetItemText(hi, i, rowText[i]);


lvitemlo.iItem = hi;
SetItem( &lvitemlo );
}


 


8.기존에 선택되어있는 것을 해체하기
———————————–
int nOldItem = GetSelectionMark();
if( nOldItem > 0 )
SetItemState( nOldItem , 0, LVIS_SELECTED);



void SetCurSel(int nIndex, BOOL bIsTrue)
{
 SetItemState(nIndex, bIsTrue ? LVIS_SELECTED | LVIS_FOCUSED : 0, LVIS_SELECTED | LVIS_FOCUSED);
}


9. List Control의 0번째 컬럼 사이즈 변경하지 못 하도록 프로그래밍


———————————————————————-
BOOL OnNotify(WPARAM wParam, LPARAM lParam, LRESULT* pResult)
{


/* 


    //사이즈가 80 이하 안되게 만든다.


    HD_NOTIFY   *pHDN = (HD_NOTIFY*)lParam;


 


    if((pHDN->hdr.code == HDN_ITEMCHANGINGW || pHDN->hdr.code == HDN_ITEMCHANGINGA)


        && pHDN->pitem->cxy < 80)


    {


        *pResult = TRUE;                // disable change


        return TRUE;                    // Processed message


    }*/


 


 


/*  // 컬럼 사이즈 변경 못하게 만든다.


    // 모든 칼럼.


    switch (((NMHDR*)lParam)->code)


    {


        case HDN_BEGINTRACKW:


        case HDN_BEGINTRACKA:


            *pResult = TRUE;                // disable tracking


            return TRUE;                    // Processed message


        default: break;


    }


 


    // 특정 칼럼.


    HD_NOTIFY   *pHDN = (HD_NOTIFY*)lParam;


 


    if((pHDN->hdr.code == HDN_BEGINTRACKW || pHDN->hdr.code == HDN_BEGINTRACKA)


            && pHDN->iItem == 0)            // Prevent only first (col# 0) from resizing


    {


        *pResult = TRUE;                // disable tracking


        return TRUE;                    // Processed message


    }*/


 


    return CListCtrl::OnNotify(wParam, lParam, pResult);


}



 


10. List Control 에 다른 Control 넣기


 ———————————————————————-
1. 요약
 특정 Column에서 다른 Control 을 띄우는 방법 설명. 여기서 사용한 방법은 현재 Cursor가 있는 위치를 파악한후 그 위치에 적당한 크기의 Edit Control를 생성 시킨다.

2. 본문
1) CListCtrl를 상속받는 CMyList라는 Class를 만든다.
2) Member변수로 CEdit m_ctrEdit를 선언한다.
3) Member함수로 OnLButtonDown()과 GetSubItemFrompt(point, nItem, nSubItem, rcClient)를 선언 OnLButtonDown() : Edit Control를 생성/삭제 시키는 역할 GetSubItemFrompt(): 현재 Cursor가 있는 곳의 List정보를 가져온다.
4) 함수 내용을 구성한 후(예제 참조) 사용은 CListCtrl m_ctrList에서 CListCtrl —> CMyList로 바꿔 주면 된다. 3.예제
실제로 클래스를 구성하면 다음과 같다.

class CMyList : public COXGridList

{

// Construction

public:

CMyList();



// Attributes

public:

CEdit m_ctrEdit;



// Operations

public:

void GetSubItemFrompt(Cpoint point, int &nItem,int&nSubItem,CRect&rect);



//Overrides

//ClassWizardgeneratedvirtualfunctionoverrides

//{{AFX_VIRTUAL(CMyList)

//}}AFX_VIRTUAL



//Implementation

public:

virtual~CMyList();



//Generatedmessagemapfunctions

protected:

//{{AFX_MSG(CMyList)

afx_msg
voidOnLButtonDown(UINTnFlags,Cpointpoint);

//}}AFX_MSG



DECLARE_MESSAGE_MAp()

};





CMyList::CMyList()

{

}



CMyList::~CMyList()

{

}





BEGIN_MESSAGE_MAp(CMyList,COXGridList)

//{{AFX_MSG_MAp(CMyList)

ON_WM_LBUTTONDOWN()

//}}AFX_MSG_MAp

END_MESSAGE_MAp()

/////////////////////////////////////////////////////////////////////////////

//CMyListmessagehandlers

voidCMyList::OnLButtonDown(UINTnFlags,Cpointpoint)

{

intnItem,nSubItem;

CRectrcClient;



//현재 point의 영역 정보를 가져온다.

GetSubItemFrompt(point, nItem, nSubItem, rcClient);



// 두번째 SubItem일(두번째 Column) 경우에만 나타나게 함.

if (nSubItem == 1)

{

if (m_ctrTimeEdit.m_hWnd == NULL)

{

// Mask Edit Control 생성

m_ctrEdit.Create

(WS_CHILD|WS_VISIBLE|WS_TABSTOp|WS_BORDER|WS_HSCROLL,

CRect(
0, 0, 30, 10), this, 1);



m_ctrEdit.MoveWindow(rcClient);

m_ctrEdit.ShowWindow(SW_SHOW);



}

else

{

m_ctrTimeEdit.MoveWindow(rcClient);

m_ctrTimeEdit.ShowWindow(SW_SHOW);

}

}

else

{

if (m_ctrTimeEdit.m_hWnd != NULL)

{

m_ctrTimeEdit.ShowWindow(SW_HIDE);

}

}



CListCtrl::OnLButtonDown(nFlags, point);

}

void CMyList::GetSubItemFrompt(Cpoint point, int &nItem, int &nSubItem, CRect &rect)

{

LVHITTESTINFO lvhti;



// Clear the subitem text the user clicked on.

lvhti.pt = point;

SubItemHitTest(&lvhti);



nItem = lvhti.iItem;

nSubItem = lvhti.iSubItem;

GetSubItemRect(nItem, nSubItem, LVIR_LABEL, rect);

}

4. 참고 마우스를 더블 클릭하는 순간에 나타나게 하고 싶다면 마우스 더블 클릭 함수에서 구현해 주면 된다. 몇가지 함수만 추가하면 특정 Column에서만 Control이 나타나게 하는 것을 쉽게 구현 할 수 있을 것이다. – 2001.08.06 Smile Seo –




11. List Control 행크기 늘리기


 ———————————————————————-
리스트 콘트롤의 행간 높이를 조절하고자 할때,
원래 윈도우가 날려주는 메세지가 있지만, CListCtrlView 를 이용하는경우 도움이 전혀 안됩니다.
이경우 마지막 방법은 이미지 리스트를 이용하는 것입니다.


CImageList m_image;


….
CListCtrl &m_list=GetListCtrl();
    m_image.Create(1,20,ILC_COLORDDB,1,0);
    list.SetImageList(&m_image,LVSIL_SMALL);
…….


을 써서 Y 크기를 조절해서 크기를 바꿀 수 있습니다.


12. List Control 에서 시스템 아이콘 사용하기


 ———————————————————————-
CImageList m_ImgList;


HIMAGELIST  hSystemSmallImageList;
SHFILEINFO  ssfi;


hSystemSmallImageList =
(HIMAGELIST)SHGetFileInfo((LPCTSTR)_T(“C:\\”), 0, &ssfi, sizeof(SHFILEINFO),
        SHGFI_SYSICONINDEX | SHGFI_SMALLICON);


m_ImgList.Attach(hSystemSmallImageList);
m_listDir.SetImageList(&m_ImgList, LVSIL_SMALL);


// 이부분을 넣지 않으면 여러번 리스트컨트롤이 나타날때 이미지가 사라진다.
HWND hList = m_listDir.GetSafeHwnd();
DWORD dwCurrentStyle=GetWindowLong(hList, GWL_STYLE);
dwCurrentStyle |= LVS_SHAREIMAGELISTS;
SetWindowLong(hList, GWL_STYLE, dwCurrentStyle);



// 나중에 InsertItem으로 아이템 추가시 이미지 번호에 아래 함수를 호출하여 얻은 리턴값을 사용한다.
int CSystemListCtrl::GetIconIndex(const CString& csFileName)  //full path and file name
{              
 SHFILEINFO    sfi;
 
 SHGetFileInfo(
   (LPCTSTR)csFileName,
   0,
   &sfi,
   sizeof(SHFILEINFO),
   SHGFI_SYSICONINDEX | SHGFI_SMALLICON );
 
 return sfi.iIcon;
}


답글 남기기

이메일 주소는 공개되지 않습니다.