Visual Studio: PictureBox not showing the full image - vb.net

During the use of the application the user stores away a picture to be used for comparison later.
When the image is retrieved from the database it does not render fully in the picture box as seen below. The correct image has been retrieved but only the top is visible.
I have tried multiple different picture box settings and image types but the result is always the same. I have also reproduced the error in another project with the same code.
The code I use is below:
Dim b() As Byte
b = DirectCast(cmd.ExecuteScalar, Byte())
If b Is Not Nothing Then
stream = New System.IO.MemoryStream
stream.Write(b, 0, b.Length)
Dim image As Image = image.FromStream(stream)
pictureBox.Image = image
End if
I cannot figure this out. Has anyone seen something like this before?
Thanks!

Where you define stream? If you read the Image.FromStream method documentation it say:
You must keep the stream open for the lifetime of the Image.
The stream is reset to zero if this method is called successively with
the same stream.

Related

vb.net- How to make any picture in a picture box round in shape

I am making an application in vb.net that has a good user interface, including the your account icon that includes a picture box. My question is that how can i make that image in the picture box round in shape?
Like This:
https://drive.google.com/open?id=1rUBq68ULDkTiFFv2uEiV_oQIh3wQIfhd
I wouldn't normally provide code for a question that doesn't show an attempt but there are a few steps in the answer and it was easier to just write the code myself than explain them. E.g.
'Get the original image.
Dim originalImage = PictureBox1.Image
'Create a new, blank image with the same dimensions.
Dim croppedImage As New Bitmap(originalImage.Width, originalImage.Height)
'Prepare to draw on the new image.
Using g = Graphics.FromImage(croppedImage)
Dim path As New GraphicsPath
'Create an ellipse that fills the image in both directions.
path.AddEllipse(0, 0, croppedImage.Width, croppedImage.Height)
Dim reg As New Region(path)
'Draw only within the specified ellipse.
g.Clip = reg
g.DrawImage(originalImage, Point.Empty)
End Using
'Display the new image.
PictureBox2.Image = croppedImage
That will create an elliptical image with the same width and height as the original. If the original is square then the final will be circular. If you want a circle regardless of the aspect ratio of the original then you'll have to manipulate that in the appropriate manner.
Though i see that you already found out the solution to your question, however here's a very simple workaround.
Assuming, your project is in WinForms, and you are using Picture Box control. The easiest way to achieve the round-image-look is to set the Image property of the PictureBox to an image that is round-shaped and is blank/transparent in the middle and white on the outside. Then , whatever image you set as a BackgroundImage , it will appear round-ish.
Here's a sample round-transparent image for you which you can set as Image(make sure to set SizeMode to stretch) and then set any picture as BackgroundImage.

Using a VB.NET variable between different forms

I am trying to use the VB.NET program settings to load a background image for every form every time the form is loaded. So far I've managed to get the program to set the background in one form, and that changes the background for every other form. However, when each form is closed and re-opened while the program is running, the background changes back to the default one. I need to somehow change the background once and load it every time the form is opened, so that it doesn't switch back every time the form is re-opened while the program is running. I think there is some way to do this using the My.Settings in VB.NET, but I'm not sure.
This is the code that changes the background for each form:
Me.BackgroundImage = PreviewBackgroundBox.Image
MainForm.BackgroundImage = PreviewBackgroundBox.Image
LogInForm.BackgroundImage = PreviewBackgroundBox.Image
The PreviewBackgroundBox is used to show the user the image before they apply it, and then when they click apply then the image is taken from the PreviewBackgroundBox and set as the background for all the forms.
Could someone help me with this?
Thanks!
Basically you need a dictionary remembering the image is to be displayed for each form. You could store such a dictionary in a module together with methods to handle the logic involved
Private imageDict As New Dictionary(Of String, Image)
Public Sub SetImage(ByVal formName As String, ByVal img As Image)
imageDict(formName) = img
End Sub
Public Function GetImage(ByVal formName As String) As Image
Dim img As Image
If imageDict.TryGetValue(formName, img) Then
Return img
End If
Return Nothing 'Or return a default image
End Function
Note: Dictionaries store some data and associate it with a key that is used to retrieve this data. Here I would use the form's name as Key. You could also use the form's type GetType(Form1) or Me.GetType() and use a Dictionary(Of Type, Image) instead.
Whenever the user selects another image call SetImage in order to remember it. When a form is opened call GetImage to get the remembered image.

VB.Net If statement to check if a specific image from my resources is loaded

I want to use an If statment to check if a specific image from my resources is loaded.
I want to change the image when it is clicked as in:
If PictureBox1.Image = My.Resources.BIKE13 Then
PictureBox1.Image = My.Resources.BIKE13_Helmet
End If
I'm going to use several ElseIf Statements
After some search I found several ways to do it but I have about 20-30 images and I'm and I need a simple method.
(VS 2010)
That code cannot possibly work for two reasons. Firstly, an Image is a reference type object, so to compare like that you would have to use the Is operator rather than =. Secondly, My.Resources creates a new object each time, so even using Is will never give you a match.
What you need to do is use the My.Resources property once and once only and assign the Image object to a member variable. You can then use Is with that field.
E.g.
Private bike13Image As Image = My.Resources.BIKE13
Private bike13HelmetImage As Image = My.Resources.BIKE13_Helmet
and
If PictureBox1.Image Is bike13Image Then
PictureBox1.Image = bike13HelmetImage
End If

