Bonjour,
Je suis de retour sur le forum, mais comme j'ai oublié mon pseudo et l'adresse mail qui allait avec, je recrée un nouveau compte.
Mon problème:
En c++ avec Borland C++ Builder 6.0, j'utilise des Forms et des threads.
Et j'ai 2 questions (dont 1 pseudo réponse) :
- pourquoi les ShowMessage(); appelés depuis des threads font tout planter ?
J'avais fait une recherche à l'époque, et la solution est de ne pas les utiliser. Barbare, mais efficace.
- pourquoi lorsque l'on fait changer trop de chose sur un Form par des threads, il plante ? Ex : un Shape ou un Label qui va changer très souvent, surtout pour un Shape qui est de grande taille.
Pour le Label, je n'ai plus souvenir de quand date mon dernier problème (on oubli).
Pour le shape, j'ai réduit sa taille au mini, mais le bug n'est pas loin.
Mais aujourd'hui, j'ai le même problème avec un TabSheet.
Dans mon Form, j'ai un "gros" TabSheet (5 onglets, de la taille de la fenêtre, de la taille de l'écran). Si je clic d'onglets à onglets, tout va bien. Mais si ce changement se fait par le programme lui-même, le changement se fait, la fenêtre se fige et aucune exception n'est levée (j'ai des try/catch(Exception &exception)/catch(...) qui enregistrent les erreurs sur fichier).
Voici 2/3 extraits:
le fichier du projet:
1 2 3 4 5 6 7 8 9
|
WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR lpCmdLine, int)
{
try
{
Application->Initialize();
Application->CreateForm(__classid(TForm1), &Form1);
Application->Run();
... |
le fichier du Form avec le thread:
1 2 3 4 5 6 7
|
DWORD WINAPI ThreadOngletsPageControl(LPVOID lpParam)
{
...
case ONGLET_TEMPERATURES:
{ Form1->PageControl1->ActivePage = Form1->TabSheetTemperatures;
... |
La fonction qui crée le thread: (désolé, la mise en page a sauté)
1 2 3 4 5 6 7 8 9 10 11 12 13 14
|
tempoThreadOngletsPageControl = 800; //ms
lpThreadAttributes_unit_maison = NULL; //pointer to thread security attributes
dwStackSize_unit_maison = 0; //initial thread stack size, in bytes
lpStartAddress_unit_maison = &ThreadOngletsPageControl; //pointer to thread function
lpParameter_unit_maison = NULL; //argument for new thread
dwCreationFlags_unit_maison = NULL; //creation flags(CREATE_SUSPENDED...)
handleThreadOngletsPageControl = CreateThread( lpThreadAttributes_unit_maison,
dwStackSize_unit_maison,
lpStartAddress_unit_maison,
lpParameter_unit_maison,
dwCreationFlags_unit_maison, lpThreadId_unit_maison);
priorityThreadOngletsPageControl = THREAD_PRIORITY_NORMAL;//2 points below normal priority for the priority class.
if(!SetThreadPriority(handleThreadOngletsPageControl,priorityThreadOngletsPageControl)) |
Ce sont les lignes
Form1->PageControl1->ActivePage = Form1->TabSheetTemperatures;
qui font planter le programme.
Alors, dans mon désespoir, j'ai essayé de mettre ces changements dans une autre fonction et de faire appel à cette fonction depuis le thread (c'est con, mais on ne sait jamais)--> ça plante toujours.
J'ai ajouté des trucs comme
1 2 3 4 5 6 7
|
Form1->PageControl1->Update();
Form1->PageControl1->Repaint();
Form1->Update();
Form1->Repaint();
... |
Mais rien y fait.
Par contre, si je fais ce changement d'onglet depuis un clic sur un bouton (ou autre, mais sans passer par le thread), ça marche.
1 2 3 4
|
void __fastcall TForm1::Button27Click(TObject *Sender)
{ Form1->PageControl1->ActivePage = Form1->TabSheetTemperatures;
} |
Donc le problème vient bien du thread.
J'ai une petite idée, mais mes compétences se limitent ici : ne serait-ce pas un problème de mémoire du thread ?
En tout cas, dans le gestionnaire des tâches de Windows, j'utilise 0% du proc et pas grand chose en mémoire, et rien ne change après plantage.
Voila, à vous et merci.
Partager