2009-05-12 5 views

Répondre

11

D'une certaine manière, oui. Vous pouvez créer un ListModel personnalisé qui utilise la méthode getElementAt(int index) pour charger la valeur correcte si elle n'a pas déjà été chargée. Voir l'exemple dans le Javadocs pour JList:

// This list model has about 2^16 elements. Enjoy scrolling. 

ListModel bigData = new AbstractListModel() { 
    public int getSize() { return Short.MAX_VALUE; } 
    public Object getElementAt(int index) { return "Index " + index; } 
}; 
+0

merci pour la réponse, je l'ai essayé et il m'a fait réaliser mon interface était si lent à cause d'une coutume « sorted » quelqu'un modèle de liste a écrit et utilisé – user105413

2

Juste pour ajouter à l'autre réponse, lorsque vous créez votre propre implémentation de ListModel, alors que vous chargez les données que vous voulez appeler:

fireIntervalAdded(Object source,int index0, int index1) 

En supposant que vous chargez des données dans votre liste de manière incrémentielle. Cela provoquera le JList qui l'utilise en tant que modèle à mettre à jour.

Voir Javadoc for fireIntervalAdded

+0

Huh, je me demande pourquoi l'exemple n'a pas fait cela. Peut-être que c'est plus pour l'esthétique (gardez la barre de défilement synchronisée). –

+0

merci pour cela aussi, je l'ai utilisé quand j'ai mis en œuvre une méthode "addAll" dans mon modèle de liste personnalisée – user105413

1

incorrect. Ce JList ci-dessus n'est pas paresseusement chargé.

Swing insiste pour accéder à chaque élément de l'ensemble du ListModel tout en l'affichant à l'écran. De plus, après avoir accédé à tous les éléments, Swing ré-accède au premier nombre d'éléments visibles à l'écran (dans la fenêtre, pas sur l'écran ci-dessous).

Exécutez cette classe "TestJList" simple pour le prouver. J'appelle println chaque fois que 'getElementAt' est exécuté. Vous pouvez voir clairement que Swing appelle cette méthode pour chaque élément du ListModel.

Cela se produit pour moi sur un MacBook unibody fonctionnant sous Mac OS X 10.6.2 avec Java:

"1.6.0_17" Java (TM) SE Runtime Environment (build 1.6.0_17-b04-248 -10M3025) Java HotSpot (TM) 64 bits serveur VM (build 14,3 b01-101, mode mixte)

import javax.swing.*; 

/** 
* This example proves that a JList is NOT lazily-loaded. 
*/ 
public class TestJList { 
    private static void createAndShowGUI() { 
     //Create and set up the window. 
     JFrame frame = new JFrame("HelloWorldSwing"); 
     frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 

     //Create an artificial ListModel. 
     ListModel bigData = 
      new AbstractListModel() { 
       public int getSize() { 
        // return Short.MAX_VALUE; // Try this if you have a long while to waste. 
        return 10; 
       } 

       public Object getElementAt(int index) { 
        System.out.println("Executing 'getElementAt' # " + index); 
        return "Index " + index; 
       } 
      }; 

     // Create a JList. 
     JList myList = new JList(bigData); 

     // Add the JList to the frame. 
     frame.getContentPane().add(myList); 

     //Display the window. 
     frame.pack(); 
     frame.setVisible(true); 
    } 

    public static void main(String[] args) { 
     //Schedule a job for the event-dispatching thread: 
     //creating and showing this application's GUI. 
     javax.swing.SwingUtilities.invokeLater(
      new Runnable() { 
       public void run() { 
        createAndShowGUI(); 
       } 
      }); 
    } 
} 

Exécuter ce code, et vous verrez:

Executing 'getElementAt' # 0 
Executing 'getElementAt' # 1 
Executing 'getElementAt' # 2 
Executing 'getElementAt' # 3 
Executing 'getElementAt' # 4 
Executing 'getElementAt' # 5 
Executing 'getElementAt' # 6 
Executing 'getElementAt' # 7 
Executing 'getElementAt' # 8 
Executing 'getElementAt' # 9 
Executing 'getElementAt' # 0 
Executing 'getElementAt' # 1 
Executing 'getElementAt' # 2 
Executing 'getElementAt' # 3 
Executing 'getElementAt' # 4 
Executing 'getElementAt' # 5 
Executing 'getElementAt' # 6 
Executing 'getElementAt' # 7 
Executing 'getElementAt' # 8 
Executing 'getElementAt' # 9 

-fin-

5

Je l'ai résolu. J'avais manqué la solution discutée en haut de la documentation de l'API JList.

Dans le code source exemple que j'ai posté dans une autre réponse à ce sujet, ajoutez cette ligne (et commentaires) après la création du JList:

// Tell JList to test rendered size using this one value rather 
    // than every item in ListModel. (Much faster initialization) 
    myList.setPrototypeCellValue("Index " + Short.MAX_VALUE); 

Le problème est que JList, par défaut, accède à chaque élément dans le ListModel entier pour déterminer à l'exécution la taille d'affichage nécessaire. La ligne ajoutée ci-dessus remplace cette valeur par défaut et demande à JList d'examiner uniquement la valeur une fois passée. Cette valeur agit comme un modèle (prototype) pour dimensionner l'affichage du JList.

Voir:

http://java.sun.com/javase/6/docs/api/javax/swing/JList.html#prototype_example

+0

Merci pour cela - c'est quelque chose que j'ai aussi manqué. –

Questions connexes