2015-11-30 7 views
1

Я проверил похожие вопросы, но ответы не были связаны с моей проблемой.Почему событие срабатывает несколько раз на C#?

Я новичок в C#, и я использую окна.

ScreenShot

Как показано в скриншоте, у меня есть form1, UserControl1 и UserControl2.

  • Form1 имеет 2 кнопки (ShowUserControl1 & ShowUserControl2) и DataGridView.

  • UserControl1 имеет кнопку «AddRow» и текстовое поле.

  • UserControl2 ничего не имеет.

я нажимаю «ShowUserControl2» кнопку ShowUserControl2 появится, то я нажимаю кнопку «ShowUserControl1» ShowUserControl1 показывает вверх, а затем вводить текст в texBox в UserControl1 и нажмите кнопку «AddRow» новая строка добавляется и она отлично работает ,

Теперь проблема:

Когда я нажимаю «ShowUserControl1», а затем нажмите кнопку «ShowUserControl2», а затем нажмите кнопку «ShowUserControl1» снова и введите текст и нажмите «AddRow» один раз, 2 строки добавляются сразу в DataGridView. Нажмите «ShowUserControl1» 3 раза и нажмите «AddRow» один раз, сразу добавьте 3 строки и так далее.

Я думаю, что даже handeler в Form1 (HandleTheEvent) выполняется несколько раз, потому что я несколько раз нажимаю кнопку «ShowUserControl1» в результате переключения между UserControls. Как предотвратить многократное срабатывание четной формы? Пожалуйста помоги. Спасибо

Form1:

public partial class Form1 : Form 
{ 

    UserControl1 UC1 = new UserControl1(); 
    UserControl2 UC2 = new UserControl2(); 

    public Form1() 
    { 
     InitializeComponent(); 
    } 
    private void Form1_Load(object sender, EventArgs e) 
    { 
     //add user controls when form loads 
     Controls.Add(UC1); 
     Controls.Add(UC2); 
    } 


    private void ShowUC(Control value) // Show/hide User Controls 
    { 
     UC1.Visible = false; 
     UC2.Visible = false; 

     value.Visible = true; 

    } 


    public void HandleTheEvent(object sender, EventArgs e) //deal with the event 
    { 

     dataGridView1.Rows.Add(1, UC1.ReturnData, 3); 

    } 


    private void ShowUserControl1_Click(object sender, EventArgs e) 
    { 


     ShowUC(UC1); //show User Control1 
     UC1.UserControl1Event += new EventHandler(HandleTheEvent); 


    } 

    private void ShowUserControl2_Click(object sender, EventArgs e) 
    { 
     ShowUC(UC2); //show User Control2 
    } 
} 

UserControl1:

public partial class UserControl1 : UserControl 
{ 

    public event EventHandler UserControl1Event; 

    public UserControl1() 
    { 
     InitializeComponent(); 
    } 


    public string ReturnData 
    { 
     get { return textBox1.Text; } 

    } 
    private void AddRow_Click(object sender, EventArgs e) 
    { 
     UserControl1Event(this, e); 

    } 
} 
+4

Вы подписываетесь и не отписываясь. Попробуйте 'UC1.UserControl1Event - = new EventHandler (HandleTheEvent); UC1.UserControl1Event + = новый EventHandler (HandleTheEvent); ' –

+0

@ Giorgi Nakeuri. Не могли бы вы рассказать мне, где разместить этот код, который вы предоставили? Спасибо. – naouf

ответ

3

управление создается из них, но каждый раз, когда ShowUserControl1_Click называется, вы снова связывание события. Это означает, что событие UserControl1Event вызвано/вызвано. HandleTheEvent вызывается несколько раз. Событие - это список обработчиков.

private void ShowUserControl1_Click(object sender, EventArgs e) 
{ 


    ShowUC(UC1); //show User Control1 


    UC1.UserControl1Event += new EventHandler(HandleTheEvent); 


} 

Вы должны связать те события в конструкторе:

public partial class Form1 : Form 
{ 

    UserControl1 UC1 = new UserControl1(); 
    UserControl2 UC2 = new UserControl2(); 

    public Form1() 
    { 
     InitializeComponent(); 

     UC1.UserControl1Event += new EventHandler(HandleTheEvent); 
    } 

Не забудьте проверить, если UserControl1Event назначается здесь:

private void AddRow_Click(object sender, EventArgs e) 
{ 
    // here! 
    if(UserControl1Event != null) 
     UserControl1Event(this, e); 
} 
+0

@ Jeroen van Langen. твоя работала как волшебство :). Но у меня есть 2 вопроса: во-первых, могу ли я связать событие в форме load вместо конструктора? потому что в форме груз работал тоже.Второй вопрос: почему мы должны проверить, назначено ли событие, поскольку оно уже точно определено в конструкторе Form1. пожалуйста, советую мне. спасибо – naouf

+0

@naouf, (1) Вы можете привязывать событие повсюду, но вы должны связывать его только. Мне нравится связывать те внутри конструктора, потому что тогда я уверен, что он называется только одним. (2) Одна из вещей, которую вы хотели бы достичь, - это повторное использование вашего кода. На этот раз вы используете это событие, в следующий раз, когда вы не захотите использовать это событие. _ (например, вы не всегда обрабатываете событие mousedown для каждого элемента управления). Если вы не привязывали обработчик к событию, вы получите «NullReferenceException», когда вы стреляете/поднимаете/вызываете его. Это потому, что вы вызываете указатель 'NULL' в качестве делегата. –

+0

@ Jeroen ван Ланген. хорошо объяснил, большое спасибо. – naouf

Смежные вопросы