Oniromancie: Tutoriels - Comment préserver son pixel-art de la dégradation de couleurs de RPG Maker 2003


Comment ça marche?

Aëdemphia
Par Sylvanor

Fighting Robots Quest
Par Boulon

Forstale
Par Ødd Clock

Geex
Par roys

Inexistence
Par Falco

La Légende d'Ibabou
Par Zaitan

Lije
Par Gaetz

LoveMaster
Par Cuddlefox

Sarcia
Par Kaëlar

Super Mario RPG - Lost Souls
Par Omegabowser

News: Concours des Alex d'Or 2017-18: (...) / News: MegaMaker : créez votre propre (...) / News: Test de Tinker Quarry / Sorties: Leave the Room / Jeux: Leave the Room /

Chat  (17 connectés)

Bienvenue
visiteur !






publicité RPG Maker!

Statistiques

Liste des
membres


Contact

60 connectés actuellement

9179783 visiteurs
depuis l'ouverture

858 visiteurs
aujourd'hui

Groupe Facebook

Barre de séparation

Partenaires




TOP
GAMEMAKING


Les 5 plus
visités

Lunae, le baz'arts d'Emz0

Le studio du chat vert

Pixelandgame

Tashiroworld

HeyMakeGames

Au hasard

The Forum Of Zelda

RPG Maker VX

FrGraph-X

Les deux derniers

Lunae, le baz'arts d'Emz0

Le studio du chat vert

Nos autres partenaires

Devenir
partenaire


Barre de séparation

Un site du réseau
War Paradise

Annuaires référenceurs





Comment préserver son pixel-art de la dégradation de couleurs de RPG Maker 2003
Ecrit par Roi of the Suisse

Le problème :

RM2003 impose comme limitations aux ressources graphiques d'être en couleurs indexées 8bits à 256 couleurs différentes maximum.
En plus de ces contraintes, le logiciel modifie les couleurs des ressources graphiques lors de l'importation. Le pixel-art subit parfois une grande dégradation.

image


Explication :

Les couleurs autorisées : une palette 16bits

Le logiciel transforme les ressources en convertissant les couleurs dans une palette 16bits. La palette 16bits comporte 65536 couleurs.
Sur les 16 bits, 5 bits sont alloués au niveau de rouge, 6 au niveau de vert, et 5 au niveau de bleu. Pourquoi cette préférence pour le vert ? Parce que le vert est au centre du spectre visible et que l'oeil humain est beaucoup plus sensible aux variations de vert qu'aux variations de rouge ou de bleu (situés aux extrémités du spectre visible).
RM2003 possède donc une liste de 65536 couleurs autorisées. Toutes les autres couleurs sont transformées en la couleur la plus proche dans la liste.
Cette liste de couleurs 16bits n'est pas forcément la même que la liste des couleurs de n'importe quelle console aux graphismes 16bits : il existe plusieurs façons de choisir 65536 couleurs parmi les 16777216 couleurs existantes.

Une histoire de sauts

La liste des couleurs utilisées par RM2003 est ainsi faite :
- pour le niveau de rouge et le niveau de bleu, la couleur augmente par sauts de 8, SAUF entre 24 et 33, 57 et 66, 90 et 99, 123 et 132, 156 et 165, 189 et 198, 222 et 231 où le saut est de taille 9.
- pour le niveau de vert, le saut est de taille 4, SAUF entre 60 et 65, 125 et 130, 190 et 195 où le saut est de taille 5.
Chacun des trois niveaux augmente de 0 à 255 à son rythme, le rythme du vert étant plus lent donc plus précis.
Par exemple, la couleur (0,4,8) est valide (sauts de taille 8 pour rouge et bleu, saut de taille 4 pour vert), tandis que la couleur (0,3,8) est interdite (saut de taille 3 pour vert).
Vous pouvez vous poser la question suivante : "Pourquoi n'ont-ils pas utilisé uniquement des sauts de 8 pour rouge et bleu, et uniquement des sauts de 4 pour vert ? Pourquoi avoir utilisé des sauts de 9 et 5 ?" La réponse est que le rajout de ces quelques sauts anormaux permet d'atteindre la valeur 255 codant pour les couleurs pures et notamment le blanc ! Sans ces sauts, la couleur la plus claire aurait été le (248,252,248) et non le blanc pur (255,255,255). Or le blanc pur étant une couleur très importante, la palette a été étirée de 248 à 255 et de 252 à 255 produisant quelques sauts anormaux au sein de la liste.

