10 Replies - 946 Views - Last Post: 02 November 2016 - 01:23 AM Rate Topic: -----

#1 JamesBowtell   User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 11
  • Joined: 01-November 16

VB.net WPF image issue

Posted 01 November 2016 - 06:03 AM

Hi All,

I'm struggling to load a resized image into a WPF image control. I have a function that takes an original JPG and resizes it.

When i try and load the resized JPG into the image control i get the following error:

An unhandled exception of type 'System.IO.FileFormatException' occurred in PresentationCore.dll

Additional information: The image cannot be decoded. The image header might be corrupted.


Can anyone see what i'm doing wrong?

Public Class Window2

    Private Sub Button_Click(sender As Object, e As RoutedEventArgs)

        Dim dlg As New Microsoft.Win32.OpenFileDialog()

        dlg.DefaultExt = ".jpg" 'Default extention 
        dlg.Filter = "Jpeg Images|*.jpg;*.jpeg" 'Filter images my extension

        'Show open file dialog box 
        Dim result As Boolean = dlg.ShowDialog()

        'Process open file dialog box results 
        If result = True Then

            Dim myJPGImage As New BitmapImage()

            'myJPGImage.BeginInit()
            'Open image
            Dim selectedImage As String

            selectedImage = dlg.FileName

            Dim resized As Image = CreateThumbnail(96, selectedImage)

            Dim memStream As MemoryStream = New MemoryStream()

            resized.Save(memStream, ImageFormat.Jpeg)

            Dim bitmap As New BitmapImage()

            bitmap.BeginInit()
            bitmap.StreamSource = memStream
            bitmap.CacheOption = BitmapCacheOption.onload
            bitmap.CreateOptions = BitmapCreateOptions.IgnoreColorProfile
            bitmap.DecodePixelWidth = 96
            bitmap.EndInit()
            bitmap.Freeze()

            picADFull.Source = bitmap

        End If
    End Sub




    Public Shared Function CreateThumbnail(ByVal ThumbnailMax As Integer, ByVal OriginalImagePath As String)

        ' Loads original image from file
        Dim imgOriginal As Image = Image.FromFile(OriginalImagePath)
        ' Finds height and width of original image
        Dim OriginalHeight As Single = imgOriginal.Height
        Dim OriginalWidth As Single = imgOriginal.Width
        ' Finds height and width of resized image
        Dim ThumbnailWidth As Integer
        Dim ThumbnailHeight As Integer
        If OriginalHeight > OriginalWidth Then
            ThumbnailHeight = ThumbnailMax
            ThumbnailWidth = (OriginalWidth / OriginalHeight) * ThumbnailMax
        Else
            ThumbnailWidth = ThumbnailMax
            ThumbnailHeight = (OriginalHeight / OriginalWidth) * ThumbnailMax
        End If
        ' Create new bitmap that will be used for thumbnail
        Dim ThumbnailBitmap As Bitmap = New Bitmap(ThumbnailWidth, ThumbnailHeight)
        Dim ResizedImage As Graphics = Graphics.FromImage(ThumbnailBitmap)
        ' Resized image will have best possible quality
        ResizedImage.InterpolationMode = InterpolationMode.HighQualityBicubic
        ResizedImage.CompositingQuality = CompositingQuality.HighQuality
        ResizedImage.SmoothingMode = SmoothingMode.HighQuality
        ' Draw resized image
        ResizedImage.DrawImage(imgOriginal, 0, 0, ThumbnailWidth, ThumbnailHeight)
        ' Save thumbnail to file

        Return ThumbnailBitmap

    End Function




Is This A Good Question/Topic? 0
  • +

Replies To: VB.net WPF image issue

#2 modi123_1   User is online

  • Suitor #2
  • member icon



Reputation: 15317
  • View blog
  • Posts: 61,418
  • Joined: 12-June 08

Re: VB.net WPF image issue

Posted 01 November 2016 - 07:04 AM

Look at your 'create thumbnail' function.. Lines 19-29.. do you actually write out the newly sized image to your return variable?
Was This Post Helpful? 0
  • +
  • -

#3 JamesBowtell   User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 11
  • Joined: 01-November 16

Re: VB.net WPF image issue

Posted 01 November 2016 - 07:28 AM

Hi modi123_1,

Thanks for replying...

isn't line 19 of the CreateThumbnail function doing this?

Dim ThumbnailBitmap As Bitmap = New Bitmap(ThumbnailWidth, ThumbnailHeight)  


Was This Post Helpful? 0
  • +
  • -

#4 modi123_1   User is online

  • Suitor #2
  • member icon



Reputation: 15317
  • View blog
  • Posts: 61,418
  • Joined: 12-June 08

