Форум программистов, компьютерный форум, киберфорум
C++ Builder
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.89/9: Рейтинг темы: голосов - 9, средняя оценка - 4.89
 Аватар для Access12
19 / 19 / 4
Регистрация: 28.04.2013
Сообщений: 139

Изменение положения и размера N-го количества компонентов

06.05.2015, 17:04. Показов 1853. Ответов 13
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Как всегда не уверен в названии темы
Доброго вечера.
Интересует следующий вопрос относительно компонента TPanel.
Имеется FormX, на FormX расположены компоненты Panel (в кол-ве 20-30шт), имеется возможность изменения размеров и положения компонента Panel1 (спойлер).
Вопрос: Можно ли, создать не знаю класс или еще чего, который будет охватывать все компоненты TPanel на FormX, при событии ,если Btn1,2,3....Btn30Click (PanelX=ButtonX,PanelY=ButtonY).
Пожалуйста :намекните,подтолкните,столкните,подкинь те,посоветуйте ... etc.

Кликните здесь для просмотра всего текста
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
void __fastcall TForm2::Panel1MouseDown(TObject *Sender, TMouseButton Button, TShiftState Shift,
          int X, int Y)
{
 
  if(Button != mbLeft) return;
 //Запомнить где
 viX0 = X;
 viY0 = Y;
 //Будем тащить
 fMove = true;
 //Переместить на передний план эту половинку
 ((TControl *)Sender)->BringToFront();
}
//---------------------------------------------------------------------------
void __fastcall TForm2::Panel1MouseMove(TObject *Sender, TShiftState Shift, int X,
          int Y)
{
if(fMove)
 {
  //Установить новые границы для того на кого нажали
  ((TPanel *)Sender)->
  SetBounds(
            ((TPanel *)Sender)->Left + X - viX0,
            ((TPanel *)Sender)->Top + Y - viY0,
            ((TPanel *)Sender)->Width,
            ((TPanel *)Sender)->Height);
 }
}
//---------------------------------------------------------------------------
void __fastcall TForm2::FormClick(TObject *Sender)
{
 SetWindowLong(Panel1->Handle,GWL_STYLE,GetWindowLong(Panel1->Handle,GWL_STYLE) & ~WS_SIZEBOX);
   Panel1->Width++;
   Panel1->Width--;
}
//---------------------------------------------------------------------------
void __fastcall TForm2::Panel1MouseUp(TObject *Sender, TMouseButton Button, TShiftState Shift,
          int X, int Y)
{
fMove = false;
}
//---------------------------------------------------------------------------
void __fastcall TForm2::Panel1DblClick(TObject *Sender)
{
SetWindowLong(Panel1->Handle,GWL_STYLE,GetWindowLong(Panel1->Handle,GWL_STYLE) | WS_SIZEBOX);
Panel1->Width++;
Panel1->Width--;
}

Всем вошедшим в тему добра, всем откликнувшимся в ней спасибо
0
cpp_developer
Эксперт
20123 / 5690 / 1417
Регистрация: 09.04.2010
Сообщений: 22,546
Блог
06.05.2015, 17:04
Ответы с готовыми решениями:

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

Создание собственного VCL компонента. Динамическое изменение количества колонок в зависимости от размера объекта
Доброго времени суток всем. Решил при создании своего компонента на основе TStringGrid инкапсулировать в него ряд свойств. Хочется...

Перемещение компонентов из положения A в положение B
Продолжаю вопросник Всем приятного вечера. Буду рад подсказкам, ссылка, да и любому посту по теме:) Описание: Имеется...

13
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33398 / 21508 / 8236
Регистрация: 22.10.2011
Сообщений: 36,906
Записей в блоге: 12
06.05.2015, 18:27
При чем тут Panel? Тебе нужен либо перехватчик TButton (аналогичный TStringGrid-овому, который был в прошлом сообщении, но для него надо переопределить метод Click, и по этому самому клику просто менять позицию соответствующей панели), либо написать обработчик нажатия для одной кнопки, и скопировать его во все остальные.
0
 Аватар для Access12
