• 0

[C#] Getting a file's large icon


Question

Hello,

I'm trying to get file icons using SHGetFileInfo (See attched image), but when I try to get the large icon of the file using SHGFI_LARGEICON, it returnes the 32x32 icon :( while I want to get the 48x48 icon.

I've figured out that if I set Windows to show large icons, I can use SHGFI_SHELLICONSIZE, but it doesn't work when Windows is set to show small icons :blink:

How can I always get the large 48x48 icon of a file? What do I need to use?

Thanks in advance for your help :)

post-62656-1115302870_thumb.jpg

Link to comment
https://www.neowin.net/forum/topic/316840-c-getting-a-files-large-icon/
Share on other sites

14 answers to this question

Recommended Posts

  • 0

Thanks for your answer :) However, I have no idea how to use SHDefExtractIcon with C#. Maybe you can tell me how?

I just want to get the large icon of any real file on the computer. I just want it to work like the Windows toolbar - it shows the icons of the files in a certain directory.

Any idea how I can use SHDefExtractIcon ?

  • 0

Setting the icons sizes just for this seems quite weird to me :blink: I don't think it's the way to do it but thanks for the creative idea :)

I have the same problem with IExtractIcon::Extract - I have no idea how to use it :( Can anybody show me an example? How do I use it in an application?

BTW, thanks for your suggestions :)

  • 0

Here's how I do it:

HRESULT CPidl::GetParentShellFolder(IShellFolder** folder,LPCITEMIDLIST*

relativePidl, IShellFolder2** folder2)const
{
	ATLASSERT(m_Pidl != NULL);
	ATLASSERT(folder != NULL);

	HRESULT _hRes;

	if(folder == NULL)
	{
 ?_hRes = E_INVALIDARG;
	}
	else if(NULL == m_Pidl)
	{
 ?_hRes = E_FAIL;
	}
	else
	{
 ?*folder = NULL;

 ?LPCITEMIDLIST pidlChild = {0};

 ?HRESULT _hRes = ?SHBindToParent(m_Pidl,
 ? ? ? ? ? ? ? ? ? ? ? ? ? ?IID_IShellFolder, 
 ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?(void**) folder, 
 ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?const_cast<LPCITEMIDLIST*>(&pidlChild));

 ?if(relativePidl != NULL)
 ?{
 ?	*relativePidl = pidlChild;
 ?}

 ?if(folder2 != NULL)
 ?{
 ?	*folder2 = NULL;

 ?	if(SUCCEEDED(_hRes) && *folder != NULL)
 ? ?(*folder)->QueryInterface(IID_IShellFolder2,reinterpret_cast<void**>(folder2));
 ?}
	}

	return _hRes;
}


HICON CPidl::ExtractIcon(UINT size, UINT flags) const
{
	ATLASSERT(m_Pidl != NULL);

	if(NULL == m_Pidl)
 ?return NULL;

	CComPtr<IShellFolder> parentFolder;
	LPCITEMIDLIST relativePidl = NULL;

	HRESULT _hRes = GetParentShellFolder(&parentFolder,&relativePidl);

	if( FAILED(_hRes) )
 ?return NULL;

	CComPtr<IExtractIcon> extractIcon;
	_hRes = parentFolder->GetUIObjectOf(NULL,1,
const_cast<LPCITEMIDLIST*>(&relativePidl),
IID_IExtractIcon,NULL,reinterpret_cast<void**>(&extractIcon) );

	if( FAILED(_hRes) || NULL == extractIcon.p)
 ?return NULL;

	TCHAR location[MAX_PATH+2] = {0};
 // +2 fixes bogus shellextension off-by-one errors.
	int ? index(0);
	UINT outFlags(GIL_FORSHELL);

	_hRes = extractIcon->GetIconLocation(GIL_FORSHELL,
location,MAX_PATH,
&index,&outFlags);

	if( FAILED(_hRes) )
 ?return NULL;

	HICON smallIcon = {0};
	HICON largeIcon = {0};

	size = MAKELONG (size,size);

	_hRes = extractIcon->Extract(location,index,&largeIcon,&smallIcon,size);

	if( FAILED(_hRes) )
 ?return NULL;

	if(largeIcon != NULL)
	{
 ?DestroyIcon(smallIcon);
 ?return largeIcon;
	}
	else
	{
 ?return smallIcon;
	}

}

  • 0