Re: VB.net WPF image issue

Posted 01 November 2016 - 07:29 AM

Where is it filled with the data from the image you are trying to shrink?
Was This Post Helpful? 0
  • +
  • -

#5 JamesBowtell   User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 11
  • Joined: 01-November 16

Re: VB.net WPF image issue

Posted 01 November 2016 - 08:34 AM

The selected image is passed into the function Dim resized As Image = CreateThumbnail(96, original)

Private Sub Button_Click(sender As Object, e As RoutedEventArgs)

        Dim dlg As New Microsoft.Win32.OpenFileDialog()

        dlg.DefaultExt = ".jpg"
        dlg.Filter = "Jpeg Images|*.jpg;*.jpeg"

        Dim result As Boolean = dlg.ShowDialog()

        If result = True Then

            'selected Jpg is storeed
            Dim ADImage As New Bitmap(dlg.FileName)

            'Original var is polulated with selected image
            Dim original As Image = ADImage

            'Resized var is populated using createThumbnail function
            Dim resized As Image = CreateThumbnail(96, original)

            'Create new memory stream
            Dim memStream As MemoryStream = New MemoryStream()

            resized.Save(memStream, ImageFormat.Jpeg)

            Dim bitmap As New BitmapImage()

            bitmap.BeginInit()
            bitmap.StreamSource = memStream
            bitmap.CacheOption = BitmapCacheOption.onload
            bitmap.CreateOptions = BitmapCreateOptions.IgnoreColorProfile
            bitmap.DecodePixelWidth = 96
            bitmap.EndInit()
            bitmap.Freeze()

            picADFull.Source = bitmap

        End If
    End Sub



The function then sets all the dimaentions and creates the new image and populates ThumbnailBitmap var

        Dim newImage As Image = New Bitmap(newWidth, newHeight)
        Using graphicsHandle As Graphics = Graphics.FromImage(newImage)
            graphicsHandle.InterpolationMode = InterpolationMode.HighQualityBicubic
            graphicsHandle.DrawImage(image, 0, 0, newWidth, newHeight)
        End Using
        Return newImage 


I've changed my function code to make sure everything is coming through to the function as an image type code is still breaking with The image cannot be decoded. The image header might be corrupted.

        Public Shared Function CreateThumbnail(ByVal ThumbnailMax As Integer, ByVal OriginalImagePath As Image) As Image

        ' Finds height and width of original image
        Dim OriginalHeight As Single = OriginalImagePath.Height
        Dim OriginalWidth As Single = OriginalImagePath.Width

        ' Finds height and width of resized image
        Dim ThumbnailWidth As Integer
        Dim ThumbnailHeight As Integer

        If OriginalHeight > OriginalWidth Then
            ThumbnailHeight = ThumbnailMax
            ThumbnailWidth = (OriginalWidth / OriginalHeight) * ThumbnailMax
        Else
            ThumbnailWidth = ThumbnailMax
            ThumbnailHeight = (OriginalHeight / OriginalWidth) * ThumbnailMax
        End If

        ' Create new bitmap that will be used for thumbnail
        Dim ThumbnailBitmap As Image = New Bitmap(ThumbnailWidth, ThumbnailHeight)

        Using graphicsHandle As Graphics = Graphics.FromImage(ThumbnailBitmap)

            ' Resized image will have best possible quality
            graphicsHandle.InterpolationMode = InterpolationMode.HighQualityBicubic
            graphicsHandle.CompositingQuality = CompositingQuality.HighQuality
            graphicsHandle.SmoothingMode = SmoothingMode.HighQuality

            ' Draw resized image
            graphicsHandle.DrawImage(OriginalImagePath, 0, 0, ThumbnailWidth, ThumbnailHeight)

        End Using

        Return ThumbnailBitmap

    End Function

Was This Post Helpful? 0
  • +
  • -

#6 modi123_1   User is online

  • Suitor #2
  • member icon



Reputation: 15317
  • View blog
  • Posts: 61,418
  • Joined: 12-June 08

Re: VB.net WPF image issue

Posted 01 November 2016 - 08:59 AM

Odd.. well I ran it and it ran fine.

        Dim foo As New Bitmap("C:\test\icon_big.png")

        Dim bar As Bitmap

        Try
            bar = CreateThumbnail(50, foo)

            bar.Save("C:\test\icon_small.png")
        Catch ex As Exception
            Stop
        End Try


Was This Post Helpful? 0
  • +
  • -

#7 JamesBowtell   User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 11
  • Joined: 01-November 16

Re: VB.net WPF image issue

Posted 01 November 2016 - 09:11 AM

I'm using a memory stream and i think the error is originating from that ...stuck
Was This Post Helpful? 0
  • +
  • -