19 / 19 / 4
Регистрация: 28.04.2013
Сообщений: 139
06.05.2015, 18:45  [ТС]
Цитата Сообщение от volvo Посмотреть сообщение
При чем тут Panel? Тебе нужен либо перехватчик TButton (аналогичный TStringGrid-овому, который был в прошлом сообщении, но для него надо переопределить метод Click, и по этому самому клику просто менять позицию соответствующей панели), либо написать обработчик нажатия для одной кнопки, и скопировать его во все остальные.
Я создал проект, создал форму, разместил на ней панели, прописал код, теперь при выборе в меню "вкл констр", на Panel1 появляется ЧекБокс(ранее в примере Button), если снять галочку с ЧекБокс1->Panel1 становится доступной к буксировке(поставил галочку-эффект обратный). Я безусловно могу прописать подобный исход для каждой из панелей, но мне стало интересно, можно ли обойтись классом для компонента TPanel и вызывать нужные свойства Чекбоксами (if (...) {} без писанины в каждой панели по отдельности при кол-ве 20-30шт), тем самым ограничившись более коротким кодом (т.е один и тот же результат, при меньшем коде).

Просто я не совсем понимаю( недостаток знаний) к чему это приведет в моем случае
0
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33398 / 21508 / 8236
Регистрация: 22.10.2011
Сообщений: 36,906
Записей в блоге: 12
06.05.2015, 18:56
А, вон тебе чего надо. Перехватчики творят чудеса. Смотри:
Перед классом формы:
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
namespace MyPanel
{
    int viX0 = 0, viY0 = 0;
    bool fMove = false;
 
    class TPanel : public Extctrls::TPanel
    {
    protected:
        DYNAMIC void __fastcall MouseDown(System::Uitypes::TMouseButton Button,
            System::Classes::TShiftState Shift, int X, int Y)
        {
            if (Button != mbLeft)
                return;
            // Запомнить где
            viX0 = X;
            viY0 = Y;
            // Будем тащить
            fMove = true;
            // Переместить на передний план эту половинку
            BringToFront();
        }
 
        DYNAMIC void __fastcall MouseMove(System::Classes::TShiftState Shift,
            int X, int Y)
        {
            if (fMove)
            {
                // Установить новые границы для того на кого нажали
 
                SetBounds(Left + X - viX0, Top + Y - viY0, Width, Height);
            }
        }
 
        DYNAMIC void __fastcall MouseUp(System::Uitypes::TMouseButton Button,
            System::Classes::TShiftState Shift, int X, int Y)
        {
            fMove = false;
        }
 
        DYNAMIC void __fastcall DblClick(void)
        {
            ActivePanel = this;
            SetWindowLong(Handle, GWL_STYLE, GetWindowLong(Handle, GWL_STYLE) | WS_SIZEBOX);
            Width += 1;
            Width -= 1;
        }
 
    public:
        static TPanel *ActivePanel;
        __fastcall virtual TPanel(Classes::TComponent* AOwner)
            : Extctrls::TPanel(AOwner)
        {
        }
    };
    TPanel *TPanel::ActivePanel = 0;
}
#define TPanel MyPanel::TPanel
Собственно, на форме тебе останется только реализовать обработчик OnClick формы:
C++
1
2
3
4
5
6
7
void __fastcall TForm2::FormClick(TObject *Sender)
{
    SetWindowLong(TPanel::ActivePanel->Handle,GWL_STYLE,
        GetWindowLong(TPanel::ActivePanel->Handle, GWL_STYLE) & ~WS_SIZEBOX);
    TPanel::ActivePanel->Width++;
    TPanel::ActivePanel->Width--;
}
Всё, сколько бы не было панелек - все будут работать как задумывалось...

Можешь проверять любые чекбоксы, где нужно...
0
 Аватар для Access12
19 / 19 / 4
Регистрация: 28.04.2013
Сообщений: 139
06.05.2015, 19:12  [ТС]
Цитата Сообщение от volvo Посмотреть сообщение
Всё, сколько бы не было панелек - все будут работать как задумывалось...
Можешь проверять любые чекбоксы, где нужно...
Глаза загорелись,по коду именно то что искал,но на радостях, при компиле, попал под расстрел =)
Кликните здесь для просмотра всего текста
[C++ Error] Unit1.h(20): E2316 'Uitypes' is not a member of 'System'
[C++ Error] Unit1.h(20): E2293 ) expected
[C++ Error] Unit1.h(66): E2316 'ActivePanel' is not a member of 'TPanel'
[C++ Error] Unit1.cpp(20): E2451 Undefined symbol 'ActivePanel'
[C++ Error] Unit1.cpp(21): E2451 Undefined symbol 'ActivePanel'
[C++ Error] Unit1.cpp(22): E2451 Undefined symbol 'ActivePanel'
[C++ Error] Unit1.cpp(23): E2451 Undefined symbol 'ActivePanel'


