I was trying to solve a specific problem that, in facts, is an example of a more general issue. Let' say that we have a couple of objects where one object depends on the other:
Bitmap AnImage; // Several instances of this object are possible: an image is loaded; then is discarded; then a new image is loaded, and so on.
Public class PixelSelection
{
string GenericAttribute;
int X;
int Y;
public PixelSelection(string myAttribute, int x, int y)
{
GenericAttribute = myAttribute;
X = x;
Y = y;
}
}
The second object:
Only a single instance of each class is required and both objects are created on demand by the user: you cannot use PixelSelection without a Bitmap instance but the need for the instance arises when the user needs to interact with the PixelSelection object.
The issue I am dealing with is how to keep in sync PixelSelection with the Bitmap; these are the possible scenarios I am considering:
The four tentative scenarios I have drafted are very different in abstraction and try to use different toolsets; worse, i feel that they could give evidence of an insufficient understanding of the OO model by me, showing confusion about object lifecycle issues and object orienting modeling. Could please someone help me to identify what is the best way to solve the problem an why, in terms of best practices, that solution is the proper answer? Thanks.
I have found a solution that works for me. I understood that the real requirement is to have a single code section where I can perform any action required to keep in sync the two objects without creating unnecessary dependencies; the answer is: events. The solution for me has been to create a class (a singleton) where a method has the complete responsibility to load the picture in its PictureBox control; the class has a method to perform the update that fires an event:
/*
* Load the picturebox in the control
*/
public void UpdatePictureBox( Bitmap BitmapToBeLoaded, PictureBox CurrentPictureBox)
{
/*
* If the Bitmap or the picturebox are null there is nothing to update: so exit keeping loaded the previous image
*/
if (BitmapToBeLoaded == null) return ;
CurrentPictureBox.Image = BitmapToBeLoaded; // Assign the Bitmap to the control
/*
* When loading, adapt the control size to the image size to avoid any distortion
*/
CurrentPictureBox.Width = BitmapToBeLoaded.Width; // Adapth width of the control size
CurrentPictureBox.Height = BitmapToBeLoaded.Height; // Adapth height of the control size
/*
* Publish events defensively: Book .Net Components, pag. 108
*/
try
{
if (null != ImageUpdated) ImageUpdated(); // Fire the event
}
catch
{
}
return ;
}
This way all the action to performed after a new image is made available are performed subscribing the event, in a single section of code easily found and documented . I do not claim that this is the best solution; but what makes me happy is the fact that the design seems more clean.