#8 IronRazer   User is offline

  • Custom Control Freak
  • member icon

Reputation: 1536
  • View blog
  • Posts: 3,864
  • Joined: 01-February 13

Re: VB.net WPF image issue

Posted 01 November 2016 - 09:55 AM

I am pretty sure that you need to save the Bitmap to the MemoryStream using the Png format. Try changing this line...
resized.Save(memStream, ImageFormat.Jpeg)


To this...
resized.Save(memStream, ImageFormat.Png)


As a side note, you are creating new instances of Bitmaps that should be Disposed when they are no longer in needed. You could combine the conversion code of the Bitmap to BitmapImage in the Function and Return a BitmapImage instead of a Bitmap. Something like below. This worked fine for me.
Imports System.Drawing
Imports System.Drawing.Drawing2D
Imports System.Drawing.Imaging
Imports System.IO
Imports Microsoft.Win32

Class MainWindow
    Private Sub button_Click(sender As Object, e As RoutedEventArgs) Handles button.Click
        Dim dlg As New OpenFileDialog
        dlg.DefaultExt = ".jpg" 'Default extention 
        dlg.Filter = "Jpeg Images|*.jpg;*.jpeg" 'Filter images my extension

        'Process open file dialog box results 
        If dlg.ShowDialog Then
            picADFull.Source = CreateThumbnail(96, dlg.FileName)
        End If
    End Sub

    Public Shared Function CreateThumbnail(ByVal ThumbnailMax As Integer, ByVal OriginalImagePath As String) As BitmapImage

        ' Loads original image from file
        Dim imgOriginal As Image = Image.FromFile(OriginalImagePath)
        ' Finds height and width of original image
        Dim OriginalHeight As Single = imgOriginal.Height
        Dim OriginalWidth As Single = imgOriginal.Width

        ' Finds height and width of resized image
        Dim ThumbnailWidth As Integer
        Dim ThumbnailHeight As Integer
        If OriginalHeight > OriginalWidth Then
            ThumbnailHeight = ThumbnailMax
            ThumbnailWidth = CInt((OriginalWidth / OriginalHeight) * ThumbnailMax)
        Else
            ThumbnailWidth = ThumbnailMax
            ThumbnailHeight = CInt((OriginalHeight / OriginalWidth) * ThumbnailMax)
        End If

        ' Create new bitmap that will be used for thumbnail
        Dim ThumbnailBitmap As Bitmap = New Bitmap(ThumbnailWidth, ThumbnailHeight)
        Dim ResizedImage As Graphics = Graphics.FromImage(ThumbnailBitmap)
        ' Resized image will have best possible quality
        ResizedImage.InterpolationMode = InterpolationMode.HighQualityBicubic
        ResizedImage.CompositingQuality = CompositingQuality.HighQuality
        ResizedImage.SmoothingMode = SmoothingMode.HighQuality
        ' Draw resized image onto the Bitmap
        ResizedImage.DrawImage(imgOriginal, 0, 0, ThumbnailWidth, ThumbnailHeight)

        Dim bmpimg As New BitmapImage 'don`t use bitmap as a name for the Bitmap as it can cause confusion
        Using memStream As New MemoryStream 'use a (Using / End Using) statement to be sure the new MemoryStream is Disposed when it is done being used.
            ThumbnailBitmap.Save(memStream, ImageFormat.Png)
            bmpimg.BeginInit()
            bmpimg.StreamSource = memStream
            bmpimg.DecodePixelWidth = 96
            bmpimg.CacheOption = BitmapCacheOption.onload
            bmpimg.EndInit()
        End Using
        ThumbnailBitmap.Dispose() 'Dispose this Bitmap when done using it

        Return bmpimg
    End Function
End Class



With that said, it seems like you could do the image resizing by using just methods that are available in WPF so that the whole conversion part is not needed. I am not much on WPF but, i am sure it could be done.
Was This Post Helpful? 0
  • +
  • -

#9 JamesBowtell   User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 11
  • Joined: 01-November 16

Re: VB.net WPF image issue

Posted 01 November 2016 - 10:01 AM

i've managed to resolve this issue by adding the below

memStream.Flush()
memStream.Position = 0


please see completed code below:

Private Sub Button_Click(sender As Object, e As RoutedEventArgs)

        Dim dlg As New Microsoft.Win32.OpenFileDialog()

        dlg.DefaultExt = ".jpg"
        dlg.Filter = "Jpeg Images|*.jpg;*.jpeg"

        Dim result As Boolean = dlg.ShowDialog()

        If result = True Then

            'selected Jpg is storeed
            Dim ADImage As New Bitmap(dlg.FileName)

            'Original var is polulated with selected image
            Dim original As Image = ADImage

            'Resized var is populated using createThumbnail function
            Dim resized As Image = CreateThumbnail(96, original)

            'Create new memory stream
            Dim memStream As MemoryStream = New MemoryStream()

            resized.Save(memStream, ImageFormat.Jpeg)

            Dim bitmap As New BitmapImage()

            memStream.Flush()
            memStream.Position = 0
            bitmap.BeginInit()
            bitmap.StreamSource = memStream
            bitmap.CacheOption = BitmapCacheOption.onload
            'bitmap.CreateOptions = BitmapCreateOptions.IgnoreColorProfile
            'bitmap.DecodePixelWidth = 96
            bitmap.EndInit()
            bitmap.Freeze()

            picADFull.Source = bitmap

        End If
    End Sub


Public Shared Function CreateThumbnail(ByVal ThumbnailMax As Integer, ByVal OriginalImagePath As Image) As Image

        ' Loads original image from file
        'Dim imgOriginal As Image = Image.FromFile(OriginalImagePath)

        ' Finds height and width of original image
        Dim OriginalHeight As Single = OriginalImagePath.Height
        Dim OriginalWidth As Single = OriginalImagePath.Width

        ' Finds height and width of resized image
        Dim ThumbnailWidth As Integer
        Dim ThumbnailHeight As Integer

        If OriginalHeight > OriginalWidth Then
            ThumbnailHeight = ThumbnailMax
            ThumbnailWidth = (OriginalWidth / OriginalHeight) * ThumbnailMax
        Else
            ThumbnailWidth = ThumbnailMax
            ThumbnailHeight = (OriginalHeight / OriginalWidth) * ThumbnailMax
        End If

        ' Create new bitmap that will be used for thumbnail
        Dim ThumbnailBitmap As Image = New Bitmap(ThumbnailWidth, ThumbnailHeight)

        Using graphicsHandle As Graphics = Graphics.FromImage(ThumbnailBitmap)

            ' Resized image will have best possible quality
            graphicsHandle.InterpolationMode = InterpolationMode.HighQualityBicubic
            graphicsHandle.CompositingQuality = CompositingQuality.HighQuality
            graphicsHandle.SmoothingMode = SmoothingMode.HighQuality

            ' Draw resized image
            graphicsHandle.DrawImage(OriginalImagePath, 0, 0, ThumbnailWidth, ThumbnailHeight)

        End Using

        Return ThumbnailBitmap

    End Function

Was This Post Helpful? 0
  • +
  • -

#10 IronRazer   User is offline

  • Custom Control Freak
  • member icon

Reputation: 1536
  • View blog
  • Posts: 3,864
  • Joined: 01-February 13

Re: VB.net WPF image issue

Posted 01 November 2016 - 10:33 AM

After saying you could probably do it in WPF without using the Bitmap class i decided to try it myself. The below example does what you want i believe. It is much shorter but, as i said, i am not a WPF guy so there might be a better way that i am not aware of.
Imports Microsoft.Win32

Class MainWindow
    Private Sub button_Click(sender As Object, e As RoutedEventArgs) Handles button.Click
        Dim dlg As New OpenFileDialog
        dlg.DefaultExt = ".jpg" 'Default extention 
        dlg.Filter = "Jpeg Images|*.jpg;*.jpeg" 'Filter images my extension

        'Process open file dialog box results 
        If dlg.ShowDialog Then
            picADFull.Source = CreateThumbnail(96, dlg.FileName)
        End If
    End Sub

    Public Shared Function CreateThumbnail(ByVal ThumbnailMax As Integer, ByVal OriginalImagePath As String) As BitmapImage
        Dim bmpimg As New BitmapImage
        bmpimg.BeginInit()
        bmpimg.UriSource = New Uri(OriginalImagePath)
        bmpimg.EndInit()

        Dim bmpimg2 As New BitmapImage
        bmpimg2.BeginInit()
        bmpimg2.UriSource = New Uri(OriginalImagePath)
        If bmpimg.Width > bmpimg.Height Then
            bmpimg2.DecodePixelWidth = ThumbnailMax
        Else
            bmpimg2.DecodePixelHeight = ThumbnailMax
        End If
        bmpimg2.EndInit()

        Return bmpimg2
    End Function
End Class


Was This Post Helpful? 0
  • +
  • -

#11 JamesBowtell   User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 11
  • Joined: 01-November 16

Re: VB.net WPF image issue

Posted 02 November 2016 - 01:23 AM

The function looks a lot better. I still had to add the graphics handlers as the native resized image quality is not that great.
Was This Post Helpful? 0
  • +
  • -

Page 1 of 1