В чем уже мой косяк? =\
Инклюды?
0
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33398 / 21508 / 8236
Регистрация: 22.10.2011
Сообщений: 36,906
Записей в блоге: 12
06.05.2015, 19:18
Это не твой косяк, а косяк твоего Билдера. Я делал в XE2, для более старых надо убрать все лишние System::Uitypes:: и System::Classes::

А вот с ActivePanel - не понял. Как это "не определен"? Он же описан: статическое поле класса, чего ему не нравится?
0
 Аватар для Access12
19 / 19 / 4
Регистрация: 28.04.2013
Сообщений: 139
06.05.2015, 19:35  [ТС]
Цитата Сообщение от volvo Посмотреть сообщение
А вот с ActivePanel - не понял. Как это "не определен"? Он же описан: статическое поле класса, чего ему не нравится?
Оказывается, если проследовать вашему совету ->
убрать все лишние System::Uitypes:: и System::Classes::
Он начинает лишь матюкаться, но компилится
Кликните здесь для просмотра всего текста
[C++ Warning] Unit1.h(65): W8022 '_fastcall TPanel::MouseDown(TObject *,TMouseButton,TShiftState,int,int)' hides virtual function '_fastcall TControl::MouseDown(TMouseButton,TShiftS tate,int,int)'
[C++ Warning] Unit1.h(65): W8022 '_fastcall TPanel::MouseMove(TObject *,TShiftState,int,int)' hides virtual function '_fastcall TControl::MouseMove(TShiftState,int,int) '
[C++ Warning] Unit1.h(65): W8022 '_fastcall TPanel::MouseUp(TObject *,TMouseButton,TShiftState,int,int)' hides virtual function '_fastcall TControl::MouseUp(TMouseButton,TShiftSta te,int,int)'


Добавлено через 10 минут
Размер-работает, Буксировка -нет, чтот я не так в класс вставил
0
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33398 / 21508 / 8236
Регистрация: 22.10.2011
Сообщений: 36,906
Записей в блоге: 12
06.05.2015, 19:45
Лучший ответ Сообщение было отмечено Access12 как решение

Решение

Разумеется... У тебя где-то типы не совпадают, как результат не отрабатывает перегруженный метод, его прототип должен совпадать идеально с прототипом базового метода. Просто открой Controls.hpp, и посмотри, какие параметры в этих трех проблемных методах используются. И точно те же самые запиши себе, как только hides virtual function уйдет - работоспособность восстановится...

Добавлено через 1 минуту
Стоп. Откуда у тебя TObject первым параметром взялся?
1
 Аватар для Access12
19 / 19 / 4
Регистрация: 28.04.2013
Сообщений: 139
06.05.2015, 19:49  [ТС]
Цитата Сообщение от volvo Посмотреть сообщение
Стоп. Откуда у тебя TObject первым параметром взялся?
А вот тут то и крот)) По вставлял их каким то боком, все, решилась проблема) Все работает.
Благодарю за оказанную помощь с вопросом

Не по теме
Можно ли уменьшить размер рамки при изменении размера панели?
0
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33398 / 21508 / 8236
Регистрация: 22.10.2011
Сообщений: 36,906
Записей в блоге: 12
07.05.2015, 13:20
Лучший ответ Сообщение было отмечено Access12 как решение

Решение

Access12, по поводу просьбы о добавлении двух CheckBox-ов, один из которых разрешает перетаскивание панели, второй - изменение ее размеров, я бы сделал их вообще членом класса MyPanel::TPanel, вот так:
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
74
75
76
77
namespace MyPanel
{
    int viX0 = 0, viY0 = 0;
    bool fMove = false;
 
    class TPanel : public Extctrls::TPanel
    {
    protected:
        DYNAMIC void __fastcall MouseDown(Controls::TMouseButton Button,
            Classes::TShiftState Shift, int X, int Y)
        {
            if (!cbxAllowMove->Checked || Button != mbLeft) // запрещено перемещение - выходим
                return;
            // Запомнить где
            viX0 = X;
            viY0 = Y;
            // Будем тащить
            fMove = true;
            // Переместить на передний план эту половинку
            BringToFront();
        }
 
