Correspondance entre les index SortedList, ListBox et des conrôles

Résolu
BasicZx81 Messages postés 140 Date d'inscription samedi 5 mars 2011 Statut Membre Dernière intervention 13 août 2013 - 3 sept. 2012 à 19:38
BasicZx81 Messages postés 140 Date d'inscription samedi 5 mars 2011 Statut Membre Dernière intervention 13 août 2013 - 6 sept. 2012 à 21:23
Bonjour,
En dernier recours je fait appel à vous car je n'arrive pas à trouver une solution satisfaisante à mon problème.
Le titre n'est pas très clair mais je tenter d'expliquer :
Mon application est un logiciel pour éditer des vidéos, il permet notamment de couper des parties d'une vidéo afin de supprimer les pubs par exemple.
J'enregistre les points de coupures de chaque morceau (Clips) qui correspondent aux numéros de Frame de la vidéo entière.
Ces points (CutBegin et CutEnd) sont enregistrés dans une SortedList (cela me permet de trier automatiquement les Clips dans l'ordre ou ils apparaissent sur la vidéo entière dans le cas par exemple ou je commence par la fin pour sélectionner mes clips)
Cette sortedlist me permet également d'alimenter une listBox pour afficher les points de coupure (toujours dans l'ordre de la vidéo)

Jusque là ça va, grâce aux numéros d'index respectif de la sortedList et de la listBox j'arrive à ajouter ou supprimer un clip et ma SortedList et listBox sont toujours synchronisé.
Donc pour résumer quand je fait SortedList.add (MonClip), celui-ci va s’insérer dans la sortedList si besoins entre 2 clips déjà ajoutés. Grace à SortedList.indexOfKey(MonClip) je sais à quel endroit mon Clip est inséré ce qui me permet de d’insérer aussi dans la ListBox au même endroit grâce à ListBox.Items.Insert(index , text).

Passons au problème :
En même temps que j'ajoute un nouveau clip dans ma (Sortedlist + ListBox)j'ajoute aussi un contrôle PictureBox dans un container (celui-ci me sert à représenter graphiquement la longueur et la position du clip sur la timeline en jouant sur la position et la dimension de celui-ci). problème : Je ne peux pas spécifier l'index d'insertion comme avec la listbox et donc ces PictureBox sont ajoutés les uns a la suite des autres sans respecter l'ordre de tri. Ainsi je suis dans l'incapacité de retrouver celui-ci dans le cas ou je souhaite supprimer un Clip de la SortedList.

J'aimerais beaucoup avoir vos conseils et astuces afin de conserver tout ces éléments synchronisés (dans le même ordre).

PS : Bizarement L'objet Container.Controls expose la méthode removeat(index) mais ne permet pas l'insertion !!!

15 réponses

Utilisateur anonyme
4 sept. 2012 à 00:33
Bonsoir,

Si j'étais toi, j'utiliserais plutôt un dictionnaire comme ceci par exemple :

Option Strict On
Public Class Form1

    'déclaration du dictionnaire
    Dim Dico As New Dictionary(Of String, MaClasse)

    Private Sub Form1_Load(sender As System.Object, e As System.EventArgs) Handles MyBase.Load

        'ajout des éléments au dico
        Dico.Add("clip1", New MaClasse() With {.cutin 2.7, .cutout 63.4, .image = Image.FromFile("test1.jpg")})
        Dico.Add("clip2", New MaClasse() With {.cutin 87.7, .cutout 105.4, .image = Image.FromFile("test2.jpg")})
        Dico.Add("clip3", New MaClasse() With {.cutin 0.8, .cutout 0.6, .image = Image.FromFile("test3.jpg")})

        'classement des clips par valeur de cutin (du plus petit au plus grand)
        'on peut classer autrement en changeant la requete
        Dim requete = From valeur As MaClasse In Dico.Values Order By valeur.cutin Ascending

        'affichage du résultat
        For Each element As MaClasse In requete
            Debug.Print(element.cutin.ToString)
            'ajout dans ta listview ici 
            '...
        Next

    End Sub

    'classe regroupant les données à classer
    Public Class MaClasse
        Public cutin As Double
        Public cutout As Double
        Public image As Image
    End Class
