How to access variables in a class from all forms - c#

I have a few forms, and a class Management which has a list of users, info and stuff. I want an instace of Management which I will be able to access from all the forms. How do I do that?
Thenx in advance.

The error
Error 3 Inconsistent accessibility: parameter type 'ProjectClasses.Management' is less accessible than method 'FinaleSystem.MenuForm.Start(ProjectClasses.Management)'
means that your MenuForm is exporting a method Start (probably it is public) having a parameter of type ProjectClasses.Management that is less accessible. Probably it is internal. Declaring the Management class as public will resolve your problem. If the class is nested within another class, declare the "parent" class as public as well. If you prefer not to make the class public, make the method Start internal instead.
public means that an item is accessible from another project. internal means that the item is only accessible within the same project. If Start was public and the type of a parameter internal or private you could not call the method from another project, since you could not create an object of the requested type. You couldn't derive a class from it either in order to use it as a parameter.
Non-nested classes have a default access modifier of internal. Nested classes have a default access modifier of private.
See https://stackoverflow.com/a/3763638/880990 for details

Best way (my point of view) is to use a MVVM pattern and have the ViewModels inherit from a base class

Just to elaborate on Thomas' answer.
Singleton
A singleton is basically a class where it only ever allows the program to holds one instance of itself. In other words, whether you're in the Superman class or the Batman class, the Singleton class, let's call it MyCar will always be the same.
A Singleton is pretty easy to implement and to grasp. Take a look at this tutorial: http://www.usmaanz.com/singleton/ to get an idea.
MVVM
A MVVM pattern is pretty powerful! It allows you to create an object which contains certain amount of properties and allow that model to be used by many Views or Forms in your case.
Let's say that a Form has the following controls:
Username
Password
Email
And in this form, we wish to hold data from what is being passed in to these controls. Therefore, the following class will help us hold that data:
public class MyModel
{
public string Name {get;set;}
public string Password {get;set;}
public string Email {get;set;}
}
Then in your Form, you may do:
MyModel model = new MyModel(){Name = txtName.Text, Password = txtPassword.Text, Email = txtEmail.txt};
This object will now hold the data of the form. You may also use this class to hold data any where else and you can obviously, freely, create as many instances of it as you want.
Hope that helps!

One possible solution is to make your Management class' properties static.
Cheers

The simple case of this is implemented as a singleton where one and only one instance of a class exists for the life of the program. Singleton has many drawbacks mostly related to difficulty of testing and correctly handling threading. The next pass at solving this is usually implemented as a service locator pattern, however this has also come to be viewed as an anti-pattern. The best way to handle this is called dependency injection. While DI is the "best way" it may be hard/over kill in your scenario.

Related

How to share a derived member variable with the base class

