Форум программистов, компьютерный форум, киберфорум
C# Windows Forms
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
 
Рейтинг 4.82/11: Рейтинг темы: голосов - 11, средняя оценка - 4.82
0 / 0 / 0
Регистрация: 19.07.2016
Сообщений: 15

Как избежать кучи копи-паста кода, когда много кнопок с одинаковыми действиями?

19.07.2016, 16:58. Показов 2532. Ответов 20
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Добрый день!
Есть форма, на ней много текст-боксов и кнопок.
Рядом с каждым текст-боксом есть кнопка, которая выполняет для своего текст-бокса функцию увеличения значения в текс-боксе на 1.
C#
1
2
3
4
5
6
private void button2_Click(object sender, EventArgs e)
        {
            int numb = Convert.ToInt16(textBox2.Text);
            numb++;
            textBox2.Text = numb.ToString();
        }
Как сделать так, что бы при нажатии кнопки, как в примере выше, textBox2 менялся на textBox3, 4, и т.д.. в зависимости от того какая кнопка?

например есть пара textBox2 и button2, нужен универсальный код для кнопки button, который будет работать в паре textBox3 и button3, textBox4 и button4 и т.д.

Спасибо!
Я только начал разбираться с программированием, мало что осознаю в ООП, поэтому если можно, разъясните в ответе что за что отвечает плиз.
Заранее благодарен!
0
Лучшие ответы (1)
Programming
Эксперт
39485 / 9562 / 3019
Регистрация: 12.04.2006
Сообщений: 41,671
Блог
19.07.2016, 16:58
Ответы с готовыми решениями:

Упрощение кода в случае, когда кнопок много, а процедуры у них схожи
А вот ещё задачка: имеется с десяток кнопок Button1...Button 10 Для всех нажатий код примерно одинаков. Как можно описать ОДНО событие,...

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

Как определить какая кнопка из кучи кнопок нажата?
Здравствуйте! Не хотелось бы вешать код на каждую кнопку, если их допустим 480 =)) Как можно все объединить, допустим так: Private...

20
 Аватар для Злобный Зайц
14 / 14 / 1
Регистрация: 21.10.2010
Сообщений: 462
19.07.2016, 17:18
Почему не использовать вместо этого NumericUpDown?
0
0 / 0 / 0
Регистрация: 19.07.2016
Сообщений: 15
19.07.2016, 17:27  [ТС]
Потому что я не могу понять как менять его внешний вид, пытался разобраться, читая на эту тему, но очень сложно пока для понимания....
А потом такой же код, как я спрашиваю, хотел бы применить и к возможности изменения координат этой пары, относительно
изменения положения других элементов, иначе там одинакового кода получается целая гора, а отличается в итоге только в имени элемента(разные цифры). Вот и пришла в голову мысль.... Читая про С#, видел слово коллекции, мало чот понял из описания, но вроде как можно все сделать как мне надо. Только вот разобраться одному сложно((
0
 Аватар для Злобный Зайц
14 / 14 / 1
Регистрация: 21.10.2010
Сообщений: 462
19.07.2016, 17:32
Тогда можно создать UserControl, содержащий текстбокс и кнопку и добавлять его сколько угодно раз на форму.
0
0 / 0 / 0
Регистрация: 19.07.2016
Сообщений: 15
19.07.2016, 17:35  [ТС]
это в VS можно сделать? или код писать?
0
 Аватар для Злобный Зайц
14 / 14 / 1
Регистрация: 21.10.2010
Сообщений: 462
19.07.2016, 17:41
Можно и программно создать, можно и в дизайнере.
Правый клик на имени проекта-Добавить/Создать элемент/Пользовательский элемент управления. Дальше - в дизайнере можно натащить туда любых стандартных контролов и прописать им обработчики событий.
0
0 / 0 / 0
Регистрация: 19.07.2016
Сообщений: 15
19.07.2016, 17:48  [ТС]
Накидал, написал, что дальше надо сделать? как-то собрать его и он появится в общем списке??
0
 Аватар для Злобный Зайц
14 / 14 / 1
Регистрация: 21.10.2010
Сообщений: 462
19.07.2016, 17:50
Да, надо его откомпилировать и добавить в список. Давненько я это делал, щас буду слишком долго вспоминать. Лучше погугли - совсем не сложно.
0
0 / 0 / 0
Регистрация: 19.07.2016
Сообщений: 15
19.07.2016, 17:52  [ТС]
Спасибо, попробую!
0
 Аватар для Злобный Зайц
