IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

C# Discussion :

Affichage signal audio en temps réel


Sujet :

C#

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre confirmé
    Inscrit en
    Octobre 2005
    Messages
    63
    Détails du profil
    Informations forums :
    Inscription : Octobre 2005
    Messages : 63
    Par défaut Affichage signal audio en temps réel
    Salut a tous,
    J'ai un soucis d'optimisation au niveau de l'affichage temps reel d'un signal audio.

    Dans mon application, je veux afficher 10 secondes d'un signal audio acquis à 16KHz. Ca fait donc 160 000 points à afficher. Le signal s'affiche par un defilement de gauche à droite (buffeur circulaire). Pour le moment j'ai deux methodes pour afficher mes courbes mais aucune ne me donne satisfaction.

    La première est la suivante:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    for (i = 0; i < this.Width - 1; i++)
      {
        g.DrawLine(P1, i, this.Height - 5 - (int)Math.Round((waveform1[(int)Math.Round(i / xS)] - maxmin1[1]) * yS), i + 1, this.Height - 5 - (int)Math.Round((waveform1[(int)Math.Round((i + 1) / xS)] - maxmin1[1]) * yS));
      }
    En gros, à chaque refresh, je dessine 160 000 / xS points sur toute la largeur this.Width de mon image bitmap dans laquelle j'affiche la courbe du signal. Le problème de cette methode c'est qu'en plus du scintillement du au refresh, j'ai un scintillement au niveau de la courbe elle meme. La raison étant qu'à chaque fois que je redessine la courbe en entier, le downsampling d'un facteur xS et le buffeur circulaire du signal font qu'une valeur acquise à t0 n'a pas la meme faleur entre l'affichage à t et l'affichage à t + 1.

    Et la seconde est celle-ci:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    for (i = 0; i < timeWindow - 1; i++)
      {
        g.DrawLine(P1, (int)Math.Round(i * xS), this.Height - 5 - (int)Math.Round((waveform1[i] - maxmin1[1]) * yS), (int)Math.Round((i + 1) * xS), this.Height - 5 - (int)Math.Round((waveform1[i + 1] - maxmin1[1]) * yS));
      }
    Cette fois, pas de downsampling, je dessine tous les points (timeWindow = 160 000), l'affichage est beaucoup plus stable car le signal acquis à t0 a la meme valeur entre 2 refresh consecutifs. Par contre, le refresh rate chute enormement à cause du nombre de points à dessiner.

    Quelqu'un aurait-il une solution pour un affichage stable et rapide?

    Merci de m'aider

  2. #2
    Membre chevronné
    Homme Profil pro
    Développeur .NET
    Inscrit en
    Février 2009
    Messages
    317
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 38
    Localisation : Belgique

    Informations professionnelles :
    Activité : Développeur .NET
    Secteur : Finance

    Informations forums :
    Inscription : Février 2009
    Messages : 317
    Par défaut
    Bonjour,

    Dans un premier temps, as tu besoin d'afficher l'entièreté de tes 160.000 points pour avoir un affichage convenable de ta courbe ?

  3. #3
    Expert confirmé

    Homme Profil pro
    Chef de projet NTIC
    Inscrit en
    Septembre 2006
    Messages
    3 580
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Chef de projet NTIC
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Septembre 2006
    Messages : 3 580
    Par défaut
    salut

    une solution simple à mettre en oeuvre:

    Tu dessines dans une bitmap... et au fur et à mesure que tu dois scroller,
    tu décales la bitmap et tu mets une deuxième bitmap que tu crées dynamiquement...

    En utilisant une telle technique, le premier "Draw" va prendre un peu de temps car tu vas créer et remplir ta bitmap, mais après, tu n'auras plus qu'à,
    soit rajouter des points à ta bitmap et la décaler vers la gauche, soit créer une deuxième bitmap collée à droite de la première et dans laquelle tu ajouteras les points...

    Si tu dois redessiner 160000 points à chaque fois, c sur que ca va un peu ramer...

    Une autre astuce est d'appeler DrawLines en passant le tableau des points calculés comme il faut car cela sera plus rapide que xx appels à DrawLine.

    De plus, calculer à chaque fois Math.Round(x) n'est pas pertinent.
    Une fois qu'un point a été calculé en Y, le x changera de -1 à chaque décalage vers la gauche, mais pas le Y.. donc, le recalculer à chaque fois est source de perte de temps importante...

  4. #4
    Membre confirmé
    Inscrit en
    Octobre 2005
    Messages
    63
    Détails du profil
    Informations forums :
    Inscription : Octobre 2005
    Messages : 63
    Par défaut
    Citation Envoyé par theMonz31 Voir le message
    salut

    une solution simple à mettre en oeuvre:

    Tu dessines dans une bitmap... et au fur et à mesure que tu dois scroller,
    tu décales la bitmap et tu mets une deuxième bitmap que tu crées dynamiquement...

    En utilisant une telle technique, le premier "Draw" va prendre un peu de temps car tu vas créer et remplir ta bitmap, mais après, tu n'auras plus qu'à,
    soit rajouter des points à ta bitmap et la décaler vers la gauche, soit créer une deuxième bitmap collée à droite de la première et dans laquelle tu ajouteras les points...

    Si tu dois redessiner 160000 points à chaque fois, c sur que ca va un peu ramer...

    Une autre astuce est d'appeler DrawLines en passant le tableau des points calculés comme il faut car cela sera plus rapide que xx appels à DrawLine.

    De plus, calculer à chaque fois Math.Round(x) n'est pas pertinent.
    Une fois qu'un point a été calculé en Y, le x changera de -1 à chaque décalage vers la gauche, mais pas le Y.. donc, le recalculer à chaque fois est source de perte de temps importante...
    Merci, je vais essayer de mettre tout ca en place.

  5. #5
    Membre confirmé
    Inscrit en
    Octobre 2005
    Messages
    63
    Détails du profil
    Informations forums :
    Inscription : Octobre 2005
    Messages : 63
    Par défaut
    Bon, j'ai essayé plusieurs choses avec plus ou moins de succès mais il y a un problème que je n'arrive pas à régler c'est le flickering du panel au refresh.

    Mon application est de type Windows Forms et j'utilise un custom panel pour afficher la courbe. J'ai copié le bout de code suivant dans le constructeur de mon panel pour essayer d'activer le double buffer mais ca n'a fait qu'empirer les choses (scintillement encore plus fort).

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    this.SetStyle(ControlStyles.DoubleBuffer |
                          ControlStyles.UserPaint |
                          ControlStyles.AllPaintingInWmPaint, true);
    this.UpdateStyles();
    Est ce que j'aurai plus de chance en passant en WPF?

  6. #6
    Expert confirmé

    Homme Profil pro
    Chef de projet NTIC
    Inscrit en
    Septembre 2006
    Messages
    3 580
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Chef de projet NTIC
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Septembre 2006
    Messages : 3 580
    Par défaut
    question bete:

    Le Paint de ton panel, ou est-il fait ?

    Dans la fonction OnPaint ou bien dans un "timer" maison ?

    Peut-etre que si tu "publies" ici le code de ton controle on pourra travailler dessus

  7. #7
    Inactif  
    Homme Profil pro
    Chef de projet NTIC
    Inscrit en
    Janvier 2007
    Messages
    6 604
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 64
    Localisation : France

    Informations professionnelles :
    Activité : Chef de projet NTIC

    Informations forums :
    Inscription : Janvier 2007
    Messages : 6 604
    Par défaut
    Citation Envoyé par Aeronia Voir le message
    Dans un premier temps, as tu besoin d'afficher l'entièreté de tes 160.000 points pour avoir un affichage convenable de ta courbe ?
    C'est un peu la question que je me posais.

  8. #8
    Membre confirmé
    Inscrit en
    Octobre 2005
    Messages
    63
    Détails du profil
    Informations forums :
    Inscription : Octobre 2005
    Messages : 63
    Par défaut
    Citation Envoyé par Aeronia Voir le message
    Bonjour,

    Dans un premier temps, as tu besoin d'afficher l'entièreté de tes 160.000 points pour avoir un affichage convenable de ta courbe ?
    Il semblerait que ce soit le cas, oui.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. MFC - affichage de données en temps réel
    Par limprid dans le forum MFC
    Réponses: 2
    Dernier message: 13/06/2012, 20h04
  2. Envoi flux audio en temps réel avec RTP
    Par cool147 dans le forum Multimédia
    Réponses: 3
    Dernier message: 28/04/2009, 13h36
  3. Affichage d'un compteur temps réel
    Par Karcynotron dans le forum MFC
    Réponses: 1
    Dernier message: 27/05/2008, 21h47
  4. Affichage de traces en temps réel -- CEdit
    Par vonemya dans le forum MFC
    Réponses: 4
    Dernier message: 23/08/2007, 15h53

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo