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

2D Java Discussion :

problème avec un pour inverser les couleurs avec LookUp


Sujet :

2D Java

  1. #1
    Futur Membre du Club
    Profil pro
    Inscrit en
    Mars 2009
    Messages
    16
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2009
    Messages : 16
    Points : 8
    Points
    8
    Par défaut problème avec un pour inverser les couleurs avec LookUp
    Bonjour,
    Je tente désespéremment de faire fonctionner un filtre pour inverser la couleur d'une image.

    Le filtre fonctionne dépendant des images. Lorsqu'il plante, j'ai droit à l'erreur
    Exception in thread "AWT-EventQueue-0" java.lang.IllegalArgumentException: LookupOp cannot be performed on an indexed image

    Y a t-il un moyen d'éviter cette erreur?

    Le code de ma fonction servant à appliquer le filtre
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
    public static BufferedImage draw(BufferedImage image)
    	{
     
    		byte[] invert = new byte[256];
    		for (int i = 0; i < 256; i++)
    		invert[i] = (byte)(255 - i);
    		BufferedImageOp invertOp = new LookupOp(new  ByteLookupTable(0, invert), null);
    		return invertOp.filter(image, null);
    	}
    Merci d'avance

  2. #2
    Rédacteur/Modérateur

    Avatar de bouye
    Homme Profil pro
    Information Technologies Specialist (Scientific Computing)
    Inscrit en
    Août 2005
    Messages
    6 864
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 48
    Localisation : Nouvelle-Calédonie

    Informations professionnelles :
    Activité : Information Technologies Specialist (Scientific Computing)
    Secteur : Agroalimentaire - Agriculture

    Informations forums :
    Inscription : Août 2005
    Messages : 6 864
    Points : 22 910
    Points
    22 910
    Billets dans le blog
    51
    Par défaut
    Citation Envoyé par Javadoc
    Class LookupOp
    [...]
    Images with an IndexColorModel cannot be used.
    Recopie ton image dans une BufferedImage.TYPE_INT_RGB d'abord.

    Par contre si tu veux garder une image de type indexed et que tu veux en inverser la palette, c'est plutot du cote du ColorModel qu'il faut aller fouiller je pense.

  3. #3
    Futur Membre du Club
    Profil pro
    Inscrit en
    Mars 2009
    Messages
    16
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2009
    Messages : 16
    Points : 8
    Points
    8
    Par défaut
    Si j'ai bien compris, je prend pour img de destination un BufferedImage qui à un type RGB? Si oui... Ne fonctionne pas.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    	public static BufferedImage draw(BufferedImage image)
    	{
    	      BufferedImage imgDest = new BufferedImage(image.getWidth(), image.getHeight(), BufferedImage.TYPE_INT_RGB);
     
    		byte[] invert = new byte[256];
    		//On crée un tableau avec les nouvelles valeurs des couleurs (Effet négatif).
    		for (int i = 0; i < 256; i++)
    		{
    			invert[i] = (byte)(255 - i);
    		}
    		BufferedImageOp invertOp = new LookupOp(new ByteLookupTable(0, invert), null);
    		return invertOp.filter(image, imgDest);
    	}

  4. #4
    Rédacteur

    Avatar de millie
    Profil pro
    Inscrit en
    Juin 2006
    Messages
    7 015
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2006
    Messages : 7 015
    Points : 9 818
    Points
    9 818
    Par défaut
    Le LookupOp ne fonctionne pas très bien en présent de canal alpha ou de ColorModel du type IndexColorModel.

    Voici une extension que j'avais fait pour le faire fonctionner => Mais j'utilise une output de type ARGB ou RGB.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    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
    /**
     * Extension du LookupOp de la bibliothèque standard qui gère :
     *  - les canaux alpha
     *  - les ColorModel de type IndexColorModel
     * 
     * @author florent
     *
     */
    public class LookupOperator extends SimpleOperator {
     
    	short[][] mLutTable;
    	short[] sLutTable;
     
    	public LookupOperator(short[][] mLutTable) {
    		this.mLutTable = mLutTable;
    	}
    	public LookupOperator(short[] sLutTable) {
    		this.sLutTable = sLutTable;
    	}
     
     
    	public void compute(BufferedImage output, BufferedImage input) {
    		if(input.getWidth()!=output.getWidth()||input.getHeight()!=output.getHeight()) 
    			throw new IllegalArgumentException("Width and Height for input/output different");
    		int nbComponents= input.getColorModel().getNumComponents();
     
    		boolean hasAlpha = input.getColorModel().hasAlpha();
    		if(mLutTable==null) {
    			if(hasAlpha)
    				mLutTable = new short[][] {sLutTable, sLutTable, sLutTable, PredefinedLUT.getIdemLUT()};
    			else
    				mLutTable = new short[][] {sLutTable, sLutTable, sLutTable};
    		}
     
     
    		if(input.getColorModel() instanceof IndexColorModel) {
    			for(int y=0; y<output.getHeight(); y++)
    				for(int x=0; x<output.getWidth(); x++) {
    					int rgb = input.getRGB(x, y);
    					int iR;
    					int iG;
    					int iB;
     
    					if(nbComponents>=3) {
    						iR = mLutTable[0][(rgb >> 16) & 0xFF];
    						iG = mLutTable[1][(rgb >> 8) & 0xFF];
    						iB = mLutTable[2][rgb & 0xFF];
    					}
    					else {
    						iR = iG = iB = mLutTable[0][rgb&0xFF];
    					}
     
    					if(hasAlpha)
    						output.setRGB(x,y, (rgb>>24&0xFF)<<24 + (iR<<16)+(iG<<8)+iB);
    					else
    						output.setRGB(x,y, (iR<<16)+(iG<<8)+iB);
    				}
    		}
    		else {
    			LookupOp op = new LookupOp(new ShortLookupTable(0,mLutTable), null);
    			op.filter(input, output);
    		}
    	}
    }
    On pourrait optimiser le cas particulier des IndexColorModel. Mais dans ce cas, en général, l'image est assez petite et il n'y a pas vraiment besoin d'optimisation.

    idemLUT correspond évidemment à cela :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
     
    static {
    		idemTable = new short[256];
    		for(int i = 0; i<256;i++)
    			idemTable[i] = (short) i;
    	}
     
    	/**
             * Retourne une LUT table qui contient un tableau rempli selon [i] = i
             * @return
             */
    	public static short[] getIdemLUT() {
    		return idemTable;
    	}

  5. #5
    Membre actif
    Avatar de karbos
    Inscrit en
    Novembre 2008
    Messages
    155
    Détails du profil
    Informations forums :
    Inscription : Novembre 2008
    Messages : 155
    Points : 255
    Points
    255
    Par défaut
    Citation Envoyé par Barilz Voir le message
    Si j'ai bien compris, je prend pour img de destination un BufferedImage qui à un type RGB? Si oui... Ne fonctionne pas.
    J'arrive un peu tard mais j'ai résolu ce problème : en fait tu essaies d'inverser ton image avec un tableau de 256 bytes, or celle-ci utilise une palette de couleurs indexées (donc moins de 256 bytes).
    Voici l'astuce pour passer de couleurs indéxées à des 256 couelurs :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
       BufferedImage imgDest = new BufferedImage(image.getWidth(), image.getHeight(), BufferedImage.TYPE_INT_RGB);
       Graphics g = imgDest.getGraphics();
       g.drawImage(image, 0, 0, null);
    Et voici le code qui inverse une image :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    	public static BufferedImage draw(BufferedImage image)
    	{
    	      BufferedImage imgDest = new BufferedImage(image.getWidth(), image.getHeight(), BufferedImage.TYPE_INT_RGB);
    	      Graphics g = imgDest.getGraphics();
                  g.drawImage(image, 0, 0, null);
     
    		byte[] invert = new byte[256];
    		//On crée un tableau avec les nouvelles valeurs des couleurs (Effet négatif).
    		for (int i = 0; i < 256; i++)
    		{
    			invert[i] = (byte)(255 - i);
    		}
    		BufferedImageOp invertOp = new LookupOp(new ByteLookupTable(0, invert), null);
     
    		//attention c'est la meme image en entree et en sortie
    		invertOp.filter(imgDest, imgDest);
    		return imgDest;
    	}

Discussions similaires

  1. [JDOM] Problème pour lire les noeuds avec JDOM
    Par Eclix dans le forum Format d'échange (XML, JSON...)
    Réponses: 7
    Dernier message: 26/05/2014, 18h11
  2. Réponses: 8
    Dernier message: 18/04/2010, 03h40
  3. problème avec idlj pour générer les stubs
    Par merlubreizh dans le forum CORBA
    Réponses: 2
    Dernier message: 25/02/2007, 10h29
  4. problème avec strtok pour récupérer les vides
    Par manikou dans le forum MFC
    Réponses: 4
    Dernier message: 02/06/2005, 20h08
  5. Réponses: 1
    Dernier message: 17/05/2004, 11h29

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