Click to See Complete Forum and Search --> : Simple questions about TreeViews


GameZelda
March 4th, 2008, 02:01 PM
I'm just making my first TreeView and I have some pretty simple questions:

1- I'm using a image list with two images: a folder and a file. Folders work fine, but when I select a file, his image changes to the image of the folder (that has the first index in the image list).

Is that a normal behavior?

I can solve it easily using TVIF_SELECTEDIMAGE in the item mask, and setting iSelectedImage to the same value that iImage, but I just want to be sure that it's not my error.

2 - There's any function to find strings (I need to avoid repeated folders)?
3 - There's any way to make the image to change when the node is expanded, or I must manage that manually?

sublime99
March 4th, 2008, 04:00 PM
you need to set iImage and iSelectedImage to the images you wish to use.

So for the folder:
iImage=folderImageUnselected
iSelectedImage=folderImageSelected

or if you do not care to differentiate between selected unselected

iImage=folderImage
iSelectedImage=folderImage

and for the file
iImage=fileImageUnselected
iSelectedImage=fileImageSelected

or if you do not care to differentiate between selected unselected

iImage=fileImage
iSelectedImage=fileImage



You need to test for the type of image to set when you call




//=============================================================================
bool SetTreeviewImagelist(const HWND hTv)
{
//set up and attach image lists to tree view common control
HIMAGELIST hImages=ImageList_Create(GetSystemMetrics(SM_CXSMICON),
GetSystemMetrics(SM_CYSMICON),
ILC_COLOR32|ILC_MASK,2,1);
if (hImages==0)
{
ErrMsg(_T("Failed to create image list."));
return false;
}
//get an instance handle for a source of icon images - for convenience use a
//known system dll
HINSTANCE hLib=LoadLibrary(_T("shell32.dll"));

if (!hLib)
{
ErrMsg(_T("Failed to load image resource library."));
return false;
}


//Because the icons are loaded from system resources ie they are shared,
//it is not necessary to free the image resources with 'DestroyIcon'.
HICON hIcon=reinterpret_cast<HICON>(LoadImage(hLib,
MAKEINTRESOURCE(4),
IMAGE_ICON,
0,0,
LR_SHARED));
ImageList_AddIcon(hImages,hIcon);


hIcon=reinterpret_cast<HICON>(LoadImage(hLib,
MAKEINTRESOURCE(5),
IMAGE_ICON,
0,0,
LR_SHARED));
ImageList_AddIcon(hImages,hIcon);

hIcon=reinterpret_cast<HICON>(LoadImage(hLib,
//MAKEINTRESOURCE(226),
MAKEINTRESOURCE(183),
IMAGE_ICON,
0,0,
LR_SHARED));
ImageList_AddIcon(hImages,hIcon);


//attach image lists to tree view common control
TreeView_SetImageList(hTv,hImages,TVSIL_NORMAL);

return true;
}



//=============================================================================
HTREEITEM InsertTreeviewItem(const HWND hTv,const ustring& txt, HTREEITEM htiParent)
{
TVITEM tvi={0};

tvi.mask=TVIF_TEXT|TVIF_IMAGE|TVIF_SELECTEDIMAGE;


//copy the text into a temporary array (vector) so it's in a suitable form
//for the pszText member of the TVITEM struct to use. This avoids using
//const_cast on 'txt.c_str()' or variations applied directly to the string that
//break its constant nature.
std::vector<TCHAR> tmp(txt.begin(),txt.end());
tmp.push_back(_T('\0'));

tvi.pszText=&tmp[0];
tvi.cchTextMax=static_cast<int>(txt.length()); //length of item label
tvi.iImage=0; //non-selected image index

TVINSERTSTRUCT tvis={0};
tvi.iSelectedImage=1; //selected image index

if((unsigned int)htiParent != 0xffff0000){ //TVI_ROOT
tvi.iImage=2; //non-selected image index
tvi.iSelectedImage=2; //selected image index
}


tvis.item=tvi;
tvis.hInsertAfter=0;
tvis.hParent=htiParent; //parent item of item to be inserted

return reinterpret_cast<HTREEITEM>(SendMessage(hTv,TVM_INSERTITEM,0,
reinterpret_cast<LPARAM>(&tvis)));
}



//=============================================================================
HTREEITEM InsertTreeviewItem(const HWND hTv,const ustring& txt, HTREEITEM htiParent)
{
TVITEM tvi={0};

tvi.mask=TVIF_TEXT|TVIF_IMAGE|TVIF_SELECTEDIMAGE;


//copy the text into a temporary array (vector) so it's in a suitable form
//for the pszText member of the TVITEM struct to use. This avoids using
//const_cast on 'txt.c_str()' or variations applied directly to the string that
//break its constant nature.
std::vector<TCHAR> tmp(txt.begin(),txt.end());
tmp.push_back(_T('\0'));

tvi.pszText=&tmp[0];
tvi.cchTextMax=static_cast<int>(txt.length()); //length of item label
tvi.iImage=0; //non-selected image index

TVINSERTSTRUCT tvis={0};
tvi.iSelectedImage=1; //selected image index

if((unsigned int)htiParent != 0xffff0000){ //TVI_ROOT
tvi.iImage=2; //non-selected image index
tvi.iSelectedImage=2; //selected image index
}


tvis.item=tvi;
tvis.hInsertAfter=0;
tvis.hParent=htiParent; //parent item of item to be inserted

return reinterpret_cast<HTREEITEM>(SendMessage(hTv,TVM_INSERTITEM,0,
reinterpret_cast<LPARAM>(&tvis)));
}