End Class
3
BasicZx81 Messages postés 140 Date d'inscription samedi 5 mars 2011 Statut Membre Dernière intervention 13 août 2013
3 sept. 2012 à 20:25
Rebonsoir je viens d'avoir une idée mais je ne suis pas sûre de moi, j'espère que vous pourrez me conseiller.
L'idée est de gérer une seconde Liste par exemple : list(of T) qui fonctionne en parrallele de la SortedList de sorte que quand j'ajoute un élément dans la sortedList, j'enregistre la clé ou l'index trié de la sortedList dans la List (of T) (non trié)
Mais celle-ci est t'elle bien adaptée et est-ce que vous pensez qu'il y a une meilleure solution ?
0
BasicZx81 Messages postés 140 Date d'inscription samedi 5 mars 2011 Statut Membre Dernière intervention 13 août 2013
4 sept. 2012 à 08:01
Merci beaucoup banana32, je vais essayer ca. Avec mes List (of T) je n'y suis pas arrivé. Je ne comprends pas pourquoi les index des contrôles ne sont pas triés dans le même ordre que ma liste : list (of T)
Il semble que les index des contrôles se mettent dans l'ordre dans lequel il se trouvent positionné dans le container (de la gauche vers la droite) quelque que soit l'ordre dans lequelle je les ajoutes. (j'espère que je suis clair )
Vous pouvez expliquer ce comportement ?
0
Utilisateur anonyme
4 sept. 2012 à 12:44
Utiliser de multiples listes (list(of ou sortedlist ou que sais-je) dans ton cas n'est pas adapté puisque tu vas devoir les gérer en parallèle. Ton code ressemblera vite à une usine à gaz.

L'avantage des dicos c'est que tu accèdes facilement à tes éléments (pour suppression ou modification) grâce à leur clé.

L'avantage d'une classe (ici MaClasse) en tant que valeur du dictionnaire, c'est que tu peux réaliser des opérations plus ou moins complexes au sein même de celle-ci (en te servant d'un constructeur par exemple) voire de lui ajouter des méthodes ou des propriétés et même des événements ou encore de lui modifier des membres tout ceci en connaissant juste sa clé (ici de type string mais ca peut être autre chose une classe aussi par exemple).

Lors de l'énumération pour affichage, tous tes éléments seront disponibles et rassemblés sur la même instance de ta classe.

Bien entendu, ça reste une suggestion car il y a des tas de manières différentes pour arriver au même résultat.
0

Vous n’avez pas trouvé la réponse que vous recherchez ?

Posez votre question
Utilisateur anonyme
4 sept. 2012 à 20:06
Et pour ton problème de PictureBox tu peux parfaitement faire hériter MaClasse de la classe PictureBox :
    Public Class MaClasse
        Inherits PictureBox
        Public cutin As Double
        Public cutout As Double
        Dim controleparent As PictureBox
        Sub New(image As Image, position As Point, controleparent As PictureBox)
            Me.Image = Image
            Me.Location = position
            controleparent = controleparent
            controleparent.Controls.Add(Me)
        End Sub

        Sub retire()
            controleparent.Controls.Remove(Me)
        End Sub
    End Class


Ainsi,pour supprimer ta picturebox de ta timeline, il te suffira d'écrire :
Dico("clip2").retire
Dico.remove("clip2")
0
Utilisateur anonyme
4 sept. 2012 à 20:14
J'ai un petit doute sur cette ligne dans le constructeur (j'ai pas testé)
controleparent.Controls.Add(Me)

Mais tu peux faire une sub 'ajouter' supplémentaire...
0
BasicZx81 Messages postés 140 Date d'inscription samedi 5 mars 2011 Statut Membre Dernière intervention 13 août 2013
5 sept. 2012 à 18:00
Merci beaucoup banana32,
J'ai pas fait tout à fait pareil, j'ai vu le post trop tard.
J'ai simlement déclaré un PictureBox dans ma classe avec :
Dim PictureBox as PictureBox pour travailler directement dans ma classe.
J'ignore si c'est mieux ou pas ce que j'ai fait je suis pas assez calé pour en juger.
J'ai même declarer une ListBox dans cette même classe pour afficher, ajouter supprimer les Clips.
Pour travaller sur la bonne instance des PictureBox et ListBox je les passent en reference avec PictureBox PictureBox1 et ListeBox ListBox1
0
BasicZx81 Messages postés 140 Date d'inscription samedi 5 mars 2011 Statut Membre Dernière intervention 13 août 2013
5 sept. 2012 à 18:36
Oups, c'est le PictureBox Container que je passe en reference, pas les PictureBox qui sont à l'interieur.
0
Utilisateur anonyme
5 sept. 2012 à 20:42
J'ignore si c'est mieux ou pas ce que j'ai fait je suis pas assez calé pour en juger.

L'essentiel c'est que ça marche, mais sans bout de code je ne peux me faire une idée. Disons qu'avec cette méthode, l'ajout et la suppression des picturebox sur ton timeline ainsi que l'instance MaClasse devient simple. On n'a plus à gérer d'index.
0
BasicZx81 Messages postés 140 Date d'inscription samedi 5 mars 2011 Statut Membre Dernière intervention 13 août 2013
5 sept. 2012 à 21:18
Bonsoir banana32, je pensais en avoir fini avec ma classe mais je me heurte à nouveau à un problème. En effet je souhaite serializer ma classe afin de sauvegarder tous les paramétres d’édition propre à la vidéo. (un fichier xml pour chaque vidéo).
J'ai déja utilisé la sérialisation sur des classes simple mais cette fois avec les Picturebox et les ListeBox que j'ai ajoutés, je n'y arrive pas. Au départ je ne pensais pas serializer les PictureBox mais maintenant qu'il sont inclus dans ma classe je me dit que ça permettrait de retrouver les PictureBox sur l'interface utilisateur à chaque chargement d'une vidéo.
Ça m'ennui de solliciter à nouveau le Forum mais je ne m'en sort vraiment pas devant une telle difficulté. Je suis aussi un peu maladroit dans la facon de contruire ma classe même si elle fonctionne très bien (hormis la serialization). J'ai vraiment envie que ma classe fonctionne avec la serialization.
Pensez vous que je peux la soumettre sur le site pour avoir des conseils ?
0
Utilisateur anonyme
5 sept. 2012 à 21:26
Je pense que la classe BinaryFormatter serait plus adaptée à ton cas.
0
Utilisateur anonyme
5 sept. 2012 à 21:32
Elle s'utilise exactement de la même façon mais produit un fichier binaire au lieu d'un xml.
0
BasicZx81 Messages postés 140 Date d'inscription samedi 5 mars 2011 Statut Membre Dernière intervention 13 août 2013
5 sept. 2012 à 21:45
Bonsoir banana32,
En binaire comme en XML j'ai le même message d'erreur :
Le type 'System.Windows.Forms.PictureBox' dans l'assembly 'System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089' n'est pas marqué comme sérialisable.

Je n'ai plus d'erreurs si je mets <NonSerialized()> devant la déclaration du PictureBox mais du coup je ne peux pas enregistrer mes contrôles.
Vous avez une idée ?
0
Utilisateur anonyme
5 sept. 2012 à 21:51
Je n'ai pas vu ton code et ne peux donc pas te répondre.
Tu peux lire cet article en entier et te faire une idée.
0
BasicZx81 Messages postés 140 Date d'inscription samedi 5 mars 2011 Statut Membre Dernière intervention 13 août 2013
6 sept. 2012 à 21:23
Bonsoir j'ai peut-être trouvé une solution en serializant uniquement les propriétés simples des PictureBox (name, Location, Widht, Height...etc)
Mais ça ne restaure tous seul pas mes PictureBox quand je deserialize. l'ideal serait d'avoir un évènement dans ma classe du Style DezerializeFinished afin que je puisse lancer une procédure qui me restaure les PictureBox.
Vous pouvez me dire si un système de ce genre existe ?
0
Rejoignez-nous