2011-09-16 29 views
4

DLL文件包含PNG资源类型中的一些图像。从.NET的本机Win32资源获取PNG图像

我可以使用Resource Hacker,Anolis Resourcer & Resource Tuner等软件查看PNG图像。检查安乐Resourcer的这个截图了解详情:

http://i51.tinypic.com/9pt93c.jpg

谁能告诉我如何获取PNG图像没有。 5220从DLL文件,并将其放入一个PictureBox?我不认为像LoadImage或LoadBitmap API会工作。

+0

它是一个嵌入式的资源或者是一个资源文件? – casperOne

回答

6
// get the assembly containing the image 
var assembly = Assembly.GetExecutingAssembly(); 

// set the picturebox image to read the embedded resource 
pictureBox1.Image = Image.FromStream(
    assembly.GetManifestResourceStream("AssemblyName.test.png") 
); 

其中AssemblyName.test.png是程序集内嵌入资源的完全限定名称。


UPDATE:

看来你正试图从一个本地装配提取资源。你可以看看following article,它说明了如何使用P/Invoke完成这个工作。

+0

@AnonMouse,那是什么? –

+0

@AnnonMouse,这是一个托管程序集或原生? –

+0

@AnonMouse,好的,我已经更新了我的答案,并附上了一篇文章链接,说明如何实现这一目标。 –

3

PNG图像不是标准的Win32资源类型之一。它通常嵌入为指定资源类型“PNG”的二进制blob,尽管这不是保证。到目前为止,最简单的方法是使用Visual Studio的File + Open + File命令打开文件。找到资源后,右键单击它并选择导出将其保存到磁盘。

以编程方式进行此操作需要大量的砂砾针。这很棘手,因为资源类型和资源ID都可以是字符串或IntPtr,因此您需要为FindResource重新创建4个重载。为了便于使用LoadLibraryEx()来加载文件而不执行任何代码。 FindResource获取资源的句柄。 SizeOfResource知道它有多大。 LoadResource + LockResource获取指向资源数据的指针。 Marshal.Copy()将资源数据复制到一个字节[]中。使用FreeResource和FreeLibrary进行清理。

4

Darin发布的链接(因此被标记为答案)不包含功能代码。我评估了发布在那里的代码(http://khason.net/blog/how-to-load-unmanaged-native-resources-from-managed-c-code/),发现它无法正常工作嵌入在任何win32 dll中的位图图像作为位图资源。

此外,汉斯帕斯坦离开了无数的步骤有效地使他的职位无用。

我已经能够找到的唯一稍微接近的解决方案来自于2004年为XP主题dll垃圾编写的文章。你可以在这里找到ThemeManager.cs http://www.codeproject.com/KB/miscctrl/XPTaskBar.aspx

然而,“GetResourcePNG”的方法,但应注意的是,我已经有很多困难的用这种方法,因为调用bitmap.RotateFlip(RotateFlipType.Rotate180FlipX) ;

我发现这里列出的代码(http://www.vbaccelerator.com/home/NET/:我的系统

更新上authui.dll内试图访问PNG图像时会导致内存问题Code/Controls/Explorer_Bar/ExplorerBar_Control_Source_Code.asp)功能最强大,产生最少的错误并产生最快的结果。该代码是用C#编写的,即使域名会另外指出。使用这两个类; ImageUtility和ResourceLibrary,您可以轻松地拉出来PNG标准的,non-.net资源库/ DLL:

public static Bitmap GetStandardResourceBitmap(String dllName, String resourceId) { 
     Bitmap result = null; 

     using (ResourceLibrary library = new ResourceLibrary() { Filename = dllName }) { 
      IntPtr hDib = library.GetResource(resourceId, ResourceLibrary.ImageType.IMAGE_BITMAP, ResourceLibrary.ImageLoadOptions.LR_CREATEDIBSECTION); 
      if (!hDib.Equals(IntPtr.Zero)) { 
       result = ImageUtility.DibToBitmap(hDib); 
       ImageUtility.DeleteObject(hDib); 
      } 
     } 

     return result; 
    } 

我选择了有RESOURCEID在我的方法的字符串,不仅是因为它不需要过载和使用编号的资源ID就像添加一个'#'一样简单。

GetStandardResourceBitmap("shell32.dll", "#632"); 

干杯

+0

我没有错过任何东西 - 你没有读完整个线程。他发布的代码不适用于win32 dll内的资源,也不是代码链接到标准win32 dll资源的功能 - 这正是作者的目标。如果你阅读整篇文章,你会发现这一点。对于标准dll中的非PNG位图资源,Bitmap.FromResource是要使用的方法。但是,未列在“PNG”资源类型中的PNG存在其他问题,如我链接的代码中概述的那样。 – shellscape