14 / 14 / 1
Регистрация: 21.10.2010
Сообщений: 462
19.07.2016, 18:01
Можно и в коде конструктора формы написать:
C#
1
2
3
MyUserControl myUserControl=new MyUserControl();
Controls.Add(myUserControl);
myUserControl.Location=new Point(<координаты X, Y>);
Тогда не нужно создавать и компилировать Windows Control Library и добавлять в тулбокс.
1
 Аватар для Людвиг Бодмер
378 / 375 / 213
Регистрация: 29.03.2013
Сообщений: 867
19.07.2016, 18:15
Yury_, мне в голову пришел вот какой велосипед: для всех пар кнопка-текстбокс задаете одинаковый номер в свойстве Tag , то есть для первой кнопки Tag=1 и для соответствующего ей текстбокса Tag=1 , для следующей кнопки и текстбокса Tag=2 и т.д. Добавляете для всех кнопок один и тот же обработчик события Click , назовем его допустим button_Click . И вот такой код обработчика, который наверняка можно улучшить:
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
private void button_Click(object sender, EventArgs e)
        {
            foreach (Control c in Controls)
            {
                if (c is TextBox)
                {
                    if (c.Tag == ((Button)sender).Tag)
                    {
                        numb = Convert.ToInt16(c.Text);
                        numb++;
                        c.Text = numb.ToString();
                    }
                }
            }
        }
1
Строитель
 Аватар для Nord790
889 / 556 / 194
Регистрация: 01.04.2014
Сообщений: 610
Записей в блоге: 6
20.07.2016, 01:00
Возьмём вставим на форму Panel (PanelControls) и на нём разместим все textBox'ы и button'ы, а дальше сделает всё этот код.
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
private void MainWindow_Load(object sender, EventArgs e)
{
    foreach(object obj in PanelControls.Controls)
        if (obj.GetType() == typeof(Button))
            ((Button)obj)
                .Click += ButtonElement_Click;
}
 
private void ButtonElement_Click(object sender, EventArgs e)
{
    string nameTextBox = ((Button)sender).Name.Replace("button","textBox");
    if ( PanelControls.Controls.ContainsKey(nameTextBox))
    {
        try
        {
                        TextBox txtBox = (TextBox)(PanelControls.Controls[nameTextBox]);
            txtBox.Text = (Convert.ToInt32(txtBox.Text) + 1).ToString();
        }
        catch {return;}
    }
}
Здесь главное что бы были определённо названные textBox'ы и button'ы, к примеру textBox1 и button1 или txt1 и btn1 и т.д.
1
0 / 0 / 0
Регистрация: 19.07.2016
Сообщений: 15
20.07.2016, 15:19  [ТС]
Спасибо, сейчас буду пробовать, а можете пояснения по коду написать?
начиная с foreach, спасибо!

Создание userControl кстати не получилось, накидал кнопки, написал их обработчики, перестроил решение, control появился, но на нем ничего не отображается, в чем может быть дело?

Добавлено через 43 минуты
Возникла ошибка:
Необработанное исключение типа "System.NullReferenceException" в WindowsFormsApplication2.exe
Дополнительные сведения: Ссылка на объект не указывает на экземпляр объекта.
Код:
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
namespace WindowsFormsApplication2
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }
 
        private void Form1_Load(object sender, EventArgs e)
        {
            foreach (object obj in PanelControls.Controls)
                if (obj.GetType() == typeof(Button))
                    ((Button)obj)
                        .Click += button1_Click;
        }
 
        private void button1_Click(object sender, EventArgs e)
        {
            string nameTextBox = ((Button)sender).Name.Replace("button", "textBox");
            if (panel1.Controls.ContainsKey(nameTextBox))
            {
                try
                {
                    TextBox txtBox = (TextBox)(panel1.Controls[nameTextBox]);
                    txtBox.Text = (Convert.ToInt32(txtBox.Text) + 1).ToString();
                }
                catch { return; }
            }
        }
 
        private class PanelControls
        {
            public static IEnumerable<object> Controls { get; internal set; }
        }
    }
}
Что не так?
Пишет про то, что ControlPanel (строка 12) возможно имеет значение null

Добавлено через 6 минут
Можете пояснения по Вашему коду написать? Пожалуйста, про object и так далее....
0
Строитель
 Аватар для Nord790
