Can't instantiate public instance of class from form code - c#

I'm working on a windows forms application in c# and I can't figure out why I can't instantiate a class object from my form code. I have several classes, and from within all of those I can instantiate instances of the other classes publicly or just within methods with no problem.
However, when I try to instantiate one of those classes from my main form, it doesn't work.
It doesn't even recognize that I've just created an instance of the class.
The real kicker is that I can successfully instantiate a class from inside a method in my frmMain class:
private void Form_Load()
{
long deltaTime; int i; int page;
if (releaseMode)
{
modCanCable can = new modCanCable();
can.WaitWhileBusy();
}
All of the classes and form classes are under the same namespace too. Please let me know if you need to me to include any more information to help me find an answer!

You can only declare the global variable at the class level. Making use of that global variable must be done inside a property, method, or function.
For a global enumerator, declare it like you would any other variable
private EnumeratorClass VariableName;
Example (following naming conventions)
private MyEnum _myVariableName;

In C# all code has to be inside of a method. The line modCanCable can = new modCanCable(); declares a private field and uses a field initializer to initialize it to a new modCanCable instance. Any other refrence to the can field must be inside of a method body.

It must be done within a method or constructor. You cannot put it just in the class.
public partial class frmMain : Form
{
modCanCable cab = new modCanCable();
public frmMain()
{
cab.property = "asd";
}
}

Related

How to define a Class which is accessible in all classes in C#?

Am new to C#, but have a plenty of experience of VB.net, now my issue is that there are no modules in C# and i need to define a class which is accessible in all classes and i don't know how to do it.
For example I have a "classProject" and I need to make it accessible everywhere, so in vb.net , I will define it in module like below.
Module ModuleMain
Public tProject As New ClassProject
End Module
Now, I need to do same in C#.
Thanks in advance.
You can do this in your case:
namespace MyProject
{
public static class classProject
{
int myIntvar = 0;
string myStringvar = "test";
}
}
And you can use this static class in your other classes like:
public class Test
{
int intTest = classProject.myIntvar; //will be 0
string stringTest = classProject.myStringvar; // will be test
}
You can use the variables in the static class since a static variable shares the value of it among all instances of the class. When you create multiple instances of classProject class, the variables myIntvar and myStringvar are shared across all of other classes in your project. Thus, at any given point of time, there will be only one integer and one string value contained in the respective variable's.
It sounds like you're looking for a static class. You can reference the access modifiers here: https://learn.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/access-modifiers
I think you need to extends your other classes to class father (ClassProject) And you can access to it with youur children classes.
//[access modifier] - [class] - [identifier]
public class Customer
{
// Fields, properties, methods and events go here...
}
see more

Good style in declaration of local variables

I need to use variables rbFileChoice.Checked and rbHandWriteChoice.Checked in method LookAtChoice. But I can't take acces to them from this method. So I use global variables rbFileIsChecked and rbHandWriteIsChecked which declarated at Constructor of my Form object.
Is that solving good style of programming? Do another manners to take an acces for private-variables consist?
public partial class fMainWindow : Form
{
bool rbFileIsChecked;
bool rbHandWriteIsChecked;
public fMainWindow()
{
InitializeComponent();
rbFileIsChecked = rbFileChoice.Checked;
rbHandWriteIsChecked = rbHandWriteChoice.Checked;
Thread threadLookForChoice = new Thread(LookAtChoice);
threadLookForChoice.Start();
}
/// <summary>
/// Функция фонового потока. Следит за выбором пользователя. В случае выбора
/// нового пункта, удаляет старые введенные значения.
/// </summary>
public static void LookAtChoice()
{
if (true)
{
}
}
}
Assuming your coding a Form class and the above controls are radio-buttons - the Form is an object and its controls are its members (and not global variables), so it makes sense that they'll be available throughout the class.
Saying that, it is good practice (not necessarily in your case) is to refactor the business logic to a simple method.
For example, creating a method that receive two boolean parameters (like the radio-button's Check property) and acts accordingly.
why u r declaring global variable instead of u can directly use it in LookAtChoice() method intialize it by using
rbFileChoice.Checked;
rbHandWriteChoice.Checked; Properties....
if you want to access your radio button outside this form. you should declare its modifer to public or internal .
internal variable can be access within the namespace but with class object.
public variable can also be access outside the namespace but with class object.

c# - How to get reference to object A inside A's class?

In my SharePoint 2010 c# / asp.net site, I have a class defined like
namespace PDF_Library.VisualWebPart1
{
public partial class PDF_Library : Usercontrol
{
public static PDF_Library current;
protected void Page_Load(object sender, EventArgs e)
{
current = (PDF_Library)this;
}
}
}
public static class Page_State
{
public static Page is_display()
{
return PDF_Library.current.Page; // didn't work...
}
}
It doesn't have a constructor.
How can I get the reference to the current instance of this class?
I tried something like this in the top
public static PDF_Library current;
Then in a function it had
current = (PDF_Library)this;
But that didn't work...
You need to understand that it does not work this way. Your question is tagged with asp.net - multi-user, multi-threaded environment where multiple instances of PDF_Library user control will be created all the time. It is absolutely uncertain which one of them will be hanging off PDF_Library.current. You need to rethink your design.
More on this: Page instance is disposed of when the request processing is finished. Normally this instance with all its controls and things such as Response, Request, Context etc will be set for garbage collection. Because you keep a reference to a UserControl instance in a static field, all these objects (including Page) will be kept in memory until this current reference is replaced with something else.
It is the fact that you used static in the function that was assinging current that this did not work. static is a method that is not tied to any instance of the class, therefor you can not use this.
Your only options are either make the method non-static or pass in a instance of the class as a parameter to the static function.
From what I can tell you are trying to create a "Singleton Pattern". See the link to the previous MSDN article for examples on how to create a singleton class.
This looks like it will have an instance. If the class is marked as static (which it doesn't appear to be) then you can just reference it by name "PDF_Library". Other wise, use ILSpy or reflector to look at the end result. I bet it has a constructor; just because you don't see one, doesn't mean it isn't there. Override the default ctor and set your instance there.
namespace PDF_Library.VisualWebPart1
{
public partial class PDF_Library : Usercontrol
{
public static PDF_Library Current;
public PDF_Library() : base() {
Current = this;
}
}
}
The problem you might be having with your Page_Load code is that it's being called too late in the lifecycle and that's why your reference call isn't working.

Using certain variables in different classes (C#)

I'm pretty new to C# and I was trying out a few things. I have a label (named 'newLabel') in the form1.cs. I have a class named 'methods.cs'. In this class I have the method
public static void updateLabel()
what I want to do is:
public static void updateLabel()
{
newLabel.Text = "New Value";
}
but this doesn't work, probably because the method is in methods.cs and the newLabel is in form1.cs.
I had the same problem with declared variables. In the methods.cs I had the variable
int value;
but I couldn't use this variable in form1.cs. I fixed this by doing
public static int value { get; set; }
I have no idea what that did but it works, but I don't know how I can apply this trick with the label.
Could someone help me with this?
Thanks!
You should read up about OOP and encapsulation. Basically you want the form
to access private fields in another object (your class) - this is restricted by encapsulation, that's why you are running into problem - you can get around them by adding those fields and methods to the "public" interface that your class is declaring by making them public properties and methods, i.e in your example:
public int Value {get;set;}
Sometimes composition is used, i.e. in your example since your class is directly accessing the form you could have a form property on your class:
public Form ViewForm {get;set;}
It would be best if you learnt C# from tutorials, but the answer to this particular question lies with something called "scope"
Essentially, scope is the visibility of variables, classes, functions and objects. A variable marked "private" can only be seen within the thing that created it (if it's created inside a function it will always be private and any variables defined inside a function can only be used inside that function). If it's created inside a class only that class can use it.
Variables or functions denoted as public (this can only be done inside a class) can be seen from outside that class. To do that you would invoke myClass.myVariable to access the variable or myClass.myFunction() to access the function.
To denote the visibility of an object you use the keywords "public" or "private". Note: This only applies to variables and functions inside classes (it also applies to other things within classes, such as nested classes and structs, but that's outside the scope of this basic intro).
for example:
class myClass
{
private int myInt;
public void myfunction()
{
myInt = 1;
}
}
This will work, as myInt can be seen by anything inside myClass
class myOtherClass
{
private void myfunction()
{
myClass myObject = new myClass();
myObject.myInt = 2;
}
}
This will not, as myInt is private to myObject and only myObject can change it. myOtherClass does not have permission and it cannot see it.
class myOtherClassTwo
{
private void myfunction()
{
myClass myObject = new myClass();
myObject.myFunction();
}
}
This, thankfully, will work. myFunction was set as public in the myClass class, so it can be seen by anybody outside of the class.
Now the keyword static which you use has a whole different meaning. I advise you not to use it until you've learned about it as you're only adding additional complexity to your problems.
I hope this has cleared things up, though I must urge you to follow some real tutorials as these basics must be thoroughly detailed or you'll be caught out later on.
Since your updateLabel method accesses the label inside the form, correct object-oriented design would dictate that this method should be in the form, too. Then you have no problem accessing newLabel.
Technically speaking: newLabel doesn’t mean anything outside a form object. You could have several copies of your form, which would mean several copies of your newLabel; which of them should it refer to? Of course the computer won’t take a guess there; it’ll expect that you tell it which form you want to use.
The reason you couldn’t access the value variable is because it was private. If you had changed it simply to:
public static int value;
then it would have worked.
From the Form1, call the updateLabel method in the mothods class:
methods updateMethod = new methods();
newLabel.Text = updateMethod.updateLabel();
With this method in the methods class:
public static string updateLabel(){
return "New Value";
}

Factory Model in C#

I have a bunch of MDI child nodes that are all created in the same way and to reduce redundant code I'd like to be able to call a method, pass it a string (name of child node), have it create the node and add it to the parent.
I can do all the stuff except create the class from a string of a class name, how can I do this?
I'm currently using this in one of my applications to new up a class
public static IMobileAdapter CreateAdapter(Type AdapterType)
{
return (IMobileAdapter)System.Activator.CreateInstance(AdapterType);
}
It's returning an instance of a class that implements IMobileAdapter, but you could use it equally easily with a string:
public static IMyClassInterface CreateClass(string MyClassType)
{
return (IMyClassInterface)System.Activator.CreateInstance(Type.GetType(MyClassType));
}
Call it using code similar to the following:
IMyClassInterface myInst = CreateClass("MyNamespace.MyClass, MyAssembly");
Of course, the class it creates must implement the interface IMyClassInterface in this case, but with a class factory, you'd likely have all your classes implementing the same interface anyway.
Edit:
In reference to your comment, for the purpose of this discussion, think of the term "assembly" as the set of files within your vb/cs project. I'm assuming that you're doing this all within a single project [assembly] and not spreading over multiple projects.
In your case as your classes will be extending the Form object, you would do something like this.
Form myInst = CreateClass("MyExtendedForm");
Or
Form myInst = CreateClass(Type.GetType("MyExtendedForm"));
Depending on whether you get the type within your CreateClass method or outside it. You would need to cast your instance to the correct type in order to access any custom members. Consider this:
class MyCustomForm : Form
{
public int myCustomField{ get; set; }
}
I've got a custom form that extends Form adding the myCustomField property. I want to instantiate this using Activator.CreateInstance():
public static Form CreateClass(string InstanceName)
{
return (Form)System.Activator.CreateInstance(Type.GetType(InstanceName));
}
I then call it using:
Form myInst = CreateClass("MyCustomForm");
So now I have my custom form stored in myInst. However, to access the custom property [myCustomField], you would need to cast your instance to the correct form:
int someVal = ((Type.GetType("MyCustomForm"))myInst).myCustomField;
Activator.CreateInstance(Type.GetType(typeName))
If you have a string which is the name of the class, then you should be able to get a Type object therefrom, by calling Type.GetType(string). From that type, you should be able to use reflection to generate an object.

Categories