I'm using Xamarin to make an Android and iOS app. I have my code split into 3 projects: Android, iOS and common. The code is basically designed such that common code is abstract and handles the the OS agnostic side of things and the Android/iOS code inherits from the common and handles the OS specific things. However, I'm tripping over how to handle custom member variables following this paradigm, as I need to hold onto a OS specific instance so that the class can do OS things, but I also need to reference the OS specific instance in the common code to commonly handle things.
Example: A common class is comprised of a question and a chart (think public survey where you can see how other people responded). The common version of these things are responsible for retrieving their data from the appropriate places (database, server). The OS specific version of these things are responsible for displaying the UI. I would like to pass into this class the Android version of the question and chart. Then I can call the class' "retrieveData" (common) function and the class' "displayUi" (OS specific function). I would really like to reference the same member variables during this process.
If I program it 'normally', the common class would contain the common class of question and chart and the inherited Android class would access this variables. But this doesn't work because when the Android class access them, it gets the variables as common and doesn't have the OS specific functionality. If I put the variables in the Android class, then the base class doesn't know about them and I can't do common things with them.
Up to this point, I've gotten around this by using Generics. But I've recently ran into a problem with that solution (Inheriting generic can't up cast). Another solution I've thought of is using the 'new' operator on a property in the Android class to mask the inherited member variable and use the get function to automatically down cast the variable into the Android version and the set function to store the variable on the base (base.variable = value). I'm not too keen on this idea as I have to double declare the variables and I have a slight problem with collections of variables (I can either use Array.Convert (or some similar method) if I need to pass in the array/list/dictionary/etc, or I can cast as I iterate though it to do whatever it is I have to do. Not great, but doable.
I'm curious if there's other ways to to handle this situation .
Edit
Here's some simplified code:
public interface IAnsweredCommon { ... }
public interface IAnsweredAndroid : IAnsweredCommon { ... }
public abstract class ConstructorCommon<AnsweredType> where AnsweredType : IAnsweredCommon
{
protected AnsweredType Answered;
...
}
public class ConstructorAndroid : ConstructorCommon<IAnsweredAndroid> { ... }
As you can see, this version is using the generic pattern. ConstructorCommon has a variable of type AnsweredType which is treated as IAnsweredCommon within the class allowing it to do non-OS specific things with it. ConstructorAndroid inherits from ConstructorCommon using IAnsweredAndroid. This allows me to instantiate ConstructorAndroid without having to specify a type and allows it to treat the inherited AnsweredType as a IAnsweredAndroid to do OS specific things.
As mentioned in the previous question; this generic way won't work for an unrelated reason. So, to make code work in that question, I need away to replicate what the generic is doing. The only other way I can think of, is to change the Answered variable type from AnsweredType to IAnsweredCommon and to implement a new property in ConstructorAndroid that hides the Answered variable (via the 'new' keyword) and implement the get to return a casted base variable and set to set the base variable:
public abstract class ConstructorCommon
{
protected IAnsweredCommon Answered;
...
}
public class ConstructorAndroid : ConstructorCommon
{
protected new IAnsweredAndroid Answered
{
get => (IAnsweredAndroid)base.Answered;
set => base.Answered = value;
}
...
}
I'm not super crazy about this idea for the reasons I stated above, so I'm curious if there's another way.

Reusable Class Library Implementation

I've built a reusable Class Library to encapsulate my Authentication logic. I want to be able to reuse the compiled *.dll across multiple projects.
What I've got works. But, something about how I'm making the reference, or how my Class Library is structured isn't quite right. And I need your help to figure out what I'm doing-wrong/not-understanding...
I've got a Class Library (Authentication.dll) which is structured like this:
namespace AUTHENTICATION
{
public static class authentication
{
public static Boolean Authenticate(long UserID, long AppID) {...}
//...More Static Methods...//
}
}
In my dependent project I've added a reference to Authentication.dll, and I've added a using directive...
using AUTHENTICATION;
With this structure I can call my Authenticate method, from my dependent project, like so...
authentication.Authenticate(1,1)
I'd like to be able to not have to include that "authentication." before all calls to methods from this Class Library. Is that possible? If so, what changes do I need to make to my Class Library, or how I'm implementing it in my dependent project?
In C# a function cannot exist without a class. So you always need to define something for it, being a class for a static method or an object for an object method.
The only option to achieve that would be to declare a base class in the Authentication assembly from which you inherit in the dependent projects.
You could expose Authenticate as a protected method (or public works too), and call it without specifying the class name.
public class MyClassInDependentProject : authentication
{
public void DoSomething(int userId, long appId)
{
var success = Authenticate(userId, appId);
…
}
}
That said, you'll quickly find this to be a bad design. It conflates a cross-cutting concern with all sorts of other classes, and those classes are now precluded from inheriting from any other class.
Composition is a core principle of object-oriented programming, and we have the idiom "Favor composition over inheritance." This simply means that we break down complexity into manageable chunks (classes, which become instantiated as objects), and then compose those objects together to handle complex processing. So, you have encapsulated some aspect of authentication in your class, and you provide that to other classes compositionally so they can use it for authentication. Thinking about it as an object with which you can do something helps, conceptually.
As an analogy, think about needing to drill a hole in the top of your desk. You bring a drill (object) into your office (class). At that point, it wouldn't make sense to simply say "On," because "On" could be handled by your fan, your lamp, your PC, etc. (other objects in your class). You need to specify, "Drill On."
If you are making a class library in C# you should learn to use the naming conventions that exists: Design Guidelines for Developing Class Libraries
Here is how you should name namespaces: https://learn.microsoft.com/en-us/dotnet/standard/design-guidelines/interface
C# is also an object oriented language, hence the need of classes (using Authentication as you should name your class).
It also seems like the data source is hard coded. Your class library users (even if it's just you) might want to configure the data source.
Google about singleton and why it's considered to be an anti pattern today (in most cases).
You are obliged to use Class in order to invoke your method, just
When is static class just NameClass.Method
When is not static, you must create instance, ClassName ob = new ClassName(); ob.Method();
The format of a call like this is class.method, and you really can't escape using the "class" moniker even with the "using" designation. Something has to "host" the function.
I don't think what you are asking for is possible without using the base class method Jay mentioned. If all you want is to simplify the syntax whenever you call Authenticate() however, this silly solution (adding an extra method in each class that needs to do authentication) may be just what you want:
private static void DoAuth(long UserID, long AppID){
authentication.Authenticate(UserID, AppID)
}
If the ID's are always the same within some context, you could also overload it:
private static void DoAuth(){
DoAuth(1,1)
}
Yes, this does mean you have to add more code wherever you want to do the authentication (that's why it's silly! ;) ). It does also however, also reduce this:
authentication.Authenticate(1,1);
...into this:
DoAuth();
I leave the cost / benefit analysis of this up to you..
I know I am some 3 years late but here goes nothing.
To keep your code cleaner and more readable you should create a new namespace for all the re-usable code that you want to have. Then in that namespace have the Authentication Class and Authenticate Function.
To use this you can easily set a using on your namespace and use the function as you are doing like
Authentication.Authenticate()
But to use
Authenticate()
by itself you can always do
using MyNamespace.Authentication;
and in your code use Authenticate Function directly.

C# Private members visibility

We have a Student class in our business model. something struck me as strange, if we are manipulating one student from another student, the students private members are visible, why is this?
class Program {
static void Main(string[] args) {
Student s1 = new Student();
Student s2 = new Student();
s1.SeePrivatePropertiesAndFields(s2);
}
}
public class Student {
private String _studentsPrivateField;
public Student() {
_studentsPrivateField = DateTime.Now.Ticks.ToString();
}
public void SeePrivatePropertiesAndFields(Student anotherStudent) {
//this seems like these should be private, even from the same class as it is a different instantiation
Console.WriteLine(anotherStudent._studentsPrivateField);
}
}
Can i have some thoughts on the design considerations/implications of this. It seems that you can't hide information from your siblings. Is there a way to mark a field or member as hidden from other instances of the same class?
There's an easy way to ensure this:
Don't mess around with private members of other instances of the same class.
Seriously - you're the one writing the Student code.
The easiest way to ensure this is to program to an interface, such as:
class Program
{
static void Main(string[] args)
{
IStudent s1 = new Student();
IStudent s2 = new Student();
s1.ExamineStudentsMembers(s1);
}
}
public interface IStudent
{
void ExamineStudentsMembers(IStudent anotherStudent);
}
public class Student : IStudent
{
private string _studentsPrivateMember;
public Student()
{
_studentsPrivateMember = DateTime.Now.Ticks.ToString();
}
public void ExamineStudentsMembers(IStudent anotherStudent)
{
Console.WriteLine(anotherStudent._studentsPrivateMember);
}
}
This will no longer compile due to ExamineStudentsMembers trying to access a private field.
If you are writing the class, you have complete control over it, so if you don't want one object to be able to modify another, don't write in that functionality.
Classes will often use private variables in other instances to implement efficient comparison and copy functions.
Private just means that the member (field/method/etc.) can be accessed only from the within the code of the parent type. From CSharpOnline
Private members of multiple instances are visible and can be invoked. This comes in handy when you are implementing a "copy constructor" or a "clone" method on your type, where the argument is an instance of the same type. If the designers would have made private fields inaccessible, then you may have to create a bunch of getter methods just for clone/copy to get at them. IMHO, I like it better the way it is. Within the same type, Reading another object's state isn't that bad as writing to it though (which could be a DONT-code-convention for you/your team.)
Accessing a sibling's private data may seem wrong when phrased like:
public void ExamineStudentsMembers(Student anotherStudent) {
//this seems very wrong
Console.WriteLine(anotherStudent._studentsPrivateMember);
}
However, it doesn't seem so odd for methods which require this sort of functionality. What methods require accessing a sibling's private data? Comparison methods (in particular equals) and objects in a data structure (say a tree or linked list).
Comparison methods often compare private data directly rather than just the public data.
For a class of nodes that make up a linked list, graph or tree, being able to access a sibling's private data is exactly what is needed. Code in the know (part of the class) can tinker around with the data structure, but code outside of the data structure cannot touch the internals.
It is interesting to note that these two cases are less common in day-to-day programming than when this language feature were first developed. Back in 1990s and early 2000s, in C++ it would have been much more common to build custom data structures and comparison methods. Perhaps it is a good time to reconsider private members.
i like the second point, you can look, but dont touch those private members.
it's funny you should say that, i knew a teacher once and he said he often had a problem deciding what classes it was ok to look at the members and which ones he could actually have a play with.
An object is just a piece of data; the class contains the functionality. A member method is just a nice trick the compiler plays; it's really more like a static method with an implied argument (sort of like extension methods). With that in mind, protecting objects from each other doesn't make any sense; you can only protect classes from each other. So it's natural that it works that way.
No, this is necessary, the method code is not specific to the instance, it is only specific to the type of the object. (virtual methods) or the declared type of the variable (for non-virtual methods). The non-static fields, on the other hand, are instance specific... That's where you have instance-level isolation.
The only difference between a static method and a non-static method is that the static method is not allowed to access other instance based (non-static) methods or fields. Any method that CAN be made static without modification will not be affected in any way by making it static, except to force compiler to throw errors anywhere it was called using instance-based syntax.
If you intend to examine a given student's information then I would change the method to be static:
public static void ExamineStudentsMembers(Student student)
{
Console.WriteLine(student._studentsPrivateMember);
}
You would then use Student.ExamineStudentsMembers(s1). Using s1.ExamineStudentsMembers(s2) would be invalid.
If this isn't the intended purpose I would rewrite the method as:
public void ExamineStudentsMembers()
{
Console.WriteLine(_studentsPrivateMember);
}
The above would then be used by writing s1.ExamineStudentsMembers()
Private members are to hide implementation details from clients. The clients should only see the interface (public methods / fields / properties).
The purpose is not to protect the programmer from himself.
This is also NOT a security feature because you can always access private fields via reflection.
It's really to separate interface & implementation (black box design), and clients programming against a contract (all public fields).
For example if you have a public get property, it could access some private field directly, or it could calculate the value from some other fields.
The purpose is, the client only knows the contract (the public property) and the implementation can be changed without affecting the client
Object scope does not ever imply security - ever! It is role of the OS to provide runtime security. It is a bug to design a system that relies on language specific object scope to limit runtime object instance data access. If this were not the case, then all non OO languages are, by definition, not secure.

Make an object accessible to only one other object in the same assembly?

Each business object has a matching object that contains sql calls. I'd like to restrict these sql objects in a way where they can only be used by the matching business object. How can this be achieved?
Update
Greg brought up the point about testability. Since the SqlObjects will contain very business-process specific sql I don't want them reused in multiple buiness objects. (Basic CRUD operations are all code-generated) Is there a way to make the SqlObjects accessible to only one business object in the business assembly (like yshuditelu and Greg Beech showed) AND expose the SqlObjects to the unit testing assembly?
If this is the approach you want or need to take, you could make the sql objects private classes within the business object.
public class BusinessObject
{
private class SqlObject { }
}
Additionally, by making use of partial classes, you could separate this into separate files if desired.
//in one file
public partial class BusinessObject
{
//business object implementation
}
//in another file
public partial class BusinessObject
{
private class SqlObject { }
}
Joel makes a good point in a comment below "the SqlObject can still inherit from a common type, to that things like connection information can be shared across those "inner" classes." this is absolutely true, and potentially very beneficial.
In response to your edit, unit tests can only test public classes and functions (without using reflection in your tests). The only option I can think of that would do this is:
make one assembly per business/sql object pair
changing the private class SqlObject to internal class SqlObject
then use the [InternalsVisibleTo("UnitTestsAssembly")] for the project
Also, at this point you wouldn't have to keep the sql object as a nested class. Generally speaking, I think this would likely add more complexity than the value it adds, but I completely understand that every situation is different, and if your requirements/expectations are driving you this, I wish you well. Personally, I think I would go with making the SqlObjects public (or internal with internals visible to for unit testing), and accept the fact that that means the sql classes are exposed to all of the business classes.
The only way to do it is make the SQL object a private nested type, i.e.
public class BusinessObject
{
private class SqlObject
{
}
}
Whether this is a good idea from the point of view of testability is another matter entirely...
You are attmepting to implement what is a Friend Class in C++. As far as I know C# and VB.Net do not have anything equivalent. My only suggestion is to make the class you wish to restrict an internal class of the class that needs to access it.
You could also work with two assemblies (one for business objects and one for the related SQL objects) and use the internal modifier on each SQL class and use then [InternalsVisibleTo("BusinessObjectAssembly")] for the SQLAssembly.

Passing objects to a UITypeEditor

I am currently hoping to use a PropertyGrid to allow users to edit some of my classes, however I've hit a wall with passing objects to the UITypeEditor(s) they use. When the user presses the drop down I want to show a listbox of already loaded textures to choose from, if they want to use a texture the application hasn't loaded yet they can click a button to choose one from a file dialog. In case I make no sense here a mock of the form:
.
My problem: To fill the listbox I need access to the class that manages the list of resources from the UITypeEditor.
Now I've solved this problem for my own classes by giving them a reference on creation to their managing object. In the UITypeEditor I then use that reference to access what I need. However I can't do this for classes I haven't written, such as the XNA Texture2D class.
Here are what the classes I'm using look like:
class StaticGeometryChunk
{
// Geometry data to draw with. Contains a reference to its managing
// class for use in its UITypeEditor.
public GeometryData { get; set; }
....
}
class Material
{
// These are XNA classes. I can't just add a reference to its managing
// class (I think?).
public Texture2D Texture1 { get; set; }
public Texture2D Texture2 { get; set; }
....
}
I've been looking at my options and they seem to be:
Make the managing classes static.
I don't really want to do this. There are several managing classes as each resource is loaded differently. There are also classes that need to be created before these and are passed in.
Make the managing classes singletons.
I don't really want to do this either. It seems like a quick and dirty way to "hide" the problem instead of "solve" it. I also might want the option of having several managing classes in the future which the singletons eliminate.
Create a wrapper class which holds the reference to a managing class and its target (such as the XNA Texture2D).
This is currently what I'm thinking of doing. Its would be quite simple and quick to do but something about it nags me but I don't know what.
Any thoughts on the above or other methods to pass what I need into the UITypeEditor?
Thank you for reading.
In the EditValue method, you are given a context. Use context.Instance to access the object that holds your property. This object should also contain a property that gives you access to the list of things you want to display. You could test if context.Instance is ITextureProvider for example, then cast it and access the textures. Not sure if this makes sense in your design but let me know.
As an alternative you can try the following approach. I find it very elegant, because it does not require to store a list of available property values in the object. Therefore, for example, you can show one set of values on one form and another set on another.
Create an interface IYourDataProviderService.
Create an implementation of IYourDataProviderService, which knows the concrete data to provide.
Create a class implementing ISite. In GetService() method return an instance of class which implements IYourDataProviderService, if the serviceType parameter is typeof(IYourDataProviderService).
I left rest of ISite methods throwing NotImplementedException (except DesignMode property) and for me it worked, but probably this is not an ideal solution.
In 'Load' event handler assign your implementation to the Site property of your propertygrid.
Enjoy!

Categories