Formalisation mathématique :

Mathématiquement, les couleurs (R,V,B) autorisées sont de la forme :
R = 8*i + i/4
V = 4*j + j/16
B = 8*k + k/4
où i et k vont de 0 à 31, et où j va de 0 à 63. Pour la division, on ignore les chiffres après la virgule, c'est une division euclidienne que l'ordinateur utilise.
Par exemple, si on prend i=29, j=55, k=17 on obtient la couleur :
R = 8*29 + 29/4 = 239
V = 4*55 + 55/16 = 223
B = 8*17 + 17/4 = 140
On en déduit que (239,223,140) est une couleur autorisée par RM2003 !


Comment éviter le problème :

Ci-dessous, une image comptabilisant les couleurs autorisées par RM2003.

image

Si, lors de votre pixel-art, vous utilisez les couleurs présentes dans cette image, vos ressources graphiques ne seront pas modifiées par RM2003. Toute ressource utilisant ces couleurs uniquement sera préservée durant l'importation dans RM2003.
Ne choisissez donc pas vos couleurs n'importe comment :
- essayez de trouver la couleur dont vous avez besoin dans l'image ci-dessus
- ou alors vérifiez que la couleur que vous utilisez correspond bien aux formules mathématiques énoncées ci-dessus.
Le danger, si vous ne faites pas attention, est d'employer dans votre palette de pixel-art deux couleurs qui sont transformées en la même couleur par RM2003, car toutes les deux sont proches d'une couleur de la liste. Cela entrainerait une dégradation malheureuse de la ressource graphique.



Merci à Nemau d'avoir mis en évidence le problème.


sriden - posté le 27/01/2015 à 18:45:41. (15535 messages postés) - roi

Citation:

Le pixel-art subit parfois une grande dégradation.


C'est pas vraiment quand on fait du pixel-art que le problème va se poser, c'est surtout quand on importe des illus de type non pixel-art, comme les décors de Sylvanor. :s
Mais gg.

 

Forum du FAMAS | Escapade | La 7e porte (jeu multimaker complet) | Vader Ou La Fin des Haricots | Polaris 03 | Ma zyk : Diaphanous Horizons


Monos - posté le 28/01/2015 à 05:51:11. (56278 messages postés) - admin

Vive le making libre

Ah je ne savais pas que Rm 2k et 2k3 avait une palette de 65536 couleurs et pas de "true colors".

Merci de l'info.

Pixner|Offgame | Le comptoire des clikeurs


Roi of the Suisse - posté le 29/01/2015 à 04:10:38. (19813 messages postés) - bocauxharam

top kek

sriden a dit:

C'est pas vraiment quand on fait du pixel-art que le problème va se poser, c'est surtout quand on importe des illus de type non pixel-art, comme les décors de Sylvanor.

Bah à la base le problème est venu de Shin, qui s'est plaint que son décor pixel-art avait été bousillé par RM2003 : plusieurs couleurs ont été transformées en la même couleur transformant l'image en bouillie.

