Link to home
Start Free TrialLog in
Avatar of jdhackett
jdhackettFlag for Ireland

asked on

Looping though image controls to load photo

Hi
I have a table which contains the file path to some photos.
On my form I have some PictureBox controls, and I can loads the photos as follows:
Private Sub Load_Photo(ByVal rowPhotos As SubmissionPhotosRow)

      picSource1.Load(rowPhotos.SubPhoto1)
      picSource2.Load(rowPhotos.SubPhoto2)
      picSource3.Load(rowPhotos.SubPhoto3)

   End Sub

Open in new window


There can be 6 photos though, and it is not required that all 6 photos be completed.
I'm trying to change the code to loop through the PictureBox controls and load a picture if there is a file specified.

 Private Sub Load_Photo(ByVal rowPhotos As SubmissionPhotosRow)

      Dim iLoop As Integer = 0
      Dim picImage As New PictureBox

      For iLoop = 1 To 6
         If Not IsDBNull(rowPhotos("SubPhoto" & iLoop)) Then
            picImage = Me.Controls.Item("picSource" & iLoop)
            picImage.Load(rowPhotos("SubPhoto" & iLoop))
         End If
      Next

   End Sub

Open in new window


However, I get "Object reference not set to an instance of an object." on the picImage.Load line
I can't seem to figure it out.
How would I solve this?
Thanks
Avatar of Paweł
Paweł
Flag of Switzerland image

 Private Sub Load_Photo(ByVal rowPhotos As SubmissionPhotosRow)

      Dim iLoop As Integer = 0
'here you're instantiating a new picturebox
      Dim picImage As New PictureBox

      For iLoop = 1 To 6
         If Not IsDBNull(rowPhotos("SubPhoto" & iLoop)) Then

'here you're setting the picture box to be a control with the id picSource#
'bet you that you don't have them all declared on your form.
            picImage = Me.Controls.Item("picSource" & iLoop)
            picImage.Load(rowPhotos("SubPhoto" & iLoop))
         End If
      Next

   End Sub

Open in new window


so to fix this make sure you have picturebox1 through picturebox6 on your form, or instantiate your picture box in your for loop and add it to your me.contorls

something like the following

 Private Sub Load_Photo(ByVal rowPhotos As SubmissionPhotosRow)

      Dim iLoop As Integer = 0

      

      For iLoop = 1 To 6
         If Not IsDBNull(rowPhotos("SubPhoto" & iLoop)) Then


           Dim picImage As New PictureBox
            picImage.Load(rowPhotos("SubPhoto" & iLoop))
            Me.Controls.add(picImage)
         End If
      Next

   End Sub

Open in new window


it's been years since i've touched VB, but that's the basic idea.
SOLUTION
Avatar of AndyAinscow
AndyAinscow
Flag of Switzerland image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Avatar of jdhackett

ASKER

Hi Andy
Its the picImage that is giving the problem. I added another step
stPhoto = rowPhotos("SubPhoto" & iLoop)
and that worked fine.
Have you checked as Pawel suggested in the earlier comment?
Hi Pawel
I changed my code to your suggestion. While it now doesn't break, it doesn't display the picture either.

 If Not IsDBNull(rowPhotos("SubPhoto" & iLoop)) Then
            Dim picImage As New PictureBox

            picImage.Load(rowPhotos("SubPhoto" & iLoop))
            Me.Controls.Add(picImage)

         End If

Open in new window


It does seem that the problem was with the
    picImage = Me.Controls.Item("picSource" & iLoop)
line.
Maybe there is a different way to point picImage at picSource?
it depends on what SubmissionPhotosRow is

if it's a collection of images then
https://msdn.microsoft.com/en-us/library/system.windows.forms.picturebox.image(v=vs.110).aspx

if it's a path, then you should stick to load
https://msdn.microsoft.com/en-us/library/f6ak7was(v=vs.110).aspx
Its a path, so I'm using picImage.Load
you're using a forms application?
try something like this
   Dim img = New PictureBox()
        img.Load("C:\Dev\WindowsApplication1\WindowsApplication1\assets\profile-placeholder.png")

'set the size
        img.SizeMode = PictureBoxSizeMode.AutoSize

        Me.Controls.Add(img)

Open in new window


if you don't set the image size, then you might not notice the images getting added
ASKER CERTIFIED SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Hi
Thanks everyone for their replies.
This is the code that worked for me, which I wrote before reading it_saiges excellent post above.
The previous problem was I had was actually due to the PictureBox being on a tab page, so I have to use Me.tabSource.Controls

  Private Sub Load_Photo(ByVal rowPhotos As SubmissionPhotosRow)
      ' Row has fields SubPhoto1 to 6, which is the path to the photo
      ' Also show the Size of the photo in Kb

      Dim iLoop As Integer = 0
      Dim picImage As New PictureBox
      Dim stPhoto As String = ""
      Dim infoReader As System.IO.FileInfo

      For iLoop = 1 To 6
         If Not IsDBNull(rowPhotos("SubPhoto" & iLoop)) Then

            stPhoto = rowPhotos("SubPhoto" & iLoop)

            picImage = CType(Me.tabSource.Controls("picSource" & iLoop), PictureBox)
            picImage.Load(stPhoto)

            infoReader = My.Computer.FileSystem.GetFileInfo(stPhoto)
            tabSource.Controls("txtSize" & iLoop).Text = Math.Round(infoReader.Length / 1024, 0)

         End If
      Next

   End Sub

Open in new window


Reading the above solutions, I see that I should of course add error checking. And better checking for nulls.
In my case, I had 6 PictureBox controls, I had not thought about FlowControl panels.
Are there advantages to using the FlowControl panels?
The one advantage that sticks out in my head is that you no longer have to worry about the number of images you need to display; e.g. - We need to support the display of 9 images.

Rather than having to recompile the program to add the controls and their management to the form, you just add the properties to the class or better yet, if you decided to implement the list of strings, you just add the paths to your datasource.

The FlowLayoutPanel will also lend itself to resizing easier than using just a set of Picturebox controls.

-saige-
Thanks, you've been a great help.

One last thing - what do you mean by *No points* above?
It's a way of signifying that I do not expect any points from that submission because I feel that Andy and Pawel had already answered your original question, i simply provided enhancement based guidance.

If you disagree you can still chose to assign points to my answer, but I would not overlook the submissions provided by Andy and Pawel.

-saige-
Thanks, that's what I thought, but I wanted to make sure.
I feel you should get some points though as your answer was very helpful.