889 / 556 / 194
Регистрация: 01.04.2014
Сообщений: 610
Записей в блоге: 6
20.07.2016, 15:21
PanelControls - это объект (Panel) на форме, а не класс
C#
1
private class PanelControls
Вложения
Тип файла: zip WindowsFormsApplication1.zip (49.5 Кб, 4 просмотров)
1
0 / 0 / 0
Регистрация: 19.07.2016
Сообщений: 15
20.07.2016, 16:14  [ТС]
Нашел в чем проблема, все работает!!!
только значение увеличивается не на 1, а на 2((
а во втором textBox все нормально

Добавлено через 41 минуту
А другая группа кнопок может по тому же принципу работать с этим же текст-боксом?
0
Строитель
 Аватар для Nord790
889 / 556 / 194
Регистрация: 01.04.2014
Сообщений: 610
Записей в блоге: 6
20.07.2016, 16:23
конечно, к примеру первая группа кнопок называют к примеру button1, 2 и т.д., а вторая группа btn1, 2 и т.д..
в коде есть момент где он просто переименовывает название
C#
1
string nameTextBox = ((Button)sender).Name.Replace("button", "textBox");
тебе главное поменять button на другое имя, главное чтобы оставалось последовательность чисел
0
0 / 0 / 0
Регистрация: 19.07.2016
Сообщений: 15
20.07.2016, 17:36  [ТС]
Nord790, Да, успел разобрать чуть раньше, спасибо. Один момент все-таки.
почему происходит перескакивание на 2???
Сделал вторые кнопки, которые уменьшают на -1, так там вообще теперь на 56 перескакивает!
Что делать?

Добавлено через 35 минут
и кнопки иногда зависимы друг от друга, т.е. пока не нажмешь первую, остальные не работают((((
0
Эксперт .NET
 Аватар для Rius
13084 / 7644 / 1670
Регистрация: 25.05.2015
Сообщений: 23,285
Записей в блоге: 14
20.07.2016, 18:24
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
using System;
using System.Collections.Generic;
using System.Windows.Forms;
 
namespace Yury_
{
    public partial class Form1 : Form
    {
        private Dictionary<Button, TextBox> mButtonTextBoxMap;
 
        public Form1()
        {
            InitializeComponent();
 
            this.mButtonTextBoxMap = new Dictionary<Button, TextBox>();
            this.mButtonTextBoxMap.Add(this.button1, this.textBox1);
            this.mButtonTextBoxMap.Add(this.button2, this.textBox2);
 
            foreach (var kvp in this.mButtonTextBoxMap)
            {
                kvp.Key.Click += this.onButton_Click;
            }
        }
 
        private void onButton_Click(object sender, EventArgs e)
        {
            if (this.mButtonTextBoxMap.ContainsKey(sender as Button))
            {
                TextBox tb = this.mButtonTextBoxMap[sender as Button];
                int numb = 0;
 
                if (int.TryParse(tb.Text, out numb))
                {
                    numb++;
                }
 
                tb.Text = numb.ToString();
            }
        }
    }
}
0
Эксперт .NET
 Аватар для Даценд
5878 / 4755 / 2939
Регистрация: 20.04.2015
Сообщений: 8,361
20.07.2016, 18:36
Или с помощью 2-х массивов:
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
private void Form1_Load(object sender, EventArgs e)
{
    Button[] btns = { button1, button2, button3, button4, button5 };
    TextBox[] tbxs = { textBox1, textBox2, textBox3, textBox4, textBox5 };
    foreach (Button btn in btns)
    {
        btn.Click += (sndr, arg) =>
        {
            int tbText;
            TextBox tb = tbxs[Array.IndexOf(btns, sndr)];
            if (int.TryParse(tb.Text, out tbText))
            {
                tbText++;
            }
            tb.Text = tbText.ToString();
        };
    }
}
0
Строитель
 Аватар для Nord790
889 / 556 / 194
Регистрация: 01.04.2014
Сообщений: 610
Записей в блоге: 6
20.07.2016, 23:57
Лучший ответ Сообщение было отмечено Yury_ как решение

Решение

Вот часть кода
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
 
namespace Project
{
    public partial class MainWindow : Form
    {
        public MainWindow()
        {
            InitializeComponent();
        }
 
        private void MainWindow_Load(object sender, EventArgs e)
        {
            //Перечисляем все элементы которые находятся на элементе panel1.
            foreach(object obj in panel1.Controls)
            {
                //Узнаём является ли значение obj типом Button.
                if (obj.GetType() == typeof(Button))
                {
                    var btn = ((Button)obj);
                    ///Узнаём что за кнопка "-" или "+".
                    ///Я делаю это через значение btn.Text.
                    ///Если кнопка является "+" или "-", то прикладываем событие Click.
                    if (btn.Text == "-" | btn.Text == "+")
                        btn.Click += Buttons_Click;
                }
            }
        }
 
        void Buttons_Click(object sender, EventArgs e)
        {
            //Это наш ID по которуму мы будем искать нужный нам textBox.
            string ID = ((Button)sender).Tag.ToString(); 
            TextBox txtBox = null;
 
            foreach (object obj in panel1.Controls)
                if (obj.GetType() == typeof(TextBox))
                    if (((TextBox)obj).Tag.ToString()  == ID)
                    { txtBox = ((TextBox)obj); break; }
            if (txtBox == null) return; // Если textBox не найден, завершаем событие.
 
            switch(((Button)sender).Text)
            {
                case "+":
                    try
                    {
                        txtBox.Text = (Convert.ToInt32(txtBox.Text) + 1).ToString();
                    }
                    catch
                    {
                        return;
                    }
                    break;
                case "-":
                    try
                    {
                        txtBox.Text = (Convert.ToInt32(txtBox.Text) - 1).ToString();
                    }
                    catch
                    {
                        return;
                    }
                    break;
            }
        }
    }
}
Вложения
Тип файла: zip Project.zip (60.2 Кб, 3 просмотров)
1
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
inter-admin
Эксперт
29715 / 6470 / 2152
Регистрация: 06.03.2009
Сообщений: 28,500
Блог
20.07.2016, 23:57
Помогаю со студенческими работами здесь

Как избежать попадания в фокус кнопок на форме при нажатии клавиш на клавиатуре?
На форме есть несколько полей Edit и кнопок BitBtn. у полей проставлены TabStop=true и в TabOrder порядковые номера обхода. У кнопок...

Как избежать тормозов в компьютере, когда происходит поиск информации на hdd?
здрасти) ..ребят а не подскажете как избежать тормозов в компе когда происходит поиск информации на hdd мож жесткий поменять иль программу...

Как выровнить много кнопок?
Ребят использую плагин «Shortcodes Ultimate» в wp. Но там кнопки с увеличением цифры (текста) растягиваются. Вот так:...

Как избежать дублирования кода?
Приветствую Вас уважаемые форумчане! Хочу обратиться к Вам за помощью. Возникли огромные пробелы в Java OOP , либо же я не до конца...

Как избежать дублирование кода ?
Ребят, подскажите, пожалуйста, верное направление. Прошу сильно не пинать. В окне есть 5 вкладок Tab с одинаковым контентом (все...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
20
Ответ Создать тему
Новые блоги и статьи
Использование SDL3-callbacks вместо функции main() на Android, Desktop и WebAssembly
8Observer8 24.01.2026
Если вы откроете примеры для начинающих на официальном репозитории SDL3 в папке: examples, то вы увидите, что все примеры используют следующие четыре обязательные функции, а привычная функция main(). . .
моя боль
iceja 24.01.2026
Выложила интерполяцию кубическими сплайнами www. iceja. net REST сервисы временно не работают, только через Web. Написала за 56 рабочих часов этот сайт с нуля. При помощи perplexity. ai PRO , при. . .
Модель сукцессии микоризы
anaschu 24.01.2026
Решили писать научную статью с неким РОманом
http://iceja.net/ математические сервисы
iceja 20.01.2026
Обновила свой сайт http:/ / iceja. net/ , приделала Fast Fourier Transform экстраполяцию сигналов. Однако предсказывает далеко не каждый сигнал (см ограничения http:/ / iceja. net/ fourier/ docs ). Также. . .
http://iceja.net/ сервер решения полиномов
iceja 18.01.2026
Выкатила http:/ / iceja. net/ сервер решения полиномов (находит действительные корни полиномов методом Штурма). На сайте документация по API, но скажу прямо VPS слабенький и 200 000 полиномов. . .
Расчёт переходных процессов в цепи постоянного тока
igorrr37 16.01.2026
/ * Дана цепь(не выше 3-го порядка) постоянного тока с элементами R, L, C, k(ключ), U, E, J. Программа находит переходные токи и напряжения на элементах схемы классическим методом(1 и 2 з-ны. . .
Восстановить юзерскрипты Greasemonkey из бэкапа браузера
damix 15.01.2026
Если восстановить из бэкапа профиль Firefox после переустановки винды, то список юзерскриптов в Greasemonkey будет пустым. Но восстановить их можно так. Для этого понадобится консольная утилита. . .
Сукцессия микоризы: основная теория в виде двух уравнений.
anaschu 11.01.2026
https:/ / rutube. ru/ video/ 7a537f578d808e67a3c6fd818a44a5c4/
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru