Bandit_world
Messages postés28Date d'inscriptionmercredi 23 juin 2004StatutMembreDernière intervention 9 juillet 2004
-
24 juin 2004 à 16:36
cs_Dobel
Messages postés333Date d'inscriptiondimanche 25 mai 2003StatutMembreDernière intervention23 novembre 2009
-
8 juil. 2004 à 15:16
Bonjour
Je voudrais savoir si quelqu'un aurait pas déjà eu à convertir l'image affichée sur un Panel en format bitmap pour ensuite l'enregistrer sur le dur.
Ce qui me pose problème, c'est surtout le coté conversion JPanel ->Bitmap
Bandit_world
Messages postés28Date d'inscriptionmercredi 23 juin 2004StatutMembreDernière intervention 9 juillet 20045 24 juin 2004 à 17:26
Dobel, tu es mon nouveau héros. Je te remercie pour ton aide précieuse. Je suis allé voir tes sources et c'est exactement ce qu'il me fallait. Tu m'as fait économisé plusieurs heures de travail et quand on sait à quel point je suis à la bourre dans mon projet, c'est pas négligeable.
Tu aurais pas des long cheveux noirs, une couronne d'épines sur la tête, et une étonnante facilité à marcher sur l'eau?
cs_Dobel
Messages postés333Date d'inscriptiondimanche 25 mai 2003StatutMembreDernière intervention23 novembre 20091 25 juin 2004 à 13:38
Salut
j'avais pas lu ton message précédant au sujet du jpeg sans utiliser ImageIO (suivi d'une conversation fort passionnante :big) )
dans ma source, pour le truc :
DataOutputStream sortie = new DataOutputStream(new FileOutputStream(fichier));
JPEGImageEncoder enc = JPEGCodec.createJPEGEncoder(sortie);
JPEGEncodeParam param = enc.getDefaultJPEGEncodeParam(image);
param.setQuality(1f, false);
enc.setJPEGEncodeParam(param);
enc.encode(image);
sortie.close();
les classes JPEGEncodeParam etc.. ne sont peut-être pas dans le package javax.imageio (elles sont dans com.sun.image.codec....)
mais ce sont en fait les codecs utilisés par ImageIO
donc les utiliser, c'est un peu comme utiliser ImageIO...
en fait, j'avais écrit ca à la place de
ImageIO.write(image, "jpg", fichier)
uniquement pour pouvoir regler la qualité
(c'est quand même bizare comme contrainte de pas pouvoir utiliser ImageIO...)
A+
Dobeliou
[Il ne faut jamais jouer à saute-mouton avec une licorne]
Vous n’avez pas trouvé la réponse que vous recherchez ?
Bandit_world
Messages postés28Date d'inscriptionmercredi 23 juin 2004StatutMembreDernière intervention 9 juillet 20045 28 juin 2004 à 11:34
Voilà, apparement, j'ai toujours un problème sur ma conversion en Bitmap. Voici mon code :
public void GraphicsToBitmap()
{
BufferedImage image = new BufferedImage(this.getWidth(), this.getHeight(), BufferedImage.TYPE_BYTE_INDEXED);
File fichier = new File("Resultats/ImageBitmapCarteOpt.bmp");
this.paint(image.getGraphics());
try{
ImageIO.write(image, "bmp",fichier);
}
catch (IOException IOE){
IOE.printStackTrace();
}
}
Il créer bien le fichier en question mais ce n'est pas l'image du Graphics qui est enregistrée.
En fait, l'image ne comporte aucune donnée.
Je ne comprend pas pourquoi ca refuse de marcher.
Au fait, j'ai bien droit d'utiliser ImageIO. En fait, sur l'ordinateur que j'utilisais, il n'avait pas une version de la plateforme API suffisament récente je crois.
Bandit_world
Messages postés28Date d'inscriptionmercredi 23 juin 2004StatutMembreDernière intervention 9 juillet 20045 29 juin 2004 à 14:34
Ma méthode GraphicsToBitmap est appelée dans la classe principale suite à l'appui sur un bouton. Ce que je ne comprend pas, c'est que j'ai aussi une méthode GraphicsToJpeg juste au dessus de la méthode GraphicsToBitmap. Les deux sont appelées au même endroit simultanément.
Pourtant, la conversion en bitmap ne crée rien d'autre qu'une image vide.
L'erreur provient donc forcément du code que j'ai affiché plus haut.
Quand tu as fait ton test, l'image générée n'était pas vide aussi?
cs_Dobel
Messages postés333Date d'inscriptiondimanche 25 mai 2003StatutMembreDernière intervention23 novembre 20091 29 juin 2004 à 15:27
je viens de constater que j'avais utiliser une béta du jdk 1.5.0
en effet, avec le 1.4, ca marche pas
en verifiant les differents formats acceptés :
String[] s = ImageIO.getWriterMIMETypes();
for (int i=0; i<s.length; i++) {
System.out.println(s[i]);
}
il semble que le bmp ne soit pas supprté par la 1.4
tu peux toujours utiliser le code que j'avais mis en commentaire dans ma source
mais l'enregistrement sera plus lent (et se sera pas du 256 couleurs comme avec l'utilisation de BufferedImage.TYPE_BYTE_INDEXED)
Salut
Dobeliou
[Il ne faut jamais jouer à saute-mouton avec une licorne]
Bandit_world
Messages postés28Date d'inscriptionmercredi 23 juin 2004StatutMembreDernière intervention 9 juillet 20045 29 juin 2004 à 15:38
Merci pour ton aide.
Effectivement, je travaille avec la jdk 1.4.
Pour l'autre code dont tu parles, il doit s'agir de ton enregistrement manuel je suppose.
Je vais essayer de voir si ça fonctionne.
Je m'y attèle tout de suite.
Bandit_world
Messages postés28Date d'inscriptionmercredi 23 juin 2004StatutMembreDernière intervention 9 juillet 20045 29 juin 2004 à 17:01
Ca marche bien!!!
Excellent.
merci beaucoup pour ton aide.
Je te poserais bien une dernière question. J'ai besoin de récupérer la couleur d'un point à un endroit précis x et y du panel pour y appliquer manuellement les algos d'érosion et de dilatation.
Tu sais pas comment faire pour récupérer la couleur d'un panel à un endroit précis.
(petite précision, l'image est une image binaire).
Merci d'avance.
cs_Dobel
Messages postés333Date d'inscriptiondimanche 25 mai 2003StatutMembreDernière intervention23 novembre 20091 29 juin 2004 à 18:37
la seule méthode que je connaise, c'est encore en passant par une BufferedImage
tu fais une BufferedImage de type TYPE_BYTE_BINARY (pour le noir et blanc)
tu dessines ton JPanel dedans de la même façon que précédemment
this.paint(image.getGraphics());
tu disposes des méthodes getRGB sur l'image
les valeurs retournées contiennent la couche alpha et sont au format ARGB
donc tu as ff000000 pour du noir et ffffffff pour du blanc
voilà !
Salut
Dobeliou
[Il ne faut jamais jouer à saute-mouton avec une licorne]
Bandit_world
Messages postés28Date d'inscriptionmercredi 23 juin 2004StatutMembreDernière intervention 9 juillet 20045 30 juin 2004 à 15:50
Excellent!!!
Tout marche.
J'arrive à faire mon érosion et ma dilatation, et mes conversion Bitmap et JPEG marchent parfaitement.
Il me reste un autre petit problème que je traine depuis longtemps.
Je dois à un certain moment de mon code voir avec précision si une ellipse2D intersects une ligne2D. Cette ligne2D peut avoir n'importe quel coefficient directeur.
Comme il m'a semblé ne pas y avoir de méthode prédéfinie dans le tutorial, et comme la position de l'ellipse est son coin supérieur gauche, j'ai fait petit calcul de base pour récupérer les coordonnées de son centre.
Ensuite, vu que je connais diamètre du cercle (car c'est une ellipse de grand axe et de petit axe égaux), j'ai fait une méthode qui renvoie true si la plus courte distance de la ligne au centre du cercle est inférieure au diamètre et false sinon.
Seulement cette méthode n'est pas très précise et il arrive que l'intersection existe et que je ne le vois pas.
Connais tu une méthode pour avoir avec précision la certitude qu'une ellipse2D et une ligne2D s'intersects?
Bandit_world
Messages postés28Date d'inscriptionmercredi 23 juin 2004StatutMembreDernière intervention 9 juillet 20045 30 juin 2004 à 16:33
Voici mon code:
public boolean IntersectsPoteau(Line2D Ligne)
{
int i, TailleMax = PoteauListe.size();
Ellipse2D poteau2;
double absHautGauche; // Coordonnées du point en haut à gauche de l'ellipse
double ordHautGauche;
double absCentre;
double ordCentre;
boolean Intersection = false;
i = 0;
for (i = 0; i < TailleMax; i++)
{
poteau2 = (Ellipse2D)PoteauListe.elementAt(i);
absHautGauche = poteau2.getX();
ordHautGauche = poteau2.getY();
absCentre = absHautGauche + (TaillePoteau/2)*Math.sin(45);
ordCentre = ordHautGauche + (TaillePoteau/2)*Math.cos(45);
if ( Ligne.ptSegDist(absCentre, ordCentre) < TaillePoteau/2)
{
Intersection = true;
}
}
return Intersection;
}
Tu aurais pas une petite idée pour l'améliorer ou pour utiliser méthode plus précise?
En tout cas, merci pour ton aide. Je suis en avance sur mes objectifs de stage grace à toi.
cs_Dobel
Messages postés333Date d'inscriptiondimanche 25 mai 2003StatutMembreDernière intervention23 novembre 20091 30 juin 2004 à 16:59
il n'y a rien a redire sur ton code ;-p
juste verifier que TaillePoteau est bien 1 double (sinon, la division par 2 retourne aussi un int...)
j'essayerais bien, pour être sur d'avoir les mêmes résultats que le dessin, de convertir en int les coordonnées du centre dans le test :
if ( Ligne.ptSegDist((int) absCentre, (int) ordCentre) < TaillePoteau/2)
Dobeliou
[Il ne faut jamais jouer à saute-mouton avec une licorne]
Bandit_world
Messages postés28Date d'inscriptionmercredi 23 juin 2004StatutMembreDernière intervention 9 juillet 20045 30 juin 2004 à 17:24
TaillePoteau est bien un double.
J'ai fait le forçage de type sur les coordonnées du centre du cercle.
Mais apparement, ça ne résoud pas le problème de détection.
Perso, je trouve ça vraiment bizarre.
J'ai passé du temps à essayer de comprendre pourquoi il détecte mal l'intersection mais, comme j'ai pas trop l'intuition divine du java pour l'instant, je bloque.
En plus, c'est une méthode toute simple donc elle devrait marcher.
cs_Dobel
Messages postés333Date d'inscriptiondimanche 25 mai 2003StatutMembreDernière intervention23 novembre 20091 30 juin 2004 à 19:12
ah si!!!
il y a bien une gaffe !
si TaillePoteau designe le diametre, alors tu as
absCentre = absHautGauche + (TaillePoteau/2);
ordCentre = ordHautGauche + (TaillePoteau/2);
sinon, c'est qu'il désigne la diagonale du carré contenant le cercle
dans ce cas, le test devrait être
if ( Ligne.ptSegDist(absCentre, ordCentre) < TaillePoteau/2*Math.sin(Math.PI/4))
de plus, les angles doivent être en radians donc ca aurait été
sin(Math.PI/4) (=racine(2)/2 ;-p)
cette fois, ca doît être bon !
A+
Dobeliou
[Il ne faut jamais jouer à saute-mouton avec une licorne]
Bandit_world
Messages postés28Date d'inscriptionmercredi 23 juin 2004StatutMembreDernière intervention 9 juillet 20045 1 juil. 2004 à 10:07
En fait, je vois pas pourquoi tu changes les coordonnées du centre.
J'ai tout de même essayé mais je n'arrive pas à un bon résultat.
Pour TaillePoteau, voici comment je le gère :
private double TaillePoteau = 20;
public void AjoutPoteau (double abscisse, double ordonnee)
{
Ellipse2D poteau = new Ellipse2D.Double(abscisse, ordonnee, TaillePoteau, TaillePoteau);
PoteauListe.addElement(poteau);
}
Donc en le déclarant comme ça, je suppose que c'est le rayon puisque c'est le demi grand axe de l'ellipse.
Bandit_world
Messages postés28Date d'inscriptionmercredi 23 juin 2004StatutMembreDernière intervention 9 juillet 20045 1 juil. 2004 à 10:14
Au fait, je viens d'aller voir ton site internet. J'ai pas pu trop y rester longtemps vu que j'ai des tuteurs de stage qui rodent mais ca m'a paru assez interessant. Je retournerais voir ca. Il y a l'air d'avoir des bonnes équations pour les fractales.
cs_Dobel
Messages postés333Date d'inscriptiondimanche 25 mai 2003StatutMembreDernière intervention23 novembre 20091 1 juil. 2004 à 11:46
TaillePoteau désigne donc bien le diamètre du cercle
donc je maintiens ce que j'ai dit ;-p
public boolean IntersectsPoteau(Line2D Ligne)
{
int i, TailleMax = PoteauListe.size();
Ellipse2D poteau2;
double absHautGauche; // Coordonnées du point en haut à gauche de l'ellipse
double ordHautGauche;
double absCentre;
double ordCentre;
boolean Intersection = false;
i = 0;
for (i = 0; i < TailleMax; i++)
{
poteau2 = (Ellipse2D)PoteauListe.elementAt(i);
absHautGauche = poteau2.getX();
ordHautGauche = poteau2.getY();
absCentre = absHautGauche + (TaillePoteau/2);
ordCentre = ordHautGauche + (TaillePoteau/2);
if ( Ligne.ptSegDist(absCentre, ordCentre) < TaillePoteau/2)
{
Intersection = true;
}
}
return Intersection;
une autre question :
est-ce que tu regardes l'intersection avec le segment délimité par les 2 points de la ligne ?
si c'est le cas, alors il faut modifier le test pour qu'il tienne compte du cas où le segment est à l'interieur du cercle :
double x1 = ligne.getP1().getX();
double y1 = ligne.getP1().getY();
double x2 = ligne.getP2().getX();
double y2 = ligne.getP2().getY();
double d1 = Math.sqrt((x1-absCentre)*(x1-absCentre)+(y1-ordCentre)*(y1-ordCentre));
double d2 = Math.sqrt((x2-absCentre)*(x2-absCentre)+(y2-ordCentre)*(y2-ordCentre));
double dist1 = Math.min(d1, d2);
double dist2 = Math.max(d1, d2);
if (dist1<=TailleMax/2 && dist2>=TailleMax/2)
Intersection = true;
voila
au sujet de mon site, ca fait assez longtemps que je n'y ais pas touché et actuellement, je suis en pleine periode de concours, mais, promis!, dès que j'ai le temps, je le continue!
Salut
Dobeliou
[Il ne faut jamais jouer à saute-mouton avec une licorne]
Bandit_world
Messages postés28Date d'inscriptionmercredi 23 juin 2004StatutMembreDernière intervention 9 juillet 20045 1 juil. 2004 à 12:00
ok, je vais voir ça après la pose de midi.
Merci pour ton aide.
Pour le segment à l'intérieur du cercle, dans mon sujet de stage, cela n'est pas physiquement possible.
Mais je vais tout tester pour voir si ca fonctionne mieux.