Передача значения от дочернего к родителю mdi в VB.net - PullRequest
4 голосов
/ 19 февраля 2009

У меня есть простая книга контактов. У приложения есть главное окно, это форма mdi. Когда контакт добавляется с помощью формы «добавить контакт», я хочу показать простое сообщение обратной связи в строке состояния родительского окна, сообщающее, что контакт был успешно добавлен.

Вот детская загрузка:

Private Sub addButton_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles addButton.Click
    Dim af As New addForm
    af.MdiParent = Me
    af.Show()
End Sub

Проблема заключается в том, что, поскольку родитель на самом деле является родителем mdi, а форма «добавить контакт» запускается с .Show() вместо .ShowDialog(), я не могу сохранить любое возвращаемое значение, которое может использоваться запуск Sub для выполнения действия.

Есть ли способ передать значение от этого потомка родителю mdi? Вот дочерняя форма, которая делает все это:

Private Sub addButton_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles addButton.Click

    Dim contact = <contact>
                      <quickName><%= quickNameTextBox.Text %></quickName>
                      <firstName><%= firstNameTextBox.Text %></firstName>
                      <lastName><%= lastNameTextBox.Text %></lastName>
                      <email><%= emailTextBox.Text %></email>
                      <website><%= websiteTextBox.Text %></website>
                      <telephone><%= telephoneTextBox.Text %></telephone>
                      <mobile><%= mobileTextBox.Text %></mobile>
                  </contact>

    Dim contactList = XDocument.Load("contactList.xml")

    contactList.Elements()(0).Add(contact)
    contactList.Save("contactList.xml")
    //something here to trigger the status update in the parent?
    //trivia: SO doesn't support VB single-quote comments...
    Me.Close()

End Sub

P.S. По-видимому, я довольно плохо помечаю вещи ... поэтому всем, кто хочет пометить этот вопрос, приветствуются.

Ответы [ 6 ]

6 голосов
/ 19 февраля 2009

То, как я справлюсь с этим, заключается в создании пользовательского события в дочернем элементе управления. Затем обработайте событие в родительском элементе управления.

Сначала определите событие в дочернем элементе управления (например, определите свое собственное):

Public Event EVENTNAME(ByVal sender as Object, ByVal ValueToReturn As String)

Затем создайте событие на дочернем элементе управления, когда ваши данные будут готовы к передаче.

RaiseEvent EVENTNAME(Me, txtBoxWithReturnValue.Text)

Как только вы это сделали, в родительской форме вы можете обрабатывать пользовательское событие. Для этого вам нужно добавить слушателя, чтобы «прослушать» событие, когда оно срабатывает:

AddHandler CONTROLNAME.EVENTNAME, AddressOf EVENTNAME

Затем вы можете написать процедуру для обработки этого нового события в родительской форме:

Private Sub FUNCTIONAME(ByVal sender As System.Object, ByVal ValueToReturn as String) Handles CONTROLNAME.EVENTNAME

'Code to handle data here

End Sub
1 голос
/ 29 июля 2010

Это самый простой ответ, никаких событий!

Ситуация: 1 MdiParent форма (Form1) и 2 дочерние формы управления (Control1Form и Control2Form). При запуске дочерние элементы управления создаются (control1 и control2) в MdiParent.

Form1 имеет метку в StatusStrip с именем StatusLabel. Control2 имеет кнопку с именем Button1

Цели: при нажатии кнопки Control2 Control2 записывает в заголовок control1 и в StatusLabel формы Form1

PARTIAL CODE

FORM1
Public Class Form1
Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
control1 = New Control1Form
control2 = New Control2Form
control1.MdiParent = Me
control1.Show()
control2.MdiParent = Me
control2.Show()
End Sub
End Class


CONTROL2FORM
Public Class Control2Form
Private Sub Button1_Click(ByVal sender As Object, ByVal e As EventArgs) Handles Button1.Click
'Title of Control1
CType(Me.ParentForm, Form1).control1.Text = "Title bar text"
'Status Strip Label
CType(Me.ParentForm, Form1).StatusLabel.Text = "Status Strip Text"
End Sub
End Class

И вуаля! Надеюсь, это поможет

0 голосов
/ 09 мая 2015

Я хотел бы добавить немного другой ответ, который работал для меня просто замечательно.

Следующие из ответа выше работали для меня отлично, пока я делал какие-либо изменения кода в родительском MDI. Когда я вставил эквивалент form1.MDIparent = me, все не удалось. Так что я оставил этот шаг.

Форма Form1 ниже должна быть именем родительской формы MDI, которую вы используете. Тогда это работает в моей среде, просто отлично подходит для передачи переменных родительскому элементу или использования других функций родительского элемента.

Перед этим у меня была проблема с ребенком, звонящим другому родителю, у которого были все пустые поля !!

CType(Me.ParentForm, Form1).control1.Text = "Title bar text"
'Status Strip Label
CType(Me.ParentForm, Form1).StatusLabel.Text = "Status Strip Text"

CType(Me.parentForm, Form1).variableDefinedinParentString = "abc" 'passing a variable

CType(Me.parentForm, Form1).subroutineLOCATEDinPARENT() 'Calling a subroutine in the parent

Может быть, это поможет некоторым другим. Я надеюсь на это!

0 голосов
/ 10 июля 2009

В VB.NET вы можете использовать пространства имен [My]. My.Forms. [Название вашей MDI-формы], так что ... если бы ваша основная форма называлась MdiMain, вы могли бы сделать что-то вроде этого.

My.Forms.MdiMain.lblStatus = "X"

Все мои дочерние формы наследуют один и тот же базовый класс, и у этого класса просто есть свойство, которое возвращает My.Forms.MdiMain. Я назвал это MdiParentForm. Таким образом, я могу просто сказать Me.MdiParentForm в любой форме и bam ... это родитель. (Меньше печатать)

0 голосов
/ 19 февраля 2009

Ответ Джона - хотя и весьма полезный - неполон. А недостающая часть может вызвать замешательство у новичков, таких как я.

Вместо того, чтобы затемнять addForm, как я делал изначально, нужно создать экземпляр addForm на уровне класса с помощью ключевого слова WithEvents, а затем использовать этот экземпляр для загрузки формы и обработчика событий.

Private WithEvents oneAddForm As New addForm //create a new instance of addForm

Private Sub addButton_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles addButton.Click
    oneAddForm.MdiParent = Me
    oneAddForm.Show()
End Sub
//using this instance to load the form...

Private Sub updateStatus(ByVal sender As System.Object, ByVal contactName As String) Handles oneAddForm.addSuccess
    statusLabel.Text = contactName & " has been added to your contact list."
End Sub
//...and to put in the event handler

Но это приводит к исключению "Не удается получить доступ к удаленному объекту ..." при попытке загрузить форму oneAddForm после ее закрытия один раз.

0 голосов
/ 19 февраля 2009

Создайте класс контроллера в MDI и передайте его в качестве параметра в дочернюю форму. Когда перед Me.Close () назначить список контактов для свойства на контроллере.

Вам необходимо разделить ваши данные и графический интерфейс. Для получения дополнительной информации о модели Model-View-Controller перейдите здесь .

...