Visual Studio 2019 Form1.cs C# Global Variable

William 41 Reputation points
2021-09-17T14:58:20.017+00:00

I need to share a variable anywhere in Form1.cs.
Tried using example, https://social.msdn.microsoft.com/Forums/windows/en-US/536b644b-bc4b-42c4-8ad5-2458553c3cd3/how-to-make-certain-variables-global-to-all-forms-c?forum=winforms, but receive the following error;

CS0122 : 'Variables.ChartArray' is inaccessible due to its protection level

Can you share a variable anywhere in Form1.cs?
If so, how?

Windows Forms
Windows Forms
A set of .NET Framework managed libraries for developing graphical user interfaces.
1,866 questions
{count} votes

Accepted answer
  1. Karen Payne MVP 35,286 Reputation points
    2021-09-17T15:29:02.82+00:00

    Consider a Singleton class

    public sealed class ApplicationSettings
    {
        private static readonly Lazy<ApplicationSettings> Lazy = 
            new Lazy<ApplicationSettings>(() => new ApplicationSettings());
    
        /// <summary>
        /// Access point to methods and properties
        /// </summary>
        public static ApplicationSettings Instance => Lazy.Value;
        public char[] ChartArray { get; set; }
    }
    

    Usage

    Read the array

    ApplicationSettings.Instance.ChartArray
    

    Update

    char[] someArray = new[] { 'c', 'd', 'e' };
    ApplicationSettings.Instance.ChartArray = someArray;
    

    Or

    ApplicationSettings.Instance.ChartArray[0] = 'a';
    

1 additional answer

Sort by: Most helpful
  1. Michael Taylor 50,426 Reputation points
    2021-09-17T15:22:59.36+00:00

    There is really no such thing as a global variable in C#. You can however have a static (shared) value contained in a class. If that class is itself static (shared) then this is about as close to a global variable as you can get. But it is generally not recommended that you do this. It generally indicates you have a design problem. Really the same thing applies to any language that allows globals. Global variables are almost always the wrong solution. There are a couple of well defined cases where such a design may make sense (singletons, for example) but even then they should be rarely used and only if there is not a better option. You can google for the whys.

    Back to your question, to expose a value from a class make it public.

    public class ParentForm : Form
    {
       //Anybody with access to the instance can read or write this value
       public string Title { get; set; }
    }
    

    To share across other forms you would simply pass an instance of the desired ParentForm around.

    public class ChildForm : Form
    {
        public ParentForm { get; set; }
    
        private void SomeFunction ()
        {
            //Assuming ParentForm has already been set...
            string parentTitle = ParentForm.Title;
        }
    }
    

    If you need to access the type without passing an instance around then use a singleton ideally.

    public class ParentForm : Form
    {
        //Note that normally you make the ctor private but that won't work with a Form
        public ParentForm ()
        {
            ...
            Default = this;
        }
    
        public static ParentForm Default { get; private set; }
    }
    

    By marking the member as static it is now accessible without an instance

    string title = ParentForm.Default.Title;
    

    If your type only contains static members then you don't really need an instance and can make the entire type static which saves an allocation.

    public static class DataManager
    {
        public static DbConnection CreateConnection () { ... }
    }
    
    //Somewhere else
    using (var conn = DataManager.CreateConnection())
    {
    }