Au contraire je pense que pour un mec comme Sylvanor, qui fait du painting, c'est foutu d'avance parce qu'il faudrait qu'il convertisse son painting en pixel art. Limite le choix des couleurs lors du painting est flou et moins soigneux, donc une fusion locale des couleurs est moins dangereuse.
Mais tu as raison dans la mesure où la fusion de couleurs sur une vraie image (comme le pont d'Osaka dans mon exemple) entraine un effet de zones assez dégueulasse.


Ce qui serait intéressant, ce serait un logiciel qui transforme les couleurs hors-liste en dithering de deux couleurs de la liste. Parce qu'avec du dithering 1bit on peut atteindre une bien meilleure approximation de l'image que sans dithering.

http://fr.wikipedia.org/wiki/Tramage_%28informatique%29

image

Es-tu une star ? | Kujira no Hara (meilleur jeu du monde) : télécharger les 5 premiers chapitres, topic du jeu


Nemau - posté le 29/01/2015 à 04:21:16. (29688 messages postés) - admin

En toute amitié

Oui j'allais faire la même remarque que srid : le terme "pixel-art" est mal choisi, vu que les couleurs seront altérées quel que soit le style des graphismes.

Pour le reste cf. mes remarques sur Level Up!.

Et merci de m'avoir crédité, t'es chou ! Même si c'est Zimsse qui t'a dit de le faire. =>[]

Citation:

- ou alors vérifiez que la couleur que vous utilisez correspond bien aux formules mathématiques énoncées ci-dessus.


Sous Paint Shop Pro il suffit d'utiliser la sélection par couleur : avec cet outil il suffit de cliquer sur un pixel de telle couleur pour que tous les autres pixels ayant cette couleur soient sélectionnés. Ainsi, en mettant la palette d'RM sur la même image, on voit tout de suite si la couleur qu'on a choisi est présente sur cette palette. Je suppose que Photoshop possède un outil équivalent.

Notez quand même que les 65536 couleurs d'RM 2000/03 ne représentent que 0,4% des 16777216 couleurs existantes (soit 1/256), donc si pour un sprite vous utilisez une couleur au pif il n'y a que 0,4% de chance qu'elle soit sur la palette d'RM. Donc il est plus judicieux de sélectionner directement les couleurs à partir de cette palette (dernière image de l'article).


Edit :

Citation:

Ce qui serait intéressant, ce serait un logiciel qui transforme les couleurs hors-liste en dithering de deux couleurs de la liste. Parce qu'avec du dithering 1bit on peut atteindre une bien meilleure approximation de l'image que sans dithering.


Souvent, lorsqu'un jeu RM 2000/03 est en mode agrandi x2 (640*480), le dithering se voit trop et ne rend du coup rien de bon. Donc ce que tu proposes pourrait quand même parfois donner de bons résultats, mais parfois seulement.

Trombinoscope ~ Calli ~ Polaris 03 ~ Le Famas ~ Level Up! ~ Les Forges


Roi of the Suisse - posté le 29/01/2015 à 06:17:51. (19813 messages postés) - bocauxharam

top kek

Il y a plusieurs types de ditherings. Ce dont tu parles est sûrement le dithering de Bayer, dit "dithering ordonné" :

image


Sinon j'ai fait un programme qui transforme une image avec la palette RM2003, mais en utilisant l'algorithme de dithering de Floyd-Steinberg :

image
à gauche la même image avec un dithering de Floyd-Steinberg, à droite l'image telle que RM2003 la transformerait (on reconnait les zones kaki)

image
image originelle

Es-tu une star ? | Kujira no Hara (meilleur jeu du monde) : télécharger les 5 premiers chapitres, topic du jeu


Nemau - posté le 29/01/2015 à 06:30:01. (29688 messages postés) - admin

En toute amitié

J'avoue, avec ton système ça rend plutôt bienxe.

Trombinoscope ~ Calli ~ Polaris 03 ~ Le Famas ~ Level Up! ~ Les Forges


Roi of the Suisse - posté le 29/01/2015 à 08:36:47. (19813 messages postés) - bocauxharam

top kek

Voilà le programme qui transforme les images PNG du dossier en images
- aux couleurs de la palette RM2003
- avec un dithering de Floyd-Steinberg
:

http://www.mediafire.com/download/x70crcqgedbu8nq/dithering.zip

Il suffit de mettre les images PNG (pixel art ou painting) dans le dossier avec le programme et de cliquer sur le programme (EXE). L'image sera convertie dans la palette RM2003, mais sera plus ressemblante à l'originale grâce au dithering.
Le programme ne marche que sur les PC 64bits je crois.

Voici la source :

Portion de code : Tout sélectionner

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
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
package main;
 
import java.awt.Color;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import javax.imageio.ImageIO;
 
public class Main {
        public static void main(String[] args) throws IOException{
                String directory = System.getProperty("user.dir");
        directory = directory.replace("\\", "/");
        File dir = new File(directory);
                File[] directoryListing = dir.listFiles();
                if (directoryListing != null) {
                        for (File file : directoryListing) { //pour chaque fichier du dossier
                                System.out.println(file.getName());
                                try{
                                        BufferedImage img = ImageIO.read(file);
                                        int width = img.getWidth();
                                        int height = img.getHeight();
                                        for(int y=0; y<height; y++){
                                                for(int x=0; x<width; x++){
                                                        Color couleurDeLImage = new Color(img.getRGB(x, y));
                                                        int rImage = couleurDeLImage.getRed();
                                                        int vImage = couleurDeLImage.getGreen();
                                                        int bImage = couleurDeLImage.getBlue();
                                                        //on cherche la couleur de la palette correspondante
                                                        int rPalette = (int) (((double) rImage)/(8.25));
                                                        int vPalette = (int) (((double) vImage)/(4.0625));
                                                        int bPalette = (int) (((double) bImage)/(8.25));
                                                        rPalette = rPalette*8 + (int)(rPalette/4);
                                                        vPalette = vPalette*4 + (int)(vPalette/16);
                                                        bPalette = bPalette*8 + (int)(bPalette/4);
                                                        Color couleurPalette = new Color(rPalette,vPalette,bPalette);
                                                        img.setRGB(x, y, colorToInt(couleurPalette) ); //on remplace la couleur de l'image par celle de la palette
        
                                                        //on transfère l'erreur aux pixels voisins
                                                        int ecartR = rImage - rPalette; 
                                                        int ecartV = vImage - vPalette;
                                                        int ecartB = bImage - bPalette;
                                                        if(x+1!=width){
                                                                couleurDeLImage = new Color(img.getRGB(x+1, y));
                                                                Color couleurDeplacee;
                                                                couleurDeplacee = new Color(Math.max(0,Math.min(255,couleurDeLImage.getRed()  +(int)(((double)ecartR)*0.4375))), 
                                                                                                                        Math.max(0,Math.min(255,couleurDeLImage.getGreen()+(int)(((double)ecartV)*0.4375))), 
                                                                                                                        Math.max(0,Math.min(255,couleurDeLImage.getBlue() +(int)(((double)ecartB)*0.4375))) );
                                                                img.setRGB(x+1, y, colorToInt(couleurDeplacee) );
                                                        }
                                                        if(x!=0 && y+1!=height){
                                                                couleurDeLImage = new Color(img.getRGB(x-1, y+1));
                                                                Color couleurDeplacee;
                                                                couleurDeplacee = new Color(Math.max(0,Math.min(255,couleurDeLImage.getRed()  +(int)(((double)ecartR)*0.1875))), 
                                                                                                                        Math.max(0,Math.min(255,couleurDeLImage.getGreen()+(int)(((double)ecartV)*0.1875))), 
                                                                                                                        Math.max(0,Math.min(255,couleurDeLImage.getBlue() +(int)(((double)ecartB)*0.1875))) );
                                                                img.setRGB(x-1, y+1, colorToInt(couleurDeplacee) );
                                                        }
                                                        if(y+1!=height){
                                                                couleurDeLImage = new Color(img.getRGB(x, y+1));
                                                                Color couleurDeplacee;
                                                                couleurDeplacee = new Color(Math.max(0,Math.min(255,couleurDeLImage.getRed()  +(int)(((double)ecartR)*0.3125))), 
                                                                                                                        Math.max(0,Math.min(255,couleurDeLImage.getGreen()+(int)(((double)ecartV)*0.3125))), 
                                                                                                                        Math.max(0,Math.min(255,couleurDeLImage.getBlue() +(int)(((double)ecartB)*0.3125))) );
                                                                img.setRGB(x, y+1, colorToInt(couleurDeplacee) );
                                                        }
                                                        if(x+1!=width && y+1!=height){
                                                                couleurDeLImage = new Color(img.getRGB(x+1, y+1));
                                                                Color couleurDeplacee;
                                                                couleurDeplacee = new Color(Math.max(0,Math.min(255,couleurDeLImage.getRed()  +(int)(((double)ecartR)*0.0625))), 
                                                                                                                        Math.max(0,Math.min(255,couleurDeLImage.getGreen()+(int)(((double)ecartV)*0.0625))), 
                                                                                                                        Math.max(0,Math.min(255,couleurDeLImage.getBlue() +(int)(((double)ecartB)*0.0625))) );
                                                                img.setRGB(x+1, y+1, colorToInt(couleurDeplacee) );
                                                        }
                                                }
                                        }
                                        String nom = file.getName().replace(".png", "").replace(".jpg", "").replace(".bpm", "");
                                        File outputfile = new File(directory+"/"+nom+".png");
                                        System.out.println(directory+"/"+nom+".png");
                                        ImageIO.write(img, "png", outputfile);
                                }catch(Exception e){
                                        //erreur, si le fichier n'est pas une image par exemple
                                        e.printStackTrace();
                                }
                    }
                }
                
                System.out.println("fini !");
        }
        
        public static int colorToInt(Color col){
                int Red = col.getRed();
                int Green = col.getGreen();
                int Blue = col.getBlue();
            Red = (Red << 16) & 0x00FF0000;
            Green = (Green << 8) & 0x0000FF00; 
            Blue = Blue & 0x000000FF; 
            return 0xFF000000 | Red | Green | Blue;
        }
}


Voici un exemple d'image transformée :

image

On ne dirait pas que c'est du 16bits, hein :kirby

Es-tu une star ? | Kujira no Hara (meilleur jeu du monde) : télécharger les 5 premiers chapitres, topic du jeu


Nemau - posté le 03/02/2015 à 02:07:52. (29688 messages postés) - admin

En toute amitié

image

image

=> Ton logiciel utilise la palette de RM 2000/03 et une méthode de dithering, mais ne limite pas son nombre de couleurs par image à 256. Du coup les images créées avec ton logiciel ne servent pas à grand chose ! \o/

Trombinoscope ~ Calli ~ Polaris 03 ~ Le Famas ~ Level Up! ~ Les Forges


Roi of the Suisse - posté le 05/02/2015 à 09:12:37. (19813 messages postés) - bocauxharam

top kek

Si !

Là c'était une image de test. Il faut évidemment prendre un cas concret : Shin.
Shin a fait un pixel art avec des couleurs trop proches. Son pixel art comporte forcément moins de 256 couleurs. En utilisant l'algorithme ci-dessus, il peut obtenir une image très ressemblante sans que deux zones ne se mélangent (comme c'était le cas).
La deuxième solution consiste à prendre des couleurs éloignées, mais il a choisi volontairement des couleurs précises, donc avec des couleurs éloignées il n'aura pas forcément le résultat qu'il souhaitait.

Autre cas concret : sriden. Son dessin comporte assez peu de couleurs pour que l'algorithme lui ponde de moins de 256.

Es-tu une star ? | Kujira no Hara (meilleur jeu du monde) : télécharger les 5 premiers chapitres, topic du jeu


Nemau - posté le 06/02/2015 à 04:30:47. (29688 messages postés) - admin

En toute amitié

Oki, autant pour oim.

N'empêche, ce serait ultime un logiciel qui convertisse n'importe quelle image en 256 couleurs avec la palette RM. Et avec une simple option à cocher si on veut en plus utiliser ta technique de dithering.

Enfin, je dis ça, mais en 15 ans d'existence de RM 2000/03, les gens qui se sont plaints de cette altération des couleurs se comptent sur les doigts d'une main. x) Sans compter que beaucoup préfèreront utiliser le patch de Cherry pour ne plus limiter le nombre de couleurs.

