0

I have this code on each form in my app that has textboxes to prevent the textboxes that are ReadOnly from being tabbed to:

private void FrmInventory_Load(object sender, EventArgs e)
{
    foreach (var txtbx in Controls.OfType<TextBox>())
    {
        txtbx.TabStop = (!txtbx.ReadOnly);
    }
}

It would be good to only have this code in one place, but how can I do that, as each time that "external" method was called, it would touch TextBoxes on the calling form, which smells a little fishy. Is an extension method the way to go, something like:

public static bool TextboxIsReadOnly(this TextBox txtbx)
{
    return txtbx.ReadOnly;
}

...and then call it like this:

foreach (var txtbx in Controls.OfType<TextBox>())
{
    txtbx.TabStop = TextboxIsReadOnly(txtbx);
}

?

That doesn't seem like it's of much value - I still would have to put most of the code in each form, just as things stand now. Creating a custom textbox that is both ReadOnly and TabStop = false seems a little overkillish...

Is there a way to have this logic execute for every TextBox-containing form, without reproducing the code all throughout the project?

B. Clay Shannon-B. Crow Raven
  • 8,547
  • 144
  • 472
  • 862
  • 4
    This doesn't make sense. A read-only field allows someone to copy the value without changing it. If you don't want anyone to be able to focus the element, you set it's `Enabled` property to `false`. – Erik Philips Jan 28 '15 at 19:11
  • I'm not saying I don't want them to be focusable; I just don't want it to be tabbed to. IOW, the default is, don't enter, but if you really want to and make the effort to (you click in it), you can. In our case, this is because there are values that are populated from a database for information, not editing, purposes. – B. Clay Shannon-B. Crow Raven Jan 28 '15 at 19:23
  • hmm.. is this how you're currently using extension methods? just use it as an instance method.. i.e. `TextBox.TextboxIsReadOnly()` – Brett Caswell Jan 28 '15 at 19:33
  • prasy's answer is good; that will work for me. – B. Clay Shannon-B. Crow Raven Jan 28 '15 at 19:41
  • 1
    @B.ClayShannon wow that is something I've never seen, glad someone could help you! – Erik Philips Jan 28 '15 at 19:47
  • 1
    also, when I see the word 'snippet'.. I think of a pre-compile code generation "snippet". http://msdn.microsoft.com/en-us/library/ms165392.aspx .. the term you're looking for is "reusable" or "Code Reuse", because your accepted solution is inheritance. – Brett Caswell Jan 28 '15 at 20:11
  • A snippet is just a small block of code. – B. Clay Shannon-B. Crow Raven Jan 28 '15 at 20:13

3 Answers3

2

Having a base class that performs that step and making it the base for all your forms would work, although you would need to be careful about calling the base version of the overloaded methods.

Guvante
  • 18,775
  • 1
  • 33
  • 64
1

You can create a baseForm and Inherit that form in each of your forms.

Add a new Windows Form to your project(baseForm) and create load event

 public class baseForm: Form
 {
    public baseForm()
    {
        this.Load += baseForm_Load;
    }

    void baseForm_Load(object sender, EventArgs e)
    {
      var t = GetAll<TextBoxX>(this);
      foreach (var txtbx in Controls.OfType<TextBox>())
      {
           txtbx.TabStop = (!txtbx.ReadOnly);
      }
     }

    public static List<T> GetAll<T>(Form f1)
    {
        List<T> f = new List<T>();
        try {
            if (f1 != null) {
                CheckInner<T>(f1.Controls, ref f);
            }
        } catch (Exception ex) {
            f.Clear();
        }

        return f;
    }
 }

And finally in each form you can do like this

public partial class FrmInventory : baseForm
{
}
prasy
  • 250
  • 1
  • 14
1

Just to elaborate on the Extension Method solution you hinted at.

Extension Method

public static partial class MyExtensions
{
   public static void UpdateTabStop(this TextBox txtBox)
   {
       txtBox.TabStop = !(txtBox.ReadOnly);
   }
   public static void UpdateTabStop(this Form frm)
   {
       foreach (var txtBox in frm.Controls.OfType<TextBox>())
       {
           txtBox.UpdateTabStop();
       }
   }
}

Then, on any Form you would do this.UpdateTabStop()... you should of course do this in an event after the controls are initialized, like Load.

Brett Caswell
  • 732
  • 1
  • 4
  • 16