        DYNAMIC void __fastcall MouseMove(Classes::TShiftState Shift,
            int X, int Y)
        {
            if (fMove)
            {
                // Установить новые границы для того на кого нажали
 
                SetBounds(Left + X - viX0, Top + Y - viY0, Width, Height);
            }
        }
 
        DYNAMIC void __fastcall MouseUp(Controls::TMouseButton Button,
            TShiftState Shift, int X, int Y)
        {
            fMove = false;
        }
 
        DYNAMIC void __fastcall DblClick(void)
        {
            if(cbxAllowResize->Checked) // только если разрешили 
            {
                ActivePanel = this;
                SetWindowLong(Handle, GWL_STYLE, GetWindowLong(Handle, GWL_STYLE) | WS_SIZEBOX);
                Width += 1;
                Width -= 1;
            }
        }
 
    public:
        static TPanel *ActivePanel;
 
        TCheckBox *cbxAllowResize; // Добавляем 2 чекбокса
        TCheckBox *cbxAllowMove;
 
        __fastcall virtual TPanel(Classes::TComponent* AOwner)
            : Extctrls::TPanel(AOwner)
        {
            cbxAllowResize = new TCheckBox(this); // создаем чекбокс, разрешающий изменение размеров панели
            cbxAllowResize->Parent = this;
            cbxAllowResize->Left = 10; // позицию подберешь сам
            cbxAllowResize->Top = 10;
            cbxAllowResize->Caption = "Resize";
            cbxAllowResize->Checked = false; // изначально все запрещено
 
            cbxAllowMove = new TCheckBox(this); // это для разрешения перетаскивания
            cbxAllowMove->Parent = this;
            cbxAllowMove->Left = 10;
            cbxAllowMove->Top = 30;
            cbxAllowMove->Caption = "Move";
            cbxAllowMove->Checked = false;
        }
    };
    TPanel *TPanel::ActivePanel = 0;
}
#define TPanel MyPanel::TPanel
Заодно обнаружился небольшой баг в обработчике OnClick формы:
C++
1
2
3
4
5
6
7
8
9
10
void __fastcall TForm1::FormClick(TObject *Sender)
{
    if (TPanel::ActivePanel) // Обязательно добавь, иначе (если кликнешь по форме до даблклика по панели) будет нехорошо
    {
        SetWindowLong(TPanel::ActivePanel->Handle, GWL_STYLE,
            GetWindowLong(TPanel::ActivePanel->Handle, GWL_STYLE) & ~WS_SIZEBOX);
        TPanel::ActivePanel->Width++;
        TPanel::ActivePanel->Width--;
    }
}
Вот и все...
1
 Аватар для Access12
19 / 19 / 4
Регистрация: 28.04.2013
Сообщений: 139
07.05.2015, 13:34  [ТС]
Цитата Сообщение от volvo Посмотреть сообщение
Access12, по поводу просьбы о добавлении
Именно то, о чем я и просил.
Премного благодарен, за столь скорый ответ
0
 Аватар для Access12
19 / 19 / 4
Регистрация: 28.04.2013
Сообщений: 139
07.05.2015, 14:12  [ТС]
И как всегда, ответ на вопрос, порождает несколько новых)))
Пытаюсь обратиться ко всем cbxAllowResize и cbxAllowMove, дабы при нажатии на кнопку ( в моем случае пункт меню), CheckBox'ы стали видимыми (в классе поставил значения для обоих вариантов Visible = false)
А вот как теперь показать,не знаю
C++
1
2
3
4
5
6
7
for(int i = 0; i < ComponentCount; i++)
 {
   TCheckBox *cbxAllowResize;
   cbxAllowResize = dynamic_cast<TCheckBox*>(Components[i]);
   if(cbxAllowResize->Visible == false) 
   cbxAllowResize -> Visible = true;
 }
Компилируются, но результата 0, хотя есть результат- окно ошибки
Хелп Добрый людь
0
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33398 / 21508 / 8236
Регистрация: 22.10.2011
Сообщений: 36,906
Записей в блоге: 12
07.05.2015, 14:23
Лучший ответ Сообщение было отмечено Access12 как решение

Решение