Trombinoscope ~ Calli ~ Polaris 03 ~ Le Famas ~ Level Up! ~ Les Forges

Suite à de nombreux abus, le post en invités a été désactivé. Veuillez vous inscrire si vous souhaitez participer à la conversation.

Haut de page

Merci de ne pas reproduire le contenu de ce site sans autorisation.
Contacter l'équipe

Plan du site:

Activité: Accueil | News | Forum | Flash-news | Chat | Commentaires | Galerie | Screen de la semaine | Sorties | Articles perso | Livre d'or | Recherche
Jeux: Index jeux séparés | Top Classiques | Top Originaux | Les autres | RPG Maker 95 | RPG Maker 2000 | RPG Maker 2003 | RPG Maker XP | RPG Maker VX | RPG Maker VX Ace | RPG Maker MV | Autres | Jeux complets | Proposer
Rubriques: Le Wiki | Collection Oniro | Tutoriaux | Scripts | Guides | Gaming-Live | Tests | Making-of | Interviews | Articles perso | OST | L'Annuaire | Divers | Palmarès
Hébergés: Aëdemphia | Fighting Robots Quest | Forstale | Geex | Inexistence | La Légende d'Ibabou | Lije | LoveMaster | Sarcia | Super Mario RPG - Lost Souls
Ressources: Jeux | Programmes | Packs de ressources | Midis | Eléments séparés | Sprites
RPG Maker 2000/2003: Chipsets | Charsets | Panoramas | Backdrops | Facesets | Battle anims | Battle charsets | Monstres | Systems | Templates
RPG Maker XP: Tilesets | Autotiles | Characters | Battlers | Window skins | Icônes | Transitions | Fogs | Templates
RPG Maker VX: Tilesets | Charsets | Facesets | Systèmes
RPG Maker MV: Tilesets | Characters | Faces | Systèmes | Title | Battlebacks | Animations | SV/Ennemis