Dizapp |
Отправлено: 22.05.2006, 16:09 |
|
Ученик-кочегар
Группа: Участник
Сообщений: 7
|
Созадю динамически трекбары:
CODE |
for(int i=0,di=0;i<Form3->selc;i++)
{
TTrackBar *trk=new TTrackBar(Form7);
trk->LineSize=1;
trk->Left=160;
trk->Top=40+di;
trk->Width=400;
trk->Height=30;
trk->Parent=Form7;
trk->Max=100;
trk->Min=0;
trk->Frequency=1;
trk->Position=0;
trk->SelEnd=0;
trk->SelStart=0;
trk->Visible=true;
trk->Enabled=true;
trk->OnChange=Form7->MyTrackChange;
di+=40;
}
void __fastcall TForm7::MyTrackChange(TObject *Sender)
{
TPos=((TTrackBar*)Sender)->Position;
Panel1->Caption="текущее значение"+(AnsiString)TPos;
}
|
Мне нужно подсчитывать суммарное значение ото всех трекбаров, различать каждый из них для записи этих значений в БД. Не могу сообразить как это сделать.. |
|
olegenty |
Отправлено: 23.05.2006, 12:23 |
|
Ветеран
Группа: Модератор
Сообщений: 2412
|
создай map < AnsiString, TTrackBar* const>, где в AnsiString суй имя родителя, либо, если родитель может быть и один, то создай map с индексом int: map < int, TTrackBar* const>. для подсчёта примени for_each. если так кажется сложным, то в случае индекса int можно воспользоваться vector < TTrackBar* const>, тогда можно просуммировать простым
CODE |
vector <TTrackBar* const> TrackBars;
... // заполняешь вектор
int VectorSize = TrackBars.size();
for (int i = 0; i < VectorSize; i++)
{
... // тут подсчёт, с доступом по индексу: TrackBars[i]->...
}
|
|
|
Grigoriy |
Отправлено: 23.05.2006, 15:14 |
|
Мастер участка
Группа: Участник
Сообщений: 381
|
QUOTE (Dizapp @ 22/05/2006, 16:09) | Созадю динамически трекбары:
CODE |
for(int i=0,di=0;i<Form3->selc;i++)
{
TTrackBar *trk=new TTrackBar(Form7);
trk->LineSize=1;
trk->Left=160;
//-----*******--------*--------*****
trk->Enabled=true;
trk->OnChange=Form7->MyTrackChange;
di+=40;
}
|
|
Кстати, код этот бессмысленный.
И не потому что предложенный olegenty код более удобен, если знаешь класс вектора.
Просто потому, что одной и той же указательной переменной trk несколько раз подряд присваивается адрес все новых и новых областей памяти. В результате вы теряете адреса блоков памяти, выделенных ОС для вашей программы, кроме последнего, который будет в последней итерации цикла сохранен в trk.
Если вы хотите динамически создать несколько блоков памяти (я имею в виду общий случай), то вам нужно будет организовать массив указателей. А сделать это можно либо самостоятельно, либо с помощью класса вектора.
Вот пример без применения вектора.
CODE |
int i,di,gf;
TTrackBar** trk;
trk = new TTrackBar* [9];//Здесь можно задавать любое целое положительное число
for(int i=0,di=0;i<gf;i++)
{
trk[i]->LineSize=1;
trk[i]->Left=160;
trk[i]->Top=40+di;
trk[i]->Width=400;
trk[i]->Height=30;
trk[i]->Parent=Form1;
trk[i]->Max=100;
trk[i]->Min=0;
trk[i]->Frequency=1;
trk[i]->Position=0;
trk[i]->SelEnd=0;
trk[i]->SelStart=0;
trk[i]->Visible=true;
trk[i]->Enabled=true;
di+=40;
}
|
|
|
Guest |
Отправлено: 23.05.2006, 16:40 |
|
Не зарегистрирован
|
QUOTE |
Просто потому, что одной и той же указательной переменной trk несколько раз подряд присваивается адрес все новых и новых областей памяти. В результате вы теряете адреса блоков памяти, выделенных ОС для вашей программы, кроме последнего, который будет в последней итерации цикла сохранен в trk.
|
CODE |
__fastcall virtual TTrackBar(Classes::TComponent* AOwner);
When one component owns another, the memory for the owned component is freed when its owner's memory is freed.
|
>кроме последнего...
Кстати, и последний так же недоступен, как и предыдущие, так как после выхода из цикла переменная trk не определена. |
|
exp |
Отправлено: 26.05.2006, 22:28 |
|
Мастер участка
Группа: Участник
Сообщений: 304
|
2Guest:
К чему поправка, непонятно. Grigory всё точно написал. Вчитайтесь и отметьте для себя, что мы теряем НЕ ПАМЯТЬ, а АДРЕСА ПАМЯТИ. Приведенную Вами цитату из хелпа все и так знают.
|
|
Dizapp |
Отправлено: 29.05.2006, 15:29 |
|
Ученик-кочегар
Группа: Участник
Сообщений: 7
|
Спасибо всем!! Все получилосьCODE |
typedef DynamicArray< TTrackBar* > TrackDinam;
TrackDinam s_array;
s_array.set_length(Form3->selc);
for (int i=0,di=0; i<s_array.Length; i++)
{
s_array[i]=new TTrackBar(Form7);
****************
s_array[i]->Visible=true;
s_array[i]->Enabled=true;
s_array[i]->OnChange=Form7->MyTrackChange;
di+=40;
}
***********
void __fastcall TForm7::MyTrackChange(TObject *Sender)
{
Panel3->Caption="позиция параметра="+(AnsiString)((TTrackBar*)Sender)->Position;
Summa=0;
for(int i=0;i<Form19->s_array.Length;i++)
{
Summa+=Form19->s_array[i]->Position;
}
Panel2->Caption="текущая сумма="+(AnsiString)Summa;
}
|
вот теперь у меня другая проблема) У меня в форме, где эти треки создаются сверху есть панель(Panel3), в которой пишется текущая позиция каждого трека. А когда много треков, то приходится прокручивать форму и панель тоже прокручивается. Как бы сделать так чтобы она (панель) не прокручивалась, а была всегда сверху? |
|
Shagg |
Отправлено: 07.06.2006, 13:58 |
|
Дежурный стрелочник
Группа: Участник
Сообщений: 69
|
В принципе можно в цикле перебрать все контролу формы:
CODE |
TControl *Control;
int sum = 0;
for (int i=0; i<Form1->ControlCount; i++)
{
Control = Form1->Controls[i];
if (Control->ClassNameIs("TTrackBar"))
sum += dynamic_cast<TTrackBar*>(Control)->Position;
}
|
или, если трэкбары у тебя не только на форме, но и на панельках всяких, можно сохранить в массиве их имена и перебирать по именам:
CODE | TControl *Control = Form1->FindChildControl(ControlName) |
а использование вектора трэкбаров, по моему, это просто не позволительное расточительство памяти |
|
Guest |
Отправлено: 07.06.2006, 15:03 |
|
Не зарегистрирован
|
QUOTE (exp @ 26/05/2006, 22:28) | 2Guest:
К чему поправка, непонятно. Grigory всё точно написал. Вчитайтесь и отметьте для себя, что мы теряем НЕ ПАМЯТЬ, а АДРЕСА ПАМЯТИ. Приведенную Вами цитату из хелпа все и так знают. |
2exp
К тому, что Grigoriy писал "Кстати, код этот бессмысленный".
Отнюдь. Указетели на блоки (адреса) мы то-же не теряем, они накапливаются в паренте. Кстати этим воспользовался Shagg.
(Это я потерял ваш пост , поэтому так поздно отвечаю) |
|