Надо искать панели, и на них уже показывать чекбоксы:
C++
1
2
3
4
5
6
7
8
    for (int i = 0; i < ComponentCount; i++)
    {
        TPanel *panel;
        if ((panel = dynamic_cast<TPanel*>(Components[i])) != 0)
        {
            panel->cbxAllowResize->Visible = true;
        }
    }
1
 Аватар для Access12
19 / 19 / 4
Регистрация: 28.04.2013
Сообщений: 139
07.05.2015, 14:27  [ТС]
Цитата Сообщение от volvo Посмотреть сообщение
Надо искать панели, и на них уже показывать чекбоксы:
Во блин, а вот 2ой раз я пытался искать cbxAllowResize, на панели.. но естественно по натыкал в код не куда надо))
Спасибо
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
raxper
Эксперт
30234 / 6612 / 1498
Регистрация: 28.12.2010
Сообщений: 21,154
Блог
07.05.2015, 14:27
Помогаю со студенческими работами здесь

Изменение размера\положения кнопок при resize формы
Всем привет! На форме 9 кнопок, 6 одного и 3 другого размера, пытаюсь изменять их размер\положение при изменении размера формы, но видимо...

Изменение размера компонентов пользователем
Доброго времени суток. Возник такой вопрос: можно ли как-то реализовать изменение размеров компонента пользователем? Чтобы, например,...

Изменение размера компонентов Swing
Приветствую Всех форумчан. Возник интересный вопрос, как динамически изменить размер любого компонента добавленного в jPanel. К примеру,...

Изменение размера видимых компонентов
Всем доброго времени суток! Вопрос, собственно такой: Есть ли в дельфи компоненты (кроме формы), размеры которых можно менять мышкой...

Растяжение окна формы и изменение размера компонентов
Есть значит вот такая вот программа - http://www.mediafire.com/download.php?vmynnyhgrgj Там тянется только listbox, тот что слева,...


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

Или воспользуйтесь поиском по форуму:
14
Ответ Создать тему
Новые блоги и статьи
SDL3 для Desktop (MinGW): Создаём пустое окно с нуля для 2D-графики на SDL3, Си и C++
8Observer8 10.03.2026
Содержание блога Финальные проекты на Си и на C++: hello-sdl3-c. zip hello-sdl3-cpp. zip Результат:
Установка CMake и MinGW 13.1 для сборки С и C++ приложений из консоли и из Qt Creator в EXE
8Observer8 10.03.2026
Содержание блога MinGW - это коллекция инструментов для сборки приложений в EXE. CMake - это система сборки приложений. Здесь описаны базовые шаги для старта программирования с помощью CMake и. . .
Как дизайн сайта влияет на конверсию: 7 решений, которые реально повышают заявки
Neotwalker 08.03.2026
Многие до сих пор воспринимают дизайн сайта как “красивую оболочку”. На практике всё иначе: дизайн напрямую влияет на то, оставит человек заявку или уйдёт через несколько секунд. Даже если у вас. . .
Модульная разработка через nuget packages
DevAlt 07.03.2026
Сложившийся в . Net-среде способ разработки чаще всего предполагает монорепозиторий в котором находятся все исходники. При создании нового решения, мы просто добавляем нужные проекты и имеем. . .
Модульный подход на примере F#
DevAlt 06.03.2026
В блоге дяди Боба наткнулся на такое определение: В этой книге («Подход, основанный на вариантах использования») Ивар утверждает, что архитектура программного обеспечения — это структуры,. . .
Управление камерой с помощью скрипта OrbitControls.js на Three.js: Вращение, зум и панорамирование
8Observer8 05.03.2026
Содержание блога Финальная демка в браузере работает на Desktop и мобильных браузерах. Итоговый код: orbit-controls-threejs-js. zip. Сканируйте QR-код на мобильном. Вращайте камеру одним пальцем,. . .
SDL3 для Web (WebAssembly): Синхронизация спрайтов SDL3 и тел Box2D
8Observer8 04.03.2026
Содержание блога Финальная демка в браузере. Итоговый код: finish-sync-physics-sprites-sdl3-c. zip На первой гифке отладочные линии отключены, а на второй включены:. . .
SDL3 для Web (WebAssembly): Идентификация объектов на Box2D v3 - использование userData и событий коллизий
8Observer8 02.03.2026
Содержание блога Финальная демка в браузере. Итоговый код: finish-collision-events-sdl3-c. zip Сканируйте QR-код на мобильном и вы увидите, что появится джойстик для управления главным героем. . . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru