Architecture réception UDP => Freeze IHM
Bonjour,
J'ai une classe permettant de recevoir des messages UDP (dans des backgroundworker), et de faire le décodage de ces messages à l'aide d'un dictionnaire définissant ces messages.
Par la suite, les données sont affichées sur l'IHM à l'aide de Binding. Cette méthode fonctionne, mais lorsque je reçois énormément de données sur un court laps de temps, le temps de décodage freeze mon IHM.
Pouvez-vous me donnez une analyse critique de ma solution actuelle et/ou me proposer des axes d'amélioration ?
Code:
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 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102
|
private byte[] m_data;
/// <summary>
/// Background worker de récupération des messages
/// de la liaison ethernet UDP 1
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void bw1_DoWork(object sender, DoWorkEventArgs e)
{
BackgroundWorker worker = sender as BackgroundWorker;
while (true)
{
if ((worker.CancellationPending == true))
{
e.Cancel = true;
break;
}
else
{
comEth1.Ret(out m_data1); // récupération du message
m_bw1.ReportProgress(0, m_data1);
}
}
}
/// <summary>
/// Lors d'un changement dans le background worker 1
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void bw1_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
lock (lockData)
{
// On renvoi les données
Data = (byte[])e.UserState;
}
}
/// <summary>
/// Background worker de récupération des messages
/// de la liaison ethernet UDP 2
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void bw2_DoWork(object sender, DoWorkEventArgs e)
{
BackgroundWorker worker = sender as BackgroundWorker;
while (true)
{
if ((worker.CancellationPending == true))
{
e.Cancel = true;
break;
}
else
{
comEth2.Ret(out m_data2); // récupération du message
m_bw2.ReportProgress(0, m_data2);
}
}
}
/// <summary>
/// Lors d'un changement dans le background worker 2
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void bw2_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
lock (lockData)
{
// On renvoi les données
Data = (byte[])e.UserState;
}
}
/// <summary>
/// Evénement sur la variable "Data" (des progresschanged) lorsque ses données changent
/// Reception des messages : Cette fonction se lance à chaque réception d'un message
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void Data_changed(object sender, EventArgs e)
{
try
{
byte[] b = Data; // Mettre dans une variable, comme ça, si Data change de valeur en plein milieu de la fonction, pas de problème
if (b != null)
{
// Traitement (assez lourd) sur "b" en fonction de mon dictionnaire de message pour décoder mes messages et les mettre dans une classe des messages sur laquelle les bindings sont réalisées
}
}
catch
{
...
}
} |
Je pense mettre le traitement (Data_Changed) dans un backgroundworker mais je ne vois pas trop où le mettre. J'ai aussi regardé les fonctions avec async, mais je ne connais pas trop le fonctionnement.
Merci d'avance. :calim2:
Cordialement