I’m building off this question and creating a simple ImageButton class that represents a button containing only an image. I implemented (at least I believe I did) the suggestions in this answer, but I’m still getting an exception with this code:
public class ImageButton : Button
{
// Overrides the property
public override Image BackgroundImage
{
get { return base.BackgroundImage; }
set
{
base.BackgroundImage = value;
if (value != null) this.Size = value.Size;
}
}
// Shadows the property (note the -new- keyword)
[DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
public new Size Size
{
get
{
return base.Size;
}
set
{
base.Size = value;
}
}
public ImageButton()
{
this.BackgroundImage = base.BackgroundImage;
this.BackgroundImageChanged += new EventHandler(ImageButton_BackgroundImageChanged);
}
void ImageButton_BackgroundImageChanged(object sender, EventArgs e)
{
this.Size = this.BackgroundImage.Size;
}
protected override void OnPaint(PaintEventArgs e)
{
e.Graphics.DrawImage(BackgroundImage, 0, 0); // <-- Error occurs here
}
protected override void OnPaintBackground(PaintEventArgs e)
{
// Do nothing
}
}
When I try to add this control to the designer, I get
The control ImageButton has thrown an unhandled exception in the
designer and has been disabled.Exception: Value cannot be null. Parameter name: image
Stack trace: ImageButton.OnPaint(PaintEventArgs e) in
ImageButton.cs:line48
Line 48 is this line:
e.Graphics.DrawImage(BackgroundImage, 0, 0);
I realise that this error is thrown because BackgroundImage is not set to a value, but I’m unsure how to do so in the code. In the actual application, this class will never be added to the designer, but rather added programmatically. How can I fix this exception?
Yes, sure, guaranteed exception. You hope that somebody has set the BackgroundImage property before the constructor runs. That’s not possible, the constructor runs before any property on the control can be set.
The next thing that goes wrong is that the Paint event will be raised in the designer as well. Which happens immediately after you drop the control on the form. That’s a Kaboom, neither the user nor your code has given the BackgroundImage property a value yet. So just fix the method: