Using properties/methods of Win form controls beyond scope of proj namespace

Hi all,

Possibly a very simple answer - but no documentation has revealed the answer so any help would be very useful.

I have a Windows forms application project with a few controls, built with the form designer. In the header file for this form (the usual "Form1.h") I have the namespace named after my project and within it, the usual managed class defining the form and its controls.

My question is, if I need to access the properties and methods of these controls from beyond the scope of the namespace, how can I resolve scope to access the form and its controls

Ideally this would be possible from a separate source file, but essentially the methods and properties of a control on the form must be accessible from outside the namespace.

TIA for any help, appreciated.

Si



Answer this question

Using properties/methods of Win form controls beyond scope of proj namespace

  • Eugene Katz

    Thanks for the help, n0n4m3! I have one further question. I understand that the form class, Form1 for example, is instantiated and the resulting object is passed as a parameter to the Application::Run() method, "gcnew Form1". All the controls on the form are then accessed using the "this->" pointer to get the form instance from within the Form1 class definition.

    By instantiating a separate instance of my Form1 class I have managed to access the controls on the new form. However, I would like to have global access to the first instance created. To do this, I created a named instance and passed this object to the Application::Run() method. Unfortunately, I can't make any further progress because when I try to make access global by declaring the form object with global scope, the compiler tells me that managed variables, on the gc heap, may not be global!

    Any further help would be very useful!

    Thanks again,

    Si


  • Robin E Davies

    Hi,
    one way would be to have a handle to the form you want to manipulate in the other source file. Make some properties to access the components in the form and that's about it.


  • Vijay Guru Prasadh

    Hi,
    if you need to have an handle to Form1 then just create it before the Application::Run() method:

    Form1^ form1 = gcnew Form1();
    form1->Show();
    Application::Run();

    Now use the form1 handle like in the other example.
    In this way you have to handle the OnClose event if you want to exit the application (this is done automatically if you use Application::Run(gcnew Form1()); ).


  • RussC_UK

    Thanks for the help, n0n4m3.

    I haven't replied recently because we lost our internet connection :-(

    I will post a code example to illustrate the problem.

    My project is a DVD collection manager that will maintain a database of DVD movies. The primary key will be the unique volume serial number. To use the QueryCancelAutoPlay interface, which notifies my program when a disc is inserted, I am required to use COM. The function shown below comes after my project namespace in my Form1.h file.

    STDMETHODIMP CQueryCancelAutoplay::AllowAutoPlay(LPCWSTR pszPath,

    DWORD dwContentType, LPCWSTR pszLabel, DWORD dwSerialNumber)

    {

    if (dwContentType & ARCONTENT_DVDMOVIE)//a DVD!

    {//do something if a DVD movie is inserted

    //I'd like to access a text box on my Form1 here - and place the DVD volume serial number in the text box

    //I just need some way of accessing the Form1 object within this function. Any ideas

    }

    }


  • Pocketmnky

    You must have a reference to a Form1 object so that you can access it. Let's check an example:

    // It looks like CQueryCancelAutoplay is unmanaged so to hold a reference to a managed object we use gcroot

    #include <vcclr.h>
    #include "Form1.h"

    class CQueryCancelAutoplay : public IQueryCancelAutoPlay
    {
    public: CQueryCancelAutoplay(Form1^ form1) { m_form1 = form1; }

    private: gcroot<Form1^> m_form1;
    }

    // then.. to manipulate form1 is easy

    STDMETHODIMP CQueryCancelAutoplay::AllowAutoPlay(LPCWSTR pszPath,
    DWORD dwContentType, LPCWSTR pszLabel, DWORD dwSerialNumber)
    {
    if (dwContentType & ARCONTENT_DVDMOVIE)//a DVD!
    {
    m_form1->SetSerialNumber("1000-000-000");
    // or if Form1 has a property that returns the textbox

    // m_form1->SerialNumberTextBox->Text = "1000-000-000";
    }
    }




  • hrubesh

    That article describes some ways of doing it (among them is the one I described). I'll make a simple example here:

    ref class MyForm : public Form
    {
    // other stuff here
    public:
    void DoSomething() {}
    };

    ref class ClassThatUsesMyForm
    {
    public:
    ClassThatUsesMyForm(MyForm^ form) { m_form = form; }

    void DoSomethingInMyForm() { m_form->DoSomething(); }

    private:
    MyForm^ m_form;
    };


    Note: This code wasn't tested and may contain one or more syntax errors.


  • TroyWolbrink

    Thank you again, n0n4m3. Your help has solved the problem. Here I'll document a summary of the problem and solution to help others with the same problem:

    Q: How can I access the properties and methods of the controls on my .NET CLR Windows form, from outside the form class definition

    A: Use gcroot<myformclass^> myformobject; to declare an object for your form with global scope, at the bottom of your project namespace in your form's .h file. Then instantiate this within your main() function using myformobject = gcnew myformclass(); and pass this newly created object to the Application::Run() call in your main() function. Now create properties for the controls on your form or declare them as public. Now from outside your form's class definition you may have mynamespace::myformobject->mycontrol->property = ...;

    Regards,

    Si


  • mkuppu

    This is very close to what I'm trying to achieve - the only difference is that my form1 object must have global scope so that I can use it in my Form1.h file and generally outside of the main function in which Application::Run is actually called.

    If I try this code in my main project .cpp file:

    ...

    Form1 ^myform;//causes error - cannot have greater scope than function scope

    void main() {

    myform = gcnew Form1();

    Application::Run(myform);

    }

    then I get the error "global or static variable may not have managed type mynamespace::Form1 ^, may not declare a global or static variable, or a member of a native type that refers to objects in the gc heap".

    Any help working around the last problem would be very useful!


  • Pankaj11

    Hi,

    Thanks for the reply, I will look into it - however my original idea was to attempt something similar to what has been described below for the Visual Basic .NET language:

    http://msdn.microsoft.com/library/default.asp url=/library/en-us/dv_vstechart/html/vbtchWorkingWithMultipleFormsInVisualBasicNETUpgradingToNET.asp

    Please scroll or jump to "Interacting with Other Forms in .NET".

    If anyone has any knowledge of VB (I have none!) I'd appreciate any suggestions of how the above might be implemented in C++ .NET.

    Regards,

    Si


  • SpunkyMan

    If I understood you well, you have problems because you have the form1 in a namespace different than the one you are accessing it and that's why you need it in the global scope
    1- that error is because the language doesn't allow managed code to be declared as global or static variables.
    2- Check this example:

    Form1.h
    namespace MyForm1NameSpace
    {
        ref class Form1 : public Form
        {
            public: Form1();
        };
    }


    Form1.cpp
    #include "Form1.h"
    namespace MyForm1NameSpace
    {
        Form1::Form1() {}
    }


    Form2.h
    // forward declaration of Form1
    namespace MyForm1NameSpace
    {
        ref class Form1;
    }

    namespace MyForm2NameSpace
    {
        ref class Form2 : public Form
        {
            public: Form2(MyForm1NameSpace::Form1^ form);
        };

        MyForm1NameSpace::Form1^ m_form;
    }


    Form2.cpp
    #include "Form2.h"
    #include "Form1.h"
    namespace MyForm2NameSpace
    {
        Form2::Form2(MyForm1NameSpace::Form1^ form)
        {
            m_form = form;
        }
    }


    Main.cpp
    #include "Form2.h"
    #include "Form1.h"

    void main()
    {
        MyForm1NameSpace::Form1^ myform1 = gcnew Form1();
        MyForm2NameSpace::Form2^ myform2 = gcnew Form2(myform1);
        Application::Run(myform1);
    }

    Hope this helps to solve your problem. If not, try to describe exactly the classes you have in your project and how you want to access from one to another.


  • Using properties/methods of Win form controls beyond scope of proj namespace