2011-08-27 3 views
2

J'ai créer un composant SWING JImageEditor qui affiche simplement une image. L'idée est d'ajouter plus de fonctionnalités au composant plus loin sur la route.Swing: le meilleur moyen de mettre en œuvre la fonctionnalité de zoom dans le composant d'image

Une fonctionnalité que je l'ai déjà mis en œuvre est le zoom. À l'heure actuelle, cette partie est prise en charge dans la méthode paintComponent(). Cependant, je pense que cela pourrait être une mauvaise idée car cela signifie que l'image sera mise à l'échelle de la taille d'origine à la "taille de zoom" actuelle chaque fois que paintComponent() est invoqué. Le code paintComponent se présente comme suit:

@Override 
protected void paintComponent(Graphics g) { 
    super.paintComponent(g); 
    Graphics2D g2 = (Graphics2D) g; 
    g2.setRenderingHint(RenderingHints.KEY_INTERPOLATION, 
      RenderingHints.VALUE_INTERPOLATION_BICUBIC); 
    int w = getWidth(); 
    int h = getHeight(); 
    double imageWidth = scale * image.getWidth(); 
    double imageHeight = scale * image.getHeight(); 
    double x = (w - imageWidth)/2; 
    double y = (h - imageHeight)/2; 
    AffineTransform at = AffineTransform.getTranslateInstance(x, y); 
    at.scale(scale, scale); 
    g2.drawRenderedImage(image, at); 
} 

Maintenant, ce que je pensais comme une alternative était de garder deux instances de BufferedImage où l'on est l'original et l'autre est la « vue » actuelle. De cette façon, je pouvais gérer le zoom/mise à l'échelle réel à chaque fois que la méthode setScale() est invoquée, au lieu de la mise à l'échelle dans paintComponent(). Cependant, l'inconvénient est que je dois conserver deux instances de BufferedImage qui conduiront à une consommation de mémoire plus élevée en fonction de la taille de l'image. Il est, bien sûr, impossible de prédire la taille des images qu'un utilisateur donné ouvrira en utilisant le composant.

Ce que je suis à la recherche est soit un coup de pouce si je suis sur la bonne voie avec mon travail, ou pouces vers le bas Si elle est mauvaise conception et devrait être considéré comme une autre solution. Je vous remercie de toutes les entrées et récompenserai toutes les réponses qui me :-) ÉCLAIRE

+0

+1 pour la séparation de vue de modèle. – trashgod

Répondre

3

Je dirais que mettre une section de synchronisation dans votre paintComponent pour mesurer le temps qu'il faut. Obtenez votre mesure de base de ce que vous avez maintenant. Ensuite, implémentez la méthode optimisée avec le BufferedImage supplémentaire. Comparez les mesures et choisissez celle qui est la plus petite. J'ai le sentiment que votre intuition est correcte: faire la transformation affine à chaque cycle de peinture est lent, et en créant un double tampon pour l'image mise à l'échelle et la source sera plus rapide. Bien que je ne puisse pas trouver quelque chose là-bas qui confirme ou nie cela, et il pourrait être affecté par l'accélération matérielle.

Si vous avez extrait cette section de code dans une classe ZoomableBufferedImage, vous pouvez facilement activer ou désactiver les versions optimisées/non optimisées. Le ZoomableBufferedImage détiendrait une référence à l'image source, et contenir une image supplémentaire tampon qu'il peut conserver la version réduite. Comme vous effectuez un zoom avant/arrière de la ZoomableBufferedImage tire à la mémoire tampon ou non en fonction de ses paramètres, puis dans sa méthode de peinture il peut dessiner soit à partir du tampon, soit en appliquant l'AffineTransform à la source et en le dessinant en fonction de ses paramètres.

Questions connexes