ImageTools only creates PNG successfully under certain conditions

I'm trying to generate images using ImageTools, and my code works and successfully creates images...but only if I have user input before trying to create the images!
If I try to generate the images in the New sub, for example, the images are created, but they only contain the textbox control from my canvas and not the image (my control consists of text + image). So the image is being created...but it's only rendering partial content.
If I put a button on my page and generate my images from the button click even handler the images are generated correctly.
So what am I doing wrong here? And how can I get my images to generate without user input (i.e. when the app launches).
I get the exact same results using WriteableBitmap in place of ImageTools, FWIW.
I create stackpanels with a canvas and my text/image elements, then use the standard code to render the images to files in isolated storage. Since it all works perfectly after user input I don't know which parts of the code to provide...I'm basically using unmodified sample code.
Code parts (this is all in my MainPage.XAML.VB):
Public Sub New()
InitializeComponent()
' some code commented out while debugging - not relevant here
SetupHubTiles() ' this is the method that sets up the images (see below)
End Sub
The SetupHubTiles method makes several calls to the following method:
Public Sub CreateHubTile(background As StackPanel, tileImage As String, tiletoupdate As HubTile)
Dim isoStoreTileImage = String.Format("isostore:{0}", tileImage)
'Create a bitmapImage to IsolatedStorage.
Using store As IsolatedStorageFile = IsolatedStorageFile.GetUserStoreForApplication()
'Tile image's Height * Width are 173 * 173.
Dim bitmap = New WriteableBitmap(173, 173)
'Render a bitmap from StackPanel.
bitmap.Render(background, New TranslateTransform())
Dim stream = store.CreateFile(tileImage)
bitmap.Invalidate()
bitmap.SaveJpeg(stream, 173, 173, 0, 100)
stream.Close()
End Using
SetHubTileImage(tileImage, tiletoupdate) ' this is what sets a control on the MainPage to display the generated image
End Sub
And finally the button click handler (which I just implemented because the code I'm using works fine in another app, but that app always gets user input before creating images, so I figured it was the only difference between the two apps)
Private Sub StartButton_Click(sender As System.Object, e As System.Windows.RoutedEventArgs) Handles StartButton.Click
SetupHubTiles()
End Sub
As you can see the code being executed is identical, but I get a different result when I run it directly in my contructor compared to running it from a button click handler.
The goal is for these images to be generated at runtime (without any interaction from the user) to be used in the UI.
I've tried a few different methods of doing this, but I always get the same results - an image is generated with just text when there should be text + image. I am using the same method in other apps with the only difference being those other apps are not creating the images as soon as the app launches, which may be the problem.
It also doesn't seem to make a difference if I change the location/type of controls that I am using to build my images.
Based on your comment, try to invoke your method either later in the loading sequence or use:
Dispatcher.BeginInvoke(() => { GenerateImages(); });
This will queue the function up to be run on the next UI thread tick which should be after any pending layout work which is queued up.
The fact that you are calling this function right at the end of the constructor has no consequence (other than the fact that the variables representing different objects have been initialized). It's all happening in the same UI thread tick, before Layout is kicked off so there is nothing in the StackPanel for you to capture.
To fix this, add your code to the Loaded event of the Page and still wrap it in a Dispatcher.BeginInvoke call so that it is guaranteed to happen after all of your Controls have rendered (at least their first pass, not withstanding any content that is loaded after the startup sequence).

VB .NET picture GetPixel & SetPixel: Include alpha?

I am trying to use GetPixel and SetPixel to copy the contents of one picture to another (I know there are other methods to do so, but there are reasons I want to try this ;D)
Anyway, the pictures are .png images, so they include transparency settings.
But for some reason, it seems like when I use GetPixel & SetPixel to put one image over another, it seems the second image completely replaces the other one. I mean, it seems the transparency settings are not respected when I use GetPixel & SetPixel.
Both images have the same size. Both have transparent areas.
Before calling SetPixel() you need to call MakeTransparnet(). Here's some code that copies the contents of the first pixel in an alpha-image onto another image and retain's the first image's alpha channel:
Using img1 = New Bitmap("c:\Users\Owner\Desktop\1.png")
PX = img1.GetPixel(0, 0)
End Using
Using img2 = New Bitmap("c:\Users\Owner\Desktop\2.png")
img2.MakeTransparent() '//Sets the transparent value and converts the image to Format32bppArgb
img2.SetPixel(0, 0, PX)
img2.Save("c:\Users\Owner\Desktop\3.png")
End Using