I’ve made a few posts in the past regarding image manipulations (resize, rotate, …) but never covered the most basic aspect, which is simply getting general information about an image. Below is a sample which utilizes WIA automation.
Private Type ImgageInfo
Height As Long
Width As Long
FileExtension As String
HorizontalResolution As Double
VerticalResolution As Double
PixelDepth As Long
End Type
Public Img As ImgageInfo
'---------------------------------------------------------------------------------------
' Procedure : WIA_GetImgDimensions
' Author : Daniel Pineault, CARDA Consultants Inc.
' Website : http://www.cardaconsultants.com
' Purpose : Retrieve various properties (dimensions, extension, resolution) of an image
' Copyright : The following is release as Attribution-ShareAlike 4.0 International
' (CC BY-SA 4.0) - https://creativecommons.org/licenses/by-sa/4.0/
' Req'd Refs: Uses Late Binding, so none required
'
' Input Variables:
' ~~~~~~~~~~~~~~~~
' sFile : Fully qualified path, filename and extension of the image file to check
'
' Usage:
' ~~~~~~
' Call WIA_GetImgDimensions(C:\Tmp\database.png )
' Debug.Print sFile, "Width: " & Img.Width, "Height: " & Img.Height, "FileExtension: " & _
' Img.FileExtension, "HorizontalResolution: " & Img.HorizontalResolution, _
' "VerticalResolution: " & Img.VerticalResolution, _
' "PixelDepth: " & Img.PixelDepth
'
' Revision History:
' Rev Date(yyyy/mm/dd) Description
' **************************************************************************************
' 1 2018-10-23 Initial Release
'---------------------------------------------------------------------------------------
Function WIA_GetImgDimensions(ByVal sFile As String) As Boolean
'For a complete listing of available WIA ImageFile properties
' Ref: https://docs.microsoft.com/en-us/previous-versions/windows/desktop/wiaaut/-wiaaut-imagefile
On Error GoTo Error_Handler
Dim oWIA As Object
Set oWIA = CreateObject("WIA.ImageFile")
oWIA.LoadFile sFile
Img.Width = oWIA.Width
Img.Height = oWIA.Height
Img.FileExtension = oWIA.FileExtension
Img.HorizontalResolution = oWIA.HorizontalResolution
Img.VerticalResolution = oWIA.VerticalResolution
Img.PixelDepth = oWIA.PixelDepth
Error_Handler_Exit:
On Error Resume Next
If Not oWIA Is Nothing Then Set oWIA = Nothing
Exit Function
Error_Handler:
MsgBox "The following error has occurred" & vbCrLf & vbCrLf & _
"Error Number: " & Err.Number & vbCrLf & _
"Error Source: WIA_GetImgDimensions" & vbCrLf & _
"Error Description: " & Err.Description & _
Switch(Erl = 0, "", Erl <> 0, vbCrLf & "Line No: " & Erl) _
, vbOKOnly + vbCritical, "An Error has Occurred!"
Resume Error_Handler_Exit
End Function
Private Sub Testme()
Dim sFile As String
sFile = "C:\Tmp\1.png"
Call WIA_GetImgDimensions(sFile)
Debug.Print sFile, "Width: " & Img.Width, "Height: " & Img.Height, _
"FileExtension: " & Img.FileExtension, _
"HorizontalResolution: " & Img.HorizontalResolution, _
"VerticalResolution: " & Img.VerticalResolution, _
"PixelDepth: " & Img.PixelDepth
sFile = "C:\Tmp\2.jpg"
Call WIA_GetImgDimensions(sFile)
Debug.Print sFile, "Width: " & Img.Width, "Height: " & Img.Height, _
"FileExtension: " & Img.FileExtension, _
"HorizontalResolution: " & Img.HorizontalResolution, _
"VerticalResolution: " & Img.VerticalResolution, _
"PixelDepth: " & Img.PixelDepth
sFile = "C:\Tmp\3.gif"
Call WIA_GetImgDimensions(sFile)
Debug.Print sFile, "Width: " & Img.Width, "Height: " & Img.Height, _
"FileExtension: " & Img.FileExtension, _
"HorizontalResolution: " & Img.HorizontalResolution, _
"VerticalResolution: " & Img.VerticalResolution, _
"PixelDepth: " & Img.PixelDepth
End Sub
Similarly, we can get the dimension using the Shell object
Private Type ImgageInfo
Height As Long
Width As Long
FileExtension As String
HorizontalResolution As Double
VerticalResolution As Double
PixelDepth As Long
End Type
Public Img As ImgageInfo
'---------------------------------------------------------------------------------------
' Procedure : Shell_GetImgDimensions
' Author : Daniel Pineault, CARDA Consultants Inc.
' Website : http://www.cardaconsultants.com
' Purpose : Retrieve the dimensions, extension of an image
' Copyright : The following is release as Attribution-ShareAlike 4.0 International
' (CC BY-SA 4.0) - https://creativecommons.org/licenses/by-sa/4.0/
' Req'd Refs: Uses Late Binding, so none required
'
' Input Variables:
' ~~~~~~~~~~~~~~~~
' sFile : Fully qualified path, filename and extension of the image file to check
'
' Usage:
' ~~~~~~
' Call Shell_GetImgDimensions(C:\Tmp\database.png )
' Debug.Print sFile, "Width: " & Img.Width, "Height: " & Img.Height
'
' Revision History:
' Rev Date(yyyy/mm/dd) Description
' **************************************************************************************
' 1 2018-10-23 Initial Release
' 2 2018-11-04 Made Option Explicit Compliant
'---------------------------------------------------------------------------------------
Function Shell_GetImgDimensions(ByVal sFile As String) As Boolean
On Error GoTo Error_Handler
Dim oShell As Object 'Shell
Dim oFolder As Object 'Folder2
Dim oFile As Object 'FolderItem
Dim sPath As String
Dim sFilename As String
Dim sDims As String
sPath = Left(sFile, InStrRev(sFile, "\") - 1)
sFilename = Right(sFile, Len(sFile) - InStrRev(sFile, "\"))
Set oShell = CreateObject("Shell.Application")
Set oFolder = oShell.NameSpace(CStr(sPath))
Set oFile = oFolder.ParseName(sFilename)
sDims = oFile.ExtendedProperty("Dimensions") '-> ?470 x 668?
sDims = Right(sDims, Len(sDims) - 1)
sDims = Left(sDims, Len(sDims) - 1)
Img.Width = CLng(Split(sDims, "x")(0))
Img.Height = CLng(Split(sDims, "x")(1))
Error_Handler_Exit:
On Error Resume Next
If Not oFile Is Nothing Then Set oFile = Nothing
If Not oFolder Is Nothing Then Set oFolder = Nothing
If Not oShell Is Nothing Then Set oShell = Nothing
Exit Function
Error_Handler:
MsgBox "The following error has occurred" & vbCrLf & vbCrLf & _
"Error Number: " & Err.Number & vbCrLf & _
"Error Source: Shell_GetImgDimensions" & vbCrLf & _
"Error Description: " & Err.Description & _
Switch(Erl = 0, "", Erl <> 0, vbCrLf & "Line No: " & Erl) _
, vbOKOnly + vbCritical, "An Error has Occurred!"
Resume Error_Handler_Exit
End Function
Private Sub Testme()
Dim sFile As String
sFile = "C:\Tmp\1.png"
Call Shell_GetImgDimensions(sFile)
Debug.Print sFile, "Width: " & Img.Width, "Height: " & Img.Height
sFile = "C:\Tmp\2.jpg"
Call Shell_GetImgDimensions(sFile)
Debug.Print sFile, "Width: " & Img.Width, "Height: " & Img.Height
sFile = "C:\Tmp\3.gif"
Call Shell_GetImgDimensions(sFile)
Debug.Print sFile, "Width: " & Img.Width, "Height: " & Img.Height
End Sub
In my case I commented out the lines to remove extraneous characters.
sDims = oFile.ExtendedProperty(“Dimensions”) ‘-> ?470 x 668?
‘Debug.Print sDims
”’ sDims = Right(sDims, Len(sDims))
”’ sDims = Left(sDims, Len(sDims))
Img.Width = CLng(Split(sDims, “x”)(0))
Img.Height = CLng(Split(sDims, “x”)(1))
because my operating system wasn’t including any. If I left them in, they results returned trunacated a digit from each dimension
the line
Switch(Erl = 0, “”, Erl 0, vbCrLf & “Line No: ” & Erl)
gives an error, because Switch is not defined.
These are basic commands. I’d start by checking my VBA references to see that they are all ok, that none are MISSING.
I’m finding this does not work when trying to get the dimensions of a webp file. When trying to load the ImageFile object with the specified file, I get the error:
The parameter is incorrect.
I am using Excel 2002.
That doesn’t surprise me as webp is a newer format (around 2018) from Google and WIA is an older technology (came out with Windows XP – around 2001). I could be wrong, but I believe WIA is limited to working with BMP, GIF, JPEG, PNG and TIFF files.
I’d look at alternative approaches, perhaps try:
It all depends on how Google created the format and what they’ve made accessible. I’ve never worked with webp, so I can’t help too much beyond suggesting trying different things.
For me, and all other interested readers, to put the effort into learning three ways that may, or may not, produce the results I’m looking for, isn’t very efficient. You have all of those implemented on your machine. A webp file can readily be found on the web to test. It is becoming the standard for major websites.
I’m not sure I follow 100%. I demonstrates a multitude of ways to approach things so people have options. You then weigh the PROs and CONs and select the right one to fill your needs. Normally, you wouldn’t have 3 libraries to perform the same task, you’d select and implement the one that works for you. At the same time, code is very small in the grand scheme of thing, so if adding 3 text modules to a project enable someone to do everything the wish to, then they can! There truly isn’t a downside to it.
As for webp, I’ve never seen it before on any website. I’ll do some testing in the coming days as it is always a good idea to be aware of new things, learn a new thing. So thank you for sharing. It will be interesting to compare file sizes, quality, rendering…
What I am trying to access is the Color Representation info like RGB, CMY, HSI ie you can see this in windows explorer right clicking on a photo file and the properties then the details tab. In the image section you have Color representation. I would like to get VBA access to this.
There are different ways to access this information, take a look at:
Thank you for your prompt reply. I have used your first example. I can’t find the description for Color representation. Looking at file explorer file properties there is reference to Color representation and yet it not in the list you generated. Things like Photoshop show this value as well. I am a bit lost as how to proceed. I wish I could save a screen shot here to show you.
I know you can get it with the FreeImage approach, probably also the GDI+ one as well. You’re after the ColorSpace property (40961) I believe.
Daniel, I am interested in using the GetImageProperties, but when i try to compile it in Excel editor i am getting the following error:
Sub or Function not defined: Getting this error on line “GetPropertyValue = Eval(GetPropertyValue)”
Type mismatch: Getting this error on line “GDIStatus = GdipCreateBitmapFromFile(StrPtr(sFile), lBitmap)”
i am using Win 11 Pro, Excel 22019. Any help is greatly appricated.
It’s because Excel doesn’t have an Eval() function. You can either edit the function and change
GetPropertyValue = Eval(GetPropertyValue)To
GetPropertyValue = Evaluate(GetPropertyValue)Or, so as to not mess with the function, add a custom Eval() function to your module like:
Public Function Eval(sInput As String)Eval = Evaluate(sInput)
End Function
Thank you Daniel for the quick reply, i am still getting the type mismatch error on line “GDIStatus = GdipCreateBitmapFromFile(StrPtr(sFile), lBitmap)”
Are you running 64-bit Excel?
yes
Yes, 64-bit Excel
Well, then that’s the problem. The code here is 32-bit. You’d need to convert it to 64-bit by updating all the APIs and calls. Not something I’ve done, because I don’t use, nor do any of my customer use 64-bit office.
I wish I could be more helpful, but it’s simply not something I can get into right now.
If you want post it to a forum and see if people there can’t assist you with the conversion.