Take the 2-minute tour ×
Programmers Stack Exchange is a question and answer site for professional programmers interested in conceptual questions about software development. It's 100% free, no registration required.

I have a form with several controls on it. Every control has to be declared in the class, formatted in the constructor (-size, location, event subscription etc), and its event-handlers declared, again, in the class.

This is getting a bit unorganized, so I was thinking of refactoring this. For every control: Preparing a class which derives from that control-type (which will include location, event-subscription and event-handlers, etc.), and then using an instance of it.

Am I going to run into any trouble doing this?

share|improve this question
    
What language do you use? –  Emmad Kareem Dec 4 '11 at 19:59
    
@EmmadKareem It’s in the tags – C# –  ispiro Dec 4 '11 at 20:01
add comment

3 Answers

up vote 4 down vote accepted

If you need to have the same control, with the same formatting, etc. in a whole bunch of places, then this isn't a bad idea. However, if each class you create would only be used once, then you're not really removing any complexity, only moving it around. I'd prefer linear, conceptually simple straight-line code to a bunch of classes that are only instantiated once.

share|improve this answer
    
+1 Frequently change to one control affects another. There just is not a great way to cleanly separate things then. Sometimes redundant code can be simplified with some sort of a loop, e.g. if you have 50 checkboxes, they can all have the same handler which will do something specific depending on the .Text or a .Tag property. –  Job Dec 5 '11 at 4:07
add comment

Ideally speaking you should be having a separate class to initialize all your controls that are commonly needed in your application. Then override them in accordance with your specific requirements in your main program. This will make life much easier for you.

share|improve this answer
add comment

I think what you might want is a Mediator, as per MVC. It sounds like you are hitting the wall on your WYSIWYG form builder and need to transfer part or all of what is going on into some automated code.

A good example of this is a keyboard I was emulating on a form, so instead of manually placing the size and location of each key, I make an algorithm do it.

If you look into MVC, particularly pureMVC, you will see that a mediator is responsible for driving and responding to controls -- so there is a bit of wiring up to do. I am not saying you have to use MVC, but just the concept of a mediator. Subclassing each control seems like overkill from the information given.

There can be more than one mediator per form too. When I do MVC I will make a mediator for ALMOST every control, excepting menus, which there will be a mediator for each, and each submenu -- and toolbar (buttons) will all be managed as a group.

Mediators are a good way isolate responsibilities, for instance, you can have one mediator in charge of the background color of treelists, or have a mediator that keeps track of focus issues.

Looking at your post again, I think you should probably look into pureMVC, there is a C# version out on the web. If you are really clever you can get Reflection to wire things up automatically based on the names of your handlers. MVC is a good way to go because it loosens the coupling of your code, so instead of directly calling functions you just send a notification up and whoever 'cares' will receive it. This way you don't have to remember at the event point all the things you need to do, and everyone out there doesn't have to be present.

The downside is, you can no longer follow your code around by jumping from function to function in all cases.

Think of it this way, every class instance is isolated and needs to know very little about the outside world -- only the message conventions. How much faster can you program a class when all it has to worry about is itself :)

Psuedo-code:

/////////////////////////////////
// I mediate a form called AppsFm
C AppsFmMed
   = NAME         //="AppsFmMed"
   //
   /////////////////////////////////
   // published message
   = ___P_LOAD  //="AppsFmMed_LOAD"
   //
   /////////////////////////////////
   // interested in messages;
   = ___I_DATAPROXYNAME_DATACHANGED //="DataProxyName_DATACHANGED"
   //
   /////////////////////////////////
   // my controls
   p it         // the form
     get{return ViewForm as AppsFm;}
   //
   p form         // the same form
   p okBU         // a button
     get{return GetControl("okBU") as SimpleButton;}
   p cancelBU     // a button
   p appsTL     // a treelist
  //
  //////////////////////////////////
  //ctors
  Cn AppsFmMed()
  Cn AppsFmMed(string mediator_name_)
  Cn AppsFmMed(string mediator_name_, object view_component_)
  Cn AppsFmMed(string mediator_name_, object view_component_, object view_form_)
  //
  //////////////////////////////////
  // notifications come here and I respond to them
  Fn HandleNotification(INotification notification_){
    switch notification_.Name
     case:___I_DATAPROXYNAME_DATACHANGED
  }
  //
  //////////////////////////////////
  // initialization code, wire up events
  Fn hookEvents()   {
      assignFormEvent("FormClosed");
      assignFormEvent("Load");
      assignControlEvent(okBU.Name, "Click", "evtClick");
      assignControlEvent(cancelBU.Name, "Click", "evtClick");
  }
  //
  //////////////////////////////////
  // utility fns
  Fn initLabels()
  Fn saveValues()
  Fn loadValues()
  Fn initForm()
  //
  //////////////////////////////////
  // I am born and registered to recieve "interests",
  Fn OnRegister()
  Fn OnRemove()
  //
  //////////////////////////////////
  // the control events are wired to these
  Fn evtClick(object sender_, EventArgs e_)
  Fn EvtLoad(object sender_, EventArgs e_)
  Fn EvtFormClosed(object sender_, FormClosedEventArgs e_)
share|improve this answer
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.