Прослушивание событий в основной форме из другой формы в C # - PullRequest
2 голосов
/ 04 марта 2009

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

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

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

Как бы я это сделал?

Вот пример кода. Я хочу получить информацию из обработчика событий the_timer_Tick для обновления каждого экземпляра SecondaryForm.

public partial class Form1 : Form
{
    Timer the_timer = new Timer();
    public Form1()
    {
        InitializeComponent();
    }

    private void button1_Click(object sender, EventArgs e)
    {
        the_timer.Tick += new EventHandler(the_timer_Tick);
        the_timer.Interval = 2000;
        the_timer.Enabled = true;
    }

    void the_timer_Tick(object sender, EventArgs e)
    {
        // I would like code in here to update all instances of SecondaryForm
        // that happen to be open now.
        MessageBox.Show("Timer ticked");
    }

    private void stop_timer_button_Click(object sender, EventArgs e)
    {
        the_timer.Enabled = false;
    }

    private void start_form_button_Click(object sender, EventArgs e)
    {
        SecondaryForm new_form = new SecondaryForm();
        new_form.Show();
    }
}

Ответы [ 3 ]

5 голосов
/ 04 марта 2009
class SecondForm
{
  private FirstForm firstForm;

  public SecondForm()
  {
    InitializeComponent();
    // this means unregistering on form closing, uncomment if is necessary (anonymous delegate)
    //this.Form_Closing += delegate { firstForm.SomeEvent -= SecondForm_SomeMethod; };
  }

  public SecondaryForm(FirstForm form) : this()
  {
    this.firstForm = form; 
    firstForm.Timer.Tick += new EventHandler(Timer_Tick);
  }

  // make it public in case of external event handlers registration
  private void Timer_Tick(object sender, EventArgs e)
  {
    // now you can access firstForm or it's timer here
  }
}

class FirstForm
{
  public Timer Timer
  {
    get
    {
      return this.the_timerl
    }
  }

  public FirstForm()
  {
    InitializeComponent();
  }

  private void Button_Click(object sender, EventArgs e)
  {
    new SecondForm(this).ShowDialog(); // in case of internal event handlers registration (in constructor)
    // or
    SecondForm secondForm = new SecondForm(this);
    the_timer.Tick += new EventHandler(secondForm.Timer_tick); // that method must be public
  }
2 голосов
/ 04 марта 2009

Рассмотрите возможность использования слабосвязанных событий. Это позволит вам соединить классы таким образом, чтобы им никогда не приходилось напрямую узнавать друг друга. Блок приложения Unity поставляется с расширением EventBroker , которое делает это очень простым.

Вот немного лизнуть сахара:

public static class EVENTS
{
    public const string UPDATE_TICKED = "event://Form1/Ticked";
}

public partial class Form1 : Form
{
    [Publishes(EVENTS.UPDATE_TICKED)]
    public event EventHandler Ticked; 

    void the_timer_Tick(object sender, EventArgs e)
    {
        // I would like code in here to update all instances of SecondaryForm
        // that happen to be open now.
        MessageBox.Show("Timer ticked");
        OnTicked();
    }

    protected virtual void OnTicked()
    {
        if (Ticked == null) return;
        Ticked(this, e);
    }
}

public partial class SecondaryForm : Form
{
    [SubscribesTo(EVENTS.UPDATE_TICKED)]
    private void Form1_Ticked(object sender, EventHandler e)
    {
        // code to handle tick in SecondaryForm
    }
}

Теперь, если вы сконструируете оба этих класса с использованием Unity, они будут автоматически соединены вместе.

Обновление

Более новые решения используют шину сообщений для обработки слабосвязанных событий. См. http://masstransit -project.com / или http://nimbusapi.github.io/ в качестве примеров.

0 голосов
/ 04 марта 2009

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

private void start_form_button_Click(object sender, EventArgs e)
{
    SecondaryForm new_form = new SecondaryForm(this);
    new_form.Show();
}

В SecondaryForm.cs:

public SecondaryForm(ISomeView parentView)
{
    parentView.SomeEvent += .....
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...