Is there a way to convert a string representation of a type name into a Type object?

  • Thread starter Thread starter Deckarep
  • Start date Start date
D

Deckarep

I want to be able to pass in a function a string say: "TextBox"

Then I need a way to convert that string representation into a Type
object so i can search through some controls and check their type.

Then I can do my check: If ( control is type) { //continue }

I'm doing this inside of a recursive function which goes through the
ControlTree.

Thanks in advance,

-Ralph

P.S. I would pass in a Type object to begin with into my recursive
call like typeof(TextBox) but my recursive function breaks and claims
that it doesn't have access to protected type member. I have no idea
why this happens.
 
P.S. I would pass in a Type object to begin with into my recursive
call like typeof(TextBox) but my recursive function breaks and claims
that it doesn't have access to protected type member. I have no idea
why this happens.

Please show us the code which you are using, and the error message(s)
produced...
 
The string approach is probably going to be ugly compared with a Type
approach; can you describe what went wrong / what you tried?
Personally I'd rather try and fix this the right way. Getting a Type
from a string is possible, but is easiest if you have the fully-
qualified name. Without it, a more pragmatic approach might be to test
whether eachControl.GetType().Name == theNameYouKnow.

I don't have it to hand, but on a machine that is shut down for the
weekend (miles away) I have a utility function something like (notepad
code):

static void ActionAll<T>(Control control, Action<T> action) where T :
Control {
if(control == null) throw new ArgumentNullException("control");
if(action == null) throw new ArgumentNullException("action");
T t = control as T;
if(t!=null) action(t);
foreach(Control child in control.Controls) {
ActionAll<T>(child, action);
}
}

[I might have optimised it with a queue/stack to avoid recursion, and
avoid repeatedly testing for null]

This allows me to say (as an example):

ActionAll<TextBox>(this, delegate(TextBox tb) {
tb.SomePropertySpecificToTextBox = "blah";
tb.SomeTextBoxSpecificMethod("bloop");
});

You get the idea...

Marc
 
The string approach is probably going to be ugly compared with a Type
approach; can you describe what went wrong / what you tried?
Personally I'd rather try and fix this the right way. Getting a Type
from a string is possible, but is easiest if you have the fully-
qualified name. Without it, a more pragmatic approach might be to test
whether eachControl.GetType().Name == theNameYouKnow.

I don't have it to hand, but on a machine that is shut down for the
weekend (miles away) I have a utility function something like (notepad
code):

static void ActionAll<T>(Control control, Action<T> action) where T :
Control {
if(control == null) throw new ArgumentNullException("control");
if(action == null) throw new ArgumentNullException("action");
T t = control as T;
if(t!=null) action(t);
foreach(Control child in control.Controls) {
ActionAll<T>(child, action);
}

}

[I might have optimised it with a queue/stack to avoid recursion, and
avoid repeatedly testing for null]

This allows me to say (as an example):

ActionAll<TextBox>(this, delegate(TextBox tb) {
tb.SomePropertySpecificToTextBox = "blah";
tb.SomeTextBoxSpecificMethod("bloop");

});

You get the idea...

Marc


private void RecurseFindControlTree( ControlCollection cc, Type
typeToFind, List<Control> foundList )
{
foreach(Control c in cc)
{

if( c is typeToFind)
foundList.Add(c);

RecurseFindControlTree(c.Controls, t, foundList);
}
}


I'm trying to do this which is not working...the compilar says "Can't
access protected member typeToFind" but type is a local member to
this recursive function. I'm not even doing anything sophisticated
just some dirty recursion to get some reporting done for my controls.
I know there's a bunch of better ways to do this but I just want to
get the code working of what I showed above.
 
Deckarep said:
private void RecurseFindControlTree( ControlCollection cc, Type
typeToFind, List<Control> foundList )
{
foreach(Control c in cc)
{

if( c is typeToFind)
foundList.Add(c);

RecurseFindControlTree(c.Controls, t, foundList);
}
}


[...] the compilar says "Can't
access protected member typeToFind" but type is a local member to
this recursive function.

"is" does not allow you to use a variable in this way; it expects a type
that is known to the compiler. You can make it work if you pass the Type as
a Generic parameter like this:


private void RecurseFindControlTree<typeToFind>(ControlCollection cc,
List<Control> foundList)
{
foreach (Control c in cc)
{

if (c is typeToFind)
foundList.Add(c);

RecurseFindControlTree<typeToFind>(c.Controls, foundList);
}
}
 
Deckarep said:
I want to be able to pass in a function a string say: "TextBox"

Then I need a way to convert that string representation into a Type
object so i can search through some controls and check their type.

If you pass in the fully-qualified name of the type (including
namespace), you can use Type.GetType. However, be warned that it will
only search mscorlib and the currently executing assembly unless you
*also* provide the assembly details. Look at Type.GetType for more
information. If the types you're interested in are always from the same
assembly, you could use Assembly.GetType.
Then I can do my check: If ( control is type) { //continue }

No, you can't do it like that - you need to use Type.IsAssignableTo (or
a similar method). The right hand operand of "is" is the name of a type
at compile time.
P.S. I would pass in a Type object to begin with into my recursive
call like typeof(TextBox) but my recursive function breaks and claims
that it doesn't have access to protected type member. I have no idea
why this happens.

I'd try to fix that rather than using Type.GetType.

Could you post a short but complete program which demonstrates the
problem?

See http://www.pobox.com/~skeet/csharp/complete.html for details of
what I mean by that.
 
Hi Jon,

I don't think there's a need to post my application.

I can clearly see that trying to check for my type via the 'is' syntax
is what was wrong.

I thought I can just a check for 'is' against a Type object...but that
simply won't do.

Anyways, thanks for all the help to everyone...now I have a couple of
solutions to work from. But I think the best solution is just
changing my code to use generics which has worked like a charm.

And by the way Jon I didn't know I could use Assembly.GetType( string
s ). This will definately help with some situations where I'm still
working with 1.1 code.

Thanks again,

-Ralph
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Back
Top