1) Get a PIDL to the file you want the icon of.

2) Get the IShellFolder parent of it and the relative PIDL.

3) Query that IShellFolder for an IExtractIcon (GetUIObjectOf) for the relative PIDL you have obtained in step2.

4) get the location of the object with IExtractIcon::GetIconLocation

5) Use that location to extract the icon with IExtractIcon::Extract(...) and give up the size as a long with the high word and low word of the long set as the size ( MAKELONG(size, size) ).

This topic is now closed to further replies.
  • Recently Browsing   0 members

    • No registered users viewing this page.
  • Posts

    • Yes while it's still a great browser it seems bloated more with each update by things I'm not the least interested in
    • We now know why Nvidia blocked yet another review, the new RTX 5050 is apparently terrible by Sayan Sen With its latest RTX 5000 series of GPUs, Nvidia has not been transparent with how its cards perform. The company did not ship review drivers for the RTX 5060 on launch day and has repeated the same deed with the new RTX 5050 as well. For those who may not have followed, Nvidia unveiled the GeForce RTX 5050 last month for $249 and released the Game Ready driver for the card this month with version 576.88. As such, the RTX 5050 has now been tested by Korean site Quasar Zone where the GPU has been compared against other cards that are priced around that same bracket. The site has found that Nvidia's new entry-level offering is worse than Intel's Arc B580, a card that launched around six months ago for the same price. As you can see in the image above, the Arc B580 was slightly faster on average. The biggest gap between the two was on Path of Exile 2. Another point in favor of the Arc GPU is that it has 12 Gigs of video memory whereas the RTX 5050 only has 8 GB. The 5050 was also pitted against Nvidia's last gen RTX 4060 as well as AMD's RX 7600, both of which are also 8 Gig cards. The 7600 is often found at around $250 these days while the RTX 4060 frequents around $275. The RTX 5050 is essentially neck and neck with the 4060 and is ever so slightly faster than the RX 7600. Once again this just highlights that Nvidia is essentially giving the same kind of performance that Intel and AMD GPUs have provided since last year or so. In fact, if we consider the Radeon RX 6600 and 6650 XT GPUs, which have been available for around $180 to $220 in the past, it becomes clearer just how bad of a value the RTX 5050 is as those 6000 series AMD cards probably get pretty close to the 5050 in rasterization throughput. Chances of something like "Fine Wine" are also slim given that the RTX 5050 just does not seem to have the hardware resources to pull off something like that later in this lifespan. If anything, we are more likely to see that happen from the Intel B580 GPU or AMD's $299 RX 9060 (there is already evidence of that). Source and images: Quasar Zone
    • A messaging network full of adult content. Ewww. 🤮
    • Why does Vivaldi feels slow to me than any other Chromium browsers? 😭 Anyone here like me?
  • Recent Achievements

    • First Post
      loose_observer earned a badge
      First Post
    • Week One Done
      BeeJay_Balu earned a badge
      Week One Done
    • Week One Done
      filminutz earned a badge
      Week One Done
    • Reacting Well
      SteveJaye earned a badge
      Reacting Well
    • One Month Later
      MadMung0 earned a badge
      One Month Later
  • Popular Contributors

    1. 1
      +primortal
      446
    2. 2
      ATLien_0
      161
    3. 3
      +FloatingFatMan
      146
    4. 4
      Nick H.
      65
    5. 5
      +thexfile
      62
  • Tell a friend

    Love Neowin? Tell a friend!