From 306a004e3627b89465b411a2a713d79ea73ffd36 Mon Sep 17 00:00:00 2001 From: Adrien Destugues Date: Sat, 14 Apr 2007 20:18:30 +0000 Subject: [PATCH] First upload of the code. git-svn-id: svn://pulkomandy.tk/GrafX2/trunk@2 416bcca6-2ee7-4201-b75f-2eb2f807beb1 --- aide.h | 2 + boutons.c | 5487 +++++++++++++++++++++++++++ boutons.h | 160 + cfg/ASCKEY.EXE | Bin 0 -> 2640 bytes cfg/ASCKEY.PAS | 11 + cfg/KEYS.EXE | Bin 0 -> 3760 bytes cfg/KEYS.PAS | 62 + cfg/SCANCODE.PAS | 1040 ++++++ cfg/VIDEOMOD.PAS | 72 + cfg/gfxcfg.pas | 1772 +++++++++ const.h | 449 +++ dat/FONTE1.FNT | Bin 0 -> 2048 bytes dat/FONTE2.FNT | Bin 0 -> 2048 bytes dat/FONTS.PKM | Bin 0 -> 38138 bytes dat/GFX2.PKM | Bin 0 -> 26703 bytes dat/GREETS.TXT | 147 + dat/HLP_CRDT.PAS | 109 + dat/HLP_GRET.PAS | 67 + dat/HLP_RGST.PAS | 52 + dat/IMG2FNT.EXE | Bin 0 -> 4544 bytes dat/IMG2FNT.PAS | 88 + dat/MAKEDAT.EXE | Bin 0 -> 18128 bytes dat/MAKEDAT.PAS | 738 ++++ dat/MAKEFNT.BAT | 3 + dat/MKGREETS.EXE | Bin 0 -> 4384 bytes dat/MKGREETS.PAS | 105 + dat/TABLES.PAS | 259 ++ dat/gfx2.ini | 289 ++ divers.c | 93 + divers.h | 133 + doc/Le moteur des opérations.html | 384 ++ doc/Les entrées.html | 176 + doc_eng.txt | 1983 ++++++++++ doc_fra.txt | 2113 +++++++++++ dpmi.asm | 472 +++ dpmi.h | 20 + file_id.diz | 21 + files.c | 539 +++ files.h | 33 + gfx2.cfg | Bin 0 -> 10351 bytes gfx2.dat | 322 ++ gfx2.gif | Bin 0 -> 1149 bytes gfx2.ico | Bin 0 -> 766 bytes gfx2.ini | 289 ++ gfx2_fra.cfg | Bin 0 -> 10286 bytes gfx2_mem.bat | 73 + global.h | 756 ++++ graph.c | 5750 +++++++++++++++++++++++++++++ graph.h | 154 + history.txt | 273 ++ init.c | 2137 +++++++++++ init.h | 15 + linux.c | 17 + linux.h | 9 + loadsave.c | 5321 ++++++++++++++++++++++++++ loadsave.h | 69 + main.c | 631 ++++ make.inc | 4 + makefile | 62 + mcnormal.asm | 227 ++ mcpourp2.asm | 246 ++ modesvdo.h | 219 ++ moteur.c | 1860 ++++++++++ moteur.h | 45 + op_asm.asm | 1498 ++++++++ op_asm.h | 153 + op_c.c | 1266 +++++++ op_c.h | 190 + operatio.c | 4301 +++++++++++++++++++++ operatio.h | 171 + pages.c | 1016 +++++ pages.h | 71 + palette.c | 1834 +++++++++ palette.h | 2 + readini.c | 642 ++++ readini.h | 1 + readline.c | 255 ++ readline.h | 9 + readme!.1st | 145 + readme.txt | 60 + saveini.c | 502 +++ saveini.h | 1 + sdlscreen.h | 33 + shade.c | 1073 ++++++ shade.h | 6 + special.c | 327 ++ special.h | 13 + struct.h | 213 ++ tech_eng.txt | 732 ++++ tech_fra.txt | 769 ++++ testvesa/comp.bat | 7 + testvesa/make.inc | 4 + testvesa/makefile | 8 + testvesa/testvesa.c | 196 + testvesa/testvesa.exe | Bin 0 -> 40426 bytes testvesa/vesa.asm | 237 ++ testvesa/vesa.h | 82 + testvesa/weoslite.exe | Bin 0 -> 13078 bytes todo.txt | 26 + 99 files changed, 51201 insertions(+) create mode 100644 aide.h create mode 100644 boutons.c create mode 100644 boutons.h create mode 100644 cfg/ASCKEY.EXE create mode 100644 cfg/ASCKEY.PAS create mode 100644 cfg/KEYS.EXE create mode 100644 cfg/KEYS.PAS create mode 100644 cfg/SCANCODE.PAS create mode 100644 cfg/VIDEOMOD.PAS create mode 100644 cfg/gfxcfg.pas create mode 100644 const.h create mode 100644 dat/FONTE1.FNT create mode 100644 dat/FONTE2.FNT create mode 100644 dat/FONTS.PKM create mode 100644 dat/GFX2.PKM create mode 100644 dat/GREETS.TXT create mode 100644 dat/HLP_CRDT.PAS create mode 100644 dat/HLP_GRET.PAS create mode 100644 dat/HLP_RGST.PAS create mode 100644 dat/IMG2FNT.EXE create mode 100644 dat/IMG2FNT.PAS create mode 100644 dat/MAKEDAT.EXE create mode 100644 dat/MAKEDAT.PAS create mode 100644 dat/MAKEFNT.BAT create mode 100644 dat/MKGREETS.EXE create mode 100644 dat/MKGREETS.PAS create mode 100644 dat/TABLES.PAS create mode 100644 dat/gfx2.ini create mode 100644 divers.c create mode 100644 divers.h create mode 100644 doc/Le moteur des opérations.html create mode 100644 doc/Les entrées.html create mode 100644 doc_eng.txt create mode 100644 doc_fra.txt create mode 100644 dpmi.asm create mode 100644 dpmi.h create mode 100644 file_id.diz create mode 100644 files.c create mode 100644 files.h create mode 100644 gfx2.cfg create mode 100644 gfx2.dat create mode 100644 gfx2.gif create mode 100644 gfx2.ico create mode 100644 gfx2.ini create mode 100644 gfx2_fra.cfg create mode 100644 gfx2_mem.bat create mode 100644 global.h create mode 100644 graph.c create mode 100644 graph.h create mode 100644 history.txt create mode 100644 init.c create mode 100644 init.h create mode 100644 linux.c create mode 100644 linux.h create mode 100644 loadsave.c create mode 100644 loadsave.h create mode 100644 main.c create mode 100644 make.inc create mode 100644 makefile create mode 100644 mcnormal.asm create mode 100644 mcpourp2.asm create mode 100644 modesvdo.h create mode 100644 moteur.c create mode 100644 moteur.h create mode 100644 op_asm.asm create mode 100644 op_asm.h create mode 100644 op_c.c create mode 100644 op_c.h create mode 100644 operatio.c create mode 100644 operatio.h create mode 100644 pages.c create mode 100644 pages.h create mode 100644 palette.c create mode 100644 palette.h create mode 100644 readini.c create mode 100644 readini.h create mode 100644 readline.c create mode 100644 readline.h create mode 100644 readme!.1st create mode 100644 readme.txt create mode 100644 saveini.c create mode 100644 saveini.h create mode 100644 sdlscreen.h create mode 100644 shade.c create mode 100644 shade.h create mode 100644 special.c create mode 100644 special.h create mode 100644 struct.h create mode 100644 tech_eng.txt create mode 100644 tech_fra.txt create mode 100644 testvesa/comp.bat create mode 100644 testvesa/make.inc create mode 100644 testvesa/makefile create mode 100644 testvesa/testvesa.c create mode 100644 testvesa/testvesa.exe create mode 100644 testvesa/vesa.asm create mode 100644 testvesa/vesa.h create mode 100644 testvesa/weoslite.exe create mode 100644 todo.txt diff --git a/aide.h b/aide.h new file mode 100644 index 00000000..a0eaa137 --- /dev/null +++ b/aide.h @@ -0,0 +1,2 @@ +void Bouton_Aide(void); +void Bouton_Stats(void); diff --git a/boutons.c b/boutons.c new file mode 100644 index 00000000..28f21d4c --- /dev/null +++ b/boutons.c @@ -0,0 +1,5487 @@ +#include "const.h" +#include "struct.h" +#include "global.h" +#include "divers.h" +#include "graph.h" +#include "moteur.h" +#include "readline.h" +#include "files.h" +#include "loadsave.h" +#include "init.h" +#include +#include + +#include +#include +#include +#include +#include +#include "boutons.h" +#include "operatio.h" + +// On dclare mchamment le prototype de Erreur pour viter de faire un +// fichier "main.h": +void Erreur(int Code); + +//-- MODELE DE BOUTON DE MENU ------------------------------------------------ +/* +void Bouton_***(void) +{ + short Bouton_clicke; + + Ouvrir_fenetre(310,190,"***"); + + Fenetre_Definir_bouton_normal(103,137,80,14,"OK",0,1,0x001C); // 1 + Fenetre_Definir_bouton_scroller(18,44,88,16,4,0); // 2 + + Afficher_curseur(); + + do + { + Bouton_clicke=Fenetre_Bouton_clicke(); + } + while (Bouton_clicke!=1); + + Fermer_fenetre(); + Desenclencher_bouton(BOUTON_***); + Afficher_curseur(); +} +*/ + + +void Message_Non_disponible(void) +{ + short Bouton_clicke; + + Ouvrir_fenetre(160,76,"Not available yet!"); + + Print_dans_fenetre(8,20,"This function will",CM_Noir,CM_Clair); + Print_dans_fenetre(12,28,"be implemented in",CM_Noir,CM_Clair); + Print_dans_fenetre(16,36,"a later version.",CM_Noir,CM_Clair); + Fenetre_Definir_bouton_normal(60,53,40,14,"OK",1,1,0x001C); // 1 + Afficher_curseur(); + + do + Bouton_clicke=Fenetre_Bouton_clicke(); + while ((Bouton_clicke<=0) && (Touche!=0x0001) && (Touche!=0x0018)); + + Fermer_fenetre(); + + // Puisque cette fonction peut tre appele par plusieurs boutons et qu'on + // ne sait pas lequel c'est, on les dsenclenche tous. De toutes faons, a + // ne sert rien d'essayer d'optimiser a puisque l'utilisateur ne devrait + // pas souvent l'appeler, et en plus y'en a pas beaucoup dsenclencher. ;) + Desenclencher_bouton(BOUTON_GRADRECT); + Desenclencher_bouton(BOUTON_TEXTE); + + Afficher_curseur(); +} + + +void Message_Memoire_insuffisante(void) +{ + short Bouton_clicke; + + Ouvrir_fenetre(216,76,"Not enough memory!"); + + Print_dans_fenetre(8,20,"Please consult the manual",CM_Noir,CM_Clair); + Print_dans_fenetre(24,28,"to know how to obtain",CM_Noir,CM_Clair); + Print_dans_fenetre(36,36,"more memory space.",CM_Noir,CM_Clair); + Fenetre_Definir_bouton_normal(60,53,40,14,"OK",1,1,0x001C); // 1 + Afficher_curseur(); + + do + Bouton_clicke=Fenetre_Bouton_clicke(); + while ((Bouton_clicke<=0) && (Touche!=0x0001) && (Touche!=0x0018)); + + Fermer_fenetre(); + Afficher_curseur(); +} + + +void Bouton_Message_initial(void) +{ + short Bouton_clicke; + char Chaine[21]; + int Pos_X,Offs_Y,X,Y; + + sprintf(Chaine,"GrafX 2.00 %s%s",ALPHA_BETA,POURCENTAGE_VERSION); + Ouvrir_fenetre(260,172,Chaine); + + Fenetre_Afficher_cadre_creux(10,20,239,62); + Block(Fenetre_Pos_X+(Menu_Facteur_X*11), + Fenetre_Pos_Y+(Menu_Facteur_Y*21), + Menu_Facteur_X*237,Menu_Facteur_Y*60,CM_Noir); + for (Y=23,Offs_Y=0; Y<79; Offs_Y+=231,Y++) + for (X=14,Pos_X=0; Pos_X<231; Pos_X++,X++) + Pixel_dans_fenetre(X,Y,Logo_GrafX2[Offs_Y+Pos_X]); + + Print_dans_fenetre(27, 88,"Copyright (c) 1996-1999 by",CM_Fonce,CM_Clair); + Print_dans_fenetre(79, 96,"Sunset Design",CM_Noir,CM_Clair); + Print_dans_fenetre(55,104,"All rights reserved",CM_Fonce,CM_Clair); + + Print_dans_fenetre( 7,120,"You should read the README!.1ST",CM_Fonce,CM_Clair); + Print_dans_fenetre( 7,128,"file before using this program",CM_Fonce,CM_Clair); + Print_dans_fenetre( 7,136,"for the first time.",CM_Fonce,CM_Clair); + + if ((*ALPHA_BETA)=='') + { + Print_char_transparent_dans_fenetre(43,119,'M',CM_Noir); + Print_char_transparent_dans_fenetre(53,121,'U',CM_Noir); + Print_char_transparent_dans_fenetre(63,119,'S',CM_Noir); + Print_char_transparent_dans_fenetre(74,120,'T',CM_Noir); + } + + Fenetre_Definir_bouton_normal(90,151,80,14,"OK",0,1,0x001C); // 1 + + Afficher_curseur(); + + do + { + Bouton_clicke=Fenetre_Bouton_clicke(); + } + while ((Bouton_clicke!=1) && (Touche!=0x0001) && (Touche!=0x0018)); + + Fermer_fenetre(); + Afficher_curseur(); +} + + + +void Changer_la_forme_du_pinceau(byte Forme) +{ + Pinceau_Forme=Forme; + Afficher_pinceau_dans_menu(); + + switch (Operation_en_cours) + { + case OPERATION_FILL : + Pinceau_Forme_avant_fill=Forme; + Pinceau_Forme=FORME_PINCEAU_POINT; + break; + case OPERATION_PIPETTE : + Pinceau_Forme_avant_pipette=Forme; + Pinceau_Forme=FORME_PINCEAU_POINT; + break; + // Note: Il existe un Pinceau_Forme_avant_lasso, mais comme le lasso aura + // t automatiquement dsactiv avant d'arriver ici, y'a pas de problme. + } +} + + +//-------------------------------- UNDO/REDO --------------------------------- +void Bouton_Undo(void) +{ + Effacer_curseur(); + Undo(); + + Set_palette(Principal_Palette); + Calculer_couleurs_menu_optimales(Principal_Palette); + + Afficher_ecran(); + Desenclencher_bouton(BOUTON_UNDO); + Tracer_cadre_de_bouton_du_menu(BOUTON_LOUPE,Loupe_Mode); + Afficher_menu(); + Afficher_curseur(); +} + +void Bouton_Redo(void) +{ + Effacer_curseur(); + Redo(); + + Set_palette(Principal_Palette); + Calculer_couleurs_menu_optimales(Principal_Palette); + + Afficher_ecran(); + Desenclencher_bouton(BOUTON_UNDO); + Tracer_cadre_de_bouton_du_menu(BOUTON_LOUPE,Loupe_Mode); + Afficher_menu(); + Afficher_curseur(); +} + + +//---------------------------- SCROLL PALETTE LEFT --------------------------- +void Bouton_Pal_left(void) +{ + Effacer_curseur(); + if (Couleur_debut_palette) + { + Couleur_debut_palette-=8; + Afficher_palette_du_menu(); + } + Desenclencher_bouton(BOUTON_PAL_LEFT); + Afficher_curseur(); +} + +void Bouton_Pal_left_fast(void) +{ + Effacer_curseur(); + if (Couleur_debut_palette) + { + Couleur_debut_palette=(Couleur_debut_palette>=64)? Couleur_debut_palette-64 : 0; + Afficher_palette_du_menu(); + } + Desenclencher_bouton(BOUTON_PAL_LEFT); + Afficher_curseur(); +} + + +//--------------------------- SCROLL PALETTE RIGHT --------------------------- +void Bouton_Pal_right(void) +{ + Effacer_curseur(); + if (Couleur_debut_palette<=184) + { + Couleur_debut_palette+=8; + Afficher_palette_du_menu(); + } + Desenclencher_bouton(BOUTON_PAL_RIGHT); + Afficher_curseur(); +} + +void Bouton_Pal_right_fast(void) +{ + Effacer_curseur(); + if (Couleur_debut_palette<=184) + { + Couleur_debut_palette=(Couleur_debut_palette<=120)? Couleur_debut_palette+64 : 192; + Afficher_palette_du_menu(); + } + Desenclencher_bouton(BOUTON_PAL_RIGHT); + Afficher_curseur(); +} + +//-------------------- Choix de la forecolor dans le menu -------------------- +void Bouton_Choix_forecolor(void) +{ + word Pos_X, Pos_Y; + + Pos_X=(Mouse_X/Menu_Facteur_X)-(LARGEUR_MENU+1); + Pos_Y=((Mouse_Y-Menu_Ordonnee)/Menu_Facteur_Y)-2; + + if ((!Config.Couleurs_separees) + || ((Pos_X%Menu_Taille_couleur!=Menu_Taille_couleur-1) && ((Pos_Y&3)!=3))) + { + Effacer_curseur(); + Encadrer_couleur_menu(CM_Noir); + Fore_color=Couleur_debut_palette+((Pos_X/Menu_Taille_couleur)<<3)+(Pos_Y>>2); + Encadrer_couleur_menu(CM_Blanc); + Afficher_foreback(); + Afficher_curseur(); + } +} + +//-------------------- Choix de la backcolor dans le menu -------------------- +void Bouton_Choix_backcolor(void) +{ + word Pos_X, Pos_Y; + + Pos_X=(Mouse_X/Menu_Facteur_X)-(LARGEUR_MENU+1); + Pos_Y=((Mouse_Y-Menu_Ordonnee)/Menu_Facteur_Y)-2; + + if ((!Config.Couleurs_separees) + || ((Pos_X%Menu_Taille_couleur!=Menu_Taille_couleur-1) && ((Pos_Y&3)!=3))) + { + Effacer_curseur(); + Back_color=Couleur_debut_palette+((Pos_X/Menu_Taille_couleur)<<3)+(Pos_Y>>2); + Afficher_foreback(); + Afficher_curseur(); + } +} + + +//---------------------- Cacher ou rafficher le menu ------------------------ +void Pixel_dans_barre_d_outil_cachee(word X,word Y,byte Couleur) +{ + // C'est fait exprs que ce soit vide... + // C'est parce que y'a rien du tout afficher vu que la barre d'outil est + // cache... C'est simple non? +} + + +void Bouton_Cacher_menu(void) +{ + Effacer_curseur(); + if (Menu_visible) + { + Menu_visible=0; + Pixel_dans_menu=Pixel_dans_barre_d_outil_cachee; + Menu_Ordonnee=Hauteur_ecran; + + if (Loupe_Mode) + { + Calculer_donnees_loupe(); + if (Loupe_Decalage_Y+Loupe_Hauteur>Principal_Hauteur_image) + { + if (Loupe_Hauteur>Principal_Hauteur_image) + Loupe_Decalage_Y=0; + else + Loupe_Decalage_Y=Principal_Hauteur_image-Loupe_Hauteur; + } + } + + // On repositionne le dcalage de l'image pour qu'il n'y ait pas d'in- + // -cohrences lorsqu'on sortira du mode Loupe. + if (Principal_Decalage_Y+Hauteur_ecran>Principal_Hauteur_image) + { + if (Hauteur_ecran>Principal_Hauteur_image) + Principal_Decalage_Y=0; + else + Principal_Decalage_Y=Principal_Hauteur_image-Hauteur_ecran; + } + // On fait pareil pour le brouillon + if (Brouillon_Decalage_Y+Hauteur_ecran>Brouillon_Hauteur_image) + { + if (Hauteur_ecran>Brouillon_Hauteur_image) + Brouillon_Decalage_Y=0; + else + Brouillon_Decalage_Y=Brouillon_Hauteur_image-Hauteur_ecran; + } + + Calculer_donnees_loupe(); + if (Loupe_Mode) + Recadrer_ecran_par_rapport_au_zoom(); + Calculer_limites(); + Calculer_coordonnees_pinceau(); + Afficher_ecran(); + } + else + { + Menu_visible=1; + Pixel_dans_menu=Pixel_dans_barre_d_outil; + Menu_Ordonnee=Hauteur_ecran-(HAUTEUR_MENU*Menu_Facteur_Y); + + Calculer_donnees_loupe(); + if (Loupe_Mode) + Recadrer_ecran_par_rapport_au_zoom(); + Calculer_limites(); + Calculer_coordonnees_pinceau(); + Afficher_menu(); + if (Loupe_Mode) + Afficher_ecran(); + } + Desenclencher_bouton(BOUTON_CACHER); + Afficher_curseur(); +} + + +//--------------------------- Quitter le programme --------------------------- +byte Bouton_Quitter_Routine_locale(void) +{ + short Bouton_clicke; + byte Enregistrer; + char Nom_du_fichier[256]; + byte Ancienne_forme_curseur; + + if (!Principal_Image_modifiee) + return 1; + + // On commence par afficher la fentre de QUIT + Ouvrir_fenetre(160,84,"Quit ?"); + Fenetre_Definir_bouton_normal(20,20,120,14,"Stay",0,1,0x0001); // 1 + Fenetre_Definir_bouton_normal(20,40,120,14,"Save & quit",1,1,0x001F); // 2 + Fenetre_Definir_bouton_normal(20,60,120,14,"Discard (Quit)",1,1,0x0020);// 3 + Afficher_curseur(); + + do + { + Bouton_clicke=Fenetre_Bouton_clicke(); + } + while (Bouton_clicke<=0); + Attendre_fin_de_click(); + + Fermer_fenetre(); + Afficher_curseur(); + + switch(Bouton_clicke) + { + case 1 : return 0; // Rester + case 2 : // Sauver et enregistrer + Nom_fichier_complet(Nom_du_fichier,0); + if ( (!Fichier_existe(Nom_du_fichier)) || Demande_de_confirmation("Erase old file ?") ) + { + Effacer_curseur(); + Ancienne_forme_curseur=Forme_curseur; + Forme_curseur=FORME_CURSEUR_SABLIER; + Afficher_curseur(); + + Sauver_image(1); + + Effacer_curseur(); + Forme_curseur=Ancienne_forme_curseur; + Afficher_curseur(); + + if (!Erreur_fichier) + // L'ayant sauve avec succs, + return 1; // On peut quitter + else + // Il y a eu une erreur lors de la sauvegarde, + return 0; // On ne peut donc pas quitter + } + else + // L'utilisateur ne veut pas craser l'ancien fichier, + return 0; // On doit donc rester + case 3 : return 1; // Quitter + } + return 0; +} + + +void Bouton_Quit(void) +{ + short Bouton_clicke; + + if (Bouton_Quitter_Routine_locale()) + { + if (Brouillon_Image_modifiee) + { + Bouton_Page(); // On passe sur le brouillon + // Si l'utilisateur prsente les derniers symptomes de l'abandon + if (Bouton_Quitter_Routine_locale()) + Sortir_du_programme=1; + } + else + Sortir_du_programme=1; + } + + if ( (Menu_visible) && (Mouse_Y+8>Menu_Ordonnee) ) + Effacer_curseur(); + + Desenclencher_bouton(BOUTON_QUIT); + + if ( (Menu_visible) && (Mouse_Y+8>Menu_Ordonnee) ) + Afficher_curseur(); +} + + +//---------------------------- Effacer l'cran ------------------------------- +void Bouton_Clear(void) +{ + Effacer_curseur(); + Backup(); + if (Stencil_Mode && Config.Clear_with_stencil) + Effacer_image_courante_Stencil(0,Stencil); + else + Effacer_image_courante(0); + Afficher_ecran(); + Desenclencher_bouton(BOUTON_CLEAR); + Afficher_curseur(); +} + +void Bouton_Clear_colore(void) +{ + Effacer_curseur(); + Backup(); + if (Stencil_Mode && Config.Clear_with_stencil) + Effacer_image_courante_Stencil(Back_color,Stencil); + else + Effacer_image_courante(Back_color); + Afficher_ecran(); + Desenclencher_bouton(BOUTON_CLEAR); + Afficher_curseur(); +} + + +//---------- Menu dans lequel on tagge des couleurs (genre Stencil) ---------- +void Menu_Tag_couleurs(char * En_tete, byte * Table, byte * Mode, byte Cancel) +{ + short Bouton_clicke; + byte Backup_table[256]; + word Indice; + word Ancien_Mouse_X; + word Ancien_Mouse_Y; + byte Ancien_Mouse_K; + byte Couleur_taggee; + byte Couleur; + byte Click; + + + Ouvrir_fenetre(176,150,En_tete); + + Fenetre_Definir_bouton_palette(6,38); // 1 + Fenetre_Definir_bouton_normal( 7, 19,78,14,"Clear" ,1,1,0x002E); // 2 + Fenetre_Definir_bouton_normal(91, 19,78,14,"Invert",1,1,0x0017); // 3 + if (Cancel) + { + Fenetre_Definir_bouton_normal(91,129,78,14,"OK" ,0,1,0x001C); // 4 + Fenetre_Definir_bouton_normal( 7,129,78,14,"Cancel",0,1,0x0001); // 5 + // On enregistre la table dans un backup au cas o on ferait Cancel + memcpy(Backup_table,Table,256); + } + else + Fenetre_Definir_bouton_normal(49,129,78,14,"OK" ,0,1,0x001C); // 4 + + // On affiche l'tat actuel de la table + for (Indice=0; Indice<=255; Indice++) + Stencil_Tagger_couleur(Indice, (Table[Indice])?CM_Noir:CM_Clair); + + Afficher_curseur(); + + do + { + Ancien_Mouse_X=Mouse_X; + Ancien_Mouse_Y=Mouse_Y; + Ancien_Mouse_K=Mouse_K; + + Bouton_clicke=Fenetre_Bouton_clicke(); + + switch (Bouton_clicke) + { + case 0 : + break; + case -1 : + case 1 : // Palette + if ( (Mouse_X!=Ancien_Mouse_X) || (Mouse_Y!=Ancien_Mouse_Y) || (Mouse_K!=Ancien_Mouse_K) ) + { + Effacer_curseur(); + Couleur_taggee=Lit_pixel(Mouse_X,Mouse_Y); + Table[Couleur_taggee]=(Mouse_K==A_GAUCHE); + Stencil_Tagger_couleur(Couleur_taggee,(Mouse_K==A_GAUCHE)?CM_Noir:CM_Clair); + Afficher_curseur(); + } + break; + case 2 : // Clear + memset(Table,0,256); + Effacer_curseur(); + for (Indice=0; Indice<=255; Indice++) + Stencil_Tagger_couleur(Indice,CM_Clair); + Afficher_curseur(); + break; + case 3 : // Invert + Effacer_curseur(); + for (Indice=0; Indice<=255; Indice++) + Stencil_Tagger_couleur(Indice,(Table[Indice]^=1)?CM_Noir:CM_Clair); + Afficher_curseur(); + } + + if (!Mouse_K) + switch (Touche) + { + case 0x0029 : // Rcupration d'une couleur derrire le menu + case 0x0033 : + Recuperer_couleur_derriere_fenetre(&Couleur,&Click); + if (Click) + { + Effacer_curseur(); + Couleur_taggee=Couleur; + Table[Couleur_taggee]=(Click==A_GAUCHE); + Stencil_Tagger_couleur(Couleur_taggee,(Click==A_GAUCHE)?CM_Noir:CM_Clair); + Afficher_curseur(); + } + } + } + while (Bouton_clicke<4); + + Fermer_fenetre(); + + if (Bouton_clicke==5) // Cancel + memcpy(Table,Backup_table,256); + else // OK + *Mode=1; + + Afficher_curseur(); +} + + +//--------------------------------- Stencil ---------------------------------- +void Bouton_Stencil_Mode(void) +{ + Stencil_Mode=!Stencil_Mode; +} + + +void Stencil_Tagger_couleur(byte Couleur, byte Couleur_de_taggage) +{ + Block(Fenetre_Pos_X+(Menu_Facteur_X*(Fenetre_Liste_boutons_palette->Pos_X+4+(Couleur >> 4)*10)), + Fenetre_Pos_Y+(Menu_Facteur_Y*(Fenetre_Liste_boutons_palette->Pos_Y+3+(Couleur & 15)* 5)), + Menu_Facteur_X<<1,Menu_Facteur_Y*5,Couleur_de_taggage); +} + + +void Bouton_Menu_Stencil(void) +{ + Menu_Tag_couleurs("Stencil",Stencil,&Stencil_Mode,1); +} + + +//--------------------------------- Masque ----------------------------------- +void Bouton_Mask_Mode(void) +{ + Mask_Mode=!Mask_Mode; +} + + +void Bouton_Mask_Menu(void) +{ + Menu_Tag_couleurs("Mask",Mask,&Mask_Mode,1); +} + + +//------------------------------- Paramtres --------------------------------- + +void Settings_Afficher_config(struct S_Config * Conf) +#define YES "YES" +#define NO " NO" +{ + struct Fenetre_Bouton_scroller * Jauge=Fenetre_Liste_boutons_scroller; + char Chaine[4]; + + Effacer_curseur(); + + // Jauge = Jauge de sensibilit Y + Jauge->Position=Conf->Indice_Sensibilite_souris_Y-1; + Fenetre_Dessiner_jauge(Jauge); + + Jauge=Jauge->Next; + // Jauge = Jauge de sensibilit X + Jauge->Position=Conf->Indice_Sensibilite_souris_X-1; + Fenetre_Dessiner_jauge(Jauge); + + Print_dans_fenetre(273, 31,(Conf->Lire_les_fichiers_caches)?YES:NO,CM_Noir,CM_Clair); + Print_dans_fenetre(273, 46,(Conf->Lire_les_repertoires_caches)?YES:NO,CM_Noir,CM_Clair); + Print_dans_fenetre(273, 61,(Conf->Lire_les_repertoires_systemes)?YES:NO,CM_Noir,CM_Clair); + + Print_dans_fenetre(223, 84,(Conf->Safety_colors)?YES:NO,CM_Noir,CM_Clair); + Print_dans_fenetre(223, 99,(Conf->Adjust_brush_pick)?YES:NO,CM_Noir,CM_Clair); + Print_dans_fenetre(223,114,(Conf->Couleurs_separees)?YES:NO,CM_Noir,CM_Clair); + Print_dans_fenetre(223,129,(Conf->Auto_set_res)?YES:NO,CM_Noir,CM_Clair); + Print_dans_fenetre(183,144,(Conf->Coords_rel)?"Relative":"Absolute",CM_Noir,CM_Clair); + + Print_dans_fenetre( 91, 84,(Conf->Afficher_limites_image)?YES:NO,CM_Noir,CM_Clair); + Print_dans_fenetre( 91, 99,(Conf->Clear_palette)?YES:NO,CM_Noir,CM_Clair); + Print_dans_fenetre( 91,114,(Conf->Maximize_preview)?YES:NO,CM_Noir,CM_Clair); + Print_dans_fenetre( 91,129,(Conf->Backup)?YES:NO,CM_Noir,CM_Clair); + switch (Conf->Curseur) + { + case 0 : Print_dans_fenetre(67,144," Solid",CM_Noir,CM_Clair); break; + case 1 : Print_dans_fenetre(67,144,"Transp",CM_Noir,CM_Clair); break; + default: Print_dans_fenetre(67,144," Thin",CM_Noir,CM_Clair); + } + + if (Conf->Fonte) + { // Fun + Print_dans_fenetre( 8,31," ",CM_Noir,CM_Clair); + Print_dans_fenetre( 78,31," ",CM_Noir,CM_Clair); + Print_dans_fenetre( 82,31,"\020",CM_Noir,CM_Clair); + Print_dans_fenetre(152,31,"\021",CM_Noir,CM_Clair); + } + else + { // Classic + Print_dans_fenetre( 82,31," ",CM_Noir,CM_Clair); + Print_dans_fenetre(152,31," ",CM_Noir,CM_Clair); + Print_dans_fenetre( 8,31,"\020",CM_Noir,CM_Clair); + Print_dans_fenetre( 78,31,"\021",CM_Noir,CM_Clair); + } + + Print_dans_fenetre(155,166,(Conf->Auto_save)?YES:NO,CM_Noir,CM_Clair); + + Num2str(Conf->Nb_pages_Undo,Chaine,2); + Fenetre_Contenu_bouton_saisie(Fenetre_Liste_boutons_special,Chaine); + + Afficher_curseur(); +} + +void Settings_Sauver_config(struct S_Config * Conf) +{ + if (Sauver_CFG()) + Erreur(0); + else + if (Sauver_INI(Conf)) + Erreur(0); +} + +void Settings_Charger_config(struct S_Config * Conf) +{ + if (Charger_CFG(0)) + Erreur(0); + else + if (Charger_INI(Conf)) + Erreur(0); +} + +void Bouton_Settings(void) +{ + int Sensibilite_X; + int Sensibilite_Y; + short Bouton_clicke; + struct S_Config Config_choisie; + char Chaine[3]; + byte On_a_recharge_la_config=0; + + Config_choisie=Config; + + Ouvrir_fenetre(307,182,"Settings"); + + // On commence par dessiner tous les cdres + Fenetre_Afficher_cadre( 5, 16,157,30); + Fenetre_Afficher_cadre( 5, 47,157,17); + Fenetre_Afficher_cadre(163, 16,139,60); + Fenetre_Afficher_cadre(253, 77, 49,82); + Fenetre_Afficher_cadre( 5, 77,247,82); // |_ Misc. + Fenetre_Afficher_cadre( 5, 65,157,14); // | + // On dcoupe le cdre bizarre des "Miscellaneous" + Pixel_dans_fenetre(6,77,CM_Blanc); + Pixel_dans_fenetre(5,78,CM_Fonce); + Block(Fenetre_Pos_X+(7*Menu_Facteur_X),Fenetre_Pos_Y+(77*Menu_Facteur_Y), + Menu_Facteur_X*154,Menu_Facteur_Y<<1,CM_Clair); + Pixel_dans_fenetre(161,77,CM_Clair); + Pixel_dans_fenetre(160,77,CM_Fonce); + + // On affiche maintenant tout le blabla + Print_dans_fenetre( 69, 19,"Font" ,CM_Fonce,CM_Clair); + Print_dans_fenetre(169, 19,"Show in filelist",CM_Fonce,CM_Clair); + Print_dans_fenetre( 9, 52,"Nb of UNDO pages",CM_Fonce,CM_Clair); + Print_dans_fenetre( 32, 70,"Miscellaneous" ,CM_Fonce,CM_Clair); + Print_dans_fenetre(258, 80,"Mouse" ,CM_Fonce,CM_Clair); + Print_dans_fenetre(258, 88,"Sens." ,CM_Fonce,CM_Clair); + Print_dans_fenetre(256,123,"X" ,CM_Fonce,CM_Clair); + Print_dans_fenetre(292,123,"Y" ,CM_Fonce,CM_Clair); + + // Boutons de fontes + Fenetre_Definir_bouton_normal(17,28,59,14,"Classic",0,1,0xFFFF); // 1 + Fenetre_Definir_bouton_normal(91,28,59,14,"Fun" ,0,1,0xFFFF); // 2 + + // Bouton Show/Hide dans le fileselect + Fenetre_Definir_bouton_normal(167, 28,131,14,"Hidden files: ",0,1,0xFFFF); // 3 + Fenetre_Definir_bouton_normal(167, 43,131,14,"Hidden dir. : ",0,1,0xFFFF); // 4 + Fenetre_Definir_bouton_normal(167, 58,131,14,"System dir. : ",0,1,0xFFFF); // 5 + + // Bouton Show/Hide Picture limits + Fenetre_Definir_bouton_normal( 9, 81,107,14,"Limits : ",0,1,0xFFFF); // 6 + // Bouton Show/Hide Picture limits + Fenetre_Definir_bouton_normal( 9, 96,107,14,"Clear pal: ",0,1,0xFFFF); // 7 + // Bouton Show/Hide Picture limits + Fenetre_Definir_bouton_normal( 9,111,107,14,"Max prev.: ",0,1,0xFFFF); // 8 + // Bouton Effectuer des backups chaque sauvegarde + Fenetre_Definir_bouton_normal( 9,126,107,14,"Backup : ",0,1,0xFFFF); // 9 + // Bouton Choix du curseur + Fenetre_Definir_bouton_normal( 9,141,107,14,"Cursor: ",0,1,0xFFFF); // 10 + + // Bouton Safety colors + Fenetre_Definir_bouton_normal(117, 81,131,14,"Safe. colors: ",0,1,0xFFFF); // 11 + // Bouton Adjust Brush Pick + Fenetre_Definir_bouton_normal(117, 96,131,14,"AdjBrushPick: ",0,1,0xFFFF); // 12 + // Bouton Separate colors + Fenetre_Definir_bouton_normal(117,111,131,14,"Separate col: ",0,1,0xFFFF); // 13 + // Bouton Passer dans la rsolution approprie aprs un chargement + Fenetre_Definir_bouton_normal(117,126,131,14,"Auto-set res: ",0,1,0xFFFF); // 14 + // Bouton Adapter la palette aprs un chargement (<=> Shift+BkSpc) + Fenetre_Definir_bouton_normal(117,141,131,14,"Coords: ",0,1,0xFFFF); // 15 + + // Bouton Reload + Fenetre_Definir_bouton_normal( 6,163, 51,14,"Reload" ,0,1,0xFFFF); // 16 + // Bouton Auto-save + Fenetre_Definir_bouton_normal( 73,163,107,14,"Auto-save: ",0,1,0xFFFF); // 17 + // Bouton Save + Fenetre_Definir_bouton_normal(183,163, 51,14,"Save" ,0,1,0xFFFF); // 18 + // Bouton Close + Fenetre_Definir_bouton_normal(250,163, 51,14,"Close" ,0,1,0x0001); // 19 + + // Jauges de sensibilit de la souris (X puis Y) + Fenetre_Definir_bouton_scroller(265,99,56,255,1,0); // 20 + Fenetre_Definir_bouton_scroller(279,99,56,255,1,0); // 21 + + // Zone de saisie du nb de pages de Undo + Fenetre_Definir_bouton_saisie(140,50,2); // 22 + + Afficher_curseur(); + + Settings_Afficher_config(&Config_choisie); + + + do + { + Bouton_clicke=Fenetre_Bouton_clicke(); + + switch(Bouton_clicke) + { + case 1 : // Classic + Config_choisie.Fonte=0; + break; + case 2 : // Fun + Config_choisie.Fonte=1; + break; + case 3 : // Hidden files + Config_choisie.Lire_les_fichiers_caches=(Config_choisie.Lire_les_fichiers_caches)?0:-1; + break; + case 4 : // Hidden dir. + Config_choisie.Lire_les_repertoires_caches=(Config_choisie.Lire_les_repertoires_caches)?0:-1; + break; + case 5 : // System dir. + Config_choisie.Lire_les_repertoires_systemes=(Config_choisie.Lire_les_repertoires_systemes)?0:-1; + break; + case 6 : // Draw limits + Config_choisie.Afficher_limites_image=!Config_choisie.Afficher_limites_image; + break; + case 7 : // Clear palette + Config_choisie.Clear_palette=!Config_choisie.Clear_palette; + break; + case 8 : // Maximize preview + Config_choisie.Maximize_preview=!Config_choisie.Maximize_preview; + break; + case 9 : // Backup + Config_choisie.Backup=!Config_choisie.Backup; + break; + case 10 : // Curseur + Config_choisie.Curseur=(Config_choisie.Curseur+1)%3; + break; + case 11 : // Safety colors + Config_choisie.Safety_colors=!Config_choisie.Safety_colors; + break; + case 12 : // Adjust brush pick + Config_choisie.Adjust_brush_pick=!Config_choisie.Adjust_brush_pick; + break; + case 13 : // Separate colors + Config_choisie.Couleurs_separees=!Config_choisie.Couleurs_separees; + break; + case 14 : // Auto-set resolution + Config_choisie.Auto_set_res=!Config_choisie.Auto_set_res; + break; + case 15 : // Coordonnes + Config_choisie.Coords_rel=!Config_choisie.Coords_rel; + break; + case 16 : // Reload + Settings_Charger_config(&Config_choisie); + On_a_recharge_la_config=1; + break; + case 17 : // Auto-save + Config_choisie.Auto_save=!Config_choisie.Auto_save; + break; + case 18 : // Save + Settings_Sauver_config(&Config_choisie); + break; + case 20 : // X Sensib. + Config_choisie.Indice_Sensibilite_souris_X=Fenetre_Attribut2+1; + break; + case 21 : // Y Sensib. + Config_choisie.Indice_Sensibilite_souris_Y=Fenetre_Attribut2+1; + break; + case 22 : // Nb pages Undo + Effacer_curseur(); + Num2str(Config_choisie.Nb_pages_Undo,Chaine,2); + Readline(142,52,Chaine,2,1); + Config_choisie.Nb_pages_Undo=atoi(Chaine); + // On corrige la valeur + if (Config_choisie.Nb_pages_Undo>NB_PAGES_UNDO_MAX) + { + Config_choisie.Nb_pages_Undo=NB_PAGES_UNDO_MAX; + Num2str(Config_choisie.Nb_pages_Undo,Chaine,2); + Fenetre_Contenu_bouton_saisie(Fenetre_Liste_boutons_special,Chaine); + } + else if (!Config_choisie.Nb_pages_Undo) + { + Config_choisie.Nb_pages_Undo=1; + Num2str(Config_choisie.Nb_pages_Undo,Chaine,2); + Fenetre_Contenu_bouton_saisie(Fenetre_Liste_boutons_special,Chaine); + } + Afficher_curseur(); + } + + if ((Bouton_clicke>=3) && (Bouton_clicke<=5)) + { + Principal_File_list_Position=0; + Principal_File_list_Decalage=0; + Brouillon_File_list_Position=0; + Brouillon_File_list_Decalage=0; + } + + if ((Bouton_clicke>=1) && (Bouton_clicke<=17)) + Settings_Afficher_config(&Config_choisie); + } + while ( (Bouton_clicke!=19) && (Touche!=0x001C) ); + + Config=Config_choisie; + + // Prise en compte de la nouvelle config + // Gestion de la sensibilit + Sensibilite_X=(Config.Indice_Sensibilite_souris_X/Menu_Facteur_X); + Sensibilite_Y=(Config.Indice_Sensibilite_souris_Y/Menu_Facteur_Y); + Sensibilite_X>>=Mouse_Facteur_de_correction_X; + Sensibilite_Y>>=Mouse_Facteur_de_correction_Y; + + Sensibilite_souris(Sensibilite_X?Sensibilite_X:1, + Sensibilite_Y?Sensibilite_Y:1); + // Gestion des fontes + if (Config.Fonte) + Fonte=Fonte_fun; + else + Fonte=Fonte_systeme; + + if (On_a_recharge_la_config) + Calculer_couleurs_menu_optimales(Principal_Palette); + + Fermer_fenetre(); + Desenclencher_bouton(BOUTON_PARAMETRES); + // Raffichage du menu pour que les inscriptions qui y figurent soient retraces avec la nouvelle fonte + Afficher_menu(); + Afficher_curseur(); + + // On vrifie qu'on peut bien allouer le nombre de pages Undo. + Nouveau_nombre_de_backups(Config.Nb_pages_Undo); +} + + +//---------------------------- Changement de page ---------------------------- +void Bouton_Page(void) +{ + byte Octet_temporaire; + word Mot_temporaire; + short Short_temporaire; + float Float_temporaire; + char Zone_temporaire[256]; + + Effacer_curseur(); + + // On dgrossit le travail avec les infos des listes de pages + Interchanger_image_principale_et_brouillon(); + + // On fait le reste du travail " la main": + Short_temporaire=Brouillon_Decalage_X; + Brouillon_Decalage_X=Principal_Decalage_X; + Principal_Decalage_X=Short_temporaire; + + Short_temporaire=Brouillon_Decalage_Y; + Brouillon_Decalage_Y=Principal_Decalage_Y; + Principal_Decalage_Y=Short_temporaire; + + Short_temporaire=Ancien_Brouillon_Decalage_X; + Ancien_Brouillon_Decalage_X=Ancien_Principal_Decalage_X; + Ancien_Principal_Decalage_X=Short_temporaire; + + Short_temporaire=Ancien_Brouillon_Decalage_Y; + Ancien_Brouillon_Decalage_Y=Ancien_Principal_Decalage_Y; + Ancien_Principal_Decalage_Y=Short_temporaire; + + Short_temporaire=Brouillon_Split; + Brouillon_Split=Principal_Split; + Principal_Split=Short_temporaire; + + Short_temporaire=Brouillon_X_Zoom; + Brouillon_X_Zoom=Principal_X_Zoom; + Principal_X_Zoom=Short_temporaire; + + Float_temporaire=Brouillon_Proportion_split; + Brouillon_Proportion_split=Principal_Proportion_split; + Principal_Proportion_split=Float_temporaire; + + Octet_temporaire=Brouillon_Loupe_Mode; + Brouillon_Loupe_Mode=Loupe_Mode; + Loupe_Mode=Octet_temporaire; + + Pixel_Preview=(Loupe_Mode)?Pixel_Preview_Loupe:Pixel_Preview_Normal; + + Mot_temporaire=Brouillon_Loupe_Facteur; + Brouillon_Loupe_Facteur=Loupe_Facteur; + Loupe_Facteur=Mot_temporaire; + + Mot_temporaire=Brouillon_Loupe_Hauteur; + Brouillon_Loupe_Hauteur=Loupe_Hauteur; + Loupe_Hauteur=Mot_temporaire; + + Mot_temporaire=Brouillon_Loupe_Largeur; + Brouillon_Loupe_Largeur=Loupe_Largeur; + Loupe_Largeur=Mot_temporaire; + + Short_temporaire=Brouillon_Loupe_Decalage_X; + Brouillon_Loupe_Decalage_X=Loupe_Decalage_X; + Loupe_Decalage_X=Short_temporaire; + + Short_temporaire=Brouillon_Loupe_Decalage_Y; + Brouillon_Loupe_Decalage_Y=Loupe_Decalage_Y; + Loupe_Decalage_Y=Short_temporaire; + + // Swap du boolen "Image modifie" + Octet_temporaire =Brouillon_Image_modifiee; + Brouillon_Image_modifiee=Principal_Image_modifiee; + Principal_Image_modifiee=Octet_temporaire; + + // Swap des infos sur les fileselects + strcpy(Zone_temporaire ,Brouillon_Repertoire_courant); + strcpy(Brouillon_Repertoire_courant,Principal_Repertoire_courant); + strcpy(Principal_Repertoire_courant,Zone_temporaire ); + + Octet_temporaire=Brouillon_Format; + Brouillon_Format=Principal_Format; + Principal_Format=Octet_temporaire; + + Mot_temporaire =Brouillon_File_list_Position; + Brouillon_File_list_Position=Principal_File_list_Position; + Principal_File_list_Position=Mot_temporaire; + + Mot_temporaire =Brouillon_File_list_Decalage; + Brouillon_File_list_Decalage=Principal_File_list_Decalage; + Principal_File_list_Decalage=Mot_temporaire; + + // A la fin, on affiche l'cran + for (Octet_temporaire=0; FACTEUR_ZOOM[Octet_temporaire]!=Loupe_Facteur; Octet_temporaire++); + Changer_facteur_loupe(Octet_temporaire); + + Set_palette(Principal_Palette); + Calculer_couleurs_menu_optimales(Principal_Palette); + Afficher_ecran(); + Desenclencher_bouton(BOUTON_PAGE); + Tracer_cadre_de_bouton_du_menu(BOUTON_LOUPE,Loupe_Mode); + Afficher_menu(); + + Afficher_curseur(); +} + + +// -- Copie de page --------------------------------------------------------- + +void Copier_image_seule(void) +{ + if (Backuper_et_redimensionner_brouillon(Principal_Largeur_image,Principal_Hauteur_image)) + { + // copie de l'image + memcpy(Brouillon_Ecran,Principal_Ecran,Principal_Largeur_image*Principal_Hauteur_image); + + // Copie des dimensions de l'image + /* + C'est inutile, le "Backuper et redimensionner brouillon" a dj modifi + ces valeurs pour qu'elles soient correctes. + */ + Brouillon_Largeur_image=Principal_Largeur_image; + Brouillon_Hauteur_image=Principal_Hauteur_image; + + // Copie des dcalages de la fentre principale (non zoome) de l'image + Brouillon_Decalage_X=Principal_Decalage_X; + Brouillon_Decalage_Y=Principal_Decalage_Y; + + // Copie du boolen "Mode loupe" de l'image + Brouillon_Loupe_Mode=Loupe_Mode; + + // Copie du facteur de zoom du brouillon + Brouillon_Loupe_Facteur=Loupe_Facteur; + + // Copie des dimensions de la fentre de zoom + Brouillon_Loupe_Largeur=Loupe_Largeur; + Brouillon_Loupe_Hauteur=Loupe_Hauteur; + + // Copie des dcalages de la fentre de zoom + Brouillon_Loupe_Decalage_X=Loupe_Decalage_X; + Brouillon_Loupe_Decalage_Y=Loupe_Decalage_Y; + + // Copie des donnes du split du zoom + Brouillon_Split=Principal_Split; + Brouillon_X_Zoom=Principal_X_Zoom; + Brouillon_Proportion_split=Principal_Proportion_split; + } + else + Message_Memoire_insuffisante(); +} + + +void Copier_certaines_couleurs(void) +{ + short Indice; + + Menu_Tag_couleurs("Tag colors to copy",Masque_copie_couleurs,NULL,0); + + if ( (!Brouillon_Image_modifiee) + || (Demande_de_confirmation("Spare page was modified. Proceed?")) ) + for (Indice=0; Indice<256; Indice++) + { + if (Masque_copie_couleurs[Indice]) + memcpy(Brouillon_Palette+Indice,Principal_Palette+Indice, + sizeof(struct Composantes)); + } +} + + +void Bouton_Copy_page(void) +{ + short Bouton_clicke; + + + Ouvrir_fenetre(168,137,"Copy to spare page"); + + Fenetre_Definir_bouton_normal(10, 20,148,14,"Pixels + palette" , 0,1,0x001C); // 1 + Fenetre_Definir_bouton_normal(10, 37,148,14,"Pixels only" , 3,1,0x002D); // 2 + Fenetre_Definir_bouton_normal(10, 54,148,14,"Palette only" , 1,1,0x0019); // 3 + Fenetre_Definir_bouton_normal(10, 71,148,14,"Some colors only" , 6,1,0x002E); // 4 + Fenetre_Definir_bouton_normal(10, 88,148,14,"Palette and remap",13,1,0x0013); // 5 + Fenetre_Definir_bouton_normal(44,114, 80,14,"Cancel" , 0,1,0x0001); // 6 + + Afficher_curseur(); + + do + { + Bouton_clicke=Fenetre_Bouton_clicke(); + } + while (Bouton_clicke<=0); + + Fermer_fenetre(); + Afficher_curseur(); + + if (Bouton_clicke!=6) + { + if (Bouton_clicke==4) + Copier_certaines_couleurs(); + else + { + if ( (!Brouillon_Image_modifiee) + || (Demande_de_confirmation("Spare page was modified. Proceed?")) ) + { + if (Bouton_clicke<=2) + Copier_image_seule(); + + if (Bouton_clicke==5) + Remap_picture(); + + if (Bouton_clicke!=2) // copie de la palette + memcpy(Brouillon_Palette,Principal_Palette,sizeof(T_Palette)); + + Brouillon_Image_modifiee=1; + } + } + } + + Effacer_curseur(); + Desenclencher_bouton(BOUTON_PAGE); + Afficher_curseur(); +} + + +// -- Suppression d'une page ------------------------------------------------- +void Bouton_Kill(void) +{ + if ( (Principal_Backups->Nb_pages_allouees==1) + || (!Demande_de_confirmation("Delete the current page?")) ) + { + if (Principal_Backups->Nb_pages_allouees==1) + Warning_message("You can't delete the last page."); + Effacer_curseur(); + Desenclencher_bouton(BOUTON_KILL); + Afficher_curseur(); + } + else + { + Effacer_curseur(); + Detruire_la_page_courante(); + + Set_palette(Principal_Palette); + Calculer_couleurs_menu_optimales(Principal_Palette); + + Afficher_ecran(); + Desenclencher_bouton(BOUTON_KILL); + Tracer_cadre_de_bouton_du_menu(BOUTON_LOUPE,Loupe_Mode); + Afficher_menu(); + Afficher_curseur(); + } +} + + +//------------------------- Dimensions Image/Ecran --------------------------- + +void Cocher_bouton_mode(short Pos_X, short Pos_Y, byte Etat) +{ + byte Couleur; + + if (Etat>=128) + Etat-=128; + switch (Etat) + { + case 0 : Couleur=CM_Blanc; break; + case 1 : Couleur=CM_Clair; break; + case 2 : Couleur=CM_Fonce; break; + default: Couleur=CM_Noir; + } + Block(Fenetre_Pos_X+Menu_Facteur_X*Pos_X,Fenetre_Pos_Y+Menu_Facteur_Y*Pos_Y, + Menu_Facteur_X*9,Menu_Facteur_Y*3,Couleur); +} + + +void Afficher_liste_modes(short Debut_liste, short Position_curseur) +{ + short Indice,Mode_courant; + short Pos_Y; + byte Couleur_texte,Couleur_fond; + char Chaine[29]; + + for (Mode_courant=Debut_liste,Indice=0; Indice<12; Indice++,Mode_courant++) + { + Pos_Y=70+(Indice<<3); + Cocher_bouton_mode(19,Pos_Y+2,Mode_video[Mode_courant].Etat); + + if (Position_curseur!=Indice) + { + Couleur_fond =CM_Noir; + if (Mode_video[Mode_courant].Etat<128) + Couleur_texte=CM_Clair; + else + Couleur_texte=CM_Fonce; + } + else + { + Couleur_fond =CM_Fonce; + if (Mode_video[Mode_courant].Etat<128) + Couleur_texte=CM_Blanc; + else + Couleur_texte=CM_Clair; + } + Num2str(Mode_video[Mode_courant].Largeur,Chaine,4); + Num2str(Mode_video[Mode_courant].Hauteur,Chaine+4,4); + switch (Mode_video[Mode_courant].Mode) + { + case MODE_SDL : + memcpy(Chaine+8," SDL ",10); + break; + + } + if (Mode_video[Mode_courant].Refresh>0) + { + Num2str(Mode_video[Mode_courant].Refresh,Chaine+18,2); + Chaine[20]=' '; + } + else + { + if (Mode_video[Mode_courant].Refresh==-1) + memcpy(Chaine+18," ",3); + else + { + Num2str(-Mode_video[Mode_courant].Refresh,Chaine+18,2); + Chaine[20]='i'; + } + } + memcpy(Chaine+21," ",2); + memcpy(Chaine+23,Mode_video[Mode_courant].Ratio,4); + Chaine[27]=' '; + Chaine[28]=0; + + Print_dans_fenetre(39,Pos_Y,Chaine,Couleur_texte,Couleur_fond); + } +} + + +void Scroller_la_liste_des_modes(short Debut_liste, short Position_curseur, int * Mode_choisi) +{ + Effacer_curseur(); + *Mode_choisi=Debut_liste+Position_curseur; + if (Fenetre_Liste_boutons_scroller->Position!=Debut_liste) + { + Fenetre_Liste_boutons_scroller->Position=Debut_liste; + Fenetre_Dessiner_jauge(Fenetre_Liste_boutons_scroller); + } + Afficher_liste_modes(Debut_liste,Position_curseur); + Afficher_curseur(); +} + + +void Bouton_Resol(void) +{ + short Bouton_clicke; + int Mode_choisi; + word Largeur_choisie; + word Hauteur_choisie; + short Debut_liste; + short Position_curseur; + short Temp; + byte Temp2; + char Chaine[5]; + struct Fenetre_Bouton_special * Bouton_saisie_Width, * Bouton_saisie_Height; + + Ouvrir_fenetre(299,190,"Picture & screen sizes"); + + Fenetre_Afficher_cadre ( 8,17,195, 33); + Fenetre_Afficher_cadre ( 8,56,283,126); + Fenetre_Afficher_cadre_creux(37,68,228,100); + Block(Fenetre_Pos_X+Menu_Facteur_X*38,Fenetre_Pos_Y+Menu_Facteur_Y*69, + Menu_Facteur_X*226,Menu_Facteur_Y*98,CM_Noir); + + Print_dans_fenetre( 12, 21,"Picture size:" ,CM_Fonce,CM_Clair); + Print_dans_fenetre( 12, 37,"Width:" ,CM_Fonce,CM_Clair); + Print_dans_fenetre(108, 37,"Height:" ,CM_Fonce,CM_Clair); + Print_dans_fenetre( 16, 60,"OK" ,CM_Fonce,CM_Clair); + Print_dans_fenetre( 55, 60,"X Y" ,CM_Fonce,CM_Clair); + Print_dans_fenetre(131, 60,"Mode" ,CM_Fonce,CM_Clair); + Print_dans_fenetre(183, 60,"Hz" ,CM_Fonce,CM_Clair); + Print_dans_fenetre(219, 60,"Ratio" ,CM_Fonce,CM_Clair); + Print_dans_fenetre( 30,170,"\03" ,CM_Fonce,CM_Clair); + Print_dans_fenetre( 62,170,"OK" ,CM_Fonce,CM_Clair); + Print_dans_fenetre(102,170,"Imperfect" ,CM_Fonce,CM_Clair); + Print_dans_fenetre(196,170,"Unsupported" ,CM_Fonce,CM_Clair); + + Fenetre_Definir_bouton_normal(223, 18,67,14,"OK" ,0,1,0x001C); // 1 + Fenetre_Definir_bouton_normal(223, 35,67,14,"Cancel" ,0,1,0x0001); // 2 + + Fenetre_Definir_bouton_saisie( 60, 35,4); // 3 + Bouton_saisie_Width=Fenetre_Liste_boutons_special; + Fenetre_Definir_bouton_saisie(164, 35,4); // 4 + Bouton_saisie_Height=Fenetre_Liste_boutons_special; + + Fenetre_Definir_bouton_special(38,70,225,96); // 5 + + Mode_choisi=Resolution_actuelle; + + if (Mode_choisi>=6) + { + if (Mode_choisi>3; + if ((Mouse_K==2) || (Temp!=Position_curseur)) + { + Effacer_curseur(); + if (Temp!=Position_curseur) + { + Position_curseur=Temp; + Afficher_liste_modes(Debut_liste,Position_curseur); + } + Mode_choisi=Debut_liste+Position_curseur; + // Si l'utilisateur s'est servi du bouton droit de la souris: + if (Mouse_K==2) + { + // On affecte galement les dimensions de l'image: + Largeur_choisie=Mode_video[Mode_choisi].Largeur; + Num2str(Largeur_choisie,Chaine,4); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_Width,Chaine); + + Hauteur_choisie=Mode_video[Mode_choisi].Hauteur; + Num2str(Hauteur_choisie,Chaine,4); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_Height,Chaine); + } + Afficher_curseur(); + } + Attendre_fin_de_click(); + break; + + case 6: // Scroller + Debut_liste=Fenetre_Attribut2; + Mode_choisi=Debut_liste+Position_curseur; + Afficher_liste_modes(Debut_liste,Position_curseur); + break; + + default: // Boutons de tag des tats des modes + Temp=Debut_liste+Bouton_clicke-7; + if (Temp) // On n'a pas le droit de cocher le mode 0 (320x200) + { + Temp2=(Mode_video[Temp].Etat & 0x80)?128:0; + + if (Fenetre_Attribut1==A_GAUCHE) + Mode_video[Temp].Etat=Temp2+(((Mode_video[Temp].Etat&0x7F)+1)&3); + else + Mode_video[Temp].Etat=Temp2+(((Mode_video[Temp].Etat&0x7F)+3)&3); + + Effacer_curseur(); + Cocher_bouton_mode(19,16+(Bouton_clicke<<3),Mode_video[Temp].Etat); + Afficher_curseur(); + } + } + + // Gestion des touches de dplacement dans la liste + switch (Touche) + { + case 0x0048 : // Haut + if (Position_curseur>0) + Position_curseur--; + else + if (Debut_liste>0) + Debut_liste--; + Scroller_la_liste_des_modes(Debut_liste,Position_curseur,&Mode_choisi); + break; + case 0x0050 : // Bas + if (Position_curseur<11) + Position_curseur++; + else + if (Debut_liste0) + Position_curseur=0; + else + { + if (Debut_liste>11) + Debut_liste-=11; + else + Debut_liste=0; + } + Scroller_la_liste_des_modes(Debut_liste,Position_curseur,&Mode_choisi); + break; + case 0x0051 : // PageDown + if (Position_curseur<11) + Position_curseur=11; + else + { + if (Debut_listeOPERATION_DESSIN_POINT) + Mode_de_dessin_en_cours=OPERATION_DESSIN_CONTINU; + + Effacer_curseur(); + Afficher_sprite_dans_menu(BOUTON_DESSIN,Mode_de_dessin_en_cours); + Demarrer_pile_operation(Mode_de_dessin_en_cours); + Afficher_curseur(); +} + + +// -- Gestion des boutons de rectangle vide et plein ------------------------ + +void Bouton_Rectangle_vide(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(OPERATION_RECTANGLE_VIDE); + Afficher_curseur(); +} + + +void Bouton_Rectangle_plein(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(OPERATION_RECTANGLE_PLEIN); + Afficher_curseur(); +} + + +// -- Gestion des boutons de cercle (ellipse) vide et plein(e) -------------- + +void Bouton_Cercle_vide(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(OPERATION_CERCLE_VIDE); + Afficher_curseur(); +} + + +void Bouton_Ellipse_vide(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(OPERATION_ELLIPSE_VIDE); + Afficher_curseur(); +} + + +void Bouton_Cercle_plein(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(OPERATION_CERCLE_PLEIN); + Afficher_curseur(); +} + + +void Bouton_Ellipse_pleine(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(OPERATION_ELLIPSE_PLEINE); + Afficher_curseur(); +} + + +// -- Gestion du menu des dgrads ------------------------------------------ +void Degrade_Dessiner_bouton_de_technique(short Pos_X,short Pos_Y,int Technique) +{ + short Ligne; + + // On commence par afficher les 2 cts qui constituent le dgrad de base: + // Ct gauche (noir) + Block(Fenetre_Pos_X+((Pos_X+2)*Menu_Facteur_X), + Fenetre_Pos_Y+((Pos_Y+2)*Menu_Facteur_Y), + Menu_Facteur_X*6, + Menu_Facteur_Y*10,CM_Noir); + // Ct droit (blanc) + Block(Fenetre_Pos_X+((Pos_X+8)*Menu_Facteur_X), + Fenetre_Pos_Y+((Pos_Y+2)*Menu_Facteur_Y), + Menu_Facteur_X*5, + Menu_Facteur_Y*10,CM_Blanc); + + switch(Technique) + { + case 1 : // Dgrad de trames simples + // Au centre, on place 10 lignes trames simplement + for (Ligne=2;Ligne<2+10;Ligne++) + if (Ligne&1) + { + // Lignes impaires + Pixel_dans_fenetre(Pos_X+ 5,Pos_Y+Ligne,CM_Blanc); + Pixel_dans_fenetre(Pos_X+ 7,Pos_Y+Ligne,CM_Blanc); + Pixel_dans_fenetre(Pos_X+ 8,Pos_Y+Ligne,CM_Noir); + } + else + { + // Lignes paires + Pixel_dans_fenetre(Pos_X+ 6,Pos_Y+Ligne,CM_Blanc); + Pixel_dans_fenetre(Pos_X+ 9,Pos_Y+Ligne,CM_Noir); + } + break; + case 2 : // Dgrad de trames tendues + // Au centre, on place 10 lignes trames de faon complique + for (Ligne=2;Ligne<2+10;Ligne++) + if (Ligne&1) + { + // Lignes impaires + Pixel_dans_fenetre(Pos_X+ 7,Pos_Y+Ligne,CM_Blanc); + Pixel_dans_fenetre(Pos_X+ 8,Pos_Y+Ligne,CM_Noir); + Pixel_dans_fenetre(Pos_X+10,Pos_Y+Ligne,CM_Noir); + } + else + { + // Lignes paires + Pixel_dans_fenetre(Pos_X+ 4,Pos_Y+Ligne,CM_Blanc); + Pixel_dans_fenetre(Pos_X+ 6,Pos_Y+Ligne,CM_Blanc); + } + } +} + +void Degrade_Charger_infos_du_tableau(int Indice) +{ + Degrade_Borne_Inferieure =Degrade_Tableau[Indice].Debut; + Degrade_Borne_Superieure =Degrade_Tableau[Indice].Fin; + Degrade_Inverse =Degrade_Tableau[Indice].Inverse; + Degrade_Melange_aleatoire=Degrade_Tableau[Indice].Melange+1; + + Degrade_Intervalle_bornes=(Degrade_Borne_Inferieure indice du dgrad dans le tableau + Fenetre_Definir_bouton_scroller(218,22,75,16,1,Degrade_Courant); // 2 + // Dfinition du scrolleur de mlange du dgrad + Fenetre_Definir_bouton_scroller(31,22,84,256,1,Degrade_Tableau[Degrade_Courant].Melange); // 3 + Scroller_de_melange=Fenetre_Liste_boutons_scroller; + // Dfinition du bouton de sens + Fenetre_Definir_bouton_normal(8,22,15,14, + (Degrade_Tableau[Degrade_Courant].Inverse)?"\033":"\032",0,1,0x000F); // 4 + // Dfinition du bouton de technique + Fenetre_Definir_bouton_normal(8,92,15,14,"",0,1,0x010F); // 5 + Degrade_Dessiner_bouton_de_technique(8,92,Degrade_Tableau[Degrade_Courant].Technique); + + Fenetre_Definir_bouton_normal(178,112,51,14,"OK",0,1,0x001C); // 6 + Fenetre_Definir_bouton_normal(123,112,51,14,"Cancel",0,1,0x0001); // 7 + + Print_dans_fenetre(5,60,"MIX",CM_Fonce,CM_Clair); + + // On tagge les couleurs qui vont avec + Tagger_intervalle_palette(Degrade_Tableau[Degrade_Courant].Debut,Degrade_Tableau[Degrade_Courant].Fin); + + Num2str(Degrade_Courant+1,Chaine,2); + Print_dans_fenetre(215,100,Chaine,CM_Noir,CM_Clair); + + // On affiche le cadre autour de la prview + Fenetre_Afficher_cadre_creux(7,111,110,16); + // On affiche la preview + Degrade_Dessiner_preview(8,112,108,14,Degrade_Courant); + + Premiere_couleur=Derniere_couleur=(Degrade_Tableau[Degrade_Courant].Inverse)?Degrade_Tableau[Degrade_Courant].Fin:Degrade_Tableau[Degrade_Courant].Debut; + + Afficher_curseur(); + + do + { + Ancien_Mouse_X=Mouse_X; + Ancien_Mouse_Y=Mouse_Y; + Ancien_Mouse_K=Mouse_K; + + Bouton_clicke=Fenetre_Bouton_clicke(); + + switch(Bouton_clicke) + { + case -1 : + case 1 : // Palette + if ( (Mouse_X!=Ancien_Mouse_X) || (Mouse_Y!=Ancien_Mouse_Y) || (Mouse_K!=Ancien_Mouse_K) ) + { + Effacer_curseur(); + Couleur_temporaire=Lit_pixel(Mouse_X,Mouse_Y); + + if (!Ancien_Mouse_K) + { + // On vient de clicker + + // On met jour l'intervalle du dgrad + Premiere_couleur=Derniere_couleur=Degrade_Tableau[Degrade_Courant].Debut=Degrade_Tableau[Degrade_Courant].Fin=Couleur_temporaire; + // On tagge le bloc + Tagger_intervalle_palette(Degrade_Tableau[Degrade_Courant].Debut,Degrade_Tableau[Degrade_Courant].Fin); + // Trac de la preview: + Degrade_Dessiner_preview(8,112,108,14,Degrade_Courant); + } + else + { + // On maintient le click, on va donc tester si le curseur bouge + if (Couleur_temporaire!=Derniere_couleur) + { + // On commence par ordonner la 1re et dernire couleur du bloc + if (Premiere_couleurCouleur_temporaire) + { + Degrade_Tableau[Degrade_Courant].Debut=Couleur_temporaire; + Degrade_Tableau[Degrade_Courant].Fin =Premiere_couleur; + } + else + Degrade_Tableau[Degrade_Courant].Debut=Degrade_Tableau[Degrade_Courant].Fin=Premiere_couleur; + // On tagge le bloc + Tagger_intervalle_palette(Degrade_Tableau[Degrade_Courant].Debut,Degrade_Tableau[Degrade_Courant].Fin); + // Trac de la preview: + Degrade_Dessiner_preview(8,112,108,14,Degrade_Courant); + Derniere_couleur=Couleur_temporaire; + } + } + Afficher_curseur(); + } + break; + case 2 : // Nouvel indice de dgrad + Effacer_curseur(); + // Nouvel indice dans Fenetre_Attribut2 + Degrade_Courant=Fenetre_Attribut2; + + // On affiche la valeur sous la jauge + Num2str(Degrade_Courant+1,Chaine,2); + Print_dans_fenetre(215,100,Chaine,CM_Noir,CM_Clair); + + // On tagge les couleurs qui vont avec + Tagger_intervalle_palette(Degrade_Tableau[Degrade_Courant].Debut,Degrade_Tableau[Degrade_Courant].Fin); + + // On affiche le sens qui va avec + Print_dans_fenetre(12,25,(Degrade_Tableau[Degrade_Courant].Inverse)?"\033":"\032",CM_Noir,CM_Clair); + + // On raffiche le mlange (jauge) qui va avec + Scroller_de_melange->Position=Degrade_Tableau[Degrade_Courant].Melange; + Fenetre_Dessiner_jauge(Scroller_de_melange); + + // On raffiche la technique qui va avec + Degrade_Dessiner_bouton_de_technique(8,92,Degrade_Tableau[Degrade_Courant].Technique); + + // On affiche la nouvelle preview + Degrade_Dessiner_preview(8,112,108,14,Degrade_Courant); + + Afficher_curseur(); + break; + case 3 : // Nouveau mlange de dgrad + Effacer_curseur(); + // Nouvel mlange dans Fenetre_Attribut2 + Degrade_Tableau[Degrade_Courant].Melange=Fenetre_Attribut2; + // On affiche la nouvelle preview + Degrade_Dessiner_preview(8,112,108,14,Degrade_Courant); + Afficher_curseur(); + break; + case 4 : // Changement de sens + Effacer_curseur(); + // On inverse le sens (par un XOR de 1) + Degrade_Tableau[Degrade_Courant].Inverse^=1; + Print_dans_fenetre(12,25,(Degrade_Tableau[Degrade_Courant].Inverse)?"\033":"\032",CM_Noir,CM_Clair); + // On affiche la nouvelle preview + Degrade_Dessiner_preview(8,112,108,14,Degrade_Courant); + Afficher_curseur(); + break; + case 5 : // Changement de technique + Effacer_curseur(); + // On change la technique par (+1)%3 + Degrade_Tableau[Degrade_Courant].Technique=(Degrade_Tableau[Degrade_Courant].Technique+1)%3; + Degrade_Dessiner_bouton_de_technique(8,92,Degrade_Tableau[Degrade_Courant].Technique); + // On affiche la nouvelle preview + Degrade_Dessiner_preview(8,112,108,14,Degrade_Courant); + Afficher_curseur(); + } + + if (!Mouse_K) + switch (Touche) + { + case 0x0029 : // Rcupration d'une couleur derrire le menu + case 0x0033 : + Recuperer_couleur_derriere_fenetre(&Couleur,&Click); + if (Click) + { + Effacer_curseur(); + Couleur_temporaire=Couleur; + + // On met jour l'intervalle du dgrad + Premiere_couleur=Derniere_couleur=Degrade_Tableau[Degrade_Courant].Debut=Degrade_Tableau[Degrade_Courant].Fin=Couleur_temporaire; + // On tagge le bloc + Tagger_intervalle_palette(Degrade_Tableau[Degrade_Courant].Debut,Degrade_Tableau[Degrade_Courant].Fin); + // Trac de la preview: + Degrade_Dessiner_preview(8,112,108,14,Degrade_Courant); + + Afficher_curseur(); + } + } + } + while (Bouton_clicke<6); + + Fermer_fenetre(); + Desenclencher_bouton(BOUTON_GRADMENU); + Afficher_curseur(); + + Traiter_pixel_de_degrade=Afficher_pixel; + if (Bouton_clicke==7) // Cancel + { + Degrade_Courant=Ancien_Degrade_Courant; + memcpy(Degrade_Tableau,Backup_Degrade_Tableau,sizeof(struct T_Degrade_Tableau)*16); + Degrade_Charger_infos_du_tableau(Degrade_Courant); + } +} + + +// -- Gestion des boutons de cercle (ellipse) dgrad(e) -------------------- + +void Bouton_Cercle_degrade(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(OPERATION_CERCLE_DEGRADE); + Afficher_curseur(); +} + + +void Bouton_Ellipse_degrade(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(OPERATION_ELLIPSE_DEGRADEE); + Afficher_curseur(); +} + + +// -- Gestion du bouton de remplissage --------------------------------------- + +void Bouton_Fill(void) +{ + if (Operation_en_cours!=OPERATION_FILL) + { + Effacer_curseur(); + if (Operation_en_cours!=OPERATION_REMPLACER) + { + Pinceau_Forme_avant_fill=Pinceau_Forme; + Pinceau_Forme=FORME_PINCEAU_POINT; + } + else + if ( (Mouse_Y=Principal_X_Zoom) ) ) + Print_dans_menu("X: Y: ",0); + Demarrer_pile_operation(OPERATION_FILL); + Afficher_curseur(); + } +} + + +void Bouton_Remplacer(void) +{ + if (Operation_en_cours!=OPERATION_REMPLACER) + { + Effacer_curseur(); + if (Operation_en_cours!=OPERATION_FILL) + { + Pinceau_Forme_avant_fill=Pinceau_Forme; + Pinceau_Forme=FORME_PINCEAU_POINT; + } + if ( (Mouse_Y=Principal_X_Zoom) ) ) + Print_dans_menu("X: Y: ( )",0); + Demarrer_pile_operation(OPERATION_REMPLACER); + Afficher_curseur(); + } +} + + +void Bouton_desenclencher_Fill(void) +{ + Pinceau_Forme=Pinceau_Forme_avant_fill; + + if (Operation_en_cours==OPERATION_REMPLACER) + if ( (Mouse_Y=Principal_X_Zoom) ) ) + Print_dans_menu("X: Y: ",0); +} + + +//---------------------------- Menu des pinceaux ----------------------------- + +void Bouton_Menu_pinceaux(void) +{ + short Bouton_clicke; + short Pos_X,Pos_Y; + byte Indice; + + Ouvrir_fenetre(310,155,"Paintbrush menu"); + + Fenetre_Afficher_cadre(8,21,294,107); + + Fenetre_Definir_bouton_normal(122,133,67,14,"Cancel",0,1,0x0001); // 1 + + for (Indice=0; IndiceTAILLE_MAXI_PATH) + { // Doh! il va falloir tronquer le rpertoire (bouh !) + + // On commence par copier btement les 3 premiers caractres (e.g. "C:\") + for (Indice=0;Indice<3;Indice++) + Nom_temporaire[Indice]=Principal_Repertoire_courant[Indice]; + + // On y rajoute 3 petits points: + strcpy(Nom_temporaire+3,"..."); + + // Ensuite, on cherche un endroit partir duquel on pourrait loger tout + // le reste de la chaine (Ouaaaaaah!!! Vachement fort le mec!!) + for (Indice++;IndiceNb_elements=Liste_Nb_elements; + Enreg->Position=Position; + Calculer_hauteur_curseur_jauge(Enreg); + Fenetre_Dessiner_jauge(Enreg); + // On efface les anciens noms de fichier: + Block(Fenetre_Pos_X+(Menu_Facteur_X<<3),Fenetre_Pos_Y+(Menu_Facteur_Y*89),Menu_Facteur_X*98,Menu_Facteur_Y*82,CM_Noir); + // On affiche les nouveaux: + Afficher_la_liste_des_fichiers(Position,Decalage); + + // On rcupre le nom du schmilblick "accder" + Determiner_element_de_la_liste(Position,Decalage,Principal_Nom_fichier); + // On affiche le nouveau nom de fichier + Print_Nom_fichier_dans_selecteur(); + // On affiche le nom du rpertoire courant + Print_repertoire_courant(); +} + + +void Relire_liste_fichiers(byte Filtre, short Position, short Decalage, + struct Fenetre_Bouton_scroller * Enreg) +{ + Lire_liste_des_fichiers(Filtre); + Trier_la_liste_des_fichiers(); + Preparer_et_afficher_liste_fichiers(Position,Decalage,Enreg); +} + + // -- Gestion du chrono -- + byte Etat_chrono; // Etat du chrono: 0=Attente d'un Xme de seconde + // 1=Il faut afficher la preview + // 2=Plus de chrono gerer pour l'instant + long Chrono_delay; // Nombre de 18.2me de secondes demands + long Chrono_cmp; // Heure de dpart du chrono + byte Nouvelle_preview; // Boolen "Il faut relancer le chrono de preview" + // Les fonctions de manipulation du chrono se trouvent dans DIVERS.ASM + + +void On_vient_de_scroller_dans_le_fileselect(struct Fenetre_Bouton_scroller * Scroller_de_fichiers) +{ + char Ancien_nom_de_fichier[13]; + + strcpy(Ancien_nom_de_fichier,Principal_Nom_fichier); + + // On regarde si la liste a boug + if (Scroller_de_fichiers->Position!=Principal_File_list_Position) + { + // Si c'est le cas, il faut mettre jour la jauge + Scroller_de_fichiers->Position=Principal_File_list_Position; + Fenetre_Dessiner_jauge(Scroller_de_fichiers); + } + // On rcupre le nom du schmilblick "accder" + Determiner_element_de_la_liste(Principal_File_list_Position,Principal_File_list_Decalage,Principal_Nom_fichier); + if (strcmp(Ancien_nom_de_fichier,Principal_Nom_fichier)) + Nouvelle_preview=1; + + // On affiche le nouveau nom de fichier + Print_Nom_fichier_dans_selecteur(); + Afficher_curseur(); +} + + +short Position_fichier_dans_liste(char * Nom) +{ + struct Element_de_liste_de_fileselect * Element_courant; + short Indice; + + for (Indice=0, Element_courant=Liste_du_fileselect; + ((Element_courant!=NULL) && (strcmp(Element_courant->Nom,Nom))); + Indice++,Element_courant=Element_courant->Suivant); + + return (Element_courant!=NULL)?Indice:0; +} + + +void Placer_barre_de_selection_sur(char * Nom) +{ + short Indice; + + Indice=Position_fichier_dans_liste(Nom); + + if ((Liste_Nb_elements<=10) || (Indice<5)) + { + Principal_File_list_Position=0; + Principal_File_list_Decalage=Indice; + } + else + { + if (Indice>=Liste_Nb_elements-5) + { + Principal_File_list_Position=Liste_Nb_elements-10; + Principal_File_list_Decalage=Indice-Principal_File_list_Position; + } + else + { + Principal_File_list_Position=Indice-4; + Principal_File_list_Decalage=4; + } + } +} + + +char FFF_Meilleur_nom[13]; +char * Nom_correspondant_le_mieux_a(char * Nom) +{ + char Nom_courant[13]; + char * Pointeur1; + char * Pointeur2; + char * Pointeur_Meilleur_nom; + struct Element_de_liste_de_fileselect * Element_courant; + byte Lettres_identiques=0; + byte Compteur; + + strcpy(FFF_Meilleur_nom,Principal_Nom_fichier); + Pointeur_Meilleur_nom=NULL; + + for (Element_courant=Liste_du_fileselect; Element_courant!=NULL; Element_courant=Element_courant->Suivant) + { + if ( (!Config.Find_file_fast) + || (Config.Find_file_fast==(Element_courant->Type+1)) ) + { + // On copie le nom de la liste en cours de traitement dans Nom_courant + // tout en le remettant sous forme normale. + for (Pointeur1=Element_courant->Nom,Pointeur2=Nom_courant;*Pointeur1;Pointeur1++) + if (*Pointeur1!=' ') + *(Pointeur2++)=*Pointeur1; + *Pointeur2=0; + // On compare et si c'est mieux, on stocke dans Meilleur_nom + for (Compteur=0; Nom_courant[Compteur]==Nom[Compteur]; Compteur++); + if (Compteur>Lettres_identiques) + { + Lettres_identiques=Compteur; + strcpy(FFF_Meilleur_nom,Nom_courant); + Pointeur_Meilleur_nom=Element_courant->Nom; + } + } + } + + return Pointeur_Meilleur_nom; +} + + +byte Bouton_Load_ou_Save(byte Load, byte Image) + // Load=1 => On affiche le menu du bouton LOAD + // Load=0 => On affiche le menu du bouton SAVE +{ + short Bouton_clicke; + struct Fenetre_Bouton_scroller * Scroller_de_fichiers; + short Temp; + unsigned Bidon; // Sert appeler _dos_setdrive + word Drives_Debut_Y; + byte Charger_ou_sauver_l_image=0; + char Nom_drive[3]=" "; + byte On_a_clicke_sur_OK=0;// Indique si on a click sur Load ou Save ou sur + //un bouton enclenchant Load ou Save juste aprs. + struct Composantes * Palette_initiale; // | Donnes concernant l'image qui + byte Image_modifiee_initiale; // | sont mmorises pour pouvoir + short Largeur_image_initiale; // |- tre restaures en sortant, + short Hauteur_image_initiale; // | parce que la preview elle les + byte Back_color_initiale; // | fout en l'air (c'te conne). + char Nom_fichier_initial[13]; // Sert laisser le nom courant du fichier en cas de sauvegarde + char Repertoire_precedent[13]; // Rpertoire d'o l'on vient aprs un CHDIR + char Commentaire_initial[TAILLE_COMMENTAIRE+1]; + char Fichier_recherche[13]=""; + char * Fichier_le_plus_ressemblant; + + Palette_initiale=(struct Composantes *)malloc(sizeof(T_Palette)); + memcpy(Palette_initiale,Principal_Palette,sizeof(T_Palette)); + + Back_color_initiale=Back_color; + Image_modifiee_initiale=Principal_Image_modifiee; + Largeur_image_initiale=Principal_Largeur_image; + Hauteur_image_initiale=Principal_Hauteur_image; + strcpy(Nom_fichier_initial,Principal_Nom_fichier); + strcpy(Commentaire_initial,Principal_Commentaire); + if (Load) + { + if (Image) + Ouvrir_fenetre(310,190,"Load picture"); + else + Ouvrir_fenetre(310,190,"Load brush"); + Fenetre_Definir_bouton_normal(125,157,51,14,"Load",0,1,0x001C); // 1 + } + else + { + if (Image) + Ouvrir_fenetre(310,190,"Save picture"); + else + Ouvrir_fenetre(310,190,"Save brush"); + Fenetre_Definir_bouton_normal(125,157,51,14,"Save",0,1,0x001C); // 1 + if (Principal_Format==0) // Correction du *.* + { + Principal_Format=Principal_Format_fichier; + Principal_File_list_Position=0; + Principal_File_list_Decalage=0; + } + + if (Principal_Format>NB_FORMATS_SAVE) // Correction d'un format insauvable + { + Principal_Format=FORMAT_PAR_DEFAUT; + Principal_File_list_Position=0; + Principal_File_list_Decalage=0; + } + // Affichage du commentaire + if (Format_Commentaire[Principal_Format-1]) + Print_dans_fenetre(46,176,Principal_Commentaire,CM_Noir,CM_Clair); + } + + Fenetre_Definir_bouton_normal(125,139,51,14,"Cancel",0,1,0x0001); // 2 + Fenetre_Definir_bouton_normal(125, 89,51,14,"Delete",0,1,0x0053); // 3 + + // Cdre autour des formats + Fenetre_Afficher_cadre( 7, 51,103, 35); + // Cdre autour des infos sur le fichier de dessin + Fenetre_Afficher_cadre(116, 51,187, 35); + // Cdre autour de la preview + Fenetre_Afficher_cadre_creux(179,88,124,84); + // Cdre autour du fileselector + Fenetre_Afficher_cadre_creux( 7,88,100,84); + + Fenetre_Definir_bouton_special(9,90,96,80); // 4 + + // Scroller du fileselector + Fenetre_Definir_bouton_scroller(110,89,82,1,10,0); // 5 + Scroller_de_fichiers=Fenetre_Liste_boutons_scroller; + + // Scroller des formats + Fenetre_Definir_bouton_scroller(12,55,27,(Load)?NB_FORMATS_LOAD+1:NB_FORMATS_SAVE,1,(Load)?Principal_Format:Principal_Format-1); // 6 + + // Texte de commentaire des dessins + Print_dans_fenetre(7,176,"Txt:",CM_Fonce,CM_Clair); + Fenetre_Definir_bouton_saisie(44,174,TAILLE_COMMENTAIRE); // 7 + + // Saisie du nom de fichier + Fenetre_Definir_bouton_saisie(200,71,12); // 8 + + Print_dans_fenetre( 27,65,"Format:",CM_Fonce,CM_Clair); + Print_dans_fenetre(120,55,"Image size :",CM_Fonce,CM_Clair); + Print_dans_fenetre(120,63,"File size :",CM_Fonce,CM_Clair); + Print_dans_fenetre(120,73,"File name:",CM_Fonce,CM_Clair); + + Print_Format(); + + // Dfinition des boutons reprsentant les lecteurs + Drives_Debut_Y=(Nb_drives<=13)? 23 : 18; + for (Temp=0; Temp=Liste_Nb_repertoires) + { + Print_dans_fenetre(127,107,"Delete",CM_Fonce,CM_Clair); + Print_dans_fenetre(127,115,"file ?",CM_Fonce,CM_Clair); + } + else + { + Print_dans_fenetre(127,107,"Remove",CM_Fonce,CM_Clair); + Print_dans_fenetre(127,115,"dir. ?",CM_Fonce,CM_Clair); + } + Print_dans_fenetre(127,123,"Yes/No",CM_Fonce,CM_Clair); + + do + { + Etat_Du_Clavier=SDL_GetKeyState(Bidon); + } while ((Etat_Du_Clavier[SDLK_y]==0) && (Etat_Du_Clavier[SDLK_n]==0) && (Etat_Du_Clavier[SDLK_ESCAPE]==0)); + + // On efface la demande de confirmation + Block(Fenetre_Pos_X+127*Menu_Facteur_X,Fenetre_Pos_Y+107*Menu_Facteur_Y, + Menu_Facteur_X*48,Menu_Facteur_Y*24,CM_Clair); + + // Si l'utilisateur confirme, + if (Touche=='Y') + { + // Si c'est un fichier + if (Principal_File_list_Position+Principal_File_list_Decalage>=Liste_Nb_repertoires) + // On efface le fichier (si on peut) + Temp=(!remove(Principal_Nom_fichier)); + else // Si c'est un repertoire + // On efface le repertoire (si on peut) + Temp=(!rmdir(Principal_Nom_fichier)); + + if (Temp) // Temp indique si l'effacement s'est bien pass + { + // On remonte si c'tait le dernier lment de la liste + if (Principal_File_list_Position+Principal_File_list_Decalage==Liste_Nb_elements-1) + { + if (Principal_File_list_Position) + Principal_File_list_Position--; + else + if (Principal_File_list_Decalage) + Principal_File_list_Decalage--; + } + else // Si ce n'tait pas le dernier, il faut faire gaffe ce + { // que ses copains d'en dessous ne remontent pas trop. + if ( (Principal_File_list_Position) + && (Principal_File_list_Position+10==Liste_Nb_elements) ) + { + Principal_File_list_Position--; + Principal_File_list_Decalage++; + } + } + // On relit les informations + Relire_liste_fichiers(Principal_Format,Principal_File_list_Position,Principal_File_list_Decalage,Scroller_de_fichiers); + // On demande la preview du nouveau fichier sur lequel on se trouve + Nouvelle_preview=1; + } + else + Erreur(0); + + // On place la barre de slection du brouillon au dbut s'il a le + // mme rpertoire que l'image principale. + if (!strcmp(Principal_Repertoire_courant,Brouillon_Repertoire_courant)) + { + Brouillon_File_list_Position=0; + Brouillon_File_list_Decalage=0; + } + } + Afficher_curseur(); + } + break; + + case 4 : // Zone d'affichage de la liste de fichiers + Effacer_curseur(); + + Temp=Calculer_decalage_click_dans_fileselector(); + if (Temp>=0) + { + if (Temp!=Principal_File_list_Decalage) + { + // On met jour le dcalage + Principal_File_list_Decalage=Temp; + + // On rcupre le nom du schmilblick "accder" + Determiner_element_de_la_liste(Principal_File_list_Position,Principal_File_list_Decalage,Principal_Nom_fichier); + // On affiche le nouveau nom de fichier + Print_Nom_fichier_dans_selecteur(); + // On affiche nouveau la liste + Afficher_la_liste_des_fichiers(Principal_File_list_Position,Principal_File_list_Decalage); + + // On vient de changer de nom de fichier, donc on doit s'appreter + // a rafficher une preview + Nouvelle_preview=1; + } + else + { + // En sauvegarde, si on a double-click sur un rpertoire, il + // faut mettre le nom de fichier au nom du rpertoire. Sinon, dans + // certains cas, on risque de sauvegarder avec le nom du fichier + // actuel au lieu de changer de rpertoire. + if (Principal_File_list_Position+Principal_File_list_Decalage On se place sur le nom de fichier qui correspond + if (Bouton_clicke<=0) + { + Temp=strlen(Fichier_recherche); + if (Temp<12) + { + Fichier_recherche[Temp]=toupper(Touche_ASCII); + Fichier_recherche[Temp+1]=0; + Fichier_le_plus_ressemblant=Nom_correspondant_le_mieux_a(Fichier_recherche); + if ( (Fichier_le_plus_ressemblant) + && (!memcmp(Fichier_recherche,FFF_Meilleur_nom,Temp+1)) ) + { + Temp=Principal_File_list_Position+Principal_File_list_Decalage; + Effacer_curseur(); + Placer_barre_de_selection_sur(Fichier_le_plus_ressemblant); + Preparer_et_afficher_liste_fichiers(Principal_File_list_Position,Principal_File_list_Decalage,Scroller_de_fichiers); + Afficher_curseur(); + if (Temp!=Principal_File_list_Position+Principal_File_list_Decalage) + Nouvelle_preview=1; + } + else + Fichier_recherche[Temp]=0; + } + } + else + *Fichier_recherche=0; + } + + if (On_a_clicke_sur_OK) + { + // Si c'est un rpertoire, on annule "On_a_clicke_sur_OK" et on passe + // dedans. + if (Repertoire_existe(Principal_Nom_fichier)) + { + Effacer_curseur(); + On_a_clicke_sur_OK=0; + + // On mmorise le rpertoire dans lequel on tait + if (strcmp(Principal_Nom_fichier,"..")) + strcpy(Repertoire_precedent,Nom_formate("..")); + else + { + for (Temp=strlen(Principal_Repertoire_courant); + (Temp>0) && (Principal_Repertoire_courant[Temp-1]!='\\'); + Temp--); + strcpy(Repertoire_precedent,Nom_formate(Principal_Repertoire_courant+Temp)); + } + + // On doit rentrer dans le rpertoire: + chdir(Principal_Nom_fichier); + Determiner_repertoire_courant(); + + // On lit le nouveau rpertoire + Lire_liste_des_fichiers(Principal_Format); + Trier_la_liste_des_fichiers(); + // On place la barre de slection sur le rpertoire d'o l'on vient + Placer_barre_de_selection_sur(Repertoire_precedent); + // Affichage des premiers fichiers visibles: + Preparer_et_afficher_liste_fichiers(Principal_File_list_Position,Principal_File_list_Decalage,Scroller_de_fichiers); + Afficher_curseur(); + Nouvelle_preview=1; + } + else // Sinon on essaye de charger ou sauver le fichier + { + strcpy(Principal_Repertoire_fichier,Principal_Repertoire_courant); + if (!Load) + Principal_Format_fichier=Principal_Format; + Charger_ou_sauver_l_image=1; + } + } + + // Gestion du chrono et des previews + if (Nouvelle_preview) + { + // On efface les infos de la preview prcdente s'il y en a une + // d'affiche + if (Etat_chrono==2) + { + Effacer_curseur(); + // On efface le "but is:" + Block(Fenetre_Pos_X+27*Menu_Facteur_X,Fenetre_Pos_Y+74*Menu_Facteur_Y, + Menu_Facteur_X*80,Menu_Facteur_Y<<3,CM_Clair); + // On efface le commentaire prcdent + Block(Fenetre_Pos_X+ 46*Menu_Facteur_X,Fenetre_Pos_Y+176*Menu_Facteur_Y, + Menu_Facteur_X<<8,Menu_Facteur_Y<<3,CM_Clair); + // On nttoie la zone o va s'afficher la preview: + Block(Fenetre_Pos_X+180*Menu_Facteur_X,Fenetre_Pos_Y+ 89*Menu_Facteur_Y, + Menu_Facteur_X*122,Menu_Facteur_Y*82,CM_Clair); + // On efface les dimensions de l'image + Block(Fenetre_Pos_X+226*Menu_Facteur_X,Fenetre_Pos_Y+ 55*Menu_Facteur_Y, + Menu_Facteur_X*72,Menu_Facteur_Y<<3,CM_Clair); + // On efface la taille du fichier + Block(Fenetre_Pos_X+226*Menu_Facteur_X,Fenetre_Pos_Y+ 63*Menu_Facteur_Y, + Menu_Facteur_X*72,Menu_Facteur_Y<<3,CM_Clair); + // Affichage du commentaire + if ( (!Load) && (Format_Commentaire[Principal_Format-1]) ) + Print_dans_fenetre(46,176,Principal_Commentaire,CM_Noir,CM_Clair); + Afficher_curseur(); + } + + Nouvelle_preview=0; + Etat_chrono=0; // Etat du chrono = Attente d'un Xme de seconde + // On lit le temps de dpart du chrono + Initialiser_chrono(Config.Chrono_delay); + } + + if (!Etat_chrono) // Prendre une nouvelle mesure du chrono et regarder + Tester_chrono(); // s'il ne faut pas afficher la preview + + if (Etat_chrono==1) // Il faut afficher la preview + { + if ( (Principal_File_list_Position+Principal_File_list_Decalage>=Liste_Nb_repertoires) && (Liste_Nb_elements) ) + { + strcpy(Principal_Repertoire_fichier,Principal_Repertoire_courant); + + Effacer_curseur(); + Charger_image(Image); + Afficher_curseur(); + + // Aprs le chargement de la preview, on restaure tout ce qui aurait + // pu tre modifi par le chargement de l'image: + memcpy(Principal_Palette,Palette_initiale,sizeof(T_Palette)); + Principal_Image_modifiee=Image_modifiee_initiale; + Principal_Largeur_image=Largeur_image_initiale; + Principal_Hauteur_image=Hauteur_image_initiale; + } + + Etat_chrono=2; // On arrte le chrono + } + } + while ( (!On_a_clicke_sur_OK) && (Bouton_clicke!=2) ); + + // Si on annule, on restaure l'ancien commentaire + if (Bouton_clicke==2) + strcpy(Principal_Commentaire,Commentaire_initial); + + // On restaure les donnes de l'image qui ont certainement t modifies + // par la preview. + memcpy(Principal_Palette,Palette_initiale,sizeof(T_Palette)); + Back_color=Back_color_initiale; + Principal_Image_modifiee=Image_modifiee_initiale; + Principal_Largeur_image=Largeur_image_initiale; + Principal_Hauteur_image=Hauteur_image_initiale; + Set_palette(Principal_Palette); + + Calculer_couleurs_menu_optimales(Principal_Palette); + Temp=(Fenetre_Pos_Y+(Fenetre_Hauteur*Menu_Facteur_Y)1024) || (Ecran_original_Y>768)) + { + Ecran_original_X=1024; + Ecran_original_Y=768; + } + + // Maintenant on peut chercher le mode qui correspond le mieux + Meilleur_mode=Resolution_actuelle; + Meilleure_largeur=0; + Meilleure_hauteur=0; + + + for (Mode=MODE_320_200; Mode<=MODE_1024_768; Mode++) + { + if (Mode_video[Mode].Etat<2) + { + Temp_X=Mode_video[Mode].Largeur; + Temp_Y=Mode_video[Mode].Hauteur; + + if ( (Ecran_original_X-TOLERANCE_X<=Temp_X) + && (Ecran_original_Y-TOLERANCE_Y<=Temp_Y) ) + return Mode; + else + { + if ( (Meilleure_largeur<=Temp_X) + && (Meilleure_hauteur<=Temp_Y) + && (Temp_X-TOLERANCE_X<=Ecran_original_X) + && (Temp_Y-TOLERANCE_Y<=Ecran_original_Y) ) + { + Meilleure_largeur=Temp_X; + Meilleure_hauteur=Temp_Y; + Meilleur_mode=Mode; + } + } + } + } + + return Meilleur_mode; +} + + +void Swapper_infos_selecteurs_image_et_brosse(void) +{ + char Chaine_temporaire[256]; + byte Octet_temporaire; + short Entier_temporaire; + + + strcpy(Chaine_temporaire ,Brosse_Repertoire_fichier); + strcpy(Brosse_Repertoire_fichier ,Principal_Repertoire_fichier); + strcpy(Principal_Repertoire_fichier,Chaine_temporaire); + + strcpy(Chaine_temporaire ,Brosse_Nom_fichier); + strcpy(Brosse_Nom_fichier ,Principal_Nom_fichier); + strcpy(Principal_Nom_fichier,Chaine_temporaire); + + Octet_temporaire =Brosse_Format_fichier; + Brosse_Format_fichier =Principal_Format_fichier; + Principal_Format_fichier=Octet_temporaire; + + Octet_temporaire=Brosse_Format; + Brosse_Format =Principal_Format; + Principal_Format=Octet_temporaire; + + Entier_temporaire =Brosse_File_list_Position; + Brosse_File_list_Position =Principal_File_list_Position; + Principal_File_list_Position=Entier_temporaire; + + Entier_temporaire =Brosse_File_list_Decalage; + Brosse_File_list_Decalage =Principal_File_list_Decalage; + Principal_File_list_Decalage=Entier_temporaire; + + strcpy(Chaine_temporaire ,Brosse_Repertoire_courant); + strcpy(Brosse_Repertoire_courant ,Principal_Repertoire_courant); + strcpy(Principal_Repertoire_courant,Chaine_temporaire); + + strcpy(Chaine_temporaire ,Brosse_Commentaire); + strcpy(Brosse_Commentaire ,Principal_Commentaire); + strcpy(Principal_Commentaire,Chaine_temporaire); +} + + +void Load_picture(byte Image) + // Image=1 => On charge/sauve une image + // Image=0 => On charge/sauve une brosse +{ + // Donnes initiales du fichier (au cas o on voudrait annuler) + char Repertoire_fichier_initial[256]; + char Nom_fichier_initial[13]; + byte Format_fichier_initial; + byte Ne_pas_restaurer; + byte Utiliser_palette_brosse; + struct Composantes * Palette_initiale; + byte Ancienne_forme_curseur; + short Principal_Largeur_image_initiale=Principal_Largeur_image; + short Principal_Hauteur_image_initiale=Principal_Hauteur_image; + char Commentaire_initial[TAILLE_COMMENTAIRE+1]; + int Nouveau_mode; + + + if (!Image) + Swapper_infos_selecteurs_image_et_brosse(); + + strcpy(Repertoire_fichier_initial,Principal_Repertoire_fichier); + strcpy(Nom_fichier_initial ,Principal_Nom_fichier); + Format_fichier_initial=Principal_Format_fichier; + + if (!Image) + { + Palette_initiale=(struct Composantes *)malloc(sizeof(T_Palette)); + memcpy(Palette_initiale,Principal_Palette,sizeof(T_Palette)); + } + + Ne_pas_restaurer=Bouton_Load_ou_Save(1,Image); + + if (Ne_pas_restaurer) + { + if (Image) + { + if (Principal_Image_modifiee) + Ne_pas_restaurer=Demande_de_confirmation("Discard unsaved changes?"); + } + else + Utiliser_palette_brosse=Demande_de_confirmation("Use the palette of the brush?"); + } + + if (Ne_pas_restaurer) + { + Ancienne_forme_curseur=Forme_curseur; + Effacer_curseur(); + Forme_curseur=FORME_CURSEUR_SABLIER; + Afficher_curseur(); + + if (Image) + { + // Si c'est une image qu'on charge, on efface l'ancien commentaire + // C'est loin d'tre indispensable, m'enfin bon... + if (Format_Backup_done[Principal_Format_fichier-1]) + Principal_Commentaire[0]='\0'; + + Ecran_original_X=0; + Ecran_original_Y=0; + } + else + Pixel_de_chargement=Pixel_Chargement_dans_brosse; + + Charger_image(Image); + + if (!Image) + { + if (!Utiliser_palette_brosse) + memcpy(Principal_Palette,Palette_initiale,sizeof(T_Palette)); + + if (Erreur_fichier==3) // On ne peut pas allouer la brosse + { + if (Brosse) free(Brosse); + Brosse=(byte *)malloc(1*1); + Brosse_Hauteur=1; + Brosse_Largeur=1; + *Brosse=Fore_color; + + if (Smear_Brosse) free(Smear_Brosse); + Smear_Brosse=(byte *)malloc(TAILLE_MAXI_PINCEAU*TAILLE_MAXI_PINCEAU); + Smear_Brosse_Hauteur=TAILLE_MAXI_PINCEAU; + Smear_Brosse_Largeur=TAILLE_MAXI_PINCEAU; + } + else + { + Brosse_Largeur=Principal_Largeur_image; + Brosse_Hauteur=Principal_Hauteur_image; + Smear_Brosse_Largeur=(Brosse_Largeur>TAILLE_MAXI_PINCEAU)?Brosse_Largeur:TAILLE_MAXI_PINCEAU; + Smear_Brosse_Hauteur=(Brosse_Hauteur>TAILLE_MAXI_PINCEAU)?Brosse_Hauteur:TAILLE_MAXI_PINCEAU; + } + + Tiling_Decalage_X=0; + Tiling_Decalage_Y=0; + + Brosse_Decalage_X=(Brosse_Largeur>>1); + Brosse_Decalage_Y=(Brosse_Hauteur>>1); + + Principal_Largeur_image=Principal_Largeur_image_initiale; + Principal_Hauteur_image=Principal_Hauteur_image_initiale; + Pixel_de_chargement=Pixel_Chargement_dans_ecran_courant; + + Enclencher_bouton(BOUTON_DESSIN,A_GAUCHE); + if (Config.Auto_discontinuous) + { + // On se place en mode Dessin discontinu la main + while (Operation_en_cours!=OPERATION_DESSIN_DISCONTINU) + Enclencher_bouton(BOUTON_DESSIN,A_DROITE); + } + Effacer_curseur(); + // On passe en brosse couleur: + Changer_la_forme_du_pinceau(FORME_PINCEAU_BROSSE_COULEUR); + } + else + { + Effacer_curseur(); + Forme_curseur=Ancienne_forme_curseur; + } + + if ( (Erreur_fichier==1) || (!Format_Backup_done[Principal_Format_fichier-1]) ) + { + Ne_pas_restaurer=0; + if (Erreur_fichier!=1) + Calculer_couleurs_menu_optimales(Principal_Palette); + } + else + { + if (Image) + { + if (Loupe_Mode) + { + Tracer_cadre_de_bouton_du_menu(BOUTON_LOUPE,0); + Pixel_Preview=Pixel_Preview_Normal; + Loupe_Mode=0; + } + + Nouveau_mode=Meilleur_mode_video(); + if ((Config.Auto_set_res) && (Nouveau_mode!=Resolution_actuelle)) + { + Initialiser_mode_video(Nouveau_mode); + Afficher_menu(); + } + else + { + Principal_Decalage_X=0; + Principal_Decalage_Y=0; + Calculer_limites(); + Calculer_coordonnees_pinceau(); + } + } + + Calculer_couleurs_menu_optimales(Principal_Palette); + Afficher_ecran(); + + if (Image) + Principal_Image_modifiee=0; + } + Afficher_menu(); + Afficher_curseur(); + } + + if (!Image) + free(Palette_initiale); + + if (!Ne_pas_restaurer) + { + strcpy(Principal_Nom_fichier ,Nom_fichier_initial); + strcpy(Principal_Repertoire_fichier,Repertoire_fichier_initial); + Principal_Format_fichier =Format_fichier_initial; + } + + if (!Image) + Swapper_infos_selecteurs_image_et_brosse(); + + Print_nom_fichier(); + Set_palette(Principal_Palette); +} + + +void Bouton_Load(void) +{ + // On sauve l'tat actuel des paramtres de l'image pour pouvoir les + // restituer en cas d'erreur n'affectant pas l'image + Upload_infos_page_principal(Principal_Backups->Pages); + + Load_picture(1); +} + + +void Bouton_Reload(void) +{ + byte Ancienne_forme_curseur; + int Nouveau_mode; + + // On sauve l'tat actuel des paramtres de l'image pour pouvoir les + // restituer en cas d'erreur n'affectant pas l'image + Upload_infos_page_principal(Principal_Backups->Pages); + + if ( (!Principal_Image_modifiee) || Demande_de_confirmation("Discard unsaved changes ?") ) + { + Effacer_curseur(); + Ancienne_forme_curseur=Forme_curseur; + Forme_curseur=FORME_CURSEUR_SABLIER; + Afficher_curseur(); + + Ecran_original_X=0; + Ecran_original_Y=0; + Charger_image(1); + + Effacer_curseur(); + Forme_curseur=Ancienne_forme_curseur; + + if (Erreur_fichier!=1) + { + if (Loupe_Mode) + { + Tracer_cadre_de_bouton_du_menu(BOUTON_LOUPE,0); + Pixel_Preview=Pixel_Preview_Normal; + Loupe_Mode=0; + } + + Nouveau_mode=Meilleur_mode_video(); + if ( ((Config.Auto_set_res) && (Nouveau_mode!=Resolution_actuelle)) && + (!Une_resolution_a_ete_passee_en_parametre) ) + { + Initialiser_mode_video(Nouveau_mode); + Afficher_menu(); + } + else + { + Principal_Decalage_X=0; + Principal_Decalage_Y=0; + Calculer_limites(); + Calculer_coordonnees_pinceau(); + } + + Afficher_ecran(); + + Principal_Image_modifiee=0; + } + } + else + Effacer_curseur(); + + Calculer_couleurs_menu_optimales(Principal_Palette); + Afficher_menu(); + if (Config.Afficher_limites_image) + Afficher_limites_de_l_image(); + + Desenclencher_bouton(BOUTON_CHARGER); + + Afficher_curseur(); +} + + +void Nom_fichier_backup(char * Nom, char * Nom_backup) +{ + short Curseur; + + strcpy(Nom_backup,Nom); + for (Curseur=strlen(Nom)-strlen(Principal_Nom_fichier); Nom_backup[Curseur]!='.'; Curseur++); + Nom_backup[Curseur+1]='\0'; + strcat(Nom_backup,"BAK"); +} + + +void Backup_du_fichier_sauvegarde(void) +{ + char Nom_du_fichier[256]; // Nom complet du fichier + char Nouveau_nom_du_fichier[256]; // Nom complet du fichier backup + + Nom_fichier_complet(Nom_du_fichier,0); + // Calcul du nom complet du fichier backup + Nom_fichier_backup(Nom_du_fichier,Nouveau_nom_du_fichier); + + Erreur_fichier=0; + + // On fait un backup si le nom du fichier n'est pas celui qu'on a choisi + // pour nommer les backups (c'est vident!). + if (strcmp(Nouveau_nom_du_fichier,Nom_du_fichier)) + { + // S'il y avait dj un fichier Backup, on l'efface + if ((Fichier_existe(Nouveau_nom_du_fichier)) + && (remove(Nouveau_nom_du_fichier)!=0)) + Erreur_fichier=1; + + if ((!Erreur_fichier) + && (rename(Nom_du_fichier,Nouveau_nom_du_fichier)!=0)) + Erreur_fichier=1; + } +} + + +void Save_picture(byte Image) + // Image=1 => On charge/sauve une image + // Image=0 => On charge/sauve une brosse +{ + // Donnes initiales du fichier (au cas o on voudrait annuler) + char Repertoire_fichier_initial[256]; + char Nom_fichier_initial[13]; + byte Format_fichier_initial; + byte Ne_pas_restaurer; + byte Ancienne_forme_curseur; + short Principal_Largeur_image_Backup=Principal_Largeur_image; + short Principal_Hauteur_image_Backup=Principal_Hauteur_image; + char Commentaire_initial[TAILLE_COMMENTAIRE+1]; + + + if (!Image) + Swapper_infos_selecteurs_image_et_brosse(); + + strcpy(Repertoire_fichier_initial,Principal_Repertoire_fichier); + strcpy(Nom_fichier_initial ,Principal_Nom_fichier); + Format_fichier_initial=Principal_Format_fichier; + + Ne_pas_restaurer=Bouton_Load_ou_Save(0,Image); + + if (Ne_pas_restaurer && Fichier_existe(Principal_Nom_fichier)) + { + Ne_pas_restaurer=Demande_de_confirmation("Erase old file ?"); + if ((Ne_pas_restaurer) && (Config.Backup)) + { + Backup_du_fichier_sauvegarde(); + if (Erreur_fichier) + { + Ne_pas_restaurer=0; + Erreur(0); + } + } + } + + if (Ne_pas_restaurer) + { + Ancienne_forme_curseur=Forme_curseur; + Effacer_curseur(); + Forme_curseur=FORME_CURSEUR_SABLIER; + Afficher_curseur(); + + if (Image) + Sauver_image(Image); + else + { + Principal_Largeur_image=Brosse_Largeur; + Principal_Hauteur_image=Brosse_Hauteur; + Sauver_image(Image); + Principal_Largeur_image=Principal_Largeur_image_Backup; + Principal_Hauteur_image=Principal_Hauteur_image_Backup; + } + + Effacer_curseur(); + Forme_curseur=Ancienne_forme_curseur; + + if ((Erreur_fichier==1) || (!Format_Backup_done[Principal_Format_fichier-1])) + Ne_pas_restaurer=0; + + Afficher_curseur(); + } + + if (!Ne_pas_restaurer) + { + strcpy(Principal_Nom_fichier ,Nom_fichier_initial); + strcpy(Principal_Repertoire_fichier,Repertoire_fichier_initial); + Principal_Format_fichier =Format_fichier_initial; + } + + if (!Image) + Swapper_infos_selecteurs_image_et_brosse(); + + Print_nom_fichier(); + Set_palette(Principal_Palette); +} + + +void Bouton_Save(void) +{ + Save_picture(1); +} + + +void Bouton_Autosave(void) +{ + byte Ancienne_forme_curseur; + char Nom_du_fichier[256]; + byte Le_fichier_existe; + + + Nom_fichier_complet(Nom_du_fichier,0); + Le_fichier_existe=Fichier_existe(Nom_du_fichier); + + if ( (!Le_fichier_existe) || Demande_de_confirmation("Erase old file ?") ) + { + if ((Le_fichier_existe) && (Config.Backup)) + Backup_du_fichier_sauvegarde(); + else + Erreur_fichier=0; + + Effacer_curseur(); + + if (!Erreur_fichier) + { + Ancienne_forme_curseur=Forme_curseur; + Forme_curseur=FORME_CURSEUR_SABLIER; + Afficher_curseur(); + + Sauver_image(1); + + Effacer_curseur(); + Forme_curseur=Ancienne_forme_curseur; + } + else + Erreur(0); + } + else + Effacer_curseur(); + + Desenclencher_bouton(BOUTON_SAUVER); + + Afficher_curseur(); +} + + +// -- Gestion des boutons de ligne ------------------------------------------ + +void Bouton_Lignes(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(Ligne_en_cours); + Afficher_curseur(); +} + + +void Bouton_Lignes_Switch_mode(void) +{ + if (Ligne_en_cours==OPERATION_LIGNE) + Ligne_en_cours=OPERATION_K_LIGNE; + else + { + if (Ligne_en_cours==OPERATION_K_LIGNE) + Ligne_en_cours=OPERATION_LIGNES_CENTREES; + else + Ligne_en_cours=OPERATION_LIGNE; + } + + Effacer_curseur(); + Afficher_sprite_dans_menu(BOUTON_LIGNES,Ligne_en_cours-OPERATION_LIGNE+6); + Demarrer_pile_operation(Ligne_en_cours); + Afficher_curseur(); +} + + +// -- Bouton de brosse ------------------------------------------------------ + +void Bouton_Brosse(void) +{ + Effacer_curseur(); + + if (Operation_en_cours!=OPERATION_PRISE_BROSSE) + Demarrer_pile_operation(OPERATION_PRISE_BROSSE); + else + Desenclencher_bouton(BOUTON_BROSSE); + + Afficher_curseur(); +} + + +void Bouton_desenclencher_Brosse(void) +{ + // On fait de notre mieux pour restaurer l'ancienne opration: + Demarrer_pile_operation(Operation_avant_interruption); +} + + +void Bouton_Restaurer_brosse(void) +{ + Effacer_curseur(); + // On passe en brosse couleur: + Changer_la_forme_du_pinceau(FORME_PINCEAU_BROSSE_COULEUR); + + Desenclencher_bouton(BOUTON_BROSSE); + Desenclencher_bouton(BOUTON_POLYBROSSE); + + Afficher_curseur(); +} + + +// -- Bouton de prise de brosse au lasso ------------------------------------ + +void Bouton_Lasso(void) +{ + Effacer_curseur(); + + if (Operation_en_cours!=OPERATION_POLYBROSSE) + { + Pinceau_Forme_avant_lasso=Pinceau_Forme; + Pinceau_Forme=FORME_PINCEAU_POINT; + Demarrer_pile_operation(OPERATION_POLYBROSSE); + } + else + Desenclencher_bouton(BOUTON_POLYBROSSE); + + Afficher_curseur(); +} + + +void Bouton_desenclencher_Lasso(void) +{ + // On fait de notre mieux pour restaurer l'ancienne opration: + Demarrer_pile_operation(Operation_avant_interruption); + Pinceau_Forme=Pinceau_Forme_avant_lasso; +} + + +// -- Bouton de pipette ----------------------------------------------------- + +void Bouton_Pipette(void) +{ + Effacer_curseur(); + + if (Operation_en_cours!=OPERATION_PIPETTE) + { + Pipette_Couleur=-1; + Demarrer_pile_operation(OPERATION_PIPETTE); + Pinceau_Forme_avant_pipette=Pinceau_Forme; + Pinceau_Forme=FORME_PINCEAU_POINT; + if (Operation_avant_interruption!=OPERATION_REMPLACER) + if ( (Mouse_Y=Principal_X_Zoom) ) ) + Print_dans_menu("X: Y: ( )",0); + } + else + Desenclencher_bouton(BOUTON_PIPETTE); + + Afficher_curseur(); +} + + +void Bouton_desenclencher_Pipette(void) +{ + if (Operation_avant_interruption!=OPERATION_REMPLACER) + if ( (Mouse_Y=Principal_X_Zoom) ) ) + Print_dans_menu("X: Y: ",0); + + // On fait de notre mieux pour restaurer l'ancienne opration: + if (Operation_en_cours==OPERATION_PIPETTE) + { + Demarrer_pile_operation(Operation_avant_interruption); + Pinceau_Forme=Pinceau_Forme_avant_pipette; + } +} + + + // -- Inversion de la couleur Fore et de la couleur Back -- +void Bouton_Inverser_foreback(void) +{ + byte Couleur_temporaire; + + Effacer_curseur(); + + Encadrer_couleur_menu(CM_Noir); + + Couleur_temporaire=Fore_color; + Fore_color =Back_color; + Back_color =Couleur_temporaire; + + Recadrer_palette(); + + Encadrer_couleur_menu(CM_Blanc); + + Afficher_foreback(); + Desenclencher_bouton(BOUTON_PIPETTE); + + Afficher_curseur(); +} + + +// -- Gestion du bouton Loupe ----------------------------------------------- + +byte On_vient_du_menu_de_facteurs_de_zoom=0; + +void Bouton_Loupe(void) +{ + Effacer_curseur(); + if ( (Operation_en_cours==OPERATION_LOUPE) || (Loupe_Mode) ) + { + Desenclencher_bouton(BOUTON_LOUPE); + } + else + { + Ancien_Principal_Decalage_X=Principal_Decalage_X; + Ancien_Principal_Decalage_Y=Principal_Decalage_Y; + Calculer_donnees_loupe(); + if ((!Config.Fast_zoom) || (Mouse_Y>=Menu_Ordonnee) || On_vient_du_menu_de_facteurs_de_zoom) + { + On_vient_du_menu_de_facteurs_de_zoom=0; + Demarrer_pile_operation(OPERATION_LOUPE); + } + else + { /* Ceci est de la duplication de code de presque toute l'opration de */ + /* la loupe... Il serait peut-tre plus propre de faire une procdure */ + /* qui s'en charge... */ + // On passe en mode loupe + Loupe_Mode=1; + + // La fonction d'affichage dans la partie image est dsormais un affichage + // spcial loupe. + Pixel_Preview=Pixel_Preview_Loupe; + + // On calcule l'origine de la loupe + Loupe_Decalage_X=Mouse_X-(Loupe_Largeur>>1); + Loupe_Decalage_Y=Mouse_Y-(Loupe_Hauteur>>1); + + // Calcul du coin haut_gauche de la fentre devant tre zoome DANS L'ECRAN + if (Loupe_Decalage_X+Loupe_Largeur>=Limite_Droite-Principal_Decalage_X) + Loupe_Decalage_X=Limite_Droite-Loupe_Largeur-Principal_Decalage_X+1; + if (Loupe_Decalage_Y+Loupe_Hauteur>=Limite_Bas-Principal_Decalage_Y) + Loupe_Decalage_Y=Limite_Bas-Loupe_Hauteur-Principal_Decalage_Y+1; + + // Calcul des coordonnes absolues de ce coin DANS L'IMAGE + Loupe_Decalage_X+=Principal_Decalage_X; + Loupe_Decalage_Y+=Principal_Decalage_Y; + + if (Loupe_Decalage_X<0) + Loupe_Decalage_X=0; + if (Loupe_Decalage_Y<0) + Loupe_Decalage_Y=0; + + // On calcule les bornes visibles dans l'cran + Recadrer_ecran_par_rapport_au_zoom(); + Calculer_limites(); + Afficher_ecran(); + + // Repositionner le curseur en fonction des coordonnes visibles + Calculer_coordonnees_pinceau(); + } + } + Afficher_curseur(); +} + + +void Bouton_Menu_Loupe(void) +{ + short Bouton_clicke; + + Ouvrir_fenetre(141,114,"Zoom factors"); + + Fenetre_Definir_bouton_normal(45,88,51,14,"Cancel",0,1,0x0001); // 1 + + Fenetre_Definir_bouton_normal( 9,25,27,14, "x2",0,Loupe_Facteur!= 2,0x003B); // 2 + Fenetre_Definir_bouton_normal( 41,25,27,14, "x3",0,Loupe_Facteur!= 3,0x003C); // 3 + Fenetre_Definir_bouton_normal( 73,25,27,14, "x4",0,Loupe_Facteur!= 4,0x003D); // 4 + Fenetre_Definir_bouton_normal(105,25,27,14, "x5",0,Loupe_Facteur!= 5,0x003E); // 5 + Fenetre_Definir_bouton_normal( 9,45,27,14, "x6",0,Loupe_Facteur!= 6,0x003F); // 6 + Fenetre_Definir_bouton_normal( 41,45,27,14, "x8",0,Loupe_Facteur!= 8,0x0040); // 7 + Fenetre_Definir_bouton_normal( 73,45,27,14,"x10",0,Loupe_Facteur!=10,0x0041); // 8 + Fenetre_Definir_bouton_normal(105,45,27,14,"x12",0,Loupe_Facteur!=12,0x0042); // 9 + Fenetre_Definir_bouton_normal( 9,65,27,14,"x14",0,Loupe_Facteur!=14,0x0043); // 10 + Fenetre_Definir_bouton_normal( 41,65,27,14,"x16",0,Loupe_Facteur!=16,0x0044); // 11 + Fenetre_Definir_bouton_normal( 73,65,27,14,"x18",0,Loupe_Facteur!=18,0x0085); // 12 + Fenetre_Definir_bouton_normal(105,65,27,14,"x20",0,Loupe_Facteur!=20,0x0086); // 13 + + Afficher_curseur(); + + do + { + Bouton_clicke=Fenetre_Bouton_clicke(); + } + while (Bouton_clicke<=0); + + if (Bouton_clicke>1) + { + Menu_Ordonnee=Menu_Ordonnee_avant_fenetre; + Changer_facteur_loupe(Bouton_clicke-2); + } + + Fermer_fenetre(); + + if ( (Bouton_clicke==1) && (!Loupe_Mode) && (Operation_en_cours!=OPERATION_LOUPE) ) + Desenclencher_bouton(BOUTON_LOUPE); + + Afficher_curseur(); + + if ( (Bouton_clicke>1) && (!Loupe_Mode) && (Operation_en_cours!=OPERATION_LOUPE) ) + { + On_vient_du_menu_de_facteurs_de_zoom=1; + Enclencher_bouton(BOUTON_LOUPE,A_GAUCHE); + } +} + + +void Bouton_desenclencher_Loupe(void) +{ + if (Loupe_Mode) + { + // On sort du mode loupe + Loupe_Mode=0; + + /* + // --> Recalculer le dcalage de l'cran lorsqu'on sort de la loupe <-- + // Centrage "brut" de lcran par rapport la loupe + Principal_Decalage_X=Loupe_Decalage_X-((Largeur_ecran-Loupe_Largeur)>>1); + Principal_Decalage_Y=Loupe_Decalage_Y-((Menu_Ordonnee-Loupe_Hauteur)>>1); + */ + // Correction en cas de dbordement de l'image + if (Ancien_Principal_Decalage_X+Largeur_ecran>Principal_Largeur_image) + Principal_Decalage_X=Principal_Largeur_image-Largeur_ecran; + else + Principal_Decalage_X=Ancien_Principal_Decalage_X; + if (Principal_Decalage_X<0) + Principal_Decalage_X=0; + + if (Ancien_Principal_Decalage_Y+Menu_Ordonnee>Principal_Hauteur_image) + Principal_Decalage_Y=Principal_Hauteur_image-Menu_Ordonnee; + else + Principal_Decalage_Y=Ancien_Principal_Decalage_Y; + if (Principal_Decalage_Y<0) + Principal_Decalage_Y=0; + + // La fonction d'affichage dans l'image est dsormais un affichage normal. + Pixel_Preview=Pixel_Preview_Normal; + + // Calculer les bornes visibles dans l'cran + Calculer_limites(); + Afficher_ecran(); // <=> Display_screen(); + // Repositionner le curseur en fonction des coordonnes visibles + Calculer_coordonnees_pinceau(); + } + else // On fait de notre mieux pour restaurer l'ancienne opration: + Demarrer_pile_operation(Operation_avant_interruption); +} + + +// -------------------------------- Grille ----------------------------------- + +void Bouton_Snap_Mode(void) +{ + Effacer_curseur(); + Snap_Mode=!Snap_Mode; + Calculer_coordonnees_pinceau(); + Afficher_curseur(); +} + + +void Bouton_Menu_Grille(void) +{ + short Bouton_clicke; + word X_choisi =Snap_Largeur; + word Y_choisi =Snap_Hauteur; + short dX_choisi=Snap_Decalage_X; + short dY_choisi=Snap_Decalage_Y; + + struct Fenetre_Bouton_special * Bouton_saisie_X; + struct Fenetre_Bouton_special * Bouton_saisie_Y; + struct Fenetre_Bouton_special * Bouton_saisie_dX; + struct Fenetre_Bouton_special * Bouton_saisie_dY; + + char Chaine[3]; + + + Ouvrir_fenetre(133,98,"Grid"); + + Fenetre_Definir_bouton_normal(12,72,51,14,"Cancel",0,1,0x0001); // 1 + Fenetre_Definir_bouton_normal(70,72,51,14,"OK" ,0,1,0x001C); // 2 + + Print_dans_fenetre(19,26, "X:",CM_Fonce,CM_Clair); + Fenetre_Definir_bouton_saisie(37,24,2); // 3 + Bouton_saisie_X=Fenetre_Liste_boutons_special; + Num2str(X_choisi,Chaine,2); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_X,Chaine); + + Print_dans_fenetre(19,47, "Y:",CM_Fonce,CM_Clair); + Fenetre_Definir_bouton_saisie(37,45,2); // 4 + Bouton_saisie_Y=Fenetre_Liste_boutons_special; + Num2str(Y_choisi,Chaine,2); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_Y,Chaine); + + Print_dans_fenetre(69,26,"dX:",CM_Fonce,CM_Clair); + Fenetre_Definir_bouton_saisie(95,24,2); // 5 + Bouton_saisie_dX=Fenetre_Liste_boutons_special; + Num2str(dX_choisi,Chaine,2); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_dX,Chaine); + + Print_dans_fenetre(69,47,"dY:",CM_Fonce,CM_Clair); + Fenetre_Definir_bouton_saisie(95,45,2); // 6 + Bouton_saisie_dY=Fenetre_Liste_boutons_special; + Num2str(dY_choisi,Chaine,2); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_dY,Chaine); + + Afficher_curseur(); + + do + { + Bouton_clicke=Fenetre_Bouton_clicke(); + + switch (Bouton_clicke) + { + case 3 : + Effacer_curseur(); + Num2str(X_choisi,Chaine,2); + Readline(39,26,Chaine,2,1); + X_choisi=atoi(Chaine); + // On corrige les dimensions + if ((!X_choisi) || (X_choisi>80)) + { + if (!X_choisi) + X_choisi=1; + else + X_choisi=80; + Num2str(X_choisi,Chaine,2); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_X,Chaine); + } + if (dX_choisi>=X_choisi) + { + dX_choisi=X_choisi-1; + Num2str(dX_choisi,Chaine,2); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_dX,Chaine); + } + Afficher_curseur(); + break; + case 4 : + Effacer_curseur(); + Num2str(Y_choisi,Chaine,2); + Readline(39,47,Chaine,2,1); + Y_choisi=atoi(Chaine); + // On corrige les dimensions + if ((!Y_choisi) || (Y_choisi>80)) + { + if (!Y_choisi) + Y_choisi=1; + else + Y_choisi=80; + Num2str(Y_choisi,Chaine,2); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_Y,Chaine); + } + if (dY_choisi>=Y_choisi) + { + dY_choisi=Y_choisi-1; + Num2str(dY_choisi,Chaine,2); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_dY,Chaine); + } + Afficher_curseur(); + break; + case 5 : + Effacer_curseur(); + Num2str(dX_choisi,Chaine,2); + Readline(97,26,Chaine,2,1); + dX_choisi=atoi(Chaine); + // On corrige les dimensions + if (dX_choisi>79) + dX_choisi=79; + if (dX_choisi>=X_choisi) + dX_choisi=X_choisi-1; + + Num2str(dX_choisi,Chaine,2); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_dX,Chaine); + + Afficher_curseur(); + break; + case 6 : + Effacer_curseur(); + Num2str(dY_choisi,Chaine,2); + Readline(97,47,Chaine,2,1); + dY_choisi=atoi(Chaine); + // On corrige les dimensions + if (dY_choisi>79) + dY_choisi=79; + if (dY_choisi>=Y_choisi) + dY_choisi=Y_choisi-1; + + Num2str(dY_choisi,Chaine,2); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_dY,Chaine); + + Afficher_curseur(); + } + } + while ( (Bouton_clicke!=1) && (Bouton_clicke!=2) ); + + if (Bouton_clicke==2) // OK + { + Snap_Largeur=X_choisi; + Snap_Hauteur=Y_choisi; + Snap_Decalage_X=dX_choisi; + Snap_Decalage_Y=dY_choisi; + Snap_Mode=1; + } + + Fermer_fenetre(); + + if ( (Bouton_clicke==2) && (!Snap_Mode) ) + Bouton_Snap_Mode(); + + Afficher_curseur(); +} + + +// ----------------------- Modifications de brosse --------------------------- + +void Bouton_Brush_FX(void) +{ + short Bouton_clicke; + short Indice; + + Ouvrir_fenetre(310,162,"Brush effects"); + + Fenetre_Afficher_cadre( 6,19,298,61); + Fenetre_Afficher_cadre( 6,83,122,53); + Fenetre_Afficher_cadre(137,83,167,53); + + Fenetre_Definir_bouton_normal(236,141, 67,14,"Cancel" ,0,1,0x0001); // 1 + Fenetre_Definir_bouton_normal( 19, 46, 27,14,"X\035" ,1,1,0x002D); // 2 + Fenetre_Definir_bouton_normal( 19, 61, 27,14,"Y\022" ,1,1,0x0015); // 3 + Fenetre_Definir_bouton_normal( 58, 46, 37,14,"90" ,0,1,0xFFFF); // 4 + Fenetre_Definir_bouton_normal( 96, 46, 37,14,"180" ,0,1,0xFFFF); // 5 + Fenetre_Definir_bouton_normal( 58, 61, 75,14,"any angle" ,0,1,0xFFFF); // 6 + Fenetre_Definir_bouton_normal(145, 46, 67,14,"Stretch" ,2,1,0x0014); // 7 + Fenetre_Definir_bouton_normal(145, 61, 67,14,"Distort" ,1,1,0x0020); // 8 + Fenetre_Definir_bouton_normal(155, 99,131,14,"Recolorize" ,1,1,0x0013); // 9 + Fenetre_Definir_bouton_normal(155,117,131,14,"Get brush colors",1,1,0x0022); // 10 + + // Boutons reprsentant les coins du brush handle: (HG,HD,C,BG,BD) + Fenetre_Definir_bouton_normal( 75, 90,11,11,"",0,1,0x0047); // 11 + Fenetre_Definir_bouton_normal(103, 90,11,11,"",0,1,0x0049); // 12 + Fenetre_Definir_bouton_normal( 89,104,11,11,"",0,1,0x004C); // 13 + Fenetre_Definir_bouton_normal( 75,118,11,11,"",0,1,0x004F); // 14 + Fenetre_Definir_bouton_normal(103,118,11,11,"",0,1,0x0051); // 15 + + Fenetre_Definir_bouton_normal(224,46,67,14,"Outline",1,1,0x0018); // 16 + Fenetre_Definir_bouton_normal(224,61,67,14,"Nibble" ,1,1,0x0031); // 17 + + Fenetre_Definir_bouton_normal( 7,141, 60,14,"Load",1,1,0x0026); // 18 + Fenetre_Definir_bouton_normal( 70,141, 60,14,"Save",1,1,0x001F); // 19 + + Print_dans_fenetre( 80, 24,"Shape modifications",CM_Fonce,CM_Clair); + Print_dans_fenetre( 10, 36,"Mirror",CM_Fonce,CM_Clair); + Print_dans_fenetre( 72, 36,"Rotate",CM_Fonce,CM_Clair); + Print_dans_fenetre(155, 36,"Deform",CM_Fonce,CM_Clair); + Print_dans_fenetre(230, 36,"Borders",CM_Fonce,CM_Clair); + Print_dans_fenetre(141, 88,"Colors modifications",CM_Fonce,CM_Clair); + Print_dans_fenetre( 20,102,"Brush",CM_Fonce,CM_Clair); + Print_dans_fenetre( 16,110,"handle",CM_Fonce,CM_Clair); + + // Dessin des pointills pour le "brush handle" + for (Indice=0; Indice<13; Indice+=2) + { + Pixel_dans_fenetre( 88+Indice, 92,CM_Fonce); + Pixel_dans_fenetre( 88+Indice,126,CM_Fonce); + Pixel_dans_fenetre( 77,103+Indice,CM_Fonce); + Pixel_dans_fenetre(111,103+Indice,CM_Fonce); + } + // Dessin des coins et du centre pour les boutons du "brush handle" + // Coin HG + Block(Fenetre_Pos_X+(Menu_Facteur_X* 77),Fenetre_Pos_Y+(Menu_Facteur_Y* 92),Menu_Facteur_X*7,Menu_Facteur_Y,CM_Noir); + Block(Fenetre_Pos_X+(Menu_Facteur_X* 77),Fenetre_Pos_Y+(Menu_Facteur_Y* 92),Menu_Facteur_X,Menu_Facteur_Y*7,CM_Noir); + // Coin HD + Block(Fenetre_Pos_X+(Menu_Facteur_X*105),Fenetre_Pos_Y+(Menu_Facteur_Y* 92),Menu_Facteur_X*7,Menu_Facteur_Y,CM_Noir); + Block(Fenetre_Pos_X+(Menu_Facteur_X*111),Fenetre_Pos_Y+(Menu_Facteur_Y* 92),Menu_Facteur_X,Menu_Facteur_Y*7,CM_Noir); + // Centre + Block(Fenetre_Pos_X+(Menu_Facteur_X* 91),Fenetre_Pos_Y+(Menu_Facteur_Y*109),Menu_Facteur_X*7,Menu_Facteur_Y,CM_Noir); + Block(Fenetre_Pos_X+(Menu_Facteur_X* 94),Fenetre_Pos_Y+(Menu_Facteur_Y*106),Menu_Facteur_X,Menu_Facteur_Y*7,CM_Noir); + // Coin BG + Block(Fenetre_Pos_X+(Menu_Facteur_X* 77),Fenetre_Pos_Y+(Menu_Facteur_Y*126),Menu_Facteur_X*7,Menu_Facteur_Y,CM_Noir); + Block(Fenetre_Pos_X+(Menu_Facteur_X* 77),Fenetre_Pos_Y+(Menu_Facteur_Y*120),Menu_Facteur_X,Menu_Facteur_Y*7,CM_Noir); + // Coin BD + Block(Fenetre_Pos_X+(Menu_Facteur_X*105),Fenetre_Pos_Y+(Menu_Facteur_Y*126),Menu_Facteur_X*7,Menu_Facteur_Y,CM_Noir); + Block(Fenetre_Pos_X+(Menu_Facteur_X*111),Fenetre_Pos_Y+(Menu_Facteur_Y*120),Menu_Facteur_X,Menu_Facteur_Y*7,CM_Noir); + + Afficher_curseur(); + + do + { + Bouton_clicke=Fenetre_Bouton_clicke(); + } + while (Bouton_clicke<=0); + + Fermer_fenetre(); + Desenclencher_bouton(BOUTON_EFFETS_BROSSE); + + // Gestion du bouton click + switch (Bouton_clicke) + { + case 2 : // Flip X + Flip_X_LOWLEVEL(); + break; + case 3 : // Flip Y + Flip_Y_LOWLEVEL(); + break; + case 4 : // 90 Rotation + Rotate_90_deg(); + break; + case 5 : // 180 Rotation + if (Brosse_Hauteur&1) + { // Brosse de hauteur impaire + Flip_X_LOWLEVEL(); + Flip_Y_LOWLEVEL(); + } + else + Rotate_180_deg_LOWLEVEL(); + Brosse_Decalage_X=(Brosse_Largeur>>1); + Brosse_Decalage_Y=(Brosse_Hauteur>>1); + break; + case 6 : // Any angle rotation + Demarrer_pile_operation(OPERATION_TOURNER_BROSSE); + break; + case 7 : // Stretch + Demarrer_pile_operation(OPERATION_ETIRER_BROSSE); + break; + case 8 : // Distort + Afficher_curseur(); + Message_Non_disponible(); // !!! TEMPORAIRE !!! + Effacer_curseur(); + break; + case 9 : // Recolorize + Remap_brosse(); + break; + case 10 : // Get brush colors + Afficher_curseur(); + Get_colors_from_brush(); + Effacer_curseur(); + break; + case 11 : // Brush Attachment: Top-Left + Brosse_Decalage_X=0; + Brosse_Decalage_Y=0; + break; + case 12 : // Brush Attachment: Top-Right + Brosse_Decalage_X=(Brosse_Largeur-1); + Brosse_Decalage_Y=0; + break; + case 13 : // Brush Attachment: Center + Brosse_Decalage_X=(Brosse_Largeur>>1); + Brosse_Decalage_Y=(Brosse_Hauteur>>1); + break; + case 14 : // Brush Attachment: Bottom-Left + Brosse_Decalage_X=0; + Brosse_Decalage_Y=(Brosse_Hauteur-1); + break; + case 15 : // Brush Attachment: Bottom-Right + Brosse_Decalage_X=(Brosse_Largeur-1); + Brosse_Decalage_Y=(Brosse_Hauteur-1); + break; + case 16 : // Outline + Outline_brush(); + break; + case 17 : // Nibble + Nibble_brush(); + break; + case 18 : // Load + Afficher_curseur(); + Load_picture(0); + Effacer_curseur(); + break; + case 19 : // Save + Afficher_curseur(); + Save_picture(0); + Effacer_curseur(); + break; + } + + Afficher_curseur(); +} + + +// -- Mode Smooth ----------------------------------------------------------- +void Bouton_Smooth_Mode(void) +{ + if (Smooth_Mode) + Fonction_effet=Aucun_effet; + else + { + Fonction_effet=Effet_Smooth; + Shade_Mode=0; + Quick_shade_Mode=0; + Colorize_Mode=0; + Tiling_Mode=0; + Smear_Mode=0; + } + Smooth_Mode=!Smooth_Mode; +} + + +byte Smooth_Matrice_defaut[4][3][3]= +{ + { {1,2,1}, {2,4,2}, {1,2,1} }, + { {1,3,1}, {3,9,3}, {1,3,1} }, + { {0,1,0}, {1,2,1}, {0,1,0} }, + { {2,3,2}, {3,1,3}, {2,3,2} } +}; + +void Bouton_Smooth_Menu(void) +{ + short Bouton_clicke; + short X,Y,I,J; + byte Matrice_choisie[3][3]; + struct Fenetre_Bouton_special * Matrice_Zone_saisie[3][3]; + char Chaine[3]; + + Ouvrir_fenetre(142,109,"Smooth"); + + Fenetre_Definir_bouton_normal(82,59,53,14,"Cancel",0,1,0x0001); // 1 + Fenetre_Definir_bouton_normal(82,88,53,14,"OK" ,0,1,0x001C); // 2 + + Fenetre_Afficher_cadre(6,17,130,37); + for (X=11,Y=0; Y<4; X+=31,Y++) + { + Fenetre_Definir_bouton_normal(X,22,27,27,"",0,1,0xFFFF); // 3,4,5,6 + for (J=0; J<3; J++) + for (I=0; I<3; I++) + Print_char_dans_fenetre(X+2+(I<<3),24+(J<<3),'0'+Smooth_Matrice_defaut[Y][I][J],CM_Noir,CM_Clair); + } + + Fenetre_Afficher_cadre(6,58, 69,45); + for (J=0; J<3; J++) + for (I=0; I<3; I++) + { + Fenetre_Definir_bouton_saisie(10+(I*21),62+(J*13),2); // 7..15 + Matrice_Zone_saisie[I][J]=Fenetre_Liste_boutons_special; + Num2str(Matrice_choisie[I][J]=Smooth_Matrice[I][J],Chaine,2); + Fenetre_Contenu_bouton_saisie(Fenetre_Liste_boutons_special,Chaine); + } + + Afficher_curseur(); + + do + { + Bouton_clicke=Fenetre_Bouton_clicke(); + + if (Bouton_clicke>2) + { + if (Bouton_clicke<=6) + { + memcpy(Matrice_choisie,Smooth_Matrice_defaut[Bouton_clicke-3],sizeof(Matrice_choisie)); + Effacer_curseur(); + for (J=0; J<3; J++) + for (I=0; I<3; I++) + { + Num2str(Matrice_choisie[I][J],Chaine,2); + Fenetre_Contenu_bouton_saisie(Matrice_Zone_saisie[I][J],Chaine); + } + Afficher_curseur(); + } + else + { + Effacer_curseur(); + I=Bouton_clicke-7; X=I%3; Y=I/3; + Num2str(Matrice_choisie[X][Y],Chaine,2); + Readline(Matrice_Zone_saisie[X][Y]->Pos_X+2, + Matrice_Zone_saisie[X][Y]->Pos_Y+2, + Chaine,2,1); + Matrice_choisie[X][Y]=atoi(Chaine); + Afficher_curseur(); + } + } + } + while ((Bouton_clicke!=1) && (Bouton_clicke!=2)); + + Fermer_fenetre(); + + if (Bouton_clicke==2) // OK + { + memcpy(Smooth_Matrice,Matrice_choisie,sizeof(Smooth_Matrice)); + Smooth_Mode=0; // On le met 0 car la fonct suivante va le passer 1 + Bouton_Smooth_Mode(); + } + + Afficher_curseur(); +} + + +// -- Mode Smear ------------------------------------------------------------ +void Bouton_Smear_Mode(void) +{ + if (!Smear_Mode) + { + if (!Colorize_Mode) + Fonction_effet=Aucun_effet; + Shade_Mode=0; + Quick_shade_Mode=0; + Smooth_Mode=0; + Tiling_Mode=0; + } + Smear_Mode=!Smear_Mode; +} + + +// -- Mode Colorize --------------------------------------------------------- +void Calculer_les_tables_de_Colorize(void) +{ + word Indice; + word Facteur_A; + word Facteur_B; + + Facteur_A=256*(100-Colorize_Opacite)/100; + Facteur_B=256*( Colorize_Opacite)/100; + + for (Indice=0;Indice<64;Indice++) + { + Table_de_multiplication_par_Facteur_A[Indice]=Indice*Facteur_A; + Table_de_multiplication_par_Facteur_B[Indice]=Indice*Facteur_B; + } +} + + +void Bouton_Colorize_Mode(void) +{ + if (Colorize_Mode) + Fonction_effet=Aucun_effet; + else + { + switch(Colorize_Mode_en_cours) + { + case 0 : + Fonction_effet=Effet_Colorize_interpole; + break; + case 1 : + Fonction_effet=Effet_Colorize_additif; + break; + case 2 : + Fonction_effet=Effet_Colorize_soustractif; + } + Shade_Mode=0; + Quick_shade_Mode=0; + Smooth_Mode=0; + Tiling_Mode=0; + } + Colorize_Mode=!Colorize_Mode; +} + + +void Bouton_Colorize_Afficher_la_selection(int Numero) +{ + short Pos_Y; // Ligne o afficher les flches de slection + + // On commence par effacer les anciennes slections: + // Partie gauche + Print_dans_fenetre(4,37," ",CM_Noir,CM_Clair); + Print_dans_fenetre(4,57," ",CM_Noir,CM_Clair); + Print_dans_fenetre(4,74," ",CM_Noir,CM_Clair); + // Partie droite + Print_dans_fenetre(129,37," ",CM_Noir,CM_Clair); + Print_dans_fenetre(129,57," ",CM_Noir,CM_Clair); + Print_dans_fenetre(129,74," ",CM_Noir,CM_Clair); + + // Ensuite, on affiche la flche l o il le faut: + switch(Numero) + { + case 0 : // Mthode interpole + Pos_Y=37; + break; + case 1 : // Mthode additive + Pos_Y=57; + break; + case 2 : // Mthode soustractive + Pos_Y=74; + } + Print_dans_fenetre(4,Pos_Y,"\020",CM_Noir,CM_Clair); + Print_dans_fenetre(129,Pos_Y,"\021",CM_Noir,CM_Clair); +} + +void Bouton_Colorize_Menu(void) +{ + short Opacite_choisie; + short Mode_choisi; + short Bouton_clicke; + char Chaine[4]; + + Ouvrir_fenetre(140,118,"Transparency"); + + Print_dans_fenetre(16,23,"Opacity:",CM_Fonce,CM_Clair); + Fenetre_Definir_bouton_saisie(87,21,3); // 1 + Print_dans_fenetre(117,23,"%",CM_Fonce,CM_Clair); + Fenetre_Definir_bouton_normal(16,34,108,14,"Interpolate",1,1,0x0017); // 2 + Fenetre_Afficher_cadre(12,18,116,34); + + Fenetre_Definir_bouton_normal(16,54,108,14,"Additive" ,2,1,0x0020); // 3 + Fenetre_Definir_bouton_normal(16,71,108,14,"Subtractive",1,1,0x001F); // 4 + + Fenetre_Definir_bouton_normal(16,94, 51,14,"Cancel" ,0,1,0x0001); // 5 + Fenetre_Definir_bouton_normal(73,94, 51,14,"OK" ,0,1,0x001C); // 6 + + Num2str(Colorize_Opacite,Chaine,3); + Fenetre_Contenu_bouton_saisie(Fenetre_Liste_boutons_special,Chaine); + Bouton_Colorize_Afficher_la_selection(Colorize_Mode_en_cours); + + Opacite_choisie=Colorize_Opacite; + Mode_choisi =Colorize_Mode_en_cours; + + Afficher_curseur(); + + do + { + Bouton_clicke=Fenetre_Bouton_clicke(); + + switch(Bouton_clicke) + { + case 1: // Zone de saisie de l'opacit + Effacer_curseur(); + Num2str(Opacite_choisie,Chaine,3); + Readline(89,23,Chaine,3,1); + Opacite_choisie=atoi(Chaine); + // On corrige le pourcentage + if (Opacite_choisie>100) + { + Opacite_choisie=100; + Num2str(Opacite_choisie,Chaine,3); + Fenetre_Contenu_bouton_saisie(Fenetre_Liste_boutons_special,Chaine); + } + Afficher_curseur(); + break; + case 2: // Mthode interpole + case 3: // Mthode additive + case 4: // Mthode soustractive + Mode_choisi=Bouton_clicke-2; + Effacer_curseur(); + Bouton_Colorize_Afficher_la_selection(Mode_choisi); + Afficher_curseur(); + } + } + while (Bouton_clicke<5); + + Fermer_fenetre(); + + if (Bouton_clicke==6) // OK + { + Colorize_Opacite =Opacite_choisie; + Colorize_Mode_en_cours=Mode_choisi; + Calculer_les_tables_de_Colorize(); + Colorize_Mode=0; // On le met 0 car la fonct suivante va le passer 1 + Bouton_Colorize_Mode(); + } + + Afficher_curseur(); +} + + +// -- Mode Tiling ----------------------------------------------------------- +void Bouton_Tiling_Mode(void) +{ + if (Tiling_Mode) + Fonction_effet=Aucun_effet; + else + { + Fonction_effet=Effet_Tiling; + Shade_Mode=0; + Quick_shade_Mode=0; + Colorize_Mode=0; + Smooth_Mode=0; + Smear_Mode=0; + } + Tiling_Mode=!Tiling_Mode; +} + + +void Bouton_Tiling_Menu(void) +{ + short Bouton_clicke; + short Offset_X_choisi=Tiling_Decalage_X; + short Offset_Y_choisi=Tiling_Decalage_Y; + char Chaine[5]; + struct Fenetre_Bouton_special * Bouton_saisie_Decalage_X; + struct Fenetre_Bouton_special * Bouton_saisie_Decalage_Y; + + Ouvrir_fenetre(138,79,"Tiling"); + + Fenetre_Definir_bouton_normal(13,55,51,14,"Cancel",0,1,0x0001); // 1 + Fenetre_Definir_bouton_normal(74,55,51,14,"OK" ,0,1,0x001C); // 2 + Fenetre_Definir_bouton_saisie(91,21,4); // 3 + Bouton_saisie_Decalage_X=Fenetre_Liste_boutons_special; + Fenetre_Definir_bouton_saisie(91,35,4); // 4 + Bouton_saisie_Decalage_Y=Fenetre_Liste_boutons_special; + Print_dans_fenetre(12,23,"Offset X:",CM_Fonce,CM_Clair); + Print_dans_fenetre(12,37,"Offset Y:",CM_Fonce,CM_Clair); + + Num2str(Tiling_Decalage_X,Chaine,4); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_Decalage_X,Chaine); + Num2str(Tiling_Decalage_Y,Chaine,4); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_Decalage_Y,Chaine); + + Afficher_curseur(); + + do + { + Bouton_clicke=Fenetre_Bouton_clicke(); + + if (Bouton_clicke==3) // Zone de saisie du dcalage X + { + Effacer_curseur(); + Num2str(Offset_X_choisi,Chaine,4); + Readline(93,23,Chaine,4,1); + Offset_X_choisi=atoi(Chaine); + // On corrige le dcalage en X + if (Offset_X_choisi>=Brosse_Largeur) + { + Offset_X_choisi=Brosse_Largeur-1; + Num2str(Offset_X_choisi,Chaine,4); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_Decalage_X,Chaine); + } + Afficher_curseur(); + } + else + if (Bouton_clicke==4) // Zone de saisie du dcalage Y + { + Effacer_curseur(); + Num2str(Offset_Y_choisi,Chaine,4); + Readline(93,37,Chaine,4,1); + Offset_Y_choisi=atoi(Chaine); + // On corrige le dcalage en Y + if (Offset_Y_choisi>=Brosse_Hauteur) + { + Offset_Y_choisi=Brosse_Hauteur-1; + Num2str(Offset_Y_choisi,Chaine,4); + Fenetre_Contenu_bouton_saisie(Bouton_saisie_Decalage_Y,Chaine); + } + Afficher_curseur(); + } + } + while ( (Bouton_clicke!=1) && (Bouton_clicke!=2) ); + + Fermer_fenetre(); + + if (Bouton_clicke==2) // OK + { + Tiling_Decalage_X=Offset_X_choisi; + Tiling_Decalage_Y=Offset_Y_choisi; + if (!Tiling_Mode) + Bouton_Tiling_Mode(); + } + + Afficher_curseur(); +} + + +//---------------------------- Courbes de Bzier ---------------------------- + +void Bouton_Courbes(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(Courbe_en_cours); + Afficher_curseur(); +} + + +void Bouton_Courbes_Switch_mode(void) +{ + if (Courbe_en_cours==OPERATION_COURBE_4_POINTS) + Courbe_en_cours=OPERATION_COURBE_3_POINTS; + else + Courbe_en_cours=OPERATION_COURBE_4_POINTS; + + Effacer_curseur(); + Afficher_sprite_dans_menu(BOUTON_COURBES,Courbe_en_cours-OPERATION_COURBE_3_POINTS+4); + Demarrer_pile_operation(Courbe_en_cours); + Afficher_curseur(); +} + + +//--------------------------------- Spray ----------------------------------- + +void Bouton_Spray(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(OPERATION_SPRAY); + Afficher_curseur(); +} + + +void Spray_Rafficher_infos(byte Couleur_selectionnee, byte Rafficher_jauge) +{ + char Chaine[3]; + + if (Rafficher_jauge) + { + Fenetre_Liste_boutons_scroller->Position=49-Spray_Multi_flow[Couleur_selectionnee]; + Fenetre_Dessiner_jauge(Fenetre_Liste_boutons_scroller); + } + Num2str(Spray_Multi_flow[Couleur_selectionnee],Chaine,2); + Print_dans_fenetre(196,130,Chaine,CM_Noir,CM_Clair); +} + + +void Bouton_Spray_Menu(void) +{ + static byte Spray_Init=0; + short Bouton_clicke; + char Chaine[4]; + word Indice; + byte Couleur_selectionnee=Fore_color; + byte Old_Spray_Mode =Spray_Mode; + short Old_Spray_Size =Spray_Size; + byte Old_Spray_Delay =Spray_Delay; + byte Old_Spray_Mono_flow=Spray_Mono_flow; + byte Old_Spray_Multi_flow[256]; + struct Fenetre_Bouton_special * Saisie_Size; + struct Fenetre_Bouton_special * Saisie_Delay; + struct Fenetre_Bouton_special * Saisie_Mono_flow; + struct Fenetre_Bouton_special * Saisie_Init; + word Ancien_Mouse_X; + word Ancien_Mouse_Y; + byte Ancien_Mouse_K; + byte Couleur; + byte Click; + + + memcpy(Old_Spray_Multi_flow,Spray_Multi_flow,256); + + + Ouvrir_fenetre(226,170,"Spray"); + + Fenetre_Definir_bouton_normal(110,148,51,14,"Cancel" ,0,1,0x0001); // 1 + Fenetre_Definir_bouton_normal(166,148,51,14,"OK" ,0,1,0x001C); // 2 + + Fenetre_Definir_bouton_scroller(178,62,74,50,1,49-Spray_Multi_flow[Couleur_selectionnee]); // 3 + + Fenetre_Definir_bouton_palette(7,56); // 4 + + Fenetre_Definir_bouton_normal( 8,148,83,14,"Mode: ",0,1,0x000F); // 5 + if (Spray_Mode) + Print_dans_fenetre(50,151," Mono",CM_Noir,CM_Clair); + else + Print_dans_fenetre(50,151,"Multi",CM_Noir,CM_Clair); + + Fenetre_Definir_bouton_normal(194, 62,19,14,"+1" ,0,1,0x004E); // 6 + Fenetre_Definir_bouton_normal(194, 79,19,14,"-1" ,0,1,0x004A); // 7 + Fenetre_Definir_bouton_normal(194, 96,19,14,"x2" ,0,1,0x0037); // 8 + Fenetre_Definir_bouton_normal(194,113,19,14,"2" ,0,1,0x00E0); // 9 + + Fenetre_Definir_bouton_normal( 8, 37,43,14,"Clear" ,1,1,0x002E); // 10 + + Print_dans_fenetre(142,25,"Size:" ,CM_Fonce,CM_Clair); + Fenetre_Definir_bouton_saisie(186,23,3); // 11 + Saisie_Size=Fenetre_Liste_boutons_special; + Num2str(Spray_Size,Chaine,3); + Fenetre_Contenu_bouton_saisie(Saisie_Size,Chaine); + + Print_dans_fenetre(142,39,"Delay:" ,CM_Fonce,CM_Clair); + Fenetre_Definir_bouton_saisie(194,37,2); // 12 + Saisie_Delay=Fenetre_Liste_boutons_special; + Num2str(Spray_Delay,Chaine,2); + Fenetre_Contenu_bouton_saisie(Saisie_Delay,Chaine); + + Print_dans_fenetre( 27,24,"Mono-Flow:",CM_Fonce,CM_Clair); + Fenetre_Definir_bouton_saisie(111,22,2); // 13 + Saisie_Mono_flow=Fenetre_Liste_boutons_special; + Num2str(Spray_Mono_flow,Chaine,2); + Fenetre_Contenu_bouton_saisie(Saisie_Mono_flow,Chaine); + + Print_dans_fenetre( 67,40,"Init:",CM_Fonce,CM_Clair); + Fenetre_Definir_bouton_saisie(111,38,2); // 14 + Saisie_Init=Fenetre_Liste_boutons_special; + Num2str(Spray_Init,Chaine,2); + Fenetre_Contenu_bouton_saisie(Saisie_Init,Chaine); + + Fenetre_Afficher_cadre(173,56,45,86); + Fenetre_Afficher_cadre(137,19,81,33); + + // On tagge toutes les couleurs utilises + for (Indice=0; Indice<256; Indice++) + if (Spray_Multi_flow[Indice]) + Stencil_Tagger_couleur(Indice,CM_Noir); + // Et enfin, on tagge la couleur slectionne + Stencil_Tagger_couleur(Couleur_selectionnee,CM_Blanc); + Spray_Rafficher_infos(Couleur_selectionnee,0); + + Afficher_curseur(); + + + do + { + Ancien_Mouse_X=Mouse_X; + Ancien_Mouse_Y=Mouse_Y; + Ancien_Mouse_K=Mouse_K; + + Bouton_clicke=Fenetre_Bouton_clicke(); + + switch (Bouton_clicke) + { + case 0 : + case 2 : // OK + break; + + case 1 : // Cancel + Spray_Mode =Old_Spray_Mode; + Spray_Size =Old_Spray_Size; + Spray_Delay =Old_Spray_Delay; + Spray_Mono_flow=Old_Spray_Mono_flow; + memcpy(Spray_Multi_flow,Old_Spray_Multi_flow,256); + break; + + case 3 : // Scroller + Effacer_curseur(); + Spray_Multi_flow[Couleur_selectionnee]=49-Fenetre_Attribut2; + Spray_Rafficher_infos(Couleur_selectionnee,0); + Afficher_curseur(); + break; + + case -1 : + case 4 : // Palette + if ( (Mouse_X!=Ancien_Mouse_X) || (Mouse_Y!=Ancien_Mouse_Y) || (Mouse_K!=Ancien_Mouse_K) ) + { + Effacer_curseur(); + Stencil_Tagger_couleur(Couleur_selectionnee,(Spray_Multi_flow[Couleur_selectionnee])?CM_Noir:CM_Clair); + + // Mettre la couleur slectionne jour suivant le click + Couleur_selectionnee=Lit_pixel(Mouse_X,Mouse_Y); + if (Mouse_K==2) + Spray_Multi_flow[Couleur_selectionnee]=0; + else + if (Spray_Multi_flow[Couleur_selectionnee]==0) + Spray_Multi_flow[Couleur_selectionnee]=Spray_Init; + + // Tagger la couleur slectionne en blanc + Stencil_Tagger_couleur(Couleur_selectionnee,CM_Blanc); + Spray_Rafficher_infos(Couleur_selectionnee,1); + Afficher_curseur(); + } + break; + + case 5 : // Toggle Mode + Spray_Mode=(Spray_Mode+1)&1; + Effacer_curseur(); + if (Spray_Mode) + Print_dans_fenetre(50,151," Mono",CM_Noir,CM_Clair); + else + Print_dans_fenetre(50,151,"Multi",CM_Noir,CM_Clair); + Afficher_curseur(); + break; + + case 6 : // +1 + for (Indice=0; Indice<256; Indice++) + { + if ( (Spray_Multi_flow[Indice]) && (Spray_Multi_flow[Indice]<49) ) + Spray_Multi_flow[Indice]++; + } + Effacer_curseur(); + Spray_Rafficher_infos(Couleur_selectionnee,1); + Afficher_curseur(); + break; + + case 7 : // -1 + for (Indice=0; Indice<256; Indice++) + { + if (Spray_Multi_flow[Indice]>1) + Spray_Multi_flow[Indice]--; + } + Effacer_curseur(); + Spray_Rafficher_infos(Couleur_selectionnee,1); + Afficher_curseur(); + break; + + case 8 : // x2 + for (Indice=0; Indice<256; Indice++) + { + if (Spray_Multi_flow[Indice]) + { + Spray_Multi_flow[Indice]<<=1; + if (Spray_Multi_flow[Indice]>49) + Spray_Multi_flow[Indice]=49; + } + } + Effacer_curseur(); + Spray_Rafficher_infos(Couleur_selectionnee,1); + Afficher_curseur(); + break; + + case 9 : // 2 + for (Indice=0; Indice<256; Indice++) + { + if (Spray_Multi_flow[Indice]>1) + Spray_Multi_flow[Indice]>>=1; + } + Effacer_curseur(); + Spray_Rafficher_infos(Couleur_selectionnee,1); + Afficher_curseur(); + break; + + case 10 : // Clear + memset(Spray_Multi_flow,0,256); + // On raffiche les infos de la couleur slectionne + Spray_Rafficher_infos(Couleur_selectionnee,1); + // On efface les anciens TAGs + Fenetre_Effacer_tags(); + // Tagger la couleur slectionne en blanc + Stencil_Tagger_couleur(Couleur_selectionnee,CM_Blanc); + break; + + case 11 : // Size + Effacer_curseur(); + Num2str(Spray_Size,Chaine,3); + Readline(188,25,Chaine,3,1); + Spray_Size=atoi(Chaine); + // On corrige les dimensions + if (Spray_Size>256) + { + Spray_Size=256; + Num2str(Spray_Size,Chaine,3); + Fenetre_Contenu_bouton_saisie(Saisie_Size,Chaine); + } + else if (!Spray_Size) + { + Spray_Size=1; + Num2str(Spray_Size,Chaine,3); + Fenetre_Contenu_bouton_saisie(Saisie_Size,Chaine); + } + Afficher_curseur(); + break; + + case 12 : // Delay + Effacer_curseur(); + Num2str(Spray_Delay,Chaine,2); + Readline(196,39,Chaine,2,1); + Spray_Delay=atoi(Chaine); + // On corrige le delai + if (Spray_Delay>10) + { + Spray_Delay=10; + Num2str(Spray_Delay,Chaine,2); + Fenetre_Contenu_bouton_saisie(Saisie_Delay,Chaine); + } + Afficher_curseur(); + break; + + case 13 : // Mono-Flow + Effacer_curseur(); + Num2str(Spray_Mono_flow,Chaine,2); + Readline(113,24,Chaine,2,1); + Spray_Mono_flow=atoi(Chaine); + // On corrige le flux + if (!Spray_Mono_flow) + { + Spray_Mono_flow=1; + Num2str(Spray_Mono_flow,Chaine,2); + Fenetre_Contenu_bouton_saisie(Saisie_Mono_flow,Chaine); + } + Afficher_curseur(); + break; + + case 14 : // Init + Effacer_curseur(); + Num2str(Spray_Init,Chaine,2); + Readline(113,40,Chaine,2,1); + Spray_Init=atoi(Chaine); + // On corrige la valeur + if (Spray_Init>=50) + { + Spray_Init=49; + Num2str(Spray_Init,Chaine,2); + Fenetre_Contenu_bouton_saisie(Saisie_Init,Chaine); + } + Afficher_curseur(); + break; + } + + if (!Mouse_K) + switch (Touche) + { + case 0x0029 : // Rcupration d'une couleur derrire le menu + case 0x0033 : + Recuperer_couleur_derriere_fenetre(&Couleur,&Click); + if (Click) + { + Effacer_curseur(); + Stencil_Tagger_couleur(Couleur_selectionnee,(Spray_Multi_flow[Couleur_selectionnee])?CM_Noir:CM_Clair); + + // Mettre la couleur slectionne jour suivant le click + Couleur_selectionnee=Couleur; + if (Click==2) + Spray_Multi_flow[Couleur_selectionnee]=0; + else + if (Spray_Multi_flow[Couleur_selectionnee]==0) + Spray_Multi_flow[Couleur_selectionnee]=Spray_Init; + + // Tagger la couleur slectionne en blanc + Stencil_Tagger_couleur(Couleur_selectionnee,CM_Blanc); + Spray_Rafficher_infos(Couleur_selectionnee,1); + Afficher_curseur(); + } + } + } + while ( (Bouton_clicke!=1) && (Bouton_clicke!=2) ); + + Fermer_fenetre(); + +/* + // Tant que l'on aura pas rsolu le problme du dsenclenchement du mode + // de dessin prcedent, il faudra laisser a en remarque et donc passer en + // spray mme si on a click sur Cancel (idem pour OK (un peu plus bas)). + if (Bouton_clicke==1) // Cancel + { + if (Operation_en_cours!=OPERATION_SPRAY) + Desenclencher_bouton(BOUTON_SPRAY); + } +*/ + + Afficher_curseur(); + +/* + if (Bouton_clicke==2) // OK +*/ + if (Operation_en_cours!=OPERATION_SPRAY) + Enclencher_bouton(BOUTON_SPRAY,A_GAUCHE); +} + + + +// -- Mode Trame (Sieve) ---------------------------------------------------- + +void Bouton_Trame_Mode(void) +{ + Trame_Mode=!Trame_Mode; +} + + +void Dessiner_trame_zoomee(short Orig_X, short Orig_Y) +{ + short Pos_X; + short Pos_Y; + short Taille_X; + short Taille_Y; + short Debut_X=Fenetre_Pos_X+(Menu_Facteur_X*230); + short Debut_Y=Fenetre_Pos_Y+(Menu_Facteur_Y*78); + + Taille_X=Menu_Facteur_X*5; // |_ Taille d'une case + Taille_Y=Menu_Facteur_Y*5; // | de la trame zoome + + // On efface de contenu prcdent + Block(Orig_X,Orig_Y, + Menu_Facteur_X*Fenetre_Liste_boutons_special->Largeur, + Menu_Facteur_Y*Fenetre_Liste_boutons_special->Hauteur,CM_Clair); + + for (Pos_Y=0; Pos_Y>(15-i))&1)?CM_Blanc:CM_Noir); +} + + +void Copier_trame_predefinie(byte Indice) +{ + short i,j; + + for (j=0; j<16; j++) + for (i=0; i<16; i++) + Trame[i][j]=(TRAME_PREDEFINIE[Indice][j]>>(15-i))&1; + Trame_Largeur=16; + Trame_Hauteur=16; +} + + +void Inverser_trame(void) +{ + byte Pos_X,Pos_Y; + + for (Pos_Y=0; Pos_Y plus grande + short Preview_Fin_Y; // | rapidit. + + + memcpy(Old_Trame,Trame,256); + + Ouvrir_fenetre(290,179,"Sieve"); + + Preview_Debut_X=Fenetre_Pos_X+(Menu_Facteur_X*230); + Preview_Debut_Y=Fenetre_Pos_Y+(Menu_Facteur_Y*78); + Preview_Fin_X=Preview_Debut_X+(Menu_Facteur_X*51); + Preview_Fin_Y=Preview_Debut_Y+(Menu_Facteur_Y*71); + + Fenetre_Afficher_cadre ( 7, 65,130,43); + Fenetre_Afficher_cadre ( 7,110,130,43); + Fenetre_Afficher_cadre_creux(142, 68, 82,82); + Fenetre_Afficher_cadre_creux(229, 77, 53,73); + + Print_dans_fenetre(228, 68,"Preview",CM_Fonce,CM_Clair); + Print_dans_fenetre( 27, 83,"Scroll" ,CM_Fonce,CM_Clair); + Print_dans_fenetre( 23,120,"Width:" ,CM_Fonce,CM_Clair); + Print_dans_fenetre( 15,136,"Height:",CM_Fonce,CM_Clair); + + Fenetre_Definir_bouton_special(143,69,80,80); // 1 + + Fenetre_Definir_bouton_normal(175,157,51,14,"Cancel",0,1,0x0001); // 2 + Fenetre_Definir_bouton_normal(230,157,51,14,"OK" ,0,1,0x001C); // 3 + + Fenetre_Definir_bouton_normal( 8,157,51,14,"Clear" ,1,1,0x002E); // 4 + Fenetre_Definir_bouton_normal( 63,157,51,14,"Invert",1,1,0x0017); // 5 + + Fenetre_Definir_bouton_normal( 8,46,131,14,"Get from brush" ,1,1,0x0022); // 6 + Fenetre_Definir_bouton_normal(142,46,139,14,"Transfer to brush",1,1,0x0014); // 7 + + Fenetre_Definir_bouton_normal(109,114,11,11,"\030",0,1,0x0148); // 8 + Fenetre_Definir_bouton_normal(109,138,11,11,"\031",0,1,0x0150); // 9 + Fenetre_Definir_bouton_normal( 97,126,11,11,"\033",0,1,0x014B); // 10 + Fenetre_Definir_bouton_normal(121,126,11,11,"\032",0,1,0x014D); // 11 + Fenetre_Definir_bouton_normal(109,126,11,11,"" ,0,1,0x0052); // 12 + Bouton_Octet_insere=Fenetre_Liste_boutons_normal; + Block(Fenetre_Pos_X+(Menu_Facteur_X*(Bouton_Octet_insere->Pos_X+2)), + Fenetre_Pos_Y+(Menu_Facteur_Y*(Bouton_Octet_insere->Pos_Y+2)), + Menu_Facteur_X*7, Menu_Facteur_Y*7, (Octet_insere)?CM_Blanc:CM_Noir); + + Fenetre_Definir_bouton_normal(109, 69,11,11,"\030",0,1,0x0048); // 13 + Fenetre_Definir_bouton_normal(109, 93,11,11,"\031",0,1,0x0050); // 14 + Fenetre_Definir_bouton_normal( 97, 81,11,11,"\033",0,1,0x004B); // 15 + Fenetre_Definir_bouton_normal(121, 81,11,11,"\032",0,1,0x004D); // 16 + + for (Indice=0; Indice<10; Indice++) + Fenetre_Definir_bouton_normal((Indice*23)+8,20,20,20,"",0,1,0x003B+Indice); // 17 -> 26 + Fenetre_Definir_bouton_normal(238,20,20,20,"",0,1,0x0085); // 27 + Fenetre_Definir_bouton_normal(261,20,20,20,"",0,1,0x0086); // 28 + Dessiner_trames_predefinies(); + + Orig_X=Fenetre_Pos_X+(Menu_Facteur_X*Fenetre_Liste_boutons_special->Pos_X); + Orig_Y=Fenetre_Pos_Y+(Menu_Facteur_Y*Fenetre_Liste_boutons_special->Pos_Y); + + Num2str(Trame_Largeur,Chaine,2); + Print_dans_fenetre(71,120,Chaine,CM_Noir,CM_Clair); + Num2str(Trame_Hauteur,Chaine,2); + Print_dans_fenetre(71,136,Chaine,CM_Noir,CM_Clair); + Dessiner_trame_zoomee(Orig_X,Orig_Y); + + + Afficher_curseur(); + + do + { + Bouton_clicke=Fenetre_Bouton_clicke(); + + switch (Bouton_clicke) + { + case -1 : + case 0 : + break; + + case 1 : // Zone de dessin de la trame + /* // Version qui n'accepte pas les clicks sur la grille + Pos_X=(Mouse_X-Orig_X)/Menu_Facteur_X; + Pos_Y=(Mouse_Y-Orig_Y)/Menu_Facteur_Y; + if ( (Pos_X%5<4) && (Pos_Y%5<4) ) + { + Pos_X/=5; + Pos_Y/=5; + if ( (Pos_X16)?16:Brosse_Largeur; + Trame_Hauteur=(Brosse_Hauteur>16)?16:Brosse_Hauteur; + for (Pos_Y=0; Pos_Y>1); + Brosse_Decalage_Y=(Brosse_Hauteur>>1); + break; + + case 8 : // Rduire hauteur + if (Trame_Hauteur>1) + { + Effacer_curseur(); + Trame_Hauteur--; + Num2str(Trame_Hauteur,Chaine,2); + Print_dans_fenetre(71,136,Chaine,CM_Noir,CM_Clair); + Dessiner_trame_zoomee(Orig_X,Orig_Y); + Afficher_curseur(); + } + break; + + case 9 : // Agrandir hauteur + if (Trame_Hauteur<16) + { + Effacer_curseur(); + for (Indice=0; Indice1) + { + Effacer_curseur(); + Trame_Largeur--; + Num2str(Trame_Largeur,Chaine,2); + Print_dans_fenetre(71,120,Chaine,CM_Noir,CM_Clair); + Dessiner_trame_zoomee(Orig_X,Orig_Y); + Afficher_curseur(); + } + break; + + case 11 : // Agrandir largeur + if (Trame_Largeur<16) + { + Effacer_curseur(); + for (Indice=0; IndicePos_X+2)), + Fenetre_Pos_Y+(Menu_Facteur_Y*(Bouton_Octet_insere->Pos_Y+2)), + Menu_Facteur_X*7, Menu_Facteur_Y*7, (Octet_insere)?CM_Blanc:CM_Noir); + Afficher_curseur(); + break; + + case 13 : // Scroll vers le haut + Effacer_curseur(); + for (Pos_X=0; Pos_X0; Pos_Y--) + Trame[Pos_X][Pos_Y]=Trame[Pos_X][Pos_Y-1]; + Trame[Pos_X][0]=Temp; + } + Dessiner_trame_zoomee(Orig_X,Orig_Y); + Afficher_curseur(); + break; + + case 15 : // Scroll vers la gauche + Effacer_curseur(); + for (Pos_Y=0; Pos_Y0; Pos_X--) + Trame[Pos_X][Pos_Y]=Trame[Pos_X-1][Pos_Y]; + Trame[0][Pos_Y]=Temp; + } + Dessiner_trame_zoomee(Orig_X,Orig_Y); + Afficher_curseur(); + break; + + default : // Boutons de trames prdfinies + Effacer_curseur(); + Copier_trame_predefinie(Bouton_clicke-17); + Dessiner_trame_zoomee(Orig_X,Orig_Y); + Num2str(Trame_Largeur,Chaine,2); + Print_dans_fenetre(71,120,Chaine,CM_Noir,CM_Clair); + Num2str(Trame_Hauteur,Chaine,2); + Print_dans_fenetre(71,136,Chaine,CM_Noir,CM_Clair); + Dessiner_trame_zoomee(Orig_X,Orig_Y); + Afficher_curseur(); + } + } + while ( (Bouton_clicke!=2) && (Bouton_clicke!=3) ); + + + Fermer_fenetre(); + + if (Bouton_clicke==2) // Cancel + { + Trame_Largeur=Old_Trame_Largeur; + Trame_Hauteur=Old_Trame_Hauteur; + memcpy(Trame,Old_Trame,256); + } + + if ( (Bouton_clicke==3) && (!Trame_Mode) ) // OK + Bouton_Trame_Mode(); + + Afficher_curseur(); +} + + +// -- Gestion des boutons de polygone vide et plein ------------------------- + +void Bouton_Polygone(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(OPERATION_POLYGONE); + Afficher_curseur(); +} + + +void Bouton_Polyform(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(OPERATION_POLYFORM); + Afficher_curseur(); +} + + +void Bouton_Polyfill(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(OPERATION_POLYFILL); + Afficher_curseur(); +} + + +void Bouton_Filled_polyform(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(OPERATION_FILLED_POLYFORM); + Afficher_curseur(); +} + + +// -- Boutons d'ajustement de l'image --------------------------------------- + +void Bouton_Ajuster(void) +{ + Effacer_curseur(); + Demarrer_pile_operation(OPERATION_SCROLL); + Afficher_curseur(); +} + + + +// -- Menu des effets (Shade, Stencil, etc...) ------------------------------ + +void Afficher_sprite_effet(short Numero_sprite, short Debut_X, short Debut_Y) +{ + short X,Y,Pos_X,Pos_Y; + + for (Y=0,Pos_Y=Debut_Y;Y&o;p5ODl&%N)RkJh+=1`|pSmGgxHPzv#~1#1!|4P`q@KFS*?PLyAv=s*vf zb$T$9dXN}B{0-$M$}Gx@1X7A_-T5m*WSo;40?K7=(A@KiF*Qco0Knm$IpohAr zwuZ^U01JUsAZZE$CJ1CfU<(9tpdHn@4gvyJ7@~K;KcUt18iqjJDkAza;P)%JUA=q8 zZT_vTWrS~tn)|oKl--}IlVRJqtv^F2zpAyfAm?Z;rIYtzn=PLJi_7AY-z7{glX{FW zsl$YfyLvuXjB|a&7$5wsR{S=-{I8!?iw_@*tB(a!sW|aCITm!KpC18*4~`PB>U_4Xi_=xw$uO|L9Xmw>s^+;4`ZIr5H&;T*I9JT%vl3DGHO zxK*)R3c(jO`%SySZz+I~B^O$Qh|A!Efm{gWLBI*}Ii1Nxmyg9$U{ZG^_H9ya#LGF| zX1TioGo_{UamQ{j(gh%FA2>p&JD?*U)O;AIB~%M^6o6U^-NkAJpq9D^2Hqi5MpNlM zGH%OlVc4KRtA%hdx}fyDhbuj-N?{Fdrmm>;c4q>kLSF{3f5DC6>`&9 zaGm!EXU?B%v>rTv;gaXf`yU9_pTE1^x~r&=f2}Crdf>e0H>b|M#|J;5oiOIxi&w&{ z8|!ew{Dn2?`-1j23C>YLG&3J%at^&G9S8JBhGxul8P%j4lSg3w@R}Tf`2%ZuAUtXI zP-Du{w1X}N53Y{F{EoGLJ}iB0DF`(i3hp*hD}1n1?v8ZIB6MQ6v$L&C=xoKglT4?q z*XH_6u+Z6e9E@RaN>}mlMXF`^fuRfYMqZ!$AwPIMd(;5Z*T`cFq(cIjM{&>4^yIOKwDjw36?HV{~Dq> zZo1N>Zi5;PQ9(Sz446SZ0s_qql@Z;Mx={+cAxd=XlDI1$6G+SAutlIjW4#a2EZ0CL zs2iXPLr)#p0xAp7?deLol8gNW4>gI0uz^t$DWbT$6{(zbl;WhVz5B*(9<#O!3}&dz z0FaH2vBv^Lzk5NSAK^YZYS1i7(Sotx5lH!TT>1Yh5qwaC#nY(y@-0&r>E69)jw`s3 zI0t*UE6unwZ!RY_88}B1E7&b`xtqINi7_^?3^_wSS&2>BpR^9vGTEHJ$zTk64T`q^ z4?uCf?XINDRbE%iG}KgAJ!5!pDhYb2M!ym97ID&XjG@_JpRi9gQsgKfrnyj4D!JBe zU0JwpUt>6bGrDi4yeV!3&Ot3xgNI`{?&u68afg$*{V(9|Aa0lsV$kg~T&N+HTwYoD z!oD02Hi=Agxlbar4WaclRTzKp8CH9^^|U;o=fmoEYhIS~HE#leR4;&b0J@xMLaK9< zu+FjIT|gzpu^^;$Iaxt>j1MaEq+Utd6L8A~tuty>>^Wj*9Fb5+VA(`YNOgUDi7w}2 z4VlT)p~Od7&qipLP%gyql27PoTK+IatkW6Cy;`U??x5bS#gj7js#w~9dxKH=T98bM;sGe0DVp<9`*cphUe2=VJ zu2$(jE3{p{-x^kLu1XWwvrh==8yU4-=OG@jn!#D%gVLn*ux_l&X>D4E8O(}jaFteY z;-c}oW8wbd1HEiw6fKe3W*=Flw+zxrw(T+?iqVDYQ!#G))Me)FO7+HSL$!2AT0)nL ztB4(?@l;z1?lx2Wh(Aq+lEmdq>n37)?0y*$h+e1oaUKXMZ54TV;A{MP*+}*4` z^6S!88QvVXEe?wEJKB;oEX{Z`K=QauC z!RQm|o_(?}7E4kzoOaO_Y2p?O(u{HT(z>PDrD@+R;OFEx_mzIBhxN%+d@-G6VdR-|CeA zDoA{)v6fF^2vKW-=`o7YS44$w96<+vr!=7FA8QldMOHa9H}wMK2j#XKEKJ`u!agxI j&j(i)I`J>vkCj;L$24AAH6t=#0xF literal 0 HcmV?d00001 diff --git a/cfg/ASCKEY.PAS b/cfg/ASCKEY.PAS new file mode 100644 index 00000000..c38075a7 --- /dev/null +++ b/cfg/ASCKEY.PAS @@ -0,0 +1,11 @@ +var touche:byte; +begin + repeat + asm + mov ah,8 + int 21h + mov touche,al + end; + write(touche,' '); + until touche=27 +end. \ No newline at end of file diff --git a/cfg/KEYS.EXE b/cfg/KEYS.EXE new file mode 100644 index 0000000000000000000000000000000000000000..d248ca04b4680cce5460bc9a8795c579444cdf98 GIT binary patch literal 3760 zcmd^CeNYtV8Gqj0y}e}*juVtvqsKA9ZS>S2t5o?gsNo~69~TfoD3VM}6P-pg#~vh; zc$~wukz257JMFYgnvr1h2QV!fW_m!Y2YZCCFd$}%fpo@E(=2l)HIe}n@wU(29nnmu zfAsI(@a+5U^YME=-gn>kVQ+aSaFB$Q%A}q%637K;0f5y=X-HK_$B&DcGt48BxzNbWi08m zP(-?@v82@a(*e&-GNE$U-Yq6dNyDc;pqj_11UPjIs1JS)8h9>(MpfrEU4&3lsW+cV zyZQTW3oLy7t6cf6_h%G1nm^_e0L5BTX><0s)0Z@8o-!st*rHEmPUkbhu83B^&9bFS z^5K38sCBkxz)ZsK$&!1b7Hai7FmCCYO9v=x>9NO;LG$Zu0-P--X*V}d7CG>}0bLy1 z5EVq=&lVAfxSrW@I9MEqQR z%cPzKIbcYH^UM{sagy$DJa6_vW&fC}go5I9Z`(IRr1uLyd~vx{cHaEe+-^q`{g&0@h8W(T{M6qQ7+$X-y-o z*~E98m>q2KXt)Gsb$ujnvzkJEx29{Y11qpndP#4$Y#}B#gGlRo_fYD3Xh|n(I`mdh zsufx?h?)zXnQ953mbw*spQTizuF|zJJU%qM(;!yJC>pV^=Qgtsav*Y{9xPm%&hF3 z9Z$N7T*sxOFTY@W!Rb8Vw1Mq8$p)L^cyOF>N=Hu|ueR+z@yct?qc6TB*&cs>oo(~> zZQ_RQ>9$=boIic;_z}_nCYw!0>vv=maFNlLY%=>wNd7A0%u|$*RYKJn-&ihW8JzL> z!oI=PVXgC+S~BVzhS|c9Zwh92g$zJB;-cAU1iH|0s~jmY~brrnpI^SaG2*WSG!Op~sdj?AGN#yfO_>%h9v zZP)Ln``eO7IFLUWzs1~L1eKrpq4Ej6oap)hndTj4%PKg7!V!$~11m zDx(r95hDzg#0v6WMv&KZJvo-*wCGu2FoSs94&n*_O*6S8V~$!=wfi-dtv zjIoM0($n;vMQy@$x6Q7K!jilo9=Req>!3B&bQC4!!- zqhFYEZ5QPI7(*RrAGcqwX6O-dk`)5Av2>`@wm8>j4;h7qI&@#hxMGSB@H$i&%W-oI zg&iG*C|qF_Zs$XAeF!%s`Z4G;(?XysmcF+*cg}t<9BdRa&QWv_L7NctaCsTV?_Yw| z7xysh>otgz>K7pwFVxqq0*O{%0eu5>WXDOd*{h^wS#z#AR8q3$q?nFuULyNMzv7!P zC{cR~E;>l#v|6S;fY=y@h$uv0`AAJ@H6biwiv_J}d31Lu;kT7bZ)g@#-iF~tSLpkC z{jfy5%cAycIzRd@B?=mT6qvi2VEO8rkdC3} zeaogV$q{3>4Vv878Yk6~`|>!>?Bh~=l2QF5?WAt-dR)gq^ve_Sr%WmT{rRtCFR~?f3|LdHoR7P3$Ai)jJD1?)=HMLLQVqmPekRdrvaUcjZyJ zhR+ZFQ}hR!LVG@&T#1M7Qd%6Q#dHYXwdf%8Lrm;Lepq5L`}bT_W&kS?R@HOwByAbq z0;Uc7fu(Bkm@n1@nbAzb3#+$%^=_7&Gz{jmB-+*m+&o+ABjAwp*+T3~MneI&SwEj? z4O=d33&RRp4U0VkiaSDPbrx07NUPz@>Z>7ronrOmqwwJValM-Z_rX(cPJ_Drr`)Ut zZr!E!pDsDwWm)JUPq;nkeAW^1wgbJr9`P1o#Dv}HSCchkppFrT8{&MB6S*4VIw{S7 z)Ay$&sw>-bG7Y4drjj%~Zp#}CJ`>ZE5N>)R%1_8^eDKs*%6z}a_pC0GhvaG3^02v! zR_)-+S~9@v=)zP(-tvZ$q=vmK8!A@~=B@THgLziO3m@>}q&SRl)UL6VjUK3(CvZ9byJNyOq|KOD%m{9TP4xEgLmXB_K9vyi=yao`Zc4-;}?05 zr%f}jEnApbxLQ90*v#z5&9`xkOO_d4-?;1}q)1&a!Yv(_>?aC;=eC;x}-TG6f3R_(MtU!6kMN>ubQT%c+>oA#)WB&WE#XfuM*{J1rfi|vF<&GAp~s^OsB~ce8i)$ z)x+rEFN_Z8{3tZ;n&*{*>z5w_xvN|%B35JfS=v5+c~0) + then write('(',hi(Touche),',',Byte2Hexa(lo(Touche)),') '); + until Touche=$0001; +END. diff --git a/cfg/SCANCODE.PAS b/cfg/SCANCODE.PAS new file mode 100644 index 00000000..001ecf3f --- /dev/null +++ b/cfg/SCANCODE.PAS @@ -0,0 +1,1040 @@ +const + Table_Normal:array[0..255] of pchar= + ( + {00} '???' + {01},'Esc' + {02},'1 !' + {03},'2 @' + {04},'3 #' + {05},'4 $' + {06},'5 %' + {07},'6 ^' + {08},'7 &' + {09},'8 *' + {0A},'9 (' + {0B},'0 )' + {0C},'- _' + {0D},'= +' + {0E},'BkSpc' + {0F},'Tab' + {10},'Q' + {11},'W' + {12},'E' + {13},'R' + {14},'T' + {15},'Y' + {16},'U' + {17},'I' + {18},'O' + {19},'P' + {1A},'[ {' + {1B},'] }' + {1C},'Retrn' + {1D},'???' + {1E},'A' + {1F},'S' + {20},'D' + {21},'F' + {22},'G' + {23},'H' + {24},'J' + {25},'K' + {26},'L' + {27},'; :' + {28},''' "' + {29},'` ~' + {2A},'???' + {2B},'\ |' + {2C},'Z' + {2D},'X' + {2E},'C' + {2F},'V' + {30},'B' + {31},'N' + {32},'M' + {33},', <' + {34},'. >' + {35},'/ ?' + {36},'???' + {37},'Grey*' + {38},'???' + {39},'Space' + {3A},'???' + {3B},'F1' + {3C},'F2' + {3D},'F3' + {3E},'F4' + {3F},'F5' + {40},'F6' + {41},'F7' + {42},'F8' + {43},'F9' + {44},'F10' + {45},'???' + {46},'???' + {47},'Home' + {48},'Up' + {49},'PgUp' + {4A},'Grey-' + {4B},'Left' + {4C},'Kpad5' + {4D},'Right' + {4E},'Grey+' + {4F},'End' + {50},'Down' + {51},'PgDn' + {52},'Ins' + {53},'Del' + {54},'???' + {55},'???' + {56},'Lft\|' + {57},'???' + {58},'???' + {59},'???' + {5A},'???' + {5B},'???' + {5C},'???' + {5D},'???' + {5E},'???' + {5F},'???' + {60},'???' + {61},'???' + {62},'???' + {63},'???' + {64},'???' + {65},'???' + {66},'???' + {67},'???' + {68},'???' + {69},'???' + {6A},'???' + {6B},'???' + {6C},'???' + {6D},'???' + {6E},'???' + {6F},'???' + {70},'???' + {71},'???' + {72},'???' + {73},'???' + {74},'???' + {75},'???' + {76},'???' + {77},'???' + {78},'???' + {79},'???' + {7A},'???' + {7B},'???' + {7C},'???' + {7D},'???' + {7E},'???' + {7F},'???' + {80},'???' + {81},'???' + {82},'???' + {83},'???' + {84},'???' + {85},'F11' + {86},'F12' + {87},'???' + {88},'???' + {89},'???' + {8A},'???' + {8B},'???' + {8C},'???' + {8D},'???' + {8E},'???' + {8F},'???' + {90},'???' + {91},'???' + {92},'???' + {93},'???' + {94},'???' + {95},'???' + {96},'???' + {97},'???' + {98},'???' + {99},'???' + {9A},'???' + {9B},'???' + {9C},'???' + {9D},'???' + {9E},'???' + {9F},'???' + {A0},'???' + {A1},'???' + {A2},'???' + {A3},'???' + {A4},'???' + {A5},'???' + {A6},'???' + {A7},'???' + {A8},'???' + {A9},'???' + {AA},'???' + {AB},'???' + {AC},'???' + {AD},'???' + {AE},'???' + {AF},'???' + {B0},'???' + {B1},'???' + {B2},'???' + {B3},'???' + {B4},'???' + {B5},'???' + {B6},'Win L' + {B7},'Win R' + {B8},'Win M' + {B9},'???' + {BA},'???' + {BB},'???' + {BC},'???' + {BD},'???' + {BE},'???' + {BF},'???' + {C0},'???' + {C1},'???' + {C2},'???' + {C3},'???' + {C4},'???' + {C5},'???' + {C6},'???' + {C7},'???' + {C8},'???' + {C9},'???' + {CA},'???' + {CB},'???' + {CC},'???' + {CD},'???' + {CE},'???' + {CF},'???' + {D0},'???' + {D1},'???' + {D2},'???' + {D3},'???' + {D4},'???' + {D5},'???' + {D6},'???' + {D7},'???' + {D8},'???' + {D9},'???' + {DA},'???' + {DB},'???' + {DC},'???' + {DD},'???' + {DE},'???' + {DF},'???' + {E0},'Enter' + {E1},'???' + {E2},'???' + {E3},'???' + {E4},'???' + {E5},'???' + {E6},'???' + {E7},'???' + {E8},'???' + {E9},'???' + {EA},'???' + {EB},'???' + {EC},'???' + {ED},'???' + {EE},'???' + {EF},'???' + {F0},'???' + {F1},'???' + {F2},'???' + {F3},'???' + {F4},'???' + {F5},'???' + {F6},'???' + {F7},'???' + {F8},'???' + {F9},'???' + {FA},'???' + {FB},'???' + {FC},'???' + {FD},'???' + {FE},'???' + {FF},'' + ); + + Table_Shift:array[0..255] of pchar= + ( + {00} '???' + {01},'Esc' + {02},'1 !' + {03},'2 @' + {04},'3 #' + {05},'4 $' + {06},'5 %' + {07},'6 ^' + {08},'7 &' + {09},'8 *' + {0A},'9 (' + {0B},'0 )' + {0C},'- _' + {0D},'= +' + {0E},'BkSpc' + {0F},'Tab' + {10},'Q' + {11},'W' + {12},'E' + {13},'R' + {14},'T' + {15},'Y' + {16},'U' + {17},'I' + {18},'O' + {19},'P' + {1A},'[ {' + {1B},'] }' + {1C},'Retrn' + {1D},'???' + {1E},'A' + {1F},'S' + {20},'D' + {21},'F' + {22},'G' + {23},'H' + {24},'J' + {25},'K' + {26},'L' + {27},'; :' + {28},''' "' + {29},'` ~' + {2A},'???' + {2B},'\ |' + {2C},'Z' + {2D},'X' + {2E},'C' + {2F},'V' + {30},'B' + {31},'N' + {32},'M' + {33},', <' + {34},'. >' + {35},'/ ?' + {36},'???' + {37},'Grey*' + {38},'???' + {39},'Space' + {3A},'???' + {3B},'???' + {3C},'???' + {3D},'???' + {3E},'???' + {3F},'???' + {40},'???' + {41},'???' + {42},'???' + {43},'???' + {44},'???' + {45},'???' + {46},'???' + {47},'Home' + {48},'Up' + {49},'PgUp' + {4A},'Grey-' + {4B},'Left' + {4C},'Kpad5' + {4D},'Right' + {4E},'Grey+' + {4F},'End' + {50},'Down' + {51},'PgDn' + {52},'Ins' + {53},'Del' + {54},'F1' + {55},'F2' + {56},'F3' + {57},'F4' + {58},'F5' + {59},'F6' + {5A},'F7' + {5B},'F8' + {5C},'F9' + {5D},'F10' + {5E},'???' + {5F},'???' + {60},'???' + {61},'???' + {62},'???' + {63},'???' + {64},'???' + {65},'???' + {66},'???' + {67},'???' + {68},'???' + {69},'???' + {6A},'???' + {6B},'???' + {6C},'???' + {6D},'???' + {6E},'???' + {6F},'???' + {70},'???' + {71},'???' + {72},'???' + {73},'???' + {74},'???' + {75},'???' + {76},'???' + {77},'???' + {78},'???' + {79},'???' + {7A},'???' + {7B},'???' + {7C},'???' + {7D},'???' + {7E},'???' + {7F},'???' + {80},'???' + {81},'???' + {82},'???' + {83},'???' + {84},'???' + {85},'???' + {86},'???' + {87},'F11' + {88},'F12' + {89},'???' + {8A},'???' + {8B},'???' + {8C},'???' + {8D},'???' + {8E},'???' + {8F},'???' + {90},'???' + {91},'???' + {92},'???' + {93},'???' + {94},'???' + {95},'???' + {96},'???' + {97},'???' + {98},'???' + {99},'???' + {9A},'???' + {9B},'???' + {9C},'???' + {9D},'???' + {9E},'???' + {9F},'???' + {A0},'???' + {A1},'???' + {A2},'???' + {A3},'???' + {A4},'???' + {A5},'???' + {A6},'???' + {A7},'???' + {A8},'???' + {A9},'???' + {AA},'???' + {AB},'???' + {AC},'???' + {AD},'???' + {AE},'???' + {AF},'???' + {B0},'???' + {B1},'???' + {B2},'???' + {B3},'???' + {B4},'???' + {B5},'???' + {B6},'???' + {B7},'???' + {B8},'???' + {B9},'???' + {BA},'???' + {BB},'???' + {BC},'???' + {BD},'???' + {BE},'???' + {BF},'???' + {C0},'???' + {C1},'???' + {C2},'Win L' + {C3},'Win R' + {C4},'Win M' + {C5},'???' + {C6},'???' + {C7},'???' + {C8},'???' + {C9},'???' + {CA},'???' + {CB},'???' + {CC},'???' + {CD},'???' + {CE},'???' + {CF},'???' + {D0},'???' + {D1},'???' + {D2},'???' + {D3},'???' + {D4},'???' + {D5},'???' + {D6},'???' + {D7},'???' + {D8},'???' + {D9},'???' + {DA},'???' + {DB},'???' + {DC},'???' + {DD},'???' + {DE},'???' + {DF},'???' + {E0},'Enter' + {E1},'???' + {E2},'???' + {E3},'???' + {E4},'???' + {E5},'???' + {E6},'???' + {E7},'???' + {E8},'???' + {E9},'???' + {EA},'???' + {EB},'???' + {EC},'???' + {ED},'???' + {EE},'???' + {EF},'???' + {F0},'???' + {F1},'???' + {F2},'???' + {F3},'???' + {F4},'???' + {F5},'???' + {F6},'???' + {F7},'???' + {F8},'???' + {F9},'???' + {FA},'???' + {FB},'???' + {FC},'???' + {FD},'???' + {FE},'???' + {FF},'???' + ); + + Table_Ctrl:array[0..255] of pchar= + ( + {00} '???' + {01},'Esc' + {02},'???' + {03},'2 @' + {04},'???' + {05},'???' + {06},'???' + {07},'6 ^' + {08},'???' + {09},'8 *' + {0A},'???' + {0B},'???' + {0C},'- _' + {0D},'= +' + {0E},'BkSpc' + {0F},'???' + {10},'Q' + {11},'W' + {12},'E' + {13},'R' + {14},'T' + {15},'Y' + {16},'U' + {17},'I' + {18},'O' + {19},'P' + {1A},'[ {' + {1B},'] }' + {1C},'Retrn' + {1D},'???' + {1E},'A' + {1F},'S' + {20},'D' + {21},'F' + {22},'G' + {23},'H' + {24},'J' + {25},'K' + {26},'L' + {27},'; :' + {28},'???' + {29},'???' + {2A},'???' + {2B},'\ |' + {2C},'Z' + {2D},'X' + {2E},'C' + {2F},'V' + {30},'B' + {31},'N' + {32},'M' + {33},'???' + {34},'???' + {35},'???' + {36},'???' + {37},'???' + {38},'???' + {39},'Space' + {3A},'???' + {3B},'???' + {3C},'???' + {3D},'???' + {3E},'???' + {3F},'???' + {40},'???' + {41},'???' + {42},'???' + {43},'???' + {44},'???' + {45},'???' + {46},'???' + {47},'???' + {48},'???' + {49},'???' + {4A},'???' + {4B},'???' + {4C},'???' + {4D},'???' + {4E},'???' + {4F},'???' + {50},'???' + {51},'???' + {52},'???' + {53},'???' + {54},'???' + {55},'???' + {56},'???' + {57},'???' + {58},'???' + {59},'???' + {5A},'???' + {5B},'???' + {5C},'???' + {5D},'???' + {5E},'F1' + {5F},'F2' + {60},'F3' + {61},'F4' + {62},'F5' + {63},'F6' + {64},'F7' + {65},'F8' + {66},'F9' + {67},'F10' + {68},'???' + {69},'???' + {6A},'???' + {6B},'???' + {6C},'???' + {6D},'???' + {6E},'???' + {6F},'???' + {70},'???' + {71},'???' + {72},'???' + {73},'Left' + {74},'Right' + {75},'End' + {76},'PgDn' + {77},'Home' + {78},'???' + {79},'???' + {7A},'???' + {7B},'???' + {7C},'???' + {7D},'???' + {7E},'???' + {7F},'???' + {80},'???' + {81},'???' + {82},'???' + {83},'???' + {84},'PgUp' + {85},'???' + {86},'???' + {87},'???' + {88},'???' + {89},'F11' + {8A},'F12' + {8B},'???' + {8C},'???' + {8D},'Up' + {8E},'Grey-' + {8F},'Keyp5' + {90},'Grey+' + {91},'Down' + {92},'Ins' + {93},'Del' + {94},'Tab' + {95},'Grey/' + {96},'Grey*' + {97},'???' + {98},'???' + {99},'???' + {9A},'???' + {9B},'???' + {9C},'???' + {9D},'???' + {9E},'???' + {9F},'???' + {A0},'???' + {A1},'???' + {A2},'???' + {A3},'???' + {A4},'???' + {A5},'???' + {A6},'???' + {A7},'???' + {A8},'???' + {A9},'???' + {AA},'???' + {AB},'???' + {AC},'???' + {AD},'???' + {AE},'???' + {AF},'???' + {B0},'???' + {B1},'???' + {B2},'???' + {B3},'???' + {B4},'???' + {B5},'???' + {B6},'???' + {B7},'???' + {B8},'???' + {B9},'???' + {BA},'???' + {BB},'???' + {BC},'???' + {BD},'???' + {BE},'???' + {BF},'???' + {C0},'???' + {C1},'???' + {C2},'???' + {C3},'???' + {C4},'???' + {C5},'???' + {C6},'???' + {C7},'???' + {C8},'???' + {C9},'???' + {CA},'???' + {CB},'???' + {CC},'???' + {CD},'???' + {CE},'Win L' + {CF},'Win R' + {D0},'Win M' + {D1},'???' + {D2},'???' + {D3},'???' + {D4},'???' + {D5},'???' + {D6},'???' + {D7},'???' + {D8},'???' + {D9},'???' + {DA},'???' + {DB},'???' + {DC},'???' + {DD},'???' + {DE},'???' + {DF},'???' + {E0},'Enter' + {E1},'???' + {E2},'???' + {E3},'???' + {E4},'???' + {E5},'???' + {E6},'???' + {E7},'???' + {E8},'???' + {E9},'???' + {EA},'???' + {EB},'???' + {EC},'???' + {ED},'???' + {EE},'???' + {EF},'???' + {F0},'???' + {F1},'???' + {F2},'???' + {F3},'???' + {F4},'???' + {F5},'???' + {F6},'???' + {F7},'???' + {F8},'???' + {F9},'???' + {FA},'???' + {FB},'???' + {FC},'???' + {FD},'???' + {FE},'???' + {FF},'???' + ); + + Table_Alt:array[0..255] of pchar= + ( + {00} '???' + {01},'Esc' + {02},'???' + {03},'???' + {04},'???' + {05},'???' + {06},'???' + {07},'???' + {08},'???' + {09},'???' + {0A},'???' + {0B},'???' + {0C},'???' + {0D},'???' + {0E},'BkSpc' + {0F},'???' + {10},'Q' + {11},'W' + {12},'E' + {13},'R' + {14},'T' + {15},'Y' + {16},'U' + {17},'I' + {18},'O' + {19},'P' + {1A},'[ {' + {1B},'] }' + {1C},'Retrn' + {1D},'???' + {1E},'A' + {1F},'S' + {20},'D' + {21},'F' + {22},'G' + {23},'H' + {24},'J' + {25},'K' + {26},'L' + {27},'; :' + {28},''' "' + {29},'` ~' + {2A},'???' + {2B},'\ |' + {2C},'Z' + {2D},'X' + {2E},'C' + {2F},'V' + {30},'B' + {31},'N' + {32},'M' + {33},', <' + {34},'. >' + {35},'/ ?' + {36},'???' + {37},'Grey*' + {38},'???' + {39},'Space' + {3A},'???' + {3B},'???' + {3C},'???' + {3D},'???' + {3E},'???' + {3F},'???' + {40},'???' + {41},'???' + {42},'???' + {43},'???' + {44},'???' + {45},'???' + {46},'???' + {47},'???' + {48},'???' + {49},'???' + {4A},'Grey-' + {4B},'???' + {4C},'???' + {4D},'???' + {4E},'Grey+' + {4F},'???' + {50},'???' + {51},'???' + {52},'???' + {53},'???' + {54},'???' + {55},'???' + {56},'???' + {57},'???' + {58},'???' + {59},'???' + {5A},'???' + {5B},'???' + {5C},'???' + {5D},'???' + {5E},'???' + {5F},'???' + {60},'???' + {61},'???' + {62},'???' + {63},'???' + {64},'???' + {65},'???' + {66},'???' + {67},'???' + {68},'F1' + {69},'F2' + {6A},'F3' + {6B},'F4' + {6C},'F5' + {6D},'F6' + {6E},'F7' + {6F},'F8' + {70},'F9' + {71},'F10' + {72},'???' + {73},'???' + {74},'???' + {75},'???' + {76},'???' + {77},'???' + {78},'1 !' + {79},'2 @' + {7A},'3 #' + {7B},'4 $' + {7C},'5 %' + {7D},'6 ^' + {7E},'7 &' + {7F},'8 *' + {80},'9 (' + {81},'0 )' + {82},'- _' + {83},'= +' + {84},'???' + {85},'???' + {86},'???' + {87},'???' + {88},'???' + {89},'???' + {8A},'???' + {8B},'F11' + {8C},'F12' + {8D},'???' + {8E},'???' + {8F},'???' + {90},'???' + {91},'???' + {92},'???' + {93},'???' + {94},'???' + {95},'???' + {96},'???' + {97},'Home' + {98},'Up' + {99},'PgUp' + {9A},'???' + {9B},'Left' + {9C},'???' + {9D},'Right' + {9E},'???' + {9F},'End' + {A0},'Down' + {A1},'PgDn' + {A2},'Ins' + {A3},'Del' + {A4},'Grey/' + {A5},'Tab' + {A6},'Enter' + {A7},'???' + {A8},'???' + {A9},'???' + {AA},'???' + {AB},'???' + {AC},'???' + {AD},'???' + {AE},'???' + {AF},'???' + {B0},'???' + {B1},'???' + {B2},'???' + {B3},'???' + {B4},'???' + {B5},'???' + {B6},'???' + {B7},'???' + {B8},'???' + {B9},'???' + {BA},'???' + {BB},'???' + {BC},'???' + {BD},'???' + {BE},'???' + {BF},'???' + {C0},'???' + {C1},'???' + {C2},'???' + {C3},'???' + {C4},'???' + {C5},'???' + {C6},'???' + {C7},'???' + {C8},'???' + {C9},'???' + {CA},'???' + {CB},'???' + {CC},'???' + {CD},'???' + {CE},'???' + {CF},'???' + {D0},'???' + {D1},'???' + {D2},'???' + {D3},'???' + {D4},'???' + {D5},'???' + {D6},'???' + {D7},'???' + {D8},'???' + {D9},'???' + {DA},'Win L' + {DB},'Win R' + {DC},'Win M' + {DD},'???' + {DE},'???' + {DF},'???' + {E0},'???' + {E1},'???' + {E2},'???' + {E3},'???' + {E4},'???' + {E5},'???' + {E6},'???' + {E7},'???' + {E8},'???' + {E9},'???' + {EA},'???' + {EB},'???' + {EC},'???' + {ED},'???' + {EE},'???' + {EF},'???' + {F0},'???' + {F1},'???' + {F2},'???' + {F3},'???' + {F4},'???' + {F5},'???' + {F6},'???' + {F7},'???' + {F8},'???' + {F9},'???' + {FA},'???' + {FB},'???' + {FC},'???' + {FD},'???' + {FE},'???' + {FF},'???' + ); diff --git a/cfg/VIDEOMOD.PAS b/cfg/VIDEOMOD.PAS new file mode 100644 index 00000000..ab9ca4ee --- /dev/null +++ b/cfg/VIDEOMOD.PAS @@ -0,0 +1,72 @@ +const + MODE_MCGA =$00; + MODE_X =$40; + MODE_VESA =$80; + MODE_XVESA=$C0; + + Table_modes_video:array[1..NB_MODES_VIDEO,1..3] of word= + ( + (MODE_MCGA ,320,200), + (MODE_X+1 ,320,224), + (MODE_X+1 ,320,240), + (MODE_X+1 ,320,256), + (MODE_X+1 ,320,270), + (MODE_X+1 ,320,282), + (MODE_X+1 ,320,300), + (MODE_X+1 ,320,360), + (MODE_X+1 ,320,400), + (MODE_X+1 ,320,448), + (MODE_X+1 ,320,480), + (MODE_X+1 ,320,512), + (MODE_X+1 ,320,540), + (MODE_X+1 ,320,564), + (MODE_X+1 ,320,600), + + (MODE_X+1 ,360,200), + (MODE_X+1 ,360,224), + (MODE_X+1 ,360,240), + (MODE_X+1 ,360,256), + (MODE_X+1 ,360,270), + (MODE_X+1 ,360,282), + (MODE_X+1 ,360,300), + (MODE_X+1 ,360,360), + (MODE_X+1 ,360,400), + (MODE_X+1 ,360,448), + (MODE_X+1 ,360,480), + (MODE_X+1 ,360,512), + (MODE_X+1 ,360,540), + (MODE_X+1 ,360,564), + (MODE_X+1 ,360,600), + + (MODE_X+1 ,400,200), + (MODE_X+1 ,400,224), + (MODE_X+1 ,400,240), + (MODE_X+1 ,400,256), + (MODE_X+1 ,400,270), + (MODE_X+1 ,400,282), + (MODE_X+1 ,400,300), + (MODE_X+1 ,400,360), + (MODE_X+1 ,400,400), + (MODE_X+1 ,400,448), + (MODE_X+1 ,400,480), + (MODE_X+1 ,400,512), + (MODE_X+1 ,400,540), + (MODE_X+1 ,400,564), + (MODE_X+1 ,400,600), + + (MODE_XVESA+1 ,640,224), + (MODE_XVESA+1 ,640,240), + (MODE_XVESA+1 ,640,256), + (MODE_XVESA+1 ,640,270), + (MODE_XVESA+1 ,640,300), + (MODE_XVESA+1 ,640,350), + (MODE_VESA+1 ,640,400), + (MODE_XVESA+1 ,640,448), + (MODE_VESA+1 ,640,480), + (MODE_XVESA+1 ,640,512), + (MODE_XVESA+1 ,640,540), + (MODE_XVESA+1 ,640,564), + (MODE_XVESA+1 ,640,600), + (MODE_VESA+1 ,800,600), + (MODE_VESA+1 ,1024,768) + ); diff --git a/cfg/gfxcfg.pas b/cfg/gfxcfg.pas new file mode 100644 index 00000000..37f61de6 --- /dev/null +++ b/cfg/gfxcfg.pas @@ -0,0 +1,1772 @@ +program GrafX2_Setup; + +{============================================================================} +const + TAILLE_FICHIER_CONFIG=10351; + TAILLE_INI =16203; + NB_MAX_OPTIONS =134; + NB_MODES_VIDEO =60; + + VERSION1 =2; + VERSION2 =0; + BETA1 =96; + BETA2 =5; + + COULEUR_TITRE =$5D; + COULEUR_SETUP =$1B; + COULEUR_SELECT =$3F; + COULEUR_EXPLIC =$2A; + COULEUR_MESSAGE =$3F; + HAUTEUR_DEBUT_SETUP =10; + HAUTEUR_FIN_SETUP =44; + TAILLE_SETUP =(HAUTEUR_FIN_SETUP-HAUTEUR_DEBUT_SETUP)*40; + +{$I SCANCODE.PAS} +{$I VIDEOMOD.PAS} + +type + Options=record + Numero : word; + Touche : word; + Touche2: word; + Libelle: string[35]; + Explic1: string[76]; + Explic2: string[76]; + Erreur : boolean; + Suppr : boolean; + end; + +var + Config:array [1..NB_MAX_OPTIONS] of Options; + NB_OPTIONS:word; + Numero_definition_option:word; + Choix_enreg:byte; + + + +{============================================================================} + +{------------------------ Passer en mode texte 80x50 ------------------------} +procedure Text_mode_80x50; assembler; +asm + mov ax,3 + int 10h + mov ax,1112h + xor bl,bl + mov dl,50 + int 10h +end; + +{------------------------ Passer en mode texte 80x25 ------------------------} +procedure Text_mode_80x25; assembler; +asm + mov ax,3 + int 10h +end; + +{---------------------------- Gestion du curseur ----------------------------} +procedure Montrer_Curseur; assembler; +asm + mov ax,0103h + mov cx,0E0Fh + int 10h +end; + +procedure Cacher_Curseur; assembler; +asm + mov ax,0103h + mov cx,0F0Eh + int 10h +end; + +procedure Goto_XY(X,Y:byte); assembler; +asm + mov ah,2 + xor bh,bh + mov dl,X + mov dh,Y + int 10h +end; + +{------- Ecrire une chaine d'une certaine couleur un certain endroit ------} +procedure Print(X,Y:word; Chaine:string; Attrib:byte); assembler; +asm + mov ax,0B800h + mov es,ax + mov ax,Y + mov bl,80 + mul bl + mov bx,X + add ax,bx + shl ax,1 + mov di,ax + + push ds + mov si,word ptr [Chaine] + mov ds,word ptr [Chaine+2] + + mov cl,[ds:si] + inc si + mov al,Attrib + @Ecrire_loop: + movsb + stosb + dec cl + jnz @Ecrire_loop + pop ds +end; + +{-------------- Dessiner un cadre plein d'une certaine couleur --------------} +procedure Cadre(X1,Y1,X2,Y2,Couleur:byte); +var + Tampon:string; + i,j:byte; +begin + Tampon[0]:=chr(X2-X1+1); + for j:=Y1 to Y2 do + begin + if j=Y1 then + begin + Tampon[1]:=''; + Tampon[X2-X1+1]:=''; + for i:=X1+1 to X2-1 do Tampon[i-X1+1]:=''; + end + else + if j=Y2 then + begin + Tampon[1]:=''; + Tampon[X2-X1+1]:=''; + for i:=X1+1 to X2-1 do Tampon[i-X1+1]:=''; + end + else + begin + Tampon[1]:=''; + Tampon[X2-X1+1]:=''; + for i:=X1+1 to X2-1 do Tampon[i-X1+1]:=' '; + end; + + Print(X1,j,Tampon,Couleur); + end; +end; + +{---------------------- Change la couleur d'une ligne -----------------------} +procedure Set_color_of_line(Num_ligne:word; X1,X2,Couleur:byte); assembler; +asm + mov ax,0B800h + mov es,ax + mov ax,Num_ligne + mov bx,80 + mul bl + mov bl,X1 + add ax,bx + add ax,ax + mov di,ax + + mov cl,X2 + sub cl,X1 + inc cl + mov al,Couleur + @Set_col_loop: + inc di + stosb + dec cl + jnz @Set_col_loop +end; + +{--------------------------- Lecture d'une touche ---------------------------} +function Lire_touche:word; assembler; +var + Touche:word; +asm + mov Touche,0 + + mov ah,11h + int 16h + + jz @Get_input_Pas_de_touche + + mov ah,10h + int 16h + + mov byte ptr[Touche],ah + + mov ah,02h + int 16h + + and al,00001111b + + mov ah,al + and ah,00000001b + shr al,1 + or al,ah + + mov byte ptr[Touche+1],al + + @Get_input_Pas_de_touche: + mov ax,Touche +end; + +{--------------- Dessiner une jolie fentre au premier plan -----------------} +function Fenetre_choix(Largeur,Hauteur:byte; Titre,Choix:string; Choix_debut,Couleur,Couleur_choix:byte):byte; +var + Temp:string; + i,Num_titre,Num_choix:byte; + X1,X2,Y1,Y2:byte; + Option_choisie:byte; + Touche:word; + Memoire_video:array[0..7999] of byte; +begin + move(mem[$B800:0000],Memoire_video,8000); + + X1:=40-(Largeur shr 1); + Y1:=25-(Hauteur shr 1); + X2:=X1+Largeur-1; + Y2:=Y1+Hauteur-1; + + Cadre(X1,Y1,X2,Y2,Couleur); + if Y2<49 then Set_color_of_line(Y2+1,X1+1,X2+1,$08); + if X2<79 then for i:=Y1+1 to Y2 do Set_color_of_line(i,X2+1,X2+1,$08); + + + Num_titre:=1; + Temp:=''; + for i:=1 to length(Titre) do + begin + if Titre[i]<>'^' + then Temp:=Temp+Titre[i] + else + begin + Print(X1+(X2-X1+1-length(Temp)) shr 1,Y1+1+Num_titre,Temp,Couleur); + Temp:=''; + inc(Num_titre); + end; + end; + + Num_choix:=1; + Temp:=''; + for i:=1 to length(Choix) do + begin + if Choix[i]<>'^' + then Temp:=Temp+Choix[i] + else + begin + Print(X1+(X2-X1+1-length(Temp)) shr 1,Y1+2+Num_choix+Num_titre,Temp,Couleur); + Temp:=''; + inc(Num_choix); + end; + end; + dec(Num_choix); + + Option_choisie:=Choix_debut; + Set_color_of_line(Y1+2+Num_titre+Option_choisie,X1+2,X2-2,Couleur_choix); + Repeat + Touche:=Lire_touche; + case Touche of + $0048 : begin + Set_color_of_line(Y1+2+Num_titre+Option_choisie,X1+2,X2-2,Couleur); + if Option_choisie=1 + then Option_choisie:=Num_choix + else dec(Option_choisie); + Set_color_of_line(Y1+2+Num_titre+Option_choisie,X1+2,X2-2,Couleur_choix); + end; + $0050 : begin + Set_color_of_line(Y1+2+Num_titre+Option_choisie,X1+2,X2-2,Couleur); + if Option_choisie=Num_choix + then Option_choisie:=1 + else inc(Option_choisie); + Set_color_of_line(Y1+2+Num_titre+Option_choisie,X1+2,X2-2,Couleur_choix); + end; + end; + until Touche=$001C; + + move(Memoire_video,mem[$B800:0000],8000); + + Fenetre_choix:=Option_choisie; +end; + +{------------------------ Passer en mode texte 80x25 ------------------------} +procedure Dessiner_ecran_principal; +var + i:byte; +begin + Cadre( 0, 0,79, 6,COULEUR_TITRE); + Print( 2, 1,'Setup program for GRAFX 2.00 (c)1996-98 Sunset Design (G.DORME & K.MARITAUD)',COULEUR_TITRE); + Print( 0, 2,'',COULEUR_TITRE); + Print(79, 2,'',COULEUR_TITRE); + for i:=1 to 78 do + Print(i,2,'',COULEUR_TITRE); + Print( 2, 3,'Use Up/Down arrows & Page-Up/Page-Down to scroll, Enter to modify, Delete to',COULEUR_TITRE); + Print( 2, 4,'remove a hot-key, and Escape to validate or cancel. (Warning: QWERTY keys!)',COULEUR_TITRE); + Print( 2, 5,'DO NOT USE Print-screen, Pause, and all other special keys!',COULEUR_TITRE); + Cadre( 0, 7,79, 9,COULEUR_SETUP); + Print( 2, 8,'Option',COULEUR_SETUP); + Print(38, 8,' Hot-key',COULEUR_SETUP); + Print(75, 8,'Err',COULEUR_SETUP); + Cadre( 0, 9,79,45,COULEUR_SETUP); + Print( 0, 9,'',COULEUR_SETUP); + Print(79, 9,'',COULEUR_SETUP); + Print(38, 7,'',COULEUR_SETUP); + Print(75, 7,'',COULEUR_SETUP); + Print(38, 9,'',COULEUR_SETUP); + Print(75, 9,'',COULEUR_SETUP); + Print(38,45,'',COULEUR_SETUP); + Print(75,45,'',COULEUR_SETUP); + Cadre( 0,46,79,49,COULEUR_EXPLIC); +end; + +{------------------------- Dfinition d'une option --------------------------} +procedure Definir_option(Numero:word;Libelle,Explic1,Explic2:string; Supprimable:boolean; Touche_par_defaut:word); +begin + Config[Numero_definition_option].Numero :=Numero; + Config[Numero_definition_option].Touche :=Touche_par_defaut; + Config[Numero_definition_option].Touche2:=$00FF; + Config[Numero_definition_option].Libelle:=Libelle; + Config[Numero_definition_option].Explic1:=Explic1; + Config[Numero_definition_option].Explic2:=Explic2; + Config[Numero_definition_option].Erreur :=false; + Config[Numero_definition_option].Suppr :=Supprimable; + inc(Numero_definition_option); +end; + +{--------------- Transformer une chane AZT en String Pascal ----------------} +function Pchar2string(Chaine:pchar):string; +var + Temp:string; + i:byte; +begin + Temp:=''; + i:=0; + while Chaine[i]>#0 do + begin + Temp:=Temp+Chaine[i]; + inc(i); + end; + Pchar2string:=Temp; +end; + +{------------- Renvoyer une chane donnant une touche "en clair" ------------} +function Nom_touche(Touche:word):string; +var + Temp,Temp2:string; + Num_table:byte; +begin + Num_table:=1; + Temp:=''; + if (hi(Touche) and 1)>0 then + begin + Temp:=Temp+' + '; + Num_table:=2; + end; + if (hi(Touche) and 2)>0 then + begin + Temp:=Temp+' + '; + Num_table:=3; + end; + if (hi(Touche) and 4)>0 then + begin + Temp:=Temp+' + '; + Num_table:=4; + end; + case Num_table of + 1: begin + Temp2:=Pchar2string(Table_Normal[lo(Touche)]); + if Temp2='???' + then Temp:='********** Invalid key! **********' + else if Temp2='' + then Temp:='' + else Temp:=Temp+'<'+Temp2+'>'; + end; + 2: begin + Temp2:=Pchar2string(Table_Shift[lo(Touche)]); + if Temp2='???' + then Temp:='**** Invalid key combination! ****' + else if Temp2='' + then Temp:='' + else Temp:=Temp+'<'+Temp2+'>'; + end; + 3: begin + Temp2:=Pchar2string(Table_Ctrl[lo(Touche)]); + if Temp2='???' + then Temp:='**** Invalid key combination! ****' + else if Temp2='' + then Temp:='' + else Temp:=Temp+'<'+Temp2+'>'; + end; + 4: begin + Temp2:=Pchar2string(Table_Alt[lo(Touche)]); + if Temp2='???' + then Temp:='**** Invalid key combination! ****' + else if Temp2='' + then Temp:='' + else Temp:=Temp+'<'+Temp2+'>'; + end; + end; + Nom_touche:=Temp; +end; + +{------------------- Complte une chaine avec un caractre ------------------} +function Completer_chaine(Chaine:string; Taille:byte; Caractere:char):string; +var + i:byte; +begin + for i:=length(Chaine)+1 to Taille do + Chaine[i]:=Caractere; + Chaine[0]:=chr(Taille); + Completer_chaine:=Chaine; +end; + +{------------------- Ecrire les informations sur une option -----------------} +procedure Ecrire(Ligne:byte; Num_option:word; Couleur:byte); +begin + Print( 2,Ligne,Completer_chaine(Config[Num_option].Libelle,35,' '),Couleur); + Print(40,Ligne,Completer_chaine(Nom_touche(Config[Num_option].Touche),34,' '),Couleur); + if Config[Num_option].Erreur + then Print(77,Ligne,'X',Couleur) + else Print(77,Ligne,' ',Couleur); +end; + +{-------------------- Ecrire un commentaire sur une option ------------------} +procedure Ecrire_commentaire(Num_option:word); +begin + Print(2,47,Completer_chaine(Config[Num_option].Explic1,76,' '),COULEUR_EXPLIC); + Print(2,48,Completer_chaine(Config[Num_option].Explic2,76,' '),COULEUR_EXPLIC); +end; + +{----------------- Ecrire toutes les premieres lignes visibles --------------} +procedure Tout_ecrire(Decalage_curseur, Position_curseur:word); +var + i:byte; +begin + i:=HAUTEUR_DEBUT_SETUP; + while (i<=HAUTEUR_FIN_SETUP) and (i0 then + begin + if Position_curseur>1 then + begin + Set_color_of_line(Position_Curseur+HAUTEUR_DEBUT_SETUP-1,1,78,COULEUR_SETUP); + dec(Position_curseur); + Set_color_of_line(Position_Curseur+HAUTEUR_DEBUT_SETUP-1,1,78,COULEUR_SELECT); + end + else + begin + if Decalage_curseur>0 then + begin + Set_color_of_line(Position_Curseur+HAUTEUR_DEBUT_SETUP-1,1,78,COULEUR_SETUP); + dec(Decalage_curseur); + Tout_Scroller_bas(Decalage_curseur,Position_curseur); + end; + end; + Ecrire_commentaire(Position_curseur+Decalage_curseur); + end; +end; + +{-------------------------- Scroller vers le bas ----------------------------} +procedure Scroll_bas(var Decalage_curseur, Position_curseur:word); +begin + if Position_curseur+Decalage_Curseur0 then + begin + if Position_curseur>1 then + begin + Set_color_of_line(Position_Curseur+HAUTEUR_DEBUT_SETUP-1,1,78,COULEUR_SETUP); + Position_curseur:=1; + Set_color_of_line(Position_Curseur+HAUTEUR_DEBUT_SETUP-1,1,78,COULEUR_SELECT); + end + else + begin + if Decalage_curseur>0 then + begin + Set_color_of_line(Position_Curseur+HAUTEUR_DEBUT_SETUP-1,1,78,COULEUR_SETUP); + if Decalage_curseur>HAUTEUR_FIN_SETUP-HAUTEUR_DEBUT_SETUP + then dec(Decalage_curseur,HAUTEUR_FIN_SETUP-HAUTEUR_DEBUT_SETUP) + else Decalage_curseur:=0; + Tout_ecrire(Decalage_curseur,Position_curseur); + end; + end; + Ecrire_commentaire(Position_curseur+Decalage_curseur); + end; +end; + +{-------------------------- Scroller vers le bas ----------------------------} +procedure Page_down(var Decalage_curseur, Position_curseur:word); +begin + if Position_curseur+Decalage_Curseur$00FF) then + begin + j:=1; + Pas_encore_erreur:=true; + while (j<=NB_OPTIONS) and (Pas_encore_erreur) do + begin + if (i<>j) and (Config[i].Touche=Config[j].Touche) then + begin + Pas_encore_erreur:=false; + Config[i].Erreur:=true; + end; + inc(j); + end; + if Pas_encore_erreur then Config[i].Erreur:=false; + end; +end; + +{------------------- Slectionner une touche modifier ---------------------} +procedure Select(Decalage_curseur, Position_curseur:word); +var + Touche,Num_ligne,Num_option,Num_table:word; +begin + Num_ligne:=Position_curseur+HAUTEUR_DEBUT_SETUP-1; + Num_option:=Position_curseur+Decalage_curseur; + Config[Num_option].Touche:=$00FF; + Ecrire(Num_ligne,Num_option,COULEUR_SELECT); + Goto_XY(40,Num_ligne); + Montrer_curseur; + + repeat + Touche:=Lire_touche; + until Touche<>$0000; + Config[Num_option].Touche:=Touche; + + Cacher_curseur; + Test_duplic; + + Num_table:=1; + if (hi(Touche) and 1)>0 + then Num_table:=2; + if (hi(Touche) and 2)>0 + then Num_table:=3; + if (hi(Touche) and 4)>0 + then Num_table:=4; + case Num_table of + 1: if Pchar2string(Table_Normal[lo(Touche)])='???' + then Config[Num_option].Erreur:=true; + 2: if Pchar2string(Table_Shift[lo(Touche)])='???' + then Config[Num_option].Erreur:=true; + 3: if Pchar2string(Table_Ctrl[lo(Touche)])='???' + then Config[Num_option].Erreur:=true; + 4: if Pchar2string(Table_Alt[lo(Touche)])='???' + then Config[Num_option].Erreur:=true; + end; + + Tout_ecrire(Decalage_curseur,Position_curseur); +end; + +{------------------------ Dslectionner une touche -------------------------} +procedure Unselect(Decalage_curseur, Position_curseur:word); +var + Num_option:word; +begin + Num_option:=Decalage_curseur+Position_curseur; + Config[Num_option].Erreur:=false; + Config[Num_option].Touche:=$00FF; + Test_duplic; + if not Config[Num_option].Suppr + then Config[Num_option].Erreur:=true; + Tout_ecrire(Decalage_curseur,Position_curseur); +end; + +{---------------------- Validation de la configuration ----------------------} +function Validation:boolean; +var + Y_a_des_erreurs:boolean; + i:word; +begin + Y_a_des_erreurs:=false; + i:=1; + while (i<=NB_OPTIONS) and not Y_a_des_erreurs do + begin + Y_a_des_erreurs:=Config[i].Erreur; + inc(i); + end; + + if Y_a_des_erreurs + then Choix_enreg:=4-Fenetre_choix(30,12, + 'There are errors in the^hot-keys configuration.^Check out the "Err" column^in order to correct them.^', + 'OK^Quit anyway^',1,$4C,$3F) + else Choix_enreg:=Fenetre_choix(30,10,'Save configuration?^','Yes^No^Cancel^',1,$2A,$6F); + Validation:=(Choix_enreg<>3); +end; + +{------------------------ Configuration des touches -------------------------} +procedure Setup; +var + Sortie_OK:boolean; + Touche:word; + Decalage_curseur:word; + Position_curseur:word; +begin + Sortie_OK:=false; + Decalage_curseur:=0; + Position_curseur:=1; + Test_duplic; + Tout_ecrire(0,1); + repeat + Touche:=Lire_Touche; + case Touche of + $0048 : Scroll_haut(Decalage_curseur,Position_curseur); + $0050 : Scroll_bas(Decalage_curseur,Position_curseur); + $0049 : Page_up(Decalage_curseur,Position_curseur); + $0051 : Page_down(Decalage_curseur,Position_curseur); + $001C : Select(Decalage_curseur,Position_curseur); + $0053 : Unselect(Decalage_curseur,Position_curseur); + $0001 : Sortie_OK:=Validation; + end; + until Sortie_OK; +end; + + + +{--- Lecture (et mise jour s'il est ancien) du fichier de configuration ---} +type + Type_shade=record + Table:array[1..512] of word; + Pas:byte; + Mode:byte; + end; + Type_mode_video=record + Etat :byte; + Largeur:word; + Hauteur:word; + end; + Type_header=record + Signature:array[1..3] of char; + Version1:byte; + Version2:byte; + Beta1:byte; + Beta2:byte; + end; + Type_chunk=record + Numero:byte; + Taille:word; + end; + Type_infos_touche=record + Numero : word; + Touche : word; + Touche2: word; + end; + +var + Modes_video :array[1..NB_MODES_VIDEO] of Type_mode_video; + Shade_actuel :byte; + Shades :array[1..8] of Type_shade; + Masque :array[1..256] of byte; + Stencil :array[1..256] of byte; + Infos_degrades:array[1..225] of byte; + Smooth_Matrice:array[1..3,1..3] of byte; + Exclude_color :array[1..256] of byte; + Quick_shade :array[1..2] of byte; + + +procedure Interpretation_du_fichier_config; +var + Fichier :file; + Indice :word; + Indice2 :word; + Taille_fichier:longint; + Header :Type_header; + Chunk :Type_chunk; + Infos_touche :Type_infos_touche; + Mode_video :Type_mode_video; + OK :boolean; +begin + {- Modes vidos -} + for Indice:=1 to NB_MODES_VIDEO do + begin + Modes_video[Indice].Etat :=Table_modes_video[Indice,1]; + Modes_video[Indice].Largeur:=Table_modes_video[Indice,2]; + Modes_video[Indice].Hauteur:=Table_modes_video[Indice,3]; + end; + {- Shade -} + Shade_actuel:=0; {1er shade} + for Indice:=1 to 8 do + begin + for Indice2:=1 to 512 do + Shades[Indice].Table[Indice2]:=256; {Case vide pas tagge} + Shades[Indice].Pas:=1; {Pas de 1} + Shades[Indice].Mode:=0; {Mode Normal} + end; + {- Masque -} + fillchar(Masque,sizeof(Masque),0); + {- Stencil -} + fillchar(Stencil,sizeof(Stencil),0); + {- Infos sur les dgrads -} + fillchar(Infos_degrades,sizeof(Infos_degrades),0); + {- Matrice du Smooth -} + Smooth_matrice[1][1]:=1; + Smooth_matrice[2][1]:=2; + Smooth_matrice[3][1]:=1; + Smooth_matrice[1][2]:=2; + Smooth_matrice[2][2]:=4; + Smooth_matrice[3][2]:=2; + Smooth_matrice[1][3]:=1; + Smooth_matrice[2][3]:=2; + Smooth_matrice[3][3]:=1; + {- Exclude colors -} + fillchar(Exclude_color,sizeof(Exclude_color),0); + {- Quick-shade -} + Quick_shade[1]:=1; {Step} + Quick_shade[2]:=0; {Loop mode (0=normal,1=loop,2=no sat.} + + Taille_fichier:=0; + assign(Fichier,'GFX2.CFG'); + {$I-} + reset(Fichier,1); + {$I+} + if (IOresult=0) then + begin {On tente de rcuprer les infos du fichier} + Taille_fichier:=filesize(Fichier); + if (Taille_fichier>=7) then + begin + blockread(Fichier,Header,7); + if Header.Signature='CFG' then + begin + {On regarde si c'est un fichier de la version actuelle} + if (Taille_fichier =TAILLE_FICHIER_CONFIG) and + (Header.Version1=VERSION1 ) and + (Header.Version2=VERSION2 ) and + (Header.Beta1 =BETA1 ) and + (Header.Beta2 =BETA2 ) then + begin {Si oui, on rcupre les touches et on s'arrte l} + seek(Fichier,sizeof(Header)+Sizeof(Chunk)); + for Indice:=1 to NB_OPTIONS do + blockread(Fichier,Config[Indice],6); + close(Fichier); + exit; + end + else + begin {Si non, c'est une ancienne version et on rcupre tout ce qu'on peut} + OK:=TRUE; + {$I-} + while OK(*not eof(Fichier)*) do + begin + blockread(Fichier,Chunk,sizeof(Chunk)); + if (IOresult<>0) then + OK:=FALSE + else + case Chunk.Numero of + 0:begin {Touches} + for Indice:=1 to (Chunk.Taille div sizeof(Infos_touche)) do + begin + blockread(Fichier,Infos_touche,sizeof(Infos_touche)); + if (IOresult<>0) then + OK:=FALSE + else + begin + Indice2:=1; + while (Indice2<=NB_OPTIONS) and + (Config[Indice2].Numero<>Infos_touche.Numero) do + inc(Indice2); + if (Indice2<=NB_OPTIONS) then + begin + Config[Indice2].Touche :=Infos_touche.Touche; + Config[Indice2].Touche2:=Infos_touche.Touche2; + end; + end; + end; + end; + 1:begin {Modes vido} + for Indice:=1 to (Chunk.Taille div sizeof(Mode_video)) do + begin + blockread(Fichier,Mode_video,sizeof(Mode_video)); + if (IOresult<>0) then + OK:=FALSE + else + begin + Indice2:=1; + while (Indice2<=NB_MODES_VIDEO) and + ( (Modes_video[Indice2].Largeur<>Mode_video.Largeur) or + (Modes_video[Indice2].Hauteur<>Mode_video.Hauteur) or + ((Modes_video[Indice2].Etat and $C0)<>(Mode_video.Etat and $C0)) ) do + inc(Indice2); + if (Indice2<=NB_MODES_VIDEO) then + Modes_video[Indice2].Etat:=Mode_video.Etat; + end; + end; + end; + 2:begin {Shade} + blockread(Fichier,Shade_actuel,sizeof(Shade_actuel)); + if (IOresult<>0) then + begin + OK:=FALSE; {Erreur => On remet un shade actuel propre} + Shade_actuel:=0; + end + else + begin + blockread(Fichier,Shades,sizeof(Shades)); + if (IOresult<>0) then + begin + OK:=FALSE; {Erreur => On remet des tables de shades propres} + for Indice:=1 to 8 do + begin + for Indice2:=1 to 512 do + Shades[Indice].Table[Indice2]:=256; {Case vide pas tagge} + Shades[Indice].Pas:=1; {Pas de 1} + Shades[Indice].Mode:=0; {Mode Normal} + end; + end; + end; + end; + 3:begin {Masque} + blockread(Fichier,Masque,sizeof(Masque)); + if (IOresult<>0) then + begin + OK:=FALSE; {Erreur => On remet un masque propre} + fillchar(Masque,sizeof(Masque),0); + end; + end; + 4:begin {Stencil} + blockread(Fichier,Stencil,sizeof(Stencil)); + if (IOresult<>0) then + begin + OK:=FALSE; {Erreur => On remet un stencil propre} + fillchar(Stencil,sizeof(Stencil),0); + end; + end; + 5:begin {Infos sur les dgrads} + blockread(Fichier,Infos_degrades,sizeof(Infos_degrades)); + if (IOresult<>0) then + begin + OK:=FALSE; {Erreur => On remet des infos sur les dgrads propres} + fillchar(Stencil,sizeof(Infos_degrades),0); + end; + end; + 6:begin {Matrice du Smooth} + blockread(Fichier,Smooth_Matrice,sizeof(Smooth_Matrice)); + if (IOresult<>0) then + begin + OK:=FALSE; {Erreur => On remet une matrice de Smooth propre} + Smooth_matrice[1][1]:=1; + Smooth_matrice[2][1]:=2; + Smooth_matrice[3][1]:=1; + Smooth_matrice[1][2]:=2; + Smooth_matrice[2][2]:=4; + Smooth_matrice[3][2]:=2; + Smooth_matrice[1][3]:=1; + Smooth_matrice[2][3]:=2; + Smooth_matrice[3][3]:=1; + end; + end; + 7:begin {Exclude colors} + blockread(Fichier,Exclude_color,sizeof(Exclude_color)); + if (IOresult<>0) then + begin + OK:=FALSE; {Erreur => On remet une table d'exclusion propre} + fillchar(Exclude_color,sizeof(Exclude_color),0); + end; + end; + 8:begin {Quick-shade} + blockread(Fichier,Quick_shade,sizeof(Quick_shade)); + if (IOresult<>0) then + begin + OK:=FALSE; {Erreur => On remet un quick-shade propre} + Quick_shade[1]:=1; {Step} + Quick_shade[2]:=0; {Loop mode} + end; + end + else + begin + seek(Fichier,filepos(Fichier)+Chunk.Taille); + if (IOresult<>0) then + OK:=FALSE; + end; + end; + end; + {$I+} + end; + end; + end; + end; + + {- Ecriture du fichier d'options -} + assign(Fichier,'GFX2.CFG'); + rewrite(Fichier,1); + + {Ecriture du header} + Header.Signature:='CFG'; + Header.Version1 :=VERSION1; + Header.Version2 :=VERSION2; + Header.Beta1 :=BETA1; + Header.Beta2 :=BETA2; + blockwrite(Fichier,Header,sizeof(Header)); + + {Enregistrement des touches} + Chunk.Numero:=0; + Chunk.Taille:=NB_OPTIONS*sizeof(Infos_touche); + blockwrite(Fichier,Chunk,sizeof(Chunk)); + for Indice:=1 to NB_OPTIONS do + blockwrite(Fichier,Config[Indice],sizeof(Infos_touche)); {Les 3 premiers champs (words) sont: Numro,Touche,Touche2} + + {Sauvegarde de l'tat de chaque mode vido} + Chunk.Numero:=1; + Chunk.Taille:=sizeof(Modes_video); + blockwrite(Fichier,Chunk,sizeof(Chunk)); + blockwrite(Fichier,Modes_video,sizeof(Modes_video)); + + {Ecriture des donnes du Shade (prcdes du shade en cours)} + Chunk.Numero:=2; + Chunk.Taille:=sizeof(Shades)+Sizeof(Shade_actuel); + blockwrite(Fichier,Chunk,sizeof(Chunk)); + blockwrite(Fichier,Shade_actuel,Sizeof(Shade_actuel)); + blockwrite(Fichier,Shades,Sizeof(Shades)); + + {Ecriture des donnes du Masque} + Chunk.Numero:=3; + Chunk.Taille:=sizeof(Masque); + blockwrite(Fichier,Chunk,sizeof(Chunk)); + blockwrite(Fichier,Masque,Sizeof(Masque)); + + {Ecriture des donnes du Stencil} + Chunk.Numero:=4; + Chunk.Taille:=sizeof(Stencil); + blockwrite(Fichier,Chunk,sizeof(Chunk)); + blockwrite(Fichier,Stencil,Sizeof(Stencil)); + + {Ecriture des donnes sur les dgrads} + Chunk.Numero:=5; + Chunk.Taille:=sizeof(Infos_degrades); + blockwrite(Fichier,Chunk,sizeof(Chunk)); + blockwrite(Fichier,Infos_degrades,Sizeof(Infos_degrades)); + + {Ecriture de la matrice de Smooth} + Chunk.Numero:=6; + Chunk.Taille:=sizeof(Smooth_Matrice); + blockwrite(Fichier,Chunk,sizeof(Chunk)); + blockwrite(Fichier,Smooth_Matrice,Sizeof(Smooth_Matrice)); + + {Ecriture de la table d'exclusion de couleurs} + Chunk.Numero:=7; + Chunk.Taille:=sizeof(Exclude_color); + blockwrite(Fichier,Chunk,sizeof(Chunk)); + blockwrite(Fichier,Exclude_color,Sizeof(Exclude_color)); + + {Ecriture des donnes du Quick-shade} + Chunk.Numero:=8; + Chunk.Taille:=sizeof(Quick_shade); + blockwrite(Fichier,Chunk,sizeof(Chunk)); + blockwrite(Fichier,Quick_shade,Sizeof(Quick_shade)); + + close(Fichier); +end; + + + +function Recreer_INI:boolean; +type + T_Buffer=array[1..TAILLE_INI] of byte; +var + Fichier_INI,Fichier_DAT:file; + Buffer:pointer;{^T_Buffer;} + Erreur:boolean; +begin + assign(Fichier_INI,'GFX2.INI'); + + assign(Fichier_DAT,'GFX2.DAT'); + {$I-} + reset(Fichier_DAT,1); + if IOresult<>0 then + Erreur:=true + else + begin + seek(Fichier_DAT,filesize(Fichier_DAT)-TAILLE_INI); + if IOresult<>0 then + Erreur:=true + else + begin + Erreur:=false; + rewrite(Fichier_INI,1); + getmem(Buffer,TAILLE_INI); + blockread (Fichier_DAT,Buffer^,TAILLE_INI); + blockwrite(Fichier_INI,Buffer^,TAILLE_INI); + freemem(Buffer,TAILLE_INI); + close(Fichier_INI); + end; + close(Fichier_DAT); + end; + {$I+} + + Recreer_INI:=Erreur; +end; + + +{------------------- Initialisation de la configuration ---------------------} +function Initialiser_config:boolean; +var + Erreur:boolean; + Fichier_INI:file; +begin + Erreur:=false; + + Numero_definition_option:=1; + + {!!! LES TOUCHES SONT CONFIGUREES POUR LES CLAVIERS QWERTY !!!} + + Definir_option(0,'Scroll up', + 'Used to scroll upwards in the picture, either in magnify and normal mode.', + 'This hot-key cannot be removed.', + false,$0048); {Haut} + Definir_option(1,'Scroll down', + 'Used to scroll downwards in the picture, either in magnify and normal mode.', + 'This hot-key cannot be removed.', + false,$0050); {Bas} + Definir_option(2,'Scroll left', + 'Used to scroll to the left in the picture, either in magnify and normal', + 'mode. This hot-key cannot be removed.', + false,$004B); {Gauche} + Definir_option(3,'Scroll right', + 'Used to scroll to the right in the picture, either in magnify and normal', + 'mode. This hot-key cannot be removed.', + false,$004D); {Droite} + Definir_option(4,'Faster scroll up', + 'Used to scroll upwards in the picture fast, either in magnify and normal', + 'mode.', + true,$0148); {Shift + Haut} + Definir_option(5,'Faster scroll down', + 'Used to scroll downwards in the picture fast, either in magnify and normal', + 'mode.', + true,$0150); {Shift + Bas} + Definir_option(6,'Faster scroll left', + 'Used to scroll to the left in the picture fast, either in magnify and normal', + 'mode.', + true,$014B); {Shift + Gauche} + Definir_option(7,'Faster scroll right', + 'Used to scroll to the right in the picture fast, either in magnify and', + 'normal mode.', + true,$014D); {Shift + Droite} + Definir_option(8,'Slower scroll up', + 'Used to scroll upwards in the picture pixel by pixel, either in magnify and', + 'normal mode.', + true,$0498); {Alt + Haut} + Definir_option(9,'Slower scroll down', + 'Used to scroll downwards in the picture pixel by pixel, either in magnify and', + 'normal mode.', + true,$04A0); {Alt + Bas} + Definir_option(10,'Slower scroll left', + 'Used to scroll to the left in the picture pixel by pixel, either in magnify', + 'and normal mode.', + true,$049B); {Alt + Gauche} + Definir_option(11,'Slower scroll right', + 'Used to scroll to the right in the picture pixel by pixel, either in magnify', + 'and normal mode.', + true,$049D); {Alt + Droite} + Definir_option(12,'Move mouse cursor 1 pixel up', + 'Used to simulate a very small mouse deplacement upwards.', + 'It''s very useful when you want a ultra-high precision.', + true,$028D); {Ctrl + Haut} + Definir_option(13,'Move mouse cursor 1 pixel down', + 'Used to simulate a very small mouse deplacement downwards.', + 'It''s very useful when you want a ultra-high precision.', + true,$0291); {Ctrl + Bas} + Definir_option(14,'Move mouse cursor 1 pixel left', + 'Used to simulate a very small mouse deplacement to the left.', + 'It''s very useful when you want a ultra-high precision.', + true,$0273); {Ctrl + Gauche} + Definir_option(15,'Move mouse cursor 1 pixel right', + 'Used to simulate a very small mouse deplacement to the right.', + 'It''s very useful when you want a ultra-high precision.', + true,$0274); {Ctrl + Droite} + Definir_option(16,'Simulate left mouse click', + 'Used to simulate a click with the left mouse button..', + 'It''s very useful when you want a ultra-high precision.', + true,$0039); {Space} + Definir_option(17,'Simulate right mouse click', + 'Used to simulate a click with the right mouse button..', + 'It''s very useful when you want a ultra-high precision.', + true,$0139); {Shift + Space} + Definir_option(18,'Show/hide option menu', + 'Switch the tool bar display on/off.', + 'This hot-key cannot be removed.', + false,$0044); {F10} + Definir_option(19,'Show/hide cursor', + 'Switch the cursor display on/off.', + 'This only works on the "small cross" and "hand" cursors.', + true,$0043); {F9} + Definir_option(20,'Set paintbrush to 1 pixel', + 'Useful when you want to use a "single-pixel-brush".', + '', + true,$0053); {Del} + Definir_option(21,'Paintbrush choice', + 'Opens a menu where you can choose a paintbrush out of 24 predefined ones.', + '', + true,$003E); {F4} + Definir_option(22,'Monochrome brush', + 'Turn your current user-defined brush into a single colored one.', + 'All non-transparent colors are set to current foreground color.', + true,$0157); {Shift + F4} + Definir_option(23,'Freehand drawing', + 'Set the drawing mode to the classical freehand one.', + '', + true,$0020); {D} + Definir_option(24,'Switch freehand drawing mode', + 'Switch between the 3 ways to use freehand drawing.', + 'These modes are: continuous, discontinuous and point by point.', + true,$0120); {Shift + D} + Definir_option(25,'Continuous freehand drawing', + 'Switch directly to continuous freehand drawing mode.', + '', + true,$0220); {Ctrl + D} + Definir_option(26,'Line', + 'Allows you to draw lines.', + '', + true,$0026); {L} + Definir_option(27,'Knotted lines', + 'Allows you to draw linked lines.', + 'This mode can also be called "Polyline".', + true,$0126); {Shift + L} + Definir_option(28,'Spray', + 'Allows you to spray brushes randomly in the picture.', + '', + true,$001E); {A (Q en AZERTY)} + Definir_option(29,'Spray menu', + 'Opens a menu in which you can configure the spray flow and size.', + '', + true,$011E); {Shift + A} + Definir_option(30,'Flood-fill', + 'Allows you to fill an area of the picture made of pixels of the same color.', + '', + true,$0021); {F} + Definir_option(124,'Replace color', + 'Allows you to replace all the pixels of the color pointed by the mouse with', + 'the fore-color or the back-color.', + true,$0121); {Shift + F} + Definir_option(31,'Bzier''s curves', + 'Allows you to draw Bzier''s curves.', + '', + true,$0017); {I} + Definir_option(32,'Bzier''s curve with 3 or 4 points', + 'Allows you to choose whether you want to draw Bzier''s curves with 3 or 4', + 'points.', + true,$0117); {Shift + I} + Definir_option(33,'Empty rectangle', + 'Allows you to draw a rectangle using the brush.', + '', + true,$0013); {R} + Definir_option(34,'Filled rectangle', + 'Allows you to draw a filled rectangle.', + '', + true,$0113); {Shift + R} + Definir_option(35,'Empty circle', + 'Allows you to draw a circle using the brush.', + '', + true,$002E); {C} + Definir_option(36,'Empty ellipse', + 'Allows you to draw an ellipse using the brush.', + '', + true,$022E); {Ctrl + C} + Definir_option(37,'Filled circle', + 'Allows you to draw a filled circle.', + '', + true,$012E); {Shift + C} + Definir_option(38,'Filled ellipse', + 'Allows you to draw a filled ellipse.', + '', + true,$032E); {Shift + Ctrl + C} + Definir_option(39,'Empty polygon', + 'Allows you to draw a polygon using the brush.', + '', + true,$0031); {N} + Definir_option(40,'Empty "polyform"', + 'Allows you to draw a freehand polygon using the brush.', + '', + true,$0231); {Ctrl + N} + Definir_option(41,'Filled polygon', + 'Allows you to draw a filled polygon.', + '', + true,$0131); {Shift + N} + Definir_option(42,'Filled "polyform"', + 'Allows you to draw a filled freehand polygon.', + '', + true,$0331); {Shift + Ctrl + N} + Definir_option(43,'Rectangle with gradation', + 'Allows you to draw a rectangle with a color gradation.', + '', + true,$0413); {Alt + R} + Definir_option(44,'Gradation menu', + 'Allows you to configure the way color gradations are calculated.', + '', + true,$0422); {Alt + G} + Definir_option(45,'Sphere with gradation', + 'Allows you to draw a rectangle with a color gradation.', + '', + true,$042E); {Alt + C} + Definir_option(46,'Ellipse with gradation', + 'Allows you to draw an ellipse filled with a color gradation.', + '', + true,$052E); {Shift + Alt + C} + Definir_option(47,'Adjust picture', + 'Allows you to move the whole picture in order to re-center it.', + 'Notice that what gets out from a side reappears on the other.', + true,$004C); {Kpad5} + Definir_option(48,'Flip/shrink picture menu', + 'Opens a menu which allows you to flip the picture horizontally/vertically or', + 'to shrink it to half-scale horizontally and/or vertically.', + true,$014C); {Shift + Kpad5} + Definir_option(49,'Drawing effects', + 'Opens a menu where you can enable/disable and configure the drawing effects', + 'listed below.', + true,$0012); {E} + Definir_option(50,'Shade mode', + 'Allows you to shade or lighten some pixels of the picture belonging to a', + 'color range, in addition of any drawing tool.', + true,$003F); {F5} + Definir_option(51,'Shade menu', + 'Opens a menu where you can choose color ranges to use with the Shade mode.', + 'This menu also contains parameters used both in Shade and Quick-shade modes.', + true,$0158); {Shift + F5} + Definir_option(131,'Quick-shade mode', + 'Does the same thing as shade mode with a simpler method (faster to define', + 'but a bit less powerful).', + true,$0262); {Ctrl + F5} + Definir_option(132,'Quick-shade menu', + 'Opens a menu where you can define the parameters of the quick-shade mode.', + '', + true,$0362); {Shift + Ctrl + F5} + Definir_option(52,'Stencil mode', + 'Allows you to mask colors that must not be affected when you are drawing.', + '', + true,$0040); {F6} + Definir_option(53,'Stencil menu', + 'Opens a menu where you can choose colors masked by the Stencil mode.', + '', + true,$0159); {Shift + F6} + Definir_option(54,'Mask mode', + 'Allows you to mask colors of the spare page that will keep you from ', + 'drawing. This mode should be called "True stencil".', + true,$046D); {Alt + F6} + Definir_option(55,'Mask menu', + 'Opens a menu where you can choose colors for the Mask mode.', + '', + true,$056D); {Shift + Alt + F6} + Definir_option(56,'Grid mode', + 'Force the cursor to snap up grid points.', + '', + true,$0022); {G} + Definir_option(57,'Grid menu', + 'Open a menu where you can configure the grid used by Grid mode.', + '', + true,$0122); {Shift + G} + Definir_option(58,'Sieve mode', + 'Only draws pixels on certain positions matching with a sieve.', + '', + true,$0222); {Ctrl + G} + Definir_option(59,'Sieve menu', + 'Opens a menu where you can configure the sieve.', + '', + true,$0322); {Shift + Ctrl + G} + Definir_option(60,'Invert sieve', + 'Inverts the pattern defined in the Sieve menu.', + '', + true,$0622); {Ctrl + Alt + G} + Definir_option(61,'Colorize mode', + 'Allows you to colorize the pixels on which your brush is pasted.', + 'This permits you to make transparency effects.', + true,$0041); {F7} + Definir_option(62,'Colorize menu', + 'Opens a menu where you can give the opacity percentage for Colorize mode.', + '', + true,$015A); {Shift + F7} + Definir_option(63,'Smooth mode', + 'Soften pixels on which your brush is pasted.', + '', + true,$0042); {F8} + Definir_option(123,'Smooth menu', + 'Opens a menu where you can define the Smooth matrix.', + '', + true,$015B); {Shift + F8} + Definir_option(64,'Smear mode', + 'Smears the pixels when you move your brush on the picture.', + '', + true,$046F); {Alt + F8} + Definir_option(65,'Tiling mode', + 'Puts parts of the brush where you draw.', + '', + true,$0430); {Alt + B} + Definir_option(66,'Tiling menu', + 'Opens a menu where you can configure the origin of the tiling.', + '', + true,$0530); {Shift + Alt + B} + Definir_option(67,'Classical brush grabbing', + 'Allows you to pick a brush defined within a rectangle.', + '', + true,$0030); {B} + Definir_option(68,'"Lasso" brush grabbing', + 'Allows you to pick a brush defined within a freehand polygon.', + '', + true,$0230); {Ctrl + B} + Definir_option(69,'Get previous brush back', + 'Restore the last user-defined brush.', + '', + true,$0130); {Shift + B} + Definir_option(70,'Horizontal brush flipping', + 'Reverse brush horizontally.', + '', + true,$002D); {X} + Definir_option(71,'Vertical brush flipping', + 'Reverse brush vertically.', + '', + true,$0015); {Y} + Definir_option(72,'90 brush rotation', + 'Rotate the user-defined brush by 90 (counter-clockwise).', + '', + true,$002C); {Z (W en AZERTY)} + Definir_option(73,'180 brush rotation', + 'Rotate the user-defined brush by 180.', + '', + true,$012C); {Shift + Z} + Definir_option(74,'Strech brush', + 'Allows you to resize the user-defined brush.', + '', + true,$001F); {S} + Definir_option(75,'Distort brush', + 'Allows you to distort the user-defined brush.', + '', + true,$011F); {Shift + S} + Definir_option(76,'Outline brush', + 'Outlines the user-defined brush with the fore color.', + '', + true,$0018); {O} + Definir_option(77,'Nibble brush', + 'Deletes the borders of the user-defined brush.', + 'This does the opposite of the Outline option.', + true,$0118); {Shift + O} + Definir_option(78,'Get colors from brush', + 'Copy colors of the spare page that are used in the brush.', + '', + true,$0085); {F11} + Definir_option(79,'Recolorize brush', + 'Recolorize pixels of the user-defined brush in order to get a brush which', + 'looks like the one grabbed in the spare page.', + true,$0086); {F12} + Definir_option(80,'Rotate by any angle', + 'Rotate the brush by an angle that you can define.', + '', + true,$0011); {W (Z en AZERTY)} + Definir_option(81,'Pipette', + 'Allows you to copy the color of a pixel in the picture into the foreground', + 'or background color.', + true,$0029); {`~ (Touche sous le Esc - en AZERTY)} + Definir_option(82,'Swap foreground/background colors', + 'Invert foreground and background colors.', + '', + true,$0129); {Shift + `~} + Definir_option(83,'Magnifier mode', + 'Allows you to zoom into the picture.', + '', + true,$0032); {M (,? sur AZERTY)} + Definir_option(84,'Zoom factor menu', + 'Opens a menu where you can choose a magnifying factor.', + '', + true,$0132); {Shift + M} + Definir_option(85,'Zoom in', + 'Increase magnifying factor.', + '', + true,$004E); {Grey +} + Definir_option(86,'Zoom out', + 'Decrease magnifying factor.', + '', + true,$004A); {Grey -} + Definir_option(87,'Brush effects menu', + 'Opens a menu which proposes different effects on the user-defined brush.', + '', + true,$0630); {Ctrl + Alt + B} + Definir_option(88,'Text', + 'Opens a menu which permits you to type in a character string and to choose a', + 'font, and then creates a new user-defined brush fitting to your choices.', + true,$0014); {T} + Definir_option(89,'Screen resolution menu', + 'Opens a menu where you can choose the dimensions of the screen in which you', + 'want to draw among the numerous X and SVGA proposed modes.', + true,$001C); {Enter} + Definir_option(90,'"Safety" resolution', + 'Set resolution to 320x200. This can be useful if you choosed a resolution', + 'that is not supported by your monitor and video card. Cannot be removed.', + false,$011C); {Shift + Enter} + Definir_option(91,'Help and credits', + 'Opens a window where you can get information about the program.', + '', + true,$003B); {F1} + Definir_option(92,'Statistics', + 'Displays miscellaneous more or less useful information.', + '', + true,$0154); {Shift + F1} + Definir_option(93,'Jump to spare page', + 'Swap current page and spare page.', + '', + true,$000F); {Tab} + Definir_option(94,'Copy current page to spare page', + 'Copy current page to spare page.', + '', + true,$010F); {Shift + Tab} + Definir_option(95,'Save picture as...', + 'Opens a file-selector that allows you to save your picture with a new', + 'path-name.', + true,$003C); {F2} + Definir_option(96,'Save picture', + 'Saves your picture with the last name you gave it.', + '', + true,$0155); {Shift + F2} + Definir_option(97,'Load picture', + 'Opens a file-selector that allows you to load a new picture.', + '', + true,$003D); {F3} + Definir_option(98,'Re-load picture', + 'Re-load the current picture.', + 'This allows you to cancel modifications made since last saving.', + true,$0156); {Shift + F3} + Definir_option(99,'Save brush', + 'Opens a file-selector that allows you to save your current user-defined', + 'brush.', + true,$025F); {Ctrl + F2} + Definir_option(100,'Load brush', + 'Opens a file-selector that allows you to load a brush.', + '', + true,$0260); {Ctrl + F3} + Definir_option(101,'Settings', + 'Opens a menu which permits you to set the dimension of your picture, and to', + 'modify some parameters of the program.', + true,$015D); {Shift + F10} + Definir_option(102,'Undo (Oops!)', + 'Cancel the last action which modified the picture. This has no effect after', + 'a jump to the spare page, loading a picture or modifying its size.', + true,$0016); {U} + Definir_option(103,'Redo', + 'Redo the last undone action. This has no effect after a jump to the spare', + 'page, loading a picture or modifying its size.', + true,$0116); {Shift + U} + Definir_option(133,'Kill', + 'Kills the current page. It actually removes the current page from the list', + 'of "Undo" pages.', + true,$0153); {Shift + Suppr} + Definir_option(104,'Clear page', + 'Clears the picture with the first color of the palette (usually black).', + '', + true,$000E); {BackSpace} + Definir_option(105,'Clear page with backcolor', + 'Clears the picture with the backcolor.', + '', + true,$010E); {Shift + BackSpace} + Definir_option(106,'Quit program', + 'Allows you to leave the program.', + 'If modifications were not saved, confirmation is asked.', + false,$0010); {Q (A en AZERTY)} + Definir_option(107,'Palette menu', + 'Opens a menu which allows you to modify the current palette.', + '', + true,$0019); {P} + Definir_option(125,'Secondary palette menu', + 'Opens a menu which allows you to define color series and some tagged colors.', + '', + true,$0119); {Shift + P} + Definir_option(130,'Exclude colors menu', + 'Opens a menu which allows you to define the colors you don''t want to use in', + 'modes such as Smooth and Transparency, or when remapping a brush.', + true,$0219); {Ctrl + P} + Definir_option(108,'Scroll palette to the left', + 'Scroll palette in the tool bar to the left, column by column.', + '', + true,$0049); {PgUp} + Definir_option(109,'Scroll palette to the right', + 'Scroll palette in the tool bar to the right, column by column.', + '', + true,$0051); {PgDn} + Definir_option(110,'Scroll palette to the left faster', + 'Scroll palette in the tool bar to the left, 8 columns by 8 columns.', + '', + true,$0149); {Shift + PgUp} + Definir_option(111,'Scroll palette to the right faster', + 'Scroll palette in the tool bar to the right, 8 columns by 8 columns.', + '', + true,$0151); {Shift + PgDn} + Definir_option(112,'Center brush attachment point', + 'Set the attachement of the user-defined brush to its center.', + '', + true,$028F); {Ctrl + 5 (pav numrique)} + Definir_option(113,'Top-left brush attachment point', + 'Set the attachement of the user-defined brush to its top-left corner.', + '', + true,$0277); {Ctrl + 7} + Definir_option(114,'Top-right brush attachment point', + 'Set the attachement of the user-defined brush to its top-right corner.', + '', + true,$0284); {Ctrl + 9} + Definir_option(115,'Bottom-left brush attachment point', + 'Set the attachement of the user-defined brush to its bottom-left corner.', + '', + true,$0275); {Ctrl + 1} + Definir_option(116,'Bottom-right brush attachment point', + 'Set the attachement of the user-defined brush to its bottom-right corner.', + '', + true,$0276); {Ctrl + 3} + Definir_option(117,'Next foreground color', + 'Set the foreground color to the next in the palette.', + '', + true,$001B); {] ($ en AZERTY)} + Definir_option(118,'Previous foreground color', + 'Set the foreground color to the previous in the palette.', + '', + true,$001A); {[ (^ en AZERTY)} + Definir_option(119,'Next background color', + 'Set the background color to the next in the palette.', + '', + true,$011B); {Shift + ]} + Definir_option(120,'Previous background color', + 'Set the background color to the previous in the palette.', + '', + true,$011A); {Shift + [} + Definir_option(126,'Next user-defined forecolor', + 'Set the foreground color to the next in the user-defined color series.', + '', + true,$000D); {'=+'} + Definir_option(127,'Previous user-defined forecolor', + 'Set the foreground color to the previous in the user-defined color series.', + '', + true,$000C); {'-_' (')' en AZERTY} + Definir_option(128,'Next user-defined backcolor', + 'Set the background color to the next in the user-defined color series.', + '', + true,$010D); {Shift + '=+'} + Definir_option(129,'Previous user-defined backcolor', + 'Set the background color to the previous in the user-defined color series.', + '', + true,$010C); {Shift + '-_' (')' en AZERTY} + Definir_option(121,'Shrink paintbrush', + 'Decrease the width of the paintbrush if it is special circle or square.', + '', + true,$0033); {,< (;. en AZERTY)} + Definir_option(122,'Enlarge paintbrush', + 'Increase the width of the paintbrush if it is special circle or square.', + '', + true,$0034); {.> (:/ en AZERTY)} + NB_OPTIONS:=Numero_definition_option-1; + + assign(Fichier_INI,'GFX2.INI'); + {$I-} + reset(Fichier_INI,1); + {$I+} + if IOresult<>0 then {Si GFX2.INI est absent, on l'extrait de GFX2.DAT} + Erreur:=Recreer_INI + else + close(Fichier_INI); + + if not Erreur then Interpretation_du_fichier_config; + + Initialiser_config:=Erreur; +end; + + +{------------------- Enregistrement de la configuration ---------------------} +procedure Enregistrer_config; +var + Fichier:file; + Indice:word; + Octet:byte; +begin + if Choix_enreg=1 then {Enregistrement des touches (si souhait)} + begin + assign(Fichier,'GFX2.CFG'); + reset(Fichier,1); + + seek(Fichier,sizeof(Type_header)+Sizeof(Type_chunk)); {Positionnement sur la 1re touche} + + for Indice:=1 to NB_OPTIONS do + blockwrite(Fichier,Config[Indice],sizeof(Type_infos_touche)); {Les 3 premiers champs (words) sont: Numro,Touche,Touche2} + + close(Fichier); + end; +end; + +{---------- Vrifier qu'on peut crire sur le lecteur de lancement ----------} +function Verifier_ecriture_possible:boolean; +var + Fichier:file; +begin + assign(Fichier,'GFX2.$$$'); + {$I-} + rewrite(Fichier,1); + close(Fichier); + erase(Fichier); + {$I+} + Verifier_ecriture_possible:=(IOresult=0); +end; + +{============================================================================} +var + Keyb_mode:byte; + +begin + if Verifier_ecriture_possible then + begin + + asm + mov ax,0AD83h + int 2Fh + mov Keyb_mode,bl + mov ax,0AD82h + xor bl,bl + int 2Fh + end; + + Text_mode_80x50; + Cacher_curseur; + Dessiner_ecran_principal; + if not Initialiser_config then + begin + Setup; + Enregistrer_config; + + Text_mode_80x25; + Montrer_curseur; + + asm + mov ax,0AD82h + mov bl,Keyb_mode + int 2Fh + end; + + halt(0); + end + else + begin + Text_mode_80x25; + writeln('Error reading GFX2.DAT! This file is either absent or corrupt.'); + Montrer_curseur; + + asm + mov ax,0AD82h + mov bl,Keyb_mode + int 2Fh + end; + halt(1); + end; + end + else + begin + writeln('Error: You mustn''t run this setup program from a read-only drive!'); + writeln; + writeln('The most probable cause of this error is that you are either running this'); + writeln('program from a CD-ROM or a protected floppy disk.'); + writeln('You should try to copy all the files of GrafX 2.00 on a hard drive, or to'); + writeln('unprotect your floppy disk if you really want to run it from this medium.'); + halt(1); + end; +end. diff --git a/const.h b/const.h new file mode 100644 index 00000000..9b79f516 --- /dev/null +++ b/const.h @@ -0,0 +1,449 @@ +#ifndef _CONST_H_ +#define _CONST_H_ + + + +// Dclaration des constantes //////////////////////////////////////////////// + +#define M_PI 3.14159265358979323846264338328 +#define M_2PI 6.28318530717958647692528676656 + +// Note: La taille du fichier GFX2.DAT est dfinie au dbut de INIT.C ! +#define POURCENTAGE_VERSION "96.5%" // Libell du pourcentage de la version +#define VERSION1 2 // | +#define VERSION2 0 // |_ Numro de version dcoup en +#define BETA1 96 // | plusieurs parties => 2.0 95.5% +#define BETA2 5 // | +#define ALPHA_BETA "" // Type de la version "" ou "" +#define TAILLE_FICHIER_CONFIG 10351 // Taille du fichier GFX2.CFG +#define NB_MODES_VIDEO 60 // Nombre de modes vido +#define NB_BOUTONS 38 // Nombre de boutons grer +#define NB_TOUCHES 134 // Nombre de combinaisons de touches +#define NB_TOUCHES_SPECIALES 72 // Nombre de touches spciales +#define NB_OPERATIONS 32 // Nombre d'oprations gres par le moteur +#define NB_FACTEURS_DE_ZOOM 12 // Nombre de facteurs de zoom +#define LARGEUR_MENU 254 // Largeur du menu en taille relle +#define HAUTEUR_MENU 44 // Hauteur du menu en taille relle +#define NB_SPRITES_CURSEUR 8 // Nombre de sprites de curseur +#define LARGEUR_SPRITE_CURSEUR 15 // Largeur d'un sprite de curseur en pixels +#define HAUTEUR_SPRITE_CURSEUR 15 // Hauteur d'un sprite de curseur en pixels +#define NB_SPRITES_EFFETS 9 // Nombre de sprites d'effets +#define NB_SPRITES_MENU 9 // Nombre de sprites de menu +#define LARGEUR_SPRITE_MENU 14 // Largeur d'un sprite de menu en pixels +#define HAUTEUR_SPRITE_MENU 14 // Hauteur d'un sprite de menu en pixels +#define LARGEUR_PINCEAU 16 // Largeur d'un sprite de pinceau prdfini +#define HAUTEUR_PINCEAU 16 // Hauteur d'un sprite de pinceau prdfini +#define TAILLE_MAXI_PINCEAU 127 // Taille maxi des pinceaux +#define NB_SPRITES_DRIVES 5 // Nombre de sprites de drives +#define LARGEUR_SPRITE_DRIVE 7 // Largeur d'un sprite de drive en pixels +#define HAUTEUR_SPRITE_DRIVE 7 // Hauteur d'un sprite de drive en pixels +#define NB_SPRITES_PINCEAU 48 // Nombre de sprites de pinceau +#define NB_TRAMES_PREDEFINIES 12 // Nombre de trames prdfinies +#define TAILLE_PILE_OPERATIONS 16 // Nombre maximum d'lments utiliss par les oprations +#define TAILLE_MAXI_PATH 37 // Taille maximum affichable du rpertoire courant dans les fentres du fileselect +#define TAILLE_COMMENTAIRE 32 // Taille maxi des commentaires pour le PKM +#define TAILLE_NOM_CONSTRUCTEUR 24 // Taille maxi du nom de constructeur VESA dans la fentre de stats. +#define NB_PAGES_UNDO_MAX 99 // Nombre maximal de pages d'undo +#define FACTEUR_DE_ZOOM_PAR_DEFAUT 4 // Facteur de zoom initial +#define NB_SECTIONS_AIDE 3 // Nombre de sections dans l'aide + +// On impose l'allocation dynamique des pages de backups de conserver un +// minimum de 256 Ko pour que le reste du programme puisse continuer +// fonctionner. +#define QUANTITE_MINIMALE_DE_MEMOIRE_A_CONSERVER (256*1024) + +#define A_GAUCHE 1 // Indique une direction (ou click) gauche +#define A_DROITE 2 // Indique une direction (ou click) droite + +#define LARGEUR_BARRE_SPLIT 6 // [ ۱ ] +#define PROPORTION_SPLIT 0.3 // proportion de la zone non-zoome en largeur par rapport l'cran +#define NB_PIXELS_ZOOMES_MIN 4 // Nombre minimal de pixels zooms en largeur (Note: En dessous de 4, on ne peut plus scroller!) + + // Les diffrents formats de fichiers: + +#define NB_FORMATS_CONNUS 12 // Nombre de formats connus (devrait tre la valeur maximale de NB_FORMATS_LOAD et NB_FORMATS_SAVE, mais plus gnralement: Card({NB_FORMATS_LOAD} UNION {NB_FORMATS_SAVE})) +#define NB_FORMATS_LOAD 12 // Nombre de formats que l'on sait charger +#define NB_FORMATS_SAVE 12 // Nombre de formats que l'on sait sauver + +enum FORMATS_RECONNUS +{ + FORMAT_PKM=1, // | + FORMAT_LBM, // | + FORMAT_GIF, // | Il faudra penser rordonner + FORMAT_BMP, // | les donnes sur les formats dans + FORMAT_PCX, // | GLOBAL.H si on modifie ces cons- + FORMAT_IMG, // |_ tantes. + FORMAT_SCx, // | + FORMAT_PI1, // | Elles reprsentent l'indice o + FORMAT_PC1, // | l'on doit aller piocher ces + FORMAT_CEL, // | donnes. + FORMAT_KCF, // | + FORMAT_PAL // | +}; + +#define FORMAT_PAR_DEFAUT FORMAT_PKM // Format par dfaut (ah bon? oh!) + + // Les diffrentes erreurs: + +enum CODES_D_ERREURS +{ + ERREUR_DAT_ABSENT=1, // Le fichier GFX2.DAT est absent + ERREUR_DAT_CORROMPU, // Mauvais fichier GFX2.DAT + ERREUR_CFG_ABSENT, // Le fichier GFX2.CFG est absent + ERREUR_CFG_CORROMPU, // Mauvais fichier GFX2.CFG + ERREUR_CFG_ANCIEN, // Ancienne version du fichier GFX2.CFG + ERREUR_MEMOIRE, // Plus de mmoire + ERREUR_LIGNE_COMMANDE, // Erreur sur la ligne de commande + ERREUR_DRIVER_SOURIS, // Pas de driver souris install + ERREUR_MODE_VESA_INVALIDE, // Mode VESA demand sur la ligne de commande invalide + ERREUR_MODE_INTERDIT, // Mode demand sur la ligne de commande interdit (coch en noir) + ERREUR_NUMERO_MODE, // Erreur de choix de mode sur la ligne de commande + ERREUR_SAUVEGARDE_CFG, // Erreur en criture pour GFX2.CFG + ERREUR_REPERTOIRE_DISPARU, // Le rpertoire de lancement n'existe plus + ERREUR_INI_ABSENT, // Le fichier GFX2.INI est absent + ERREUR_INI_CORROMPU, // Le fichier GFX2.INI est corrompu + ERREUR_SAUVEGARDE_INI, // Le fichier GFX2.INI n'est pas inscriptible + ERREUR_SORRY_SORRY_SORRY // On le refera plus, promis +}; + + // Les diffrents types de modes vidos + +enum TYPES_DE_MODES_VIDEO +{ + MODE_SDL + /*MODE_MCGA, + MODE_X, + MODE_VESA, // Attention! Si on change la numrotation, il faut + MODE_XVESA // que les 2 plus grandes valeurs soient ces 2 modes!*/ +}; + + // Les diffrents modes vidos (avec leur n d'ordre) + +enum MODES_VIDEO +{ + MODE_320_200, // !!! MODE 0 !!! + MODE_320_224, + MODE_320_240, + MODE_320_256, + MODE_320_270, + MODE_320_282, + MODE_320_300, + MODE_320_360, + MODE_320_400, + MODE_320_448, + MODE_320_480, + MODE_320_512, + MODE_320_540, + MODE_320_564, + MODE_320_600, + MODE_360_200, // 15 + MODE_360_224, + MODE_360_240, + MODE_360_256, + MODE_360_270, + MODE_360_282, + MODE_360_300, + MODE_360_360, + MODE_360_400, + MODE_360_448, + MODE_360_480, + MODE_360_512, + MODE_360_540, + MODE_360_564, + MODE_360_600, + MODE_400_200, // 30 + MODE_400_224, + MODE_400_240, + MODE_400_256, + MODE_400_270, + MODE_400_282, + MODE_400_300, + MODE_400_360, + MODE_400_400, + MODE_400_448, + MODE_400_480, + MODE_400_512, + MODE_400_540, + MODE_400_564, + MODE_400_600, + MODE_640_224, // 45 + MODE_640_240, + MODE_640_256, + MODE_640_270, + MODE_640_300, + MODE_640_350, + MODE_640_400, + MODE_640_448, + MODE_640_480, + MODE_640_512, + MODE_640_540, + MODE_640_564, + MODE_640_600, + MODE_800_600, + MODE_1024_768 // 59 +}; + + // Les diffrentes catgories de bouton: + +enum FAMILLES_DE_BOUTONS +{ + FAMILLE_OUTIL=1, // Outils de dessin + FAMILLE_INTERRUPTION, // Opration phmre + FAMILLE_INSTANTANE, // Pif paf + FAMILLE_TOOLBAR, // Cache/Montre la barre d'outils + FAMILLE_EFFETS // Effets +}; + + // Les diffrentes formes de bouton: + +enum FORMES_DE_BOUTONS +{ + FORME_BOUTON_SANS_CADRE, // Ex: la palette + FORME_BOUTON_RECTANGLE, // Ex: la plupart + FORME_BOUTON_TRIANGLE_HAUT_GAUCHE, // Ex: Rectangles vides + FORME_BOUTON_TRIANGLE_BAS_DROITE // Ex: Rectangles pleins +}; + + // Les diffrentes formes de curseur: + +enum FORMES_DE_CURSEUR +{ + FORME_CURSEUR_FLECHE, + FORME_CURSEUR_CIBLE, // Utilise le pinceau + FORME_CURSEUR_CIBLE_PIPETTE, // Utilise le pinceau + FORME_CURSEUR_SABLIER, + FORME_CURSEUR_MULTIDIRECTIONNEL, + FORME_CURSEUR_HORIZONTAL, + FORME_CURSEUR_CIBLE_FINE, // Utilise le pinceau + FORME_CURSEUR_CIBLE_PIPETTE_FINE, // Utilise le pinceau + FORME_CURSEUR_CIBLE_XOR, + FORME_CURSEUR_RECTANGLE_XOR, + FORME_CURSEUR_ROTATE_XOR +}; + + // Les diffrentes formes de pinceaux (les types de pinceaux doivent tre au dbut) + +enum FORMES_DE_PINCEAUX +{ + FORME_PINCEAU_ROND, + FORME_PINCEAU_CARRE, + FORME_PINCEAU_BARRE_HORIZONTALE, + FORME_PINCEAU_BARRE_VERTICALE, + FORME_PINCEAU_SLASH, + FORME_PINCEAU_ANTISLASH, + FORME_PINCEAU_ALEATOIRE, + FORME_PINCEAU_X, + FORME_PINCEAU_PLUS, + FORME_PINCEAU_LOSANGE, + FORME_PINCEAU_ROND_TRAME, + FORME_PINCEAU_CARRE_TRAME, + FORME_PINCEAU_DIVERS,// Ce doit tre le dernier des types de pinceaux, comme a il indique le nombre de types de pinceaux (-1) + FORME_PINCEAU_POINT, // Utilis pour rduire de pinceau 1 point dans certaines oprations + FORME_PINCEAU_BROSSE_COULEUR, + FORME_PINCEAU_BROSSE_MONOCHROME +}; + + // Les diffrents tats de bouton: + +#define BOUTON_RELACHE 0 +#define BOUTON_ENFONCE 1 + + // Les diffrents modes de Shade + +enum MODES_DE_SHADE +{ + MODE_SHADE_NORMAL, + MODE_SHADE_BOUCLE, + MODE_SHADE_NOSAT +}; + + // Les diffrents chunks du fichier .CFG + +enum CHUNKS_CFG +{ + CHUNK_TOUCHES, + CHUNK_MODES_VIDEO, + CHUNK_SHADE, + CHUNK_MASQUE, + CHUNK_STENCIL, + CHUNK_DEGRADES, + CHUNK_SMOOTH, + CHUNK_EXCLUDE_COLORS, + CHUNK_QUICK_SHADE +}; + + // Les diffrents types de lecteurs: + +enum TYPES_DE_LECTEURS +{ + DRIVE_FLOPPY_3_5, // 0: Diskette 3" + DRIVE_FLOPPY_5_25, // 1: Diskette 5" + DRIVE_HDD, // 2: HDD + DRIVE_CDROM, // 3: CD-ROM + DRIVE_NETWORK // 4: Logique (rseau?) +}; + + // Les diffrents boutons: + +enum NUMEROS_DE_BOUTONS +{ + BOUTON_PINCEAUX, + BOUTON_AJUSTER, + BOUTON_DESSIN, + BOUTON_COURBES, + BOUTON_LIGNES, + BOUTON_SPRAY, + BOUTON_FLOODFILL, + BOUTON_POLYGONES, + BOUTON_POLYFILL, + BOUTON_RECTANGLES, + BOUTON_FILLRECT, + BOUTON_CERCLES, + BOUTON_FILLCERC, + BOUTON_GRADRECT, + BOUTON_GRADMENU, + BOUTON_SPHERES, + BOUTON_BROSSE, + BOUTON_POLYBROSSE, + BOUTON_EFFETS_BROSSE, + BOUTON_EFFETS, + BOUTON_TEXTE, + BOUTON_LOUPE, + BOUTON_PIPETTE, + BOUTON_RESOL, + BOUTON_PAGE, + BOUTON_SAUVER, + BOUTON_CHARGER, + BOUTON_PARAMETRES, + BOUTON_CLEAR, + BOUTON_AIDE, + BOUTON_UNDO, + BOUTON_KILL, + BOUTON_QUIT, + BOUTON_PALETTE, + BOUTON_PAL_LEFT, + BOUTON_PAL_RIGHT, + BOUTON_CHOIX_COL, + BOUTON_CACHER +}; + + // Les actions des touches spciales + +enum ACTIONS_SPECIALES +{ + SPECIAL_MOUSE_UP, // | + SPECIAL_MOUSE_DOWN, // | + SPECIAL_MOUSE_LEFT, // | + SPECIAL_MOUSE_RIGHT, // | + SPECIAL_CLICK_LEFT, // | Il faut garder + SPECIAL_CLICK_RIGHT, // | ces constantes + SPECIAL_NEXT_FORECOLOR, // | au dbut de la + SPECIAL_PREVIOUS_FORECOLOR, // |_ liste car elles + SPECIAL_NEXT_BACKCOLOR, // | sont rutilises + SPECIAL_PREVIOUS_BACKCOLOR, // | avec leurs valeurs + SPECIAL_RETRECIR_PINCEAU, // | brutes en ASM dans + SPECIAL_GROSSIR_PINCEAU, // | Get_input !!! + SPECIAL_NEXT_USER_FORECOLOR, // | + SPECIAL_PREVIOUS_USER_FORECOLOR, // | + SPECIAL_NEXT_USER_BACKCOLOR, // | + SPECIAL_PREVIOUS_USER_BACKCOLOR, // | + SPECIAL_SCROLL_UP, + SPECIAL_SCROLL_DOWN, + SPECIAL_SCROLL_LEFT, + SPECIAL_SCROLL_RIGHT, + SPECIAL_SCROLL_UP_FAST, + SPECIAL_SCROLL_DOWN_FAST, + SPECIAL_SCROLL_LEFT_FAST, + SPECIAL_SCROLL_RIGHT_FAST, + SPECIAL_SCROLL_UP_SLOW, + SPECIAL_SCROLL_DOWN_SLOW, + SPECIAL_SCROLL_LEFT_SLOW, + SPECIAL_SCROLL_RIGHT_SLOW, + SPECIAL_SHOW_HIDE_CURSOR, + SPECIAL_PINCEAU_POINT, + SPECIAL_DESSIN_CONTINU, + SPECIAL_FLIP_X, + SPECIAL_FLIP_Y, + SPECIAL_ROTATE_90, + SPECIAL_ROTATE_180, + SPECIAL_STRETCH, + SPECIAL_DISTORT, + SPECIAL_OUTLINE, + SPECIAL_NIBBLE, + SPECIAL_GET_BRUSH_COLORS, + SPECIAL_RECOLORIZE_BRUSH, + SPECIAL_ROTATE_ANY_ANGLE, + SPECIAL_LOAD_BRUSH, + SPECIAL_SAVE_BRUSH, + SPECIAL_INVERT_SIEVE, + SPECIAL_ZOOM_IN, + SPECIAL_ZOOM_OUT, + SPECIAL_CENTER_ATTACHMENT, + SPECIAL_TOP_LEFT_ATTACHMENT, + SPECIAL_TOP_RIGHT_ATTACHMENT, + SPECIAL_BOTTOM_LEFT_ATTACHMENT, + SPECIAL_BOTTOM_RIGHT_ATTACHMENT, + SPECIAL_EXCLUDE_COLORS_MENU, + SPECIAL_SHADE_MODE, // | + SPECIAL_SHADE_MENU, // | + SPECIAL_QUICK_SHADE_MODE, // | + SPECIAL_QUICK_SHADE_MENU, // | + SPECIAL_STENCIL_MODE, // | + SPECIAL_STENCIL_MENU, // | + SPECIAL_MASK_MODE, // | Il faut que le premier effet soit + SPECIAL_MASK_MENU, // | SPECIAL_SHADE_MODE, et que le + SPECIAL_GRID_MODE, // | dernier soit SPECIAL_TILING_MENU, + SPECIAL_GRID_MENU, // |_ et que seuls des effets soient + SPECIAL_SIEVE_MODE, // | dfinis entre ces deux l car + SPECIAL_SIEVE_MENU, // | des tests sur cet intervalle sont + SPECIAL_COLORIZE_MODE, // | faits dans le moteur. + SPECIAL_COLORIZE_MENU, // | + SPECIAL_SMOOTH_MODE, // | + SPECIAL_SMOOTH_MENU, // | + SPECIAL_SMEAR_MODE, // | + SPECIAL_TILING_MODE, // | + SPECIAL_TILING_MENU // | +}; + + // Dfinition des oprations: + +enum OPERATIONS +{ + OPERATION_DESSIN_CONTINU, // Dessin la main continu + OPERATION_DESSIN_DISCONTINU, // Dessin la main discontinu + OPERATION_DESSIN_POINT, // Dessin la main point par point + OPERATION_LIGNE, // Lignes + OPERATION_K_LIGNE, // Lignes relies + OPERATION_LIGNES_CENTREES, // Lignes concentriques + OPERATION_RECTANGLE_VIDE, // Rectangle vide + OPERATION_RECTANGLE_PLEIN, // Rectangle plein + OPERATION_CERCLE_VIDE, // Cercle vide + OPERATION_CERCLE_PLEIN, // Cercle plein + OPERATION_ELLIPSE_VIDE, // Ellipse vide + OPERATION_ELLIPSE_PLEINE, // Ellipse pleine + OPERATION_FILL, // Fill + OPERATION_REMPLACER, // Remplacer couleur + OPERATION_PRISE_BROSSE, // Prise de brosse rectangulaire + OPERATION_POLYBROSSE, // Prise d'une brosse multiforme + OPERATION_PIPETTE, // Rcupration d'une couleur + OPERATION_LOUPE, // Positionnement de la fentre de loupe + OPERATION_COURBE_3_POINTS, // Courbe 3 points + OPERATION_COURBE_4_POINTS, // Courbe 4 points + OPERATION_SPRAY, // Spray + OPERATION_POLYGONE, // Polygone + OPERATION_POLYFORM, // Polyforme + OPERATION_POLYFILL, // Polyfill + OPERATION_FILLED_POLYFORM, // Polyforme rempli + OPERATION_SCROLL, // Scroll + OPERATION_CERCLE_DEGRADE, // Cercles dgrads + OPERATION_ELLIPSE_DEGRADEE, // Ellipses dgrades + OPERATION_TOURNER_BROSSE, // Faire tourner brosse + OPERATION_ETIRER_BROSSE, // Etirer brosse + OPERATION_DEFORMER_BROSSE, // Deformer brosse + + OPERATION_AUCUNE +}; + + + +#endif diff --git a/dat/FONTE1.FNT b/dat/FONTE1.FNT new file mode 100644 index 0000000000000000000000000000000000000000..c2fa61f9926763237f11be35343258ea558b6434 GIT binary patch literal 2048 zcmXw4ziT5$6n>avqeA!=W5N{XtU|>W2bsc%DHh)mOt{j84_pcpM2aP-I?ORB#vH*# z2qsksCVzm*U*Kv9VF-sXS1l^c;UX9phpoz}5aWE`oAq01-n=*O_q=^8lECepA7AV^ zalVPcJE>xf-sO@zuh_XJHn~eQuwa*Cjqxtr#VF!-cAzdXTwGj)D684~larG%*^ZLA zS)c|;V&bvJxm-#E4K7v zO&2s|u#y0a_BX6pDZl;W{Ool}{SZTtWeEI%uIn0hK>(KYzo-#c!i>AVgiA?kK}yZP zlo#D@cRD?kFrCe3(}4I1QP3m}WF_1@e1@X>W8AdAtZ6TV�@?IG@zDXTB&Rfqnp9 zafN#Z(V+E!D_22&G#W7kiCWeuPVdFZQO%4qakOHbm~w_s?kdKxZ`J!Hd z`DfrVPtvjWvSF={}F|`H`3fNau(LZ(!FABl~j5+%#>}1^vl}5g9d82;)7g z!trrrmPpf#@v5nPV^f~4O7*BDVQUh0MZ%1)o|rM@v@VcS47rwea9!ekVPQ)6PndFO zG=Uw(#zr(2=7)S)o19K$d-rsCdip2zAb@mQ41J}+*Ep?7^+;sqRSfb<1Hmz+ z?V&|IP$dkET;{X+^b+^73ISv0s8h-ZrO`Nn)sL~s{?@);m;keL(FWQk2u#I1Dm-SN zi07a|8vYqTH+M1Lq9;hR}_#}y~Mar3Rv&kbMk41hKk}|`E-})Lhb8$>rd5+Ld`OaO|_r= z(ouWz}mD#<9=*`s@%?7c-{heYWCpa?Cjxyw>b^r>IgHC14}Ub0YTz{HTD4g z`P08s&b7f{Fgd7?MBZQJoCEl{=@$7>g&HloBi;;>4{mRb;=8wx9ybD&B0e{uSYl{;u)?PypLL6CWNc_a~`=khvQsAA* Z^G@eqFn$0 literal 0 HcmV?d00001 diff --git a/dat/FONTE2.FNT b/dat/FONTE2.FNT new file mode 100644 index 0000000000000000000000000000000000000000..ba632692380f6ee7acc51019272f42dd466f748f GIT binary patch literal 2048 zcmXw4ziS*v6n+S^xnhwQBf=C%bj1<2Fk}mHOtHu&h{J^n7Ye9cgjrlH;VN;MVIzzY zE=({fObGf5ME(MiVmZPP%yOg%#}R}P#vCq;d_^!<9HV^S?CR~^zL_`g_q_L3qyfEm z{`_K3i#9W7jh4bWXLKZyHXds|bF)Y{dtkvT!rQrPd+nTv-rIw?ID2t%VV!IS&tATK zIU-q;Gg4boG#W{Af9L*(Kf5Z@dln~ha=A!VVaEnag^>4*?X23s=POI?~!0C(anHA$JQ(QH!Eo zPb$Ffu#U>V&DZNlhQA*sPu{)|UFhS>`dE~rFCr=-C`l9nv;%GQ0S{EElxN|Z%=Dsx zB$16ER7qAznonm7YeZ?vr($f-9lifU(qT6YPK{*Qe(l0gT(#^5;7hY?ZGj!+VH^BY zL-{n%cgas<{Ixitl|+Tu8}9%&Ac;8*x``x`e*fF~*~3)A?#`3aT3PKM?hk`C^x3M) zQ(4u+VP33cH_KL41-sSNILk7eKb+RJk;%lm_mhc8N_WPBp!e%~EViC6SG9%z1n@1~ zzZ38UcJbe3UBjJ)WgKfe9Im0ySUY=X0vXr!YCg4MCZn!JJPy}_1WOKX^5c~kxaZ*X z%|Gj6PwchUWANMQ80oB}^l2?c^I8%uClwM{GoKiFs#Q}g#^r}xQYnuUGRUJ z&A=yenFG8&#v{mpU0hZo$UYR}e1Xh^zMG|pA7#|a=P*M*Z2gpVj*QG4Yt??zKT@w3 zhr;reK3cObGsecM0uu zRjEe0X!y~oK0gT(%sdsyIO{=kfx3n(9v9*ZO>~^H;9#$;R^Uf|?v<}g85|zE`TQN_ zP!gcG81jA(Iuc>1&*P$voAya>;$Ys;DX7VB;6#!+u>}W9B+L1-o}w;sk2qbzeiIK; z4+i~5BImcy59iHubM7C`vlf;OUPfHRar_Z~Ofp$D_?G^$;}1v#;JDp? z?5w~H5)tMf__+{i^+wy=K=lnV;09~LHecM6h-FLP_6N}S9qj=19*{vE^cuqFMgZ^6 z?K$aGLq&1?+0$vR*~ebLKX2`Mu{ic>>BhF#-`J(0_WXvJZnciJVTt$qrUi;}xoqKX z3#56qM_p-$@7qs*)tqaC!Js^x`G-7jp@j+xD7riZSsT$SyjzAXVCO#iUY(WRI_I?%8# zc^;06~;Q4II>WX_=)QGxg+?g56nB0yPeMK$B%n**au**@2FnN1JPQ0 H+`Rq=k}7w9 literal 0 HcmV?d00001 diff --git a/dat/FONTS.PKM b/dat/FONTS.PKM new file mode 100644 index 0000000000000000000000000000000000000000..f61715f5270298753dafde1b19e8383ab0a09b3f GIT binary patch literal 38138 zcmeHP&5mWsQNDL>byv6Sp)BkH6_(7;3TxPz4J^!pB|>7ss%^;<5)xtyufQwt0=x&} zJ$MNgJb=HS_%b5Ty|?;jEYApfy6R@0JdqJ!d=VL$=Tz1F-QWD}>GJST=l?wMzaRhU z*MIP%)6Y()zpAgF{`9A-KRZAF`OoL&q5suaUmZq1Uw&rbJI=t{(;4gFe@w6poXZowSNi}3S7Ik9!IY&27q4;g`e}{O3Jnp!gY7*5 zhxC^1wn>asR(4lg~Z!V_?2yc|OHxwsfP(!I}7;zN$#e*gJ`HIu<&&Ek+IU_1> z(*}vxXHHU>2A8Fq-T+1>OaHn~tTg}hbmnv@GJE1NBLR|F%8A9*6K-EHAI$?B8m;t% zLV88TJ&p)*6c)$MIQ6U%Z({MzLS7Su<#PPsD4`JB`qoo;78^yow>jKWQWMv zw7=F8ZL2M0&a_(##2%R`Wp3=4|KdX+v|O0m2aXac))BAI<*d9_j;vq`KG)nHT1hf6 zgbo^P@$Ac99PJpwLK;e*${fyPdP$!Nqim9IvmPujq?er(Dx&H1QlB&vw`vK(LJ#bM zWUnY&dYX8XFD=1XQb{S^qX*qO^>RO{6V5WuX`JW#W=TnXv#P~6`cUOc&<12Gi}FK7 zE1GWSrjx^tk}DW^dM&14OqIxkDxilXqedYLV`*P1wpm(ihu@5zB3AqrKjAfe;hGZ{ z-{{}jDmjzrI?i;}*00;9L0nhvKn`;}j|+RFsdNDW_7A29Dla#$7T-;;@yq#NLFD`=1QI=bS1 z>2p>BiKhSxrmix`yRWt@Af3vFUUXmc7WPKWqTIcfY1RbN3!VZZ-KovdzGocy?D1)- z$t^~~QHLgHjfXZCqqo|aI^J91GWmAKTL)vt+sGxf^zk_P)-`64FJ#@VyVJjG<`jR< zmC;gTazc?NNp(D`v^iP}inL)4T4$CzTD+;MA?Xdd%>;Lh(puk%jRj?*bc*6!^PA#N zSh;i^tYq+5z;uT8f-6f1zGEfv?!H2ooJ%g#K0|3SMJsZyQNpO{cBivd4r z+BwCwlFatXe?md=-a>Be1KQ&vPB3N*p%K;??$*k(9E*^wu;fPaJh+zATD&T*b8$y3 zR+6bMXHmK%%cxl(DLhF^liE%yj?Q$O-nM0BuE=6Ydyb_|b@W$c#HacJ4B@d}nH~5N zwAIHX%BVPt7M`z^5=(oD7{jjGSCL#Cl;20$m`Xd#9{P(H+~2r6UVj98a@fd&@>Z*~ zT(Y#cW6zxA854@hp7F$O(#U)3pvl;n`3g{R(A!?fgXB5~x7rfF+DX?e8(4T+ukBSf z3QzBSwOll}>-sTuNrzD_mvpq)j0LI%#m+iTb~H=sa{d=gKL0N*g;KDEof*@0>_mG^ zOLA)fUf$k#Rcts(DV+P6?bf5A%Co(ekNx+{?3#CZWyOuM9j};RT!5LC@!DQ8ygNZ5 zy<*u{ON8i0n23TSQ{ipiKYE_)_sR7A0~3rF6Qv?Ze2~y)w)tEf*q(J@BK|Rg>zcDu zh}LkK*rs}W=yZn)9q_n@fJbULq-79rX&1`)!kcO?8oB1vBf7AV`R{9;=SCB6 z(vlAm#|~^$if1i^dsKoO{ldJwtn27aK;6#m?H=0OKD9mv2N;Djc7y+(){JXmBO&Zx z&zAlxCTSvUFpaWAIGeA}jHN~cDW+^2^ey!6sx>Uey7th_w4Dq$) zz^zsXrWpKC0;9E3q2R93Mc95KTK6%{54ai`6b2ir1WUXLzh@KW1~WFVp)1glM?V>NQeHVfF%;&NitkF&ZA>`Tx-Qs>KQVZI=JCUaCq`e|+d2xlsh^1}hVTgCoXF0_rB68HJ0pF_T z=q-P2-gpyux8YhzAb)DSGRbG0V^Uqt{|rwr=ih}Nm-C+i&iQ-%_)Crc45lyVKc~us z4%x@A723Wg;QQmDB)XV?p5YNuw8rAh(jKeTwzloX1f2kBNF#DKgfOjlyNuHa@=&g@ z6?1wl3$rdn@C!?gi_Q6htE< zc|^$840Yf%OoR&lbsK_c_kPh^T16*Q$gTwKY*~n$$SL7Xx7?V*aA;Mc<2W2r`DQ_c z$(k#N1VCkS7T$;mZIwW%fF75?7$A7aAi0}IN@=WG=@<(jJSs~}=14EjWzns|KZ<4a zqz#6&^h(ZQpMwoT$gNLp!`tx0Y8AE45H5*(uwt9s-w6@w?c~p^-UVak;bD2cFAou$ z?D)ix_XNRt)fVL?8wS&o&pYtv_%gZ;ViYMBHn;Q(j71a8!0TLJw^X){Uo2$>ZF0yl zy)y=U)cqJ?ixD8dQ`)^5T{$9#a_&cA8?b1 zdl4;%1Zkvvel8NnCQIyN^ zNSdCGaK_VSu?Nc2kK`bqd=Lk`S~$91f|;K-Jm&h?8V7xxejcw!x&_d|9_L5*?B5z| zo1H(-yWMW)rj0Kf)*~_CN9lhD=TTR#k8NZ8Kf+5@MC_y3OS!+|7ZLEu_fzce*B<=| zMt>jQl;%F&v%b_Ue_Gc4--DF(cCRf^2lDqvm-8ED@%aac5swwyL0xHtO^~&leWr+x zCCN&CzfA(7qhrESeCTr^}cGz3uYaBRtFp z-M;zZ9LzbloDv`MgXtz11S3xH$wXN3So3-Ml@xeYCQ+XBP@*59X&V~&h{e;gZ!&x2 zOJ{`UD(>$gA)Glqr)wYE2Lw7P=nM0-#Z;DQN7|mZI#euU>ch25BCqrV^*$KNoGYl z*N7IYDpmJye>qPkVEfrT)HRnGa&G2(c$j0~qz?mH_I5s05Fy5u@ctpU?kHImh1yma zK|ShHk}%*xvh-GI$UcN=a*UfrA7rN=rDzU)lm64?i@yNWhcC`w8z!CRqN)~f@YVj+ zxcp<;gKH~lbYlON`H0N`k|x+-J^cJv2r8u&bdV&j!#yJ4B*3WvxpasKh4C+mbt`yb zA6l4HNkNdWAJJj<2&@yA;S8J#Juxu_FwB=iby0&$7$OYpx|X2T&z0)oeV2e@lmaS* z5}M(`42|^hlisW4F2iw2;h?mJDO6;*Eph5{GQ(pjUf#%D1FXB2*&%qVmVrVvawljex|GCmU>Zbk|Sm6NSEno%OaJCDx8_O zbPE9y$4`aF@?`YDPz9@IMT@!ORq&;qOeu3?$NYyE#X6_)14oGz>xg%Z6!}Co_qtuhOgNAP-CjFHY)HU-g!DxDc?) zpauCz2~pbRyA-$O+z;EPq*ILIMC$uJu3>I%TUCp1^r6ZXhhiik`g*Hq zMH3mn&P^wWv@r{4fIkyAVdIo0b3zLQeaW=(v{^v?z!1 z^OzjYVR`!{HJ+q~xrR{*|M<_KX$r33qO)c->(B{L7U2m+m-lQy7 zk@PW@Ko|hB#eBR1hVB<2(kHu@vq!0fp3p*=0fhlhX7y{g@2QX*` zDl>$hNmD2=HX}`UsGRcvJG4YA@0ng|Z(ny3se)3L1_~M{8Vq6%=FzEMZMr)+q`2jj znhfiDA;jRwL)xcST|0$$tW6!Tw%E%q3R1-h@hoP8tDxYLU+~R;8m6qX_DPv$+2DZ@p(Gj+Q%NYs?%G_^&I}1V zy!3Jp6~hMkxhP3KG2>e;;V(ufhjQbZLQh3V>}E-2l$Ug|?mDWx35r*p*3DkUE8!rA zFOqI?A)h=_`+DGk3^qOnkGpH7j~MhteU`B~c1@Y4$&$TF?h^=&lvfV3$JUbN{#~;K zLVYm6nF7Wp8VsXE=qMfbU@6%bPu<#_AbfnoDtoP)TJht4|JefWV8uuh5`Lwl71--> zu4(i&UFl;8qyzcDz_FX#$vQJFPd1gF=Ec4DGxOFxj^)1Fgupt=W5_VrAdS3bO5DtN zre<8r3)70l-IEG2%|w9x2oYG zY{2SpKzX^YVE`p0@W}@ewn8Z(aE3AVrXz8PZPcWVI^1Jz@9EM{o~d_D>%i1~!yr~p zzXr9%CegQ4dP^5rh^f|(J%Tbbd4M46bLrlQ@GzmusA;CVmWCxY9=ONk+`YJ7N7T@aF9{@US(aOZOV8i0N)f9(L|$`X3%Tn_vM zXI)Fwl^!2s(g&Auv*%N?X*kY1UbjcvnL+v@Ye=0@v3IwX3&c=Zyc8HY zofx#5yoR{*nXc6mk@#XTp#ooGL(cMCF#qO(TCDcEN#+!lkUcSVC!iZ9}_}_<=rCKq%ZnSxA^Iy1UwzafawNlg`9kwUj3~ zK_up2KeS7);s-E(NYV}59vPo~qM%v{yG~lbeWhA%;^>1Wa`L0)12qfC0o~aMBi){oyZ+3L3 zCEOK|ka53NUR}w{lRnGQGCiYi^g5TsNpKyFtZd+9W)XE9TECx4K5~YbVhcB-8BFkt zjHoqv*Lg{Ke0yu5IUg1CiMhHRwP`V{wxgN@L8>vD4`)->4-V4d)D3D^Mvhbr1|fs& z@jBz=1>eL(AJ^_FRhqP~Y?_iZC~K`0gc_zFzwV@BFhKaY__i`zeg$IMHLV`9;_@0l zC}k}Iq+u)od@^!OqrD0s#C@jn(^RW$o|H>p%0Fb7eplHz z^G$k6!Erp-DcXgHHGLJMmowejKlR+|-x_P1*E%MS%uU;P#wt4!!$npn0sFGsIO@vv zv2BdQ7GF2$+d6OJIq*&S=$`#sV{LQCd~dvU1kb>FH$AOLv2O&F?X zo%Kbij%bjWwjBVn0;+8ILC)pOC5V+xu$>1WP{UB<4%_`v+`g4gLa5w%?P=483Psqd|AS(1#+(?Kn`Or&%-<*#QVAvrGG`RS12CUEv z4uE*L6D#s&;$CXRz2t>|q?j1nvQkKJ;$Jv(+U#_wMExe{m=1M%n2mZ!Ew@<#4K;Q% zSEwaL2~{1pJbJhW%~!C;96s_;*Gk)P;W^}&JbaV&u+8P0a(XdVGSV1XrkD5rxw(C2 z2o(bPq&|PLW66r0ULjy;XybmPWM3OlMV0TU_#?F=8IY%sw{P7Nf8W^nQ;3JtAOF|G z`HVjW{uQiXLpbB(krXqwyncM7kI#?Ky!R{#HoW_6ITtqVd78)T=gZ^exinlJAD++p zfGT+LnA_d6cq_U*lLSDJS>K(X(stqq)Ln=JO8M-fq_zw!fg8oSM4x#J-}Cp zogeL`J(iaz&jtyM1vzM_^qX)WpPwIb7b0xLgxC&;)Pguww5YNaJ96^I=_3N67xpMk?ffia8UBI#F=TMzOs65!PRX`i zIJ%vj(zwv6=NV8Qr)OL>$N3>7z#s z!~B((Vy#BpAL|DIw(RDb130R^mE8_>r4Bj63T5i3wsj42^zEE+S^}(AY85%o0R+cM zZReTalRWqRS$de=!l-L=phSg~Y6Ai(mAbZarht}oiA^o zTkfTWuh5aJPiyxQ{b@Rg_?@?(cg`Pta$V6$Q!={6j)?Js=uekPdM#3*M2V@2(7kfH zGMLtDMb=gV3U$x9;OsszF;`(R$G5z-+^stvd&k^E`ocr4M1;>lL_Vy(6W``(H|g#^ zB$?>77TGV!Y%I%DCbv^i{n$ z?kq)s@sCsW2^-}5vv^YwsBYRT0#ay7Kij)#BBYER+#S>h?jv$*req9L7s|Gs;~SY+VC)v(O~ULYQQ^?ERU5Bgk3mQqy@<6D-MzXLdBl! zO$N{xbUDBaB(;mOQ`K(U165M7t&lu+UUBIh;c%C$nr6d{p9YZahnGl6i@edb7 zg!#*df_|M5bO4hGixw+U7+3c3uVQC7WP(nH3NdUZVS&dv&ft=)46(1pHD}WRMKsfQ z8CvvI3It@8LM{!ZLl!dDw667G4%97mG7t)AhQz|8jQJDddtnd(+!9?;tyzljp}10! zhHq_Ny?XB#+AA4tg16;Ul(SiJuD!U@lG+asz&5V#f48=Gm-D}q&CB^qGI2To5uP>P z;`?ilf~8+FdJau3Dw0-@S;hiNxY#NifUvHSgV&=&_7TsV!1@HhaFjn8#WfO&e~-eq zlN#eAs(xPUXCX*Eot~eb`4$IH;7A`l(jyHa^7y1DQfXUV=s-&I`Bi$hPfymkY;L6e zQa))J*-HXvw&&^3tHK%N&+8E`0OS%r#RNam#RIxcgVrbfA9JXePU+PYoT6tnYUlBi zK*fYFB;Y$f?G^T@i1{W0TlWbZ=R``3wD#9`&K@g^hH7BAYH*w*3JwVEI|6e0ur5E0Ptdq z#FY|^*D&PdC@adOL7@i;)B+YD?h&U)9YtL}O$urtpr;0M0gr7*TY-I7*Og%Kl2L4j z+HCsT-YZU3r5G`nDxPckOP-3Vqr&p0Bv5eog2qZII$1d2S|x>aJMS&wsM_Ju?PbN1 zi^^u%T68x`znstVkSCg@n!YY`|J!e|z5Ng+_;UU+KmJ=Ml`aKdAzCq9fMlL5p_EmR z>zv|rqzhw*bH{@ww6;~#4}{TLa_@{;j!_YE6v*%?CL z|GSc9W4E|p(eN_Xy~-ODA!x3r3ffhdAKS1b3Yzd-PH(geZ&EKgB=p>NV1ybTu=-Ts z(1Q|sdu8a`QVtd#<`+Adx7Glqu7si5$#-6os+tUM_n8D!;Gg;p#M;~8dfNSv; z4tN;!jiahodaKulZry#4V-=~kxI(ueF5lYF@W>7gkC;rapFiFi7;XdKf+unWY32}! z1`jzZvwt1zTX;G4X--||*r&$lH4DM;NC)4_Gv=cHSZ2C2Ot;Osns^Lc<>;2%NjT;K z%gl8i>3_qU!-(^sOl-SS~8cWq+KSaSn^4Nz#X zQtPA1se!9;OSG}}r;5N$YG90Iuwr&)r3dsIa8QAlQ9LCM;;y~Ydy03Hpv}80=%3({ ze9|rk)mI9~R@EL{O93H0!vFCYdC|-*hqmf}Gf*#R|4^qCZzEw>o6@~dwYlzHyHx?Y z>lSOJwmN$MTXO5AjBa1LC$IQCaxCokqooDPwac`4k6Uf1d!HDvD+N7pt7pgX9LbZ_ zRz%hsxsi#kIjBK*Jew8s>gWVRYmMZHl#`3#|WOMVYLGEk0>bIUOx5vkr{G(zL}{Xe>cCkd%OKcE2arILusXkk^bJgHTz2p zp3VNvXSLJ)J-}I&#T=Ax@vMHx2xJjq&e7Rla22ub4qpG`?){nYV3!99a(n!qUd#!z z-`iqbdBaylLRb6iN*N9Is_NdY0(8QO%J0UKq+>d>YppNk+7Y{RrG;kcpMCs(qAKUe zIJ1YTIq$Rs37dBquX)*M4^FQ!kOz-;vBFN0YJ2(s(r00xeVii&8ii`Dv!<(#n=hfx znP&Ik^a_zxscmk%CrclL9T54jg;!?jA)kp`CKhnHV#0J20&r`ceAlt7j$Z_H2mXUL z7yht_n@l}PyYH&c<0WqJOliG1k!6c2zjPo2xQ%i$iM*Tr;NHjgEeM!N7BmKbL$I3VnJdbGCSwid;`XovZb#Hgp6XxAjZ_m(=irfp0aNsBul5sYtoilsy2`!+W`$v&JO|KZn8gj*W` literal 0 HcmV?d00001 diff --git a/dat/GFX2.PKM b/dat/GFX2.PKM new file mode 100644 index 0000000000000000000000000000000000000000..ba52ebe587bb5fb0a8c96f4982e640ea78053363 GIT binary patch literal 26703 zcmeI4OOqT~me+5(dxS^66z_LL##D)t2B|6al)6eiCB_nl2BsN?R;wgsW<+FYH{1RM z^sr%-Qfb8oGd=-^@c}Sn!2*m0>-h{UFk_!)7{C9y_j-6lWR_AjV>Z3$&I*6r$2tG= zKaYFeBh)Yc{4ZRRy1jdQPXBwvpL_I32TomGcJ;qg{<^29I@pOz{`dU(^JmYVJ$?H0 z$&)9KA3uKh@ZtUY_h+-&cs%a+`|WnSUaub>9_D$Trs=73&z*bb+*9YCIQQ7OhtA!1 zZsy$BxxRC4=jzTKI+r__I(K^No^;e+Y)^Uppz`QnQae*W^y=2u@GfAh`$x8GJwJah6>S3hhClhkKl#ZQ-~Rp2fBs^I&!_pB!d`+;u9hK|IW62eVmYHtWr1liBRE+3dk=_INh?>1_7( zZ1(MJc1k1>d*d-dPB8Dgz3dy2_bA)RAs?g}vu z-ASGz!e%mCXBxxVl$G)3c{1F$PNae?D9qpn#8m@kR(p^+3hmDXMdYOc08Kqj$g4~8vVUo-$J~nOxcrvUY3Uwwh$@haY^k&QyeDo_)Y=GyZ z3_t3&sjwJSAT!5bf)9G=^-i?zI%L&N5(CTtovq6ag%Auy6GXLu}uZ%=8dm+Gv$O&<^@(&BsQMFs<^-V8|&8i~9hDl;<(E8nm- zf_qOR0?Nr%O@=my`9^jCZGo7rHOL6L1m}1(InwOPSoY?GF;V-LEwE6wgxQI!1dm{p z0KnQ0+X07+@Cdf;Aj=~E2;QOVZF4sF&kz3@LNkmJKmRq*H)>3KEMqkC!7RRlPPl4yi?HDcXF|(0s{KE_m09R7HzPmM}_i;2r9cdZj2} z(FmU(i1Di%Q;Ow7E*iSR0+B@%mDkEATI|vbz<@{xiUi+#%-cXVX_3}UeKf*y+wQjg zLCCta5YE7TW(6Z;L$$EMiZES@C`7TiwStCq72C4GOwgLlcr36hi$!iN%>qUYs2RG5 z7o{ZwxFZ!jK{Rh=i8mlRY8VXpzBc$s!m;Go;){I-;#D9E*qSL~1YOrVunYM%G8rED?7~@aj0fJV%ywi#7~7z$7-z`s-g*gY<1JB*VO)&ZkZ8D{)p_%v`+H=Vj*{lD z)`Lv5rW75GK$6UWem<)G0;pkZT-{%Cm$;wV@oP&LW3@ck7MdT}-CCD~ZjIS)VuR~l z1{!g$53~F*?SXIMIPPrYS&V94nOlFo+q%uI$uK=t=C8-gXyQ&aK)EckxU@T#RaMh? zTOrtO^FxCgLxHiJRp=M64isB)5P1^TF{#l4=RX?G`drjJ{1UR>kML>@aD|1)%fO5H zSRj1lvpfI={@0s7rC?-9+d51oUIJ}iwG|IpX(O3@5a%cZJrm@n@+!)r01Lip)v`z# zw~zG;gX)ZqG53Wjtlok2n6H=@DwJ^n3auHmqE4oZ80{~Gn?5^eg5T8mHth}}k8m#l zDx0+r@(z=4#7c}bc|5MJ5`j6kqln`1mn3@qT6Dca^JA$rAR|7}Ff$rf_?Jo8958{{ zb`f@q;9#^N7xi94-7g9Bi&iOK$BrhkNekjJRxHWp5N%q3j3|j)8|7nfZ4i^xi)2^` zK3!KG!HeO;IBdcnOrZvOmYFKWwFp#?b(Nqa+7yk}z3NP1M3BLhbtu_`os2Tjg;^1V z_R5-Xy*p;bz!O^NhX_Jl=;Rv|5@IvbB{?Ayx16TL^`HPp(0Mi_9!Vy&pxB_>STZEI zkJS>~S`G{kl@fwDO3KaP&xP}v1Zb@WvGzjzvm3A*&;D98WJmPHV1IAaV zTP*~W&-JP}3~?h#-a=f(bJrGR{_>eZeM3xIJo?#w+p_l5wmIIb zzJmJ_xn93S-L5^RSbp&(0D`?Wp$1qjr@OFDDPc5JAkKX87UT zwGnzurl%YlO4b#m*o7sdghW3@m9Q8M6Ko+fPY@xpD<*@?@QxPkESkY18jL8v5Cg|T z&L-K_dJhhl!Db7#(lTuRi(zB=SyYPxi+Q_h!R;-Gu^e|)>*5{)15jc`_z0?)h<;}j z+@(GrYZh>3xlE7?g56=8Z!&rB;v?+_F917Opl}5?5-o3{1t!5y^aiXq*=9oAe#bK` z|L9F)lyQBH>E$iC-(>rv?-J9SV=M&9O%07`VUwzj_VL<-7jKaB|6>6K*2FHA15iO} zuoCAREmpJ!sEagf@el6%Nsihjw35?=Dug^uj0eR4Cd;Uzx8-`&%g@89%rUJjMwJSSQ zmQy?VZalvq^c5Jw)WT{n8IJUDLH=kw$y;a1s7p_QgjTJMw;~}Iv5eUv!NVy!n&;Q` z-z^}Lx@wvM;0po(V2@-L7*w_*0MTN*bnj+M01I^wL8bs9SVT$q1Ts)+-#YO4AK>r? z)`wJtLdICe85)J9f9jHMD@s;2ZyN9Y?oYvKvANT zDk?(7i(bDdez_Acd;AH^S%ii#RnMp7hhAv;4S#_qGe;@gj2e)baks&d0H6i?b!l-0 zQhS(;7`J&b1HG9XF^jTDcw$^|FbO5QHzKCM0)2j#oCY)gMxmw3N0Sd+C2~9^7B`CMBk`(o9vyQ@jw7jI; z=%9RC$=)d+ruz1b+40D2HCztW0{;m|MKqMv?|fiFa{cd9SK;)Z6Zh-uB>zuPuQNoj zBiaW7k6U?7e%9HymX7tLzR$Q)3kV?1&yVx6AQjda?W>OuD}SBUr66|tAsml+mfdXU z%d1c?)`DzuiiWRvFgyV}l9|SlrMEa@jn`Q8`Y{}jlKN3;mc9^`7LqUu3X^ko4(^Z8 zGP_n^%|dfiP1WZ{saIb=BM#G90uXch5EAnlKMQ18!KqV!F0oxGz#7m4e8PEn?)H>L#Q zIH;iU*t}E%5c_QVrg2h#Ec#MhZMsntbgMBULAzlPj>L`8jC-x{p@Q;aN54nJjIdwy zTEgB@!5 zNE`CoBj2XpIEAM>hzJR!*+Q}rZh-C6mE8D;Wn`3BE0SSh_5(oQL(2GJ>JRg z*rjqU($=7Cu$Z#NF^u%!n5DOt8mrYq=p_$)DtIt=phYB{)Nd2kO}>XW>;(hm3F_5m zL(J`H@(ocHJ|wP;R)5yxj(M)s7RFFx#CJnfmZyYng@d2$)oQFgJq2+pi%PhEY;lRh zRTv1daMnZEMuT;bJ9@5HC@PIgi{$W#G^xh0h%Ssx^+&fi1bpQ27H$uZae#MYK0 zu6}XN?~CqTCwr{cdm^L0zTT@U*!QZmD5LgNd-g!T2c;Ujr@}yK*sCz_j}i7ym7jaZ z^yte*%_M@3UFlvzl%JZjx2JavG~{k?Pg1#&)QIHgNc?BlHs+`#Vo$|rzwR_ev12ke zu93?S^_bWIHh^}|==L!GxV^0H>=hrxc0;9p9xN!~B1<_#Q$hEfS={XEPK`AEx9n)vZ#vPTs1!JM0! zhLR zp+s1t*AC+^OmJ0#6&Bu#fW{Uju0P@liHtML{Qo3S`mekX$Yhj|xkVzGbL9jrewHq~ zp%jE~#rseELh~zFRZ(D-wH%Jq6*QCza{KncFQbm=6ZaEaU0;A0sniKYXGyA6sUS0C zhFB}7tZ}go*Vda~5ip1>=RM(YYbm)EAOQ@ecd2k?EakfPSIPB%Ox)``y_q6Q%j1}Z z$3E$Cp*&t%x!0D|9>-Mm^(Yr^_Kz*_CMmFl)_SJm3I9Qob@IJW0H z^k{vwpEznXyCA6wZv(Wfpo%4oCKG0^wSmRA!@4`7BI(TA<6@-W9ja9?qU>D~1ImhR z!>$OzG?QsYuJ5(-#XfD{sN80_$@IHUfAmUpt*`WSS3LWQI(6tpA4eEqr40Huz!;}O zFQQ>(>mE7lP6-?wjBO7xrWi{A_e zDC{6?Yhhwaow5v;q)(`+O#b^*yOtw0pa`Nh6D5N51x}c+$tI~l!R9uCXHRhB4OW!i zN|~=M987umGWv$7SjUQ9BeBc&bjihpYfOP)oOj>)hkGJ(^KOF%fjAT&y6`)&7?`-< zYd``Jj2gLt=z=SsC?sysuh-%c*{#>*SYYdTjh8H0`4=q*BmE`M!dz%03sqXkLS zu9xd_iF$6oE+>X;@cJcDz=9g(a1=$T8a$J$sIrg0Llf_G%z9=@y}jbO@lteolget5 zPOH746t6M!#U3}I63H+A*I;m^)kKBKYc-`RQ(ouhl`nT}L%fyoY+r7V8xMY=+bSVy^`- zcJg}4U~jL7U^eA?ZNP%c+XBbF7s4GYHm^Edjnffn&8fk5Zu1X+XunruYtIQW2v1z& zN6Fq2tz97xg`l&|AZOqO@lx?O2F}|njOFSQ=q)(?ksLI5Qrz+g2`(?Ak6S>2h|QRzVW+* z9Fui>WZo6drkEWpcO%JcR!rWGN9&h&;71wy2qc0aMA)4qnY0^Ix5xm4e~bU4X+g{m zLF+928=~=rtmZ92kwYQ)WS9 zTrZGpZ+AFb86+#Phkt~I*s>xuZx~tGw95wru^Sv`^lj@2Nhdo>YD!|!_%U-zig39W zz)+;jk|M47)iYfzZ)GF6E;sl%xw!^{(fn`RYvl>$BFfzoyN&v`+>j4}ZSiGswIle) z0+vRE`(O>BBR6^)ek5FPM$9{1#E;^YLbO3nzNS7J(KLH|$)rzO3{2He#d1 zbyZmB&CSugp7F7Aiv7@P>7lgP^iW*>e%Mg2ES9MvlgqM{5qHNVb+PZPJ;w%rp4oK>ZFd8T7WjIWSlMpf(%LS*i? zAg?-3j@!oDfkfiha@6vPAU1>qRClH#P7d>Ujb&bpe)%}`zvYR3W4G(FO;{0LJl_rG zu8iN$+vP-@{#af#cXMOqvr-!$FLNE~b`?@Zd83fkMoZr;lEr>Q79K&_Rne-=S9mmy zDaO~%wq4?=P2Bppwo7^?ThFI#?(`(m-YAhc}cGtEj5$I^kd(p3L$lT>gR z1+5K_-tut7@p_TqMl`GuMT}95cZu`{g1j_sll_n#385hhh|#C}NS*AG;59W~+8Rcb zzI(QL%w5}X_qo!qk9Ob@pUxlGE91qekn2m-Pn*3t{%#uA`aT`)kJDGS>8==e=EMgv zeG{m!NA)6FzT)eC``G|*@BK~U{+g8JjiQa>3CCV|@~tTut>+zHQ#!o>{A)gXbmILW za{MU$goN+%8O5+Lir04)J#Xj*D?4n>9((pGjl4$he3Lb^4bWyv{?SjkMQ= zrIGr58}bNay}>kee6z#v6&YBT=;b1=TG(kfSP-{D<((SW2-*A-st{xT9BV+)>Wf%$ zD;ZmJAoqp`maRcn`K)rXdE;9|ZTfj(Yu{MuD_C7C%JrzZ`A1`@q-7Awj?(?k{&u|) z*%IgX<>kp(C`b}$XR+h~=>cjJ+>WrFhFxG=ExY_#AuSnmM?wv?2Plw4YQ#;E+rqs` zsTJU&+!va6gW<+$^2d(ZAqFCc;ujYX7``yD>~6{0Z7BOh*LNUlBM6vtN9MF{D-2ce zn8MExh(BFfL@Gl5F2c|N*$U3* zwBX-OlTE%Uv%jx~&|eRxc^2wU%>bDJBW@okGg#m_g|Aqs!4QK2Z?K2ryF&z zy1l`eng8V^nPlV9h<^Uh6?!RST7Jy5pLDZMhjAm}`VUDfZ5x`_)TRu3Y>bnher(b7 zGu$ZYrkzeZ=~QjjlxhENFiP4fb8TuJZIv-U74Fs0tu>*Klc)WwZii8wZiiD1mHpvZ zliv-KQQA&g8J#`Zd5ks5I309)d9Rn}uX{sAX)zKzsjNymSsNkytv2&2o&IPdLH~9% zh6IU9lXliIS%=BE+V5aQ1+$^E5FBNBjl@TIL9W-^)9#iuZ`K!r~ zv3l9--fNF8%B%E~PR$t2WMI3NJY-JN5jR(o$G-vU_15C56I8c*1eA&N z^d*hFFIW==(!ZWe76=%a!SZaUHFZuhhaLFqL(-q4C^eN*wM(VcLo!nVg@XyxnLdBYwD-3g2&& zMK+(0dZWn%>UfvY;Ya&okT6!-F)4cFfLQ3X2mH!wG{SRo!ohSzq>Ys{$AiIegl80s z!(?Fp>|m6ETVXj(Pfn7Vz9UKo`k^_2q)?q?^du*lb={jUmdmNa1R$hD=O~AAi?z`@ z3l721Y4>>s217PMnO@$ta`KbHL3E(VWn%?di|6P55ZZ{5tkr5Z8)VCg8#j_>EomJm z%}TqgdX=}6#$mJ3XwsoTYj^uJ1z2{+iZeE z6=Xaf_LX`^(wt4ZkS0Jlt=b1N2?7ARY9}P5K<(!QbVZR}F^YV-CVaZ2XrGFiAzuOF z9E2WVEz(n59nd75d!(1>!JtZ~MR+$wim%+b^dxog*ghs2C={(~Q+SA}>|{Ds$e>1^ z?v3Fvg5n=A(UDg{Rh8fTIzu@1ZK$Eb5rQ@8b&{^|tLS-TEE^*rkAZd6JJAS+9JKoj z)(+_cJ$3X%4-~W%a=<@>h^m5{$SASjRxJ$OVSJZq*x7z zBSb_`wI+QZ&>eOTBiPAFaW_f2z)yRVu~6Zsq@yyPEK{=f7}P4@Qs3$N>RyrWGlX_NRDdfJtOf#T~T{Qa8PMcDvPp5LT#rs-st(tGt&iD)W_FNj#u{Hozl?jS))&y@+$OZn=jX{)D)#upC1hL9HkhKd6v|%G zSLIFmhl2swBDl$PG%z4|(1W7%V4+-a$KVF^B=ZpFLg4d;&N&{DrcWb>K(cA;8 zG6$q^EgrL^UmFaPzWyC%U~*<)Ap!CaL8rZ?A;s`_@7^Ty^y2*7iM~tyQ=nCLIS{N? zO9~i?gzO1E zaPA|2xxBobwq7(|v>Gj7Ru+qK@_qXLUGhE^&hcvX7SqzVZ$S&n7cZL47Zk!*1fii+ zG00ZvxD+23Fu1R6Sw9_U`w^i2z3GscRLBDOs*=2`o-ec|QWX)jOF%4_qYob%jSu=0 zjfhJY`3FIzRW0-R^uvemKM3CUo$ucb#5m-?g?vc7!iHw+B`($;rcZ1nD}I-nnx40- z%jFz4jj}9RW@g)~^Yd3PzI*-V?EE~r zs4yxyOW(Zy?!_ybbazpi&lx*kLUXd>pJ%E>o}V?q)qbhvGV7n6$qma(6RcWAwqITn zg(TvfJvq5D7z&=g4Hdk{?A!a`%X)N-#;W1U_pE<4I6pfBX0kd=E?ET^^EWSyyatpF zjW(XbUI+`KuG_7#0-a^_AG+bUY z(8)Y|gTK(kr+TqiTmb2EewH-$&5`Hw;p{OI z43bq1X=e;;5yrh9+Ox~~rPelKNS7oFq8(Xz>4*aRtVE8!(>F@czq}xy3%rzEq;KB5ddb7d3(CIXSe(B$ zH#LaoS1ecfbhVlXf@RT4Igegm&=@W*7horBD+-ZJP{JP=MR5_fU&9fQGMq6#2bRPp z%UsWg=SYSavCJBzb<{kA7BOhGPX%THbd^Fb@wS#eN&>OD$mi#B*1;=yIzM}@m925aO$ti6 zxynTO#ICZX^qhQl$DOa4b7m8aUV}`l^EtTX@lph<#)qp^Fe&d`zw5+lG zk;lvtgNSCUMv#FlQW1YBDU^01rKqu?{3+m$?8 za^Rm@MvG$e9t$0_AWLck1pr&HhqF5?$y%qhUDBSyF3j(V-1X3FLz(#pMT(!e`TvC? z%hqs}8MAMtTDerZBeP21LNeJUO1fHfk*tn5;%*uAQ0(J}V2~*+>G&lj>j-Ibh4LB6 z`u7?O2{Vqv7D^VHXiw9x0__)g(LAnXm*=(F&sZf3j)18@V!h^hX%L#!~{Zqub wsy(zd@hD^o+&_$RvJkh%nsJAsAn2tWqCfeDLuMa~VRuhbC26U_{{8y@2M2+ stops the program when you'); + Ecrire_ligne_d_aide(N,' are entering values. So don''t press'); + Ecrire_ligne_d_aide(N,' these keys until we fix this bug.'); + Ecrire_ligne_d_aide(N,' - A few different key combinations return'); + Ecrire_ligne_d_aide(N,' the same code.'); + Ecrire_ligne_d_aide(N,' - A red flash appears at start up when an'); + Ecrire_ligne_d_aide(N,' empty Zip drive is found.'); + Ecrire_ligne_d_aide(N,' - Some functions aren''t finished yet.'); + Ecrire_ligne_d_aide(N,' This is normal for a Beta version, so'); + Ecrire_ligne_d_aide(N,' don''t worry.'); + Ecrire_ligne_d_aide(N,' But if you still find some bugs in the'); + Ecrire_ligne_d_aide(N,' next versions, then we''d appreciate'); + Ecrire_ligne_d_aide(N,' that you tell us what they exactly are'); + Ecrire_ligne_d_aide(N,' and how and when they occur.'); + {XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX} + {XXXXXXXXXXXXXXXXXXXXXX} + Terminer_section_d_aide; +end; diff --git a/dat/HLP_GRET.PAS b/dat/HLP_GRET.PAS new file mode 100644 index 00000000..7dac365f --- /dev/null +++ b/dat/HLP_GRET.PAS @@ -0,0 +1,67 @@ +{ + Ce fichier contient la partie "Greetings ..." de l'aide de GRAFX 2 +} + +procedure Generer_l_aide_Greetings; +begin + Demarrer_section_d_aide; + {XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX} + {XXXXXXXXXXXXXXXXXXXXXX} + Ecrire_ligne_d_aide(T,'GREETINGS:'); + Ecrire_ligne_d_aide(N,''); + Ecrire_ligne_d_aide(N,'Our best regards go to...'); + Ecrire_ligne_d_aide(N,''); + Ecrire_ligne_d_aide(N,' Access Filter Pink'); + Ecrire_ligne_d_aide(N,' Ace Fiver Pixel'); + Ecrire_ligne_d_aide(N,' AcidJam Flan Profil'); + Ecrire_ligne_d_aide(N,' Acryl Fred Prowler'); + Ecrire_ligne_d_aide(N,' Alexel FreddyV Puznik'); + Ecrire_ligne_d_aide(N,' Alias Frost Quick'); + Ecrire_ligne_d_aide(N,' Amiral Gal(GDC) Ra'); + Ecrire_ligne_d_aide(N,' Arrakis GainX Raster'); + Ecrire_ligne_d_aide(N,' Avocado Gandalf Ravian'); + Ecrire_ligne_d_aide(N,' Baloo Goblin RedBug'); + Ecrire_ligne_d_aide(N,' Barti Greenpix7 Rem'); + Ecrire_ligne_d_aide(N,' Bat Grid Rez'); + Ecrire_ligne_d_aide(N,' Biro GrosQuick Roudoudou'); + Ecrire_ligne_d_aide(N,' Bisounours HackerCroll Sacrilege'); + Ecrire_ligne_d_aide(N,' BlackAxe Haplo Sam'); + Ecrire_ligne_d_aide(N,' Bonnie Hof SandMan'); + Ecrire_ligne_d_aide(N,' Boo Hornet Scape'); + Ecrire_ligne_d_aide(N,' Boz Hulud Sbastien'); + Ecrire_ligne_d_aide(N,' Carine Java Shodan'); + Ecrire_ligne_d_aide(N,' Chandra JBT Skal'); + Ecrire_ligne_d_aide(N,' Cheetah Jrme Skyfire'); + Ecrire_ligne_d_aide(N,' Chill Julien(JCA) Sphair'); + Ecrire_ligne_d_aide(N,' Cougar KalMinDo Sprocket'); + Ecrire_ligne_d_aide(N,' Cremax KaneWood Stef'); + Ecrire_ligne_d_aide(N,' Cyclone Karma Stony'); + Ecrire_ligne_d_aide(N,' Dake Keith303 Sumaleth'); + Ecrire_ligne_d_aide(N,' Danny Lazur Sunday'); + Ecrire_ligne_d_aide(N,' Danube LightShow Suny'); + Ecrire_ligne_d_aide(N,' Darjul Lluvia Sybaris'); + Ecrire_ligne_d_aide(N,' Darwin Louie TBF'); + Ecrire_ligne_d_aide(N,' DarkAngel Luk Tempest'); + Ecrire_ligne_d_aide(N,' Das Made Thor'); + Ecrire_ligne_d_aide(N,' Decker Mamos TMK'); + Ecrire_ligne_d_aide(N,' DerPiipo Mandrixx TwoFace'); + Ecrire_ligne_d_aide(N,' Destop Mangue Underking'); + Ecrire_ligne_d_aide(N,' Diabolo Mars Unreal'); + Ecrire_ligne_d_aide(N,' DineS Mephisto VaeVictis'); + Ecrire_ligne_d_aide(N,' Drac Mercure Vastator'); + Ecrire_ligne_d_aide(N,' DrYes Mirec Vatin'); + Ecrire_ligne_d_aide(N,' Edyx Moa Veckman'); + Ecrire_ligne_d_aide(N,' Eller Moxica Wain'); + Ecrire_ligne_d_aide(N,' Ellyn MRK Wally'); + Ecrire_ligne_d_aide(N,' EOF Nitch WillBe'); + Ecrire_ligne_d_aide(N,' Fall Noal Xoomie'); + Ecrire_ligne_d_aide(N,' Fame Nytrik Xtrm'); + Ecrire_ligne_d_aide(N,' Fantom Optic YannSulu'); + Ecrire_ligne_d_aide(N,' Fear Orome Z'); + Ecrire_ligne_d_aide(N,' Feather Pahladin Zeb'); + Ecrire_ligne_d_aide(N,' Fennec Phar Zebig'); + Ecrire_ligne_d_aide(N,' and all #pixel, #demofr and #coders.'); + {XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX} + {XXXXXXXXXXXXXXXXXXXXXX} + Terminer_section_d_aide; +end; diff --git a/dat/HLP_RGST.PAS b/dat/HLP_RGST.PAS new file mode 100644 index 00000000..d0b7975f --- /dev/null +++ b/dat/HLP_RGST.PAS @@ -0,0 +1,52 @@ +{ Ce fichier contient la partie "Register?" de l'aide de GrafX2 } + +procedure Generer_l_aide_Register; +begin + Demarrer_section_d_aide; + {XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX} + {XXXXXXXXXXXXXXXXXXXXXX} + Ecrire_ligne_d_aide(T,'REGISTERING ?'); + Ecrire_ligne_d_aide(N,''); + Ecrire_ligne_d_aide(N,' You''ll probably say:'); + Ecrire_ligne_d_aide(N,' "Does this mean that I have to pay?"'); + Ecrire_ligne_d_aide(N,''); + Ecrire_ligne_d_aide(N,' And we''ll reply to you: No...'); + Ecrire_ligne_d_aide(N,''); + Ecrire_ligne_d_aide(T,'GRAFX 2.00 IS FREEWARE'); + Ecrire_ligne_d_aide(N,''); + Ecrire_ligne_d_aide(N,' ... But, but, but...'); + Ecrire_ligne_d_aide(N,''); + Ecrire_ligne_d_aide(N,' Considering the amount of work (and love)'); + Ecrire_ligne_d_aide(N,' we put in this program, we would extremely'); + Ecrire_ligne_d_aide(N,' appreciate that you "give" us something in'); + Ecrire_ligne_d_aide(N,' exchange for the use you make of it.'); + Ecrire_ligne_d_aide(N,' Let''s say some money, or a nice picture'); + Ecrire_ligne_d_aide(N,' you drew with GrafX2, or a postcard...'); + Ecrire_ligne_d_aide(N,''); + Ecrire_ligne_d_aide(N,' If you make profit with an image you drew'); + Ecrire_ligne_d_aide(N,' with GrafX2, it would be great if you sent'); + Ecrire_ligne_d_aide(N,' us this picture. If you used it for a game,'); + Ecrire_ligne_d_aide(N,' would be wiser not to send all your graphs,'); + Ecrire_ligne_d_aide(N,' what about sending a copy of the game?'); + Ecrire_ligne_d_aide(T,''); + Ecrire_ligne_d_aide(T,'FREEWARE CONVENTIONS:'); + Ecrire_ligne_d_aide(N,''); + Ecrire_ligne_d_aide(N,' This version of GrafX2 is being released'); + Ecrire_ligne_d_aide(N,' to you as is.'); + Ecrire_ligne_d_aide(N,' All bugs should be reported to either'); + Ecrire_ligne_d_aide(N,' Robinson or X-Man.'); + Ecrire_ligne_d_aide(N,' The authors take no responsibility for'); + Ecrire_ligne_d_aide(N,' lost work, or damaged equipment caused'); + Ecrire_ligne_d_aide(N,' directly or indirectly by this program.'); + Ecrire_ligne_d_aide(N,' GrafX2 cannot be modified in any way'); + Ecrire_ligne_d_aide(N,' without our written consent.'); + Ecrire_ligne_d_aide(N,' Finally, the charging of monetary fees by'); + Ecrire_ligne_d_aide(N,' any unauthorized party for the circulation'); + Ecrire_ligne_d_aide(N,' or use of this utility is expressly'); + Ecrire_ligne_d_aide(N,' forbidden.'); + Ecrire_ligne_d_aide(N,' This means that if you had to pay for'); + Ecrire_ligne_d_aide(N,' getting GrafX2, you have been swindled.'); + {XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX} + {XXXXXXXXXXXXXXXXXXXXXX} + Terminer_section_d_aide; +end; diff --git a/dat/IMG2FNT.EXE b/dat/IMG2FNT.EXE new file mode 100644 index 0000000000000000000000000000000000000000..a1739989cafa7bbe2730b303ade8ac1ea1a876a1 GIT binary patch literal 4544 zcmbtYeNYtV8GmkfZ|}H+llXyF&2cokNjx=pYlw1y7z1cV@q$rSD1J1O#Ee0Ew+G2I z9_KJ^a<^!krs*F{G9w|)Oo5~rndt$o9^4@xhKgq@6sb*tH0xZF8p(i(^sdjlcSJHx zrhk<2ckjFVKJV}O*ynlPU3ZlDRSB>T4DfEkyT9vTAs65<04zrwK~y2!2ruF^;IY1+1< zz>;71q$z9L^9P?P&oO1?AFU8^EIs=4(~fe{bm(A(!*t~S!(_GW{>`FTULhVnT9Ik0 zC^sED=rD-~kCod^N6H)N2eh%u6u@Zph<6{6NFYeG4G4sL=7OYI7;fi%y(wRu!c4>R^Jqan3DQRRb` z18MCGRKEMjcny3j$jGRCn{Z6^O$bJt(dK)KGT01qA!U$zDIb=~-FumMuZ_CM``;*a ze=={^n{VuOe|*#Z@0+3_*L~?`{907yzO@|!yuY7O5M3CS`I!isrJdRC^LVl>{tR(2pQ z0MxRy`&O)fIOCBG8#Aq0**Tk>MNaIP&zGCZ?e?Q~6PON)CRm%K1KUwM>7)+RmZQgB zv>$%vS<&>sQxBTfZQQ`G-e@sBdena8V8tQc|1z5e7i)5|0Gz6e^;vM^SVa0VZ^EGOkr*=L5t`PuIeiAmWlLt=6ddjB+pR}`_u26-iv5Q^Q@ zEKNr;$lF0=xt=_#WvHy5fffi;Evh)(iQ^QqE#YuPLM`EX2Et2h9ScET1Ol3#*s&aB z9o*f|7PG}%^aq&KG$!GGO&}H`hU?y)$VodGPP(^s(?FU%nRtQ5^yFy)Qc*F^bl7=6 zpCixraWC)Ck{!9YLu2j~XTZ$J4_|pnuFVM1s7s@@Gy6x8a;Ea z<)kVtXRXqSW+S_+i0dv!8~5up^ay=xCOT-oRohjnN##6MTD{+?4G{mIg@EmeqGEQJ z%&ST@`%Cr;vmDMp24d{Fg#G;?=SEK2i8fSg&6muV9Sq&ihgdFHl}JZgOf!>>=7@&# zRHOQ8#+gurgkw;uDZ%9ERTLeDINjDb-R3!Tok-Wq`_brABV2HQB7J9O@@?}S#n?Dy zlC5YDlAc7;eI)|g@1Lb54|gBy>rnF{`SXZV$JJCX#UnyK1|$KRvy#Nbtfk^T)=B3i z3I(i_VnTD4PE-~0{(x^#9fS8gW<@w4IyNiqNUl`Ah zfO55D_Db27=o46}kd<6oX^*ZzE{sS$L6_Ftv$e6TpH+;ThsNm}t&<upNSZHE$pb01F!alY~7?sPVl@56TMV6i&F_xy?!&eWauYuN0?S~+& zZq02kk6EmfN2AVV#-i>$*fErn97rokwX@bvQ7v_$B9aGZH?@&nXLH-)yOQO1qRvfH zz79jW-1r1HUCv0o-Fp(f<7ml1+TK)qDj(veoeVaj+AjT&s7ANK%dPo3ak0lhyhY}3 z)<_>xm-QQFEqXlaOq24pF;)@`q^J9(LFD$qqj3+*utQ?Z@%idQqFUYt;q=z@fwU~z z2Vh^Ryg-~{R|6lN;WE{trY#!1^shG+H|{+x(jw zy}g#tCf`0af{}}@bXVzcmCe8&(45&>NqIZ(%IM-U!RkajI<#IqB~gym_f^yQl|p}E z?zAt+B|G(f$0@$g+F8j;onh=?jZ&|oMEebaa`q@@H*=tNXt@jOsJC-!kp8N`8>*mv1g;zV)7Sk<=soRqEe1`HpCiZc7)XN?m^VpS(ZJ zY&GYz7^zu}XfC?NG;`jSs37wLbnF9NpU9&3?>MQB%!9pK=WHA-)gkD6F3~Zm1an2gCdEtp)2UUREbxcSD;S zVu!K=GmO7x9TrV)yth=Ow}fv=SImQ0M{yQHM-JnFbm^Q9q!InK7w?(AHa%Q(4e*t3 zCnn#T%>h32+Vm9ub9be?zs|JN?k>$v?v+K-p#F+;++(mJLq#_7OHfJ&N*7!ywM6Lve*P7V4NAlM z5pkY=>P5};2wE}%{H+&Mfv*C{_%-3Wa}Z4kn_`@Hy*s?v9bg@OsNfF_A+&!Ox#XPE z1q#M4&mp-@&Xk%@O;Wx=+LL_J1t}UiA!?MSQ%L{74kYC#TDx47)Mf3*-+pW7aZ2i( zX~dTl?GsXOi)pfPFSeL(au5?U)?8xU#7Vk|{AI*WjVDN#%!T+W#D_>(dXh-3k!k&-by9$@)8G304<4Vw3jhEB literal 0 HcmV?d00001 diff --git a/dat/IMG2FNT.PAS b/dat/IMG2FNT.PAS new file mode 100644 index 00000000..30c4ab8a --- /dev/null +++ b/dat/IMG2FNT.PAS @@ -0,0 +1,88 @@ +program IMG2FNT; + +const + COULEUR_TEXTE=15; + +var + Fichier:file; + Image:array[0..20479] of byte; + Fonte:array[0..2047] of byte; + Offset_dans_image:longint; + Masque:byte; + Position:word; + i,j,k,l:word; + Errcode:integer; + +begin + if (paramcount<2) or (paramcount>3) then + begin + writeln('Syntaxe: IMG2FNT [offset dans l''image]'); + writeln('Attention: ne pas taper les extensions!'); + halt(1); + end; + + if paramcount=3 then + begin + val(paramstr(3),Offset_dans_image,Errcode); + if Errcode<>0 then + begin + writeln('Syntaxe: IMG2FNT [offset dans l''image]'); + writeln('Attention: ne pas taper les extensions!'); + halt(1); + end; + end + else + Offset_dans_image:=0; + + assign(Fichier,paramstr(1)+'.img'); + reset(Fichier,1); + seek(Fichier,896+Offset_dans_image); + blockread(Fichier,Image,17280); + close(Fichier); + + {Transformation de l'image en 0 pour le fond et 255 pour le texte} + for i:=0 to 17279 do + if Image[i]<>COULEUR_TEXTE + then Image[i]:=0 + else Image[i]:=255; + + for i:=0 to 255 do + for j:=0 to 7 do + begin + Fonte[(i shl 3)+j]:=0; + Masque:=128; + for k:=0 to 7 do + begin + asm {Position:=((i DIV 45)*2880) + ((i MOD 45)*8) + (j*360) +k} + mov ax,i + mov bl,45 + div bl + push ax + xor ah,ah + mov bx,2880 + mul bx + mov dx,ax + pop ax + mov cl,8 + shr ax,cl + mov cl,3 + shl ax,cl + add dx,ax + add dx,k + mov Position,dx + mov ax,j + mov bx,360 + mul bx + add Position,ax + end; + Fonte[(i shl 3)+j]:=Fonte[(i shl 3)+j] + (Masque and Image[Position]); + Masque:=Masque shr 1; + end; + end; + + assign(Fichier,Paramstr(2)+'.fnt'); + rewrite(Fichier,1); + blockwrite(Fichier,Fonte,2048); + close(Fichier); +end. + diff --git a/dat/MAKEDAT.EXE b/dat/MAKEDAT.EXE new file mode 100644 index 0000000000000000000000000000000000000000..1eb6a764a4803a2faabaea7d2db45ebff192b61c GIT binary patch literal 18128 zcmc(H3tUrIy6@Ua2oVwRS*sSds1b`&1WQ}+0YZW(ASJxSQ5ztTU`XiB4iCp7mMJ3y zooRbd&lykW+&a$8J)_R~*%{9a+H({|>ucKjm>I41p0?UYDAwBABPukx|8MV|1gG=3 z=l;&`cT-pLU;nk%x4v&ZzV)q5(t^r!Y&Ls=&0^~{>wo&s8kWge|D%k}V2srv?LxYb zG?Qb@h*XGFht!PpJ)}cON02TcT|v5yG)2YObfiS2rASRk9Z1`dUPk%{qytC?k**+p zgfw2wm;tF8$%^y|QkVwvk={r8_b|q;Ar)#FGa=O>{TS)@NKb|{7OBH0k^yNYQYlg; z(g4y;q;HUZIEJxbApI-SA*AC-r;)B9eTp=K#6>`Vr0Ga=k)A?Yiey5nKx#k|kTxT2 zMS2_QK9V14@>s^EA;lrhMJhvDi?kc*pOKCsokR+cguY14NSl#fLHb9e|3JEqlsJyD zWTa=2nvf17^&_QEX6!MZv0o)H_U5CEokRKz=?>B`()xuMKcwf7o=18S=@q0OBmD&F zEu>3G?;(AR^d-_Aq+z766viTuCLnPvUOkOnsAhrvBp4@74Rq-&}rU_LiF~M;4ymx9#XJzqmF+ zg{o*YdTmGFJpa7DgRK4bUaC6r=JMW3cHVn4uD`VFtwf4v*+|NEknaz6_Z+a+)znMMD+;Cn`#1qfG2B)9l)eKH8{{ZIk`l%}{JJ zDHeacO-qWAdXi#3DE9AAZ0FY+NxRJ&WyF-B4(iedUD`F!A2mpoQQdWr?50@7W)kgB z+pO8%_JC}ET03-Z3+aq8RTr%)AW{3mq{-QOV_#U$#U1@US4XxVX8sdRntgj-O#b}# zPj_5h*w@whnUCJRzU_x=Aem}F_aBalSIa~_xAQDAk|8p)(-ouSyE^X#n^g=?DYr&q zCW?xrDUlj%J^ajY6xXCZ*-4+<50~7h9;j-)dgm|3#jB4jR7I8Vv;&E{H#>)Y+(5m0 z>*4joR<23Ps|G5eM->_zY2sorw(6aQW8>A{lizqc*AI7f`g|UU?&=)D=lbD=7rHu2 zhPz%V8zy$)1<#I>Vb4F64ezW)n?R9lgr~F07Y21N6c_D`MX98&_xv|B7GEhwdEMV^ z>%1oo&kbK!=S}o+!{>SBrY{3MY>sME5ByA(fer=rz^f_`#$rLFIuUX+AfZ`3uuavC z*6E$!8Fs4&o@a7q-LTjqtLi!Bxe^e#b2lk?s_RNu=O>CK-!AU_$hYG8?$V1=JDM1A}Z-)g4k*D&5w3 z-#4njJ(B#<3KBzQ$scuf77s7%%fNf{rmoJfeS;c5-bY*WwQu1CHM*RL9{-|E->&pm zExQlPDlws7V_b`e-954{p?<`2RNq<@ZBFK&pfWAYi%&lb@M6YWe==zBB+UzVS{Q zR<>?_z$ejWW8{Dz^f|9RuYu`zyI)9PDMk(4v_$;q;5asP@1@M2Jg<@5w(3t>Vbd6W zgKEFgCpjxmo3HzYCa%c)6MvESjr&{Me14VtTA(vsz_aUcT67ujdyKjaeytxql4BGlo%l*E`I06~&qoXfUcL9%#AS{a_SW5R341#v%ne~X(8c{|?9U2+N1Jaf zfI&JXX_7iQ#hZ6>4|sEJ(3@{R-2SH?oQMZKI5DF=c$?3A6&7lkxWv=h1~<3K*UPaC zd^A7W)wx;PgVG(I@BfyJX!8-18QEe*VP?GUCFQ?)o; zj9eTo>J~pNYG}G7bEGNsqt?{B(!};*$iv+GJB&IlrXO9ocakc)Tw_H_QchM0CP6v9 zaa`-d@D>qvii-`U#e7ayp^49*o0XSi;AhU9$>-Vm zR^H6J9TwhhtHb-VZX0iLiM%K{8+p6aQRlW$MOwj{zzWtpxPn9RNIRmB`Atv!N$k~F_Y6q1T+6tg`3m^ozUuU={(w&#aY7G#bwRm?NE09U>JQQ{FMRvzqP6TTQ&{M z;ufng9X$wrXpsLa^N{=3Y})a+=7G$W2Kq=yDQTDoe#jQ9p;Fg>w@Op~pH-rJK}2q` z!BCP{m}^RB53hC$d=>2=!BS@yYFvDslNX&yNlEcMpH*FLak+TqWwhBvix9{a*&G{Z zQ58#o!KcyI6so}&*;*|2*;L0?v(nrU5MwtxLQRSUXRXaXhbjrJ_8@N*EH%Llk4nvU zi$J367RU^gP_3HQG9_E&-sG@JI@xXJpw_%maKgI4>uI;GdLuGf4K~3X6qIZ3vM1!` zWY3eT6`QFiK`?K$1;pfvfu{auSEl)^Hv86$(5wZee1Y1q8I$vzr zG#4^#LZ~0qaJmB4@_ez=T_gRI>bab5htn-c)~zsCZ?p*6g40gJVKP?>HoK+HLOt41 zl+~h4@CtLIJtW>_Zos51cRC!l-~w3T4A@SZnJ^j!W(U^D@=@mV{0gVwumnvpRht_v zq?2<~$Q*u!+wKmTXL`O018%d>U}l>I8{EF~T4`=F2QYfHI%~`htlMlW`W6BuE0>pq z>hPwGW?F99R*OY6TLW^Q7hY}%N;Pe4t+fdj>dk7CMn$f+(rt$l2`jU+Xq}iEt!A5` zMrJRKxcfuc@wsI;AL`S zowh$#DSdE!tc(d4jn*SPk`rYPS&R zwG3*3Xu^c`PouNu=&>!&y#jAqVdA{6?LJWdowQ&?%XcMagI|p^JMV8ZMF`{y)R-rTG zUU|O4>1?oBFvCW3XrJ+XVXG+Ef=i)76dEu{Mzce722Klpb)#qtS-%F$+63nihiaD4 zrsMh5f^(GMN-PwVi`Jm=MP{qrToYKMm6j@4ZnQWYp^+`Jj+TcSwmK+-)x(orv*3*_ z_WAs*8cTz-R*?8v)lRGvS5hca_vU?F&mFloE~?zS`9JH`M?NPc5V}do8syd!(nWzQ zA(TjHC85=XG6{)<(g^J&G@sBBLh*#I6Pij$6ActaXdWRAp+Z9UzXoyOeliTM}!!m z$caFAZUZeObc4_uLe~hj6S_?3r-a@nbcWDzLZ1^lL}>gZp#6l>2>qPUT0*Z9Y9sU# zp`Q`jM(6~gHbS2g5($l+3{-#Hd-SW*{W0<$$t}(@R`4lF$;pqxx2-VnrTHa!1z9Bq zzJSnzVuNXQerZYG>OvkjLf(**SF*a8&Yf&$W2-=}nop>n$1i;9sk8-8J;_(K@}|;4 zlc9vqF_`jl3z;svnA(`qr(ug0=arNg3i+(U9HrQh!!KWx4$p;1qBJi*KdZFBz~`(k z#=HDll~tV27i6JfR%s5^GfP2Le6h32=5RUbl;yEK0(8X!c+hw_0p*2buTC&GGz9lw zhzL~*R1SWUp%e$XL<~|vo+;Y^%?b^xOHJvCRH+1RmB&AXE<6IwRvyPRVmn1PU+rvY zMC?*C1y!-r%grJfKATTin4FY0FKIrB$agj`uv?mN4hc>-JSqHavjsl5S+I$s#X;?! zOiq0=jcm(uxhxG;g= z_{aH#MM(>luFKI2b%pV3giEiXIfIAdD@+!#0G=eE5$RbAcgD}H$j@7zG8f@EUyXxC zwD1j1v^O`HH{opJn`|`}XEZ7c7MIfwW1J3`Y-9=IpN%eRXQ;N@8eJAiYxHFk;L1&W zYEts!e2vrf5E@%rU^d(spHPk>yG^tx>YB)*+8nUA0Y{G0!HbAI9I|FEj39;2HO^`m zshd!gom*s>&*wQ17dN>r^ZBA|Ia6a3ahI6K*O{9vyxT=ngYe(xXfoT~W{fRwwb&bz zXc#fO0j*6|bF+hAVHWCOb`z$E1|4%RjSP+(j9sJC-dYExlv$M3%0f{cV&JBfq!je| zfJ_9Ac7zJ?6ja3XMY!rX17atmBK0I9W;WMWq~JM1oij;Vaaoulr`tsnDhAb~Ni(}q zfLH(_FS0mp_!?VnEvDCjXAxFRj|&eda7)1HQRQs1BuQHhE5K}bIr(O%+g^imL~@uT zNw9RtKoX5aqs7^Xk!iL%1H;B+s&S=3Wm^MQdy^#s)nsLpFp0*zd;@R9?#(JO@qv9$ zLyf=8@aa54ITs>sL_Bz8G8J_Ga-t1(OEn&wIB>jX38HHviOe&iARGJ0?ZQM_CV*RB zPz0{PR*n0FvsR=9SCm}=s&at|`A3k?E67EDxvdF0CX^>3B(T&V{%|atHwmSt>=sF= z-HAAiPgpiD0VKBe{8ic1+p471Nv0$|VO5^Vve9heu^V_-D~7IN9_dvd@%g-fkP!RQKG#`A!-41w`xgF`=bwBcIXRin&nsA+ zYcTN%#^S8PY{R^VsptXE$tOsjao%()S(qFWY37#;X80GuW*LL{YJsE|?MLh>p}~^b z;IbvT9X7kIA*og%bNL3u+M?NAlWB3dZ1zy$q*9Y1-(WKFd4=*4z>$$oCYazRaXWXx zZKcyHbc_7LMbLUx6)iG(^~`ngRW<=`s|M~RoyQHQl}|}Vp3arAs|r__7xK$X@t^>Q z6u*F9oGl9WrHPBPm+}-nV?|;s1l(`474D(c>89z$E{CVWW`Kd@s<7KFt|X`g^Bi-@ zW#hquwChO(9Mncjs|%0yM4KH>5`Mjfb`g|w*GVpI0iVU!TAD{~GBhC1i_=K*PA+&s z(JeS=74wo>E{ZfMLJJBYpId7;yR5vqu@TXui^rBn&@G6(yAj(B>YE+X+Td{`5nK66 zTO*Il13VX0sl}bSCW(w&06QSN*6l!852s7El2Nrbhs|Y0C#@DSi3TimVmZi*+9ijB zna9nO&My}l&*xpv@lsWJV49tR&?@^LemQ2$R!c()E$JeP4r)*zePdj362d22E%I)izA8EnXllEGT6df7?Cs3UOZ&I!5SI zLhlm#--NUe16?GvfY50|lDs2?N{IVcLR$&#CG;gNI zQau7Ro)AwcJXr6WPr+pncbiZtp#eftz4r-8ef;55^zkf}o(*zG34NEi-x7M6&@Vp? zXu6xwe&T)mfjnMw@Bcrwf{V~8KtINfvMB;eqy5UaKFE^}+T0pN! zoDY8|zkz@o%ZAfML?j(8a7l=W;hRN@#o#_S@(JXx?1+-)CDLKiNN$vLgcDcJs`Z3 z5rO7gL>#dgH`#4B;OSoLd>+xPnMd3O-SA`xkAUV%O=|?4aMC40KAe?`jd*@tjd)eI zJx@Lmq;6nMtxc4hP*mMuhC-w@NrLTk9|?$}dQ#Yl2Yzy}8#r2UO3x<)9McmYApHbgK8y>Ngyc^B>xQWy&j1oUBUw7TZcmCqMB{Gb{X4w!K+ zH?}IVGh*BZ%d*MA`A67RW+V|r zXvss8v~F-X^q$&~ZW?gboqfOK3l#GlYIlXo%3Ogk~oIy+mjw zp>2f93AGVwCnSF0J^TLYe)($+xQ_@4SC4usoA`$#WsgFaic8X8 zo{wxm=7BFz{66rNL+_bCzNvj)!%6kL-@ht-)^qio)yL}Rdw;1As`|(3qw5!Yf2`yu zBF`hgUCGZzej)PDDf!2dUygi(k~bo6LVlf+FGs!x`2rF1k zZ$SQ#k~bsoM1GHwe-`;I$nRA0s`^^=@A7sl`H9H$$Zt~evyoqje7%x?9QozQS1NfU z@+Rb0D*1BcYmiS@@>b;C$Umy&TkC6SNL=2BWrBvJmWIUT4Ogmg^)2-=*6%a#opOeFR@k51Zsc%7+m^PWQ zb}>-@AW<6?Y9~>@kf;iU+Dp_Si83hEzY%p-qEciED-qISAkE7w%miX)5)-8`vxrF{ zX5_ML`66PniTO-n48)WWb6H`^h_Mj!roz+_(?rYxg=qmp#(~-;Q$*k&tOK`Q;dV+K z%mde|aC;>V_JOk~+`ma23gSA;Qm43U?8|d z68AlYgMr{+AnG;B91O%v$DpEjy~0c&W+pND3NwqC6k^g9W)U&j#3U$;ftV6vrYKAq zF&1Jp3R6c+6ER=?QCY!2o45ViP`t!2&tiH8=fj3%NBFws#AerJhc`DviwW?lR7EbZo!4WY;2YY@hhpjz0aa7zQ*w zvA_ADq038Hj4S3)3>&(pJ}QLkGqgG;X!W}$vBC46Q$78OvESi324lLSD!8uLO73`U zG1t=vaT8Pfb{BKIOSs+7aJ>#Lsz_@(D-A)Ece_TiJIeb#&4Xh)C-%f-j1&#&tz8w| zSZyUI&U+(Y<$aXxD&xEhha~IPSUp&sV2mpTW=p*C#W%dy=U1#qfaJ}7wUTYz0Yz~qGi3m zV*_PA&wFXdw`fLoE#>y^%H;N*(J-0OA79e7bSc-P&E&e48u7V;L)jZ6s=+6=9%C_s zVd@->@So}u?TJM_S2Nys-|By3hI(*%Mv1n0oDi0gqj70HIT}x}{FDA&%Q?@K94=A2 zl$$;!lbaLGVm(VUxf5wd&VMluTjiMNO#6qoI<7^lkK)G!XR$b%cUOdaw{S<$|GPVm zdfw^jhgv;vW~60u;s$+2skV6#t0cpqX}+#4H$AQQjMID8sl-%*1sY&&;;HFZIzEh6 zpH%-*a|=>uM|IHvzWnEnR_mA(s=y4Gn)@P=@G*EnQU6_t0f?tj!js!0aa7Ie*X zGPKLN<~VJ+=iZL~-AlPHSfTF<(|47sQu~Vhv4tG9^`}*Y6JE>-zZHM8t0H`0u^*;X z4jmoxyG=%?-)tecNw5nsg|t1yra)^vgep= z^?x+q7PJ}fG=DBe78iNPV3T<@>~8TS``IsF`sGV{b(mgVs#3;i?@N0(#6c0sw*Ihi<~eu% z%K6Xezd1UF;rYJy8SZSy(q}m4=FaYVh8q|+;`uslM~(`UqS_L^d6GUOOo*l#+N|4x z?Ti`X&i0;W10N6fUSb394~H?8FfQ@9Ys}E)4DEVOKIKhxu~?G2v=hym zk<`Auz56fi?QLg!0r&3RZV>nOfO{!wZ*ROB+`%Yzd+)*3Z0rU1n0@J|nl#;~uIu(; zYpVBLyPMLtC+>_+UeFO~o?Hy8L4!{%J|pp|!)H`#AKnQ?oQYtEUcWS`JM^ndgX%-S zzJyJKpOoo62Gx?+FNqVD{OXc8Zpr>jV$4ZcU&{t(7i-I-ymMG3i73TtlEu6cgNTKR zTK!3bYX7Bm*fsmvplUy-h}-&{3eu+P@d<%Cl2ykBrxv|2iFqgEx0Zck%MQZrD4dMOr5NY%$N+ack{>Xu4Z_N~9$O46v*q~asAdUu*{vL z_cZJD8O;%5VyxCwtUpl>9XCXTtFNfP8u6b?{Ho{J+VD7iSF>(xpIg^Y_FGwh(bL7{ zT9Y@GTN}Qia!o}*hWp?8W$BqD{a2UVPw73Yv9Y)465mNY@6xExq+ZbKk2goEef#;5 z+j|my*v4DX{T7XTOfdvrV{5}Ju{cgi9od*7ZiON)Ym~U75O*rI4@&R2qCdVNQawC! z`=^P+lCp}(aYe;t5V{>g*H>0R|Gt1&n%wo;-dJ7g1@BFtJ3`;FWf~LJ-bO|XVBg|# z`0c|qaeT&Y_ia?_&$um)*|#`CD#{YrZkJ1lZNSG*Pekcb762)TkRHbNc~ zwReJ4q&4aN8zw2MqhHER4dkR|k-cx|JcU|Mo6b`fk?Sq=c}^a0(u7{y=KdB`()#T;Z1IUQcrZE(A9-tL zWgO0rqhgrn7&@YL`Rio|snxGD4=Sx`*V zgt*iT`XRRljhovi#&f^jSX^KGquQZ+ zwVpGQ47{CXRqL=8h%#$FYdwvIIzhTg@=I&@V`E%kiq8BV?Gf%>U^ z{~p86e{lZ7`Sa&5W+uKp{e4&13iaC)-!E_vtQ(xN4)O57=U-nRdikZHFJB(|5=}0q zUOoT0OQ#4k6u85cZq_MUYNLO7?&4=>J3fpPwK#PzU%MYH_}Q_GA1DRr5(Oik_b^(@ ziMel2_o)>6S@9K2uUs-}9QUOkZBlg~4b_QI>Kxw^iSgETBYMSnYsa46qCUtm^_Pi9 zg^8Io17lA=r%FAYakNS6!SBga`}TNFNuB6|0;B_5-#sqn^L=_2=F;ik4D)v%y>m`| zFSlE+i{CkVZp5BwiWs2-dVcr0lsk03Qj^3p!i=okeP8{Hd$Q-G=Uva4yxTt)qda## zXFW|3#=%cg`vx^D5{=q8S{(tibQHPn(|6B72kF0qVZVzwEox!?&)ur@;}`*{Dy^aY z+@7@VT+JTD!-3I?fW25-AQej_C${wlQ+2dyx#z-88nqmge~2ypPz}FtqF=PFz^&>m zeu)=FN59&S3iv&fRKee*#f=BW`+QN}0r|&z{w7_Nw?*p0I_~Ms1PY+fwxQUAZ@z7$bE@QBQ2zi7lGc z(_Q0w*%CSG7`I>L50gEZ>cC>jVU2;m!bx7)71ry}9*S4fl})bv812fOw`Sfs*52Ds zMf7WE_av#gTkTC`z5f(w00;N0OI?OZU8PgH3Z{0gn|9JLS>5m zVUsUtXB}6VOOx7%P!GFD+56l7uALohXYhoGWL#KbsaG>Di+nq{X`(uN@GH;7#B&Gz zenkq2qX?$o^UmQ2=E44K9Y1sxyXY#zRctjD--4|E)C(^U-NC>1W6ACJ(*5y+<#*hX%R zs#3i}vp%d_n;d>i$Htgr`0>A(Fn!{JNo;c5l*b;rKJJ09-7!w3)`V%pbz>sNMvjY$ zju}5;;-tw_9-8{_wCOV*iH+lD#?P8PM?W`V-lK{07bHEFyf7s-bX8_cmt|%x&(1Lz zb64c8T$Nu?xEf)ksid^5ykbq|+V3#7ZvBR5n3+{o*H~mVYw3UPVzmWymOj7tLg)9l zb#;4sw(t1C4__qeC04)D-r#UHK8r8Xx|^C?S~q=n^K)%m+P6O6!P-W@o~f#-wbt7m zje^+JvWZGIw=tDQtBZ(?ikUEJ%G7ByV)^*l`h-U-D!;S-fo|oD-~VUGzf8qsGWHto O6TOV77#;}(U;hU&IU#8P literal 0 HcmV?d00001 diff --git a/dat/MAKEDAT.PAS b/dat/MAKEDAT.PAS new file mode 100644 index 00000000..c974e000 --- /dev/null +++ b/dat/MAKEDAT.PAS @@ -0,0 +1,738 @@ +program makedat; + +type tpalette=array[0..767] of byte; +var palette:tpalette; + +{****************************************************************************} +{****************************************************************************} +{****************************************************************************} + +Procedure XMODE;assembler; +const + X360Y270 : array[0..18] of word = + ( $12E7, $6B00, $5901, $5A02, $8E03, $5E04, $8A05, $3006, $F007, $0008, + $6109, $2010, $A911, $1B12, $2D13, $0014, $1F15, $2F16, $E317 ); +asm + push ds + + mov ax,13h + int 10h + + mov dx,3c4h + mov ax,0604h + out dx,ax + mov ax,0100h + out dx,ax + + lea si,X360Y270 + lodsb + or al,al + jz @@DontSetDot + mov dx,3C2h + out dx,al + + @@DontSetDot: + mov dx,3C4h + mov ax,0300h + out dx,ax + mov dx,3D4h + mov al,11h + out dx,al + inc dx + in al,dx + and al,07fh + out dx,al + dec dx + cld + xor cx,cx + lodsb + mov cl,al + + @@SetCRTParmsLoop: + lodsw + out dx,ax + loop @@SetCRTParmsLoop + + mov dx,3C4h + mov ax,0f02h + out dx,ax + mov ax,0A000h + mov es,ax + sub di,di + sub ax,ax + mov cx,8000h + rep stosw + + mov dx,3D4h + mov al,13h + out dx,al + inc dx + mov ax,90 + shr ax,1 + out dx,al + + pop ds +end; + +Procedure pixel(x,y : word;coul : byte);assembler; +asm + mov dx,3C4h + mov ax,0102h + mov cx,x + and cx,3 + shl ah,cl + out dx,ax + + mov ax,0A000h + mov es,ax + + mov ax,y + mov bx,90 + mul bx + + mov bx,x + shr bx,2 + add ax,bx + mov di,ax + mov al,coul + stosb +end; + +Function lit_pixel(x,y : word):byte; +var a : byte; +begin + asm + mov ax,0A000h + mov es,ax + + mov ax,y + mov bx,90 + mul bx + + mov bx,x + mov cl,bl + and cl,3 + + shr bx,2 + add ax,bx + mov di,ax + + mov dx,3CEh + mov al,4 + mov ah,cl + out dx,ax + + mov al,[es:di] + mov a,al + end; + lit_pixel:=a; +end; + + +procedure set_palette; assembler; +asm + push ds + lea si,palette + mov dx,3C8h + xor al,al + out dx,al + inc dl + mov cx,768 + rep outsb + pop ds +end; + + +{----------------------------------------------------------------------------} +{----------------------------------------------------------------------------} +{----------------------------------------------------------------------------} + +type t_os_tampon=array[0..63999] of byte; +var os_index:word; +var os_tampon:^t_os_tampon; + +function octet_suivant(var f:file):byte; +var effect_result:word; +begin + inc(os_index); + if (os_index>=64000) then + begin + {$I-} + blockread(f,os_tampon^,64000,effect_result); + {$I+} + os_index:=0; + end; + octet_suivant:=os_tampon^[os_index]; +end; + +procedure init_os; +begin + new(os_tampon); + os_index:=64000; +end; + +procedure close_os; +begin + dispose(os_tampon); +end; + +{----------------------------------------------------------------------------} + +var eo_index:word; +var eo_tampon:^t_os_tampon; + +procedure ecrire_octet(var f:file; octet:byte); +var + effect_result:word; +begin + eo_tampon^[eo_index]:=octet; + inc(eo_index); + if (eo_index>=64000) then + begin + blockwrite(f,eo_tampon^,64000,effect_result); + eo_index:=0; + end; +end; + +procedure init_eo; +begin + new(eo_tampon); + eo_index:=0; +end; + +procedure close_eo(var f:file); +var effect_result:word; +begin + if eo_index>0 then blockwrite(f,eo_tampon^,eo_index,effect_result); + dispose(eo_tampon); +end; + +{----------------------------------------------------------------------------} +{----------------------------------------------------------------------------} +{----------------------------------------------------------------------------} + + + +{--------------------- DEPACKER une IMAGE au format PKM ---------------------} +procedure load_PKM(nom_fichier:string); +{errcode retourn: 0=OK , 1=pas un PKM , 2=taille incorrecte} +type + header = record {taille: 780 octets} + ident : array[1..3] of char; { chane "PKM" } + methode : byte; { mthode de compression: } + { 0 = compression en ligne (c)KM } + { autres = inconnues pour le moment } + Recon1 : byte; { octet de reconnaissance sur 1 octet } + Recon2 : byte; { octet de reconnaissance sur 2 octets } + longx : word; { taille de l'image en X } + longy : word; { taille de l'image en Y } + palette : tpalette; { palette RVB 256*3 } + jump : word; { taille du saut entre le header et l'image } + end; +var + TailleX,TailleY:word; + errcode:byte; + coul,octet:byte; + taille_fichier:word; + i,j,k:word; + c:longint; + offsX,offsY,X,Y:word; + fich:file; + head: header; + taille_image: longint; +begin + offsX:=0; + offsY:=0; + assign(fich,Nom_Fichier); + reset(fich,1); + taille_fichier:=filesize(fich); + blockread(fich,head,SizeOf(Header)); + if Head.LongY>270 then Head.LongY:=270; + + if (head.ident<>'PKM') then + begin + errcode:=1; + exit; + end; + if (head.longX>360) then + begin + errcode:=2; + exit; + end; + + { dfinition de la palette } + Palette:=head.palette; + + set_palette; + + TailleX:=Head.LongX; + TailleY:=Head.LongY; + taille_image:=Head.LongX; + taille_image:=taille_image*Head.LongY; + Seek(fich,SizeOf(Header)+Head.Jump); + + init_os; + + j:=0; + octet:=octet_suivant(fich); + c:=0; + while (cHead.Recon1) and (octet<>Head.Recon2) + then + begin + X:=c mod head.longX; + Y:=c div head.longX; + if (X<360) and (Y<270) then + pixel(X,Y,octet); + inc(j); + octet:=octet_suivant(fich); + inc(c); + end + else + begin + if octet=Head.Recon1 + then + begin + inc(j); + octet:=octet_suivant(fich); + coul:=octet; + inc(j); + octet:=octet_suivant(fich)-1; + for i:=0 to octet do + begin + X:=(c+i) mod head.longX; + Y:=(c+i) div head.longX; + if (X<360) and (Y<270) then + pixel(X,Y,coul); + end; + c:=c+octet+1; + inc(j); + octet:=octet_suivant(fich); + end + else + begin + inc(j); + octet:=octet_suivant(fich); + coul:=octet; + inc(j); + octet:=octet_suivant(fich); + k:=(octet shl 8)+octet_suivant(fich); + for i:=0 to (k-1) do + begin + X:=(c+i) mod head.longX; + Y:=(c+i) div head.longX; + if (X<360) and (Y<270) then + pixel(X,Y,coul); + end; + c:=c+k; + j:=j+2; + octet:=octet_suivant(fich); + end; + end; + end; + close_os; + close(fich); + errcode:=0; +end; + +{****************************************************************************} +{****************************************************************************} +{****************************************************************************} + +var Crypt_curseur:byte; +const Crypt_cle:string[13]='Sunset Design'; + +function crypt(octet:byte):byte; +begin + crypt:=octet xor ord(Crypt_cle[Crypt_curseur]); + Crypt_curseur:=(Crypt_curseur mod 13)+1; +end; + +procedure Ecrire_palette(var Fichier:file); +var i:word; +begin + for i:=0 to 767 do ecrire_octet(Fichier,crypt(palette[i])); +end; + +procedure Lire_et_ecrire_sprite(var Fichier:file; x1,y1,x2,y2:word); +var i,j:word; +begin + for j:=y1 to y2 do + for i:=x1 to x2 do + ecrire_octet(Fichier,crypt(lit_pixel(i,j))); +end; + + +procedure Ecrire_trames_predefinies(var Fichier:file); +var + n,i,j:word; + Octet:byte; + Pixel_lu:byte; +begin + for n:=0 to 11 do {Pour chaque trame prdfinie} + begin + for j:=0 to 15 do + begin + Octet:=0; + for i:=0 to 7 do + begin + Octet:=(Octet shl 1); + Pixel_lu:=lit_pixel(9+(17*n)+i,196+j); + if Pixel_lu>0 then + inc(Octet); + end; + ecrire_octet(Fichier,crypt(Octet)); + + Octet:=0; + for i:=0 to 7 do + begin + Octet:=(Octet shl 1); + Pixel_lu:=lit_pixel(1+(17*n)+i,196+j); + if Pixel_lu>0 then + inc(Octet); + end; + ecrire_octet(Fichier,crypt(Octet)); + end; + end; +end; + + +procedure Rajouter_fichier(var Fichier:file;Nom_fichier:string;Crypter:boolean); +var + Fichier_a_ajouter:file; + Taille :word; + Indice :word; +begin + assign (Fichier_a_ajouter,Nom_fichier); + reset (Fichier_a_ajouter,1); + Taille:=filesize(Fichier_a_ajouter); + + init_os; + if (Crypter) then + for Indice:=1 to Taille do + ecrire_octet(Fichier,crypt(octet_suivant(Fichier_a_ajouter))) + else + for Indice:=1 to Taille do + ecrire_octet(Fichier,octet_suivant(Fichier_a_ajouter)); + close_os; + + close(Fichier_a_ajouter); +end; + + +procedure Coder_partie_de_fonte(var Fichier:file;Pos_X,Pos_Y,Nb_char:word); +var + X,Y:word; + Indice_char:word; + Couleur_temporaire:byte; +begin + for Indice_char:=1 to Nb_char do + begin + for X:=0 to 5 do + for Y:=0 to 7 do + begin + Couleur_temporaire:=lit_pixel(Pos_X+X,Pos_Y+Y); + + if not (Couleur_temporaire in [25,7,15]) + then Couleur_temporaire:=0; + + ecrire_octet(Fichier,crypt(Couleur_temporaire)); + end; + + inc(Pos_X,6); + end; +end; + + +var + Fichier:file; + Position_de_depart_de_la_section_d_aide:longint; + Nombre_de_lignes_d_aide :word; + Nombre_d_octets_utilises:word; + + +procedure Demarrer_section_d_aide; +begin + Nombre_de_lignes_d_aide :=0; + Nombre_d_octets_utilises:=0; + assign(Fichier,'GFX2.DAT'); + reset (Fichier,1); + Position_de_depart_de_la_section_d_aide:=filesize(Fichier); + seek(Fichier,Position_de_depart_de_la_section_d_aide); + {On crit temporairement des valeurs errones dans le fichier:} + blockwrite(Fichier,Nombre_de_lignes_d_aide ,2); {Nb de lignes} + blockwrite(Fichier,Nombre_d_octets_utilises,2); {Nb d'octets utiliss} +end; + + +procedure Terminer_section_d_aide; +begin + seek (Fichier,Position_de_depart_de_la_section_d_aide); + {On crit dfinitivement les valeurs correctes dans le fichier:} + blockwrite(Fichier,Nombre_de_lignes_d_aide ,2); {Nb de lignes} + blockwrite(Fichier,Nombre_d_octets_utilises,2); {Nb d'octets utiliss} + close (Fichier); +end; + +const + TITRE = 1; + SOUS_TITRE = 2; + NORMAL = 3; + T = TITRE; + S = SOUS_TITRE; + N = NORMAL; + +{$I TABLES} + +procedure Ecrire_ligne_d_aide(De_type:byte;Chaine:string); +var + Code:byte; {Code inscrire dans le fichier} + Indice:byte; {Indice de balayage de la chane} +begin + + if length(Chaine)>44 then + begin + close (Fichier); + asm + mov ax,3 + int 10h + end; + writeln('ERREUR DANS L''AIDE !!! Il y a une ligne qui est trop longue !!!'); + halt(1); + end; + + case De_type of + + TITRE : + begin + {1re ligne:} + + {On code la taille de la 1re ligne chane:} + Code:=(length(Chaine) shl 1) or $80; + blockwrite(Fichier,Code,1); + + {On code la 1re ligne de la chane selon la table des caractres} + {de titrage:} + for Indice:=1 to length(Chaine) do + begin + Code:=TABLE_TITRE[ord(Chaine[Indice])]; + blockwrite(Fichier,Code,1); + inc(Code); + blockwrite(Fichier,Code,1); + end; + + {On met jour les compteurs:} + inc(Nombre_de_lignes_d_aide); + inc(Nombre_d_octets_utilises,(length(Chaine) shl 1)+1); + + {2me ligne:} + + {On code la taille de la 2me ligne chane:} + Code:=(length(Chaine) shl 1) or $80; + blockwrite(Fichier,Code,1); + + {On code la 2me ligne de la chane selon la table des caractres} + {de titrage:} + for Indice:=1 to length(Chaine) do + begin + Code:=TABLE_TITRE[ord(Chaine[Indice])]; + if Chaine[Indice] in ['A'..'V'] + then inc(Code,44) + else inc(Code,40); + + blockwrite(Fichier,Code,1); + inc(Code); + blockwrite(Fichier,Code,1); + end; + + {On met jour les compteurs:} + inc(Nombre_de_lignes_d_aide); + inc(Nombre_d_octets_utilises,(length(Chaine) shl 1)+1); + end; + + SOUS_TITRE : + begin + {On code la taille de la chane:} + Code:=length(Chaine); + blockwrite(Fichier,Code,1); + + {On code la chane selon la table des sous-titres:} + for Indice:=1 to length(Chaine) do + begin + Code:=TABLE_SOUS_TITRE[ord(Chaine[Indice])]; + blockwrite(Fichier,Code,1); + end; + + {On met jour les compteurs:} + inc(Nombre_de_lignes_d_aide); + inc(Nombre_d_octets_utilises,length(Chaine)+1); + end; + + NORMAL : + begin + {On code la taille de la chane:} + Code:=length(Chaine); + blockwrite(Fichier,Code,1); + + {On code la chane selon la table des caractres normaux:} + for Indice:=1 to length(Chaine) do + begin + Code:=TABLE_NORMAL[ord(Chaine[Indice])]; + blockwrite(Fichier,Code,1); + end; + + {On met jour les compteurs:} + inc(Nombre_de_lignes_d_aide); + inc(Nombre_d_octets_utilises,length(Chaine)+1); + end; + + end; + +end; + + +{$I HLP_GRET} +{$I HLP_CRDT} +{$I HLP_RGST} + + +BEGIN + XMODE; + + Load_PKM('GFX2.PKM'); + + assign(Fichier,'GFX2.DAT'); + rewrite(Fichier,1); + init_eo; + + Crypt_curseur:=1; + + Ecrire_palette(Fichier); + Lire_et_ecrire_sprite(Fichier, 1, 1,254, 44); {Menu} + + Lire_et_ecrire_sprite(Fichier, 2, 47, 15, 60); {Shade} + Lire_et_ecrire_sprite(Fichier, 19, 47, 32, 60); {Colorize} + Lire_et_ecrire_sprite(Fichier, 36, 47, 49, 60); {Smooth} + Lire_et_ecrire_sprite(Fichier, 53, 47, 66, 60); {Tiling} + Lire_et_ecrire_sprite(Fichier, 70, 47, 83, 60); {Stencil} + Lire_et_ecrire_sprite(Fichier, 87, 47,100, 60); {Sieve} + Lire_et_ecrire_sprite(Fichier,104, 47,117, 60); {Grid} + Lire_et_ecrire_sprite(Fichier,121, 47,134, 60); {Mask} + Lire_et_ecrire_sprite(Fichier,138, 47,151, 60); {Smear} + + Lire_et_ecrire_sprite(Fichier, 1, 85, 15, 99); {Fleche} + Lire_et_ecrire_sprite(Fichier, 17, 85, 31, 99); {Viseur} + Lire_et_ecrire_sprite(Fichier, 65, 85, 79, 99); {Viseur pipette} + Lire_et_ecrire_sprite(Fichier, 33, 85, 47, 99); {Sablier} + Lire_et_ecrire_sprite(Fichier, 49, 85, 63, 99); {Multidirectionnel} + Lire_et_ecrire_sprite(Fichier, 81, 85, 95, 99); {Horizontal} + Lire_et_ecrire_sprite(Fichier, 97, 85,111, 99); {Viseur fin} + Lire_et_ecrire_sprite(Fichier,113, 85,127, 99); {Viseur pipette fin} + + Lire_et_ecrire_sprite(Fichier, 2,102, 15,115); {Dessin continu} + Lire_et_ecrire_sprite(Fichier, 19,102, 32,115); {Dessin interrompu} + Lire_et_ecrire_sprite(Fichier, 36,102, 49,115); {Dessin point} + Lire_et_ecrire_sprite(Fichier, 53,102, 66,115); {Pinceau-brosse} + Lire_et_ecrire_sprite(Fichier, 70,102, 83,115); {Courbe 3 pts} + Lire_et_ecrire_sprite(Fichier, 87,102,100,115); {Courbe 4 pts} + Lire_et_ecrire_sprite(Fichier,104,102,117,115); {Ligne} + Lire_et_ecrire_sprite(Fichier,121,102,134,115); {K-Line} + Lire_et_ecrire_sprite(Fichier,138,102,151,115); {Lignes concentiques} + + Lire_et_ecrire_sprite(Fichier, 1,120, 16,135); {Pinceau 1} + Lire_et_ecrire_sprite(Fichier, 18,120, 33,135); {Pinceau 2} + Lire_et_ecrire_sprite(Fichier, 35,120, 50,135); {Pinceau 3} + Lire_et_ecrire_sprite(Fichier, 52,120, 67,135); {Pinceau 4} + Lire_et_ecrire_sprite(Fichier, 69,120, 84,135); {Pinceau 5} + Lire_et_ecrire_sprite(Fichier, 86,120,101,135); {Pinceau 6} + Lire_et_ecrire_sprite(Fichier,103,120,118,135); {Pinceau 7} + Lire_et_ecrire_sprite(Fichier,120,120,135,135); {Pinceau 8} + Lire_et_ecrire_sprite(Fichier,137,120,152,135); {Pinceau 9} + Lire_et_ecrire_sprite(Fichier,154,120,169,135); {Pinceau 10} + Lire_et_ecrire_sprite(Fichier,171,120,186,135); {Pinceau 11} + Lire_et_ecrire_sprite(Fichier,188,120,203,135); {Pinceau 12} + Lire_et_ecrire_sprite(Fichier, 1,137, 16,152); {Pinceau 13} + Lire_et_ecrire_sprite(Fichier, 18,137, 33,152); {Pinceau 14} + Lire_et_ecrire_sprite(Fichier, 35,137, 50,152); {Pinceau 15} + Lire_et_ecrire_sprite(Fichier, 52,137, 67,152); {Pinceau 16} + Lire_et_ecrire_sprite(Fichier, 69,137, 84,152); {Pinceau 17} + Lire_et_ecrire_sprite(Fichier, 86,137,101,152); {Pinceau 18} + Lire_et_ecrire_sprite(Fichier,103,137,118,152); {Pinceau 19} + Lire_et_ecrire_sprite(Fichier,120,137,135,152); {Pinceau 20} + Lire_et_ecrire_sprite(Fichier,137,137,152,152); {Pinceau 21} + Lire_et_ecrire_sprite(Fichier,154,137,169,152); {Pinceau 22} + Lire_et_ecrire_sprite(Fichier,171,137,186,152); {Pinceau 23} + Lire_et_ecrire_sprite(Fichier,188,137,203,152); {Pinceau 24} + Lire_et_ecrire_sprite(Fichier, 1,154, 16,169); {Pinceau 25} + Lire_et_ecrire_sprite(Fichier, 18,154, 33,169); {Pinceau 26} + Lire_et_ecrire_sprite(Fichier, 35,154, 50,169); {Pinceau 27} + Lire_et_ecrire_sprite(Fichier, 52,154, 67,169); {Pinceau 28} + Lire_et_ecrire_sprite(Fichier, 69,154, 84,169); {Pinceau 29} + Lire_et_ecrire_sprite(Fichier, 86,154,101,169); {Pinceau 30} + Lire_et_ecrire_sprite(Fichier,103,154,118,169); {Pinceau 31} + Lire_et_ecrire_sprite(Fichier,120,154,135,169); {Pinceau 32} + Lire_et_ecrire_sprite(Fichier,137,154,152,169); {Pinceau 33} + Lire_et_ecrire_sprite(Fichier,154,154,169,169); {Pinceau 34} + Lire_et_ecrire_sprite(Fichier,171,154,186,169); {Pinceau 35} + Lire_et_ecrire_sprite(Fichier,188,154,203,169); {Pinceau 36} + Lire_et_ecrire_sprite(Fichier, 1,171, 16,186); {Pinceau 37} + Lire_et_ecrire_sprite(Fichier, 18,171, 33,186); {Pinceau 38} + Lire_et_ecrire_sprite(Fichier, 35,171, 50,186); {Pinceau 39} + Lire_et_ecrire_sprite(Fichier, 52,171, 67,186); {Pinceau 40} + Lire_et_ecrire_sprite(Fichier, 69,171, 84,186); {Pinceau 41} + Lire_et_ecrire_sprite(Fichier, 86,171,101,186); {Pinceau 42} + Lire_et_ecrire_sprite(Fichier,103,171,118,186); {Pinceau 43} + Lire_et_ecrire_sprite(Fichier,120,171,135,186); {Pinceau 44} + Lire_et_ecrire_sprite(Fichier,137,171,152,186); {Pinceau 45} + Lire_et_ecrire_sprite(Fichier,154,171,169,186); {Pinceau 46} + Lire_et_ecrire_sprite(Fichier,171,171,186,186); {Pinceau 47} + Lire_et_ecrire_sprite(Fichier,188,171,203,186); {Pinceau 48} + + Lire_et_ecrire_sprite(Fichier, 1,188, 7,194); {Diskette 3"} + Lire_et_ecrire_sprite(Fichier, 9,188, 15,194); {Diskette 5"} + Lire_et_ecrire_sprite(Fichier, 17,188, 23,194); {HDD} + Lire_et_ecrire_sprite(Fichier, 25,188, 31,194); {CD-ROM} + Lire_et_ecrire_sprite(Fichier, 33,188, 39,194); {Network} + + Lire_et_ecrire_sprite(Fichier, 1,213,231,268); {Logo GrafX2} + + Ecrire_trames_predefinies(Fichier); + + Rajouter_fichier(Fichier,'FONTE1.FNT',true); {Fonte systme} + + Rajouter_fichier(Fichier,'FONTE2.FNT',true); {Fonte exotique} + + Load_PKM('FONTS.PKM'); + + Coder_partie_de_fonte(Fichier,0,121,45); {Petites fontes} + Coder_partie_de_fonte(Fichier,0,129,45); + Coder_partie_de_fonte(Fichier,0,137,45); + Coder_partie_de_fonte(Fichier,0,145,12); + Coder_partie_de_fonte(Fichier,0,153,44); {Grosse fonte} + Coder_partie_de_fonte(Fichier,0,161,44); + Coder_partie_de_fonte(Fichier,0,169,40); + Coder_partie_de_fonte(Fichier,0,177,40); + + close_eo(Fichier); + close (Fichier); + + asm + mov ax,3 + int 10h + end; + + Generer_l_aide_Credits; + Generer_l_aide_Register; + Generer_l_aide_Greetings; + + + reset(Fichier,1); + seek(Fichier,filesize(Fichier)); + init_eo; + Rajouter_fichier(Fichier,'GFX2.INI',false); + close_eo(Fichier); + + writeln('Le fichier GFX2.DAT est cr. (taille = ',filesize(Fichier),' octets)'); + close(Fichier); +END. diff --git a/dat/MAKEFNT.BAT b/dat/MAKEFNT.BAT new file mode 100644 index 00000000..5928138f --- /dev/null +++ b/dat/MAKEFNT.BAT @@ -0,0 +1,3 @@ +@echo off +img2fnt fonts fonte1 +img2fnt fonts fonte2 17280 \ No newline at end of file diff --git a/dat/MKGREETS.EXE b/dat/MKGREETS.EXE new file mode 100644 index 0000000000000000000000000000000000000000..9043a0ed8e84fdbde9653696bce10039d7a1de13 GIT binary patch literal 4384 zcmbW54^R_#7RTTIVG}|UIJMS8g{A0Pjio>;2Lx)W2Cbu*11ShqN+Dt_0<+mj@2n8Y z-1I`wX?xS&4cE?;qcb-n+znXfZh@;t1Lcp$h;*ju*mkD1wJsOWqtek{jmf=Df`5AE zZtgOC`0ela-uwREzTa zHjIJK%USR90*v2Xzuh~bo@)nC=t*^DQX=!PXur(I8ZcUXH8~oW?^i)9^n+d6nd_%RR z#?IrArQX6@_{zFU*{SkQv?1nsORcp&k!8174ps58i_KCkSR3jqYeKGu0yfI$NZJ4J zIhr0tg^eO}lw(;_HE-oDm37wIdP^joM|ZDZv$e=%+WmCl*5ceXYYi(N>{hsb4H`E@ zHSV(W?DH0z!19*bD!#_X);6$01C|n_mPd_ZSqkl&{)4@$zJ{%;t7B6etuI>Y*0ZTK zmO~Buc~%}zt!}8X@HTl0toLpUf5?i9^22)5miijQ{aZe?oemy32%SgdP5IfvrVNdr zo(F9ynh1F>-)}m2G)hP|5iR6&PIS}W=%(uErsn9T(decd(M>DKsLAI>H$5<_OQqR{ zXGn(IP~bmI&0d0qqa|F~#=CMaGza1%k8GsWfrV9&O^)}CGzdB2g<|EAc07mDzj95B zTF{*}hZZiZVWjb~f3QZH;)fbW`hgm0iU(+fbMCmC^WEKmXAjZf6a?C_+cKl>9v|qtTc#Gf2VBZ|IO6mC`%l8i`p9{q%=Y#|(A0TLs-}pcopuwa~o`x>rE= zDmaerTo(!5EQ~Sh;3MeJu7}g=_)|IL;9_{ypVm9DVJgMBvcp8SjnS9>k)%x?QWGMq zo=O>7Oo*v+`w57v5wDXO*ijN$Vj4U*^d?zbu& zSK^D`eru28@|@%LoS-#2&d){q0%82!4)EyRlO)_~8)3@Yt|YgPy$KF~j*U7U43-Y; zo=S0Dbrdco$}0Ah@2lLKtT-=D1G@SsaUAwk_!MFg^b`6|LY2AIoe8cpaULPRD*@u% z!sEx?T=;6a&eQbp&5!dT!Im(T05>mDXLto?V3fc!T-OrtU2u(ecyvkG(B?~UYM%gS zQWlIPr9p=q1SM@CS{GZD6>YJXusawBldZFLPb5z&!SyNXsj^&KY0hb)v1PDTW2?kgt9RpX`ARjZf}wt| zPdRkb>!XI=^Om@-jx;lz%S7h)dxb^$C%u9uzt1ZqjN#qy2j8k9rc^7fhH_b=gj|pr zP5@~K2n;u7BKy31Cu!&dAK6DlgwSYAgSPP zJX6Y)a={QPNf`S#0Z7%j6jK&kaJWgQty_ZaYP&@rW(J4}wktjI{T~32`KLvtOtGXV zDioFFd&(9x?0@lu)s3?HNv}PJbM3+$T9mr;x(ha%n$*uQ+(?s}3iPr5`4hT;f^)Xu z^ewbKwg?3;L4~3mH^+ErA}d7XwngNgx<~E|%8l#YnDp_B+(@OGy5*mLS9dFvY(!FH zE_wzcs4+nc8nh(f*FBTmP7BJm`gGDF8jsVsO`;<1oK*dZ*d3fF{^7KKbqF&C^{64@P| zP;c2n55vOF*_d8rh1SUR!xE|N3DVi1JRa!_i@6{^6nO7kJF)j%cxn0)ecy&ASGk^H zwl`DKp+H!1ZKQ^)LqW2HtCW_5+Y6N3FP{n;zPB?Y`&3e8P%eQiW`&59TAXEEg^a6N z>3T-BReJxnYiy)hsT8IUyw3CgD#BuJlfkRW{2AOYb5ip2_Cp&hr|&xF?{QCNOs zln`iKphY)ENn9niNr|g;867=O%d^Ul#b^typKxkK$PYignm#fZgO~4l1#%$IaWox- z*kdK>_(YUDW5hUm$QpVtg`FRFtrTI)RLYIB4)HnJgnyJ>v@Z#T+bKy0qG2HbPmGgZ zr)i0^WT|uKGUwjJG1CeMJ!VQmz0fnLpV3dC9Jy&K6(^j!Qo?X zIAG8L;S<4z52*eV!^Z;az_CPu+U&dT`cOAL7z{>KWI6dH@W|gi6oX~)y7L!i^=|)s hk7wa~$GvSZcyI5&UMCm<-ofKf#Q!7!zFzM8{0mt+xRL+> literal 0 HcmV?d00001 diff --git a/dat/MKGREETS.PAS b/dat/MKGREETS.PAS new file mode 100644 index 00000000..bf3d07ed --- /dev/null +++ b/dat/MKGREETS.PAS @@ -0,0 +1,105 @@ +program mkgreets; + +const + NB_MAX_LIGNES=50; + TAILLE_MAX_NICK=14; + +var + Fichier : text; + Greets : array[0..3,0..NB_MAX_LIGNES-1] of string[TAILLE_MAX_NICK]; + Total_nicks: word; + +{-----------------------------} + +procedure Init_greets; +var + i,j:word; +begin + for i:=0 to 3 do + for j:=0 to NB_MAX_LIGNES-1 do + Greets[i,j]:=''; +end; + +{-----------------------------} + +procedure Compter_greets; +var + Temp:String; +begin + Total_nicks:=0; + while not eof(Fichier) do + begin + readln(Fichier,Temp); + inc(Total_nicks); + end; +end; + +{-----------------------------} + +procedure Lire_greets; +var + Nb_nicks:word; +begin + Nb_nicks:=0; + while not eof(Fichier) do + begin + readln(Fichier,Greets[Nb_nicks div Total_nicks, Nb_nicks mod Total_nicks]); + inc(Nb_nicks); + end; +end; + +{-----------------------------} + +procedure Ecrire_greets; +var + i:word; +begin + writeln(Fichier,'{'); + writeln(Fichier,' Ce fichier contient la partie "Greetings ..." de l''aide de GRAFX 2'); + writeln(Fichier,'}'); + writeln(Fichier,''); + writeln(Fichier,'procedure Generer_l_aide_Greetings;'); + writeln(Fichier,'begin'); + writeln(Fichier,' Demarrer_section_d_aide;'); + writeln(Fichier,' {XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX}'); + writeln(Fichier,' {XXXXXXXXXXXXXXXXXXXXXX}'); + writeln(Fichier,' Ecrire_ligne_d_aide(T,''GREETINGS:'');'); + writeln(Fichier,' Ecrire_ligne_d_aide(N,'''');'); + writeln(Fichier,' Ecrire_ligne_d_aide(N,''Our best regards go to...'');'); + writeln(Fichier,' Ecrire_ligne_d_aide(N,'''');'); + + for i:=0 to Total_nicks-1 do + begin + write(Fichier,' Ecrire_ligne_d_aide(N,'' ',Greets[0,i]); + if (Greets[1,i]<>'') then + write(Fichier,' ':TAILLE_MAX_NICK-length(Greets[0,i]),Greets[1,i]); + if (Greets[2,i]<>'') then + write(Fichier,' ':TAILLE_MAX_NICK-length(Greets[1,i]),Greets[2,i]); + writeln(Fichier,''');'); + end; + + writeln(Fichier,' Ecrire_ligne_d_aide(N,'' and all #pixel, #demofr and #coders.'');'); + writeln(Fichier,' {XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX}'); + writeln(Fichier,' {XXXXXXXXXXXXXXXXXXXXXX}'); + writeln(Fichier,' Terminer_section_d_aide;'); + writeln(Fichier,'end;'); +end; + +{-----------------------------} + +begin + Init_greets; + assign(Fichier,'greets.txt'); + reset(Fichier); + Compter_greets; + Total_nicks:=(Total_nicks+2) div 3; + + reset(Fichier); + Lire_greets; + close(Fichier); + + assign(Fichier,'hlp_gret.pas'); + rewrite(Fichier); + Ecrire_greets; + close(Fichier); +end. diff --git a/dat/TABLES.PAS b/dat/TABLES.PAS new file mode 100644 index 00000000..e0ac2dfd --- /dev/null +++ b/dat/TABLES.PAS @@ -0,0 +1,259 @@ +{Ce fichier contient pour chaque type de fonte l'indice qu'il faut coder:} + +const + +TABLE_NORMAL:array[32..151] of byte = +( + 0, + 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, + 0, + 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, + 0, + 0, + 93, + 94, + 95, + 96, + 0, + 97, + 0, + 98, + 99, + 100, + 101, + 0, + 0, + 0, + 0, + 0, + 0, + 102, + 0, + 103, + 0, + 0, + 104, + 105 +); + + + +TABLE_SOUS_TITRE:array[32..90] of byte = +( + 0, + 0, + 0, + 0, + 0, + 0, + 0, + 0, + 0, + 0, + 0, + 0, + 0, + 132, + 133, + 134, + 135, + 136, + 137, + 138, + 139, + 140, + 141, + 142, + 143, + 144, + 145, + 0, + 0, + 0, + 0, + 146, + 0, + 106, + 107, + 108, + 109, + 110, + 111, + 112, + 113, + 114, + 115, + 116, + 117, + 118, + 119, + 120, + 121, + 122, + 123, + 124, + 125, + 126, + 127, + 128, + 129, + 130, + 131 +); + + + + +TABLE_TITRE:array[32..90] of byte = +( + 126, + 126, + 126, + 126, + 126, + 126, + 126, + 126, + 126, + 126, + 126, + 126, + 126, + 96, + 98, + 100, + 102, + 104, + 106, + 108, + 110, + 112, + 114, + 116, + 118, + 120, + 122, + 126, + 126, + 126, + 126, + 124, + 126, + 0, {A} + 2, {B} + 4, {C} + 6, {D} + 8, {E} + 10, {F} + 12, {G} + 14, {H} + 16, {I} + 18, {J} + 20, {K} + 22, {L} + 24, {M} + 26, {N} + 28, {O} + 30, {P} + 32, {Q} + 34, {R} + 36, {S} + 38, {T} + 40, {U} + 42, {V} + 88, {W} + 90, {X} + 92, {Y} + 94 {Z} +); + diff --git a/dat/gfx2.ini b/dat/gfx2.ini new file mode 100644 index 00000000..ff02bc72 --- /dev/null +++ b/dat/gfx2.ini @@ -0,0 +1,289 @@ +###### GrafX2 initialization file ###### Fichier d'initialisation de GrafX2 ## +# # # # +# You may modify this file with any # Vous pouvez modifier ce fichier avec # +# standard ASCII text editor. # n'importe quel diteur de texte # +# # ASCII standard. # +# # # +# Comments are preceded by ';' or # Les commentaires sont prcds par # +# '#'. # ';' ou '#'. # +# # # +# Options are not case sensitive and # Les options ne sont pas sensibles # +# spaces are ignored. # la casse et les espaces sont ignors.# +# # # +# You must not change the order of # Vous ne devez pas changer l'ordre # +# the sections and their options. # des sections et de leurs options. # +# You must not delete or put into # Vous ne devez pas effacer ou mettre # +# comment any section nor option. # en commentaire une section ou option.# +# # # +# Each option is preceded by a # Chaque option est prcde par un # +# comment which explains its meaning. # commentaire qui explique sa fonction.# +# # # +############################################################################## + + + +[MOUSE] # [SOURIS] + + ; The sensitivity of the mouse can La sensibilit de la souris peut + ; take values from 1 to 64. The prendre des valeurs de 1 64. Plus + ; smaller values, the faster. les valeurs sont petites, plus c'est + ; rapide. + X_sensitivity = 3 ; (default 3) + Y_sensitivity = 3 ; (default 3) + + ; Due to the fact that those stupid A cause du fait que ces imbciles de + ; mouse drivers' makers don't care programmeurs de gestionnaires de + ; if the mouse moves by steps of 2, souris se fichent que votre souris se + ; 4 or even 8 pixels, we have to deplace par pas de 2, 4 ou mme 8 + ; stretch the virtual area of the pixels, nous devons largir la zone + ; mouse and divide coordinates to virtuelle de la souris et diviser les + ; get a one-pixel step motion. coordonnes pour obtenir un pas de 1. + ; (Warning: the mouse movement can (Attention: le dplacement de la + ; be correct in some video modes souris peut tre correct dans certains + ; but not in others... But all the modes vidos mais pas dans d'autres... + ; "Modes X" should behave the same Mais tout les Modes X devraient se + ; way, so you won't have to test comporter de la mme manire, donc + ; them all). vous n'aurez pas tous les tester. + ; A correction factor of 0 means Un facteur de correction de 0 signifie + ; that you are very lucky because que vous avez de la chace car votre + ; your driver doesn't need any driver n'a pas besoin de correction. + ; correction. If you set the Si vous dfinissez le facteur de + ; correction factor to 1, it means correction 1, cela signifie que + ; that your mouse moves by steps of votre souris se dplace par pas de 2 + ; 2 pixels; 2 for 4; 3 for 8, etc... pixels; 2 pour 4; 3 pour 8, etc... + ; If you want to use GrafX2 in a Si vous dsirez lancer GrafX2 dans une + ; Win95 window, you should turn fentre Windows95, vous devriez passer + ; these values to 0 (and increase X ces valeurs 0 (et augmenter les sen- + ; and Y sensitivities above). sibilits X et Y dfinies plus haut). + X_correction_factor = 3 ; (default 3) + Y_correction_factor = 3 ; (default 3) + + ; Aspect of the main cursor (cross) Aspect du curseur principal (croix) + ; 1: Solid 1: Solide + ; 2: Transparent 2: Transparent + ; 3: Thin (solid) 3: Fin (solide) + Cursor_aspect = 1 ; (default 1) + + + +[MENU] # [MENU] + + ; Colors of the menus (the black Couleurs des menus (la couleur noire + ; and the white colors cannot be et la couleur blanche ne peuvent pas + ; modified). tre modifies). + ; Values are in {Red,Green,Blue} Les valeurs sont dans l'ordre {Rouge, + ; order and are between 0 and 63. Vert,Bleu} et vont de 0 63. + Light_color = 42,42,42 ; (default 42,42,42) + Dark_color = 27,27,27 ; (default 27,27,27) + ; + ; Light_color = 24,25,30 ; \_ Nightmare + ; Dark_color = 13,14,19 ; / + ; + ; Light_color = 10,45,28 ; \_ Forest + ; Dark_color = 5,27,12 ; / + ; + ; Light_color = 48,41,26 ; \_ Gold + ; Dark_color = 26,22,15 ; / + ; + ; Light_color = 10,40,55 ; \_ Oceanic + ; Dark_color = 10,20,32 ; / + + ; Aspect ratio and size of the Proportion des menus et de la barre + ; menus and the tool-bar. d'outils. + ; Possible values: Valeurs possibles: + ; 0: Do not adapt (pixels are not 0: Ne pas adapter (les pixels ne sont + ; stretched) pas tirs) + ; 1: Adapt the menus and the tool- 1: Adapter les menus et la barre + ; bar according to the resolution d'outils suivant la rsolution + ; 2: Slightly adapt the ratio of 2: Adapter lgrement les proportions + ; the menus and tool-bar des menus et de la barre d'outils + Menu_ratio = 1 ; (default 1) + + ; Font: Police de caractres (fonte): + ; 1: Classic 1: Classique + ; 2: Fun 2: Fun + Font = 1 ; (default 1) + + + +[FILE_SELECTOR] # [SELECTEUR_DE_FICHIERS] + + ; Show special files and Afficher les fichiers et rpertoires + ; directories (values are 'yes' or spciaux (les valeurs sont 'yes' ou + ; 'no'). 'no'). + Show_hidden_files = no ; (default 'no') + Show_hidden_directories = no ; (default 'no') + Show_system_directories = no ; (default 'no') + + ; Delay before displaying a preview Dlai avant d'afficher une preview + ; in file-selectors (in 18.2th of dans les slecteurs de fichiers (en + ; second). Possible values range 18.2mes de seconde) Les valeurs + ; from 1 to 256. possibles vont de 1 256. + Preview_delay = 8 ; (default 8) + + ; Maximize the preview of the Maximiser la preview des images pour + ; pictures so that it is as big as qu'elle soit aussi grande que + ; possible. If you're not in the possible. + ; same resolution as the picture's Si vous n'tes pas dans la mme rso- + ; one, it can try to correct the lution que celle de l'image, cela peut + ; aspect ratio, but if the picture essayer de corriger les proportions, + ; does not fill the whole screen, mais si l'image ne prend pas tout + ; it can be worse. l'cran, cela peut tre pire. + Maximize_preview = no ; (default 'no') + + ; This option is used to place the Cette option est utilise pour placer + ; selection bar on a filename by la barre de slection sur un nom de + ; typing its first letters. fichier en tapant ses 1res lettres. + ; For example, if you want to find Par exemple, si vous voulez trouver le + ; the "PICTURE.PKM" in a directory fichier "PICTURE.PKM" dans un rper- + ; that also contains "PALETTE.PAL", toire contenant galement le fichier + ; you'll just have to type P and I. "PALETTE.PAL", vous n'aurez qu' taper + ; The different values of "FFF" P puis I. + ; indicate if you want to find the Les different valeurs de "FFF" + ; name in both files and directories indiquent si vous voulez trouvez le nom + ; or just in only one of these: dans les fichiers ET les rpertoires ou + ; 0: files and directories simplement dans l'un OU l'autre. + ; 1: files only 0: fichiers et rpertoires + ; 2: directories only 1: fichiers seulement + ; 2: rpertoires seulement + Find_file_fast = 0 ; (default 0) + + +[LOADING] # [CHARGEMENT] + + ; Automatically set the resolution Passer automatiquement dans la bonne + ; when loading a picture. rsolution lors du chargement d'une + ; You should set this value to image. + ; 'yes' after disabling the video Vous devriez dfinir cette option + ; modes that are not supported by 'yes' aprs avoir inhib les modes + ; your video card or monitor. vido qui ne sont pas supports par + ; votre matriel. + Auto_set_resolution = no ; (default 'no') + + ; If the variable above is set to Si la variable ci-dessus est 'yes', + ; 'yes', this one tells if you want celle-ci indique si vous voulez + ; to set the resolution according dfinir la rsolution suivant: + ; to: 1: les dimensions de "l'cran + ; 1: the internal "original screen" d'origine" internes l'image + ; dimensions of the picture 2: les vritables dimensions de + ; 2: the actual dimensions of the l'image + ; picture + Set_resolution_according_to = 1 ; (default 1) + + ; If you load a picture with a Si vous chargez une image ayant une + ; palette of less than 256 colors, palette de moins de 256 couleurs, + ; this option defines if you want cette option indique si vous souhaitez + ; to clear the palette or to keep effacer la palette ou bien conserver + ; the colors of the previous les couleurs de l'image prcdente qui + ; picture that are over the number se situent au-del du nombre de la + ; of colors of the new picture. nouvelle image. + ; For example, if you load a Par exemple, si vous chargez une image + ; 32-color picture, the colors 32 de 32 couleurs, les couleurs 32 255 + ; to 255 will be set to black if seront passes en noir si cette option + ; this option is set to 'yes', or est 'yes', ou bien elles resteront + ; they will be kept unchanged if inchanges si elle est 'no'. + ; this option is set to 'no'. + Clear_palette = yes ; (default 'yes') + + +[MISCELLANEOUS] # [DIVERS] + + ; Draw the limits of the picture. Afficher les limites de l'image + Draw_limits = yes ; (default 'yes') + + ; Adjust the brush grabbing in Ajuster la capture de brosse en mode + ; "grid" mode. "grille". + Adjust_brush_pick = yes ; (default 'yes') + + ; Coordinates: Coordonnes: + ; 1: Relative 1: Relatives + ; 2: Absolute 2: Absolues + Coordinates = 1 ; (default 1) + + ; Create a backup file when saving. Crer un fichier backup lors des + ; sauvegardes. + Backup = no ; (default 'no') + + ; Number of pages stored in memory Nombre de pages stockes en mmoire + ; for "undoing". destines annuler les dernires + ; Values are between 1 and 99. modifications. Valeurs entre 1 et 99. + Undo_pages = 1 ; (default 1) + + ; Speed of the scroll-bars (in VBLs Vitesse des barre de dfilement (en + ; waited) while clicking with the VBLs attendus) lorsque l'un des + ; left or right button of the mouse. boutons de la souris est enfonc. + ; Values can be between 1 and 255. Les valeurs sont comprises entre 1 et + ; The bigger values, the slower. 255. Plus elles sont grandes, plus + ; c'est lent. + Gauges_scrolling_speed_Left = 10 ; (default 10) + Gauges_scrolling_speed_Right = 3 ; (default 3) + + ; Automatically save the configu- Enregistre automatiquement la configu- + ; ration when exiting the program. ration lorsqu'on quitte le programme. + Auto_save = yes ; (default 'yes') + + ; Maximum number of vertices used Nombre maximum de vertex utiliss dans + ; in filled polygons and polyforms, les polygnes et polyformes pleins, et + ; and lasso. Possible values range le lasso. Les valeurs possibles vont + ; from 2 to 16384. de 2 16384. + ; Each vertex takes 4 bytes. Chaque vertex prend 4 octets. + Vertices_per_polygon = 1024 ; (default 1024) + + ; Automatically zoom into the Zoomer automatiquement la zone pointe + ; pointed area when you press the par la souris lorsque vous appuyez sur + ; short-key of the Magnifier button la touche de raccourci de la loupe. + ; while being above the picture. + Fast_zoom = yes ; (default 'yes') + + ; Separate the colors in the tool- Sparer les couleurs dans la barre + ; bar by a black squaring. d'outils par un quadrillage noir. + Separate_colors = yes ; (default 'yes') + + ; Initial value of the feedback for Valeur initiale du "feedback" pour les + ; the drawing modes (cf. docs). modes de dessin (cf. docs). + FX_feedback = yes ; (default 'yes') + + ; When you reduce the palette or Si vous rduisez la palette ou "zappez" + ; "zap" some colors out of it, it is quelques couleurs, il est possible + ; possible that there are not enough qu'il ne reste pas assez de couleurs + ; colors left to draw the menus. pour afficher les menus. Mettre cette + ; Switching the following variable variable 'yes' ramnera automatiquent + ; on will bring back the colors of les couleurs du menu s'il reste moins + ; the menu if there are less than 4 de 4 couleurs aprs une "rduction" ou + ; colors left after "reducing" or un "zapping". + ; "zapping". + Safety_colors = yes ; (default 'yes') + + ; Display a message at startup Afficher un message au dmarrage + ; telling the version number of the indiquant le numro de version du + ; program. programme. + Opening_message = yes ; (default 'yes') + + ; Take the Stencil into account when Prendre le Stencil en compte lorsqu'on + ; clearing the image. efface l'image. + Clear_with_stencil = yes ; (default 'yes') + + ; Directly set the discontinuous Passer automatiquement en mode de + ; freehand drawing mode after brush dessin discontinu aprs la prise d'une + ; grabbing. brosse. + Auto_discontinuous = no ; (default 'no') + + ; Save the screen dimensions in GIF Sauver les dimensions de l'cran dans + ; files. If you want to read these les fichiers GIF. Si vous voulez lire + ; files with Photoshop or Alchemy, ces fichiers avec Photoshop ou Alchemy, + ; and maybe some other programs, you et peut-tre d'autres programmes, vous + ; must set this option to 'no'. devez mettre cette option 'no'. + Save_screen_size_in_GIF = no ; (default 'no') + + ; Automaticaly count the number of Compter automatiquement le nombre de + ; different colors used when opening couleurs diffrentes utilises lors de + ; the palette editor window. (Set it d'ouverture de la fentre d'dition de + ; to 'no' if you have a slow PC or la palette. (Mettez-le 'no' si vous + ; if you edit huge pictures) avez un PC lent ou bien si vous ditez + ; d'normes images). + Auto_nb_colors_used = yes ; (default 'yes') + + ; Number of the default video mode Numro du mode vido par dfaut au + ; at startup (see the list by typing dmarrage (voir la liste en tapant + ; "gfx2 /?" at the DOS prompt). "gfx2 /?" sur la ligne de commande). + Default_video_mode = 0 ; (default 0) diff --git a/divers.c b/divers.c new file mode 100644 index 00000000..b64d625b --- /dev/null +++ b/divers.c @@ -0,0 +1,93 @@ +#include + +#include "struct.h" +#include "sdlscreen.h" +#include "global.h" + +word Palette_Compter_nb_couleurs_utilisees(dword* Tableau) +{ + int Nombre_De_Pixels=0; //ECX + Uint8* Pixel_Courant=Ecran; //ESI + Uint8 Couleur; //AL/EAX + word Nombre_Couleurs=0; + int i; + + + + //Calcul du nombre de pixels dans l'image + Nombre_De_Pixels=Principal_Hauteur_image*Principal_Largeur_image; + + // On parcourt l'cran courant pour compter les utilisations des couleurs + for(i=0;i++;i>Nombre_De_Pixels) + { + Couleur=*Pixel_Courant; //on lit la couleur dans l'cran + + Tableau[Couleur]++; //Un point de plus pour cette couleur + + // On passe au pixel suivant + Pixel_Courant++; + } + + //On va maintenant compter dans la table les couleurs utilises: + + Couleur=0; //EDX + + do + { + if (Tableau[Couleur]!=0) + Nombre_Couleurs++; + + Couleur++; + + }while (Couleur<256); + + return Nombre_Couleurs; +} + +void Set_palette(T_Palette Palette) +{ + SDL_SetPalette(Ecran, SDL_LOGPAL|SDL_PHYSPAL, Palette, 0, 256); +} + +void Attendre_fin_de_click(void) +{ + do + SDL_PumpEvents(); + while (SDL_GetMouseState(NULL, NULL)&SDL_BUTTON(0)); +} + +void Effacer_image_courante_Stencil(byte Couleur, byte * Pochoir) +//Effacer l'image courante avec une certaine couleur en mode Stencil +{ + int Nombre_De_Pixels=0; //ECX + //al=Couleur + //edi=Ecran + Uint8* Pixel_Courant=Ecran; //dl + int i; + + Nombre_De_Pixels=Principal_Hauteur_image*Principal_Largeur_image; + + for(i=0;i++;i0 = droite, Ellipse_Curseur_X<0 = gauche) et +// Ellipse_Curseur_Y pixels (Ellipse_Curseur_Y>0 = en bas, +// Ellipse_Curseur_Y<0 = en haut) du centre se trouve dans l'ellipse en +// cours. + +byte Pixel_dans_cercle(void); +// Indique si le pixel se trouvant Cercle_Curseur_X pixels +// (Cercle_Curseur_X>0 = droite, Cercle_Curseur_X<0 = gauche) et +// Cercle_Curseur_Y pixels (Cercle_Curseur_Y>0 = en bas, +// Cercle_Curseur_Y<0 = en haut) du centre se trouve dans le cercle en +// cours. + +byte Bit(byte Octet, byte Rang); +// Extrait un bit d'un certain rang partir d'un octet. + +byte Couleur_ILBM_line(word Pos_X, word Vraie_taille_ligne); +// Renvoie la couleur du pixel (ILBM) en Pos_X. + +// Gestion du chrono dans les fileselects +void Initialiser_chrono(long Delai); +void Tester_chrono(void); + +void Remplacer_une_couleur(byte Ancienne_couleur, byte Nouvelle_couleur); +void Remplacer_toutes_les_couleurs_dans_limites(byte * Table_de_remplacement); + +byte Meilleure_couleur(byte Rouge,byte Vert,byte Bleu); +byte Meilleure_couleur_sans_exclusion(byte Rouge,byte Vert,byte Bleu); + +byte Effet_Colorize_interpole (word X,word Y,byte Couleur); +byte Effet_Colorize_additif (word X,word Y,byte Couleur); +byte Effet_Colorize_soustractif(word X,word Y,byte Couleur); +byte Effet_Trame(word X,word Y); + +void Flip_Y_LOWLEVEL(void); +void Flip_X_LOWLEVEL(void); +void Rotate_90_deg_LOWLEVEL(byte * Source,byte * Destination); +void Rotate_180_deg_LOWLEVEL(void); +void Zoomer_une_ligne(byte * Ligne_originale,byte * Ligne_zoomee,word Facteur,word Largeur); +void Copier_une_partie_d_image_dans_une_autre(byte * Source,word S_Pos_X,word S_Pos_Y,word Largeur,word Hauteur,word Largeur_source,byte * Destination,word D_Pos_X,word D_Pos_Y,word Largeur_destination); diff --git a/doc/Le moteur des opérations.html b/doc/Le moteur des opérations.html new file mode 100644 index 00000000..95b43913 --- /dev/null +++ b/doc/Le moteur des opérations.html @@ -0,0 +1,384 @@ + + + + + + + +GrafX2 - Le moteur des oprations + + + + +

GrafX2 - Le moteur des oprations

+ +
+ +

Explication du principe :

+ +

Qu'appelle-t'on une opration? C'est l'emploi d'un outil de +dessin. Par exemple, le trac libre la main d'un pinceau (ou +d'une brosse) est une opration. Plus exactement, c'est tout +comportement de la souris lorsqu'elle se trouve sur les pixels de +l'image dite. De ce fait, la gestion de la pipette se fait +galement au travers des oprations.

+ +

Le moteur charg de grer ces oprations est simplifi +autant que possible. Son principe est le suivant : lorsque +la souris est au-dessus de l'image, la boucle principale de +gestion de GrafX2 (situe dans MOTEUR.C) dtermine la partie +atomique d'instructions excuter, puis l'excute, pour +chaque combinaison d'un type d'opration (un entier, que l'on +nommera pour les besoins de cette page ID_OP), d'un tat de la +souris (tat de ses boutons plus exactement, cod sur un entier +galement), et d'un nombre de valeurs prsentes dans une pile +(pas la pile systme, mais une pile de mots 16-bits +spcialement mise en place pour les oprations, afin qu'elles y +stockent des paramtres pour les oprations suivantes). On +appelle "partie atomique" une squence d'instructions +qui doivent tre excutes intgralement chaque itration +de la boucle principale. Elle se contente de ne faire que ce +qu'elle doit faire face la situation qu'implique la +combinaison (ID_OP,Code souris, Etat pile) pour laquelle elle est +appele.

+ +

En fait, le moteur doit tre aid pour dterminer les +insctructions excuter. Chacune de ces parties atomiques est +crite sous la forme d'une fonction contenant tout le code qui +lui est ncessaire. Ces fonctions sont ce que l'on a appel des +"fonction_action" (dfinition dans STRUCT.H), c'est +dire une simple fonction qui ne reoit pas de paramtres et qui +n'en renvoie pas. Un simple void Ma_fonction(void)...

+ +

Il n'est pas dans mon intention de vous apprendre crire +ces fonctions atomiques. Dans le cas des oprations les plus +simples implmenter selon ce principe, la conception des +parties atomiques est assez intuitive, mais il arrive dans +certains cas que la mthode trouve certaines limites, il faut +alors tricher un peu (mais gentiment! - en plaant des valeurs +arbitraires dans la pile uniquement pour permettre la transition +vers une autre combinaison choisie, donc une autre partie +atomique, par exemple). Vous pourrez trouver tous les exemples +que vous voudrez dans le fichier OPERATIO.C.

+ +

Aprs avoir crit les parties atomiques qui vont tre +ncessaires pour la gestion complte d'une opration (dans le +fichier OPERATIO.C), et avoir renseign les prototypes de ces +fonctions (dans OPERATIO.H), il faut indiquer au moteur dans +quelles conditions utiliser ces fonctions. Cela se fait dans la +phase d'initialisation du programme (situe dans le fichier +INIT.C), o l'on renseigne chacune des fonctions atomiques, en +dcrivant les valeurs de combinaison qui doivent dclencher +leur appel. La fonction appele se contente d'en prendre note en +remplissant un tableau nomm "Operation" (variable +globale dclare dans GLOBAL.H, et indexe par les 3 valeurs +de la combinaison : ID_OP, code souris, tat pile) l'aide de +l'adresse de la fonction appeler. Ce tableau va servir au +moteur faire un appel direct de la fonction atomique d'aprs +la combinaison, sans avoir faire toute une srie de tests +(swich/case) fastidieux.

+ +

Comme nous avons pressenti qu'il arriverait frquemment que +des fonctions atomiques auraient besoin systmatiquement +d'effacer la souris pour faire des affichages l'cran ou dans +l'image, et de la rafficher ensuite, et dans le souci d'viter +de faire abusivement du copier/coller de code, nous avons +rajout un boolen dans le tableau Operation qui permet +d'indiquer que la fonction atomique demande au moteur de se +charger lui-mme de l'effacement et de la restauration du +curseur de la souris l'cran. Finalement, je ne suis pas +certain que cela s'est rvel d'une grande utilit, mais je +vous le signale tout de mme pour que vous compreniez +l'existance du paramtre "Effacer souris" qu'il faut +indiquer lorsqu'on renseigne une fonction atomique lors de +l'initialisation.

+ +

Il est important de noter qu'une fonction atomique est +appele en permanence par la boucle principale, indpendamment +du fait que la souris change d'tat ou non. Ces appels +rpts permettent par exemple d'avoir un spray qui continue + agir lorsqu'on presse le bouton de la souris sans la +dplacer.

+ +

De plus, les fonctions atomiques n'ont pas se soucier du +positionnement de la souris car ds que la pile contient des +donnes (gnralement ds le premier clic), la souris est +limite par le moteur afin de ne pas sortir de l'image. Le +moteur s'assure galement que la souris ne franchis pas la barre +de split en mode "loupe". Enfin, n'oubliez pas de vider +compltement la pile en temps voulu, lorsque l'opration peut +s'achever! ;-)

+ +
+ +

Informations pour l'implmentation :

+ +
    +
  • Le renseignement d'une fonction atomique se fait dans + INIT.C l'aide de :
  • +
+ +
+

Initialisation_operation(ID_OP, Etat souris, Taille pile, + Callback, Effacer souris);

+
+ +
    +
  • La pile disposition des oprations pour le stockage + des paramtres :
      +
    • Elle contient des mots 16-bits (type word, + dfinit dans STRUCT.H)
    • +
    • Pour y poser une valeur : + Operation_PUSH(val)
    • +
    • Pour en retirer une valeur : + Operation_POP(&var)
    • +
    • Exemples de valeurs y mettre : + coordonnes de souris, de pinceau... des + couleurs... des valeurs bidons pour changer + l'tat de la pile...
      +
    • +
    +
  • +
  • A l'intrieur d'une fonction atomique :
      +
    • Si la fonction correspond la premire tape + d'une opration, appeler + Initialiser_debut_operation()
    • +
    • Si la fonction correspond la premire tape + d'une opration qui peut modifier l'image, + appeler Backup() avant modification de l'image ; + ce qui permettra l'utilisateur d'annuler la + modification avec "undo" s'il le + souhaite.
    • +
    • Pour afficher les coordonnes de la souris, + appeler Print_coordonnees() sans vous soucier de + savoir si la barre d'outils est visible. Si vous + avez besoin d'afficher une coordonne qui doit + s'adapter au mode relatif ou absolu (selon le + paramtrage effectu par l'utilisateur), + utilisez Aff_coords_rel_ou_abs(RefX,RefY). Si les + coordonnes sont configures pour tre + relatives, cette fonction affichera la + diffrence entre les coordonnes actuelles du + pinceau et les coordonnes de rfrence + passes en paramtres. Dans le cas d'infos + spciales afficher dans la barre de menu, on + pourra se servir de la fonction + Print_dans_menu(texte,position en caractres).
    • +
    • Si vous avez besoin de vous assurer que les + boutons de la souris sont relchs un moment + de la fonction, utilisez Attendre_fin_de_click()
    • +
    • Etudiez OPERATIO.C pour avoir des exemples.
      +
    • +
    +
  • +
  • Pour dmarrer une opration (aprs avoir cliqu sur + un bouton de la barre d'outils par exemple), appeler + Demarrer_pile_operation(ID_OP). Note: il faut que le + curseur soit cach avant l'appel (et son tat n'est pas + chang aprs). (voir exemples dans BOUTONS.C)
    +
  • +
  • On peut connatre l'ID_OP de l'opration en cours + grce la variable globale Operation_en_cours
    +
  • +
  • La variable globale Operation_Taille_pile correspond + la taille de la pile d'oprations. Elle peut tre + consulte et ventuellement modifie (mme s'il est + prfrable d'utiliser Operation_PUSH et Operation_POP + dans ce dernier cas).
  • +
+ +
+ +

Comment rajouter une opration?

+
+ + + + + + + + + + + + + + + + + +
Dans CONST.H :
    +
  • rajouter un identifiant (ID_OP) dans l'enum + OPERATIONS (exemple : OPERATION_DUMMY)
  • +
+
Dans GLOBAL.H :
    +
  • rajouter l'identifiant de la forme de curseur + utiliser pour cette opration dans la table + CURSEUR_D_OPERATION[]. Faites bien attention + l'insrer au bon endroit (place correspondant + ID_OP).
  • +
+
Dans OPERATIO.C :
    +
  • Ecrire chaque fonction atomique de l'opration.
  • +
+
+

Exemple :

+
+
+
+

void Dummy_1_0(void)
+ // Opration : OPERATION_DUMMY
+ // Click Souris: 1
+ // Taille_Pile : 0
+ // Souris efface: Oui (prcis grce + Initialiser_operation() dans INIT.C)
+ {
+      Initialiser_debut_operation();
+      Backup();
+
+      // ACTIONS...
+
+      Operation_PUSH(une_valeur_ncessaire_pour_les_prochaines_tapes);
+      Operation_PUSH(une_autre_valeur_ncessaire_plus_tard);
+ }

+
+
+
+
+

(Pour cet exemple, l'tape suivante + dfinir sera donc une tape avec la taille de + pile 2)

+
+
+
    +
  • Il y a une action par dfaut qui se contente + d'afficher les coordonnes de la souris + lorsqu'on ne dfinit pas explicitement de + fonction atomique grant une certaine + combinaison (ID_OP, Etat souris, Taille pile).
  • +
  • Si l'opration reprsente une interruption + temporaire, et qu'il vous parat juste de + restaurer l'opration prcdente une fois + qu'elle est termine (cas de la loupe, de la + pipette, des prises de brosse, ...), rajouter + l'ID_OP dans la section correspondante de la + fonction Demarrer_pile_operation(), en dbut de + fichier.
  • +
  • Si l'opration voit un intrt accepter que + l'utilisateur change de couleur de pinceau en + cours d'opration (cas du dessin continu, + discontinu, le spray, et les lignes centres), + rajouter l'ID_OP dans la section correspondante + de la fonction Demarrer_pile_operation(), en + dbut de fichier.
  • +
+
Dans OPERATIO.H :
    +
  • Ecrire le prototype des ces fonctions atomiques.
  • +
+
Dans INIT.C :
    +
  • Dans Initialisation_des_operations(), pour chaque + fonction atomique de l'opration, crire un + appel Initialiser_operation(ID_OP, Etat + souris, Taille pile, Callback, Effacer souris);
      +
    • ID_OP : identifiant de l'opration + dont dpend la fonction atomique + (dfini dans CONST.H)
    • +
    • Etat souris :
        +
      • 0 = boutons relachs
      • +
      • 1 = bouton gauche enfonc
      • +
      • 2 = bouton droit enfonc
      • +
      • (note : l'tat "boutons + gauche et droit enfoncs" + n'existe pas, seuls les 3 tats + ci-dessus sont autoriss)
      • +
      +
    • +
    • Taille pile : nombre de paramtres + dans la pile
    • +
    • Callback : nom de la fonction + atomique appeler pour la combinaison + des 3 paramtres prcdents
    • +
    • Effacer souris : boolen indiquant + que le moteur se chargera d'effacer le + curseur souris avant l'appel la + fonction atomique, et de le rafficher + aprs sa sortie.
    • +
    +
  • +
+
+

Exemple :

+
+
+
+

Initialiser_operation(OPERATION_DUMMY, 1, 0, + Dummy_1_0, 1);

+
+
+
+
+ + + + + diff --git a/doc/Les entrées.html b/doc/Les entrées.html new file mode 100644 index 00000000..d01ee1ba --- /dev/null +++ b/doc/Les entrées.html @@ -0,0 +1,176 @@ + + + + + + + +GrafX2 - Les entres + + + + +

GrafX2 - Les entres

+ +
+ +

Get_input() (dans DIVERS.ASM):

+ +
    +
  • Touches :
      +
    • Met jour la variable "Touche", un + mot 16-bits qui contient dans sa partie basse la + valeur du scan-code (valeur plutt lie la + gographie de la touche) de la touche enfonce + traiter, et dans sa partie haute un codage des + touches de contrles enfonces au moment de + l'appel.
        +
      • (Touche & 0x0100) => Shift
      • +
      • (Touche & 0x0200) => Control
      • +
      • (Touche & 0x0400) => Alt
      • +
      +
    • +
    • Met dans la variable "Touche_ASCII" la + valeur ASCII (valeur lie au caractre que + reprsente la touche) de la touche enfonce + traiter.
    • +
    • Dans le cas o la variable globale + "Autoriser_changement_de_couleur_pendant_operation" + serait 0, et qu'il existerait au moins une + valeur dans la pile des oprations, la fonction + filtre les touches. Cela signifie que l'on ne + peut pas interrompre une opration en cours, + sauf pour changer la couleur du pinceau si + l'opration l'autorise (utile pour faire varier + la couleur du pinceau l'aide des touches + pendant qu'on dessine).
    • +
    +
  • +
  • Souris :
      +
    • Met jour la position (Mouse_X,Mouse_Y) de la + souris en fonction de sa position dans un cran + virtuel. Cet cran est volontairement plus grand + que la rsolution relle du mode vido car de + nombreux drivers ne fournissent pas la position + de la souris au pixel prs...
    • +
    • Met jour l'tat des boutons de la souris + (Mouse_K). La variable vaut 0 si aucun bouton + n'est enfonc, 1 si seul le bouton gauche est + enfonc, et 2 si seul le bouton droit est + enfonc. Dans le cas o les 2 boutons seraient + enfonc, Get_input() considre qu'aucun bouton + n'est enfonc (Mouse_K = 0).
    • +
    • La fonction corrige la position de la souris afin + de l'empcher de sortir de la surface d'image + sur laquelle elle se trouve si au moins une + valeur est dans la pile des oprations (la + souris ne sort pas de la zone de dessin tant que + l'opration de dessin n'est pas termine), et + elle simule galement le dplacement et les + clics de la souris si la combinaison de touches + courante correspond de telles commandes. Dans + ce dernier cas, la touche est ensuite filtre + afin d'viter de faire travailler la fonction + appelante pour rien.
    • +
    • Dans le cas o la souris change d'tat ou que + la variable globale + "Forcer_affichage_curseur" est place + 1, le curseur de la souris est raffich. La + fonction laisse toujours la variable + Forcer_affichage_curseur 0 en fin d'appel.
    • +
    • La fonction fait appel + Calculer_coordonnees_pinceau() qui se charge de + calculer convenablement les coordonnes du + pinceau (Pinceau_X,Pinceau_Y) en fonction de la + position de la souris l'cran, de la position + de la zone de dessin dans l'image, du facteur de + zoom et de l'effet de la grille.
    • +
    +

    Important : Dans la plupart des cas, + vous n'avez pas appeler cette fonction car le moteur + (boucle principale, gestionnaire de fentre, slecteurs + de fichier, ...) s'en est dj charg. Vous pouvez + donc considrer que les variables concernes sont + dj jour. Si vous appeliez vous-mme la fonction + Get_input() un moment inoportun, certaines commandes + de l'utilisateur, prises en compte par le moteur, ne + seraient pas traites.

    +
  • +
+ +

Attendre_fin_de_click() (dans DIVERS.ASM):

+ +
+

S'il vous arrive d'avoir besoin de vous assurer que + l'utilisateur n'appuie plus sur les boutons de la souris + un instant donn, cette fonction attend jusqu' ce que + l'utilisateur relache le bouton. La valeur de Mouse_K vaut + alors 0, mais s'il a dplac la souris avant de suspendre + sa pression, la position (Mouse_X,Mouse_Y) n'est pas encore + jour. Cependant, cela ne devrait pas tre gnant (au + pire, un appel Get_input() mettra ces valeurs jour).

+
+ + + + + diff --git a/doc_eng.txt b/doc_eng.txt new file mode 100644 index 00000000..4e7afbe0 --- /dev/null +++ b/doc_eng.txt @@ -0,0 +1,1983 @@ + Ŀ + + + + .00 + + + + + + GRAFX 2.00 96.5% + + - USER'S MANUAL - + + + Ŀ + CONTENTS + + + - Presentation + - Required equipment + - Configuration files + - Available options + - Let's talk about $$$, baby + - Drawing tips + - Trouble-shooting/General hints/FAQ + + + + + + +Presentation: + + + This program is designed for drawing 256-color pictures in a huge range of + resolutions (actually, there are 60 with some coming from the Amiga world). + No one can contest that most of the beautiful GFX of the Scene were drawn + on Amiga. But these GFX are in video resolutions that aren't the common PC + modes. So we wanted to make the first paint program on PC that could + visualize those pictures, and that could allow you, of course, to draw yours + in the video mode that you want. + + This program was first shown at the Wired'96 where it met a big success + (bigger than all our expects) so we hope you'll like it too. + + It's made up of many drawing tools, effects and menus. All the effects + will work with any drawing tool. + + This software has been created for YOU, PC users who envy Amiga owners + for their fantastic paint programs. This software doesn't pretend to replace + the best programs on Amiga, but it modestly tries to fill the gap between PC + and Amiga in the field of bitmap drawing. + If you dream about a very useful option we haven't thought of yet, do not + hesitate to tell us. If we also think it can be useful, and above all if it + is possible to include it in the program :), then we'll implement it as soon + as possible. + + + + +Required equipment: + + + To run GrafX2, you'll need: + + - a PC (386DX or higher), + - DOS 5 or higher (maybe it works with DOS 3.1 but we don't remember which + functions of the INT 21h we use), + - a VGA compatible video card (a VLB or PCI card is strongly recommended) + - a mouse (and its driver), + - 3 Megabytes of RAM (can work with less if you use the DOS4GW or Windows + disk-cache). + + But if you want to use it more efficiently, you'll need: + + - at least a 486DX66 (to improve global speed), + - at least 8 Mb of RAM for grabbing very big brushes and to use multi-undo, + - a VESA 1.2 (or later) compatible video card (to access more video modes). + + + + +Configuration files: + + + GrafX2 needs two files to store its configuration: 'GFX2.INI' and + 'GFX2.CFG'. + + GFX2.INI: + + + This file contains the parameters defined in the settings menu and some + others. You may edit this file with any standard ASCII editor. + When you click on Reload in the settings menu, all the data contained in + this file are restored. When you click on Save or when you quit the + program with the Auto-save option on, all the current parameters are + written into (updated in) this file. + + If you corrupted this file and don't manage to fix the problem, then + delete it and run GFXCFG.EXE. It will automatically create a default + initialization file when it is absent. + + + GFX2.CFG: + + + This file contains the keyboard configuration plus the state of the + following variables in the program: + video modes + shade tables + stencil + mask + gradients + + All these variables are saved when clicking on the Save button in the + settings menu or when exiting the program with the Auto-save option on. + However, when you click on Reload in the settings menu, only the state + of each video mode is restored. + + Note: the GFX2_FRA.CFG file is a default configuration file for AZERTY + keyboards. If you have got an AZERTY keyboard, you may replace the + GFX2.CFG file by GFX2_FRA.CFG. + + Important: from version 2.00 95.5%, .CFG files will have ascending + compatibility. This means that you'll be able to retrieve most of their + contents from a release to another by copying your old .CFG file into + your new GrafX2 directory and running GFXCFG.EXE. Indeed, this program + will convert your old file for it is usable by the new version of GrafX2. + But copying a .CFG file from an earlier version than version 95.5% won't + work. Moreover, (I don't see why you would do that, but...) copying a + recent .CFG file to an older version shouldn't work neither. + + + Note: We highly recommand not to modify the keys related to the mouse + emulation in the GFXCFG program because the values you could use may inter- + fere with the keyboard shortcuts used in the menus. + + + + +Available options: + + + The different options available in GrafX2 will be listed and detailed + below. They will be described as follows: + + ͻ ͻ + 1 3 triangular buttons will 1 / + be detailed like this: / 2 + ͹ ͼ + 2 4 + + ͼ + + + 1 - Paintbrushes + 2 - Adjust picture / Effects on the picture + 3 - Hand-drawing + 4 - Splines + 5 - Lines + 6 - Spray + 7 - Floodfill + 8 - Polygons / Polyforms + 9 - Polyfills / Filled polyforms + 10 - Empty rectangles + 11 - Filled rectangles + 12 - Empty circles/ellipses + 13 - Filled circles/ellipses + 14 - Rectangles with gradation + 15 - Gradation menu + 16 - Spheres / Ellipses with gradation + 17 - Brush grabbing / restore + 18 - Polyformed brush grabbing (lasso) / restore + 19 - Brush effects + 20 - Drawing modes + 21 - Text + 22 - Magnifier mode / Menu + 23 - Pipette / Invert colors + 24 - Screen size / Safety resolution + 25 - Spare page / Copy current to spare + 26 - Save picture / Autosave + 27 - Load picture / Reload + 28 - Settings + 29 - Clear picture + 30 - Help / Statistics + 31 - Oops (Undo/Redo) + 32 - Kill current page + 33 - Quit program + 34 - Palette menu + 35 - Scroll palette left / right + 36 - Palette window + 37 - Hide menu + + + + When you will use any drawing tool, left-clicking will draw with the Fore + color while right-clicking will draw with the Back-color. + + When dialog boxes or windows will come on the screen, Cancel (or No) will + always be emulated by the key, and OK (or Yes) by the key. + + In the different menus, the titles of the buttons that contain an under- + lined letter can be emulated by pressing this letter on the keyboard. + + In some menus, you can select a color range in the palette. This means + that you can click on a color and move the mouse to another by maintaining + the button pressed to select a color range. + + + + 1 - Paintbrushes: + + + Left click: + ============> + + Displays a menu where you can choose the shape of your paintbrush. + + Paintbrushes are sorted by family. You can see some paintbrushes of + the same family but with different sizes. There is at least one paint- + brush from each family displayed in this menu. + Here is the list of all the different paintbrush families: + + + + + + + + + + Square Disc Sieve Sieve Diamond Random + square disc shaped + ______________________________________________________________ + + + + + + + + + + Horiz. Vertical Slash Back- Cross X Cross + + bar bar slash + + The 3 last paintbrushes in the menu belong to the "miscellaneous" + family and their size cannot be modified. + + + Right click: + ============> + + Transforms your current user-defined brush into a paintbrush. This is + actually a "monochromisation" of your user-defined brush. This means + that every color of the brush that aren't the Back-color will be set to + the Fore-color. But this option doesn't alter the brush: you'll just + have to right-click on the "Get brush" buttons to get your brush back. + + + Note: When you press (not in the menu) the key (default value), + the current paintbrush becomes the smallest member of the "Disc" family: + i.e one pixel. + + + + 2 - Adjust picture / Effects on the picture: + + + Left click: + ============> + + Allows you to scroll the picture to re-center your graph for example. + + Any part of the picture that goes out of the image by a side comes + back by the opposite one. + + It is assimilated to the drawing tools family. + + + Right click: + ============> + + *** Not implemented yet *** + + + + 3 - Hand-drawing: + + + Left click: + ============> + + Selects the current hand-drawing mode as the active drawing tool. + There are 3 hand-drawing modes: + + - Continuous hand-drawing: as you move the mouse, the paintbrush is + regularily pasted on the picture. This drawing tool allows to change + the fore and back colors when being in use. + + - Discontinuous hand-drawing: as you move the mouse, the paintbrush is + pasted on the picture every time a delay is passed (actually, the + delay is 1 VBL (vertical blanking)). This drawing tool allows to + change the fore and back colors when being in use. + + - Dot by dot hand-drawing: the paintbrush is only pasted at the + position where you first clicked. + + + Right click: + ============> + + Toggles the different hand-drawing modes and activates, at the same + time, the hand-drawing tool. + + + + 4 - Splines: + + + Left click: + ============> + + Selects the current curve-drawing mode as the active drawing tool. + There are 2 different curve-drawing modes: + + - 4 control points curves: define the basic line like a classical + line, then move, with the left mouse button, the inner control + points to choose the shape of your curve. When the curve has the + shape you want, click with the right mouse button to draw it + definitively. + + - 3 control points curves: the same as above, but you'll have only one + inner control point to place. Moreover, the spline will be traced + just after placing this point. + + + Right click: + ============> + + Toggles the different curve-drawing modes and activates, at the same + time, the curve-drawing tool. + + + + 5 - Lines: + + + Left click: + ============> + + Selects the current line-drawing mode as the active drawing tool. + There are 3 line-drawing modes: + + - Classical lines: when first clicking on the picture, you'll define + the start of the line. Maintain your click to choose the end of the + line and release the mouse button to set it. + + - Knotted lines: works like classical lines, but the end of your line + will automatically become the start of the next one. When you want + to stop chaining lines, use the opposite mouse button. "The opposite + button" means that if you started to draw lignes with the left + button (Fore-color), you'll have to stop the procedure with the + right button; and conversely. + + - Concentric lines: when first clicking on the picture, you'll define + the center of the lines. In fact, the center is defined by the + position of the mouse when you release the mouse button. Then you + can draw lines from the center to the current mouse position by + clicking. To stop drawing concentric lines, use the opposite mouse + button. This drawing tool allows to change the fore and back colors + when being in use. + + + Right click: + ============> + + Toggles the different line-drawing modes and activates, at the same + time, the line-drawing tool. + + + + 6 - Spray: + + + Left click: + ============> + + Selects the spray as the active drawing tool. This drawing tool allows + to change the fore and back colors when being in use. + + + Right click: + ============> + + Displays a menu where you can configure the spray: + + - Size: Defines the diameter of the circle in which will effectively + fit the spray. + + - Delay: Defines the number of VBLs that will be waited for between + two flows of spray. + + - Mode: Defines whether you want to use a monochrome spray or a multi- + colored one. + + - Mono-flow: Defines the number of paintbrushes that will be pasted in + the circle of the spray at each cycle. + + - Palette: Left-click on a color of the palette to see how much it + will be used in the multicolored flow, and modify it by using the + gauge on the right. If the flow of this color was equal to 0, then + the "Init" value will be applied. Or set the flow of a color to 0 by + clicking on it with the right mouse button. + + - Clear: Removes all the colors from the multicolored flow. + Actually, this puts a 0 value in the use of each color. + + - Init: Allows you to define a value that will be set to the color you + click on in the palette if its value is equal to 0. This permits to + tag a set of colors more quickly. + + - +1,-1,x2,2: Modify the values of all the tagged colors (and only + them). + + + Tip: If you often use the Shade mode, and are bored to click many + times on a color to reach the color you want, you can define a + spray with "Size"=1, "Mono-flow"=1, and "Delay"=2 (or more, + according to your reflexes). And then, you'll just have to click + a few hundredths of second to modify a color. + + + + 7 - Floodfill: + + + Left click: + ============> + + Selects the filler as the active drawing tool. The filler, as any + drawing tool, will be affected by all the effects! + + Note that only the visible part of the picture will be filled (as + every other drawing tools, the floodfill only alters the visible part of + the picture; this avoids unwanted effects that wouldn't be controlled by + the user). + + + Right click: + ============> + + Selects the color replacement as the active drawing tool. + + Any rule has its exceptions and this one doesn't depart from that. + Indeed, this tool is the only one to be affected by no effect (except + Stencil) and to be able to modify non visible parts of the picture. + The function of this tool being replacing all the occurences of a + color in the picture by another, if would have been a shame to limit + modifications only to the visible part of the picture. + + + + 8 - Polygons / Polyforms: + + + Left click: + ============> + + Selects the polygons as the active drawing tool. + + This works just like knotted-lines but loops the extremities when + you're finished. + + + Right click: + ============> + + Selects the polyforms as the active drawing tool. + + This works like a combination of free-hand drawing and knotted-lines. + If you keep the mouse button pressed, you'll draw as if you were in + free-hand drawing mode. And, if you release the mouse button, it will + work like knotted lines. + + Click on the opposite mouse button (i.e.: click right if you started + to draw with the left mouse button, and vice versa) to terminate the + operation. The two extremities will be linked automatically. + + + + 9 - Polyfills / Filled polyforms: + + + Work exactly the same way as the polygons et polyforms above, but fill + in the interior of the drawn shapes. + + + + 10 - Empty rectangles: + + + Any click: + ==========> + + Selects the empty rectangles as the active drawing tool. + + Set a corner of a rectangle. Maintain the click to move the opposite + corner and release the mouse button to set it definitively. + + + + 11 - Filled rectangles: + + + Any click: + ==========> + + Selects the filled rectangles as the active drawing tool. + + Works like an empty rectangle. + + + + 12 - Empty circles/ellipses: + + + Left click: + ============> + + Selects the empty circles as the active drawing tool. + + Position the center of the cercle and maintain the mouse button to + select its radius. + + + Right click: + ============> + + Selects the empty ellipses as the active drawing tool. + + Position the center of the cercle and maintain the mouse button to + select its dimensions. + + + + 13 - Filled circles/ellipses: + + + Work like empty circles and ellipses. + + + + 14 - Rectangles with gradation: + + + *** Not implemented yet *** + + + + 15 - Gradation menu: + + + Any click: + ==========> + + Opens a window where you can define the way gradations are processed. + The different sections of this menu are: + + - Direction (arrow): Switches the direction of the gradation. + + - Dithering method: Toggles the 3 following methods: + - No dithering + - Basical dithering + - Enhanced dithering + + - Mix: Mixes the gradation with a more or less random factor. + + - Palette: Select a color range to build a gradation. + + - Index scroller: Defines the current gradation among a set of 16 that + will be memorised. + + + + 16 - Spheres / Ellipses with gradation: + + + Left click: + ============> + + Selects the spheres as the active drawing tool. + + Position the center of the sphere and maintain the mouse button to + select its radius. Then place the spot-light. + + + Right click: + ============> + + Selects the ellipses with gradation as the active drawing tool. + + *** The current version of this tool isn't the right one; *** + *** so we'll explain how to use it when it will be done *** + + + If you trace a sphere or an ellipse with gradation with the right mouse + button, the result will be the same figure filled with the Back-color. + + + + 17 - Brush grabbing / restore: + + + Left click: + ============> + + Engages a brush grabbing. + + Click on a corner of the rectangle containing the brush then maintain + the click to define the opposite corner of the rectangle. Release the + mouse button to grab the brush. Performing this operation with the right + mouse button will erase the area where the brush was grabbed with the + Back-color. + + + Right click: + ============> + + Restores the old brush. + + + + 18 - Polyformed brush grabbing (Lasso) / restore: + + + Left click: + ============> + + Grabs a brush of any shape by defining a polyform (please refer to + section 8 for more explanations). + + + Right click: + ============> + + Restores the old brush (same as above). + + + + 19 - Brush effects: + + + Any click: + ==========> + + Displays a menu where the following options are available: + + - X: Flip-X. + + - Y: Flip-Y. + + - Rotate by 90: Rotates the brush by an angle of 90 degrees. + + - Rotate by 180: Rotates the brush by an angle of 180 degrees. + + - Rotate by any angle: Triggers an interactive operation that allows + you to rotate the brush. For this, start by placing the center or + rotation with the left mouse button (if, at this moment, you press + the right button, the operation with be cancelled). After that, you + can define the angle of rotation as many times as you want by moving + the mouse and left-clicking. Then validate with the right button + when you are satisfied. + Meanwhile, you can press on the 8 outer digits of the numeric pad + for defining angles multiple of 45: + 135 90 45 + \ | / + '7' '8' '9' + 180 -'4' '6'- 0 + '1' '2' '3' + / | \ + 225 270 315 + + + - Stretch: Triggers an interactive operation that enables you to stretch + the brush. For this, start by placing the upper-left cornerof the + brush with the left mouse button (if, at this moment, you press the + right button, the operation will be cancelled). after that, you can + place the opposite corner as many times as you need, then validate + with the right mouse button when you are satisfied. If you place + this point at coordinates inferior to the ones of the first point, + the brush will be inverted. + Meanwhile, you can press the following keys whose effects are: + 'D' : double the brush in X and Y + 'H' : reduce the brush by half in X and Y + 'X' : double the brush in X + 'Shift+X': reduce the brush by half in X + 'Y' : double the brush in Y + 'Shift+Y': reduce the brush by half in Y + 'N' : restore the normal size of the brush (can be useful + because it's the only way for cancelling) + + - Distort: *** Not implemented yet *** + + - Outline: + This option permits to draw the outlines of the brush with the Fore- + color. + + - Nibble: + This option "nibbles" the outlines of the brush. It's in some way + the opposite effect of the Outline option. + + - Recolorize: Remaps the brush so that it looks like it would in the + spare page, using the current palette. + + - Get brush colors: Transfers the spare page's colors used by the + brush to the current palette. + + - Brush handle: Allows you to choose where to place the handle of the + brush. + + - Load / Save: load or save a brush from disk. + + + + 20 - Drawing modes: + + + This button opens a menu where you can switch on or off the different + drawing modes. ([F1]-[F9] keys correspond to the 9 buttons) + + In this menu, the "All off" button switches all the drawing modes off. + The [Del] key is the keyboard shortcut for this button. + + The "Feedback" button is only used in "Shade", "Quick-shade, "Transpa- + rency" and "Smooth" modes. When it is set, it means that the _current_ + state of the picture has to be taken into account for the effect instead + of the state in which the image was when you started to click for drawing. + The best, as often, is that you try by yourself with and without Feedback + to see the difference. + + The other buttons are the following: + + + * Shade mode / Menu: + -------------------- + + It consists in increasing or decreasing the color number within a user- + defined range. This shows its real dimension when used with a range of + colors that shade off. Then, you can work on a part of your picture where + colors belong to the same range without having to change your brush color + all the time. + You can choose the incrementation or decrementation of the color by + pressing the left or right mouse button while drawing. If you click on a + color that does not belong to the range, it will remain unchanged. + + Left click: + ============> + + Switches the Shade mode. + + + Right click: + ============> + + Opens a menu where you can define one table of shades within a range + of 8 memorised by the program. + The different sections of this menu are: + + - Palette: You can define in it the color blocks that will be inserted + into the table of shades. + + - Scroller: Used to change flick through the tables of shades. + + - table of shades definition area: The 512 squares should be widely + sufficient to define the different shades since every 256 colors of + the palette cannot be present more than once in each table. + + - A window (on the top-right side) permits to visualize the different + shades defined in he current table. + + - Copy: Copy the contents of the table in a buffer. + (Each time you open this menu, the current table is automatically + transfered into this buffer). + + - Paste: Copy the contents of the buffer above in the current table. + + - Clear: Reset the "shades" table. + + - Insert: Used to insert the block selected in the palette at the + cursor's position in the table of shades. + IF you click with the left mouse button on this button THEN + IF a block of more than one color is selected in the table THEN + It is deleted and the block defined in the palette is inserted. + ELSE + The block defined in the palette is inserted at the postion just + before the selected square. + END IF + ELSE + The block defined in the palette is inserted by erasing the colors + following the beginning of the bloc selected in the table. + END IF + + - Delete: Delete the block selected in the table. + + - Blank: Follows this algorithm: + IF you click with the left mouse button on this button THEN + Replace the block selected in the table by blank squares. + ELSE + IF a block of more than one color is selected in the table THEN + Insert blank squares to the left and to the right of the block. + (this is useful for isolating a shade quickly) + ELSE + Insert blank squares to the left of the selected square. + END IF + END IF + + - Invert: Invert the order of the block selected in the table. + + - Swap: Allows you you move a block (this exchanges it with what is + where you want to move it). + + - Undo: Cancel the last modification of the table. + + - The 2 numbers displayed on the right of these buttons are: + (above) - the number of the color selected in the palette if only + one color is selected. + (below) - the number of the color contained in a square in the + shades table if this square is the only one selected. + + - The "mode" button displays 3 different modes: + "Normal": + Shades in the range and saturates to its boundaries. + "Loop": + Shades in the range and loops if boundaries are passed. + "No saturation": + Shades in the range and doesn't saturate if boundaries are passed. + If the Step (see below) is set to 1, this option does exactly the + same as the Normal mode. + + - Set/Disable: If you want to define several shades in the same table + but you'd like these shades not to be effective at the same time, you + can mask (disable) some parts of the table so that they will be + interpreted a blank squares. + To do that, select a block in the table of shades and click on "Set". + The block will be underlined with a white line; this means that it is + disabled. + + - Clear/Enable: This does exactly the opposite as the button above. + + - Step: Defines the step of incrementation of the shade. The bigger, + the faster you run through the colors of the shade. + For example: if the step is 2 and that you have defined a shade with + the colors 0,1,4,5,9 and that you click on a pixel of color 1, it will + take the value 5 which is 2 positions next in the la table. + + (We are sorry for these technical considerations quite far from a + purely artistic point of view; but know that this effect is really very + useful and it is preferable that you understand its whole functionment + if you want to fully take advantage of it). + + + + * Quick-shade mode / Menu: + -------------------------- + + This drawing mode has about the same effect as Shade mode's except that + it is faster to configurate but a little bit less powerful. + When you draw on a color of the image which is between the fore- and the + back-color in the palette, the color tends towards the fore-color + (according to the step defined) if you draw with the left mouse button, or + it tends towards the back-color if you are using the right mouse button. + + Left click: + ============> + + Switches the Quick-shade mode. + + + Right click: + ============> + + Opens a menu with a few parameters that mean exactly the same as in + the menu of Shade mode. These parameters are the step and the loop/satu- + ration mode (normal, loop, no saturation). + + + + * Stencil mode / Menu: + ---------------------- + + It is used to prevent some colors from being modified if you draw on + them. The main application of the stencil is when you want to change one + color or more into another. + + Left click: + ============> + + Switches the Stencil mode. + + + Right click: + ============> + + Opens a menu where you can define a stencil. + The different sections of this menu are: + + - Clear: No color is protected. + + - Invert: Colors that were protected are unprotected and vice versa. + + - Palette: Select colors that should be protected with the left mouse + button or unprotect colors with the right mouse button. + + + + * Mask mode / Menu: + ---------------------- + + This effect could have been called "True stencil" because it protects + some parts of the picture instead of some colors. The colors you tag + represent the pixels in the spare page, corresponding to the pixels in the + current page, that you don't want to alter. + For example, draw a simple white figure on a black background in the + spare page. Then, tag the black color in the menu of the Mask mode. When + you'll draw in the current page, only the pixels corresponding to the + white (non-black) ones in the spare page will be modified. + + Left click: + ============> + + Switches the Mask mode. + + + Right click: + ============> + + Opens a menu where you can set the colors of the Mask. + This menu works the same way as the one of the Stencil, so please + refer to the Stencil paragraph to know how to use it. + + + + * Grid mode / Menu: + ------------------- + + This is useful to snap the cursor to the cross-points of a grid. It's + generally used to draw a grid before drawing sprites of the same size such + as a font or tiles, or for drawing figures or grabbing brushes with their + dimensions multiple of the step of the grid.'); + + Left click: + ============> + + Switches the Grid mode. + + + Right click: + ============> + + Opens a menu where you can define the grid parameters. + These parameters are: + + - X,Y: Steps of the grid. + + - dX,dY: Offsets of the grid. + + + + * Sieve mode / Menu: + -------------------- + + This effect allows you, by defining a pattern, to draw only on + particular points of the picture. + If you are a Manga drawer, you might find this useful to make patterned + shades or color transitions. + + Left click: + ============> + + Switches the Sieve mode. + + + Right click: + ============> + + Opens a menu where you can define the Sieve parameters. + This menu consists in: + + - 16x16 drawing area: You can define a pattern in it (left click => + white pixel / right click => black pixel). + All the white pixels indicate that, when you'll draw, pixels will be + applied on the picture at the corresponding positions whereas black + pixels won't modify the picture: whites pixels are the "holes of the + sieve". + + - 12 default patterns: They can be copied to the drawing area. + + - "Transfer to brush": Copies the pattern to the brush (white pixels + => Fore-color / black pixels => Back-color). + + - "Get from brush": Puts the brush into the drawing area (back-color + => black pixels / others => white pixels). + + - Scrolling 4-arrows pad: Scrolls the pattern in the drawing area. + + - Resizing 4-arrows pad: Defines the dimensions of the pattern. + + - Default-value (black or white square): Indicates which value must be + inserted when you increase the dimensions of the pattern. + + - "Clear": Sets the whole pattern with the default value (see above). + + - "Invert": It... inverts :) ... black and white pixels. + + + + * Transparency mode (Colorize) / Menu: + -------------------------------------- + + This allows to mix the color(s) of the paintbrush with the colors of the + picture. It's used to make transparency effects like with watercolors. + + Left click: + ============> + + Switches the Transparency mode. + + + Right click: + ============> + + Opens a menu where you can define the Transparency parameters. + These parameters are: + + - Interpolation rate: Indicates the percentage of the applied color + that will be considered upon the replaced color. + + - Interpolation method: Uses an interpolation algorithm to compute the + color, according to the interpolation rate. + + - Additive method: Uses the lightest colors to choose the color to + apply. + For example: if you want to apply a color RGB:30,20,40 on a color + RGB:10,50,20, the color applied will be the one, in the palette, + that is the closest to the theoretic color RGB:30,50,40. + + - Subtractive method: uses the darkest colors to choose the color to + apply. + For example: if you want to apply a color RGB:30,20,40 on a color + RGB:10,50,20, the color applied will be the one, in the palette, + that is the closest to the theoretic color RGB:10,20,20. + + + + * Smooth mode / Menu: + --------------------- + + It provides an easy but not as efficient anti-aliasing as any artist's + touch. Anyway this effect finds a better use in making a blurry aspect. + + Left click: + ============> + + Switches the Smooth mode. + + + Right click: + ============> + + Opens a menu where you can define the Smooth matrix or choose one + among the 4 ones predefined. + The middle square represents the pixel on which you draw and the 8 + others represent the neighbour pixels. Then, the point on which one draw + will be replaced by the weighted average (according to values of each + squares) of the 9 defined points. + + + + * Smear mode / Menu: + --------------------- + + It smears pixels in the direction you are moving your paintbrush, just + as if you wanted to spread fresh paint with your fingers. You can combine + this effect with the transparency effect. + + Any click: + ==========> + + Switches the Smear mode. + + + + * Tiling mode / Menu: + --------------------- + + It consists in displaying parts of the brush that are adjusted on a + tiling when you are drawing. It's mainly used for quickly drawing a + background with a pattern, but there is a great number of other + possibilities. + + Left click: + ============> + + Switches the Tiling mode. + + + Right click: + ============> + + Opens a menu where you can define the Tiling parameters. + These parameters are the offsets of the tiling. + + + + 21 - Text: + + + *** Not implemented yet *** + + + + 22 - Magnifier mode / Menu: + + + Left click: + ============> + + Engages/Disengages the choice of the zoomed window. If you're already + in magnifier mode, you'll return to normal mode. + + + Right click: + ============> + + Displays a menu where you can choose the magnifying factor. + + + Note: When you are in Zoom mode, you can move the "split" bar by + clicking on it and moving your mouse left or right while holding the mouse + button down. + + + + 23 - Pipette / Invert colors: + + + Left click: + ============> + + Engages a color grabbing. + + Click on the picture to get the color of the pixel you're on. You can + either get a new Fore-color or Back-color with respectively left or + right mouse button. + + + Right click: + ============> + + Swap Fore-color and Back-color. + + + The color currently pointed will be displayed in the tool-bar right + after the coordinates. + If you click outside the picture, the color 0 will be returned. + + + + 24 - Screen size / Safety resolution: + + + Left click: + ============> + + Displays a menu where you can define the size of your picture (up to + 1024x768) by clicking in the boxes named "Width" and "Height"; and the + resolution in which you want to draw (in the list). + + Clicking on a resolution button with the right mouse button will not + only set the resolution of the screen, but also set the picture + dimensions to the screen ones. + + Resolutions written in dark gray are VESA modes that aren't supported + by your video card. If you have some modes like that, you should try to + run a VESA driver such as Univesa or Univbe before running the program. + If these modes still aren't available, then this means that your video + card really doesn't support them. + + The small buttons on the left-hand side of the lines in the list of + modes have been designed to allow you to disable some modes that are not + supported by your card. So, the modes that you will disable won't be + used when loading pictures with "Auto-set resolution" ON. + + When you click on one of these buttons, its color changes to one of + the 4 following. The signification for each color of these buttons is: + + - Light gray: The video mode is OK. It can be used by the auto-set + resolution option when you load picture, and you can select it in + the menu of resolutions. + + - White: It works exactly the same as above. Moreover, it allows you + to tag your favourite modes. Indeed, the huge number of video modes + makes it more difficult to find the mode your want in the list; so + you can tag your favoutite ones in white, so that it will be easier + to locate them. (Note: you cannot disable the standard 320x200 mode) + + - Dark gray: It allows you to indicate which modes are not really + perfect (flickering, not centered, etc...) but which can be used + even so. The difference with the light grey button is that these + modes won't be used by the auto-set resolution option. + + - Black: Use it for totally unsupported modes. Thus, these modes won't + be selected the "auto-set res." and the program will prevent you + from selecting them from the menu of resolutions. + + + Right click: + ============> + + Automaticaly switches to the 320x200 MCGA mode. + + + + 25 - Spare page / Copy current to spare: + + + Left click: + ============> + + Jumps to spare page. The current page is then considered as the new + spare page, and the spare page considered as the new current page. + + + Right click: + ============> + + Opens a menu where you can choose whether you want to copy the whole + picture (keyboard short-cut in this menu is [Return]), only the pixels, + only the palette, or only some colors. + In this last case, a second menu (stencil-like) will propose you to + tag the colors you want to copy (they are all selected by default). + Please refer to section "18 - Stencil" to know how to use this last + menu. + The last option the menu ("Copy palette and remap"), remaps the spare + page with the current palette and replicates this palette to the spare + page. This option is useful to quickly remap a picture with the palette + of another. + + + + 26 - Save picture / Autosave: + + + Left click: + ============> + + Displays a fileselector where the following options are available: + + - Drives: Allow you to change the current drive. You can use + + to change drives too. + + - Format: Allows you to choose the file format you want. (PAL and KCF + file formats are "palette" files). + + - Filename: Allows you to give a new name to the picture. If no + extension is given, the default (according to the format) will be + used. + + - File-list: Allows you to flick through the disk tree or to overwrite + an existing file. + + - Delete: Allows you to delete the item under the selection bar. + If the item is a directory, it must be empty to be removed. + + - Save: Saves the picture with the current filename, with the chosen + format and with the current comment (for PKM files). If the current + filename represents a directory, you'll enter it. + + - Comment (Txt): If you're using the PKM format, you can type in a + comment on your picture. + + Note: The Backspace key brings you directly to the parent directory. + Type in the 1st lettets of a filename you are looking for to + access it faster. + + + Right click: + ============> + + Save the current picture with its current filename, format and + comment. + + If the file already exists, a confirmation box will appear. + + + + 27 - Load picture / Reload: + + + Left click: + ============> + + This works the same way as Save. + + You'll have access in the format selector to a "*.*" filter. And of + course, you won't be able to type in any comment. + + + Right click: + ============> + + Reloads the picture. + + If you want to load a picture and that you haven't saved the last + modifications of the current picture, a confirmation box will appear. + + + + 28 - Settings: + + + Any click: + ==========> + + Displays a menu where you can configure some miscellaneous elements of + the program: + + - Number of UNDO pages: indicates the total number of pages that + GrafX2 will memorize. Each time you modify the picture, its current + state is memorized in one of these pages. To flick through these + pages, use the "Oops" button (Undo/Redo). + + - Font: determines whether you want to use GrafX2 with a classical + font, or another one a bit funnier. + + - Mouse sensibility: Modifies the speed of the mouse. + + - Show/Hide in file list: Defines whether some particular files or + directories must be displayed by the fileselectors or not. + + - Show/Hide picture limits: Indicates if the picture boundaries must + be displayed when you are in a resolution bigger than the picture. + + - Clear palette: Indicates if loading a file with a palette of less + than 256 colors must erase the rest of the current palette (replace + by the black color). + + - Maximize preview: maximizes the preview of the pictures so that it + is as big as possible. If you're not in the same resolution as the + picture's one, it can try to correct the aspect ratio, but if the + picture does not fill the whole screen, it can be worse. + + - Backup: when you'll save a picture over an existing file, the + program will rename this file to "*.BAK" where * is the name of the + picture without its extension. If the backup file already exists in + the directory, it will be replaced. If you save a picture with the + name of the backup file, no backup file will be created (of course!) + ;). + + - Cursor: allows you to choose whether you prefer a solid cursor or a + transparent cursor. + + - Safety colors: Brings back the 4 default colors of the menus if you + run an operation that passes the image in less than four colors in + the palette editor. + + - Adjust brush pick: This option is used when you grab a brush in Grid + (Snap) mode. Then, the right-most and down-most pixels won't be + picked up with the rest of the brush. This option has been made + because, if people grab brushes in Grid mode, that's mostly when + they want to grab sprites. + For example: if you have 16x16 sprites on your page, you'll set the + grid mode to 16x16. But the cursor will snap at points like (0,0), + (16,0), (16,16) and so on... And the problem is that, from (0,0) to + (16,16), there are 17 pixels! But if you keep the adjust-brush-pick + option on, the unwanted pixels will be ignored. + Moreover, this option adjusts the brush handle so that the brush + still fits in the grid, instead of placing the handle in the center + of the brush. + + - Separate colors: Draws a squaring around the colors of the tool-bar. + + - Auto-set resolution: sets the best resolution for the loaded image. + + - Coordinates: Choose if you want to display relative or absolute + coordinates when using tools such as circles, rectangles, etc... + for example, if you draw a circle: if coords are relative, the + radius of the circle will be displayed, while in absolute coords, + the coordinates of the cursor will be displayed. + + - Reload: loads the previously saved configuration. + + - Auto-save: means that the configuration will be automatically saved + when you'll quit the program. + + - Save: saves the configuration at once. + + All modifications will be effective just after closing the menu. + + + + 29 - Clear picture: + + + Left click: + ============> + + Clears the picture with the color number 0. + + + Right click: + ============> + + Clears the picture with the Back-color. + + + + 30 - Help / Statistics: + + + Left click: + ============> + + Displays an info window where you'll find some credits, help about the + credits, different effects, greetings, registering... + + + Right click: + ============> + + Displays a window where you'll find miscellaneous informations about + the system. + + Note: you should take care to keep more than 128 Kb in order to let the + program run in a proper way. + + + + 31 - Oops (Undo/Redo): + + + Left click: + ============> Allows you to undo the last modification on the picture. + + Right click: + ============> Allows you to redo the last modification undone on the + picture. + + The maximum number of UNDO that you can perform can be defined in the + settings menu. + + Undo/Redo aren't effective after page switching, picture loading and + picture size modifications. + + + + 32 - Kill currenty page: + + + Any click: + ==========> + + Removes the current page from the list of "Undo" pages. This allows + you to free some memory if you need it. For instance, this will allow + you to delete the start-up page after having loaded an image. A message + will appear if you've already erased all the pages except the last one. + + Note: Another way to free some memory is to decrease the number of + "Undo" pages. Or else, if you have recentlt grabbed a very big + brush that you don't use any more, you can grab a new smaller one. + The memory allocated by the big brush will be thus freed. + + + + 33 - Quit program: + + + Any click: + ==========> + + Allows you to leave GrafX2. If there are unsaved modifications in the + current or spare page, a confirmation box will ask you if you really + want to quit GrafX2, if you want to save (Auto-save, no fileselector) or + if you want to stay in GrafX2. + + + + 34 - Palette menu: + + + Left click: + ============> + + Displays a menu where the following options are available: + + - Palette: Allows you to choose a color-block to edit. If you click + with the right mouse button, you'll choose a new Back-color. + + - RGB gauges: Allow you to modify the current selection. + + - "+" and "-": Allow you to lighten or darken the current selection. + + - Default: Restores the predifined GrafX2 palette. + + - Gray: Transforms the current selection into its gray-scaled + equivalent. + + - Negative: Transforms the current selection into its reverse video + equivalent. + + - Invert: Swaps the colors of the current selection so that the first + colors become the last ones. + + - X-Invert: Works as above but modifies the picture so that it looks + the same. + + - Swap: Swaps the current selection with another color-block. Click on + the beginning of the new color-block. + + - X-Swap: Works as above but modifies the picture so that it looks the + same. This may be useful if you want to sort your palette. + + - Copy: Copies the current selection to another color-block. Click on + the beginning of the new color-block. + + - Spread: Computes a gradation between two colors. If your selection + is only made up of one color, select the second color in the + palette. Otherwise, the two colors used will be its extremities. + + - Used: Indicates the number of colors used in the picture. + + - Zap unused: Erases the unused colors with copies of the current + selection. (The keyboard shortcut for this button is ). + + - Reduce: Allows you to reduce the palette to the number of colors you + want (and modifies the picture). + + - Undo: Allows you to recover the last modifications made on the + palette. If the last operation modified the picture, it won't + recover them: you'll have to click on Cancel to do so. + + + If you press , the program will replace, as well as + possible, some unused colors by the four default colors of the menu. + The image won't look altered because the modified colors (in the case + they were used on a few points) will be replaced by the closest colors + in the rest of the palette. + This option is really useful when you modify the palette so that there + are no colors that fit for the menu (eg: "Zap unused" while very little + colors are used in the picture; or "Reduce" with a very small number of + colors). + + If you press the key below or <,> (QWERTY), the menu will + disappear and you will be able to pick up a color from the picture + easily. Press to cancel. + + If only one color is selected (not a block), the <[> and <]> keys can + be used to select the previous or next Forecolor (Backcolor if you press + at the same time). + + Warning! If you press Undo after an action that modifies the picture + (X-Swap, X-Invert and Reduce colors), the picture won't be remapped as + it was just before this action. Only Cancel will. + + + Right click: + ============> + + Opens a menu from where you can access the following menus: + + - A menu in which you can select the colors that have not to be used + for smoothing, for the transparency mode and for remapping. + + - A menu in which you can define color series. + *** Not implemented yet *** + + + + 35 - Scroll palette left / right: + + + Left click: + ============> + + Scrolls the palette window in the right of the menu. + + + Right click: + ============> + + Same as above, but faster. + + + + 36 - Palette window: + + + Left click: + ============> + + Defines the Fore-color. + + + Right click: + ============> + + Defines the Back-color. + + + + 37 - Hide menu: + + + Any click: + ==========> + + Allows you to hide the menu. If you do this, take care to watch before + the key to press to show the menu back (the default key is ). + + + + +Let's talk about $$$, baby: + + + Please refer to the "Register?" section in the internal help of GrafX2. + + To sum up this section, let's just say that GrafX2 is freeware. But you + can anyway send us money, graphics, or just a postcard to show us that we + made a useful program. + + You must note that the version you have is already the "complete" version + (the same as the registered version) so we won't send you any other copy of + GrafX2. But if you register for one version, we'll consider that you won't + have to register for the next ones. + + + + +Drawing tips: + + + This section deals with tips that can help you to draw some cool effects, + or just to draw faster. + Note that, in most cases, these tips only make a big part of the work and + that you'll have to touch up in zoom mode if you want to draw a picture + worthy of the name! ;) + Moreover, if you've found out nice tips by yourself, and if you want to + share them with the others, don't hesitate to tell us. + + Anti-aliasing: + + + This is not an effect proposed by GrafX2 but a drawing method. It + consists in placing medium colored pixels in the angles formed by + contrasted pixels for artistically smoothing their aspect. + From our point of view, this is essential for drawing really nice + pictures. + An easy but tiresome way (the best way!) is to start by adding 1 middle + color, then antialias the new colors "recursively" while you have + intermediate colors in your palette. + + + + + ۱ + + + ۲ + + + + Smear mode combined with concentric lines: + + + By combining this effect and this drawing tool, you can spread an area + from a central point. + If you aren't in high resolution, it can be useful to switch on the + transparency mode too (see next section). + + A possible application is to draw fluffy hair. For that, you can choose + one of the pre-defined paintbrushes loking like random points. According + to the hair density you wish to obtain, you can choose a paintbrush with + more or less points. Then, place the center of the concentric lines in the + middle of the plush, and rotate the mouse around it keeping the mouse + button pressed. + With the same method, by turning around more, you can manage to give + an explosion effect to an object. + + You can also create easily and quickly sun rays with this method. For + that, after having drawn the primary shape of the sun in the sky, choose + a paintbrush according to the size of the rays you want (but a small one + will often be prefered), and place the center of the lines in the center + of the sun. Then trace the ray at the length you want. If you didn't take + a big paintbrush, you'll be able first to draw an aura around the sun by + rotating quickly, and then to add more important rays with precision. + + + Smear mode combined with Transparency mode: + + + This two drawing modes, once combined, permit to spread parts of the + picture as fresh paint. + It is recommanded to use the transparency method which consists in + interpolating with an opacity of about 60% and the effects "Feedback" on. + + As in the prvious section, it can be useful for drawing hair and + especially eyelashes if you have got a good palette (i.e. a palette that + contains color gradations between every colors you'll draw on during the + operation. + For drawing eyelashes for example, after having drawn the eye and the + eyelid, trace a quite thick black line representing the base of the eye- + lashes (this is that black line you'll spread out on the eyelid). Then, in + smear+transparency mode, draw with the freehand continuous tool (with a + small paintbrush: 1, 2 or 3 pixels wide according to what you draw: a face + or a close-up on an eye) starting from the base of the eyelashes in giving + their shape. You'll see your black bar looking more and more like eye- + lashes. + + One can also use these effects for mixing colors on the screen like + paint. For example, if one want to draw a background made of abstract + shapes composed of color mixings, one can proceed like what follows: + - Define a palette containing a gradation between the different colors you + wish to use . + - Draw very vaguely the different colored areas with a big paintbrush (in + normal mode). + - With a smaller paintbrush, and with the spray, apply these same colors + but lighter or darker on the previously defined areas. + - Always with the same paintbrush in spray, but this time in smear mode + (not necessarily with transparency... but why not?), mix all these colors + on the screen to obtain a "multicolored pulp" vaguely conserving the + different color areas. + - At last, in Smear+Transparency mode, with a medium rounded paintbrush, + hand-draw by whirling or making waves, etc... conserving the same movement + to avoid breaks. This aims at eliminating the pixellisation made by the + spray and giving the final mixed paint aspect. + - Now, if it's ugly, it's either because my explanations are incomprehen- + sible, or because you have no talent! :p + + + Spray combined with shade mode: + + + If you often use Shade mode, and you are tired of clicking plenty of + times on a pixel for reaching the color you want, you can define a spray + with "Size"=1, "Mono-flow"=1, and "Delay"=2 (or more, according to your + reflexes). Then you'll just have to click a few hundredth of second for + modifying a color. + + With a wider diameter, it permits to add granularity to a texture, + because placing lighter or darker pixels creates some ruggedness. + Different textures appropriated to this effect are: sand, rock, etc... + Of course, you'll need a color gradation corresponding to color of the + texture. + + You can also draw more elaborated textures - \ + using a paintbrush of the shape of a small curve \ \ + or line as these figures "try" to show. ;) ` \ + Thus, you can create textures of straw, hair, | \ + rock, marble (although hand-drawing would be + more recommanded than spray for this last one). + + + Shade mode used for replacing a color gradation by another one: + + + If you drew something with colors belonging to a gradation and you'd + like to replace all these colors by the ones of another gradation (with + the same number of colors), proceed as follows: + - Define these 2 gradations in the same shade table in the shade menu + without separating them by a blank square. + - Set the "no saturation" shade mode. + - Define the step of the shade with the size of the two gradations (e.g.: + enter 16 if each gradation contains 16 colors). + - Now, you just have to draw on the area you want the colors to change + (with the left mouse button if you placed the gradation to replace first + in the shade table, or inversely). + + + Spheres combined with additive transparency mode: + + + Starting from a dark background (if possible all of the same color), + trace overlapping spheres with their lighting point at their center. + You'll quickly obtain a "blob" effect. + + + How to draw drops: + + + Here is a fast and efficient method to draw drops. + Just draw very bright pixels on the side of the drop where the main light + is, and less bright ones on the opposite side. Then draw shadows according + to the position of the light. + + Here are examples with a light + coming from the top-left corner. + (they are best viewed in 80x50 ۰ + text mode) ۰ + ۲ + You may think that the smallest + drop doesn't really look like a ۱ + drop, but draw it in graph mode + and you'll see it DOES look + like a drop. + + If you don't trust me, then know that it's by looking at Lazur's graphs + that I found this method. And in a general way, it's always good to study + the work of the best artists to learn new techniques. + + + + +Trouble-shooting / General hints / FAQ: + + + * Video card problems: + + - VESA modes are disabled by Windows NT. And it is said that it will be + the same under Windows 2000 (we haven't tried it yet, and we aren't in a + hurry!). + + - If your video card is not VESA compatible in hardware, you should try to + run a VESA driver such as Univesa or Univbe. + + - If your card is VESA compatible but doesn't display the screen correctly + in VESA resolutions, that's probably because they don't fulfil all the + criteria that we expect. The explanation is that, for a better efficiency, + we have had to neglect some specificities on some video cards. However, + we always try to improve the compatibility with any kind of the VESA + standard in each new version. + + - If you have an ATI Mach 64 video card (e.g. ATI Xpert), you should use + the m64vbe TSR supplied with the card to fully support our fancy XVESA + modes by typing "m64vbe vga". + + + * Memory problems: + + - Since the 94.666% version, we use the EOS dos-extender Copyright (c)1996 + Eclipse instead of the usual DOS4GW. The reason is that it is much + smaller in disk space (a smaller zip should please your phone bills) and + in memory (so you'll be able to run GrafX2 with more device handlers + using conventionnal memory). In addition, this dos-extender is inside + the main file, which reduces the number of files (your FAT will be happy + for that). + + The backdraw is that this dos-extender doesn't manage disk-cache. So, if + you haven't at least 4 Megabytes of RAM, you'll have to use the batch + file GFX2_MEM.BAT . + + Notice that: + - you'll have to configure this file according to the location of some + files in the tree of your hard-disk(s). + - you'll have to have the file DOS4GW.EXE somewhere in the tree of + your hard-disk(s). + - you'll need at least 16 Megabytes of free space on your current + hard-disk. + + If you ever encounter problems using GrafX2 (with at least 4 Megabytes + of RAM) that would vanish using GFX2_MEM, we would thank you to let us + know. + + EOS is a shareware dos-extender, with very interesting libraries for + music, graphism, ... for Watcom, Tasm or Masm applications. If you want + more informations on its features or its libraries, don't hesitate to + contact us in order to be put in relationship with its authors. + + + * Sound card problems: + + Q: No sound comes out from my Ultra-maxi-sound-blaster-galaxy-64-3D-pnp, + so what can I do? + A: Well... You must understand that this program is not a soundtracker nor + a music-player :) ... So if you want some music, you'll have either to + play modules with a good player that can run background (with a DOS + shell), or to switch your Hi-Fi on. + + + * Miscellaneous: + + - If you corrupted the GFX2.CFG file and that GrafX2 uses it as is, with + an incorrect behavior, don't hesitate to erase GFX2.CFG and to re-run + GFXCFG to create a new correct one. Indeed, the only tests of validity + we do on the configuration file are checking its size and its version + number. + + - It may happen that you get a version already configured by one of your + friends who could have used some "Windows 95" keys while you haven't got + such keyboard yourself. In this case, you'll have to reconfigure these + combinations using GFXCFG. + + + * Frequently asked questions: + + Q: How can I set the dimensions of the picture? + A: We thought it was obvious that you had to click in the areas where the + dimensions are written in the resolution menu (Width & Height) but many + people asked this question (?!). So, to sum up, everywhere you'll see a + value or text written in black in a sort of encrusted area, this means + that if you click on it, you'll be able to modify its value. + Moreover, if you want the picture dimensions to be the same as the ones + of the screen, you just have to right-click on the resolution in the + list. + + Q: Where can I get the latest version of GrafX2? + A: The only place where you will find the latest version for sure is our + web site: http://www-msi.ensil.unilim.fr/~maritaud/sunset + Nevertheless, it isn't impossible that GrafX2 may also be found on FTP + sites dedicated to the "demo-scene" (e.g. ftp://ftp.scene.org). + + Q: How can I make the brush become monochrome, and how can I get it back + to its normal state? + A: You can do it (assuming that you haven't modified the default keys) + with the keys + to make the brush become monochrome, and + + to get the multi-coloured brush back. + + Q: Why is the tool bar at the bottom of the screen instead of at the right + side like in Deluxe Paint (copyright Electronic Arts)? + A: Well... GrafX2 IS NOT Deluxe Paint! We know that you are used to Deluxe + Paint but you'll have to get used to GrafX2! ;) If you really can't + stand using GrafX2 like this, then you'll have to wait for GrafX3 but + we probably won't release it before year 2000! Actually, the main + reason why we put the tool bar with such a basical aspect is that it + was easier (therefore faster) to redraw the whole screen just by + telling the routine where to stop (where starts the tool bar). + Moreover, one of the best Amiga paint programs (Brilliance) has got the + tool bar at the bottom of the screen too. + + Q: Why aren't the hidden parts of the picture filled when I use the "Flood + fill" tool? + A: For the simple and "quite" good reason that it is preferable that the + user controls perfectly what he is drawing. Thus, he won't see too late + that he has fucked up a part of his picture. The other tools work the + same way. And for the less good reason that is was more convenient for + us. ;) + + Q: Is it possible to launch the program in a different resolution than + 320x200? + A: Yes, you just have to type GFX2 at the DOS prompt. Type + GFX2 /? to get the list of all the video modes. + + Q: Is it normal that some buttons don't work (e.g.: the Text button)? + A: Yes, this is because we haven't had the time to make them (I remind you + that GrafX2 is still at a Beta version state). + However, here is the list of the buttons that don't respond in GrafX2: + - Grad. rectangles + - Text + - Effects on the picture + - and the following button in the "Brush effects" menu: Distort. + + Q: Will you release a Windows version? + A: GrafX2 would lose its soul by being adapted to a windowed system or a + system that doesn't support all its video modes. And anyway, it can be + run from Windows 9x (we don't know about Windows 2000 but we don't + care). So that's OK the way it is. The only interesting thing that + Windows could bring is the clipboard. + + Q: Will you release a Linux version? + A: Although this is about the same problem as with the Windows version, + Linux lacks programs like GrafX2; so, even a limited version would be + interesting in this OS. Therefore, we would like to release a Linux + version. But we have no experience in Linux programming and our code is + completely indecipherable for others. So you'll have to wait... + + Q: How can I contact you? + A: Actually, this is not really this question since those people managed + to contact us ;) but... + + * Snail mail: + GUILLAUME DORME (Robinson) KARL MARITAUD (X-Man) + 15, rue de l'observatoire 10, rue de la Brasserie + 87000 LIMOGES (FRANCE) 87000 LIMOGES (FRANCE) + + * E-mail: + dorme@msi.unilim.fr maritaud@ensil.unilim.fr + + Do not hesitate to contact us; we love that! :) + We'll try to reply to every e-mails (if any answer is needed), and also + to certain normal letters (Yes of course, we won't ruin ourselves for + stamps just to say "Thanks for writing!" :)). diff --git a/doc_fra.txt b/doc_fra.txt new file mode 100644 index 00000000..12b66a5a --- /dev/null +++ b/doc_fra.txt @@ -0,0 +1,2113 @@ + Ŀ + + + + .00 + + + + + + GRAFX 2.00 96.5% + + - MANUEL D'UTILISATION - + + + Ŀ + SOMMAIRE + + + - Prsentation + - Equipement requis + - Fichiers de configuration + - Options disponibles + - Let's talk about $$$, baby + - Astuces de dessin + - Problmes/Astuces gnrales/Questions + frquentes (FAQ) + + + + + + +Prsentation: + + + Ce programme a t conu pour pouvoir dessiner des images en 256 couleurs + dans un trs grand nombre de rsolutions (en fait, il y en a pour l'instant + 60 avec quelques-unes venant du monde Amiga). + Personne ne peut contester que la majeure partie des superbes GFX de la + "Scne" ont t dessins sur Amiga. Mais ces GFX sont dans des rsolutions + diffrentes des modes PC habituels. Alors nous avons voulu crer le premier + logiciel de dessin sur PC qui pourrait visualiser ces images, et qui + pourrait bien sr vous permettre de dessiner les vtres dans le mode vido + que vous voulez. + + Ce logiciel a t prsent pour la premire fois la Wired'96 o il a eu + un gros succs (bien plus que ce quoi nous nous attendions), alors nous + esprons que vous l'aimerez aussi. + + Il consiste en un certain nombre d'outils de dessin, d'effets et de menus. + Tous les effets fonctionnent avec n'importe quel outil de dessin. + + Sachez que ce logiciel a t cr pour VOUS, utilisateurs de PC qui enviez + les possesseurs d'Amiga pour les fantastiques logiciels de dessin dont ils + disposent. Ce logiciel n'a pas la prtention de remplacer les meilleurs + programmes de dessin Amiga, mais tente modestement de combler le gouffre + qu'il y a entre les logiciels PC et Amiga dans le domaine du dessin bitmap. + Si vous rvez d'une option trs utile que nous n'ayons pas encore prvue, + n'hsitez pas nous en faire part. Si nous la jugeons utile galement, et + surtout s'il est possible de l'inclure dans le programme :), nous l'y + mettrons ds que possible. + + + + +Equipement requis: + + + Pour pouvoir utiliser GrafX2, vous aurez besoin de: + + - un PC (386DX ou suprieur), + - DOS 5 ou suprieur (a marche peut-tre avec le DOS 3.1 mais on ne se + rappelle pas quelles sont les fonctions de l'INT 21h que nous utilisons), + - une carte vido compatible VGA (une carte VLB ou PCI est fortement recom- + mande), + - une souris 2 boutons (et son gestionnaire), + - 3 Megaoctets de RAM (a peut marcher avec moins si vous utilisez le cache + disque de DOS4GW ou bien celui de Windows :/). + + Mais pour une utilisation plus efficace, vous aurez besoin de: + + - au moins un 486DX66 (pour augmenter la vitesse globale), + - au moins 8 Mo de RAM pour capturer de trs grosses brosses et pour uti- + liser le multi-undo, + - une carte vido compatible VESA 1.2 (pour accder plus de modes vido). + + + + +Fichiers de configuration: + + + GrafX2 ncessite deux fichiers pour stocker sa configuration: 'GFX2.INI' + et 'GFX2.CFG'. + + GFX2.INI: + + + Ce fichier contient les paramtres dfinis dans le menu de configuration + (settings) ainsi que quelques autres. Vous pouvez diter ce fichier + l'aide d'un diteur de texte ASCII standard. + Lorsque vous cliquez sur Reload (recharger) dans le menu des "settings", + toutes les donnes contenues dans ce fichier sont restaures. Lorsque vous + cliquez sur Save (sauvegarder) ou bien lorsque vous quittez le programme + alors que l'option Auto-save (sauvegarde automatique) est enclenche, tous + les paramtres actuels sont crits (mis jour) dans ce fichier. + + Si vous avez corrompu ce fichier et que vous n'arrivez pas corriger le + problme, alors effacez-le et lancez GFXCFG.EXE. I crera automatiquement + un fichier d'initialisation par dfaut lorsque celui-ci est absent. + + + GFX2.CFG: + + + Ce fichier contient la configuration du clavier ainsi que l'tat des + variables du programme suivantes: + modes vido + tables de "shade" + stencil (pochoir) + masque + dgrads + + Toutes ces variables sont enregistres lorsqu'on clique sur le bouton + Save (sauvegarder) dans le menu de configuration ou bien lorsqu'on sort du + programme avec l'option Auto-save (sauvegarde automatique) enclenche. + Cependant, lorsque vous cliquez sur Reload (recharger) dans le menu des + "settings", seul l'tat de chaque mode vido est restaur. + + Note: le fichier GFX2_FRA.CFG est un fichier de configuration par dfaut + pour les claviers AZERTY. Si vous utilisez un clavier AZERTY, vous devriez + remplacer le fichier GFX2.CFG par GFX2_FRA.CFG. + + Important: partir de la version 2.00 95.5%, les fichiers .CFG auront + une compatibilit ascendante. Ceci signifie que vous pourrez rcuprer la + majeure partie de leur contenu d'une version l'autre en copiant votre + ancien fichier .CFG dans le rpertoire de votre nouvelle version de GrafX2 + et en lanant GFXCFG.EXE. En effet, ce programme convertira votre ancien + fichier afin qu'il soit utilisable par la nouvelle version de GrafX2. + Mais, copier un fichier .CFG d'une version antrieure la version 95.5% + ne marchera pas. De plus, (je ne vois pas pourquoi vous le feriez mais...) + copier un fichier .CFG rcent dans une version plus ancienne ne devrait + pas fonctionner non plus. + + + Note: Nous vous recommandons de ne pas modifier les touches affectes + l'mulation de la souris dans le programme GFXCFG car les valeurs que vous + donneriez pourraient interfrer avec les raccourcis utiliss dans les menus. + + + + +Options disponibles: + + + Les diffrentes options disponibles dans GrafX2 seront listes et + dtailles ci-dessous. Elles seront dcrites comme suit: + + ͻ ͻ + 1 3 Les boutons triangulaires 1 / + seront dtaills comme a: / 2 + ͹ ͼ + 2 4 + + ͼ + + + 1 - Pinceaux + 2 - Ajuster l'image / Effets sur l'image + 3 - Bouton Dessin la main + 4 - Courbes de Bzier (Splines) + 5 - Lignes + 6 - Arographe (Spray) + 7 - Remplissage (Flood-fill) / Remplacement de couleur + 8 - Polygnes / Polyformes + 9 - Polygnes/Polyformes plein(e)s + 10 - Rectangles vides + 11 - Rectangles pleins + 12 - Cercles/Ellipses vides + 13 - Cercles/Ellipses plein(e)s + 14 - Rectangles avec dgrad + 15 - Menu de dgrad + 16 - Sphres / Ellipses avec dgrad + 17 - Prise de brosse / Restauration + 18 - Prise de brosse par polyforme (lasso) / Restauration + 19 - Effets sur la brosse + 20 - Modes de dessin + 21 - Texte + 22 - Mode Loupe / Menu + 23 - Pipette / Inverser les couleurs + 24 - Taille de l'cran / Rsolution de scurit + 25 - Page de brouillon / Copier vers le brouillon + 26 - Sauver l'image / Sauvegarde automatique + 27 - Charger une image / Recharger + 28 - Paramtres gnraux (Settings) + 29 - Effacer l'image + 30 - Aide / Statistiques + 31 - Oops (Dfaire/Refaire) + 32 - Dtruire la page courante + 33 - Quitter le programme + 34 - Menu de palette + 35 - Dplacer la palette gauche / droite + 36 - Fentre de palette + 37 - Cacher le menu + + + + Quand vous utiliserez n'importe quel outil de dessin, un clic gauche + dessinera avec la couleur principale, tandis qu'un clic droit dessinera avec + la couleur de fond. + + Lorsque des botes de dialogue apparatront l'cran, Cancel (ou No) sera + toujours mul par la touche , et OK (ou Yes) par . + + Dans les diffrents menus, les titres sur les boutons contenant une lettre + souligne peuvent tre muls en tapant cette lettre au clavier. + + Dans quelques menus, vous pouvez slectionner un bloc de couleurs dans la + palette. Cela signifie que vous pouvez cliquer sur une couleur et dplacer + la souris vers une autre en maintenant le bouton appuy pour slectionner + un bloc de couleurs. + + Vous pouvez dplacer une fentre pour rendre visible l'image qui est + derrire en cliquant en haut de la fentre (sur le titre) et en maintenant + le bouton de la souris enfonc tout en la dplaant. + + + + 1 - Pinceaux: + + + Clic gauche: + ============> + + Affiche un menu ou vous pouvez choisir la forme de votre pinceau. + + Les pinceaux sont rangs par famille. Vous pouvez voir quelques + pinceaux de la mme famille mais avec des tailles diffrentes. Il y a au + moins un pinceau de chaque famille affich dans ce menu. + Voici la liste de toutes les diffrentes familles de pinceaux: + + + + + + + + + + Carr Disque Carr Disque Losange Alatoire + tram tram + _______________________________________________________________ + + + + + + + + + + Barre Barre Slash Anti- Croix X Croix + + horiz. verticale slash + + Les 3 derniers pinceaux dans le menu appartiennent la famille + "divers" et leur taille ne peut pas tre modifie. + + + Clic droit: + ============> + + Transforme votre brosse actuelle en pinceau. En fait, c'est une + "monochromisation" de la brosse. C'est--dire que toutes les couleurs de + la brosse qui ne sont pas la couleur de fond passeront de la mme + couleur que la couleur principale. Mais cette option ne modifie pas la + brosse: vous n'avez qu' cliquer avec le bouton droit sur une des + boutons "Get brush" pour rcuprer la brosse en couleur. + + + Note: Lorsque vous appuyez (pas dans le menu) sur la touche + (valeur par dfaut), le pinceau actuel devient le plus petit membre de la + famille "Disque": c'est--dire 1 pixel. + + + + 2 - Ajuster l'image / Effets sur l'image: + + + Clic gauche: + ============> + + Vous permet de dplacer ("scroller") l'image pour recentrer votre + graphe par exemple. + Toute partie du dessin qui sort d'un cot de l'image revient par le + ct oppos. + + Ceci est considr comme tant de la famille des outils de dessin. + + + Clic droit: + ============> + + *** Pas encore implment *** + + + + 3 - Bouton Dessin la main: + + + Clic gauche: + ============> + + Selectionne le mode dessin la main actuel comme outil de dessin + actif. Il y a 3 modes de dessin la main: + + - Dessin continu: Lorsque vous dplacez le curseur de la souris, le + pinceau est rgulirement appliqu sur l'image, reliant les + diffrents points de l'cran sur lesquels vous tes passs. Cet + outil de dessin autorise le changement de la couleur principale et + de la couleur de fond durant son utilisation. + + - Dessin discontinu: Lorsque vous dplacez la souris, le pinceau est + appliqu la position actuelle de la souris chaque VBL (balayage + vertical de l'cran). Cet outil de dessin autorise le changement de + la couleur principale et de la couleur de fond durant son + utilisation. + + - Dessin point par point: Le pinceau est simplement appliqu la + position o vous avez cliqu en premier. + + + Clic droit: + ============> + + Permute les diffrents modes de dessin la main, et active en mme + temps l'outil de dessin la main. + + + + 4 - Courbes de Bzier (Splines): + + + Clic gauche: + ============> + + Selectionne le mode de courbe courant comme outil de dessin actif. + Il y a deux modes de courbes diffrents: + + - Courbes 4 points de contrle: Dfinissez la ligne de base comme + une ligne classique; puis dplacez, avec le bouton gauche de la + souris, les points de contrle internes afin de choisir la forme de + la courbe. Quand la courbe a la forme que vous dsirez, cliquez sur + le bouton droit de la souris pour la tracer dfinitivement. + + - Courbes 3 points de contrle: Fonctionne comme dcrit ci-dessus, + mais vous n'aurez qu'un seul point de contrle interne placer. + De plus, la courbe sera trace juste aprs avoir plac ce point. + + + Clic droit: + ============> + + Permute les diffrents modes de courbes, et active en mme temps + l'outil de dessin de courbes. + + + + 5 - Lignes: + + + Clic gauche: + ============> + + Selectionne le mode de dessin de lignes actuel comme outil de dessin + actif. Il y a 2 modes de dessin de lignes: + + - Lignes classiques: En cliquant une premire fois sur l'image, vous + dfinirez de dbut de la ligne. Maintenez le bouton appuy pour + placer la fin de la ligne; et relchez le bouton pour tracer la + ligne. + + - Lignes relies: Fonctionne de la mme manire que prcdemment, mais + la fin d'une ligne deviendra automatiquement le dbut de la + suivante. Lorsque vous voudrez arrter l'enchinement de lignes, + utilisez le bouton oppos de la souris. "Le bouton oppos" signifie + que si vous avez commenc tracer les lignes avec le bouton gauche + (couleur principale), il faudra interrompre le traitement avec le + bouton de droite; et rciproquement. + + - Lignes concentriques: lors du premier clic sur l'image, vous + dfinirez le centre des lignes. En ralit, le centre est dfini + par la position de la souris lorsque vous relchez son bouton. + Ensuite vous pouvez dessiner des lignes partant du centre vers la + position actuelle de la souris en cliquant. Pour arrter de dessiner + des lignes concentriques, utilisez le bouton oppos de la souris. + Cet outil de dessin autorise le changement de la couleur principale + et de la couleur de fond durant son utilisation. + + + Clic droit: + ============> + + Permute les diffrents modes de dessin de lignes, et active en mme + temps l'outil de dessin de lignes. + + + + 6 - Arographe (Spray): + + + Clic gauche: + ============> + + Selectionne l'arographe comme outil de dessin actif. Cet outil de + dessin autorise le changement de la couleur principale et de la + couleur de fond durant son utilisation. + + + Clic droit: + ============> + + Affiche le menu de configuration de l'arographe: + + - Size (Taille): Dfinit le diamtre du cercle dans lequel l'aro- + graphe fonctionnera. + + - Delay (Dlai): Dfinit le nombre de VBL (balayage vertical de + l'cran) qui seront attendus entre deux jets (cycles) de l'aro- + graphe. + + - Mode: Dfinit si vous dsirez utiliser un arographe monochrome ou + multicolore. + + - Mono-flow (flux en monochrome): Dfinit le nombre de fois que le + pinceau sera alatoirement appliqu dans le cercle de l'arographe + chaque jet (cycle). + + - Palette: Un clic gauche sur une couleur de la palette vous permettra + de voir en quelle quantit elle sera utilise dans le flux multi- + colore, et de la modifier en utilisant la jauge sur la droite. Si le + flux de cette couleur tait gal 0, il sera mis la valeur + "Init". Un clic droit sur une couleur fera automatiquement passer sa + quantit 0, ce qui revient la supprimer du flux multicolore. + + - Clear (Effacer): Supprime toutes les couleurs du flux multicolore. + En fait, cela place une valeur nulle dans l'utilisation de chacune + des couleurs. + + - Init: Ceci vous permet de dfinir une valeur qui sera automatique- + ment applique aux couleurs ayant un flux nul lorsque vous cliquerez + dans la palette l'aide du bouton gauche. Cette option permet de + dfinir plus rapidement un ensemble de couleurs. + + - +1,-1,x2,2: Modifie la valeur de toutes les couleurs selectionnes + (et seulement celles-ci). + + + + 7 - Remplissage (Flood-fill) / Remplacement de couleur: + + + Clic gauche: + ============> + + Slectionne le remplisseur comme outil de dessin actif. + Le remplisseur, comme n'importe quel outil de dessin, sera affect par + tous les effets. + + Remarquez que seule la partie visible de l'image sera remplie (de mme + que pour tous les autres outils de dessin, le remplissage n'affecte que + la partie visible du dessin; ceci vitant des effets indsirables et non + contrls par l'utilisateur). + + + Clic droit: + ============> + + Slectionne le remplacement de couleur comme outil de dessin. + + Chaque rgle a ses exceptions et la rgle nonce ci-dessus n'y droge + pas. Cet outil est en effet le seul n'tre affect par aucun effet ( + l'exception du Stencil) et pouvoir galement modifier les parties non + visibles de l'image. + Le but de cet outil tant de remplacer toutes les occurences d'une + couleur dans l'image par une autre, il aurait t dommage de se limiter + modifier uniquement la partie visible de l'image. + + + + 8 - Polygnes / Polyformes: + + + Clic gauche: + ============> + + Slectionne les polygnes comme outil de dessin actif. + + Ceci fonctionne exactement comme les lignes relies en reliant les + extrmits quand vous avez termin. + + + Clic droit: + ============> + + Slectionne les polyformes comme outil de dessin actif. + + Cet outil fonctionne comme une combinaison du dessin la main et des + lignes relies. + Si vous maintenez le bouton de la souris press, vous dessinerez comme + si vous tiez en mode de dessin la main. Et, si vous relchez le + bouton de la souris, cela fonctionnera comme les lignes relies. + + Cliquez sur le bouton de la souris oppos (i.e.: cliquez droite si + vous avez commenc dessiner avec le bouton gauche de la souris, et + vice versa) pour terminer l'opration. Les deux extrmits seront + relies automatiquement. + + + + 9 - Polygones/Polyformes plein(e)s: + + + Fonctionnent exactement de la mme manire que les polygnes et poly- + formes ci-dessus, mais remplissent l'intrieur des formes ainsi dfinies. + + + + 10 - Rectangles vides: + + + N'importe quel clic: + ====================> + + Selectionne les rectangles vides comme outil de dessin actif. + + Placez le coin d'un rectangle. Maintenez le clic pour dplacer le coin + oppos et relachez le bouton de la souris pour le placer dfinitivement. + + + + 11 - Rectangles pleins: + + + N'importe quel clic: + ====================> + + Slectionne les rectangles pleins comme outil de dessin actif. + + Fonctionne comme un rectangle vide. + + + + 12 - Cercles/Ellipses vides: + + + Clic gauche: + ============> + + Slectionne les cercles vides comme outil de dessin actif. + + Positionnez le centre du cercle et maintenez le bouton de la souris + pour choisir son rayon. + + + Clic droit: + ============> + + Slectionne les ellipses vides comme outil de dessin actif. + + Positionnez le centre du cercle et maintenez le bouton de la souris + pour choisir ses dimensions. + + + + 13 - Cercles/Ellipses plein(e)s: + + + Fonctionne comme les cercles et les ellipses vides. + + + + 14 - Rectangles avec dgrad: + + + *** Pas encore implment *** + + + + 15 - Menu de dgrad: + + + N'importe quel clic: + ====================> + + Ouvre une fentre dans laquelle vous pouvez dfinir la faon dont les + dgrads sont traits. + Les diffrentes sections de ce menu sont: + + - Direction (flche): Change le sens du dgrad. + + - Mthode de transition: Permute parmi les trois mthodes suivantes: + - Pas de transition + - Transition de base + - Transition amliore + + - Mix (Mlange): Mlange le dgrad avec un facteur alatoire plus ou + moins important. + + - Palette: Selectionnez un intervale de couleurs pour constituer un + dgrad. + + - Ascenseur d'index: Dfinit le dgrad courant parmi un ensemble de + 16 mmoriss. + + + + 16 - Sphres / Ellipses avec dgrad: + + + Clic gauche: + ============> + + Slectionne les sphres comme outil de dessin actif. + + Positionnez le centre de la sphre et maintenez le bouton de la souris + pour choisir son rayon. Ensuite placez la source de l'clairage. + + + Clic droit: + ============> + + Slectionne les ellipses avec dgrad comme outil de dessin actif. + + *** La version actuelle de cet outil n'est pas la bonne, donc *** + *** nous expliquerons son fonctionnement quand elle sera acheve. *** + + + Si vous tracez une sphre ou une ellipse dgrade avec le bouton droit + de la souris, le rsultat sera la mme figure remplie avec la couleur de + fond. + + + + 17 - Prise de brosse / Restauration: + + + Clic gauche: + ============> + + Dmarre une prise de brosse. + + Cliquez sur un coin du rectangle contenant la brosse puis maintenez le + clic pour dfinir le coin oppos du rectangle. Relachez le bouton de la + souris pour prendre la brosse. Effectuer cette opration avec le bouton + droit de la souris effacera la zone dans laquelle la brosse a t prise + avec la couleur de fond. + + + Clic droit: + ============> + + Restaure l'ancienne brosse. + + + + 18 - Prise de brosse par polyforme / Restauration: + + + Clic gauche: + ============> + + Capture une brosse de forme quelconque en dfinissant un "polyforme" + (veuillez vous rferer la section 8 pour plus d'explications). + + + Clic droit: + ============> + + Restaure l'ancienne brosse (pareil que ci-dessus). + + + + 19 - Effets sur la brosse: + + + N'importe quel clic: + ====================> + + Affiche un menu dans lequel les options suivantes sont disponibles: + + - X: Inversion selon X (symtrie par rapport (Oy)). + + - Y: Inversion selon Y (symtrie par rapport (Ox)). + + - Rotate by 90: Effectue sur la brosse une rotation de 90 degrs. + + - Rotate by 180: Effectue sur la brosse une rotation de 180 degrs. + + - Rotate by any angle (Rotation de n'importe quel angle): Engendre une + opration interactive qui permet de faire tourner la brosse. Pour + cela, commencez par placer le centre de rotation avec le bouton + gauche de la souris (si, ce moment-l, vous appuyez sur le bouton + droit, l'opration sera annule). Ensuite vous pouvez dfinir + l'angle de rotation autant de fois que vous le voulez en dplaant + la souris et en cliquant avec le bouton gauche. Puis vous validerez + avec le bouton droit lorsque vous serez satisfait. + Pendant ce temps, vous pouvez appuyer sur les 8 chiffres extrieurs + du pav numrique pour dfinir des angles multiples de 45: + 135 90 45 + \ | / + '7' '8' '9' + 180 -'4' '6'- 0 + '1' '2' '3' + / | \ + 225 270 315 + + - Stretch (Etirement): Engendre une opration interactive qui permet + d'tirer la brosse. Pour cela, commencez par placer le coin haut- + gauche de la brosse avec le bouton gauche de la souris (si, ce + moment-l, vous appuyez sur le bouton droit, l'opration sera + annule). Ensuite vous pouvez placer le coin oppos autant de fois + que vous le voulez, puis vous validerez avec le bouton droit lorsque + vous serez satisfait. Si vous placez ce point des coordonnes + infrieures celles du point de dpart, la brosse sera inverse. + Pendant ce temps, vous pouvez appuyer sur les touches suivantes dont + voici les effets: + 'D' : double la brosse en X et en Y + 'H' : rduit la brosse de moiti en X et en Y + 'X' : double la brosse en X + 'Shift+X': rduit la brosse de moiti en X + 'Y' : double la brosse en Y + 'Shift+Y': rduit la brosse de moiti en Y + 'N' : restaure la taille normale de la brosse (peut se + rvler utile car c'est le seul moyen d'annuler) + + - Distort (Dformation): + *** Pas encore implment *** + + - Outline (Contours): + Cette option permet de dessiner les contours de la brosse avec la + couleur principale (Fore-color). + + - Nibble (Grignotter): + Cette option "grignotte" les contours de la brosse. C'est en quelque + sorte l'effet inverse de l'option Outline. + + - Recolorize: Modifie la brosse de faon ce qu'elle ressemble + l'aspect qu'elle aurait dans la page de brouillon, en utilisant la + palette courante. + + - Get brush colors: Transfre les couleurs de la page de brouillon + utilises par la brosse, dans la palette courante. + + - Brush handle: Vous permet de choisir o placer la prise (poigne) de + la brosse. + + - Load / Save: charger ou sauvegarder une brosse. + + + + 20 - Modes de dessin: + + + Ce bouton ouvre un menu dans lequel vous pouvez activer/dsactiver les + diffrents modes de dessin. (Les touches [F1]-[F9] correspondent aux 9 + boutons) + + Dans ce menu, le bouton "All off" (tout teint) dsactive tous les modes + de dessin. La touche [Suppr] est le raccourci clavier pour ce bouton. + + Le bouton "Feedback" sert uniquement pour les modes "Shade", "Quick- + shade", "Smooth" et "Transparence". Lorsqu'il est activ, il indique que + l'tat _actuel_ de l'image doit tre pris en compte pour l'effet au lieu + de l'tat dans lequel tait l'image lorsqu'on a click pour commencer + tracer. Le mieux, comme bien souvent, est que vous testiez par vous-mme + avec et sans Feedback pour constater la diffrence. + + Les autres boutons sont les suivants: + + + * Mode Shade (Ombrage) / Menu: + ------------------------------ + + Cet effet consiste incrmenter ou dcrmenter le numro de la couleur + dans un ensemble dfini par l'utilisateur. Cela montre sa vraie + dimension lorsque l'ensemble de couleurs est un dgrad. Alors, vous + pouvez travailler sur une partie de l'image o les couleurs appartiennent + ce mme ensemble sans avoir changer la couleur de votre pinceau + systmatiquement. + Vous pouvez choisir d'incrmenter ou de dcrmenter la couleur en + cliquant sur le bouton gauche ou droit de la souris lorsque vous dessinez. + Si vous cliquez sur une couleur qui n'appartient pas l'ensemble de + couleurs, elle restera inchange. + + Clic gauche: + ============> + + Active/Dsactive le mode Shade. + + + Clic droit: + ============> + + Ouvre un menu dans lequel vous pouvez dfinir une table de shades + parmi les 8 mmorises par le programme. + Les diffrentes sections de ce menu sont: + + - Palette: Vous pouvez dfinir dans celle-ci les blocs de couleurs + insrer dans la table des shades. + + - Scroller: Sert changer de table de shades. + + - Zone de dfinition de table de Shades: Les 512 cases fournies + sont largement suffisantes pour dfinir les diffrents shades puisque + chacune des 256 couleurs de la palette ne peut tre prsente qu'une + seule fois dans chaque table. + + - Une fentre (celle situe en haut droite) qui vous permet de + visualiser les diffrents shades dfinis dans la table actuelle. + + - Copy (copier): Copie le contenu actuel de la table dans un buffer. + (Lors de l'ouverture du menu, la table courante est automatiquement + range dans le buffer). + + - Paste (coller): Copie le contenu du buffer ci-dessus dans la table + actuelle. + + - Clear (tout effacer): Permet de rinitialiser la table de "shades". + + - Insert (insrer): Sert insrer le bloc slectionn dans la palette + la position du curseur dans la table des shades. + SI vous clickez avec le bouton gauche de la souris sur ce bouton ALORS + SI un bloc de plus d'une case est slectionn dans la table ALORS + Il est effac puis on insre le bloc dfini dans la palette. + SINON + On insre le bloc dfini dans la palette juste avant la case + slectionne. + FIN SI + SINON + Le bloc dfini dans la palette est insr en crasant les couleurs + suivant le dbut du bloc slectionn dans la table. + FIN SI + + - Delete (effacer): Supprime le bloc slectionn dans la table. + + - Blank (vide): Suit l'algorithme suivant: + SI vous clickez avec le bouton gauche de la souris sur ce bouton ALORS + On remplace le bloc slectionn dans la table par des cases vides + SINON + SI un bloc de plus d'une case est slectionn dans la table ALORS + Insrer une case vide gauche et une case vide droite du bloc + (ceci sert isoler un shade rapidement) + SINON + Insrer une case vide gauche de la case slectionne + FIN SI + FIN SI + + - Invert (inverser): Inverse l'ordre du bloc slectionn dans la + table. + + - Swap (changer): Permet de dplacer un bloc (cela l'change avec ce + qu'il y a l ou veut le dplacer). + + - Undo (dfaire): Permet d'annuler la dernire modification de la + table. + + - Les 2 numros qui s'affichent droite de ces boutons sont: + (en haut)- le numro de la couleur slectionne dans la palette si + une seule est slectionne. + (en bas) - le numro de la couleur contenue dans la case de la table + de shades si cette case est la seule slectionne. + + - Le bouton de "mode" affiche 3 tats diffrents: + "Normal": + Opre l'intrieur de l'intervalle de couleurs et sature ses + bordures. + "Loop" (Boucle): + Boucle lorsque les bornes de l'intervalle sont dpasses. + "No saturation": + Ne sature pas aux bornes de l'intervalle si elles sont dpasses. + Si le Pas (voir plus bas) est de 1, cette option fait exactement la + mme chose que le mode Normal. + + - Set/Disable (placer un masque): Si vous voulez dfinir plusieurs + shades dans une mme table mais que vous souhaiteriez qu'ils ne soient + pas tous effectifs en mme temps, vous pouvez en masquer certains ce + qui aura pour effet qu'ils seront interprts comme des cases vides. + Pour ce faire, slectionnez un bloc dans la table des shades et + clickez sur "Set". Le bloc sera alors soulign d'un trait blanc; ce + qui signifie qu'il est dsactiv. + + - Clear/Enable (enlever le masque): fait exactement l'inverse du + bouton prcdent. + + - Step (pas): Dfinit un pas d'incrmentation du shade. Plus le pas + est grand et plus vous parcourerez rapidement les couleurs du shade. + Par exemple: si le pas est de 2 et que vous avez dfini un shade avec + les couleurs 0,1,4,5,9 et que vous clickez sur un pixel de couleur 1, + il prendra alors la couleur 5 qui est 2 cases plus loin dans la table. + + (Nous sommes dsols pour ces considrations techniques assez + lointaines d'une vision prement artistique; mais sachez que cet effet + est vraiment trs utile et qu'il est prfrable que vous compreniez son + fonctionnement si vous voulez en profiter pleinement). + + + + * Mode Quick-shade (Ombrage) / Menu: + ------------------------------------ + + Ce mode de dessin a peu prs le mme effet que le mode Shade si ce + n'est qu'il est beaucoup plus rapide configurer mais un peu moins + puissant. + Lorsque vous dessinez sur une couleur de l'image qui se situe entre la + couleur principale (fore-color) et la couleur de fond (back-color) dans la + palette, la couleur tend se rapprocher de la fore-color (suivant le pas + dfini) si l'on dessine avec le bouton gauche de la souris, ou bien tend + vers la back-color si l'on dessine avec le bouton droit. + + Clic gauche: + ============> + + Active/Dsactive le mode Quick-shade. + + + Clic droit: + ============> + + Ouvre un menu avec quelques paramtres qui reprsentent exactement la + mme chose que dans le menu du mode Shade. Ces paramtres sont le pas et + le mode de bouclage/saturation (normal, loop, no saturation). + + + + * Mode Stencil (Pochoir) / Menu: + -------------------------------- + + C'est utilis pour empcher la modification de certaines couleurs si + vous essayez de dessiner sur elles. L'application principale du stencil + est lorsque vous voulez remplacer une ou plusieurs couleurs par une autre. + + Clic gauche: + ============> + + Active/Dsactive le mode Stencil. + + Clic droit: + ============> + + Ouvre un menu dans lequel vous pouvez dfinir un stencil. + Les diffrentes sections de ce menu sont: + + - Clear (Effacer): Dprotge toutes les couleurs. + + - Invert (Inverser): Les couleurs qui taient protges ne le sont + plus et vice versa. + + - Palette: Selectionnez les couleurs qui doivent tre protges avec + le bouton gauche de la souris ou dprotgez-les avec le bouton + droit. + + + + * Mode Masque / Menu: + --------------------- + + Cet effet aurait pu tre appel "True stencil" (vrai pochoir) car il + protge des parties de l'image au lieu de protger des couleurs. Les + couleurs que vous slectionnez reprsentent les pixels dans la page de + brouillon, correspondant aux pixels dans la page actuelle, que vous ne + voulez pas modifier. + Par exemple, dessinez une simple figure blanche sur un fond noir dans la + page de brouillon. Puis, slectionnez la couleur noire dans le menu du + mode Masque. Lorsque vous dessinerez dans la page actuelle, seulement les + pixels correspondant aux pixels blancs (non-noirs) dans la page de + brouillon seront modifis. + + Clic gauche: + ============> + + Active/Dsactive le mode Masque. + + Clic droit: + ============> + + Ouvre un menu dans lequel vous pouvez dfinir les couleurs du masque. + Ce menu fonctionne de la mme faon que celui du Stencil. Veuillez + donc vous rfrer au paragraphe consacr au Stencil pour savoir comment + utiliser ce menu. + + + + * Mode Grille / Menu: + --------------------- + + C'est utile pour accrocher le curseur aux points de croisement d'une + grille. C'est gnralement utilis pour dessiner une grille avant de + dessiner des sprites de la mme taille tels que des "tiles" ou une fonte, + ou bien pour dessiner des figures ou prendre des brosses avec des + dimensions multiples du pas de la grille.'); + + Clic gauche: + ============> + + Active/Dsactive le mode Grille. + + + Clic droit: + ============> + + Ouvre un menu dans lequel vous pouvez dfinir les paramtres de la + grille. Ces paramtres sont: + + - X,Y: Pas de la grille. + + - dX,dY: Dcalages de la grille. + + + + * Mode Trame (Passoire) / Menu: + ------------------------------- + + Cet effect permet, en dfinissant un motif, de dessiner seulement sur + des points particuliers de l'image. + Si vous tes un dessinateur Manga, vous pourriez trouver a utile pour + dessiner des ombres avec diffrentes trames ou bien des transitions de + couleurs. + + Clic gauche: + ============> + + Active/Dsactive le mode Trame. + + + Clic droit: + ============> + + Ouvre un menu dans lequel vous pouvez dfinir les paramtres des + trames. Ce menu est constitu de: + + - Zone de dessin 16x16: Vous pouvez dfinir une trame dedans (clic + gauche => pixel blanc / clic droit => pixel noir). + Tous les pixel blancs indiquent que lorsque vous dessinerez, des + pixels seront appliques sur l'image aux positions correspondantes + tandis que des pixels noirs n'entrneront aucun affichage: les + points blancs correspondent aux "trous de la passoire". + + - 12 trames par dfaut: Elles peuvent tres recopies vers la zone de + dessin (16x16). + + - "Transfer to brush" (transfrer vers la brosse): Copie la trame vers + la brosse (pixels blancs => couleur principale / pixels noirs => + couleur de fond). + + - "Get from brush" (rcuprer partir de la brosse): Place la brosse + dans la zone de dessin (couleur de fond => pixels noirs / les autres + => pixels blancs). + + - 4 flches de dplacement (scrolling): Dplacent la trame dans la + zone de dessin. + + - 4 flches de dimensionnement: Dfinissent les dimensions de la + trame. + + - Valeur par dfaut (carr noir ou blanc): Indique quelle couleur doit + tre insre quand vous augmentez les dimensions de la trame. + + - "Clear" (Effacer): Remplit toute la trame avec la valeur par dfaut + (voir ci-dessus). + + - "Invert" (Inversion): Il ... inverse :) ... les pixels noirs et + blancs. + + + + * Mode Transparence (Colorize) / Menu: + -------------------------------------- + + Cela permet de mlanger les couleur(s) du pinceau (brosse) avec les + couleurs de l'image. C'est utilis pour faire des effets de transparence + comme avec de l'aquarelle. + + Clic gauche: + ============> + + Active/Dsactive le mode Transparence. + + + Clic droit: + ============> + + Ouvre un menu dans lequel vous pouvez dfinir les paramtres de + transparence. Ces paramtres sont: + + - Taux d'interpolation: Indique le pourcentage de la couleur applique + qui sera considre sur la couleur remplace. + + - Mthode par interpolation: Utilise une mthode de moyenne pondre + pour calculer la couleur, selon le taux d'interpolation. + + - Mthode additive: Utilise les teintes les plus claires pour choisir + la couleur appliquer. + Par exemple: si vous voulez appliquer une couleur ayant les teintes + 30,20,40 sur une couleur 10,50,20, la couleur qui sera applique + sera celle qui, dans la palette, sera la plus proche de la couleur + thorique 30,50,40. + + - Mthode soustractive: Utilise les teintes les plus sombres pour + choisir la couleur appliquer. + Par exemple: si vous voulez appliquer une couleur ayant les teintes + 30,20,40 sur une couleur 10,50,20, la couleur qui sera applique + sera celle qui, dans la palette, sera la plus proche de la couleur + thorique 10,20,20. + + + + * Mode Smooth (adouci) / Menu: + ------------------------------ + + Cela permet d'obtenit un effet d'anti-aliasing primaire mais ce n'est + vraiment pas aussi efficace que si c'tait fait par un artiste. De toutes + faon, cet effet est surtout utile pour donner un aspect flou. + + Click gauche: + =============> + + Active/Dsactive le mode Smooth. + + + Clic droit: + ============> + + Ouvre un menu dans lequel vous pouvez dfinir la matrice du Smooth ou + bien en choisir une parmi les 4 prdfinies. + La case du milieu reprsente le pixel sur lequel on dessine et les 8 + cases qui l'entourent reprsentent les pixels voisins. Le point sur + lequel on dessine sera alors remplac par la moyenne pondre (suivant + les valeurs de chaque case) des 9 points dfinis. + + + + * Mode Smear (taler) / Menu: + ------------------------------ + + Cet effet tale les pixels dans la direction dans laquelle vous bougez + votre pinceau, comme si vous vouliez taler de la peinture fraiche avec + le doigt. Vous pouvez combiner cet effet avec l'effet de transparence. + + N'importe quel clic: + ====================> + + Active/Dsactive le mode Smear. + + + + * Mode Tiling (Dallage) / Menu: + ------------------------------- + + Cela consiste appliquer des parties de la brosse ajustes sur une + sorte de carrelage lorsque vous dessinez. C'est principalement utilis + pour dessiner rapidement un fond avec un certain motif, mais un grand + nombre d'autres utilisations est possible. + + Clic gauche: + ============> + + Active/Dsactive le mode Tiling. + + + Clic droit: + ============> + + Ouvre un menu dans lequel vous pouvez choisir les paramtres de + Tiling. Ces paramtres sont les dcalages du dallage. (Daaaallaaaage... + Ton univers impitoyaaable... :) Je suis vraiment dsol... j'ai pas pu + m'en empcher :)) + + + + 21 - Texte: + + + *** Pas encore implment *** + + + + 22 - Mode Loupe / Menu: + + + Clic gauche: + ============> + + Dmarre/Annule le choix de la partie zoome. Si vous tes dj en mode + Loupe, vous retournerez en mode normal. + + + Clic droit: + ============> + + Affiche un menu dans lequel vous pouvez choisir le facteur de loupe. + + + Note: Lorsque vous tes en mode Loupe, vous pouvez dplacer la barre de + sparation ("split") en cliquant dessus et en dplaant la souris vers la + gauche ou vers la droite en maintenant enfonc le bouton de la souris. + + + + 23 - Pipette / Inverser les couleurs: + + + Clic gauche: + ============> + + Dmarre une prise de couleur. + + Cliquez sur l'image pour rcuprer la couleur du pixel sur lequel vous + tes. Vous pouvez prendre indiffrement une nouvelle couleur principale + ou couleur de fond en utilisant respectivement le bouton gauche ou droit + de la souris. + + + Clic droit: + ============> + + Echange la couleur principale et la couleur de fond. + + + La couleur sur laquelle vous pointez actuellement sera affiche dans la + barre d'outils la suite des coordonnes. + Si vous clickez en dehors de l'image, la couleur 0 vous sera renvoye. + + + + 24 - Taille de l'cran / Rsolution de scurit: + + + Clic gauche: + ============> + + Affiche un menu dans lequel vous pouvez dfinir la taille de votre + image (jusqu' 1024x768) en cliquant dans les botes nommes "Width" + (Largeur) et "Height" (Hauteur); et la rsolution (dans la liste) dans + laquelle vous souhaitez dessiner. + + Cliquer sur une rsolution avec le bouton droit de la souris ne + changera pas seulement la rsolution de l'cran, mais changera aussi les + dimensions de l'image par celles de l'cran. + + Les rsolutions affiches en gris fonc sont des modes VESA qui ne + sont pas supports par votre carte vido. Si vous avez des modes comme + cela, vous devriez essayer de lancer un driver VESA tel que Univesa ou + Univbe avant de lancer le programme. Si ces modes restent indisponibles, + alors cela signifie que votre carte vido ne les supporte vraiment pas. + + Les petits boutons sur le ct gauche des lignes dans la liste des + modes ont t conus pour vous permettre d'inhiber certains modes qui ne + sont pas supports par votre carte. + + Lorsque vous clickez sur l'un de ces boutons, sa couleur change vers + l'une des 4 suivantes. La signification de chacune de ces couleurs est: + + - Gris clair: Le mode vido est correct. Il peut tre utilis par + l'option de changement de rsolution automatique lorsque vous + chargez une image, et vous pouvez le slectionner dans le menu des + rsolutions. + + - Blanc: Cela fonctionne exactement comme ci-dessus. De plus, cela + vous permet de cocher vos modes prfrs. En effet, le nombre + impressionnant de modes vido rendant difficile la recherche d'un + mode en particulier dans la liste, aussi vous pouvez mettre ceux que + vous utilisez frquemment en blanc afin qu'ils soient plus facile + localiser ultrieurement. (Note: vous ne pouvez pas inhiber le mode + 320x200 standard) + + - Gris fonc: Il vous permet d'indiquer quels modes ne sont pas + parfaits (clignotements, dcentrage, surbrillance, etc...) mais qui + peuvent tout de mme tres utiliss par "l'auto-rsolution". La + diffrence avec les boutons gris clair est que ces modes ne seront + pas utiliss par l'option de changement de rsolution automatique. + + - Black: Utilisez cette couleur pour les modes qui ne fonctionnent + vraiment pas. Ainsi, ces modes ne seront pas utiliss par l'option + "auto-set res." et le programme vous empchera de les slectionner + partir du menu des rsolutions. + + + Clic droit: + ============> + + Passe automatiquement au mode 320x200 MCGA. + + + + 25 - Page de brouillon / Copier vers le brouillon: + + + Clic gauche: + ============> + + Passe la page de brouillon. La page courante est alors considre + comme la nouvelle page de brouillon, et la page de brouillon comme la + nouvelle page courante. + + + Clic droit: + ============> + + Ouvre un menu dans lequel vous pouvez choisir si vous voulez copier + toute l'image (touche de raccourci dans ce menu: [Return]), seulement + les pixels, seulement la palette, ou seulement quelques couleurs. + Dans ce dernier cas, un second menu (genre stencil) vous proposera de + slectionner les couleurs copier (par dfaut, elles sont toutes + slectionnes). + Veuillez vous reporter la section "18 - Stencil" pour savoir comment + utiliser ce dernier menu. + La dernire option du menu ("Copier palette et remapper"), adapte la + page de brouillon avec la palette actelle puis recopie cette palette sur + la page de brouillon. Cette option est utile pour remapper rapidement + une image avec la palette d'une autre. + + + + 26 - Sauver l'image / Sauvegarde automatique: + + + Clic gauche: + ============> + + Affiche un selecteur de fichier dans lequel les options suivantes sont + disponibles: + + - Lecteurs: Vous permettent de changer le lecteur courant. Vous pouvez + aussi utiliser + pour changer de lecteur. + + - Format: Vous permet de choisir le format de fichier que vous voulez + (les formats PAL et KCF sont des formats de palette). + + - Filename (Nom de fichier): Vous permet de donner un nouveau nom + l'image. Si aucune extension n'est donne, une par dfaut (dpendant + du format) sera utilise. + + - Liste de fichiers: Vous permet de parcourir l'arborescence du disque + ou de remplacer un fichier dj existant. + + - Delete (Supprimer): Permet d'effacer le fichier ou le rpertoire (si + celui-ci est vide) se trouvant sous la barre de slection. + + - Save (Sauver): Sauve l'image avec le nom de fichier courant, le + format choisi et le commentaire courant (pour les fichiers PKM). + Si le nom de fichier courant reprsente un rpertoire, vous entrerez + dedans. + + - Commentaire (Txt): Si vous utilisez le format PKM, vous pouvez + saisir un commentaire de votre image. + + Note: La touche Backspace vous amne directement au rpertoire parent. + Tapez les 1res lettres d'un nom de fichier que vous recherchez + pour y accder plus rapidement. + + Clic droit: + ============> + + Sauve l'image courante avec son nom de fichier, son format et son + commentaire actuels. + + + Si le nom de fichier utilis pour sauver l'image existe dj, une + demande de confirmation apparatra. + + + + 27 - Charger une image / Recharger: + + + Clic gauche: + ============> + + Cela fonctionne de la mme faon que la sauvegarde. + + Vous aurez accs dans le selecteur de format un filtre "*.*". + Et bien videmment, vous ne pourrez pas saisir de commentaire. + + + Clic droit: + ============> + + Recharge l'image. + + + Si vous voulez charger une image et que vous n'avez pas sauv les + dernires modifications de l'image courante, une demande de confimation + apparatra. + + + + 28 - Paramtres gnraux (Settings): + + + N'importe quel clic: + ====================> + + Affiche un menu dans lequel vous pouvez configurer divers lments du + programme: + + - Nombre de pages d'UNDO: Indique le nombre total de pages que GrafX2 + mmorisera. Chaque fois que vous modifiez l'image, son tat courant + est mmoris dans l'une de ces pages. Pour parcourir ces pages, + utilisez le bouton Oops(Undo/Redo). + + - Fonte: Dtermine si vous voulez utiliser GrafX2 avec une police de + caractres classique ou une autre un peu plus amusante. + + - Sensibilit de la souris: Modifie la vitesse de la souris. + + - Montrer/Cacher les fichiers dans les listes: Dfinit si certains + fichiers/rpertoires aux attributs particuliers doivent apparatre + ou non dans les slecteurs de fichiers. + + - Montrer/Cacher les limites de l'image: Indique si les limites de + l'image doivent tre affiches lorsque vous tes dans une rsolution + plus grande que l'image. + + - Ecraser la palette: Indique si le chargement d'un fichier dont la + palette fait moins de 256 couleurs doit craser le reste de la + palette actuelle (remplacer par du noir). + + - Maximiser la preview: Maximise la preview des images de faon ce + qu'elle prenne le plus de place. Si vous n'tes pas dans la mme + rsolution que celle utilise par l'image, cela peut corriger + l'aspect ratio, mais si l'image ne remplit pas tout l'cran, cela + peut tre pire. + + - Backup: Lorsque vous sauverez une image sur un fichier existant, le + programme renommera ce fichier en "*.BAK" o * est le nom de l'image + sans son extension. Si le fichier de backup existe dj dans le + rpertoire, il sera remplac. Si vous sauvez une image avec le nom + du fichier de backup, aucun fichier de backup ne sera cr (bien + videmment!) ;). + + - Curseur: Vous permet de choisir un curseur solide (sprite) ou + transparent. + + - Couleurs de sret: Remet les 4 couleurs par dfaut des menus si + vous effectuez une opration qui passe l'image en moins de quatre + couleurs dans l'diteur de palette. + + - Adjust brush pick (ajuster la prise de brosse): Cette option est + utilise lorsque vous capturez une brosse en mode Grille. Alors, les + pixels en bas et droite ne seront pas pris avec le rest de la + brosse. Cette option t faite car, si les gens rcuprent des + brosses en mode Grille, c'est principalement lorsqu'ils veulent + rcuprer des sprites. + Par exemple: si vous avez des sprites 16x16 sur votre page, vous + dfinirez une grille de 16x16. Mais le curseur se positionnera sur + des points tels que (0,0), (16,0), (16,16) etc... Et le problme est + que, de (0,0) (16,16), il y a 17 pixels! Mais si vous slectionnez + l'option adjust-brush-pick, les pixels indsirables seront ignors. + De plus, cette option ajuste la "poigne" de la brosse de faon ce + que la brosse concide toujours avec la grille, au lieu de placer + systmatiquement l'attache au centre de la brosse. + + - Sparer les couleurs: Dessiner un quadrillage autour des couleurs + de la barre d'outil. + + - Changer automatiquement de rsolution: Passe dans la meilleure + rsolution pour l'image charge. + + - Coordonnes: Choisissez si vous souhaitez afficher des coordonnes + relatives ou absolues lorsque vous utilisez des outils tels que les + cercles, les rectangles, etc... Par exemple, si vous dessinez un + cercle: si les coordonnes sont relatives, le rayon du cercle sera + affich, tandis qu'en coordonnes absolues coords, ce sont les + coordonnes du curseur qui seront affiches. + + - Reload (Recharger): Charge la configuration prcdemment sauve. + + - Auto-save (Sauvegarde automatique): Signifie que la configuration + sera automatiquement sauve quand vous quitterez le programme. + + - Save (Sauver): Sauve la configuration tout de suite. + + + Toutes les modifications prennent effet juste aprs avoir ferm le menu + des paramtres gnraux. + + + + 29 - Effacer l'image: + + + Clic gauche: + ============> + + Efface l'image avec la couleur numro 0. + + + Clic droit: + ============> + + Efface l'image avec la couleur de fond. + + + + 30 - Aide / Statistiques: + + + Clic gauche: + ============> + + Affiche une fentre d'information o vous trouverez quelques crdits, + de l'aide sur les diffrents effets, des greetings, des information sur + l'enregistrement, etc... + + + Clic droit: + ============> + + Affiche une fentre d'informations o vous trouverez diverses + informations sur le systme. + + Note: pour assurer le bon fonctionnement du programme, il est conseill + de disposer de plus de 128 Ko de libres. + + + + 31 - Oops (Dfaire/Refaire): + + + Clic gauche: + ============> + + Vous permet d'annuler la dernire modification sur l'image. + + + Clic droit: + ============> + + Vous permet de refaire la dernire modification annule sur l'image. + + + Le nombre maximum d'annulations (UNDO) que vous pouvez effectuer peut + tre dfini dans le menu des paramtres gnraux. + + Dfaire/Refaire une modification est impossible aprs un changement de + page, une chargement d'image ou la modification de la taille de l'image. + + + + 32 - Dtruire la page courante (Kill): + + + N'importe quel clic: + ====================> + + Supprime la page courante de la liste des pages "Undo". Cela vous + permet de librer un peu de mmoire si le besoin s'en fait sentir. Cela + permet notamment d'effacer de la mmoire la page de dmarrage aprs + avoir charg une image. Un message s'affichera lorsque vous aurez + supprim toutes les pages sauf la dernire. + + Note: Un autre moyen de librer de la mmoire est de rduire le nombre + de pages "Undo". Ou encore, si vous avez rcemment captur une + trs grosse brosse dont vous ne vous servez plus, vous pouvez en + prendre une plus petite. La mmoire alloue pas la grosse brosse + sera alors libre. + + + + 33 - Quitter le programme: + + + N'importe quel clic: + ====================> + + Vous permet de quitter GrafX2. S'il y a des modifications non sauves + dans la page courante ou de brouillon, une boite de confirmation vous + demandera si vous dsirez rellement quitter GrafX2, si vous voulez + sauver (sauvegarde automatique, pas de slecteur de fichier) ou si vous + voulez rester dans GrafX2. + + + + 34 - Menu de palette: + + + Clic gauche: + ============> + + Affiche un menu dans lequel les options suivantes sont disponibles: + + - Palette: Vous permet de choisir un bloc de couleurs diter. Si + vous cliquez avec le bouton droit de la souris, vous dfinirez une + nouvelle couleur de fond. + + - Jauges RGB: Vous permettent de modifier la slection courante. + + - "+" et "-": Vous permettent d'claircir ou d'assombrir la slection + courante. + + - Default (Palette par dfaut): Restaure la palette prdfinie de + GrafX2. + + - Gray (Gris): Transforme la slection courante en son quivalent en + niveaux de gris. + + - Negative (Ngatif): Transforme la slection courante en son + quivalent en vido inverse. + + - Invert (Invertion): Echange les couleurs de la slection courante de + faon ce que les premires couleurs deviennent les dernires. + + - X-Invert (Inverser de faon tendue): Fonctionne comme ci-dessus + mais modifie l'image de faon ce qu'elle semble inchange. + + - Swap (Echanger): Echange la slection courante avec un autre bloc de + couleurs. Cliquez sur le dbut du nouveau bloc de couleur. + + - X-Swap (Echanger de faon tendue): Fonctionne comme ci-dessus mais + modifie l'image de faon ce qu'elle semble inchange. Cela peut + tre utile si vous voulez rordonner votre palette. + + - Copy (Copier): Copie la slection courante vers un autre bloc de + couleurs. Cliquez sur le dbut du nouveau bloc de couleurs. + + - Spread (Dgrad): Calcule un dgrad entre deux couleurs. Si votre + slection n'est faite que d'une seule couleur, slectionnez la + deuxime couleur dans la palette. Sinon, les deux couleurs seront + les extrmits de la slection. + + - Used (Comptage): Indique le nombre de couleurs utilises dans + l'image. + + - Zap unused (Supprimer les couleurs inutilises): crase les couleurs + inutilises avec des copies de la slection courante. (La touche de + raccourci de ce bouton est ). + + - Reduce (Rduire): Vous permet de rduire la palette au nombre de + couleurs que vous dsirez (modifie l'image). + + - Undo (Dfaire): Vous permet d'annuler la dernire opration faite + sur la palette. Si la dernire opration a modifi l'image, cela + n'annulera pas les modifications de l'image: vous devrez cliquer sur + Cancel pour cela. + + + Si vous appuyez sur , le programme insrera au mieux les + quatre couleurs par dfaut du menu la place de couleurs peu ou pas + utilises. L'image ne paratra pas altre car les couleurs modifies + (dans le cas o elles taient utilises) seront remplaces par les plus + proches couleurs dans le reste de la palette. + Cette option se rvle fort utile lorsque vous passez la palette dans un + tat ou aucune couleur ne convient pour le menu (ex: "Zap unused" alors + que trs peu de couleurs sont utilises dans l'image; ou encore "Reduce" + avec un trs faible nombre de couleurs). + + Si vous appuyez sur la touche en dessous de ou <,> (QWERTY), + le menu disparatra et vous pourrez ainsi piocher aisment une couleur + de l'image. Appuyez sur Pour annuler. + + Si une seule couleur est slectionne (pas un bloc), les touches <[> + et <]> (<^> et <$> en AZERTY) peuvent tre utilises pour passer la + couleur principale prcdente ou suivante (couleur de fond si vous + appuyez sur en mme temps). + + Attention! Si vous appuyez sur Undo aprs une action qui modifie + l'image (X-Swap, X-Invert et Reduce colors), l'image ne sera pas + remappe comme elle tait juste avant cette action. Elle le sera + uniquement avec Cancel (Annuler). + + + Clic droit: + ============> + + Ouvre un menu permettant d'accder aux menus suivants: + + - Menu dans lequel on slectionne les couleurs qui ne doivent pas tre + employes pour le Smooth, le mode de transparence et le remappage. + + - Un menu dans lequel on peut dfinir des suites de couleurs. + *** Pas encore implment *** + + + + 35 - Dplacer la palette gauche / droite: + + + Clic gauche: + ============> + + Dplace la fentre de palette ( la droite du menu). + + + Clic droit: + ============> + + Idem, mais plus rapidement. + + + + 36 - Fentre de palette: + + + Clic gauche: + ============> + + Dfinit la couleur principale. + + + Clic droit: + ============> + + Dfinit la couleur de fond. + + + + 37 - Cacher le menu: + + + N'importe quel clic: + ====================> + + Vous permet de cacher le menu. Si vous faites cela, prenez soin de + regarder pralablement la touche presser pour rafficher le menu (la + touche par dfaut est ). + + + + +Let's talk about $$$, baby: + + + Veuillez vous rfrer la section "Register?" de l'aide interne de + GrafX2. + + Pour rsumer cette section, disons que GrafX2 est freeware. Mais vous + pouvez quand mme nous envoyer de l'argent, des dessins, ou simplement une + carte postale pour nous montrer que nous avons fait un programme qui vous + est utile. + + Nous attirons votre attention sur le fait que la version que vous avez + entre les mains est dj la version "complte" (la mme que la version + enregistre) aussi nous ne vous enverrons pas d'autre copie de GrafX2. Mais + si vous vous enregistrez pour une version, nous considererons que vous + n'avez pas vous enregistrer pour les suivantes. + + + + +Astuces de dessin: + + + Cette section parle des astuces qui permettent d'obtenir des effets + sympathiques, ou qui servent simplement dessiner plus vite. + Notez que, dans la plupart des cas, ces astuces ne permettent que de faire + une grosse partie du travail et qu'il vous faudra bien sr fignoler la + loupe si vous souhaitez faire un dessin digne de ce nom! ;) + De plus, si vous avez vous aussi des astuces sympa et que vous souhaitez + en faire profiter les autres, n'hsitez pas on nous les signaler. + + + Anti-aliasing: + + + Ce n'est pas un effet propos par GrafX2 mais une mthode de dessin. + Cela consiste placer des pixels de couleur moyennes dans les angles + forms par des pixels contrasts pour adoucir de faon esthtique leur + aspect. + A notre avis, c'est essential pour dessiner des images vraiment belles. + Une mthode facile mais fatigante (la meilleure mthode!) est de + commencer par ajouter 1 couleur moyenne puis d'antialiaser les nouvelles + couleurs "rcursivement" tant qu'il y a des couleurs intermdiaires dans + votre palette. + + + + + ۱ + + + ۲ + + + + Mode "Smear" combin avec les lignes concentriques: + + + En combinant cet effet et cet outil de dessin, vous pouvez arriver + "parpiller" une zone partir d'un point central. + Si vous n'tes pas en haute rsolution, il peut s'avrer utile d'en- + clencher galement le mode de Transparence (cf. section suivante). + + Une application possible est de dessiner des poils sur une peluche. Pour + cela, vous pouvez choisir un des pinceaux prdfinis qui ressemblent un + ensemble alatoire de points. Selon la densit de poils que vous souhaitez + donner votre peluche, vous pouvez choisir un pinceau contenant plus ou + moins de points. Placez ensuite le centre des lignes concentriques environ + au centre de la peluche, puis faites tourner la souris autour de la + peluche en maintenant le bouton de la souris enfonc. + Avec la mme mthode, mais en insistant plus longtemps, vous pouvez + donner un effet d'explosion sur un objet. + + Vous pouvez galement crer facilement et rapidement des rayons de + soleil avec cette mthode. Pour cela, aprs avoir plac la forme premire + du soleil sur le ciel, choisissez un pinceau en fonction de la taille des + rayons que vous voulez crer (mais un petit pinceau sera souvent + prfrable), et placez le centre des lignes au centre du soleil. Puis + tracez les rayons la longueur que vous voulez. Si vous n'avez pas pris + un trop gros pinceau, vous pourrez dans un premier temps tracer + rapidement une aurole autour du soleil en tournant rapidement autour et + en maintenant le bouton de la souris enfonc, et dans un deuxime temps + vous rajouterez des rayons plus importants avec prcision. + + + Mode "Smear" combin avec l'effet de Transparence: + + + Ces deux modes de dessin combins permettent d'taler des parties + d'image comme de la peinture fraiche. + Il est recommand d'utiliser la mthode de transparence qui consiste + interpoler avec une opacit d'environ 60% et le "Feedback" des effets + enclench. + + Tout comme dans la section prcdente, cela peut servir dessiner des + poils et notamment des cils si vous avez une palette adapte (c'est--dire + une palette contenant des dgrads de couleurs entre toutes les couleurs + sur lesquelles vous dessinerez pendant cette opration. + Pour dessiner des cils par exemple, aprs avoir dessin l'oeil et la + paupire, tracez un trait noir assez pais reprsentant la base des cils (c'est ce + noir que vous talerez sur la paupire). Puis, en mode smear+transparence, + dessinez des traits la main (avec un petit pinceau: 1, 2 ou 3 pixels de + large suivant que vous dessiniez un visage ou un oeil en gros plan) en + partant de la base des cils et en donnant leur forme. Vous verrez petit-- + petit votre barre noire s'effiler en forme de cils. + + On peut galement se servir de ces effets pour mlanger des couleurs + l'cran et donner ainsi un aspect de peinture. Par exemple, si l'on + souhaite raliser un fond comportant des formes abstraites composes de + mlanges de couleurs, on peut procder comme suit: + - Dfinir un palette comportant un dgrad entre les diffrentes teintes + que vous souhaitez utiliser. + - Dessiner trs vaguement l'aide d'un gros pinceau les diffrentes zones + de couleurs (en mode normal). + - Avec un plus petit pinceau, et l'aide du spray, appliquer ces mmes + teintes mais en plus clair ou plus fonc sur les zones prcdemment + dfinies. + - Toujours avec le mme pinceau en spray, mais cette fois-ci en mode smear + (pas forcment avec transparence... mais pourquoi pas?), mlangez un peu + toutes les couleurs l'cran pour obtenir une "bouillie multicolore" tout + en conservant vaguement les diffrentes zones de couleurs. + - Enfin, en mode Smear+Transparence, avec un pinceau moyen arrondi, + dessinez la main en faisant des tourbillons, des vagues, etc... en + conservant a peu prs le mme mouvement pour viter les cassures. Ceci + a pour but d'liminer la pixellisation opre par le spray et de donner + l'aspect final de peinture mlange. + - Maintenant, si c'est moche, c'est soit que j'explique mal, soit que vous + n'avez pas de talent! :p + + + Spray combin au mode shade: + + + Si vous utilisez souvent le mode Shade, et que a vous fatigue de + cliquer plein de fois sur une couleur pour atteindre celle que vous + voulez, vous pouvez definir un spray avec "Size"=1, "Mono-flow"=1, et + "Delay"=2 (ou plus, selon vos rflexes). Et vous n'aurez alors plus qu' + cliquer quelques centimes de seconde pour modifier une couleur. + + Avec un diamtre plus large, cela permet de rajouter de la granularit + une texture, car placer des petits pixels plus foncs ou plus clairs + permet de crer des asprits. Diffrentes textures appropries cet + effet sont: du sable, de la pierre, etc... + Il faut bien sr que vous ayez un dgrad adapt la couleur de la + texture. + + Vous pouvez galement raliser des textures - \ + plus labores en employant un pinceau en forme \ \ + de petite courbe ou ligne comme "tentent" de le ` \ + montrer les figures ci-contre. ;) | \ + Vous pourrez ainsi raliser des textures de paille, + de cheveux, de pierres stries ou de marbre (le spray tant + toutefois moins recommand que le dessin la main pour ce dernier). + + + Mode shade pour remplacer les couleurs d'un dgrad par un autre: + + + Si vous avec dessin quelque chose avec des couleurs appartenant un + dgrad et que vous souhaitiez remplacer toutes ces couleurs par celles + d'un autre dgrad (du mme nombre de couleurs), procdez comme suit: + - Dfinissez dans le menu du mode shade les 2 dgrads en question sans + les sparer par une case vide. + - Passez le shade en mode "no saturation" + - Dfinissez le pas du shade avec la taille des dgrads (ex: entrez 16 si + vos dgrads comportent chacun 16 couleurs). + - Et voil, vous n'avez plus qu' dessiner par dessus la zone qui doit + changer de teinte (avec le bouton gauche de la souris si vous avez plac + le dgrad remplacer en premier dans la table de shade, ou inversement). + + + Sphres combines avec le mode de transparence additive: + + + En partant d'un fond sombre (et si possible de couleur unie), tracez des + sphres qui se chevauchent avec leur point d'clairage au centre. Vous + obtiendrez rapidement un effet de "blobs". + + + Comment dessiner une goutte: + + + Voici une mthode rapide et efficace pour dessiner des gouttes. + Dessinez simplement des pixels trs brillants sur le ct de la goutte + d'o vient la lumire, et des pixels moins brillants sur le ct oppos. + Enfin, dessinez les ombres suivant la position de la lumire. + + Voici des exemples avec une lumire + venant du coin haut-gauche. + (il est prfrable de les regarder ۰ + en mode texte 80x50) ۰ + ۲ + Vous pouvez penser que la plus + petite goutte ne ressemble pas a ۱ + une goutte, mais dessinez-la en mode + graphique et vous verrez qu'elle a + bien l'air d'une goutte. + + Si vous n'avez pas confiance, dites-vous que c'est en observant les graphs + de Lazur que j'ai trouv cette mthode. Et d'une faon gnrale, il est + toujours bon de regarder le travail des artistes confirms pour apprendre + de nouvelles techniques. + + + + +Problmes/Astuces gnrales/Questions frquentes (FAQ): + + + * Problmes de carte vido: + + - Les modes VESA sont rendus inaccessibles par Windows NT. Et il parait + que a va tre pareil sous Windows 2000 (on n'a pas encore essay, mais on + n'est pas presss!). + + - Si votre carte vido n'est pas compatible VESA matriellement, vous + devriez essayer de lancer un driver VESA tel que Univesa ou Univbe. + + - Si votre carte est compatible VESA mais n'affiche pas correctement le + contenu de l'cran dans les rsolutions VESA, c'est probablement parce + qu'elle ne rpond pas tous les critres que nous attendons. L'explica- + tion est que, pour une plus grande efficacit, nous avons d ngliger + certaines spcificits de quelques cartes vidos. Cependant, nous tentons + chaque nouvelle version d'augmenter la compatibilit avec toutes les + formes du standard VESA. + + - Si vous possdez une carte vido ATI Mach 64 (e.g. ATI Xpert), vous + devriez utiliser le programme rsident m64vbe fourni avec la carte pour + supporter compltement nos modes XVESA en tapant: "m64vbe vga". + + + * Problmes de mmoire: + + - Depuis la version 94.666%, nous utilisons le dos-extender EOS Copyright + (c) 1996 Eclipse, au lieu du traditionnel DOS4GW. La raison en est qu'il + est beaucoup plus petit en place disque (un zip plus petit, a devrait + faire plaisir vos factures de tlphone) et en mmoire (vous pouvez + donc lancer GrafX2 avec plus de gestionnaires utilisant la mmoire + conventionnelle). De plus, ce dos-extender est intgr l'xcutable de + GrafX2, ce qui diminue galement le nombre de fichiers (votre FAT vous + en sera reconnaissante). + + L'inconvnient est que ce dos-extender ne gre pas de cache disque. + Ainsi, si vous ne disposez pas d'au moins 4 Mgaoctets de RAM, vous + devrez utiliser le fichier batch GFX2_MEM.BAT . + + Il est noter que: + - vous devrez configurer ce fichier selon l'emplacement de certains + fichiers dans l'arborescence de votre (vos) disque(s) dur(s) + - vous devrez avoir quelque part dans l'arborescence de votre (vos) + disque(s) dur(s) le fichier DOS4GW.EXE . + - vous devrez disposer d'au moins 16 Mgaoctets de libre sur votre + disque dur courant. + + Si vous avez rencontr des problmes dans l'utilisation de GrafX2 (avec + au moins 4 Mgaoctets de mmoire) qui se seraient rsolus en utilisant + GFX2_MEM, nous vous serions reconnaissant de nous en faire part. + + EOS est un dos-extender shareware, accompagn de bibliothques trs + intressantes pour la musique, le graphisme, ... pour des applications + Watcom, Tasm ou Masm. Si vous dsirez avoir plus d'informations sur ses + fonctionnalits ou les bibliothques qui l'accompagne, n'hsitez pas + nous contacter pour que nous vous mettions en relation avec ses auteurs. + + + * Problmes de carte son: + + Q: Aucun son ne sort de ma Ultra-maxi-sound-blaster-galaxy-64-3D-pnp, + alors que puis-je faire ? + R: Et bien... Vous devez comprendre que ce programme n'est ni un + soundtracker ni un player de musique :) ... Aussi, si vous voulez de la + musique, vous devrez soit jouer des modules avec un bon player qui peut + tourner en arrire-plan (avec une session DOS), soit allumer votre + chaine Hi-Fi. + + + * Divers: + + - Si vous avez foutu en l'air le fichier GFX2.CFG et que GrafX2 l'utilise + tel quel, avec un comportement anormal, n'hsitez pas effacer GFX2.CFG + et relancer GFXCFG pour en crer un nouveau, et correct. En effet les + seuls tests de validit que nous faisons sur le fichier de configuration + sont sa taille et son numro de version. + + - Il se peut que vous ayez rcupr une version de GrafX2 dj configure + par un ami qui aurait pu utiliser des touches "Windows 95" alors que + vous ne disposez pas vous-mme d'un clavier adapt. Dans ce cas, il vous + faudra reconfigurer ces combinaisons l'aide de GFXCFG. + + + * Questions frquemment poses: + + Q: Comment puis-je choisir les dimensions de l'image ? + R: Nous pensions qu'il tait vident que vous deviez cliquer dans les + zones o les dimensions sont affiches, dans le menu de rsolution + (Width & Height) mais beaucoup de personnes nous ont pos cette + question (?!). Alors, pour rsumer, partout o vous verrez une valeur + ou un texte affich en noir dans une sorte de zone incruste, cela + signifie qu'en cliquant dessus vous pourrez modifier cette valeur. + De plus, si vous voulez que les dimensions de l'image soient celles + de l'cran, il vous suffit de cliquer sur la rsolution dans la liste + avec le bouton droit de la souris. + + Q: O puis-je obtenir la dernire version de GrafX2 ? + R: Le seul endroit o vous puissiez tre sr de trouver la toute dernire + version est sur notre site web: + http://www-msi.ensil.unilim.fr/~maritaud/sunset + Toutefois, il n'est pas impossible que GrafX2 se retrouve galement sur + des sites FTP ddis la "demo-scene" (e.g. ftp://ftp.scene.org). + + Q: Comment puis-je passer la brosse en monochrome, et comment puis-je la + rcuprer dans son tat normal? + R: Vous pouvez le faire ( supposer que vous n'avez pas chang les touches + par dfaut) avec les touches + pour rendre la brosse + monochrome, et + pour rcuprer la brosse en couleur. + + Q: Pourquoi est-ce que la barre d'outil est en bas de l'cran et non pas + sur le ct droit comme dans Deluxe Paint (Copyright Electronic Arts) ? + R: Eh bien... GrafX2 N'EST PAS Deluxe Paint! Nous savons que vous tes + habitus Deluxe Paint mais vous allez devoir vous habituer GrafX2! + ;) Si vous ne supportez vraiment pas d'utiliser GrafX2 comme cela, vous + devrez attendre GrafX3 mais nous ne le raliserons certainement pas + avant l'an 2013! En fait, la principale raison pour laquelle nous avons + conu la barre d'outil avec un aspect aussi basique est que cela + facilitait (et acclrait) l'affichage de l'cran, en indiquant aux + routines o s'arrter (l o commence la barre d'outil). + De plus, l'un des meilleurs logiciels de dessin sur Amiga (Brilliance) + affiche galement la barre du menu en bas de l'cran. + + Q: Pourquoi est-ce que la partie de l'image cache par le menu n'est pas + remplie lorsque j'utilise l'outil "Flood-fill"? + R: Pour la simple et "assez" bonne raison qu'il est prfrable que l'uti- + lisateur contrle parfaitement ce qu'il dessine. Ainsi il ne pourra pas + remarquer trop tard qu'il a saccag une partie de son dessin. Il en est + de mme pour tous les autres outils. Et puis pour une moins bonne + raison qui est que c'tait plus pratique pour nous. ;) + + Q: Y'a-t-il un moyen pour lancer le programme dans une autre rsolution + que 320x200 ? + R: Oui, il suffit de taper GFX2 sur la ligne de commande + du DOS. Pour obtenir la liste de tous les modes vido, tapez: GFX2 /?. + + Q: Est-ce normal que certains boutons ne marchent pas (par exemple: le + bouton Texte) ? + R: Oui, c'est que nous n'avons pas encore eu le temps de les faire (je + vous rappelle que GrafX2 en est encore au stade des Beta versions). + Voici cependant la liste des boutons qui ne repondent pas dans GrafX2: + - Rectangles dgrads (Grad. rectangles) + - Texte + - Effets sur l'image + - et le bouton suivant dans le menu "Brush effects": Torsion (Distort) + + Q: Allez-vous sortir une version Windows? + R: GrafX2 perdrait son me en tant adapt un systme fentr ou un + systme qui ne supporte pas tous ses modes vidos. Et de toutes faons, + il peut se lancer partir de Windows 9x (on ne sait pas pour Windows + 2000 mais on s'en fiche). Alors c'est bien comme a. La seule chose + intressante que pourrait apporter Windows est le presse-papier. + + Q: Allez-vous sortir une version Linux? + R: Bien que ce soit peu prs le mme problme qu'avec la version + Windows, Linux manque de programmes comme GrafX2; donc, mme une + version limite serait intressante pour cet OS. Par consquent, nous + aimerions sortir une version Linux. Mais nous n'avons aucune exprience + de programmation Linux et notre code est compltement indechiffrable + pour les autres. Alors vous devrez attendre... + + Q: Comment puis-je vous contacter ? + R: En fait, ce n'est pas exactement cette question qu'on nous pose puisque + ces gens arrivent nous contacter ;) mais... + + * Poste: + GUILLAUME DORME (Robinson) KARL MARITAUD (X-Man) + 15, rue de l'observatoire 10, rue de la Brasserie + 87000 LIMOGES (FRANCE) 87000 LIMOGES (FRANCE) + + * E-mail: + dorme@msi.unilim.fr maritaud@ensil.unilim.fr + + N'hsitez pas nous contacter; on adore a! :) + Nous essaierons de rpondre tous les e-mails (s'il ncessitent une + rponse), et certains courriers (Bah oui! On ne va pas se ruiner en + timbres juste pour vous dire "merci d'avoir crit!" :)). diff --git a/dpmi.asm b/dpmi.asm new file mode 100644 index 00000000..a09a5659 --- /dev/null +++ b/dpmi.asm @@ -0,0 +1,472 @@ +.386P +.MODEL FLAT + + + +_TEXT Segment dword public 'code' + Assume cs:_TEXT, ds:_DATA + + +; -- Fonctions DPMI -- +public Physical_address_mapping +public Free_physical_address_mapping +public Lock_linear_region +public Unlock_linear_region +public Allocate_ldt_descriptor +public Free_ldt_descriptor +public Set_segment_base_address +public Set_segment_limit +public Set_descriptor_access_rights +public Get_segment_base_address + + + + + +Physical_address_mapping proc near + + push ebp + mov ebp,esp + + arg Physical_address:dword,Physical_size:dword,Linear_address_pointer:dword + + push ebx + push esi + push edi + + ; On met dans BX:CX l'adresse physique mapper + mov eax,Physical_address + mov cx,ax + shr eax,16 + mov bx,ax + + ; On met dans SI:DI la taille de l'adresse physique mapper + mov eax,Physical_size + mov di,ax + shr eax,16 + mov si,ax + + ; On appelle le service DPMI de mappage d'adresse physique + mov ax,0800h + int 31h + + jc Physical_address_mapping_Erreur + + ; On sauve l'adresse linaire l'adresse donne + mov eax,Linear_address_pointer + mov [eax+00h],cx + mov [eax+02h],bx + ; Et on renvoie un code d'erreur nul + xor ax,ax + + Physical_address_mapping_Erreur: + + pop edi + pop esi + pop ebx + + mov esp,ebp + pop ebp + + ret + +Physical_address_mapping endp + + + + + +Free_physical_address_mapping proc near + + push ebp + mov ebp,esp + + arg Linear_address:dword + + push ebx + + ; On met dans BX:CX l'adresse linaire dmapper + mov eax,Linear_address + mov cx,ax + shr eax,16 + mov bx,ax + + ; On appel le service DPMI de libration d'un mappage d'adresse physique + mov ax,0801h + int 31h + + jc Free_physical_address_mapping_Erreur + + ; On renvoie un code d'erreur nul + xor ax,ax + + Free_physical_address_mapping_Erreur: + + pop ebx + + mov esp,ebp + pop ebp + + ret + +Free_physical_address_mapping endp + + + + + +Lock_linear_region proc near + + push ebp + mov ebp,esp + + arg Linear_address:dword,Linear_size:dword + + push ebx + push esi + push edi + + ; On met dans BX:CX l'adresse linaire locker + mov eax,Linear_address + mov cx,ax + shr eax,16 + mov bx,ax + + ; On met dans SI:DI la taille de l'adresse linaire locker + mov eax,Linear_size + mov di,ax + shr eax,16 + mov si,ax + + ; On appel le service DPMI de lockage d'adresse linaire + mov ax,0600h + int 31h + + jc Lock_linear_region_Erreur + + ; On renvoie un code d'erreur nul + xor ax,ax + + Lock_linear_region_Erreur: + + pop edi + pop esi + pop ebx + + mov esp,ebp + pop ebp + + ret + +Lock_linear_region endp + + + + + + +Unlock_linear_region proc near + + push ebp + mov ebp,esp + + arg Linear_address:dword,Linear_size:dword + + push ebx + push esi + push edi + + ; On met dans BX:CX l'adresse linaire dlocker + mov eax,Linear_address + mov cx,ax + shr eax,16 + mov bx,ax + + ; On met dans SI:DI la taille de l'adresse linaire dlocker + mov eax,Linear_size + mov di,ax + shr eax,16 + mov si,ax + + ; On appel le service DPMI de dlockage d'adresse linaire + mov ax,0601h + int 31h + + jc Unlock_linear_region_Erreur + + ; On renvoie un code d'erreur nul + xor ax,ax + + Unlock_linear_region_Erreur: + + pop edi + pop esi + pop ebx + + mov esp,ebp + pop ebp + + ret + +Unlock_linear_region endp + + + + + + + +Allocate_ldt_descriptor proc near + + push ebp + mov ebp,esp + + arg Nombre_de_descripteurs:word,Base_selector_pointer:dword + + push ebx + push esi + push edi + + ; On met dans CX le nombre de descripteurs ldt allouer + mov cx,Nombre_de_descripteurs + + ; On appel le service DPMI d'allocation de descripteurs ldt + mov ax,0000h + int 31h + + jc Allocate_ldt_descriptor_Erreur + + ; On sauve la valeur du slecteur de base + mov ebx,Base_selector_pointer + mov [ebx],ax + ; Et on renvoie un code d'erreur nul + xor ax,ax + + Allocate_ldt_descriptor_Erreur: + + pop edi + pop esi + pop ebx + + mov esp,ebp + pop ebp + + ret + +Allocate_ldt_descriptor endp + + + + + + +Free_ldt_descriptor proc near + + push ebp + mov ebp,esp + + arg Selector:word + + push ebx + push esi + push edi + + ; On met dans BX le descripteur ldt librer + mov bx,Selector + + ; On appel le service DPMI de libration de descripteur ldt + mov ax,0001h + int 31h + + jc Free_ldt_descriptor_Erreur + + ; On renvoie un code d'erreur nul + xor ax,ax + + Free_ldt_descriptor_Erreur: + + pop edi + pop esi + pop ebx + + mov esp,ebp + pop ebp + + ret + +Free_ldt_descriptor endp + + + + + + +Set_segment_base_address proc near + + push ebp + mov ebp,esp + + arg Selector:word,Linear_base_address:dword + + push ebx + + ; On met dans CX:DX l'adresse de base linaire assigner au segment + mov eax,Linear_base_address + mov dx,ax + shr eax,16 + mov cx,ax + + ; On met dans BX le slecteur auquel il faut assigner l'adresse de base + mov bx,Selector + + ; On appel le service DPMI d'assignation d'adresse de base un segment + mov ax,0007h + int 31h + + jc Set_segment_base_address_Erreur + + ; On renvoie un code d'erreur nul + xor ax,ax + + Set_segment_base_address_Erreur: + + pop ebx + + mov esp,ebp + pop ebp + + ret + +Set_segment_base_address endp + + + + + + +Set_segment_limit proc near + + push ebp + mov ebp,esp + + arg Selector:word,Segment_limit:dword + + push ebx + + ; On met dans CX:DX la limite (taille) assigner au segment + mov eax,Segment_limit + mov dx,ax + shr eax,16 + mov cx,ax + + ; On met dans BX le slecteur auquel il faut assigner une limite + mov bx,Selector + + ; On appel le service DPMI d'assignation de limite un segment + mov ax,0008h + int 31h + + jc Set_segment_limit_Erreur + + ; On renvoie un code d'erreur nul + xor ax,ax + + Set_segment_limit_Erreur: + + pop ebx + + mov esp,ebp + pop ebp + + ret + +Set_segment_limit endp + + + + + +Set_descriptor_access_rights proc near + + push ebp + mov ebp,esp + + arg Selector:word,Rights:word + + push ebx + + ; On met dans CX les droits assigner au segment + mov cx,Rights + + ; On met dans BX le slecteur auquel il faut assigner des droits + mov bx,Selector + + ; On appel le service DPMI d'assignation de droits un segment + mov ax,0009h + int 31h + + jc Set_descriptor_access_rights_Erreur + + ; On renvoie un code d'erreur nul + xor ax,ax + + Set_descriptor_access_rights_Erreur: + + pop ebx + + mov esp,ebp + pop ebp + + ret + + + +Set_descriptor_access_rights endp + + + + + + +Get_segment_base_address proc near + + push ebp + mov ebp,esp + + arg Selector:word,Linear_base_address_pointer:dword + + push ebx + + ; On met dans BX le slecteur dont il faut lire l'adresse de base + mov bx,Selector + + ; On appel le service DPMI de lecture d'adresse de base d'un segment + mov ax,0006h + int 31h + + jc Get_segment_base_address_Erreur + + ; On sauve l'adresse de base linaire du segment + mov eax,Linear_base_address_pointer + mov [eax+00h],dx + mov [eax+02h],cx + ; On renvoie un code d'erreur nul + xor ax,ax + + Get_segment_base_address_Erreur: + + pop ebx + + mov esp,ebp + pop ebp + + ret + +Get_segment_base_address endp + + + + + +_TEXT ENDS +END diff --git a/dpmi.h b/dpmi.h new file mode 100644 index 00000000..7e525d61 --- /dev/null +++ b/dpmi.h @@ -0,0 +1,20 @@ + +#ifndef _DPMI_H_ +#define _DPMI_H_ + + + + word Physical_address_mapping(byte * Physical_address,dword Size,byte * * Linear_address_pointer); + word Free_physical_address_mapping(byte * Linear_address); + word Lock_linear_region(byte * Linear_address,dword Size); + word Unlock_linear_region(byte * Linear_address,dword Size); + word Allocate_ldt_descriptor(word Nombre_de_descripteurs,word * Base_selector_pointer); + word Free_ldt_descriptor(word Selector); + word Set_segment_base_address(word Selector,byte * Linear_base_address); + word Set_segment_limit(word Selector,dword Segment_limit); + word Set_descriptor_access_rights(word Selector,word Rights); + word Get_segment_base_address(word Selector,byte * * Linear_base_address_pointer); + + + +#endif diff --git a/file_id.diz b/file_id.diz new file mode 100644 index 00000000..c0437ca5 --- /dev/null +++ b/file_id.diz @@ -0,0 +1,21 @@ +Ŀ + Sunset-Design presents 96.5% + + + + .00 + + + GrafX 2.00 Beta 96.5% + + The ultimate multi-resolution ۲ + bitmap paint program for PC ۲ + + features: + - all the useful tools and much more + - 60 resolutions! (MCGA, Mode-X, VESA) + (including Amiga resolutions!) + - GIF,LBM,BMP,PCX,PKM,... file support + + Try it! You'll love it! + diff --git a/files.c b/files.c new file mode 100644 index 00000000..4542c406 --- /dev/null +++ b/files.c @@ -0,0 +1,539 @@ +#include "const.h" +#include "struct.h" +#include "global.h" +#include "graph.h" +#include "divers.h" +#include +#include +#include + +#include +#include +#include +#include +#include +#include + + +#include "linux.h" + +#define COULEUR_FICHIER_NORMAL CM_Clair // Couleur du texte pour une ligne de fichier non slectionn +#define COULEUR_REPERTOIRE_NORMAL CM_Fonce // Couleur du texte pour une ligne de rpertoire non slectionn +#define COULEUR_FOND_NORMAL CM_Noir // Couleur du fond pour une ligne non slectionne +#define COULEUR_FICHIER_SELECT CM_Blanc // Couleur du texte pour une ligne de fichier slectionne +#define COULEUR_REPERTOIRE_SELECT CM_Clair // Couleur du texte pour une ligne de reprtoire slectionne +#define COULEUR_FOND_SELECT CM_Fonce // Couleur du fond pour une ligne slectionne + + +int Determiner_repertoire_courant(void) +// Modifie Principal_Repertoire_courant en y mettant sa nouvelle valeur (avec le nom du +// disque) +// +// Renvoie 1 s'il y a et une erreur d'accs +{ + return (getcwd(Principal_Repertoire_courant,256)==NULL); +} + + +int Repertoire_existe(char * Repertoire) +// Dtermine si un rpertoire pass en paramtre existe ou non dans le +// rpertoire courant. +{ + DIR* Enreg; // Structure de lecture des lments + + if (strcmp(Repertoire,"..")==0) + return 1; + else + { + // On va chercher si le rpertoire existe l'aide d'un Opendir. S'il + // renvoie NULL c'est que le rpertoire n'est pas accessible... + + Enreg=opendir(Repertoire); + if (Enreg==NULL) + return 0; + else + { + closedir(Enreg); + return 1; + } + } +} + + +int Fichier_existe(char * Fichier) +// Dtermine si un fichier pass en paramtre existe ou non dans le +// rpertoire courant. +{ + struct stat* buf; + int Resultat; + + Resultat=stat(Fichier,buf); + if (Resultat!=0) + return(errno!=ENOENT); + else + return 1; + +} + + + +// Conventions: +// +// * Le fileselect modifie le rpertoire courant. Ceci permet de n'avoir +// qu'un findfirst dans le rpertoire courant faire: + + +// -- Dstruction de la liste chane --------------------------------------- +void Detruire_liste_du_fileselect(void) +// Cette procdure dtruit la chaine des fichiers. Elle doit tre appele +// avant de rappeler la fonction Lire_liste_des_fichiers, ainsi qu'en fin de +// programme. +{ + // Pointeur temporaire de destruction + struct Element_de_liste_de_fileselect * Element_temporaire; + + while (Liste_du_fileselect!=NULL) + { + // On mmorise l'adresse du premier lment de la liste + Element_temporaire =Liste_du_fileselect; + // On fait avancer la tte de la liste + Liste_du_fileselect=Liste_du_fileselect->Suivant; + // Et on efface l'ancien premier lment de la liste + free(Element_temporaire); + } +} + + +// -- Formatage graphique des noms de fichier / rpertoire ------------------ +char * Nom_formate(char * Nom) +{ + static char Resultat[13]; + int Curseur; + int Autre_curseur; + + if (strcmp(Nom,"..")==0) + { + strcpy(Resultat,".. "); + } + else + { + strcpy(Resultat," . "); + // On commence par recopier la partie prcdent le point: + for (Curseur=0;( (Nom[Curseur]!='.') && (Nom[Curseur]!='\0') );Curseur++) + Resultat[Curseur]=Nom[Curseur]; + + // Ensuite on recopie la partie qui suit le point (si ncessaire): + if (Nom[Curseur]) + { + for (Curseur++,Autre_curseur=9;Nom[Curseur]!='\0';Curseur++,Autre_curseur++) + Resultat[Autre_curseur]=Nom[Curseur]; + } + } + return Resultat; +} + + +// -- Rajouter la liste des lments de la liste un lment --------------- +void Ajouter_element_a_la_liste(struct dirent* Enreg) +// Cette procdure ajoute la liste chaine un fichier pass en argument. +{ + // Pointeur temporaire d'insertion + struct Element_de_liste_de_fileselect * Element_temporaire; + + // On alloue de la place pour un nouvel lment + Element_temporaire=(struct Element_de_liste_de_fileselect *)malloc(sizeof(struct Element_de_liste_de_fileselect)); + + // On met jour le nouvel emplacement: + strcpy(Element_temporaire->Nom,Nom_formate(Enreg->d_name)); + Element_temporaire->Type =(Enreg->d_type == DT_DIR); + + Element_temporaire->Suivant =Liste_du_fileselect; + Element_temporaire->Precedent=NULL; + + if (Liste_du_fileselect!=NULL) + Liste_du_fileselect->Precedent=Element_temporaire; + Liste_du_fileselect=Element_temporaire; +} + + +// -- Lecture d'une liste de fichiers --------------------------------------- +void Lire_liste_des_fichiers(byte Format_demande) +// Cette procdure charge dans la liste chaine les fichiers dont l'extension +// correspond au format demand. +{ + int Attribut; // Attribut des fichiers/rpertoires lire + DIR* Repertoire_Courant; //Rpertoire courant + struct dirent* Enreg; // Structure de lecture des lments + char Filtre[6]="*."; // Place pour crire "*.XXX" et un '\0' + + char Chaine[20]; + + // Tout d'abord, on dduit du format demand un filtre utiliser: + if (Format_demande) // Format (extension) spcifique + strcat(Filtre,Format_Extension[Format_demande-1]); + else // *.* + strcat(Filtre,"*"); + + + // Ensuite, on vide la liste actuelle: + Detruire_liste_du_fileselect(); + // Aprs effacement, il ne reste ni fichier ni rpertoire dans la liste + Liste_Nb_fichiers=0; + Liste_Nb_repertoires=0; + + // On lit tous les rpertoires: + + Repertoire_Courant=opendir(getcwd(NULL,0)); +/* +Ceci est revoir... pas tout fait gr pareil sous linux... + Attribut=(_A_NORMAL|_A_SUBDIR|//_A_RDONLY|_A_ARCH| + (_A_HIDDEN & Config.Lire_les_repertoires_caches)| + (_A_SYSTEM & Config.Lire_les_repertoires_systemes)); +*/ + Enreg=readdir(Repertoire_Courant); + while (Enreg) + { + // Si l'lment n'est pas le rpertoire courant + if ( (strcmp(Enreg->d_name,".")!=0) && + // et que l'lment trouv est rellement un rpertoire + (Enreg->d_type == DT_DIR) ) + { + // On rajoute le rpertore la liste + Ajouter_element_a_la_liste(Enreg); + Liste_Nb_repertoires++; + } + // On cherche l'lment suivant + Enreg=readdir(Repertoire_Courant); + } + + // Enfin, on lit les fichiers du format demand: + +/* +Ici aussi, revoir... + Attribut=(_A_NORMAL|_A_SYSTEM|//_A_RDONLY|_A_ARCH| + (_A_HIDDEN & Config.Lire_les_fichiers_caches)); +*/ + + rewinddir(Repertoire_Courant); + Enreg=readdir(Repertoire_Courant); + while (Enreg) + { + if (Enreg->d_type==DT_REG) //Il s'agit bien d'un fichier + { + // On rajoute le fichier la liste + Ajouter_element_a_la_liste(Enreg); + Liste_Nb_fichiers++; + } + // On cherche l'lment suivant + Enreg=readdir(Repertoire_Courant); + } + + closedir(Repertoire_Courant); + + Liste_Nb_elements=Liste_Nb_repertoires+Liste_Nb_fichiers; +} + + +// -- Tri de la liste des fichiers et rpertoires --------------------------- +void Trier_la_liste_des_fichiers(void) +// Tri la liste chaine existante dans l'ordre suivant: +// +// * Les rpertoires d'abord, dans l'ordre alphabtique de leur nom +// * Les fichiers ensuite, dans l'ordre alphabtique de leur nom +{ + byte La_liste_est_triee; // Boolen "La liste est trie" + byte Inversion; // Boolen "Il faut inverser les lments" + struct Element_de_liste_de_fileselect * Element_precedent; + struct Element_de_liste_de_fileselect * Element_courant; + struct Element_de_liste_de_fileselect * Element_suivant; + struct Element_de_liste_de_fileselect * Element_suivant_le_suivant; + + // Avant de trier quoi que ce soit, on vrifie qu'il y ait suffisamment + // d'lments pour qu'il soit possibles qu'ils soient en dsordre: + if (Liste_Nb_elements>1) + { + do + { + // Par dfaut, on considre que la liste est trie + La_liste_est_triee=1; + + Element_courant=Liste_du_fileselect; + Element_suivant=Element_courant->Suivant; + + while ( (Element_courant!=NULL) && (Element_suivant!=NULL) ) + { + // On commence par supposer qu'il n'y pas pas besoin d'inversion + Inversion=0; + + // Ensuite, on vrifie si les deux lments sont bien dans l'ordre ou + // non: + + // Si l'lment courant est un fichier est que le suivant est + // un rpertoire -> Inversion + if ( (Element_courant->Type==0) && (Element_suivant->Type==1) ) + Inversion=1; + // Si les deux lments sont de mme type et que le nom du suivant + // est plus petit que celui du courant -> Inversion + else if ( (Element_courant->Type==Element_suivant->Type) && + (strcmp(Element_courant->Nom,Element_suivant->Nom)>0) ) + Inversion=1; + + + if (Inversion) + { + // Si les deux lments ncessitent d'tre invers: + + // On les inverses: + + // On note avant tout les lments qui encapsulent nos deux amis + Element_precedent =Element_courant->Precedent; + Element_suivant_le_suivant=Element_suivant->Suivant; + + // On permute le chanage des deux lments entree eux + Element_courant->Suivant =Element_suivant_le_suivant; + Element_courant->Precedent=Element_suivant; + Element_suivant->Suivant =Element_courant; + Element_suivant->Precedent=Element_precedent; + + // On tente un chanage des lments encapsulant les compres: + if (Element_precedent!=NULL) + Element_precedent->Suivant=Element_suivant; + if (Element_suivant_le_suivant!=NULL) + Element_suivant_le_suivant->Precedent=Element_courant; + + // On fait bien attention modifier la tte de liste en cas de besoin + if (Element_courant==Liste_du_fileselect) + Liste_du_fileselect=Element_suivant; + + // Ensuite, on se prpare tudier les lments prcdents: + Element_courant=Element_precedent; + + // Et on constate que la liste n'tait pas encore gnialement trie + La_liste_est_triee=0; + } + else + { + // Si les deux lments sont dans l'ordre: + + // On passe aux suivants + Element_courant=Element_courant->Suivant; + Element_suivant=Element_suivant->Suivant; + } + } + } + while (!La_liste_est_triee); + } +} + + +// -- Affichage des lments de la liste de fichier / rpertoire ------------ +void Afficher_la_liste_des_fichiers(short Decalage_premier,short Decalage_select) +// +// Decalage_premier = Dcalage entre le premier fichier visible dans le +// slecteur et le premier fichier de la liste +// +// Decalage_select = Dcalage entre le premier fichier visible dans le +// slecteur et le fichier slectionn dans la liste +// +{ + struct Element_de_liste_de_fileselect * Element_courant; + byte Indice; // Indice du fichier qu'on affiche (0 -> 9) + byte Couleur_texte; + byte Couleur_fond; + + + // On vrifie s'il y a au moins 1 fichier dans la liste: + if (Liste_Nb_elements>0) + { + // On commence par chercher pointer sur le premier fichier visible: + Element_courant=Liste_du_fileselect; + for (;Decalage_premier>0;Decalage_premier--) + Element_courant=Element_courant->Suivant; + + // Pour chacun des 10 lments inscriptibles l'cran + for (Indice=0;Indice<10;Indice++) + { + // S'il est slectionn: + if (!Decalage_select) + { + // Si c'est un fichier + if (Element_courant->Type==0) + Couleur_texte=COULEUR_FICHIER_SELECT; + else + Couleur_texte=COULEUR_REPERTOIRE_SELECT; + + Couleur_fond=COULEUR_FOND_SELECT; + } + else + { + // Si c'est un fichier + if (Element_courant->Type==0) + Couleur_texte=COULEUR_FICHIER_NORMAL; + else + Couleur_texte=COULEUR_REPERTOIRE_NORMAL; + + Couleur_fond=COULEUR_FOND_NORMAL; + } + + // On affiche l'lment + Print_dans_fenetre(9,90+(Indice<<3),Element_courant->Nom,Couleur_texte,Couleur_fond); + + // On passe la ligne suivante + Decalage_select--; + Element_courant=Element_courant->Suivant; + if (!Element_courant) + break; + } // Fin de la boucle d'affichage + + } // Fin du test d'existence de fichiers +} + + +// -- Rcuprer le libell d'un lment de la liste ------------------------- +void Determiner_element_de_la_liste(short Decalage_premier,short Decalage_select,char * Libelle) +// +// Decalage_premier = Dcalage entre le premier fichier visible dans le +// slecteur et le premier fichier de la liste +// +// Decalage_select = Dcalage entre le premier fichier visible dans le +// slecteur et le fichier rcuprer +// +// Libelle = Chaine de rception du libell de l'lment +// +{ + struct Element_de_liste_de_fileselect * Element_courant; + char * Curseur; + + + // On vrifie s'il y a au moins 1 fichier dans la liste: + if (Liste_Nb_elements>0) + { + // On commence par chercher pointer sur le premier fichier visible: + Element_courant=Liste_du_fileselect; + for (;Decalage_premier>0;Decalage_premier--) + Element_courant=Element_courant->Suivant; + + // Ensuite, on saute autant d'lments que le dcalage demand: + for (;Decalage_select>0;Decalage_select--) + Element_courant=Element_courant->Suivant; + + // On recopie la chane en la dformatant (i.e. tous les chars sauf ' ') + for (Curseur=Element_courant->Nom;*Curseur!='\0';Curseur++) + if (*Curseur!=' ') + *(Libelle++)=*Curseur; + *Libelle='\0'; + } // Fin du test d'existence de fichiers +} + + +// ----------------- Dplacements dans la liste de fichiers ----------------- + +void Select_Scroll_Down(short * Decalage_premier,short * Decalage_select) +// Fait scroller vers le bas le slecteur de fichier... (si possible) +{ + if ( ((*Decalage_select)<9) + && ( (*Decalage_select)+1 < Liste_Nb_elements ) ) + // Si la slection peut descendre + Afficher_la_liste_des_fichiers(*Decalage_premier,++(*Decalage_select)); + else // Sinon, descendre la fentre (si possible) + if ((*Decalage_premier)+100) + // Si la slection peut monter + Afficher_la_liste_des_fichiers(*Decalage_premier,--(*Decalage_select)); + else // Sinon, monter la fentre (si possible) + if ((*Decalage_premier)>0) + Afficher_la_liste_des_fichiers(--(*Decalage_premier),*Decalage_select); +} + + +void Select_Page_Down(short * Decalage_premier,short * Decalage_select) +{ + if (Liste_Nb_elements-1>*Decalage_premier+*Decalage_select) + { + if (*Decalage_select<9) + { + if (Liste_Nb_elements<10) + { + *Decalage_premier=0; + *Decalage_select=Liste_Nb_elements-1; + } + else *Decalage_select=9; + } + else + { + if (Liste_Nb_elements>*Decalage_premier+18) + *Decalage_premier+=9; + else + { + *Decalage_premier=Liste_Nb_elements-10; + *Decalage_select=9; + } + } + } + Afficher_la_liste_des_fichiers(*Decalage_premier,*Decalage_select); +} + + +void Select_Page_Up(short * Decalage_premier,short * Decalage_select) +{ + if (*Decalage_premier+*Decalage_select>0) + { + if (*Decalage_select>0) + *Decalage_select=0; + else + { + if (*Decalage_premier>9) + *Decalage_premier-=9; + else + *Decalage_premier=0; + } + } + Afficher_la_liste_des_fichiers(*Decalage_premier,*Decalage_select); +} + + +void Select_End(short * Decalage_premier,short * Decalage_select) +{ + if (Liste_Nb_elements<10) + { + *Decalage_premier=0; + *Decalage_select=Liste_Nb_elements-1; + } + else + { + *Decalage_premier=Liste_Nb_elements-10; + *Decalage_select=9; + } + Afficher_la_liste_des_fichiers(*Decalage_premier,*Decalage_select); +} + + +void Select_Home(short * Decalage_premier,short * Decalage_select) +{ + Afficher_la_liste_des_fichiers((*Decalage_premier)=0,(*Decalage_select)=0); +} + + + +short Calculer_decalage_click_dans_fileselector(void) +/* + Renvoie le dcalage dans le slecteur de fichier sur lequel on a click. + Renvoie le dcalage du dernier fichier si on a click au del. + Renvoie -1 si le slecteur est vide. +*/ +{ + short Decalage_calcule; + + Decalage_calcule=(((Mouse_Y-Fenetre_Pos_Y)/Menu_Facteur_Y)-90)>>3; + if (Decalage_calcule>=Liste_Nb_elements) + Decalage_calcule=Liste_Nb_elements-1; + + return Decalage_calcule; +} diff --git a/files.h b/files.h new file mode 100644 index 00000000..e8da20e8 --- /dev/null +++ b/files.h @@ -0,0 +1,33 @@ +// Modifie Principal_Repertoire_courant en y mettant sa nouvelle valeur +// (avec le nom du disque) +int Determiner_repertoire_courant(void); +// Dtermine si un rpertoire pass en paramtre existe ou non dans le +// rpertoire courant. +int Repertoire_existe(char * Repertoire); +// Dtermine si un fichier pass en paramtre existe ou non dans le +// rpertoire courant. +int Fichier_existe(char * Fichier); + +// -- Destruction de la liste chane --------------------------------------- +void Detruire_liste_du_fileselect(void); +// -- Lecture d'une liste de fichiers --------------------------------------- +void Lire_liste_des_fichiers(byte Format_demande); +// -- Tri de la liste des fichiers et rpertoires --------------------------- +void Trier_la_liste_des_fichiers(void); +// -- Affichage des lments de la liste de fichier / rpertoire ------------ +void Afficher_la_liste_des_fichiers(short Decalage_premier,short Decalage_select); +// -- Rcuprer le libell d'un lment de la liste ------------------------- +void Determiner_element_de_la_liste(short Decalage_premier,short Decalage_select,char * Libelle); + +// -- Dplacements dans la liste des fichiers ------------------------------- + +void Select_Scroll_Down(short * Decalage_premier,short * Decalage_select); +void Select_Scroll_Up (short * Decalage_premier,short * Decalage_select); +void Select_Page_Down (short * Decalage_premier,short * Decalage_select); +void Select_Page_Up (short * Decalage_premier,short * Decalage_select); +void Select_End (short * Decalage_premier,short * Decalage_select); +void Select_Home (short * Decalage_premier,short * Decalage_select); + +short Calculer_decalage_click_dans_fileselector(void); + +char * Nom_formate(char * Nom); diff --git a/gfx2.cfg b/gfx2.cfg new file mode 100644 index 0000000000000000000000000000000000000000..a15e8851fa49a03c76c472e1e357fe119b37ea26 GIT binary patch literal 10351 zcmeI2*>Y4>6o$WZItic<#3+yuL(*atZQE{)0}hZ7Wsso3Fa!{YaXJnWmC4ye!8^<2 zomG}qJ__FX81W5wgYCCo!`_|hul`zl@4xn5Yh_*a?BOFNOa1I=z)=zf^Rnc)Y;Z#M zakNPEGcN}?E;n#OZshmA#3ufd_wa|jmp|oZekl`M_)QLSRc_^)ypR35ZDYS@@8=cu z5VP_D7UY8*klQ)y>JG-$I~i9GGw#_DCXMW3(#R-d>W3Ipk1?VCmI?K4&m~XpP*3Qc zXfmXJn6`QkZG9f0ZDf*mBk?F*f+1hgqA8!GE!(vF6HhVc{tk2Q z?D~SlJ`T#KSv2w!%lh16S%)d6jX%RV|Yq*wNutI_^2_O%q4VVzP=Yd5o6v*UUeRjR@MKGR>5@f4>Qxndf;w= zLJS5*0j6qJ8khgTuT4CD!rdmv|^motzjKrdH6zddIlPk`J5IRm|%fjj|vx%&C-IRk}1 iDsl?+_NOnWp#R_he+vw3q9}{9&u_6Imwcl?CgMM1Eh1(B literal 0 HcmV?d00001 diff --git a/gfx2.dat b/gfx2.dat new file mode 100644 index 00000000..24f77a13 --- /dev/null +++ b/gfx2.dat @@ -0,0 +1,322 @@ +Sunse^ nesCMDSuDsO^5DOYCr{F`{LpK5QZLVr{l`QLZa{ZLVXUhNYDRGwJ\FLExRITFW[zlr|uDby`vg/KjxbliTrmpfK D^siPnSFnsJt oesNgnpunlet;Dedig}Suase DbsidnSJQs^O sRsZTn|ZnXNtcePJgqLuuhec7Dv`ihaS~esbs GfsiXnSNnsRt wesFgnxunTetDeliguSuyseg DjsilnSrnsft {ZsR\ndBn@VtkeXBgItuMPek?D~hipySf}sj{ Onsn`nPvnsZt es^gn`un\et DeTigMSuqseo DrsitnSznsnt CesjXnlNnHRtwe@FgAxuETeSDFlixuSnysrg WjsflnXrntft#{esRcjd}f@ixTuY|rHJlLnxjeVLrDyd@]hFMSEl]TSJQsZt$a{^ob`y~\ua +Q|UpzLNTpR@nnpYGv@ax\ElBA_LiXnSJjw^|(siZw~|`{Y|mYxQHFpvPtYOajtA[jXe|TI`KDZsiXnTJn|Zt7{elVgIluALeCDZKiX^SJFsZT {}sVwnl}nLetDbLihQSbQszK cZsFXndJnLZt|eLYgQ{uQSeK8DZciXfSJntZt/{edVgqluILe[DRLiXQSJVsZD {MsVGnlmnLutLeLFOSPTZGL[PPuTNJEseHn3nrcOscpddlksXyopsiTrigb'Csen`iTcnset DesignSunset DespszGgyin:^is~wKc{gvf2Vtcyw~Ce~jyh;_~hr{pSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset Dyo2{5Omzgq`4Pq`zszBipoyo7Pqtn`iGritbs'CbtnpnSunset DesignSunset Drg}sKotin:_yhuynSkri}b4Wwcyw~Anuh~n:]|nignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset{X>o2/{?)sqtOitgq`4Pq|}szGazgbs'CtnqiTcxe}i DesignSunset DesignSunsq`3Pvkp~wJoth~oZ{mvxqLunset DesignSu4(9(=Yyou{rIazgv`4Pqg}szGazgbsCseq;Eonset DesignSunset DesignSuz`q`3S|jp~wInuh~h?Desiga\g|awf2Vv`zt}@f}e}oDydzt}@f}`vg3Wv`sgnSuwawf2Vwb{v|Ag|set ZxnsszGf}`vg4Wv`zquSunsej=X~k|szGazgq`'Pqgn`iTrigbs'Cbt~nSunset DesignSunset DesignSunset Sq`zt}Eltin;Xyor{sMixgpa5Qpg}t}@fzgvg3Pqg|r{Iiuo~b4Pqg}szGazgqb>Zye}s{F`{fpa5Qp`~Ygzt}@azgqa5QsktgpNirira4Pqg}szGazgq`4Pbtn`iTritbs'_esignSunset DesignSunset DesignSunsem4Wv`ztxJoti~h(5g0 +0set~;siyxGaz`q`3PvgzuvHoumet Dei}szGazgq`4Pqi7gyGazg`4Vw`zsrSunset D;signMhro|`4Pqg}s/{;s79nSun-;* Dek}t}@f}`vg3Wvcs~wJhnset=Qqg}szGazgq`8;j}szGa`wf3WqktgnSunset Den5;2Da) ;signSunset:Qv`zt}@f}`vg3T}js|rOoyssg3Wv`}szGaze{*f;5>Ga#5`rPqf|r{Ecxesb6R}itgnSunset}>(2Bd>`qatQseqxEcxki~;-ignS+ns;)z?*0yDbydrc7S}kqpyDmrset DesignSunset DesignSunset DesignSunsei9Sbtn`iTritbs'Cbtn`iTritbb6Rse`i?5+nse*~8.5;3(3/9nucwC|wz?(2<5.5ud0Tcy|g)?izl~;-490 *1se*~#y7A'zfpa5RseptNu0-;*~Des49nSu1-8(z=+qyDbydrc7SrkrynSunset DesignSunset DesignSunset DesignSuns{h9Rbtn`iTritbs'Cbtn`iTcxerc7Srts<4 +-6+?(}esignSu0-;)}8/5;2 /4*< x1#:28-6*<-y=+109#; 5 u2+1?7 +,7*?.|9/3;3(0-;*~;-79n +0se,wTu#xtDesignSunset DesignSunset DesignSunset DesignSunset<^}d`iTrxd}m:_bepyDmvk}c\=$>=2+0-;*~;-793(3.8)|>)?7~ecu0Tucyw~Ce~cud0Tucyw~Ce~cu0Tucw~C%4)9(|9/4:3(3.9*~;-7gnS+4//z?)?~e~cd0Tucy>5,4/8)zucyw~Ce~cdT+3=4)2/9)}8.790,3-;*~Des7:5!5cwgrQse{nSu2*;)}8(2;3(0-;*~;-i;nunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunse*}>+7gnS+3-;*~;-790 (3.8)~;-4;2.5(>.z3cyw~Ce~cud0T3(1<2(3/9-0TucywCe~c&y9/5<4 (3.8*~:,7:0 +0-;*~8(>:3g}gpb6Xesig3 (2(9/y8.4;0 (0-;* 9s4g2+n/8* 9.ignSunset DesignSunset DesignSunset DesignSunset DesignSunset Desig0 +0-;(y9.4:0 +3/8)}8.4:3(3.;*~9/2<5 /7*3'pTcyw~Ce~cu&x>/5;2)5"ud0Tucyw~Ce~&2.|>(5:3 +0-;+;-7;0 +2(?/~8-5;yFcxi{t Des2;3(0-8t D;/493 u0-9(}e.4:nu3s9t}DesignSunset DesignSunset DesignSunset DesignSunset DesignSun-;t~e-793 +3(>)};s4<3)3/9(|9/5;2(3.9/z?)0>7#:!ud0Tucyw~Ce>*>.|>(5<6e~cud0Tucw~-6'?/{8.794 +0-8*~;-7;3(0,et 8.pqxIknset 8.2:0 +nset ;signu3s8t}D8s4:0S(3.8t DesignSunset DesignSunset DesignSunset DesignSunset DesignS+0-;*~D;-793)4+;*};-792)2/9({>(3?3(7/9.z=+0=4e~cudTucyw~.5)>.{=*>w~Ce~cudTu>>7 +/4)>({8.4:2 +0-;*~8-ignSun-9) Zykq}pMnnse({8.79nSunset De-ignS(nset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset Design u0set~8.5;3(3(;*~D;-4;3)5/?/{9)5;2)5(>/{>)1wCe~cud0Tuc==4 /6$0.zucyw~Ce~cud0?)3;2 )2.8)}8-795(2.8)}8-790+nset>_}krgnSuns;*~esignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset Design +0-;)};.4;2(3-;*~8.4:3(2)9)}8/2<5)5(?.zucyw~ecud0T1*0?<"9%0d0Tucyw~Ce~cu'w?/5<2.6/9)}9.4;2+0-;t D;-ignSun-et DesignS+0-et De-ignSnse DesSe +esignSunset DesignSunset DesignSunset DesignSunset Desig0 +n-e*~;-490(3-;*~e.7g0 (3(8*~;-4:3(3.9(|>.4:3/8cd0Tcy~e~u0Tucyw~Ce~cudTucwe~cu$w9/3;2)2/8*~:,681 unset Desig0 unset DesignS+n-et DesSet + +siSu +t DesignSunset DesignSunset DesignSunset DesignSunset Desi90 unset~;.4;0+3.8)}8/2<5(0-;*~;-4:0)2(>(|;.2<4 /4)?.z<*0?6 -9+=,x6+:?7-7*?.y=$>09 ,4)9(|8.5;2(0-:+:signSunset DesignSunset DesignSunset D +sin.z?)3=5 +"9$0!x?)3=7 /4(>/|9.4:3(3.8)}8.790 *1,:t DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSu0-et e-790 (3-;*~;-ign u0-8)}8.490 +3.8)}8/5;2)2/9)}9(0?4 /5(9(|9(3<5)2/8*~8.4:3(3.;*~:,6gnSunset DesignSunset DesignSunset DesignSe +ei/y9/5:3(0-;)|9/4:3 *1,;*}8-4:3 +0-;+:,6gnSunset DesignSunset DesignSunset DesicYW^SM~K!0T]sƣgR5E D Suf8EsWMeLLnSne D}kvS n]reiaVMhst'HikqvSmvk}DesqgSmnse@xDQ+igvwQvset DesqnSunsed Desfof%>Se,`AWignkqvSYt DesQ_VSunset DesignSunset#VSM\|e/M~suL\KygVkuL T]~kunsuL0Deset!7Qgn߲DkunK!0T]ciwvGe~thQ_rKeV70Te󉟐sgz[}kg~k ~]d (  n?uR'1@4PqsqGv{EfCet 8ignCMcL0uKw~Cencud08]cigf_b{et d GnSu.3%4\DesA ?]nsud|g/ VKud DesignSuvkud0D}s SunseL  nC s0D#1W +nK LVivcunset8tUCYWvSEvk}l8tes=_k!nsel8:}kignSuns}lDesgnSunset tUskabKEeHFnKMvk}lDo{nO#h,BiitބooSI8eokvKE^s8gR5Pu DekqgvKuns}l \}Ce^3Evet 8eign3Ev}D@Do{^SEnO'%Oikrgt=?/aSIFxe!(5s[@g x3/u†si[vKE^ e +8\)nD 3 niat 8S5#@$e hs켽gr ucyW^cus5Vcerұ#nVKDWn il$ i_^cE^C]tCqkhSMvk}l8|ekUnSunset Desg^cmnset De e-u悙sigR5er&2nSuR\Dkkq^cEnseut8DYkYWSynoix,s}l0tUCugnS De5unsYsigt :hSuDesWR nk} +tUoign5t D_~Sun(esikset悫onS K \UC W^Kuvk}l8\}sYv_mvCetFsignCMDY/me患 i^ot(Sn i:eCqb/s]\XHgnS lP| O/usYބsYR5e |}CYnknK}lDUki_vKIneh i_FoA + t8tSunw +:eE1?s] 8gn?u t}s/uVesYn5e a?uR\D s nk}H@$Ykqy^c ^t(]y~Se}qRKms}DXHgvcuVk}H \Us/uvCes]?ne@xDnS b + 8eO/ukelPig5.3et 8awmcnSUk^;q}t8\}kqg|wWwt AE_C&SustDs2;0ٖ͑Ce~cud0Tucy~Ce~cu0ucyOF{F[M\ DeAOF{unu0Tu[Af]F[M\lM[AOnSfM\lManSuF[M DesywCnset Dcyw~Ce~let DucynSunsetTucyw~Cj~cud DeignSe~cd0Tucyx~Le~cM\kM[AOF{ZNLet DeLIHF{]F[tDesigSF[M\kE\AOFSust DM[g{]Fcu esiOF{nset Dsw~Cuns\lM[AOQSunsud?TzsignSj~lud0DesVOF{]F[MlM[ywC~cud0TsignSunlud0Tset /Kj|fha\t Des σ syB(琕  uUl&si eBrnScUDD]cQ#*keVނit"U SuLDe{ Ns[ລWgV? DsgSuvkl8Ds_hkner]uinTybk}l8D}kq^cns}t^D}sigZ uZ+et8`AkignSuns}l Desig~Sunsj|(5#Ig6wQJWet |akI[nSuns]LDesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunsbs'CetignSunset DesignSunset DesignSunses'DesignSunset DbtignSunset DesignSunset DbsngnSuitbs'Desi`nTunses'CbtignSrntet DesignSunjbm Cesi`wTuises'Cbtn`nSrnt|s Deti~iJunset Desi`iSuwtet'Cejn~nSunjbm Desp`wSrises9DetngnSunset ]bjn`wSuijbm9Cesp`wTliset D|tpgnSunt|s DesignSunset Desi~iSunset']esignSunset DesignSunset DesignSunset DesignSuwtbs']esn~nSliset DesignSunset DesignSunset Desi`wSuwtet9Cbtn~nSunset DesignSunses9C|tignJrit|t Dbtn`iSunjbs']esi`wTliset DesignSuntet Desi`nSunsbs'CbsignSrnset DetignSunset DesignSunset DesignSuns|s DesigiJunset DesignSunset DesignSuntet Desi`nSunset'DesignSunset DesignSunset DesignSunset DetignSunset DesignSunset DesignSliset D|tpgnSuwt|t Dejn~nSunsbm DesignSunset9Cbtn~nSrwjbm'Detp`wSrnsbs9D|tigwTrit|t DesignSunset Desi`nSuises'CbtngnSunses DesignSunset Desi`nJritet'Dbji`nSrntet'Detp`nSrns|s9DetignSunset CesigiSuiset CesngiSuises9C|jngnJrwtbm DesignSuntbs'DesignSrnset DetignSuntbs'DesigiSunset DesigiTrnsbt CetigiSuisbt CesngiJlises ]btpgnSunset D|tn`iJunt|s ]bsi`nTuntet'Dbjp`nSlnjbs9DesignSunsbt DesigiSunset Cejn`iSuijbm Desn`wSunset DesignJrwtbm Dbjn~wTuntes Dbsi`wTlwtet9C|tn~nSunset Dejn~nSlnsbm'DetigiSrnsbt C|ti~iSuwtbs']esignSunset DesignSunset DetigiSunset DesignSunset DesignSunset DesignSunset D|tignTunt|t DesignSunset DesignSunset ]bjignSlijbm D|tpgwTlnt|t D|tignSunset DesignSuntes Desi`nTunset'DbsignSunset DesignSunset Desn~nSuwtem']ejn~nSlijbm Desp`wSunset Desi~iSunset']esignSrnjbt'Detp`wSuns|s9DesignSunset ]btn`wSuijet9CesngiTuises9CbsngnJrites DesignSunjbs'Cbsi`wSrnset'DetignSrwsbt Dejn`iTrnset DesigiTritbt CetigiSuisbt Cesn~iJlisem']btpgnSunset Dejn`iJunjbm ]bsi`wSuntet'Desi`nSrnset'DesignSunsbs'CbtigiSunsbt C|sigiSuwt|t9Cesi~iTrwset DesignTritbs DbsngnTuntes Dbsi`nSuntet'Desi`nSunset Detn`iTrnsbt'DesigiSrnset CesignSuiset DesignSunset9CbtpgnJrws|s DbjignTuntet'Dbsi`nSritet DesignSritbs'Desi`nSunset'DesignSrnset Cbtn`iSunset DesignSunses DesngnTritbs DbsignTunset DesignSunset Detn~nSunsem'DetignJrnsbs'CbjigiSunset DesignSuitbs'Cesi~iJunsem']bjignTlnjbm DesigwTunset Desi`iTritet Desi`nSunset'DesignSrnset DetignSunset Cbtn`iSuwt|t Desi~iJunsem']esignTritbs DesignSuntbs'Cbsi~iJunset ]bjignSunjbm Detn`iTrnset DesignJrit|t ]bji~iSuijet Cesn~nSlisem'CbtpgnSunset Dbtn`iTuntet'Desi`nSrnset']|tignSlit|t DesignSunsem'CbjigwTlnjbt C|sn~iSuijem']esp`iTliset DesignTritbs Dbsi`wSuntet'C|si`wJrwtet9Cbji`nSunset Dejn~nSrnsbm'DetigiSrnsbt Cetp~iSuis|s']esignSunses DesignTunset Dbtn`iTuntet Desi`nSunset DesignSritbs9DesignJrnset DetignSunjbt Cbtn`wSunset Desn`iJunset ]btpgnSuns|s Desp`iJuntbs9DesignSunset'Cbtn`nSuns|s9Desi~iJunset ]bjigiTritbt DesignSuijem'Cesp`wTlnset9C|signJrwt|t Dbji~iTunset Desi`iJunset ]bjignSunjbs'Desp`wSunsbs9DesignSunset Cesp`iSuis|s9Cesn~iJuises']esngnTlnses DesignSunset DesignSunset'Cbtn`nSrnset'DesignSunset DesignTlnset D|tpgnSuns|s9DesignJrwset DejngnSunset DesignSunset Desi`nSuntet'Cbtn`nSunset DesignSunset DesngnSunses DesignTunset DbsignSuntet DesignSunset DesignSunt|t Desi~iSunset DesignSunset DespgwTlnses C|tignTuisbt DbjngiSunjbs'CesignSunses'CbtngnSuises DesngnTunses9]bsignJrijet DesignSuwtbs9Desn~nJrnses DetignTunjbt D|si`wSunset DesigwTrwset C|jngnSuises DesngnTuntbs'CbsignSunset ]btn~nSuijbm'DesngiSrnses9CetignJrisbt DesignSunses Desp`iTrites9DbsignTuntet DbsignSunset DesigwTrijes C|sp`nTuiset'DbsngnSrwtes'Cbtn~nSunset Cbtn`iSunsbt DesigiSunset C|signSuwtbs DesignSunset DesignJunjet'Dbtn`nSunset9DesignSunset DesignSunset'DesignSrns|t D|tngiTrit|t DesignSunset DesignSuntbs'CbsignJrwset ]bjn~nSuijem'DesignSunset DesignSunset Cbtn`wSunset9CesignSunset DesignSritbs DetpgnSuns|s'DesigiJunset ]btn`nSunset Desn`iTrnses DesignTunset DbjignSunjbs'CesignSunset9CbtpgnSrws|s DetignTunsbm ]bsigwTrijet DesignSuitbs'CbsngnSrnses DetignTlnjbt D|tn`wSunset Desi~iTrwset']ejngnSrnses DetignTunsbs'CbtngnSunset Cbtn`nSuwt|t Desn~nSunses9DesignJriset DesignSunjbm Cesi`wTuiset'DbsngnSrnt|s Deti~iJunset DesigiSunset'Cbtn~nSuisem'DesngnSrnset DetignSunset Dbtn`wSunset9CesignSuiset DesngnSritbs DesignSunsbs9DesignJrijet Desp`nSunjbs9Desn`wSunset DesignTrit|t Desi~iSunses']esignSliset'CbtpgnSunset DetpgwTuns|s9C|signJrwset ]bjn~nSuijem'DesignSunses'Cbji`nSunjbt'DesigiSrnset C|ti`iTrit|t DesignSrns|s Deti~iTunsbm']bsigiTlntet C|si`nSunset DesignSunset9C|sigwTrwtbm C|sigwTuiset DbsignSunset DesignSunset Dbtn`iTrnset DesignSunset DesignSunset DetignSuisbm DejngwTrwtbm Dejn~nSunset Desi~iTrwsem']ejngiTlnses9CbsignTrwtet DbsignSunset Dbtn~nSrnsem'DesignSrnsbt DetignSritbt DesignSunjbs']esi`wTlisem'DbsngnTrntes Dejn`nTunset DesignJuwt|t9Cbsn~iSrwtes Cejn`wTuiset9CbtngnSunset D|sp`wSuites9Cesp`nTuiset'DbsngnSlitbs DesignSuns|s'C|sigiJuwt|s Cesi`iJuisem']espgnTlnset DesignSlitbm ]btp`wTuijbt'Dbsp`iJrntet ]bti`nSunset Dejn`iJuntbm']bsigiSrntet'C|ti`nSuwtbt'DesignSunsem'CbjigiTlijbt ]bsngiSunt|s Cesi~iTuiset DesignSrnjbm Detp`wTuns|s'CbsigiJrntet ]bti`nSunset Desi~iTlns|s']|tigiJrnsbt ]btp~iSuns|s']esignSunset DbtpgnJrns|s DbjignTunjbt DbsignSritet DesignSuntbs9DetpgnJrns|s DetignSunsbt Detn`iSunset Desnha\zase{9Djsign\un|et DjjihnSuntj{/KjsignSunset/Kj|fhnSzn|et/De|ihnSznsjs/C||igi\ra|bt DesignSuntj{/CesnhwSlase{9Desfgn\unse{ Djsign\unset Desiha\za|et/DesihnSzwset/Detf~nJznses/KjtignSunset Kj|fhaSuasjt KesfgaSuase{ Desfgn\unse{ DesignSun|j{/Kjsihn\unset/DjsignSznset De|ignSunset DesignTza|bt Cjji~aSuajet Kesfgn\uase{ Dj|fgnSunset Dj|fha\unse{ Design\unset DjsignSza|j{/DesignSunset DesigaSunsjt Kj|fhaSuaset KesignSunset DesignSun|js Desigw\un|et ]jsiha\zatet/DesignSunset De|fha\znsem/]esigw\lajet K|sphwSuwset9KesignSunse{/Kj|fgnSunse{ Design\unset DjsignSun|et DesignSza|j{/Dejf~nSunsem/]esigw\lnset Kj|fhaSunset Desfha\zasem/]esignSlajet DesphwSun|j{/KjsignSunset Cj|f`nSrajem/De|pgnSznsjm D||igi\za|bt DesignSua|j{/Kesfgn\unse{ Djsign\lw|et Db|f`nSunset Desigi\zatet'K|sphnSzwsjm/De|pgw\rnsb{/Kb|ignSunset Kj|fhaSuase{9Desfgn\zwse{9]jtfgnTzate{ DesignSuntjs Djsihw\un|et/DjsihnSzn||m/De|i`a\rnset DesigaSunset KesignSua|j{/KesfgnSunse{ DesignSunset Dj|fhaTunset ]jsignSun|et DesphnSza|j{'DesignSunsj{/CesignSla||t Desi`aSuns|{/]esfhaTunset Design\za|j{ Desi~aJunsem/]esignSlajet/Kj|fhnSunset De|pgw\zns|{9K|signJzwset ]jjf~nSuajem/KesignSunse{/]esignSlajet Despha\uns|{9DesihaJunset DesignSzns|{/De|i~aJznsjm/]e|iga\lnsjt K|sigaSunset DesignSunset DjsignSun|et DesihnSunset DesignSunset DesignSunset DesignSznset DesignSunset DesignSunset9KesignJzwset ]jjignSlajet De|pgnSunset Desi`a\zatet/]||phnSzw||t/De|f~nJznsb{/KjtignSunset DesignSun|et Kesfha\zaset DesfgnSunset DesignSun|es/Kjsihn\ln|et/DjsihnSzw|et/Detf`nSznset DesigaSunsjt KesigaSuasjt Kesf~aJlases/Cj|ngnSunset Dj|fhnSunset/DesignSznset Dj|fhnSunsjt DesignSunsj{/De|igaSznsjt Ke|igaSuasjm9Kesfgi\ziset DesignTza|js Djjfgw\un|e{ Djsihn\lw|et9Db|f`nSunset De|ignSunsjt DesigaSla|jt K||pgnSua||t DesignSunses/Cj|ngn\laj|{ Djsfgn\un||{9]jsi`aTzatet DesignSratet9De|phnSznsjt/De|igaJznjjt Cj|fhiSunset DesignSunset DesignSznsjt DesignSunset DesignSunset'KesignSzwset De|i`aSznsjm/]esigi\rnset DesignSuntj{/Kj|nha\za|j{/Kj|fha\rnset/DjsignSzn|et De|ihnSunsjt/CesigaSza|j{/Kjtfha\za|es/Kj|fhnSunset Kj|fha\za|j{/Kj|fha\za|j{ Desihn\unset/DjsignSzn|et De|ihiSuntjs/Kj|fha\ra|j{/Cjsnha\rntet DesignTza|j{/Cj|fha\za|j{/Kj|f`nSunse{ Design\unset DjsignSun|bt Desiha\unset'KjsignSui|et DesignSunsj{/Kj|fha\za|j{/Kj|fha\zaset DesfgnSunse{ Design\rnset Dj|ngnSuntj{/Kj|fgi\za|j{ Db|fha\unset De|fha\za|j{/Kj|fha\za|j{/Kesign\uaset DjsfgnSun|e{ Desihn\unset/DjsignSun|et DesihnSunset DesignSza|j{/Kj|fha\za|j{/Kj|fhaSunse{ Kesign\uaset DjsfgnSun|e{ Desihn\unset DjsignSun|et DesignSunset Cj|fha\ra|j{/Kj|fha\za|js DesigaSunset KesignSuaset Djsf`nSun|e{/KesihaTzaset/KetfgnSzaset Desiha\za|j{/Kj|fha\za|j{/KjsignSuaset DesfgnSunse{ Design\unset Djsfha\za|j{/Kj|fha\za|j{/KesignSunset DesignSunset DesignSunset De|fha\za|j{/Kj|fha\za|j{/DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset Desiga\za|j{/Kj|fha\za|j{/Kj|ignSunset Design\za|j{/Kj|fha\za|j{/Kj|fgnSuw||t DejfhaJunjj{/Kjspha\la||{/K|spha\zwset9KjjignSuajet DesignSunse{/Kj|fha\za|j{/Kj|fha\zaset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset Desfha\za|j{/Kj|fha\za|j{/K||fhwSuns|{/K|signJza||t ]j|f~nSla|jm De|fha\za|j{/Kj|fha\za|j{/DesignSua|j{/Kj|fha\za|j{/Kj|fhaJza||t DejfhaJunsem/KjjignSla|jm Despha\za|j{/Kj|fha\za|j{/Kj|fhnSunset Db|fha\zi|j{/Kj|fha\za|j{'Design\unset DjsignSun|et DesihiSunset/Kj|fha\ra|j{/Kjsnha\za|et Desiga\za|j{/Kj|fha\za|j{/Kj|fgnSun|e{ Desihn\unset/DjsignSzn|bt Db|iha\za|jt'Kj|fhiSui|j{'DesignSunses/Kj|fhi\za|j{/Kj|fha\zatet DesfgnSunse{ Design\unset DjtignSun|j{/Kj|f`a\za|j{ Cj|fha\unset De|fha\za|j{/Kj|fha\za|j{/Kesign\uaset DjsfgnSun|e{ Desiha\rnses/Kj|fha\zatj{/Kjtigi\zatet DesignSui|j{'Detfha\zisj{/Kj|fgaTunsb{ Kesign\uaset DjsfgnSun|e{'Desihi\zaset/Kb|fgnSrasb{ DesngnSunset/DesignSznset De|ignSunsjt Desiga\za|j{/Kj|fha\za|j{/Kj|fgnSunse{ Design\unset DjsignSunset Desiha\za|j{/Kj|fha\za|j{/KjsignSunset DesignSunset DesignSunset Desfha\za|j{/Kj|fha\za|j{/KesignSun|j{/Kj|fha\za|j{/Kj|fha\unset DesignSunset DesignSunset DesignSua|j{/Kj|fha\za|j{/Kj|fhaSunset Dj|fha\un|j{/Kjsiha\za|et DesignSunset DesignSunset DesignSunset Kj|fhaSua|j{/Kesfha\zaset Design\za|j{ Dj|fha\un|j{/KjsignSun|et DesihnSunset/DesignSznset Db|iga\za|jt Kj|fhiSua|j{'DesignSunse{/Kjtign\za|js Dj|fha\unset CjsignSun|et DesihnSunset/DesignTznset Kj|ignSua|bt Desf`nSunset Desfha\zase{/Kj|fgn\za|j{ Design\unset DjsignSun|et DesihnSunses/De|fha\znsj{/Kjtiga\zatet DesignSua|j{/Kesfha\zase{/Kj|fgnSunse{ Design\unset DjsignSun|et DesihnSunset/DesignSznset De|ignSunset Kj|fhaSua|j{/Kesfha\zaset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset Desiga\zatet Kj|fhiSua|j{/KesignSraset DesfgnSunse{ Design\unset Djsiha\za|et/Kj|fhnSza|j{/DesignSunsj{/Kj|iga\za|jt Kj|fhaSunset DesignSunset DesignSunset DesignSun|j{/Kjsiha\za|et/Kj|fhnSunset DesignSunset DesignSunset DesignSua|j{/Kesfha\zase{/Kj|fgnSunset DesignSunset DesignSunset DesignSua|js Desfha\rnse{/Kj|ignSuntjt DesigaSunset KesignSrase{/Kj|fgn\za|js Dj|fhiSunset DesignSunset/Kj|fhnSza|j{/De|fha\znset DesignSunset ]esignSuajet DesfhiSunse{/Kj|fgnSza|j{ Desnha\unset Desiha\za|et/Kj|fhnSza|j{/DesignSznset De|ignSunsjt DesigaSunset KesignSuaset DesfgnSunse{ DesignSun|j{/Kjsiha\za|et/Kj|fhnSunset DesignSunset DesignSunset DesignSua|j{/Kesfha\zase{/Kj|fgnSunset Dj|fha\un|j{/Kjsiha\za|et DesignSunset DesignSunset DesigwSunset Kj|fhaSua|j{/Kesfha\zaset Design\za|bt Dj|fhaTun|j{/KjsignSui|et DesihnSunset/DesignSznset Db|iga\za|jt Kj|fhiSua|j{'DesignSunse{/Kj|fgn\za|j{ Dj|fha\unset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset Desfha\rnse{/Kj|ngn\za|j{ Desigi\unse{9Djsign\zw|et Db|fhnSunsb{/]e|fha\zasj{/Kjtfga\zates DesignSua|j{/Kesfha\zase{/Kj|fgnSunset DesignSunset DesignSunset/CesignSza|j{/De|fha\znses/Kj|ignSunset Desf`nSunse{/Cesign\zaset DetfgnSunse{ Design\unset DjsignSui|et/Kj|fhnSza|j{'De|fhaTunset DesignSunset DesignSunset DesignSunse{/Kj|fgn\za|j{ Dj|fha\unset DesignSunset DesignSunset DesignSunsj{/Kbsiga\za|bt Kj|fhaSunset'KesignSuaset DesfgnSunse{ Desigi\un|j{/Kjsiha\zatet/Kj|ngnSunset DetignSunsj{ Desiga\zwset Cj|f~nSunjj{/]esigw\zaset9Kj|pgnTza||t Dj|f~nSun|jt Desi`nSunset DesignSza|j{/Kj|fha\za|j{/Kj|fhnSunset DesignSunset DejignSunset Design\za|j{/Kj|fha\za|j{/Kj|fgnSunset/KbsignSza|jt De|fha\lnjet'Kj|phnSuw|j{/Desi~a\znsem/Kj|igi\zajj{/Kj|pgw\za|et Dj|ngnSunset DesihaTunset/Kj|ignSza|j{9Desi`a\zwset ]j|fhnSunjj{/Despha\znsb{/K|sfha\zwse{/Kjsign\ziset DesignSun|et DesihnSunset/DesignJznset ]j|ignSla|jt D||fhaSuw|j{9KetfhaJua|j{/]esfha\unse{/CesignSunset DesignSunset DesignSunset DesigaSunset KesignSuaset DesfgnSunse{ DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DespgnSuns|{ Desi~a\unsem/Kjsigw\zajet9Kj|pgnJza||t Dj|f~nSunset Desi`a\za|js/Kj|fha\za|j{/KjtignJza|et ]j|fhnSla|jm/D||fhwSzi|j{9De|fha\za|b{/Kj|fhnTza|j{/DesignSunset DesignSunset DesignJznset Dj|fha\za|j{/Kj|fha\za|j{ DesignSunset DesignSunset DesignSunset Db|ignSri|jt Db|fhaSun|j{'Desihi\unset/DjsignSzn|et De|ihiSuntjt/Kj|fhaSra|j{/Cesnha\rnset DesignTznset Cj|ignSua|jt Desf`nSun|e{ Desihn\unset/DjsignSzn|bt Db|nha\za|j{'Kj|fhi\ui|j{'DbsignSunsj{/Kj|fga\za|j{ Kj|fha\unset DjsignSun|et DesihnSunsj{/Kesiga\zaset Kj|fgnSunsjt DesigaSunset De|fha\zasj{/Kj|fga\za|j{ Kesign\uaset DjsfgnSun|e{ Desihn\unset/CjsignSza|et DetfhnSunses DesignSui|j{/Kjtfha\za|j{/Kj|fhaTunse{ Kesign\uaset DjsfgnSun|e{'Desihi\zaset/Kb|fgnSrasb{ DesngnSunset/DesignSznset De|ignSunsjt DesigaSuns|s/Kesi`a\zas|{/Kj|f~a\zije{/Kjjign\zajet Dj|pgnSunset Desigi\zates'Kj|fhi\za|j{/Kj|ngnSratjt DesfgaSunse{ Kesign\uatet Cjtfha\za|js/Kj|f`aSra|js CesignSunsb{/Kbsi`a\za|bt/Kj|fhaSziset'Ke|ignSuasjt DesfgaSunse{ Kbsign\ua|j{/Kj|nha\za|jt'Kj|fhaSunset DesignSunset DesignSunset DesignSunset'KbsignSza|et Detf`nSunset DesignSunset DesignSunset DesignSraset Db|fgnSun|j{ DesihiSunset/DesignTznset Cj|ignSua|js Detf`a\za|j{ Cj|fhaTuntj{/CesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset Desfha\zase{/Kj|fgn\za|j{ DejfhaJunjj{/]esiha\lnset9Kj|pgnSuw|j{9De|fha\znsj{/Kj|iga\za|jt DesignSunsb{/Kesiha\zase{/Kj|fgn\zijet DjjignSunjet DesihwSunset/KbjignSza|j{/Desfha\znset'Kj|ignSunset DesignSunset DesignSunset Design\za|j{ Dj|fha\un|j{/KjsignSunset DesignSunset DesignSunset DesignSra|jt Dj|fhaSua|j{/KesfhiSuase{9DesfgnJunse{ Design\unset DjsignSun|et DesihnSunset/DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunses/Cesign\zaset Db|ngnSunset DesignSunset DesignSunset DesignSunjj{/Despha\lns|{/K|siga\zwset KjjignSuajet DespgnSunset DesignSunset DesignSunset DesignSunset/Kj|ngnSza|j{'De|fha\znsjm Db|igwSunsjt DesigaSunset KesignSrase{/Kj|fgn\za|js Dj|fhiSunset DesignSunset DesignSunset DesignSznsj{/Kj|iga\za|jt Kj|fhaSunset KesignSunset DesignSunset DesignSun|j{/Kjsiha\za|et/Kj|fhnSunset/DesignSznset De|ignSunsjt DesigaSunset KesignSuaset DesfgnSunset DesihiSunset/KbsignSza|et DesnhnSunset/DesignSznset De|ignSuntjt Kj|fhaSua|j{/Cesfha\rnset DesignSunset DesignSunset DesignSunset DesignSunset De|fha\znsj{/Kj|iga\za|jt DesignSunset DesignSunset DjtignSun|js Desiha\unset CjsignSun|et DesihnSunset/DesignTznsj{/Kj|iga\za|bt Kj|f`nSunset Desfha\rnse{/Kj|ngn\za|j{ Desigi\unset DjsignSun|et DesihnSunses/De|fha\znsj{/Kjtiga\zatet DesignSunset DesignSunset DesignSunset Dj|fha\un|j{/Kjsiha\za|et DesignSunset DesignSunset DesignSunset Kj|f`nSua|j{/Cesfha\zaset DetfgnSunse{ Design\unset DjsignSui|et/Kj|fhnSza|j{'De|fhaTunset DesignSuatet DesfhiSunse{/KesignSraset DesfgnSunse{ Design\unset Cjsiha\za|et/Kj|f`nSza|js DesignSunset DesignSunset DesignSunset DesignTziset Dj|fgnSuntjs DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSua|es/Cesfhn\zase{/Db|ngnSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunset DesignSunsetj ~~~~~~ "# + Z[~jkbcfgfg89NO,-67*}qn~u}rvj}nv~u}r{n|xu~}rxwponmr}x{)#NOXQHFGSB  AX35.3%4$%3)'."# &'$%z{01NO4523<=RSPQ{r}}nwjwmmn|rpwnmk'p~ruuj~vnmx{vntj{uvj{r}j~m'@KH@R2NAHMRNM@KH@R8 -@M$OQNFQ@LLDQOQNFQ@LLDQ$'&8@QSHRSvr|lnuujwnx~|+4GHRHRNTQUDQXEHQRSOQNFQ@LBNLOHKDCHM7@SBNL# ,,NV KDUDKQNTSHMDRVDQDVQHSSDMHM&!RRDLAKDQNOSHLHYDCENQ @MC&BNLOHKDCVHSG"NQK@MC4!3- ,7DVDQDHMROHQDCAXSGD83DS-NCDQNTSHMD,EQNL8,)"SNBQD@SDLNQD@L@YHMFUHCDNQDRNKTSHNMR,4G@MJRSN%BKHORDENQSGDHQ%/3CNRDWSDMCDQ7%/3KHSD ,3NLDHMENQL@SHNMS@JDMEQNLRDUDQ@KCNBR,0#'0% )MSDQUTD 0#)MSDQCHS F@UDTR@MHMU@KT@AKDGDKO&4G@MJRSN3G@VM(@QFQD@UDRENQGHR,EHKKDCONKXFNMQNTSHMDEQNL!KKDFQNU)4G@MJRSN#@QKNR-@CD0@QCNENQGHRFQD@S'Q@E8KNFN+!SGNTR@MCSG@MJRSNSGD@TSGNQRNESGD!CHEEDQDMSSGHMFRKHRSDC@ANUD'7D@KRNVNTKCKHJDSNSG@MJ@KKSGD&ODNOKDVGNF@UDTRHCD@RSNHLOQNUD +'Q@E8orunox{vj}|l{nmr}|0+-3TMRDS$DRHFM,"-%KDBSQNMHB!QSR')&#NLOTRDQUD"-0-HBQNRNES0#8: 3NES)-'"HU@R77HDCL@MM 3#W#NKNQHW (#%, +#&+/3+)3DJ@D3DSRXRSDL 0) 0#$DF@R%KHSD0!,DQLLGMNANCX XY~&'~&'&'~()$%~|}:;HIRSHI01HIFGRS,-01RSTUPQ |wjruvjru'5),,!5-%$/2-%2NAHMRNM  QTDCDKNARDQU@SNHQD,)-/'%3&2!.#% +!2,-!2)4!5$8 -@M  QTDCDK@"Q@RRDQHD,)-/'%3&2!.#% nvjruCNQLD LRHTMHKHLEQL@QHS@TC DMRHKTMHKHLEQ()$%  $%$%~ + "#&'z{TUPQ45BC45PQPQ<=FG67HINODE,-RS<=HIFG3NTQBDRHYD@ANTS+A&'Q@E8RAHQSGC@SD*TKXSGXY~() $%z{@AFGHIFG./TU89PQ* #SQK #RSNORSGDOQNFQ@LVGDMXNT(@QDDMSDQHMFU@KTDR3NCNMSOQDRR&SGDRDJDXRTMSHKVDEHWSGHRATF, !EDVCHEEDQDMSJDXBNLAHM@SHNMRQDSTQMSGDR@LDBNCD, !QDCEK@RG@OOD@QR@SRS@QSTOVGDM@MDLOSX:HOCQHUDHRENTMC( 3NLDETMBSHNMR@QDMSEHMHRGDCXDS*4GHRHRMNQL@KENQ@"DS@UDQRHNM RNCNMSVNQQX+"TSHEXNTRSHKKEHMCRNLDATFRHMSGD(MDWSUDQRHNMR SGDMVDC@OOQDBH@SD+SG@SXNTSDKKTRVG@SSGDXDW@BSKX@QD!@MCGNV@MCVGDMSGDXNBBTQ-d"# $%&' "# ~|}NO4589<=PQRS45NO<=FG899NTKKOQNA@AKXR@X($NDRSGHRLD@MSG@S)G@UDSNO@X!MCVDKKQDOKXSNXNT.N "# + Z[~jkbcfgfg~$%~ + "#  XY"# 89NO,-67<=PQ67NO4545,-NO45 "TS ATS ATS+#NMRHCDQHMFSGD@LNTMSNEVNQJ@MCKNUD +VDOTSHMSGHROQNFQ@L VDVNTKCDWSQDLDKX+@OOQDBH@SDSG@SXNTFHUDTRRNLDSGHMFHM%DWBG@MFDENQSGDTRDXNTL@JDNEHS),DSRR@XRNLDLNMDX NQ@MHBDOHBSTQD'XNTCQDVVHSG'Q@E8 NQ@ONRSB@QC+)EXNTL@JDOQNEHSVHSG@MHL@FDXNTCQDV+VHSG'Q@E8 HSVNTKCADFQD@SHEXNTRDMS,TRSGHROHBSTQD)EXNTTRDCHSENQ@F@LD ,VNTKCADVHRDQMNSSNRDMC@KKXNTQFQ@OGR 'VG@S@ANTSRDMCHMF@BNOXNESGDF@LD + "#  XY"# ~*+ &'$%z{67NO4545,-NO4501HIFGVW45FGRS<=HIFGPQ+4GHRUDQRHNMNE'Q@E8HRADHMFQDKD@RDCSNXNT@RHR(!KKATFRRGNTKCADQDONQSDCSNDHSGDQ2NAHMRNMNQ8 -@M)4GD@TSGNQRS@JDMNQDRONMRHAHKHSXENQ(KNRSVNQJ NQC@L@FDCDPTHOLDMSB@TRDC)CHQDBSKXNQHMCHQDBSKXAXSGHROQNFQ@L''Q@E8B@MMNSADLNCHEHDCHM@MXV@XVHSGNTSNTQVQHSSDMBNMRDMS,&HM@KKX SGDBG@QFHMFNELNMDS@QXEDDRAX,@MXTM@TSGNQHYDCO@QSXENQSGDBHQBTK@SHNM%NQTRDNESGHRTSHKHSXHRDWOQDRRKX ENQAHCCDM(4GHRLD@MRSG@SHEXNTG@CSNO@XENQ)FDSSHMF'Q@E8 XNTG@UDADDMRVHMCKDC7p "#  &' $%z{89NO4545RS<=FG89PQ/TQADRSQDF@QCRFNSN"!BBDRR&HKSDQ0HMJ#!BD&HUDQ0HWDK$!BHC*@L&K@M0QNEHK%!BQXK&QDC0QNVKDQ$!KDWDK&QDCCX60TYMHJ#!KH@R&QNRS1THBJ !LHQ@K'@dK'$# 2@$!QQ@JHR'@HM82@RSDQ$!UNB@CN'@MC@KE2@UH@M$"@KNN'NAKHM2DC"TF!"@QSH'QDDMOHW2DL!"@S'QHC2DY'"HQN'QNR1THBJ2NTCNTCNT'"HRNTMNTQR(@BJDQ#QNKK3@BQHKDFD!"K@BJ!WD(@OKN3@L%"NMMHD(NE3@MC-@M#"NN(NQMDS3B@OD'"NY(TKTC3_A@RSHDM$#@QHMD*@U@3GNC@M"#G@MCQ@*"43J@K%#GDDS@G*_QgLD3JXEHQD$#GHKK*TKHDM*#! 3OG@HQ&#NTF@Q+@K-HM$N3OQNBJDS"#QDL@W+@MD7NNC3SDE##XBKNMD+@QL@3SNMX&$@JD+DHSG3TL@KDSG$$@MMX,@YTQ3TMC@X"$@MTAD,HFGS3GNV3TMX%$@QITK,KTUH@3XA@QHR!$@QVHM,NTHD4"&%$@QJ!MFDK,TJ4DLODRS"$@R-@CD4GNQ!$DBJDQ-@LNR4-+%$DQ0HHON-@MCQHWW4VN&@BD'$DRSNO-@MFTD5MCDQJHMF$$H@ANKN-@QR5MQD@K'$HMD3-DOGHRSN6@D6HBSHR&$Q@B-DQBTQD6@RS@SNQ#$Q9DR-HQDB6@SHM%%CXW-N@6DBJL@M"%KKDQ-NWHB@7@HM#%KKXM-2+7@KKX$%/&.HSBG7HKK"D$&@KK.N@K8NNLHD"&@LD.XSQHJ8SQL&&@MSNL/OSHB9@MM3TKT&D@Q/QNLD:!&D@SGDQ0@GK@CHM:DA#&DMMDB0G@Q:DAHF&@MC@KKOHWDK CDLNEQ@MCBNCDQR###### GrafX2 initialization file ###### Fichier d'initialisation de GrafX2 ## +# # # # +# You may modify this file with any # Vous pouvez modifier ce fichier avec # +# standard ASCII text editor. # n'importe quel diteur de texte # +# # ASCII standard. # +# # # +# Comments are preceded by ';' or # Les commentaires sont prcds par # +# '#'. # ';' ou '#'. # +# # # +# Options are not case sensitive and # Les options ne sont pas sensibles # +# spaces are ignored. # la casse et les espaces sont ignors.# +# # # +# You must not change the order of # Vous ne devez pas changer l'ordre # +# the sections and their options. # des sections et de leurs options. # +# You must not delete or put into # Vous ne devez pas effacer ou mettre # +# comment any section nor option. # en commentaire une section ou option.# +# # # +# Each option is preceded by a # Chaque option est prcde par un # +# comment which explains its meaning. # commentaire qui explique sa fonction.# +# # # +############################################################################## + + + +[MOUSE] # [SOURIS] + + ; The sensitivity of the mouse can La sensibilit de la souris peut + ; take values from 1 to 64. The prendre des valeurs de 1 64. Plus + ; smaller values, the faster. les valeurs sont petites, plus c'est + ; rapide. + X_sensitivity = 3 ; (default 3) + Y_sensitivity = 3 ; (default 3) + + ; Due to the fact that those stupid A cause du fait que ces imbciles de + ; mouse drivers' makers don't care programmeurs de gestionnaires de + ; if the mouse moves by steps of 2, souris se fichent que votre souris se + ; 4 or even 8 pixels, we have to deplace par pas de 2, 4 ou mme 8 + ; stretch the virtual area of the pixels, nous devons largir la zone + ; mouse and divide coordinates to virtuelle de la souris et diviser les + ; get a one-pixel step motion. coordonnes pour obtenir un pas de 1. + ; (Warning: the mouse movement can (Attention: le dplacement de la + ; be correct in some video modes souris peut tre correct dans certains + ; but not in others... But all the modes vidos mais pas dans d'autres... + ; "Modes X" should behave the same Mais tout les Modes X devraient se + ; way, so you won't have to test comporter de la mme manire, donc + ; them all). vous n'aurez pas tous les tester. + ; A correction factor of 0 means Un facteur de correction de 0 signifie + ; that you are very lucky because que vous avez de la chace car votre + ; your driver doesn't need any driver n'a pas besoin de correction. + ; correction. If you set the Si vous dfinissez le facteur de + ; correction factor to 1, it means correction 1, cela signifie que + ; that your mouse moves by steps of votre souris se dplace par pas de 2 + ; 2 pixels; 2 for 4; 3 for 8, etc... pixels; 2 pour 4; 3 pour 8, etc... + ; If you want to use GrafX2 in a Si vous dsirez lancer GrafX2 dans une + ; Win95 window, you should turn fentre Windows95, vous devriez passer + ; these values to 0 (and increase X ces valeurs 0 (et augmenter les sen- + ; and Y sensitivities above). sibilits X et Y dfinies plus haut). + X_correction_factor = 3 ; (default 3) + Y_correction_factor = 3 ; (default 3) + + ; Aspect of the main cursor (cross) Aspect du curseur principal (croix) + ; 1: Solid 1: Solide + ; 2: Transparent 2: Transparent + ; 3: Thin (solid) 3: Fin (solide) + Cursor_aspect = 1 ; (default 1) + + + +[MENU] # [MENU] + + ; Colors of the menus (the black Couleurs des menus (la couleur noire + ; and the white colors cannot be et la couleur blanche ne peuvent pas + ; modified). tre modifies). + ; Values are in {Red,Green,Blue} Les valeurs sont dans l'ordre {Rouge, + ; order and are between 0 and 63. Vert,Bleu} et vont de 0 63. + Light_color = 42,42,42 ; (default 42,42,42) + Dark_color = 27,27,27 ; (default 27,27,27) + ; + ; Light_color = 24,25,30 ; \_ Nightmare + ; Dark_color = 13,14,19 ; / + ; + ; Light_color = 10,45,28 ; \_ Forest + ; Dark_color = 5,27,12 ; / + ; + ; Light_color = 48,41,26 ; \_ Gold + ; Dark_color = 26,22,15 ; / + ; + ; Light_color = 10,40,55 ; \_ Oceanic + ; Dark_color = 10,20,32 ; / + + ; Aspect ratio and size of the Proportion des menus et de la barre + ; menus and the tool-bar. d'outils. + ; Possible values: Valeurs possibles: + ; 0: Do not adapt (pixels are not 0: Ne pas adapter (les pixels ne sont + ; stretched) pas tirs) + ; 1: Adapt the menus and the tool- 1: Adapter les menus et la barre + ; bar according to the resolution d'outils suivant la rsolution + ; 2: Slightly adapt the ratio of 2: Adapter lgrement les proportions + ; the menus and tool-bar des menus et de la barre d'outils + Menu_ratio = 1 ; (default 1) + + ; Font: Police de caractres (fonte): + ; 1: Classic 1: Classique + ; 2: Fun 2: Fun + Font = 1 ; (default 1) + + + +[FILE_SELECTOR] # [SELECTEUR_DE_FICHIERS] + + ; Show special files and Afficher les fichiers et rpertoires + ; directories (values are 'yes' or spciaux (les valeurs sont 'yes' ou + ; 'no'). 'no'). + Show_hidden_files = no ; (default 'no') + Show_hidden_directories = no ; (default 'no') + Show_system_directories = no ; (default 'no') + + ; Delay before displaying a preview Dlai avant d'afficher une preview + ; in file-selectors (in 18.2th of dans les slecteurs de fichiers (en + ; second). Possible values range 18.2mes de seconde) Les valeurs + ; from 1 to 256. possibles vont de 1 256. + Preview_delay = 8 ; (default 8) + + ; Maximize the preview of the Maximiser la preview des images pour + ; pictures so that it is as big as qu'elle soit aussi grande que + ; possible. If you're not in the possible. + ; same resolution as the picture's Si vous n'tes pas dans la mme rso- + ; one, it can try to correct the lution que celle de l'image, cela peut + ; aspect ratio, but if the picture essayer de corriger les proportions, + ; does not fill the whole screen, mais si l'image ne prend pas tout + ; it can be worse. l'cran, cela peut tre pire. + Maximize_preview = no ; (default 'no') + + ; This option is used to place the Cette option est utilise pour placer + ; selection bar on a filename by la barre de slection sur un nom de + ; typing its first letters. fichier en tapant ses 1res lettres. + ; For example, if you want to find Par exemple, si vous voulez trouver le + ; the "PICTURE.PKM" in a directory fichier "PICTURE.PKM" dans un rper- + ; that also contains "PALETTE.PAL", toire contenant galement le fichier + ; you'll just have to type P and I. "PALETTE.PAL", vous n'aurez qu' taper + ; The different values of "FFF" P puis I. + ; indicate if you want to find the Les different valeurs de "FFF" + ; name in both files and directories indiquent si vous voulez trouvez le nom + ; or just in only one of these: dans les fichiers ET les rpertoires ou + ; 0: files and directories simplement dans l'un OU l'autre. + ; 1: files only 0: fichiers et rpertoires + ; 2: directories only 1: fichiers seulement + ; 2: rpertoires seulement + Find_file_fast = 0 ; (default 0) + + +[LOADING] # [CHARGEMENT] + + ; Automatically set the resolution Passer automatiquement dans la bonne + ; when loading a picture. rsolution lors du chargement d'une + ; You should set this value to image. + ; 'yes' after disabling the video Vous devriez dfinir cette option + ; modes that are not supported by 'yes' aprs avoir inhib les modes + ; your video card or monitor. vido qui ne sont pas supports par + ; votre matriel. + Auto_set_resolution = no ; (default 'no') + + ; If the variable above is set to Si la variable ci-dessus est 'yes', + ; 'yes', this one tells if you want celle-ci indique si vous voulez + ; to set the resolution according dfinir la rsolution suivant: + ; to: 1: les dimensions de "l'cran + ; 1: the internal "original screen" d'origine" internes l'image + ; dimensions of the picture 2: les vritables dimensions de + ; 2: the actual dimensions of the l'image + ; picture + Set_resolution_according_to = 1 ; (default 1) + + ; If you load a picture with a Si vous chargez une image ayant une + ; palette of less than 256 colors, palette de moins de 256 couleurs, + ; this option defines if you want cette option indique si vous souhaitez + ; to clear the palette or to keep effacer la palette ou bien conserver + ; the colors of the previous les couleurs de l'image prcdente qui + ; picture that are over the number se situent au-del du nombre de la + ; of colors of the new picture. nouvelle image. + ; For example, if you load a Par exemple, si vous chargez une image + ; 32-color picture, the colors 32 de 32 couleurs, les couleurs 32 255 + ; to 255 will be set to black if seront passes en noir si cette option + ; this option is set to 'yes', or est 'yes', ou bien elles resteront + ; they will be kept unchanged if inchanges si elle est 'no'. + ; this option is set to 'no'. + Clear_palette = yes ; (default 'yes') + + +[MISCELLANEOUS] # [DIVERS] + + ; Draw the limits of the picture. Afficher les limites de l'image + Draw_limits = yes ; (default 'yes') + + ; Adjust the brush grabbing in Ajuster la capture de brosse en mode + ; "grid" mode. "grille". + Adjust_brush_pick = yes ; (default 'yes') + + ; Coordinates: Coordonnes: + ; 1: Relative 1: Relatives + ; 2: Absolute 2: Absolues + Coordinates = 1 ; (default 1) + + ; Create a backup file when saving. Crer un fichier backup lors des + ; sauvegardes. + Backup = no ; (default 'no') + + ; Number of pages stored in memory Nombre de pages stockes en mmoire + ; for "undoing". destines annuler les dernires + ; Values are between 1 and 99. modifications. Valeurs entre 1 et 99. + Undo_pages = 1 ; (default 1) + + ; Speed of the scroll-bars (in VBLs Vitesse des barre de dfilement (en + ; waited) while clicking with the VBLs attendus) lorsque l'un des + ; left or right button of the mouse. boutons de la souris est enfonc. + ; Values can be between 1 and 255. Les valeurs sont comprises entre 1 et + ; The bigger values, the slower. 255. Plus elles sont grandes, plus + ; c'est lent. + Gauges_scrolling_speed_Left = 10 ; (default 10) + Gauges_scrolling_speed_Right = 3 ; (default 3) + + ; Automatically save the configu- Enregistre automatiquement la configu- + ; ration when exiting the program. ration lorsqu'on quitte le programme. + Auto_save = yes ; (default 'yes') + + ; Maximum number of vertices used Nombre maximum de vertex utiliss dans + ; in filled polygons and polyforms, les polygnes et polyformes pleins, et + ; and lasso. Possible values range le lasso. Les valeurs possibles vont + ; from 2 to 16384. de 2 16384. + ; Each vertex takes 4 bytes. Chaque vertex prend 4 octets. + Vertices_per_polygon = 1024 ; (default 1024) + + ; Automatically zoom into the Zoomer automatiquement la zone pointe + ; pointed area when you press the par la souris lorsque vous appuyez sur + ; short-key of the Magnifier button la touche de raccourci de la loupe. + ; while being above the picture. + Fast_zoom = yes ; (default 'yes') + + ; Separate the colors in the tool- Sparer les couleurs dans la barre + ; bar by a black squaring. d'outils par un quadrillage noir. + Separate_colors = yes ; (default 'yes') + + ; Initial value of the feedback for Valeur initiale du "feedback" pour les + ; the drawing modes (cf. docs). modes de dessin (cf. docs). + FX_feedback = yes ; (default 'yes') + + ; When you reduce the palette or Si vous rduisez la palette ou "zappez" + ; "zap" some colors out of it, it is quelques couleurs, il est possible + ; possible that there are not enough qu'il ne reste pas assez de couleurs + ; colors left to draw the menus. pour afficher les menus. Mettre cette + ; Switching the following variable variable 'yes' ramnera automatiquent + ; on will bring back the colors of les couleurs du menu s'il reste moins + ; the menu if there are less than 4 de 4 couleurs aprs une "rduction" ou + ; colors left after "reducing" or un "zapping". + ; "zapping". + Safety_colors = yes ; (default 'yes') + + ; Display a message at startup Afficher un message au dmarrage + ; telling the version number of the indiquant le numro de version du + ; program. programme. + Opening_message = yes ; (default 'yes') + + ; Take the Stencil into account when Prendre le Stencil en compte lorsqu'on + ; clearing the image. efface l'image. + Clear_with_stencil = yes ; (default 'yes') + + ; Directly set the discontinuous Passer automatiquement en mode de + ; freehand drawing mode after brush dessin discontinu aprs la prise d'une + ; grabbing. brosse. + Auto_discontinuous = no ; (default 'no') + + ; Save the screen dimensions in GIF Sauver les dimensions de l'cran dans + ; files. If you want to read these les fichiers GIF. Si vous voulez lire + ; files with Photoshop or Alchemy, ces fichiers avec Photoshop ou Alchemy, + ; and maybe some other programs, you et peut-tre d'autres programmes, vous + ; must set this option to 'no'. devez mettre cette option 'no'. + Save_screen_size_in_GIF = no ; (default 'no') + + ; Automaticaly count the number of Compter automatiquement le nombre de + ; different colors used when opening couleurs diffrentes utilises lors de + ; the palette editor window. (Set it d'ouverture de la fentre d'dition de + ; to 'no' if you have a slow PC or la palette. (Mettez-le 'no' si vous + ; if you edit huge pictures) avez un PC lent ou bien si vous ditez + ; d'normes images). + Auto_nb_colors_used = yes ; (default 'yes') + + ; Number of the default video mode Numro du mode vido par dfaut au + ; at startup (see the list by typing dmarrage (voir la liste en tapant + ; "gfx2 /?" at the DOS prompt). "gfx2 /?" sur la ligne de commande). + Default_video_mode = 0 ; (default 0) diff --git a/gfx2.gif b/gfx2.gif new file mode 100644 index 0000000000000000000000000000000000000000..bd327aab5d28e2cc4dc48c0d9a31df8fa6248a45 GIT binary patch literal 1149 zcmZ?wbh9u|RA5kGn9cwK4Pe{=rW$~}1`s%K;J_cC_#cKpUR~8-yg*hG*AG!9j zt4bLhSg^#CNlG=&q#@yn#{?Ee3x&!D2N@^x1mu|*Y*zK0ZXkG0C-U>NlT$=vccpv~ zUg9&!CHK)4%}dWcmPPQY$W$%J4qR_JQSWc&r*v;NQ_EGg0%0#gH>ob1_2<@AwTM;e z4 zB)+6>o2aOEEK+#w+3RkmtKB*#>ZhFXQOz&AVDTkx?W*~^-gVD5_;AzA{#ZMYO9dcdJ>PvG%s4IdR%7I^+u+!`0i!N$taq!#Fr5F#uq@Gwn`&my62>%!-W cO)`hl7jOV literal 0 HcmV?d00001 diff --git a/gfx2.ico b/gfx2.ico new file mode 100644 index 0000000000000000000000000000000000000000..0c78ce5e33be2556f2b9e548fe556e49264ba2a6 GIT binary patch literal 766 zcmZuvEpNjx5WQ}xI#4A;qbuCMXi(8W$XGy8N}|E4VA4XS1VqYT3TV=Rlkyje+JUJX znhYv=?>PfgwR3#--Fx?8$08$)+3Z#*?^hysSRXKFm?7p!JZO;&*#D9N1d?UL0*$TI zb&ZvPb)Q(v9VP}{R2Opd1Q~qXMHAIHj_4RSkjU5EzBRPtn26t*&X6!xO62cKtr`&G zxGy!1f?kb*f2!JZ_4~3aE644tvWbGuC_czb-<>rIQotqca}QO^Hwst_hCx&-;s`~K zD)24Q$DuR1A`}8x#80b@4k-wWeCTfl2aDiHxhpcj;;B}hF&hoZ7I{?NxhA*H^issX zZrEf<#{z}4b4`-qCA3ii_dvoTO;gxaS-{@PG-(O51D9bkz#tTbDaz1K+Ey{vIHa{_ z*d(M&KOOL3m4JcH4@10vNWfU~m@Z%Nyh_>xeefR8VQ^Zn6TrAAHWmi<^K_(%-+ekA zYq$HW=4X+61Ns+kW-oGGFeh_Q_Cqb! GMDz~;ekG0o literal 0 HcmV?d00001 diff --git a/gfx2.ini b/gfx2.ini new file mode 100644 index 00000000..ff02bc72 --- /dev/null +++ b/gfx2.ini @@ -0,0 +1,289 @@ +###### GrafX2 initialization file ###### Fichier d'initialisation de GrafX2 ## +# # # # +# You may modify this file with any # Vous pouvez modifier ce fichier avec # +# standard ASCII text editor. # n'importe quel diteur de texte # +# # ASCII standard. # +# # # +# Comments are preceded by ';' or # Les commentaires sont prcds par # +# '#'. # ';' ou '#'. # +# # # +# Options are not case sensitive and # Les options ne sont pas sensibles # +# spaces are ignored. # la casse et les espaces sont ignors.# +# # # +# You must not change the order of # Vous ne devez pas changer l'ordre # +# the sections and their options. # des sections et de leurs options. # +# You must not delete or put into # Vous ne devez pas effacer ou mettre # +# comment any section nor option. # en commentaire une section ou option.# +# # # +# Each option is preceded by a # Chaque option est prcde par un # +# comment which explains its meaning. # commentaire qui explique sa fonction.# +# # # +############################################################################## + + + +[MOUSE] # [SOURIS] + + ; The sensitivity of the mouse can La sensibilit de la souris peut + ; take values from 1 to 64. The prendre des valeurs de 1 64. Plus + ; smaller values, the faster. les valeurs sont petites, plus c'est + ; rapide. + X_sensitivity = 3 ; (default 3) + Y_sensitivity = 3 ; (default 3) + + ; Due to the fact that those stupid A cause du fait que ces imbciles de + ; mouse drivers' makers don't care programmeurs de gestionnaires de + ; if the mouse moves by steps of 2, souris se fichent que votre souris se + ; 4 or even 8 pixels, we have to deplace par pas de 2, 4 ou mme 8 + ; stretch the virtual area of the pixels, nous devons largir la zone + ; mouse and divide coordinates to virtuelle de la souris et diviser les + ; get a one-pixel step motion. coordonnes pour obtenir un pas de 1. + ; (Warning: the mouse movement can (Attention: le dplacement de la + ; be correct in some video modes souris peut tre correct dans certains + ; but not in others... But all the modes vidos mais pas dans d'autres... + ; "Modes X" should behave the same Mais tout les Modes X devraient se + ; way, so you won't have to test comporter de la mme manire, donc + ; them all). vous n'aurez pas tous les tester. + ; A correction factor of 0 means Un facteur de correction de 0 signifie + ; that you are very lucky because que vous avez de la chace car votre + ; your driver doesn't need any driver n'a pas besoin de correction. + ; correction. If you set the Si vous dfinissez le facteur de + ; correction factor to 1, it means correction 1, cela signifie que + ; that your mouse moves by steps of votre souris se dplace par pas de 2 + ; 2 pixels; 2 for 4; 3 for 8, etc... pixels; 2 pour 4; 3 pour 8, etc... + ; If you want to use GrafX2 in a Si vous dsirez lancer GrafX2 dans une + ; Win95 window, you should turn fentre Windows95, vous devriez passer + ; these values to 0 (and increase X ces valeurs 0 (et augmenter les sen- + ; and Y sensitivities above). sibilits X et Y dfinies plus haut). + X_correction_factor = 3 ; (default 3) + Y_correction_factor = 3 ; (default 3) + + ; Aspect of the main cursor (cross) Aspect du curseur principal (croix) + ; 1: Solid 1: Solide + ; 2: Transparent 2: Transparent + ; 3: Thin (solid) 3: Fin (solide) + Cursor_aspect = 1 ; (default 1) + + + +[MENU] # [MENU] + + ; Colors of the menus (the black Couleurs des menus (la couleur noire + ; and the white colors cannot be et la couleur blanche ne peuvent pas + ; modified). tre modifies). + ; Values are in {Red,Green,Blue} Les valeurs sont dans l'ordre {Rouge, + ; order and are between 0 and 63. Vert,Bleu} et vont de 0 63. + Light_color = 42,42,42 ; (default 42,42,42) + Dark_color = 27,27,27 ; (default 27,27,27) + ; + ; Light_color = 24,25,30 ; \_ Nightmare + ; Dark_color = 13,14,19 ; / + ; + ; Light_color = 10,45,28 ; \_ Forest + ; Dark_color = 5,27,12 ; / + ; + ; Light_color = 48,41,26 ; \_ Gold + ; Dark_color = 26,22,15 ; / + ; + ; Light_color = 10,40,55 ; \_ Oceanic + ; Dark_color = 10,20,32 ; / + + ; Aspect ratio and size of the Proportion des menus et de la barre + ; menus and the tool-bar. d'outils. + ; Possible values: Valeurs possibles: + ; 0: Do not adapt (pixels are not 0: Ne pas adapter (les pixels ne sont + ; stretched) pas tirs) + ; 1: Adapt the menus and the tool- 1: Adapter les menus et la barre + ; bar according to the resolution d'outils suivant la rsolution + ; 2: Slightly adapt the ratio of 2: Adapter lgrement les proportions + ; the menus and tool-bar des menus et de la barre d'outils + Menu_ratio = 1 ; (default 1) + + ; Font: Police de caractres (fonte): + ; 1: Classic 1: Classique + ; 2: Fun 2: Fun + Font = 1 ; (default 1) + + + +[FILE_SELECTOR] # [SELECTEUR_DE_FICHIERS] + + ; Show special files and Afficher les fichiers et rpertoires + ; directories (values are 'yes' or spciaux (les valeurs sont 'yes' ou + ; 'no'). 'no'). + Show_hidden_files = no ; (default 'no') + Show_hidden_directories = no ; (default 'no') + Show_system_directories = no ; (default 'no') + + ; Delay before displaying a preview Dlai avant d'afficher une preview + ; in file-selectors (in 18.2th of dans les slecteurs de fichiers (en + ; second). Possible values range 18.2mes de seconde) Les valeurs + ; from 1 to 256. possibles vont de 1 256. + Preview_delay = 8 ; (default 8) + + ; Maximize the preview of the Maximiser la preview des images pour + ; pictures so that it is as big as qu'elle soit aussi grande que + ; possible. If you're not in the possible. + ; same resolution as the picture's Si vous n'tes pas dans la mme rso- + ; one, it can try to correct the lution que celle de l'image, cela peut + ; aspect ratio, but if the picture essayer de corriger les proportions, + ; does not fill the whole screen, mais si l'image ne prend pas tout + ; it can be worse. l'cran, cela peut tre pire. + Maximize_preview = no ; (default 'no') + + ; This option is used to place the Cette option est utilise pour placer + ; selection bar on a filename by la barre de slection sur un nom de + ; typing its first letters. fichier en tapant ses 1res lettres. + ; For example, if you want to find Par exemple, si vous voulez trouver le + ; the "PICTURE.PKM" in a directory fichier "PICTURE.PKM" dans un rper- + ; that also contains "PALETTE.PAL", toire contenant galement le fichier + ; you'll just have to type P and I. "PALETTE.PAL", vous n'aurez qu' taper + ; The different values of "FFF" P puis I. + ; indicate if you want to find the Les different valeurs de "FFF" + ; name in both files and directories indiquent si vous voulez trouvez le nom + ; or just in only one of these: dans les fichiers ET les rpertoires ou + ; 0: files and directories simplement dans l'un OU l'autre. + ; 1: files only 0: fichiers et rpertoires + ; 2: directories only 1: fichiers seulement + ; 2: rpertoires seulement + Find_file_fast = 0 ; (default 0) + + +[LOADING] # [CHARGEMENT] + + ; Automatically set the resolution Passer automatiquement dans la bonne + ; when loading a picture. rsolution lors du chargement d'une + ; You should set this value to image. + ; 'yes' after disabling the video Vous devriez dfinir cette option + ; modes that are not supported by 'yes' aprs avoir inhib les modes + ; your video card or monitor. vido qui ne sont pas supports par + ; votre matriel. + Auto_set_resolution = no ; (default 'no') + + ; If the variable above is set to Si la variable ci-dessus est 'yes', + ; 'yes', this one tells if you want celle-ci indique si vous voulez + ; to set the resolution according dfinir la rsolution suivant: + ; to: 1: les dimensions de "l'cran + ; 1: the internal "original screen" d'origine" internes l'image + ; dimensions of the picture 2: les vritables dimensions de + ; 2: the actual dimensions of the l'image + ; picture + Set_resolution_according_to = 1 ; (default 1) + + ; If you load a picture with a Si vous chargez une image ayant une + ; palette of less than 256 colors, palette de moins de 256 couleurs, + ; this option defines if you want cette option indique si vous souhaitez + ; to clear the palette or to keep effacer la palette ou bien conserver + ; the colors of the previous les couleurs de l'image prcdente qui + ; picture that are over the number se situent au-del du nombre de la + ; of colors of the new picture. nouvelle image. + ; For example, if you load a Par exemple, si vous chargez une image + ; 32-color picture, the colors 32 de 32 couleurs, les couleurs 32 255 + ; to 255 will be set to black if seront passes en noir si cette option + ; this option is set to 'yes', or est 'yes', ou bien elles resteront + ; they will be kept unchanged if inchanges si elle est 'no'. + ; this option is set to 'no'. + Clear_palette = yes ; (default 'yes') + + +[MISCELLANEOUS] # [DIVERS] + + ; Draw the limits of the picture. Afficher les limites de l'image + Draw_limits = yes ; (default 'yes') + + ; Adjust the brush grabbing in Ajuster la capture de brosse en mode + ; "grid" mode. "grille". + Adjust_brush_pick = yes ; (default 'yes') + + ; Coordinates: Coordonnes: + ; 1: Relative 1: Relatives + ; 2: Absolute 2: Absolues + Coordinates = 1 ; (default 1) + + ; Create a backup file when saving. Crer un fichier backup lors des + ; sauvegardes. + Backup = no ; (default 'no') + + ; Number of pages stored in memory Nombre de pages stockes en mmoire + ; for "undoing". destines annuler les dernires + ; Values are between 1 and 99. modifications. Valeurs entre 1 et 99. + Undo_pages = 1 ; (default 1) + + ; Speed of the scroll-bars (in VBLs Vitesse des barre de dfilement (en + ; waited) while clicking with the VBLs attendus) lorsque l'un des + ; left or right button of the mouse. boutons de la souris est enfonc. + ; Values can be between 1 and 255. Les valeurs sont comprises entre 1 et + ; The bigger values, the slower. 255. Plus elles sont grandes, plus + ; c'est lent. + Gauges_scrolling_speed_Left = 10 ; (default 10) + Gauges_scrolling_speed_Right = 3 ; (default 3) + + ; Automatically save the configu- Enregistre automatiquement la configu- + ; ration when exiting the program. ration lorsqu'on quitte le programme. + Auto_save = yes ; (default 'yes') + + ; Maximum number of vertices used Nombre maximum de vertex utiliss dans + ; in filled polygons and polyforms, les polygnes et polyformes pleins, et + ; and lasso. Possible values range le lasso. Les valeurs possibles vont + ; from 2 to 16384. de 2 16384. + ; Each vertex takes 4 bytes. Chaque vertex prend 4 octets. + Vertices_per_polygon = 1024 ; (default 1024) + + ; Automatically zoom into the Zoomer automatiquement la zone pointe + ; pointed area when you press the par la souris lorsque vous appuyez sur + ; short-key of the Magnifier button la touche de raccourci de la loupe. + ; while being above the picture. + Fast_zoom = yes ; (default 'yes') + + ; Separate the colors in the tool- Sparer les couleurs dans la barre + ; bar by a black squaring. d'outils par un quadrillage noir. + Separate_colors = yes ; (default 'yes') + + ; Initial value of the feedback for Valeur initiale du "feedback" pour les + ; the drawing modes (cf. docs). modes de dessin (cf. docs). + FX_feedback = yes ; (default 'yes') + + ; When you reduce the palette or Si vous rduisez la palette ou "zappez" + ; "zap" some colors out of it, it is quelques couleurs, il est possible + ; possible that there are not enough qu'il ne reste pas assez de couleurs + ; colors left to draw the menus. pour afficher les menus. Mettre cette + ; Switching the following variable variable 'yes' ramnera automatiquent + ; on will bring back the colors of les couleurs du menu s'il reste moins + ; the menu if there are less than 4 de 4 couleurs aprs une "rduction" ou + ; colors left after "reducing" or un "zapping". + ; "zapping". + Safety_colors = yes ; (default 'yes') + + ; Display a message at startup Afficher un message au dmarrage + ; telling the version number of the indiquant le numro de version du + ; program. programme. + Opening_message = yes ; (default 'yes') + + ; Take the Stencil into account when Prendre le Stencil en compte lorsqu'on + ; clearing the image. efface l'image. + Clear_with_stencil = yes ; (default 'yes') + + ; Directly set the discontinuous Passer automatiquement en mode de + ; freehand drawing mode after brush dessin discontinu aprs la prise d'une + ; grabbing. brosse. + Auto_discontinuous = no ; (default 'no') + + ; Save the screen dimensions in GIF Sauver les dimensions de l'cran dans + ; files. If you want to read these les fichiers GIF. Si vous voulez lire + ; files with Photoshop or Alchemy, ces fichiers avec Photoshop ou Alchemy, + ; and maybe some other programs, you et peut-tre d'autres programmes, vous + ; must set this option to 'no'. devez mettre cette option 'no'. + Save_screen_size_in_GIF = no ; (default 'no') + + ; Automaticaly count the number of Compter automatiquement le nombre de + ; different colors used when opening couleurs diffrentes utilises lors de + ; the palette editor window. (Set it d'ouverture de la fentre d'dition de + ; to 'no' if you have a slow PC or la palette. (Mettez-le 'no' si vous + ; if you edit huge pictures) avez un PC lent ou bien si vous ditez + ; d'normes images). + Auto_nb_colors_used = yes ; (default 'yes') + + ; Number of the default video mode Numro du mode vido par dfaut au + ; at startup (see the list by typing dmarrage (voir la liste en tapant + ; "gfx2 /?" at the DOS prompt). "gfx2 /?" sur la ligne de commande). + Default_video_mode = 0 ; (default 0) diff --git a/gfx2_fra.cfg b/gfx2_fra.cfg new file mode 100644 index 0000000000000000000000000000000000000000..d14370a561cbdc644c36ec830194a2b18c872a2d GIT binary patch literal 10286 zcmeI2$x;+S6h&`U1BwHKC?KM?t>T1jx8giNg99om4j_Uk&gFnOfzt*e)SY3uGr};! zPtl#9fjgJ}!SlS|u(F9hapP6yt<3wfb4B0r6R{?wKe5y=Q=~x{>om;i46IUrWUAI6 ztkG$>Kxg1WeW^0l>N{MduW+%x!6o__o0jS`tkZK?uNSaE`*Ca3e&#OIQFN2~;BsAr zD|7@l>oQMUlt;HJk6x)fbKBHGWtBRpwBux2tp@ZOtwXP6hB2pw$~s(41vR19tBBs9 zA`Tl>q|%{c&a_Eo>YG)jzC~r~TUDmMO--!7Qw6wPMOaj^+O$Ihj4x?`k!99y+No~1 zOCwae)PvrwE9gC%WY%6yGHV~JF!o%aen17@bx;M~a!7?5(_vM3dPJiZeG;=-gWL0QnjHYek>cd-OSd zfP?JMbe?^iE@%r+FOrApk~X1-7;75F$#hvI);U6dOjk(VG^%#SjIj^XRb4`l(_7Ou z)uXSoGvg=?p>ME1(@hPdZ|OQKzpV*)N8?oP(r42>HKP;Gi0QuS&=2UR=^;HgJz`I$ zNmgoltdl&Q(s}qqpYVCAm++b1!RMNWFEj(EIU}YS&Wq`#Rx$pS+Td$?WqL!eIN_a< zdZJ&d^hEQHzYay9&e7)RbR>?{@xw9iPz>4~U5=5slDJjkR*73BZk4!I;#P@UB@tGM zTP1GAUxN z{yG$aI!CADS~NEsr>=guns+6i(eCJSjKp*K9N@Q~iyQOeRtSF~fsjB(6NthMkkQVE zdp{)L34|LUoP&@+mJ5N?1hcR%bsBoJ +#include "struct.h" + +GLOBAL struct S_Config +{ + byte Fonte; + int Lire_les_fichiers_caches; + int Lire_les_repertoires_caches; + int Lire_les_repertoires_systemes; + byte Afficher_limites_image; + byte Curseur; + byte Maximize_preview; + byte Auto_set_res; + byte Coords_rel; + byte Backup; + byte Adjust_brush_pick; + byte Auto_save; + byte Nb_pages_Undo; + byte Indice_Sensibilite_souris_X; + byte Indice_Sensibilite_souris_Y; + byte Mouse_Facteur_de_correction_X; + byte Mouse_Facteur_de_correction_Y; + byte Valeur_tempo_jauge_gauche; + byte Valeur_tempo_jauge_droite; + long Chrono_delay; + struct Composantes Coul_menu_pref[4]; + int Nb_max_de_vertex_par_polygon; + byte Clear_palette; + byte Set_resolution_according_to; + byte Ratio; + byte Fast_zoom; + byte Find_file_fast; + byte Couleurs_separees; + byte FX_Feedback; + byte Safety_colors; + byte Opening_message; + byte Clear_with_stencil; + byte Auto_discontinuous; + byte Taille_ecran_dans_GIF; + byte Auto_nb_used; + byte Resolution_par_defaut; +} Config; + + // Tableau des touches spciales +GLOBAL word Config_Touche[NB_TOUCHES_SPECIALES]; + + +GLOBAL struct S_Mode_video +{ + short Largeur; + short Hauteur; + byte Mode; + word Facteur_X; + word Facteur_Y; + char Ratio[5]; + signed char Refresh; // <0 => entrelac + word Mode_VESA_de_base; + void * Pointeur; + byte Etat; // 0:Cool 1:OK ; 2:Bof ; 3:Naze ; si on rajoute +128 => incompatible +}; +GLOBAL struct S_Mode_video Mode_video[NB_MODES_VIDEO]; + + +GLOBAL struct +{ + byte Granularite; // Facteur de gestion de la granularit + byte Code_fenetres; // Utilisation des fentres: 0=AA 1=BB 2=AB 3=BA + byte * WinFuncPtr; + byte * Adresse_physique_LFB; // Si = 0 => Pas de LFB + dword Taille_LFB; // Taille de la mmoire LFB +} VESA_Mode_Infos[4]; + + + + // Palette par dfaut + +GLOBAL T_Palette Palette_defaut; + + // Couleurs du menu + +GLOBAL byte CM_Noir; +GLOBAL byte CM_Fonce; +GLOBAL byte CM_Clair; +GLOBAL byte CM_Blanc; +GLOBAL byte CM_Trans; +GLOBAL struct Composantes Coul_menu_pref[4]; + + // Etat des entres + +GLOBAL word Mouse_X; // Abscisse de la souris +GLOBAL word Mouse_Y; // Ordonne de la souris +GLOBAL byte Mouse_K; // Etat des boutons de la souris +GLOBAL word Touche; +GLOBAL Uint8* Etat_Du_Clavier; // Scancode de la touche en cours et etat des touches de ctrl +GLOBAL byte Touche_ASCII; // Code ASCII de la touche en cours + +GLOBAL byte Mouse_Facteur_de_correction_X; +GLOBAL byte Mouse_Facteur_de_correction_Y; + +GLOBAL byte Autoriser_changement_de_couleur_pendant_operation; + + // Donnes sur le curseur + +GLOBAL byte Forme_curseur; +GLOBAL byte Forme_curseur_avant_fenetre; // Forme du curseur avant l'ouverture d'une fentre +GLOBAL byte Forcer_affichage_curseur; // Forcer l'affichage du curseur au prochain Get_input(); +GLOBAL byte Cacher_curseur; +GLOBAL byte Curseur_dans_menu; // Boolen "Le curseur se trouve dans le menu" +GLOBAL byte Curseur_dans_menu_precedent; // Boolen "Le curseur se trouvait prcdemment dans le menu" +GLOBAL word Curseur_Decalage_X[NB_SPRITES_CURSEUR]; // Coordonnes X du point sensible de curseurs en sprite +GLOBAL word Curseur_Decalage_Y[NB_SPRITES_CURSEUR]; // Coordonnes Y du point sensible de curseurs en sprite +GLOBAL byte SPRITE_CURSEUR[NB_SPRITES_CURSEUR][HAUTEUR_SPRITE_CURSEUR][LARGEUR_SPRITE_CURSEUR]; // Dessins des sprites de curseur +GLOBAL byte FOND_CURSEUR[HAUTEUR_SPRITE_CURSEUR][LARGEUR_SPRITE_CURSEUR]; // Contenu du dessous du curseur + + // Donnes sur le pinceau + +GLOBAL byte Pinceau_Forme; +GLOBAL byte Pinceau_Forme_avant_fill; +GLOBAL byte Pinceau_Forme_avant_pipette; +GLOBAL byte Pinceau_Forme_avant_lasso; +GLOBAL byte Cacher_pinceau; +GLOBAL short Pinceau_X; +GLOBAL short Pinceau_Y; +GLOBAL byte SPRITE_PINCEAU [NB_SPRITES_PINCEAU][HAUTEUR_PINCEAU][LARGEUR_PINCEAU]; +GLOBAL word Pinceau_predefini_Largeur[NB_SPRITES_PINCEAU]; +GLOBAL word Pinceau_predefini_Hauteur[NB_SPRITES_PINCEAU]; +GLOBAL byte Pinceau_Type[NB_SPRITES_PINCEAU]; +GLOBAL word Pinceau_predefini_Decalage_X[NB_SPRITES_PINCEAU]; +GLOBAL word Pinceau_predefini_Decalage_Y[NB_SPRITES_PINCEAU]; +GLOBAL byte * Pinceau_Sprite; +GLOBAL short Pinceau_Largeur; +GLOBAL short Pinceau_Hauteur; +GLOBAL short Pinceau_Decalage_X; +GLOBAL short Pinceau_Decalage_Y; + + // Commandes graphiques + +GLOBAL fonction_afficheur Pixel; // Affiche un point l'cran +GLOBAL fonction_afficheur Pixel_dans_menu;// Affiche un point dans le menu (ou pas si le menu est invisible) +GLOBAL fonction_lecteur Lit_pixel; // Teste la couleur d'un pixel dans l'cran +GLOBAL fonction_effaceur Clear_screen; // Efface rapidement tout l'cran (en faisant attention de ne pas effacer le menu) +GLOBAL fonction_display Display_screen; // Affiche rapidement tout l'cran (en faisant attention de ne pas effacer le menu) +GLOBAL fonction_block Block; // Affiche rapidement un bloc l'cran +GLOBAL fonction_afficheur Pixel_Preview_Normal; // Affiche un point de l'image l'cran en mode normal (pas en mode loupe) +GLOBAL fonction_afficheur Pixel_Preview_Loupe; // Affiche un point de l'image l'cran en mode loupe +GLOBAL fonction_afficheur Pixel_Preview; // Affiche un point de l'image l'cran en fonction de l'tat du mode loupe +GLOBAL fonction_Ligne_XOR Ligne_horizontale_XOR;// Affiche une ligne horizontale en XOR (pour placer la loupe) +GLOBAL fonction_Ligne_XOR Ligne_verticale_XOR; // Affiche une ligne verticale en XOR (pour placer la loupe) +GLOBAL fonction_display_brush_Color Display_brush_Color; // Affiche une partie de la brosse en couleur +GLOBAL fonction_display_brush_Mono Display_brush_Mono; // Affiche une partie de la brosse en monochrome +GLOBAL fonction_display_brush_Color Clear_brush; // Efface la partie de la brosse affiche l'cran +GLOBAL fonction_remap Remap_screen; // Remappe une partie de l'cran avec les nouvelles couleurs du menu +GLOBAL fonction_procsline Afficher_ligne; // Afficher une ligne +GLOBAL fonction_procsline Lire_ligne; // Afficher ou lire une ligne +GLOBAL fonction_display_zoom Display_zoomed_screen; // Affiche rapidement toute la partie zoome l'cran (en faisant attention de ne pas effacer le menu) +GLOBAL fonction_display_brush_Color_zoom Display_brush_Color_zoom; +GLOBAL fonction_display_brush_Mono_zoom Display_brush_Mono_zoom; +GLOBAL fonction_display_brush_Color_zoom Clear_brush_zoom; + + // Donnes sur les dimensions de l'cran + +GLOBAL int Resolution_actuelle; // Rsolution graphique courante +GLOBAL short Ecran_original_X; // |_ Dimensions de l'cran d'origine de +GLOBAL short Ecran_original_Y; // | l'image qui vient d'tre charge. +GLOBAL short Largeur_ecran; // Largeur de l'cran +GLOBAL short Hauteur_ecran; // Hauteur de l'cran +GLOBAL short Limite_Haut; // | +GLOBAL short Limite_Bas; // |_ Limites dans lesquelles +GLOBAL short Limite_Gauche; // | on peut crire +GLOBAL short Limite_Droite; // | +GLOBAL short Limite_visible_Bas; // |_ Derniers points visibles +GLOBAL short Limite_visible_Droite; // | " l'image" + +GLOBAL short Limite_Haut_Zoom; // | +GLOBAL short Limite_Bas_Zoom; // |_ Limites dans lesquelles on peut +GLOBAL short Limite_Gauche_Zoom; // | crire dans la partie zoome +GLOBAL short Limite_Droite_Zoom; // | +GLOBAL short Limite_visible_Bas_Zoom; // |_ Derniers points visibles " +GLOBAL short Limite_visible_Droite_Zoom; // | l'image" dans la partie zoome + +GLOBAL byte * Buffer_de_ligne_horizontale; // Buffer d'affichage de lignes + + // Donnes sur l'image actuelle: + +GLOBAL byte * Principal_Ecran; // Ecran virtuel courant +GLOBAL T_Palette Principal_Palette; // Palette de l'cran en cours + +GLOBAL byte Principal_Image_modifiee; // L'image courante a t modifie +GLOBAL short Principal_Largeur_image; // Largeur de l'image dans laquelle l'utilisateur dsire travailler +GLOBAL short Principal_Hauteur_image; // Hauteur de l'image dans laquelle l'utilisateur dsire travailler +GLOBAL short Principal_Decalage_X; // Dcalage en X de l'cran par rapport au dbut de l'image +GLOBAL short Principal_Decalage_Y; // Dcalage en Y de l'cran par rapport au dbut de l'image +GLOBAL short Ancien_Principal_Decalage_X; +GLOBAL short Ancien_Principal_Decalage_Y; + +GLOBAL char Principal_Repertoire_fichier[256]; // |_ Nom complet = +GLOBAL char Principal_Nom_fichier[13]; // | Repertoire_fichier+"\"+Nom_fichier +GLOBAL byte Principal_Format_fichier; // Format auquel il faut lire et crire le fichier +GLOBAL byte Principal_Format; // Format du fileselect +GLOBAL short Principal_File_list_Position; // Dbut de la partie affiche dans la liste de fichiers +GLOBAL short Principal_File_list_Decalage; // Dcalage de la barre de slection dans le fileselector +GLOBAL char Principal_Repertoire_courant[256]; // Rpertoire actuel sur disque +GLOBAL char Principal_Commentaire[TAILLE_COMMENTAIRE+1]; // Commentaire de l'image + +GLOBAL short Principal_Split; // Position en X du bord gauche du split de la loupe +GLOBAL short Principal_X_Zoom; // (Menu_Facteur_X) + Position en X du bord droit du split de la loupe +GLOBAL float Principal_Proportion_split; // Proportion de la zone non-zoome par rapport l'cran + + // Donnes sur le brouillon: + +GLOBAL byte * Brouillon_Ecran; // Ecran virtuel brouillon +GLOBAL T_Palette Brouillon_Palette; // Palette de l'cran de brouillon + +GLOBAL byte Brouillon_Image_modifiee; // Le brouillon a t modifi +GLOBAL short Brouillon_Largeur_image; // Largeur du brouillon dans laquelle l'utilisateur dsire travailler +GLOBAL short Brouillon_Hauteur_image; // Hauteur du brouillon dans laquelle l'utilisateur dsire travailler +GLOBAL short Brouillon_Decalage_X; // Dcalage en X du brouillon par rapport au dbut de l'image +GLOBAL short Brouillon_Decalage_Y; // Dcalage en Y du brouillon par rapport au dbut de l'image +GLOBAL short Ancien_Brouillon_Decalage_X; +GLOBAL short Ancien_Brouillon_Decalage_Y; + +GLOBAL char Brouillon_Repertoire_fichier[256]; // |_ Nom complet = +GLOBAL char Brouillon_Nom_fichier[13]; // | Repertoire_fichier+"\"+Nom_fichier +GLOBAL byte Brouillon_Format_fichier; // Format auquel il faut lire et crire le fichier +GLOBAL byte Brouillon_Format; // Format du fileselect +GLOBAL short Brouillon_File_list_Position; // Dbut de la partie affiche dans la liste de fichiers +GLOBAL short Brouillon_File_list_Decalage; // Dcalage de la barre de slection dans le fileselector +GLOBAL char Brouillon_Repertoire_courant[256]; // Rpertoire actuel sur disque +GLOBAL char Brouillon_Commentaire[TAILLE_COMMENTAIRE+1]; // Commentaire de l'image + +GLOBAL short Brouillon_Split; // Position en X du bord gauche du split de la loupe +GLOBAL short Brouillon_X_Zoom; // (Menu_Facteur_X) + Position en X du bord droit du split de la loupe +GLOBAL float Brouillon_Proportion_split; // Proportion de la zone non-zoome par rapport l'cran + +GLOBAL byte Brouillon_Loupe_Mode; // On est en mode loupe dans le brouillon +GLOBAL word Brouillon_Loupe_Facteur; // Facteur de zoom dans le brouillon +GLOBAL word Brouillon_Loupe_Hauteur; // Largeur de la fentre de zoom dans le brouillon +GLOBAL word Brouillon_Loupe_Largeur; // Hauteur de la fentre de zoom dans le brouillon +GLOBAL short Brouillon_Loupe_Decalage_X;// Decalage horizontal de la fentre de zoom dans le brouillon +GLOBAL short Brouillon_Loupe_Decalage_Y;// Decalage vertical de la fentre de zoom dans le brouillon + +GLOBAL byte Masque_copie_couleurs[256]; // Tableau des couleurs copier vers le brouillon + + // Sauvegarde de l'image: + +GLOBAL byte * Ecran_backup; // Sauvegarde de l'cran virtuel courant +GLOBAL S_Liste_de_pages * Principal_Backups; // Liste des pages de backup de la page principale +GLOBAL S_Liste_de_pages * Brouillon_Backups; // Liste des pages de backup de la page de brouillon + + + // Donnes sur la brosse: + +GLOBAL byte * Brosse; // Sprite de la brosse +GLOBAL word Brosse_Decalage_X; // Centre horizontal de la brosse +GLOBAL word Brosse_Decalage_Y; // Centre vertical de la brosse +GLOBAL word Brosse_Largeur; // Largeur de la brosse +GLOBAL word Brosse_Hauteur; // Hauteur de la brosse + +GLOBAL char Brosse_Repertoire_fichier[256]; // | +GLOBAL char Brosse_Nom_fichier[13]; // | +GLOBAL byte Brosse_Format_fichier; // | Infos sur le +GLOBAL byte Brosse_Format; // |_ slecteur de +GLOBAL short Brosse_File_list_Position; // | fichiers de la +GLOBAL short Brosse_File_list_Decalage; // | brosse. +GLOBAL char Brosse_Repertoire_courant[256]; // | +GLOBAL char Brosse_Commentaire[TAILLE_COMMENTAIRE+1]; // | + +GLOBAL byte Brosse_Centre_rotation_defini; // | Infos sur le +GLOBAL short Brosse_Centre_rotation_X; // |- centre de rotation +GLOBAL short Brosse_Centre_rotation_Y; // | de la brosse + + // Donnes sur le menu + +GLOBAL byte Menu_visible; // Le menu est actif l'cran +GLOBAL word Menu_Ordonnee; // Ordonne o commence le menu +GLOBAL word Menu_Ordonnee_Texte; // Ordonne o commence le texte dans le menu +GLOBAL word Menu_Facteur_X; // Facteur de grossissement du menu en X +GLOBAL word Menu_Facteur_Y; // Facteur de grossissement du menu en Y +GLOBAL word Menu_Taille_couleur; // Taille d'une couleur de la palette du menu + + + // Donnes sur la fentre de menu + +GLOBAL byte Une_fenetre_est_ouverte; + +GLOBAL word Fenetre_Pos_X; // Position du bord gauche de la fentre dans l'cran +GLOBAL word Fenetre_Pos_Y; // Position du bord haut de la fentre dans l'cran +GLOBAL word Fenetre_Largeur; // Largeur de la fentre +GLOBAL word Fenetre_Hauteur; // Hauteur de la fentre + +GLOBAL byte Menu_visible_avant_fenetre; // Le menu tait visible avant d'ouvir une fentre +GLOBAL word Menu_Ordonnee_avant_fenetre; // Ordonne du menu avant d'ouvrir une fentre +GLOBAL byte Cacher_pinceau_avant_fenetre;// Le pinceau tatit dj cach avant l'ouverture de la fenetre? + +GLOBAL word Nb_boutons_fenetre; +GLOBAL struct Fenetre_Bouton_normal * Fenetre_Liste_boutons_normal; +GLOBAL struct Fenetre_Bouton_palette * Fenetre_Liste_boutons_palette; +GLOBAL struct Fenetre_Bouton_scroller * Fenetre_Liste_boutons_scroller; +GLOBAL struct Fenetre_Bouton_special * Fenetre_Liste_boutons_special; +GLOBAL int Fenetre_Attribut1; +GLOBAL int Fenetre_Attribut2; + + + + +// Dfinition des boutons //////////////////////////////////////////////////// + +GLOBAL struct +{ + // Informations sur l'aspect du bouton (graphisme): + word Decalage_X; // Dcalage par rapport la gauche du menu + word Decalage_Y; // Dcalage par rapport au haut du menu + word Largeur; // Largeur du bouton + word Hauteur; // Hauteur du bouton + byte Enfonce; // Le bouton est enfonc + byte Forme; // Forme du bouton + + // Information sur les clicks de la souris: + fonction_action Gauche; // Action dclenche par un click gauche sur le bouton + fonction_action Droite; // Action dclenche par un click droit sur le bouton + word Raccourci_gauche; // Raccourci clavier quivalent un click gauche sur le bouton + word Raccourci_droite; // Raccourci clavier quivalent un click droit sur le bouton + + // Informations sur le dsenclenchement du bouton gr par le moteur: + fonction_action Desenclencher; // Action appele lors du dsenclenchement du bouton + byte Famille; // Ensemble de boutons auquel celui-ci appartient + +} Bouton[NB_BOUTONS]; + + + +// Informations sur les diffrents modes de dessin + +GLOBAL fonction_effet Fonction_effet; + +GLOBAL byte * FX_Feedback_Ecran; + +GLOBAL byte Exclude_color[256]; // Couleurs exclure pour Meilleure_couleur + + // Mode smear: + +GLOBAL byte Smear_Mode; // Le mode smear est enclench +GLOBAL byte Smear_Debut; // On vient juste de commencer une opration en Smear +GLOBAL byte * Smear_Brosse; // Sprite de la brosse de Smear +GLOBAL word Smear_Brosse_Largeur; // Largeur de la brosse de Smear +GLOBAL word Smear_Brosse_Hauteur; // Hauteur de la brosse de Smear +GLOBAL short Smear_Min_X,Smear_Max_X,Smear_Min_Y,Smear_Max_Y; // Bornes de la Brosse du smear + + // Mode shade: + +GLOBAL struct T_Shade Shade_Liste[8]; // Listes de shade +GLOBAL byte Shade_Actuel; // Numro du shade en cours +GLOBAL byte * Shade_Table; // Table de conversion de shade en cours +GLOBAL byte Shade_Table_gauche[256]; // Table de conversion de shade pour un clic gauche +GLOBAL byte Shade_Table_droite[256]; // Table de conversion de shade pour un clic droit +GLOBAL byte Shade_Mode; // Le mode shade est enclench + +GLOBAL byte Quick_shade_Mode; // Le mode quick-shade est enclench +GLOBAL byte Quick_shade_Step; // Pas du mode quick-shade +GLOBAL byte Quick_shade_Loop; // Normal / Loop / No sat. + + // Mode stencil: + +GLOBAL byte Stencil_Mode; // Le mode stencil est enclench +GLOBAL byte Stencil[256]; // Tableau des couleurs protges + + // Mode grille: + +GLOBAL byte Snap_Mode; // Le mode grille est enclench +GLOBAL short Snap_Largeur; // Largeur entre 2 points de la grille +GLOBAL short Snap_Hauteur; // Hauteur entre 2 points de la grille +GLOBAL short Snap_Decalage_X; // Position en X du point le + gauche +GLOBAL short Snap_Decalage_Y; // Position en Y du point le + en haut + + // Mode trame: + +GLOBAL byte Trame_Mode; // Le mode Trame est enclench +GLOBAL byte Trame[16][16]; // Sprite de la trame +GLOBAL word TRAME_PREDEFINIE[12][16]; // Trames prsfinies (compactes sur 16*16 bits) +GLOBAL short Trame_Largeur; // Largeur de la trame +GLOBAL short Trame_Hauteur; // Hauteur de la trame + + // Mode colorize: + +GLOBAL byte Colorize_Mode; // Le mode Colorize est enclench +GLOBAL byte Colorize_Opacite; // Intensit du Colorize +GLOBAL byte Colorize_Mode_en_cours; // Le type de Colorize en cours (0-2) +GLOBAL word Table_de_multiplication_par_Facteur_A[64]; +GLOBAL word Table_de_multiplication_par_Facteur_B[64]; + + // Mode smooth: + +GLOBAL byte Smooth_Mode; // Le mode Smooth est enclench +GLOBAL byte Smooth_Matrice[3][3]; // La matrice du Smooth actuel + + // Mode Tiling: + +GLOBAL byte Tiling_Mode; // Le mode Tiling est enclench +GLOBAL short Tiling_Decalage_X; // Dcalage du tiling en X +GLOBAL short Tiling_Decalage_Y; // Dcalage du tiling en Y + + // Mode Mask + +GLOBAL byte Mask_Mode; // Le mode Masque est enclench +GLOBAL byte Mask[256]; // Tableau des couleurs constituant le masque + + // Mode loupe: + +GLOBAL byte Loupe_Mode; +GLOBAL word Loupe_Facteur; +GLOBAL word Loupe_Hauteur; +GLOBAL word Loupe_Largeur; +GLOBAL short Loupe_Decalage_X; +GLOBAL short Loupe_Decalage_Y; +GLOBAL word * Table_mul_facteur_zoom; +GLOBAL word TABLE_ZOOM[NB_FACTEURS_DE_ZOOM][512]; + +#ifdef VARIABLES_GLOBALES + word FACTEUR_ZOOM[NB_FACTEURS_DE_ZOOM]={2,3,4,5,6,8,10,12,14,16,18,20}; +#else + extern word FACTEUR_ZOOM[NB_FACTEURS_DE_ZOOM]; +#endif + + // Donnes sur les ellipses et les cercles: + +GLOBAL dword Table_des_carres[1025]; +GLOBAL long Ellipse_Curseur_X; +GLOBAL long Ellipse_Curseur_Y; +GLOBAL long Ellipse_Rayon_vertical_au_carre; +GLOBAL long Ellipse_Rayon_horizontal_au_carre; +GLOBAL long Ellipse_Limite_High; +GLOBAL long Ellipse_Limite_Low; +GLOBAL long Cercle_Curseur_X; +GLOBAL long Cercle_Curseur_Y; +GLOBAL long Cercle_Limite; + + // Donnes sur les dgrads: + +GLOBAL short Degrade_Borne_Inferieure; // Plus petite couleur englobe par le dgrad +GLOBAL short Degrade_Borne_Superieure; // Plus grande couleur englobe par le dgrad +GLOBAL int Degrade_Inverse; // Boolen "Le dgrad est en ralit invers" +GLOBAL long Degrade_Intervalle_bornes; // = Abs(Degrade_Borne_Inferieure-Degrade_Borne_Superieure)+1 +GLOBAL long Degrade_Intervalle_total; // Valeur maximum des indices passs la fonction de dgrad (!!! >0 !!!) +GLOBAL long Degrade_Melange_aleatoire; // Facteur de mlange (1-256+) du dgrad +GLOBAL fonction_degrade Traiter_degrade; // Fonction de traitement du dgrad, varie selon la mthode choisie par l'utilisateur. +GLOBAL fonction_afficheur Traiter_pixel_de_degrade; // Redirection de l'affichage + +GLOBAL struct T_Degrade_Tableau Degrade_Tableau[16]; // Donnes de tous les dgrads +GLOBAL int Degrade_Courant; // Indice du tableau correspondant au dgrad courant + + + + // Donnes sur le Spray: + +GLOBAL byte Spray_Mode; // Mode Mono(1) ou Multicolore(0) +GLOBAL short Spray_Size; // Diamtre du spray en pixels +GLOBAL byte Spray_Delay; // Dlai en VBLs entre 2 "pschiitt" +GLOBAL byte Spray_Mono_flow; // Nombre de pixels qui sortent en mme temps en mono +GLOBAL byte Spray_Multi_flow[256]; // Idem pour chaque couleur + + + // Donnes diverses sur le programme: + +GLOBAL byte Sortir_du_programme; +GLOBAL char Repertoire_du_programme[256]; // Rpertoire dans lequel se trouve le programme +GLOBAL char Repertoire_initial[256]; // Rpertoire partir duquel t lanc le programme +GLOBAL byte Fore_color; +GLOBAL byte Back_color; +GLOBAL byte Mode_de_dessin_en_cours; +GLOBAL byte Courbe_en_cours; +GLOBAL byte Ligne_en_cours; +GLOBAL byte Couleur_debut_palette; +GLOBAL byte Un_fichier_a_ete_passe_en_parametre; +GLOBAL byte Une_resolution_a_ete_passee_en_parametre; // utilise uniquement si la variable prcdente est 1 + + // Variables concernant l'OBJ DIVERS + +GLOBAL word INPUT_Nouveau_Mouse_X; +GLOBAL word INPUT_Nouveau_Mouse_Y; +GLOBAL byte INPUT_Nouveau_Mouse_K; +GLOBAL byte INPUT_Keyb_mode; + +GLOBAL int MC_Indice; +GLOBAL int MC_DR; +GLOBAL int MC_DV; +GLOBAL int MC_DB; +GLOBAL int * MC_Table_differences; + + // Variables concernant l'OBJ VIDEO + + // Partie concernant le mode X: +GLOBAL dword MODE_X_Decalage_synchro; +GLOBAL word MODE_X_Largeur_de_ligne; +GLOBAL dword MODE_X_Valeur_initiale_de_esi; +GLOBAL dword MODE_X_Valeur_initiale_de_edi; + // Partie concernant le VESA: +GLOBAL byte Granularite; // Facteur de gestion de la granularit de la carte +GLOBAL byte VESA_Erreur; +GLOBAL byte * VESA_WinFuncPtr; // Handler software de changement de banque +GLOBAL word * VESA_Liste_des_modes; +GLOBAL dword VESA_Decalage_synchro; +GLOBAL word VESA_Largeur_ecran_en_dword; +GLOBAL byte VESA_Banque_en_cours; // Variable normalement locale VIDEO.ASM +GLOBAL byte VESA_Derniere_banque_Fenetre_A_utilisee; +GLOBAL byte VESA_Derniere_banque_Fenetre_B_utilisee; +GLOBAL fonction_action VESA_Change_banque_lecture; +GLOBAL fonction_action VESA_Change_banque_ecriture; +GLOBAL fonction_action VESA_Change_banque_lect_ecr; +GLOBAL byte VESA_Version_Unite; +GLOBAL byte VESA_Version_Decimale; +GLOBAL char VESA_Constructeur[TAILLE_NOM_CONSTRUCTEUR+1]; +GLOBAL word VESA_Taille_memoire; + + // Les diffrents sprites: + +GLOBAL byte BLOCK_MENU[HAUTEUR_MENU][LARGEUR_MENU]; +GLOBAL byte SPRITE_MENU[NB_SPRITES_MENU][HAUTEUR_SPRITE_MENU][LARGEUR_SPRITE_MENU]; +GLOBAL byte SPRITE_EFFET[NB_SPRITES_EFFETS][HAUTEUR_SPRITE_MENU][LARGEUR_SPRITE_MENU]; + +GLOBAL byte * Logo_GrafX2; + +GLOBAL byte Fonte_systeme[256*8*8]; +GLOBAL byte Fonte_fun [256*8*8]; +GLOBAL byte Fonte_help [315][6][8]; +GLOBAL byte * Fonte; + + // Les donnes de l'aide: + +GLOBAL struct Section_d_aide Table_d_aide[NB_SECTIONS_AIDE]; +GLOBAL byte Section_d_aide_en_cours; // Indice de la table d'aide en cours de consultation +GLOBAL word Position_d_aide_en_cours; // Numro de la ligne d'aide en cours de consultation + + // Donnes sur les oprations + +GLOBAL word Operation_avant_interruption; // N de l'opration en cours avant l'utilisation d'une interruption +GLOBAL word Operation_en_cours; // N de l'opration en cours +GLOBAL word Operation_Pile[TAILLE_PILE_OPERATIONS]; // Pile simplifie +GLOBAL byte Operation_Taille_pile; // Taille effective de la pile (0=vide) +GLOBAL byte Operation_dans_loupe; // Indique si l'opration a commenc dans la partie Zoome ou non + +GLOBAL short Pipette_Couleur; +GLOBAL short Pipette_X; +GLOBAL short Pipette_Y; + + +#ifdef VARIABLES_GLOBALES + byte CURSEUR_D_OPERATION[NB_OPERATIONS]= + { + FORME_CURSEUR_CIBLE , // Dessin la main continu + FORME_CURSEUR_CIBLE , // Dessin la main discontinu + FORME_CURSEUR_CIBLE , // Dessin la main point par point + FORME_CURSEUR_CIBLE , // Lignes + FORME_CURSEUR_CIBLE , // Lignes relies + FORME_CURSEUR_CIBLE , // Lignes centres + FORME_CURSEUR_CIBLE_XOR , // Rectangle vide + FORME_CURSEUR_CIBLE_XOR , // Rectangle plein + FORME_CURSEUR_CIBLE , // Cercles vides + FORME_CURSEUR_CIBLE , // Cercles pleins + FORME_CURSEUR_CIBLE , // Ellipses vides + FORME_CURSEUR_CIBLE , // Ellipses pleines + FORME_CURSEUR_CIBLE , // Fill + FORME_CURSEUR_CIBLE , // Remplacer + FORME_CURSEUR_CIBLE_XOR , // Prise de brosse rectangulaire + FORME_CURSEUR_CIBLE , // Prise d'une brosse multiforme + FORME_CURSEUR_CIBLE_PIPETTE , // Rcupration d'une couleur + FORME_CURSEUR_RECTANGLE_XOR , // Positionnement de la fentre de loupe + FORME_CURSEUR_CIBLE , // Courbe 3 points + FORME_CURSEUR_CIBLE , // Courbe 4 points + FORME_CURSEUR_CIBLE , // Spray + FORME_CURSEUR_CIBLE , // Polygone + FORME_CURSEUR_CIBLE , // Polyforme + FORME_CURSEUR_CIBLE , // Polyfill + FORME_CURSEUR_CIBLE , // Polyforme rempli + FORME_CURSEUR_MULTIDIRECTIONNEL, // Scroll + FORME_CURSEUR_CIBLE , // Cercles dgrads + FORME_CURSEUR_CIBLE , // Ellipses dgrades + FORME_CURSEUR_ROTATE_XOR , // Faire tourner brosse + FORME_CURSEUR_CIBLE_XOR , // Etirer brosse + FORME_CURSEUR_CIBLE // Deformer brosse + }; +#else + extern byte CURSEUR_D_OPERATION[NB_OPERATIONS]; +#endif + + + // Procdures appeler: Opration,Mouse_K,Etat de la pile + +GLOBAL struct +{ + byte Effacer_curseur; // Boolen "il faut effacer le curseur pour l'opra." + fonction_action Action; // Action appele +} Operation[NB_OPERATIONS][3][TAILLE_PILE_OPERATIONS]; + + + +// Informations sur les lecteurs + +GLOBAL byte Nb_drives; +GLOBAL struct T_Drive Drive[26]; +GLOBAL byte SPRITE_DRIVE[NB_SPRITES_DRIVES][HAUTEUR_SPRITE_DRIVE][LARGEUR_SPRITE_DRIVE]; + + +// -- Section des informations sur les formats de fichiers ------------------ + + // Comptage du nb d'lments dans la liste: +GLOBAL short Liste_Nb_elements; +GLOBAL short Liste_Nb_fichiers; +GLOBAL short Liste_Nb_repertoires; + // Tte de la liste chane: +GLOBAL struct Element_de_liste_de_fileselect * Liste_du_fileselect; + +// ------------------- Inititialisation des formats connus ------------------- + +#include "loadsave.h" +void Rien_du_tout(void); + +#ifdef VARIABLES_GLOBALES + // Extension du format + char Format_Extension[NB_FORMATS_CONNUS][4]= + { + "PKM", // PKM + "LBM", // LBM + "GIF", // GIF + "BMP", // BMP + "PCX", // PCX + "IMG", // IMG + "SC?", // SCx + "PI1", // PI1 + "PC1", // PC1 + "CEL", // CEL + "KCF", // KCF + "PAL" // PAL + }; + + // Fonction appeler pour vrifier la signature du fichier + fonction_action Format_Test[NB_FORMATS_LOAD]= + { + Test_PKM, // PKM + Test_LBM, // LBM + Test_GIF, // GIF + Test_BMP, // BMP + Test_PCX, // PCX + Test_IMG, // IMG + Test_SCx, // SCx + Test_PI1, // PI1 + Test_PC1, // PC1 + Test_CEL, // CEL + Test_KCF, // KCF + Test_PAL // PAL + }; + + // Fonction appeler pour charger l'image + fonction_action Format_Load[NB_FORMATS_LOAD]= + { + Load_PKM, // PKM + Load_LBM, // LBM + Load_GIF, // GIF + Load_BMP, // BMP + Load_PCX, // PCX + Load_IMG, // IMG + Load_SCx, // SCx + Load_PI1, // PI1 + Load_PC1, // PC1 + Load_CEL, // CEL + Load_KCF, // KCF + Load_PAL // PAL + }; + + // Fonction appeler pour sauvegarder l'image + fonction_action Format_Save[NB_FORMATS_SAVE]= + { + Save_PKM, // PKM + Save_LBM, // LBM + Save_GIF, // GIF + Save_BMP, // BMP + Save_PCX, // PCX + Save_IMG, // IMG + Save_SCx, // SCx + Save_PI1, // PI1 + Save_PC1, // PC1 + Save_CEL, // CEL + Save_KCF, // KCF + Save_PAL // PAL + }; + + // indique si l'on doit considrer que l'image n'est plus modifie + byte Format_Backup_done[NB_FORMATS_CONNUS]= + { + 1, // PKM + 1, // LBM + 1, // GIF + 1, // BMP + 1, // PCX + 1, // IMG + 1, // SCx + 1, // PI1 + 1, // PC1 + 1, // CEL + 0, // KCF + 0 // PAL + }; + + // Le format de fichier autorise un commentaire + byte Format_Commentaire[NB_FORMATS_CONNUS]= + { + 1, // PKM + 0, // LBM + 0, // GIF + 0, // BMP + 0, // PCX + 0, // IMG + 0, // SCx + 0, // PI1 + 0, // PC1 + 0, // CEL + 0, // KCF + 0 // PAL + }; +#else + extern char Format_Extension[NB_FORMATS_CONNUS][4]; + extern fonction_action Format_Load[NB_FORMATS_LOAD]; + extern fonction_action Format_Save[NB_FORMATS_SAVE]; + extern fonction_action Format_Test[NB_FORMATS_LOAD]; + extern byte Format_Backup_done[NB_FORMATS_CONNUS]; + extern byte Format_Commentaire[NB_FORMATS_CONNUS]; +#endif + +GLOBAL signed char Erreur_fichier; // 0: opration I/O OK + // 1: Erreur ds le dbut de l'opration + // 2: Erreur durant l'opration => donnes modifies + //-1: Interruption du chargement d'une preview + +GLOBAL int Ligne_INI; + +GLOBAL fonction_afficheur Pixel_de_chargement; +GLOBAL fonction_lecteur Lit_pixel_de_sauvegarde; + +#endif diff --git a/graph.c b/graph.c new file mode 100644 index 00000000..3b666f27 --- /dev/null +++ b/graph.c @@ -0,0 +1,5750 @@ +#include "sdlscreen.h" +#include "graph.h" +#include "divers.h" +#include +#include + +#include +#include +#include +#include "moteur.h" +#include "boutons.h" +#include "pages.h" +#include "global.h" + + +// On dclare mchamment le prototype de Erreur pour viter de faire un +// fichier "main.h": +void Erreur(int Code); + +/* +byte Meilleure_couleur(byte R,byte V,byte B) +{ + short Coul; + int Delta_R,Delta_V,Delta_B; + int Dist; + int Best_dist=0x7FFFFFFF; + byte Best_color; + + for (Coul=0; Coul<256; Coul++) + { + if (!Exclude_color[Coul]) + { + Delta_R=(int)Principal_Palette[Coul].R-R; + Delta_V=(int)Principal_Palette[Coul].V-V; + Delta_B=(int)Principal_Palette[Coul].B-B; + + if (!(Dist=(Delta_R*Delta_R*30)+(Delta_V*Delta_V*59)+(Delta_B*Delta_B*11))) + return Coul; + + if (Dist>3)*Menu_Taille_couleur)*Menu_Facteur_X; + Debut_Y=Menu_Ordonnee_avant_fenetre+((2+((Couleur&7)<<2))*Menu_Facteur_Y); + Fin_X=Debut_X+Largeur; + Fin_Y=Debut_Y+Hauteur; + + // On affiche le bloc en entier si on peut, sinon on le dcoupe autour + // de la fentre. + if ( (Debut_Y>=Coin_Y) || (Fin_X<=Fenetre_Pos_X) || (Debut_X>=Coin_X) ) + Block(Debut_X,Debut_Y,Largeur,Hauteur,Vraie_couleur); + else + { + + if (Debut_X>=Fenetre_Pos_X) + { + if ( (Fin_X>Coin_X) || (Fin_Y>Coin_Y) ) + { + if ( (Fin_X>Coin_X) && (Fin_Y>Coin_Y) ) + { + Block(Coin_X,Debut_Y,Fin_X-Coin_X,Coin_Y-Debut_Y,Vraie_couleur); + Block(Debut_X,Coin_Y,Largeur,Fin_Y-Coin_Y,Vraie_couleur); + } + else + { + if (Fin_Y>Coin_Y) + Block(Debut_X,Coin_Y,Largeur,Fin_Y-Coin_Y,Vraie_couleur); + else + Block(Coin_X,Debut_Y,Fin_X-Coin_X,Hauteur,Vraie_couleur); + } + } + } + else + { + if (Fin_XCoin_Y) + { + Block(Debut_X,Debut_Y,Fenetre_Pos_X-Debut_X,Coin_Y-Debut_Y,Vraie_couleur); + Block(Debut_X,Coin_Y,Largeur,Fin_Y-Coin_Y,Vraie_couleur); + } + else + Block(Debut_X,Debut_Y,Fenetre_Pos_X-Debut_X,Hauteur,Vraie_couleur); + } + else + { + if (Fin_Y>Coin_Y) + { + Block(Debut_X,Debut_Y,Fenetre_Pos_X-Debut_X,Coin_Y-Debut_Y,Vraie_couleur); + Block(Coin_X,Debut_Y,Fin_X-Coin_X,Coin_Y-Debut_Y,Vraie_couleur); + Block(Debut_X,Coin_Y,Largeur,Fin_Y-Coin_Y,Vraie_couleur); + } + else + { + Block(Debut_X,Debut_Y,Fenetre_Pos_X-Debut_X,Hauteur,Vraie_couleur); + Block(Coin_X,Debut_Y,Fin_X-Coin_X,Hauteur,Vraie_couleur); + } + } + } + } + } + } +} + + +void Remapper_ecran_apres_changement_couleurs_menu(void) +{ + short Indice; + byte Table_de_conversion[256]; + short Temp,Temp2; + + if ( (CM_Clair!=Old_Clair) + || (CM_Fonce!=Old_Fonce) + || (CM_Blanc!=Old_Blanc) + || (CM_Noir !=Old_Noir ) + || (CM_Trans!=Old_Trans) ) + { + // Cration de la table de conversion + for (Indice=0; Indice<256; Indice++) + Table_de_conversion[Indice]=Indice; + + Table_de_conversion[Old_Noir ]=CM_Noir; + Table_de_conversion[Old_Fonce]=CM_Fonce; + Table_de_conversion[Old_Clair]=CM_Clair; + Table_de_conversion[Old_Blanc]=CM_Blanc; + + // Remappage de l'cran + + Temp=Fenetre_Hauteur*Menu_Facteur_Y; + + Remap_screen(Fenetre_Pos_X, Fenetre_Pos_Y, + Fenetre_Largeur*Menu_Facteur_X, + (Fenetre_Pos_Y+Temp255)) + Indice++; + + // On note la position de la premire case de la squence + Premier=Indice; + + // On recherche la position de la dernire case de la squence + for (Dernier=Premier;Liste[Dernier+1]<256;Dernier++); + + // Pour toutes les cases non vides (et non inhibes) qui suivent + switch (Mode) + { + case MODE_SHADE_NORMAL : + for (;(Indice<512) && (Liste[Indice]<256);Indice++) + { // On met jour les tables de conversion + Couleur=Liste[Indice]; + Table_inc[Couleur]=Liste[(Indice+Pas<=Dernier)?Indice+Pas:Dernier]; + Table_dec[Couleur]=Liste[(Indice-Pas>=Premier)?Indice-Pas:Premier]; + } + break; + case MODE_SHADE_BOUCLE : + Temp=1+Dernier-Premier; + for (;(Indice<512) && (Liste[Indice]<256);Indice++) + { // On met jour les tables de conversion + Couleur=Liste[Indice]; + Table_inc[Couleur]=Liste[Premier+((Pas+Indice-Premier)%Temp)]; + Table_dec[Couleur]=Liste[Premier+(((Temp-Pas)+Indice-Premier)%Temp)]; + } + break; + default : // MODE_SHADE_NOSAT + for (;(Indice<512) && (Liste[Indice]<256);Indice++) + { // On met jour les tables de conversion + Couleur=Liste[Indice]; + if (Indice+Pas<=Dernier) + Table_inc[Couleur]=Liste[Indice+Pas]; + if (Indice-Pas>=Premier) + Table_dec[Couleur]=Liste[Indice-Pas]; + } + } + } +} + + +// Transformer un nombre (entier naturel) en chane +void Num2str(dword Nombre,char * Chaine,byte Taille) +{ + int Indice; + + for (Indice=Taille-1;Indice>=0;Indice--) + { + Chaine[Indice]=(Nombre%10)+'0'; + Nombre/=10; + if (Nombre==0) + for (Indice--;Indice>=0;Indice--) + Chaine[Indice]=' '; + } + Chaine[Taille]='\0'; +} + +// Transformer une chane en un entier naturel (renvoie -1 si ch. invalide) +int Str2num(char * Chaine) +{ + int Valeur=0; + + for (;*Chaine;Chaine++) + { + if ( (*Chaine>='0') && (*Chaine<='9') ) + Valeur=(Valeur*10)+(*Chaine-'0'); + else + return -1; + } + return Valeur; +} + + +// Arrondir un nombre rel la valeur entire la plus proche +short Round(float Valeur) +{ + short Temp=Valeur; + + if (Valeur>=0) + { if ((Valeur-Temp)>= 0.5) Temp++; } + else + { if ((Valeur-Temp)<=-0.5) Temp--; } + + return Temp; +} + +// Arrondir le rsultat d'une division la valeur entire suprieure +short Round_div_max(short Numerateur,short Diviseur) +{ + if (!(Numerateur % Diviseur)) + return (Numerateur/Diviseur); + else + return (Numerateur/Diviseur)+1; +} + + + +int Min(int A,int B) +{ + return (AB)?A:B; +} + + + + +void Transformer_point(short X, short Y, float cosA, float sinA, + short * Xr, short * Yr) +{ + *Xr=Round(((float)X*cosA)+((float)Y*sinA)); + *Yr=Round(((float)Y*cosA)-((float)X*sinA)); +} + + + +// -- Recadrer la partie non-zoome de l'image par rapport la partie zoome +// lorsqu'on scrolle en mode Loupe -- +void Recadrer_ecran_par_rapport_au_zoom(void) +{ + // Centrage en X + if (Principal_Largeur_image>Principal_Split) + { + Principal_Decalage_X=Loupe_Decalage_X+(Loupe_Largeur>>1) + -(Principal_Split>>1); + if (Principal_Decalage_X<0) + Principal_Decalage_X=0; + else + if (Principal_Largeur_imageMenu_Ordonnee) + { + Principal_Decalage_Y=Loupe_Decalage_Y+(Loupe_Hauteur>>1) + -(Menu_Ordonnee>>1); + if (Principal_Decalage_Y<0) + Principal_Decalage_Y=0; + else + if (Principal_Hauteur_image>1)-X_theorique)/Loupe_Facteur)*Loupe_Facteur); + Principal_Split=Principal_X_Zoom-(Menu_Facteur_X*LARGEUR_BARRE_SPLIT); + + // Correction en cas de dbordement sur la gauche + while (Principal_Split*(Loupe_Facteur+1)=X_theorique) + { + Principal_Split-=Loupe_Facteur; + Principal_X_Zoom-=Loupe_Facteur; + } +} + + + +// -------------------- Calcul des information de la loupe ------------------- +void Calculer_donnees_loupe(void) +/* + Aprs modification des donnes de la loupe, il faut recalculer les limites. +*/ +{ + Calculer_split(); + + Loupe_Largeur=(Largeur_ecran-Principal_X_Zoom)/Loupe_Facteur; + + Loupe_Hauteur=Menu_Ordonnee/Loupe_Facteur; + if (Menu_Ordonnee%Loupe_Facteur) + Loupe_Hauteur++; + + if (Loupe_Mode && Loupe_Decalage_X) + { + if (Principal_Largeur_image=Principal_Hauteur_image) + Limite_Bas=Principal_Hauteur_image-1; + else + Limite_Bas=Limite_visible_Bas; + + if (Limite_visible_Droite>=Principal_Largeur_image) + Limite_Droite=Principal_Largeur_image-1; + else + Limite_Droite=Limite_visible_Droite; + + // -- Calcul des limites de la partie zoome de l'image -- + Limite_Haut_Zoom =Loupe_Decalage_Y; + Limite_Gauche_Zoom=Loupe_Decalage_X; + Limite_visible_Bas_Zoom =Limite_Haut_Zoom+Loupe_Hauteur-1; + Limite_visible_Droite_Zoom=Limite_Gauche_Zoom+Loupe_Largeur-1; + + if (Limite_visible_Bas_Zoom>=Principal_Hauteur_image) + Limite_Bas_Zoom=Principal_Hauteur_image-1; + else + Limite_Bas_Zoom=Limite_visible_Bas_Zoom; + + if (Limite_visible_Droite_Zoom>=Principal_Largeur_image) + Limite_Droite_Zoom=Principal_Largeur_image-1; + else + Limite_Droite_Zoom=Limite_visible_Droite_Zoom; + } + else + { + // -- Calcul des limites de la partie visible de l'image -- + Limite_Haut =Principal_Decalage_Y; + Limite_Gauche=Principal_Decalage_X; + Limite_visible_Bas =Limite_Haut+(Menu_visible?Menu_Ordonnee:Hauteur_ecran)-1; // A REVOIR POUR SIMPLIFICATION + Limite_visible_Droite=Limite_Gauche+Largeur_ecran-1; + + if (Limite_visible_Bas>=Principal_Hauteur_image) + Limite_Bas=Principal_Hauteur_image-1; + else + Limite_Bas=Limite_visible_Bas; + + if (Limite_visible_Droite>=Principal_Largeur_image) + Limite_Droite=Principal_Largeur_image-1; + else + Limite_Droite=Limite_visible_Droite; + } +} + + +// -- Calculer les coordonnes du pinceau en fonction du snap et de la loupe - +void Calculer_coordonnees_pinceau(void) +{ + if ((Loupe_Mode) && (Mouse_X>=Principal_X_Zoom)) + { + Pinceau_X=((Mouse_X-Principal_X_Zoom)/Loupe_Facteur)+Loupe_Decalage_X; + Pinceau_Y=(Mouse_Y/Loupe_Facteur)+Loupe_Decalage_Y; + } + else + { + Pinceau_X=Mouse_X+Principal_Decalage_X; + Pinceau_Y=Mouse_Y+Principal_Decalage_Y; + } + + if (Snap_Mode) + { + Pinceau_X=(((Pinceau_X+(Snap_Largeur>>1)-Snap_Decalage_X)/Snap_Largeur)*Snap_Largeur)+Snap_Decalage_X; + Pinceau_Y=(((Pinceau_Y+(Snap_Hauteur>>1)-Snap_Decalage_Y)/Snap_Hauteur)*Snap_Hauteur)+Snap_Decalage_Y; + } +} + + +// ------------ Changer le facteur de zoom et tout mettre jour ------------- +void Changer_facteur_loupe(byte Indice_facteur) +{ + short Centre_X; + short Centre_Y; + + Centre_X=Loupe_Decalage_X+(Loupe_Largeur>>1); + Centre_Y=Loupe_Decalage_Y+(Loupe_Hauteur>>1); + + Loupe_Facteur=FACTEUR_ZOOM[Indice_facteur]; + Table_mul_facteur_zoom=TABLE_ZOOM[Indice_facteur]; + Calculer_donnees_loupe(); + + if (Loupe_Mode) + { + // Recalculer le dcalage de la loupe + // Centrage "brut" de lcran par rapport la loupe + Loupe_Decalage_X=Centre_X-(Loupe_Largeur>>1); + Loupe_Decalage_Y=Centre_Y-(Loupe_Hauteur>>1); + // Correction en cas de dbordement de l'image + if (Loupe_Decalage_X+Loupe_Largeur>Principal_Largeur_image) + Loupe_Decalage_X=Principal_Largeur_image-Loupe_Largeur; + if (Loupe_Decalage_Y+Loupe_Hauteur>Principal_Hauteur_image) + Loupe_Decalage_Y=Principal_Hauteur_image-Loupe_Hauteur; + if (Loupe_Decalage_X<0) + Loupe_Decalage_X=0; + if (Loupe_Decalage_Y<0) + Loupe_Decalage_Y=0; + + Recadrer_ecran_par_rapport_au_zoom(); + + Pixel_Preview=Pixel_Preview_Loupe; + } + else + Pixel_Preview=Pixel_Preview_Normal; + + Calculer_limites(); + Calculer_coordonnees_pinceau(); +} + + +// -- Affichage de la limite de l'image ------------------------------------- +void Afficher_limites_de_l_image(void) +{ + short Debut; + short Pos; + short Fin; + byte Droite_visible; + byte Bas_visible; + short Ancienne_Limite_Zoom; + + Droite_visible=Principal_Largeur_image<((Loupe_Mode)?Principal_Split:Largeur_ecran); + Bas_visible =Principal_Hauteur_imageMode_video[Numero].Facteur_Y) + && (Menu_Facteur_X==Menu_Facteur_Y) ) + Menu_Facteur_X++; + break; + default: // ne pas adapter + Menu_Facteur_X=1; + Menu_Facteur_Y=1; + } + + if (Buffer_de_ligne_horizontale) + free(Buffer_de_ligne_horizontale); + + Buffer_de_ligne_horizontale=(byte *)malloc((Largeur_ecran>Principal_Largeur_image)?Largeur_ecran:Principal_Largeur_image); + + switch (Mode_video[Numero].Mode) + { + case MODE_SDL: + Pixel= Pixel_SDL; + Lit_pixel= Lit_Pixel_SDL; + Clear_screen= Effacer_Tout_l_Ecran_SDL; + Display_screen= Afficher_partie_de_l_ecran_SDL; + Block= Block_SDL; + Pixel_Preview_Normal= Pixel_Preview_Normal_SDL; + Pixel_Preview_Loupe=Pixel_Preview_Loupe_SDL; + Ligne_horizontale_XOR=Ligne_horizontale_XOR_SDL; + Ligne_verticale_XOR=Ligne_verticale_XOR_SDL; + Display_brush_Color=Display_brush_Color_SDL; + Display_brush_Mono=Display_brush_Mono_SDL; + Clear_brush=Clear_brush_SDL; + Remap_screen=Remap_screen_SDL; + Afficher_ligne=Afficher_une_ligne_ecran_SDL; + Lire_ligne=Lire_une_ligne_ecran_SDL; + Display_zoomed_screen=Afficher_partie_de_l_ecran_zoomee_SDL; + Display_brush_Color_zoom=Display_brush_Color_zoom_SDL; + Display_brush_Mono_zoom=Display_brush_Mono_zoom_SDL; + Clear_brush_zoom=Clear_brush_zoom_SDL; + Set_Mode_SDL(); + break; + + switch(Mode_video[Numero].Mode_VESA_de_base) + { + case 0x100 : Indice_VESA=0; // 640x400 + break; + case 0x101 : Indice_VESA=1; // 640x480 + break; + case 0x103 : Indice_VESA=2; // 800x600 + break; + default : Indice_VESA=3; // 1024x768 + } + + // On regarde si le mode supporte le LFB + if (VESA_Mode_Infos[Indice_VESA].Adresse_physique_LFB!=0) + { + // C'est le cas => on va s'en servir + + Set_VESA_mode(Mode_video[Numero].Mode_VESA_de_base | 0x4000); + Initialiser_le_LFB(VESA_Mode_Infos[Indice_VESA].Adresse_physique_LFB, + VESA_Mode_Infos[Indice_VESA].Taille_LFB); + if (Mode_X_Ptr!=NULL) + Retoucher_CRTC(); + } + else + { + // Ce n'est pas le cas, on continue comme si de rien n'tait + Granularite =VESA_Mode_Infos[Indice_VESA].Granularite; + VESA_WinFuncPtr=VESA_Mode_Infos[Indice_VESA].WinFuncPtr; + + Initialiser_mode_video_VESA(Mode_video[Numero].Mode_VESA_de_base); + if (Mode_X_Ptr!=NULL) + Retoucher_CRTC(); + } + } + Set_palette(Principal_Palette); + + Resolution_actuelle=Numero; + + Menu_Taille_couleur=((Largeur_ecran/Menu_Facteur_X)-(LARGEUR_MENU+2)) >> 3; + Menu_Ordonnee=Hauteur_ecran; + if (Menu_visible) + Menu_Ordonnee-=HAUTEUR_MENU*Menu_Facteur_Y; + Menu_Ordonnee_Texte=Hauteur_ecran-(Menu_Facteur_Y<<3); + Bouton[BOUTON_CHOIX_COL].Largeur=(Menu_Taille_couleur<<3)-1; + + Clip_mouse(); + Mouse_X = Largeur_ecran >> 1; + Mouse_Y = Hauteur_ecran >> 1; + Set_mouse_position(); + + Sensibilite_X=Config.Indice_Sensibilite_souris_X/Mode_video[Numero].Facteur_X; + Sensibilite_Y=Config.Indice_Sensibilite_souris_Y/Mode_video[Numero].Facteur_Y; + Sensibilite_X>>=Mouse_Facteur_de_correction_X; + Sensibilite_Y>>=Mouse_Facteur_de_correction_Y; + Sensibilite_souris(Sensibilite_X?Sensibilite_X:1,Sensibilite_Y?Sensibilite_Y:1); + + Brouillon_Decalage_X=0; // | Il faut penser viter les incohrences + Brouillon_Decalage_Y=0; // |- de dcalage du brouillon par rapport + Brouillon_Loupe_Mode=0; // | la rsolution. + } + + Pixel_Preview=Pixel_Preview_Normal; + + Principal_Decalage_X=0; // Il faut quand mme modifier ces valeurs chaque + Principal_Decalage_Y=0; // fois car on n'est pas l'abri d'une modification + // des dimensions de l'image. + Calculer_donnees_loupe(); + Calculer_limites(); + Calculer_coordonnees_pinceau(); +} + + +// -- Interface avec l'image, affecte par le facteur de grossissement ------- + + // fonction d'affichage "Pixel" utilise pour les oprations dfinitivement + // Ne doit aucune condition tre appele en dehors de la partie visible + // de l'image dans l'cran (a pourrait tre grave) +void Afficher_pixel(short X,short Y,byte Couleur) + // X & Y sont la position d'un point dans l'IMAGE + // Couleur est la couleur du point + // Le Stencil est gr. + // Les effets sont grs par appel Fonction_effet(). + // La Loupe est gre par appel Pixel_Preview(). +{ + if ( ( (!Trame_Mode) || (Effet_Trame(X,Y)) ) + && (!((Stencil_Mode) && (Stencil[Lit_pixel_dans_ecran_courant(X,Y)]))) + && (!((Mask_Mode) && (Mask[Lit_pixel_dans_ecran_brouillon(X,Y)]))) ) + { + Couleur=Fonction_effet(X,Y,Couleur); + Pixel_dans_ecran_courant(X,Y,Couleur); + Pixel_Preview(X,Y,Couleur); + } +} + + +// -- Interface avec le menu et les fentres --------------------------------- + + // Affichage d'un pixel dans le menu (le menu dot tre visible) + +void Pixel_dans_barre_d_outil(word X,word Y,byte Couleur) +{ + Block(X*Menu_Facteur_X,(Y*Menu_Facteur_Y)+Menu_Ordonnee,Menu_Facteur_X,Menu_Facteur_Y,Couleur); +} + + // Affichage d'un pixel dans la fentre (la fentre dot tre visible) + +void Pixel_dans_fenetre(word X,word Y,byte Couleur) +{ + Block((X*Menu_Facteur_X)+Fenetre_Pos_X,(Y*Menu_Facteur_Y)+Fenetre_Pos_Y,Menu_Facteur_X,Menu_Facteur_Y,Couleur); +} + + +// -- Affichages de diffrents cdres dans une fentre ----------------------- + + // -- Cadre gnral avec couleurs paramtrables -- + +void Fenetre_Afficher_cadre_general(word Pos_X,word Pos_Y,word Largeur,word Hauteur, + byte Couleur_HG,byte Couleur_BD,byte Couleur_S,byte Couleur_CHG,byte Couleur_CBD) +// Paramtres de couleurs: +// Couleur_HG =Bords Haut et Gauche +// Couleur_BD =Bords Bas et Droite +// Couleur_S =Coins Haut-Droite et Bas-Gauche +// Couleur_CHG=Coin Haut-Gauche +// Couleur_CBD=Coin Bas-Droite +{ + // Bord haut (sans les extrmits) + Block(Fenetre_Pos_X+((Pos_X+1)*Menu_Facteur_X), + Fenetre_Pos_Y+(Pos_Y*Menu_Facteur_Y), + (Largeur-2)*Menu_Facteur_X,Menu_Facteur_Y,Couleur_HG); + + // Bord bas (sans les extrmits) + Block(Fenetre_Pos_X+((Pos_X+1)*Menu_Facteur_X), + Fenetre_Pos_Y+((Pos_Y+Hauteur-1)*Menu_Facteur_Y), + (Largeur-2)*Menu_Facteur_X,Menu_Facteur_Y,Couleur_BD); + + // Bord gauche (sans les extrmits) + Block(Fenetre_Pos_X+(Pos_X*Menu_Facteur_X), + Fenetre_Pos_Y+((Pos_Y+1)*Menu_Facteur_Y), + Menu_Facteur_X,(Hauteur-2)*Menu_Facteur_Y,Couleur_HG); + + // Bord droite (sans les extrmits) + Block(Fenetre_Pos_X+((Pos_X+Largeur-1)*Menu_Facteur_X), + Fenetre_Pos_Y+((Pos_Y+1)*Menu_Facteur_Y), + Menu_Facteur_X,(Hauteur-2)*Menu_Facteur_Y,Couleur_BD); + + // Coin haut gauche + Pixel_dans_fenetre(Pos_X,Pos_Y,Couleur_CHG); + // Coin haut droite + Pixel_dans_fenetre(Pos_X+Largeur-1,Pos_Y,Couleur_S); + // Coin bas droite + Pixel_dans_fenetre(Pos_X+Largeur-1,Pos_Y+Hauteur-1,Couleur_CBD); + // Coin bas gauche + Pixel_dans_fenetre(Pos_X,Pos_Y+Hauteur-1,Couleur_S); +} + + // -- Cadre dont tout le contour est d'une seule couleur -- + +void Fenetre_Afficher_cadre_mono(word Pos_X,word Pos_Y,word Largeur,word Hauteur,byte Couleur) +{ + Fenetre_Afficher_cadre_general(Pos_X,Pos_Y,Largeur,Hauteur,Couleur,Couleur,Couleur,Couleur,Couleur); +} + + // -- Cadre creux: fonc en haut-gauche et clair en bas-droite -- + +void Fenetre_Afficher_cadre_creux(word Pos_X,word Pos_Y,word Largeur,word Hauteur) +{ + Fenetre_Afficher_cadre_general(Pos_X,Pos_Y,Largeur,Hauteur,CM_Fonce,CM_Blanc,CM_Clair,CM_Fonce,CM_Blanc); +} + + // -- Cadre bomb: clair en haut-gauche et fonc en bas-droite -- + +void Fenetre_Afficher_cadre_bombe(word Pos_X,word Pos_Y,word Largeur,word Hauteur) +{ + Fenetre_Afficher_cadre_general(Pos_X,Pos_Y,Largeur,Hauteur,CM_Blanc,CM_Fonce,CM_Clair,CM_Blanc,CM_Fonce); +} + + // -- Cadre de sparation: un cadre bomb dans un cadre creux (3D!!!) -- + +void Fenetre_Afficher_cadre(word Pos_X,word Pos_Y,word Largeur,word Hauteur) +{ + Fenetre_Afficher_cadre_creux(Pos_X,Pos_Y,Largeur,Hauteur); + Fenetre_Afficher_cadre_bombe(Pos_X+1,Pos_Y+1,Largeur-2,Hauteur-2); +} + + +//-- Affichages relatifs la palette dans le menu --------------------------- + + // -- Affichage des couleurs courante (fore/back) de pinceau dans le menu -- + +void Afficher_foreback(void) +{ + if (Menu_visible) + { + Block((LARGEUR_MENU-17)*Menu_Facteur_X,Menu_Ordonnee+Menu_Facteur_Y,Menu_Facteur_X<<4,Menu_Facteur_Y*7,Back_color); + Block((LARGEUR_MENU-13)*Menu_Facteur_X,Menu_Ordonnee+(Menu_Facteur_Y<<1),Menu_Facteur_X<<3,Menu_Facteur_Y*5,Fore_color); + } +} + + // -- Tracer un cadre de couleur autour de la Fore_color dans le menu -- + +void Encadrer_couleur_menu(byte Couleur) +{ + word Debut_X,Debut_Y,Fin_X,Fin_Y; + word Indice; + + if ((Fore_color>=Couleur_debut_palette) && (Fore_color>3)*Menu_Taille_couleur)*Menu_Facteur_X; + Debut_Y=Menu_Ordonnee+((1+(((Fore_color-Couleur_debut_palette)&7)<<2))*Menu_Facteur_Y); + + Block(Debut_X,Debut_Y,(Menu_Taille_couleur+1)*Menu_Facteur_X,Menu_Facteur_Y,Couleur); + Block(Debut_X,Debut_Y+(Menu_Facteur_Y<<2),(Menu_Taille_couleur+1)*Menu_Facteur_X,Menu_Facteur_Y,Couleur); + + Block(Debut_X,Debut_Y+Menu_Facteur_Y,Menu_Facteur_X,Menu_Facteur_Y*3,Couleur); + Block(Debut_X+(Menu_Taille_couleur*Menu_Facteur_X),Debut_Y+Menu_Facteur_Y,Menu_Facteur_X,Menu_Facteur_Y*3,Couleur); + } + else + { + if (Couleur==CM_Noir) + { + Debut_X=(LARGEUR_MENU+1+((Fore_color-Couleur_debut_palette)>>3)*Menu_Taille_couleur)*Menu_Facteur_X; + Debut_Y=Menu_Ordonnee+((2+(((Fore_color-Couleur_debut_palette)&7)<<2))*Menu_Facteur_Y); + + Block(Debut_X,Debut_Y,Menu_Taille_couleur*Menu_Facteur_X, + Menu_Facteur_Y<<2,Fore_color); + } + else + { + Debut_X=LARGEUR_MENU+1+((Fore_color-Couleur_debut_palette)>>3)*Menu_Taille_couleur; + Debut_Y=2+(((Fore_color-Couleur_debut_palette)&7)<<2); + + Fin_X=Debut_X+Menu_Taille_couleur-1; + Fin_Y=Debut_Y+3; + + for (Indice=Debut_X; Indice<=Fin_X; Indice++) + Block(Indice*Menu_Facteur_X,Menu_Ordonnee+(Debut_Y*Menu_Facteur_Y), + Menu_Facteur_X,Menu_Facteur_Y, + ((Indice+Debut_Y)&1)?CM_Blanc:CM_Noir); + + for (Indice=Debut_Y+1; Indice>3)*Menu_Taille_couleur)*Menu_Facteur_X, + Menu_Ordonnee+((2+((Couleur&7)<<2))*Menu_Facteur_Y), + (Menu_Taille_couleur-1)*Menu_Facteur_X, + Menu_Facteur_Y*3, + Couleur_debut_palette+Couleur); + else + for (Couleur=0;Couleur<64;Couleur++) + Block((LARGEUR_MENU+1+(Couleur>>3)*Menu_Taille_couleur)*Menu_Facteur_X, + Menu_Ordonnee+((2+((Couleur&7)<<2))*Menu_Facteur_Y), + Menu_Taille_couleur*Menu_Facteur_X, + Menu_Facteur_Y<<2, + Couleur_debut_palette+Couleur); + + Encadrer_couleur_menu(CM_Blanc); + } +} + + // -- Recalculer l'origine de la palette dans le menu pour rendre la + // Fore_color visible -- + +void Recadrer_palette(void) +{ + byte Ancienne_couleur=Couleur_debut_palette; + + if (Fore_color=Couleur_debut_palette+64) + Couleur_debut_palette+=8; + } + if (Ancienne_couleur!=Couleur_debut_palette) + Afficher_palette_du_menu(); +} + + + // -- Afficher la barre de sparation entre les parties zoomes ou non en + // mode Loupe -- + +void Afficher_barre_de_split(void) +{ + // Partie grise du milieu + Block(Principal_Split+(Menu_Facteur_X<<1),Menu_Facteur_Y, + (LARGEUR_BARRE_SPLIT-4)*Menu_Facteur_X, + Menu_Ordonnee-(Menu_Facteur_Y<<1),CM_Clair); + + // Barre noire de gauche + Block(Principal_Split,0,Menu_Facteur_X,Menu_Ordonnee,CM_Noir); + + // Barre noire de droite + Block(Principal_X_Zoom-Menu_Facteur_X,0,Menu_Facteur_X,Menu_Ordonnee,CM_Noir); + + // Bord haut (blanc) + Block(Principal_Split+Menu_Facteur_X,0, + (LARGEUR_BARRE_SPLIT-3)*Menu_Facteur_X,Menu_Facteur_Y,CM_Blanc); + + // Bord gauche (blanc) + Block(Principal_Split+Menu_Facteur_X,Menu_Facteur_Y, + Menu_Facteur_X,(Menu_Ordonnee-(Menu_Facteur_Y<<1)),CM_Blanc); + + // Bord droite (gris fonc) + Block(Principal_X_Zoom-(Menu_Facteur_X<<1),Menu_Facteur_Y, + Menu_Facteur_X,(Menu_Ordonnee-(Menu_Facteur_Y<<1)),CM_Fonce); + + // Bord bas (gris fonc) + Block(Principal_Split+(Menu_Facteur_X<<1),Menu_Ordonnee-Menu_Facteur_Y, + (LARGEUR_BARRE_SPLIT-3)*Menu_Facteur_X,Menu_Facteur_Y,CM_Fonce); + + // Coin bas gauche + Block(Principal_Split+Menu_Facteur_X,Menu_Ordonnee-Menu_Facteur_Y, + Menu_Facteur_X,Menu_Facteur_Y,CM_Clair); + // Coin haut droite + Block(Principal_X_Zoom-(Menu_Facteur_X<<1),0, + Menu_Facteur_X,Menu_Facteur_Y,CM_Clair); +} + + // -- Afficher tout le menu -- + +void Afficher_menu(void) +{ + word Pos_X; + word Pos_Y; + char Chaine[4]; + + + if (Menu_visible) + { + // Affichage du sprite du menu + for (Pos_Y=0;Pos_Y=Principal_X_Zoom) )) + { + if ( (Operation_en_cours!=OPERATION_PIPETTE) + && (Operation_en_cours!=OPERATION_REMPLACER) ) + Print_dans_menu("X: Y: ",0); + else + { + Print_dans_menu("X: Y: ( )",0); + Num2str(Pipette_Couleur,Chaine,3); + Print_dans_menu(Chaine,20); + Print_general(170*Menu_Facteur_X,Menu_Ordonnee_Texte," ",0,Pipette_Couleur); + } + Print_coordonnees(); + } + Print_nom_fichier(); + } + } +} + + +// -- Affichage de texte ----------------------------------------------------- + + // -- Afficher une chane n'importe o l'cran -- + +void Print_general(short X,short Y,char * Chaine,byte Couleur_texte,byte Couleur_fond) +{ + word Indice; + short Pos_X; + short Pos_Y; + char Caractere; + short Reel_X; + short Reel_Y; + short Largeur; + short Repeat_Menu_Facteur_X; + short Repeat_Menu_Facteur_Y; + + Reel_Y=Y; + Largeur=strlen(Chaine)*Menu_Facteur_X*8; + for (Pos_Y=0;Pos_Y<8;Pos_Y++) + { + Reel_X=0; // Position dans le buffer + for (Indice=0;Chaine[Indice]!='\0';Indice++) + { + Caractere=Chaine[Indice]; + for (Pos_X=0;Pos_X<8;Pos_X++) + for (Repeat_Menu_Facteur_X=0;Repeat_Menu_Facteur_X=0) && (Pinceau_Y>=0) + && (Pinceau_X=Debut) && (C<=Fin) && (Debut!=Fin)) + { + Largeur=1+Fin-Debut; + + if ( ((Mouse_K==A_GAUCHE) && Sens) || ((Mouse_K==A_DROITE) && (!Sens)) ) + C-=Quick_shade_Step%Largeur; + else + C+=Quick_shade_Step%Largeur; + + if (CFin) + switch (Quick_shade_Loop) + { + case MODE_SHADE_NORMAL : return Fin; + case MODE_SHADE_BOUCLE : return (C-Largeur); + default : return Couleur; + } + } + + return C; +} + + // -- Effet de Tiling -- + +byte Effet_Tiling(word X,word Y,byte Couleur) +{ + return Lit_pixel_dans_brosse((X+Brosse_Largeur-Tiling_Decalage_X)%Brosse_Largeur, + (Y+Brosse_Hauteur-Tiling_Decalage_Y)%Brosse_Hauteur); +} + + // -- Effet de Smooth -- + +byte Effet_Smooth(word X,word Y,byte Couleur) +{ + int R,V,B; + byte C; + int Poids,Poids_total; + byte X2=((X+1)(Limite_Droite+1)) + { + (*Largeur)=(Limite_Droite-(*X))+1; + } + + if ((*Y)(Limite_Bas+1)) + { + (*Hauteur)=(Limite_Bas-(*Y))+1; + } +} + + // -- Calcul de redimensionnement du pinceau pour viter les dbordements + // de l'cran zoom et de l'image -- + +void Calculer_dimensions_clipees_zoom(short * X,short * Y,short * Largeur,short * Hauteur) +{ + if ((*X)(Limite_Droite_Zoom+1)) + { + (*Largeur)=(Limite_Droite_Zoom-(*X))+1; + } + + if ((*Y)(Limite_Bas_Zoom+1)) + { + (*Hauteur)=(Limite_Bas_Zoom-(*Y))+1; + } +} + + + // -- Afficher le pinceau (de faon dfinitive ou non) -- + +void Afficher_pinceau(short X,short Y,byte Couleur,byte Preview) + // X,Y: position du centre du pinceau + // Couleur: couleur appliquer au pinceau + // Preview: "Il ne faut l'afficher qu' l'cran" +{ + short Debut_X; // Position X (dans l'image) partir de laquelle on affiche la brosse/pinceau + short Debut_Y; // Position Y (dans l'image) partir de laquelle on affiche la brosse/pinceau + short Largeur; // Largeur dans l'cran selon laquelle on affiche la brosse/pinceau + short Hauteur; // Hauteur dans l'cran selon laquelle on affiche la brosse/pinceau + short Debut_Compteur_X; // Position X (dans la brosse/pinceau) partir de laquelle on affiche la brosse/pinceau + short Debut_Compteur_Y; // Position Y (dans la brosse/pinceau) partir de laquelle on affiche la brosse/pinceau + short Pos_X; // Position X (dans l'image) en cours d'affichage + short Pos_Y; // Position Y (dans l'image) en cours d'affichage + short Compteur_X; // Position X (dans la brosse/pinceau) en cours d'affichage + short Compteur_Y; // Position Y (dans la brosse/pinceau) en cours d'affichage + short Fin_Compteur_X; // Position X ou s'arrte l'affichade de la brosse/pinceau + short Fin_Compteur_Y; // Position Y ou s'arrte l'affichade de la brosse/pinceau + byte Couleur_temporaire; // Couleur de la brosse en cours d'affichage + int Position; + byte * Temp; + + if (!(Preview && Mouse_K)) + switch (Pinceau_Forme) + { + case FORME_PINCEAU_POINT : // !!! TOUJOURS EN PREVIEW !!! + if ( (Pinceau_X>=Limite_Gauche) + && (Pinceau_X<=Limite_Droite) + && (Pinceau_Y>=Limite_Haut) + && (Pinceau_Y<=Limite_Bas) ) + Pixel_Preview(Pinceau_X,Pinceau_Y,Couleur); + break; + case FORME_PINCEAU_BROSSE_COULEUR : // Brosse en couleur + Debut_X=X-Brosse_Decalage_X; + Debut_Y=Y-Brosse_Decalage_Y; + Largeur=Brosse_Largeur; + Hauteur=Brosse_Hauteur; + Calculer_dimensions_clipees(&Debut_X,&Debut_Y,&Largeur,&Hauteur); + Debut_Compteur_X=Debut_X-(X-Brosse_Decalage_X); + Debut_Compteur_Y=Debut_Y-(Y-Brosse_Decalage_Y); + Fin_Compteur_X=Debut_Compteur_X+Largeur; + Fin_Compteur_Y=Debut_Compteur_Y+Hauteur; + if (Preview) + { + if ( (Largeur>0) && (Hauteur>0) ) + Display_brush_Color(Debut_X-Principal_Decalage_X, + Debut_Y-Principal_Decalage_Y, + Debut_Compteur_X,Debut_Compteur_Y, + Largeur,Hauteur,Back_color, + Brosse_Largeur); + + if (Loupe_Mode) + { + Calculer_dimensions_clipees_zoom(&Debut_X,&Debut_Y,&Largeur,&Hauteur); + Debut_Compteur_X=Debut_X-(X-Brosse_Decalage_X); + Debut_Compteur_Y=Debut_Y-(Y-Brosse_Decalage_Y); + + if ( (Largeur>0) && (Hauteur>0) ) + { + // Corrections des au Zoom: + Debut_X=(Debut_X-Loupe_Decalage_X)*Loupe_Facteur; + Debut_Y=(Debut_Y-Loupe_Decalage_Y)*Loupe_Facteur; + Hauteur=Debut_Y+(Hauteur*Loupe_Facteur); + if (Hauteur>Menu_Ordonnee) + Hauteur=Menu_Ordonnee; + + Display_brush_Color_zoom(Principal_X_Zoom+Debut_X,Debut_Y, + Debut_Compteur_X,Debut_Compteur_Y, + Largeur,Hauteur,Back_color, + Brosse_Largeur, + Buffer_de_ligne_horizontale); + } + } + } + else + { + if ((Smear_Mode) && (Shade_Table==Shade_Table_gauche)) + { + if (Smear_Debut) + { + if ((Largeur>0) && (Hauteur>0)) + Copier_une_partie_d_image_dans_une_autre(Principal_Ecran, + Debut_X,Debut_Y, + Largeur,Hauteur, + Principal_Largeur_image, + Smear_Brosse, + Debut_Compteur_X, + Debut_Compteur_Y, + Smear_Brosse_Largeur); + Smear_Debut=0; + } + else + { + for (Pos_Y=Debut_Y,Compteur_Y=Debut_Compteur_Y;Compteur_Y=Smear_Min_Y) && (Compteur_X>=Smear_Min_X) ) + Afficher_pixel(Pos_X,Pos_Y,Smear_Brosse[Position]); + Smear_Brosse[Position]=Couleur_temporaire; + } + } + Smear_Min_X=Debut_Compteur_X; + Smear_Min_Y=Debut_Compteur_Y; + Smear_Max_X=Fin_Compteur_X; + Smear_Max_Y=Fin_Compteur_Y; + } + else + { + if (Shade_Table==Shade_Table_gauche) + for (Pos_Y=Debut_Y,Compteur_Y=Debut_Compteur_Y;Compteur_Y0) && (Hauteur>0) ) + Display_brush_Mono(Debut_X-Principal_Decalage_X, + Debut_Y-Principal_Decalage_Y, + Debut_Compteur_X,Debut_Compteur_Y, + Largeur,Hauteur, + Back_color,Fore_color, + Brosse_Largeur); + + if (Loupe_Mode) + { + Calculer_dimensions_clipees_zoom(&Debut_X,&Debut_Y,&Largeur,&Hauteur); + Debut_Compteur_X=Debut_X-(X-Brosse_Decalage_X); + Debut_Compteur_Y=Debut_Y-(Y-Brosse_Decalage_Y); + + if ( (Largeur>0) && (Hauteur>0) ) + { + // Corrections des au Zoom: + Debut_X=(Debut_X-Loupe_Decalage_X)*Loupe_Facteur; + Debut_Y=(Debut_Y-Loupe_Decalage_Y)*Loupe_Facteur; + Hauteur=Debut_Y+(Hauteur*Loupe_Facteur); + if (Hauteur>Menu_Ordonnee) + Hauteur=Menu_Ordonnee; + + Display_brush_Mono_zoom(Principal_X_Zoom+Debut_X,Debut_Y, + Debut_Compteur_X,Debut_Compteur_Y, + Largeur,Hauteur, + Back_color,Fore_color, + Brosse_Largeur, + Buffer_de_ligne_horizontale); + } + } + } + else + { + if ((Smear_Mode) && (Shade_Table==Shade_Table_gauche)) + { + if (Smear_Debut) + { + if ((Largeur>0) && (Hauteur>0)) + Copier_une_partie_d_image_dans_une_autre(Principal_Ecran, + Debut_X,Debut_Y, + Largeur,Hauteur, + Principal_Largeur_image, + Smear_Brosse, + Debut_Compteur_X, + Debut_Compteur_Y, + Smear_Brosse_Largeur); + Smear_Debut=0; + } + else + { + for (Pos_Y=Debut_Y,Compteur_Y=Debut_Compteur_Y;Compteur_Y=Smear_Min_Y) && (Compteur_X>=Smear_Min_X) ) + Afficher_pixel(Pos_X,Pos_Y,Smear_Brosse[Position]); + Smear_Brosse[Position]=Couleur_temporaire; + } + } + Smear_Min_X=Debut_Compteur_X; + Smear_Min_Y=Debut_Compteur_Y; + Smear_Max_X=Fin_Compteur_X; + Smear_Max_Y=Fin_Compteur_Y; + } + else + { + for (Pos_Y=Debut_Y,Compteur_Y=Debut_Compteur_Y;Compteur_Y0) && (Hauteur>0) ) + Display_brush_Mono(Debut_X-Principal_Decalage_X, + Debut_Y-Principal_Decalage_Y, + Debut_Compteur_X,Debut_Compteur_Y, + Largeur,Hauteur, + 0,Fore_color, + TAILLE_MAXI_PINCEAU); + + if (Loupe_Mode) + { + Calculer_dimensions_clipees_zoom(&Debut_X,&Debut_Y,&Largeur,&Hauteur); + Debut_Compteur_X=Debut_X-(X-Pinceau_Decalage_X); + Debut_Compteur_Y=Debut_Y-(Y-Pinceau_Decalage_Y); + + if ( (Largeur>0) && (Hauteur>0) ) + { + // Corrections des au Zoom: + Debut_X=(Debut_X-Loupe_Decalage_X)*Loupe_Facteur; + Debut_Y=(Debut_Y-Loupe_Decalage_Y)*Loupe_Facteur; + Hauteur=Debut_Y+(Hauteur*Loupe_Facteur); + if (Hauteur>Menu_Ordonnee) + Hauteur=Menu_Ordonnee; + + Display_brush_Mono_zoom(Principal_X_Zoom+Debut_X,Debut_Y, + Debut_Compteur_X,Debut_Compteur_Y, + Largeur,Hauteur, + 0,Fore_color, + TAILLE_MAXI_PINCEAU, + Buffer_de_ligne_horizontale); + } + } + + Brosse=Temp; + } + else + { + if ((Smear_Mode) && (Shade_Table==Shade_Table_gauche)) + { + if (Smear_Debut) + { + if ((Largeur>0) && (Hauteur>0)) + Copier_une_partie_d_image_dans_une_autre(Principal_Ecran, + Debut_X,Debut_Y, + Largeur,Hauteur, + Principal_Largeur_image, + Smear_Brosse, + Debut_Compteur_X, + Debut_Compteur_Y, + Smear_Brosse_Largeur); + Smear_Debut=0; + } + else + { + for (Pos_Y=Debut_Y,Compteur_Y=Debut_Compteur_Y;Compteur_Y=Smear_Min_Y) && (Compteur_X>=Smear_Min_X) ) + Afficher_pixel(Pos_X,Pos_Y,Smear_Brosse[Position]); + Smear_Brosse[Position]=Couleur_temporaire; + } + } + Smear_Min_X=Debut_Compteur_X; + Smear_Min_Y=Debut_Compteur_Y; + Smear_Max_X=Fin_Compteur_X; + Smear_Max_Y=Fin_Compteur_Y; + } + else + { + for (Pos_Y=Debut_Y,Compteur_Y=Debut_Compteur_Y;Compteur_Y=Limite_Gauche) + && (Pinceau_X<=Limite_Droite) + && (Pinceau_Y>=Limite_Haut) + && (Pinceau_Y<=Limite_Bas) ) + Pixel_Preview(Pinceau_X,Pinceau_Y,Lit_pixel_dans_ecran_courant(Pinceau_X,Pinceau_Y)); + break; + case FORME_PINCEAU_BROSSE_COULEUR : // Brosse en couleur + case FORME_PINCEAU_BROSSE_MONOCHROME : // Brosse monochrome + Debut_X=X-Brosse_Decalage_X; + Debut_Y=Y-Brosse_Decalage_Y; + Largeur=Brosse_Largeur; + Hauteur=Brosse_Hauteur; + Calculer_dimensions_clipees(&Debut_X,&Debut_Y,&Largeur,&Hauteur); + Debut_Compteur_X=Debut_X-(X-Brosse_Decalage_X); + Debut_Compteur_Y=Debut_Y-(Y-Brosse_Decalage_Y); + Fin_Compteur_X=Debut_Compteur_X+Largeur; + Fin_Compteur_Y=Debut_Compteur_Y+Hauteur; + + if ( (Largeur>0) && (Hauteur>0) ) + Clear_brush(Debut_X-Principal_Decalage_X, + Debut_Y-Principal_Decalage_Y, + Debut_Compteur_X,Debut_Compteur_Y, + Largeur,Hauteur,Back_color, + Principal_Largeur_image); + + if (Loupe_Mode) + { + Calculer_dimensions_clipees_zoom(&Debut_X,&Debut_Y,&Largeur,&Hauteur); + Debut_Compteur_X=Debut_X; + Debut_Compteur_Y=Debut_Y; + + if ( (Largeur>0) && (Hauteur>0) ) + { + // Corrections dues au Zoom: + Debut_X=(Debut_X-Loupe_Decalage_X)*Loupe_Facteur; + Debut_Y=(Debut_Y-Loupe_Decalage_Y)*Loupe_Facteur; + Hauteur=Debut_Y+(Hauteur*Loupe_Facteur); + if (Hauteur>Menu_Ordonnee) + Hauteur=Menu_Ordonnee; + + Clear_brush_zoom(Principal_X_Zoom+Debut_X,Debut_Y, + Debut_Compteur_X,Debut_Compteur_Y, + Largeur,Hauteur,Back_color, + Principal_Largeur_image, + Buffer_de_ligne_horizontale); + } + } + break; + default: // Pinceau + Debut_X=X-Pinceau_Decalage_X; + Debut_Y=Y-Pinceau_Decalage_Y; + Largeur=Pinceau_Largeur; + Hauteur=Pinceau_Hauteur; + Calculer_dimensions_clipees(&Debut_X,&Debut_Y,&Largeur,&Hauteur); + Debut_Compteur_X=Debut_X-(X-Pinceau_Decalage_X); + Debut_Compteur_Y=Debut_Y-(Y-Pinceau_Decalage_Y); + Fin_Compteur_X=Debut_Compteur_X+Largeur; + Fin_Compteur_Y=Debut_Compteur_Y+Hauteur; + + Temp=Brosse; + Brosse=Pinceau_Sprite; + + if ( (Largeur>0) && (Hauteur>0) ) + { + Clear_brush(Debut_X-Principal_Decalage_X, + Debut_Y-Principal_Decalage_Y, + Debut_Compteur_X,Debut_Compteur_Y, + Largeur,Hauteur,0, + Principal_Largeur_image); + } + + if (Loupe_Mode) + { + Calculer_dimensions_clipees_zoom(&Debut_X,&Debut_Y,&Largeur,&Hauteur); + Debut_Compteur_X=Debut_X; + Debut_Compteur_Y=Debut_Y; + + if ( (Largeur>0) && (Hauteur>0) ) + { + // Corrections dues au Zoom: + Debut_X=(Debut_X-Loupe_Decalage_X)*Loupe_Facteur; + Debut_Y=(Debut_Y-Loupe_Decalage_Y)*Loupe_Facteur; + Hauteur=Debut_Y+(Hauteur*Loupe_Facteur); + if (Hauteur>Menu_Ordonnee) + Hauteur=Menu_Ordonnee; + + Clear_brush_zoom(Principal_X_Zoom+Debut_X,Debut_Y, + Debut_Compteur_X,Debut_Compteur_Y, + Largeur,Hauteur,0, + Principal_Largeur_image, + Buffer_de_ligne_horizontale); + } + } + + Brosse=Temp; + break; + } +} + + +// -- Fonctions de manipulation du curseur ----------------------------------- + + + // -- Afficher une barre horizontale XOR zoome + +void Ligne_horizontale_XOR_Zoom(short Pos_X, short Pos_Y, short Largeur) +{ + short Pos_X_reelle=Principal_X_Zoom+(Pos_X-Loupe_Decalage_X)*Loupe_Facteur; + short Pos_Y_reelle=(Pos_Y-Loupe_Decalage_Y)*Loupe_Facteur; + short Largeur_reelle=Largeur*Loupe_Facteur; + short Pos_Y_Fin=(Pos_Y_reelle+Loupe_Facteur=Principal_X_Zoom) ) ) + || (Une_fenetre_est_ouverte) || (Forme_curseur==FORME_CURSEUR_SABLIER) ) + Forme=Forme_curseur; + else + Forme=FORME_CURSEUR_FLECHE; + + switch(Forme) + { + case FORME_CURSEUR_CIBLE : + if (!Cacher_pinceau) + Afficher_pinceau(Pinceau_X,Pinceau_Y,Fore_color,1); + if (!Cacher_curseur) + { + if (Config.Curseur==1) + { + Debut_Y=(Mouse_Y<6)?6-Mouse_Y:0; + if (Debut_Y<4) + Ligne_verticale_XOR (Mouse_X,Mouse_Y+Debut_Y-6,4-Debut_Y); + + Debut_X=(Mouse_X<6)?(short)6-Mouse_X:0; + if (Debut_X<4) + Ligne_horizontale_XOR(Mouse_X+Debut_X-6,Mouse_Y,4-Debut_X); + + Fin_X=(Mouse_X+7>Largeur_ecran)?Mouse_X+7-Largeur_ecran:0; + if (Fin_X<4) + Ligne_horizontale_XOR(Mouse_X+3,Mouse_Y,4-Fin_X); + + Fin_Y=(Mouse_Y+7>Menu_Ordonnee/*Hauteur_ecran*/)?Mouse_Y+7-Menu_Ordonnee/*Hauteur_ecran*/:0; + if (Fin_Y<4) + Ligne_verticale_XOR (Mouse_X,Mouse_Y+3,4-Fin_Y); + } + else + { + Temp=(Config.Curseur)?FORME_CURSEUR_CIBLE_FINE:FORME_CURSEUR_CIBLE; + Debut_X=Mouse_X-Curseur_Decalage_X[Temp]; + Debut_Y=Mouse_Y-Curseur_Decalage_Y[Temp]; + + for (Pos_X=Debut_X,Compteur_X=0;Compteur_X<15;Pos_X++,Compteur_X++) + for (Pos_Y=Debut_Y,Compteur_Y=0;Compteur_Y<15;Pos_Y++,Compteur_Y++) + { + Couleur=SPRITE_CURSEUR[Temp][Compteur_Y][Compteur_X]; + if ( (Pos_X>=0) && (Pos_X=0) && (Pos_YLargeur_ecran)?Mouse_X+6-Largeur_ecran:0; + if (Fin_X<3) + Ligne_horizontale_XOR(Mouse_X+3,Mouse_Y,3-Fin_X); + + Fin_Y=(Mouse_Y+6>Menu_Ordonnee/*Hauteur_ecran*/)?Mouse_Y+6-Menu_Ordonnee/*Hauteur_ecran*/:0; + if (Fin_Y<3) + Ligne_verticale_XOR (Mouse_X,Mouse_Y+3,3-Fin_Y); + + // Petites barres aux extrmits + + Debut_X=(!Mouse_X); + Debut_Y=(!Mouse_Y); + Fin_X=(Mouse_X>=Largeur_ecran-1); + Fin_Y=(Mouse_Y>=Menu_Ordonnee-1); + + if (Mouse_Y>5) + Ligne_horizontale_XOR(Debut_X+Mouse_X-1,Mouse_Y-6,3-(Debut_X+Fin_X)); + + if (Mouse_X>5) + Ligne_verticale_XOR (Mouse_X-6,Debut_Y+Mouse_Y-1,3-(Debut_Y+Fin_Y)); + + if (Mouse_X=0) && (Pos_X=0) && (Pos_Y=0) && (Pos_Y>=0) ) + { + FOND_CURSEUR[Compteur_Y][Compteur_X]=Lit_pixel(Pos_X,Pos_Y); + if (Couleur!=CM_Trans) + Pixel(Pos_X,Pos_Y,Couleur); + } + } + break; + case FORME_CURSEUR_CIBLE_XOR : + Pos_X=Pinceau_X-Principal_Decalage_X; + Pos_Y=Pinceau_Y-Principal_Decalage_Y; + + Compteur_X=(Loupe_Mode)?Principal_Split:Largeur_ecran; // Largeur de la barre XOR + if ((Pos_Y=Limite_Haut)) + Ligne_horizontale_XOR(0,Pinceau_Y-Principal_Decalage_Y,Compteur_X); + + if ((Pos_X=Limite_Gauche)) + Ligne_verticale_XOR(Pinceau_X-Principal_Decalage_X,0,Menu_Ordonnee); + + if (Loupe_Mode) + { + if ((Pinceau_Y>=Limite_Haut_Zoom) && (Pinceau_Y<=Limite_visible_Bas_Zoom)) + Ligne_horizontale_XOR_Zoom(Limite_Gauche_Zoom,Pinceau_Y,Loupe_Largeur); + if ((Pinceau_X>=Limite_Gauche_Zoom) && (Pinceau_X<=Limite_visible_Droite_Zoom)) + Ligne_verticale_XOR_Zoom(Pinceau_X,Limite_Haut_Zoom,Loupe_Hauteur); + } + break; + case FORME_CURSEUR_RECTANGLE_XOR : + // !!! Cette forme ne peut pas tre utilise en mode Loupe !!! + Debut_X=Mouse_X-(Loupe_Largeur>>1); + Debut_Y=Mouse_Y-(Loupe_Hauteur>>1); + if (Debut_X+Loupe_Largeur>=Limite_Droite-Principal_Decalage_X) + Debut_X=Limite_Droite-Loupe_Largeur-Principal_Decalage_X+1; + if (Debut_Y+Loupe_Hauteur>=Limite_Bas-Principal_Decalage_Y) + Debut_Y=Limite_Bas-Loupe_Hauteur-Principal_Decalage_Y+1; + if (Debut_X<0) + Debut_X=0; + if (Debut_Y<0) + Debut_Y=0; + Fin_X=Debut_X+Loupe_Largeur-1; + Fin_Y=Debut_Y+Loupe_Hauteur-1; + + Ligne_horizontale_XOR(Debut_X,Debut_Y,Loupe_Largeur); + Ligne_verticale_XOR(Debut_X,Debut_Y+1,Loupe_Hauteur-2); + Ligne_verticale_XOR( Fin_X,Debut_Y+1,Loupe_Hauteur-2); + Ligne_horizontale_XOR(Debut_X, Fin_Y,Loupe_Largeur); + + Debut_X=(Mouse_X-3); + Debut_Y=(Mouse_Y-3); + Fin_X =(Mouse_X+4); + Fin_Y =(Mouse_Y+4); + if (Debut_X<0) + Debut_X=0; + if (Debut_Y<0) + Debut_Y=0; + if (Fin_X>Largeur_ecran) + Fin_X=Largeur_ecran; + if (Fin_Y>Menu_Ordonnee) + Fin_Y=Menu_Ordonnee; + + Ligne_horizontale_XOR(Debut_X,Mouse_Y,Fin_X-Debut_X); + Ligne_verticale_XOR (Mouse_X,Debut_Y,Fin_Y-Debut_Y); + break; + default: //case FORME_CURSEUR_ROTATE_XOR : + Debut_X=1-(Brosse_Largeur>>1); + Debut_Y=1-(Brosse_Hauteur>>1); + Fin_X=Debut_X+Brosse_Largeur-1; + Fin_Y=Debut_Y+Brosse_Hauteur-1; + + if (Brosse_Centre_rotation_defini) + { + if ( (Brosse_Centre_rotation_X==Pinceau_X) + && (Brosse_Centre_rotation_Y==Pinceau_Y) ) + { + cosA=1.0; + sinA=0.0; + } + else + { + Pos_X=Pinceau_X-Brosse_Centre_rotation_X; + Pos_Y=Pinceau_Y-Brosse_Centre_rotation_Y; + cosA=(float)Pos_X/sqrt((Pos_X*Pos_X)+(Pos_Y*Pos_Y)); + sinA=sin(acos(cosA)); + if (Pos_Y>0) sinA=-sinA; + } + + Transformer_point(Debut_X,Debut_Y, cosA,sinA, &X1,&Y1); + Transformer_point(Fin_X ,Debut_Y, cosA,sinA, &X2,&Y2); + Transformer_point(Debut_X,Fin_Y , cosA,sinA, &X3,&Y3); + Transformer_point(Fin_X ,Fin_Y , cosA,sinA, &X4,&Y4); + + X1+=Brosse_Centre_rotation_X; + Y1+=Brosse_Centre_rotation_Y; + X2+=Brosse_Centre_rotation_X; + Y2+=Brosse_Centre_rotation_Y; + X3+=Brosse_Centre_rotation_X; + Y3+=Brosse_Centre_rotation_Y; + X4+=Brosse_Centre_rotation_X; + Y4+=Brosse_Centre_rotation_Y; + Pixel_figure_Preview_xor(Brosse_Centre_rotation_X,Brosse_Centre_rotation_Y,0); + Tracer_ligne_Preview_xor(Brosse_Centre_rotation_X,Brosse_Centre_rotation_Y,Pinceau_X,Pinceau_Y,0); + } + else + { + X1=X3=1-Brosse_Largeur; + Y1=Y2=Debut_Y; + X2=X4=Pinceau_X; + Y3=Y4=Fin_Y; + + X1+=Pinceau_X; + Y1+=Pinceau_Y; + Y2+=Pinceau_Y; + X3+=Pinceau_X; + Y3+=Pinceau_Y; + Y4+=Pinceau_Y; + Pixel_figure_Preview_xor(Pinceau_X-Fin_X,Pinceau_Y,0); + Tracer_ligne_Preview_xor(Pinceau_X-Fin_X,Pinceau_Y,Pinceau_X,Pinceau_Y,0); + } + + Tracer_ligne_Preview_xor(X1,Y1,X2,Y2,0); + Tracer_ligne_Preview_xor(X2,Y2,X4,Y4,0); + Tracer_ligne_Preview_xor(X4,Y4,X3,Y3,0); + Tracer_ligne_Preview_xor(X3,Y3,X1,Y1,0); + } +} + + // -- Effacer le curseur -- + +void Effacer_curseur(void) +{ + byte Forme; + short Debut_X; + short Debut_Y; + short Fin_X; + short Fin_Y; + short Pos_X; + short Pos_Y; + short Compteur_X; + short Compteur_Y; + short Fin_Compteur_X; // Position X ou s'arrte l'affichage de la brosse/pinceau + short Fin_Compteur_Y; // Position Y ou s'arrte l'affichage de la brosse/pinceau + int Temp; + byte Couleur; + float cosA,sinA; + short X1,Y1,X2,Y2,X3,Y3,X4,Y4; + + if ( ( (Mouse_Y=Principal_X_Zoom) ) ) + || (Une_fenetre_est_ouverte) || (Forme_curseur==FORME_CURSEUR_SABLIER) ) + Forme=Forme_curseur; + else + Forme=FORME_CURSEUR_FLECHE; + + switch(Forme) + { + case FORME_CURSEUR_CIBLE : + if (!Cacher_curseur) + { + if (Config.Curseur==1) + { + Debut_Y=(Mouse_Y<6)?6-Mouse_Y:0; + if (Debut_Y<4) + Ligne_verticale_XOR (Mouse_X,Mouse_Y+Debut_Y-6,4-Debut_Y); + + Debut_X=(Mouse_X<6)?(short)6-Mouse_X:0; + if (Debut_X<4) + Ligne_horizontale_XOR(Mouse_X+Debut_X-6,Mouse_Y,4-Debut_X); + + Fin_X=(Mouse_X+7>Largeur_ecran)?Mouse_X+7-Largeur_ecran:0; + if (Fin_X<4) + Ligne_horizontale_XOR(Mouse_X+3,Mouse_Y,4-Fin_X); + + Fin_Y=(Mouse_Y+7>Menu_Ordonnee/*Hauteur_ecran*/)?Mouse_Y+7-Menu_Ordonnee/*Hauteur_ecran*/:0; + if (Fin_Y<4) + Ligne_verticale_XOR (Mouse_X,Mouse_Y+3,4-Fin_Y); + } + else + { + Temp=(Config.Curseur)?FORME_CURSEUR_CIBLE_FINE:FORME_CURSEUR_CIBLE; + Debut_X=Mouse_X-Curseur_Decalage_X[Temp]; + Debut_Y=Mouse_Y-Curseur_Decalage_Y[Temp]; + + for (Pos_X=Debut_X,Compteur_X=0;Compteur_X<15;Pos_X++,Compteur_X++) + for (Pos_Y=Debut_Y,Compteur_Y=0;Compteur_Y<15;Pos_Y++,Compteur_Y++) + if ( (Pos_X>=0) && (Pos_X=0) && (Pos_YLargeur_ecran)?Mouse_X+6-Largeur_ecran:0; + if (Fin_X<3) + Ligne_horizontale_XOR(Mouse_X+3,Mouse_Y,3-Fin_X); + + Fin_Y=(Mouse_Y+6>Menu_Ordonnee/*Hauteur_ecran*/)?Mouse_Y+6-Menu_Ordonnee/*Hauteur_ecran*/:0; + if (Fin_Y<3) + Ligne_verticale_XOR (Mouse_X,Mouse_Y+3,3-Fin_Y); + + // Petites barres aux extrmits + + Debut_X=(!Mouse_X); + Debut_Y=(!Mouse_Y); + Fin_X=(Mouse_X>=Largeur_ecran-1); + Fin_Y=(Mouse_Y>=Menu_Ordonnee-1); + + if (Mouse_Y>5) + Ligne_horizontale_XOR(Debut_X+Mouse_X-1,Mouse_Y-6,3-(Debut_X+Fin_X)); + + if (Mouse_X>5) + Ligne_verticale_XOR (Mouse_X-6,Debut_Y+Mouse_Y-1,3-(Debut_Y+Fin_Y)); + + if (Mouse_X=0) && (Pos_X=0) && (Pos_Y=0) && (Pos_Y>=0) ) + Pixel(Pos_X,Pos_Y,FOND_CURSEUR[Compteur_Y][Compteur_X]); + break; + case FORME_CURSEUR_CIBLE_XOR : + Pos_X=Pinceau_X-Principal_Decalage_X; + Pos_Y=Pinceau_Y-Principal_Decalage_Y; + + Compteur_X=(Loupe_Mode)?Principal_Split:Largeur_ecran; // Largeur de la barre XOR + if ((Pos_Y=Limite_Haut)) + Ligne_horizontale_XOR(0,Pinceau_Y-Principal_Decalage_Y,Compteur_X); + + if ((Pos_X=Limite_Gauche)) + Ligne_verticale_XOR(Pinceau_X-Principal_Decalage_X,0,Menu_Ordonnee); + + if (Loupe_Mode) + { + if ((Pinceau_Y>=Limite_Haut_Zoom) && (Pinceau_Y<=Limite_visible_Bas_Zoom)) + Ligne_horizontale_XOR_Zoom(Limite_Gauche_Zoom,Pinceau_Y,Loupe_Largeur); + if ((Pinceau_X>=Limite_Gauche_Zoom) && (Pinceau_X<=Limite_visible_Droite_Zoom)) + Ligne_verticale_XOR_Zoom(Pinceau_X,Limite_Haut_Zoom,Loupe_Hauteur); + } + break; + case FORME_CURSEUR_RECTANGLE_XOR : + // !!! Cette forme ne peut pas tre utilise en mode Loupe !!! + Debut_X=Mouse_X-(Loupe_Largeur>>1); + Debut_Y=Mouse_Y-(Loupe_Hauteur>>1); + if (Debut_X+Loupe_Largeur>=Limite_Droite-Principal_Decalage_X) + Debut_X=Limite_Droite-Loupe_Largeur-Principal_Decalage_X+1; + if (Debut_Y+Loupe_Hauteur>=Limite_Bas-Principal_Decalage_Y) + Debut_Y=Limite_Bas-Loupe_Hauteur-Principal_Decalage_Y+1; + if (Debut_X<0) + Debut_X=0; + if (Debut_Y<0) + Debut_Y=0; + Fin_X=Debut_X+Loupe_Largeur-1; + Fin_Y=Debut_Y+Loupe_Hauteur-1; + + Ligne_horizontale_XOR(Debut_X,Debut_Y,Loupe_Largeur); + Ligne_verticale_XOR(Debut_X,Debut_Y+1,Loupe_Hauteur-2); + Ligne_verticale_XOR( Fin_X,Debut_Y+1,Loupe_Hauteur-2); + Ligne_horizontale_XOR(Debut_X, Fin_Y,Loupe_Largeur); + + Debut_X=(Mouse_X-3); + Debut_Y=(Mouse_Y-3); + Fin_X =(Mouse_X+4); + Fin_Y =(Mouse_Y+4); + if (Debut_X<0) + Debut_X=0; + if (Debut_Y<0) + Debut_Y=0; + if (Fin_X>Largeur_ecran) + Fin_X=Largeur_ecran; + if (Fin_Y>Menu_Ordonnee) + Fin_Y=Menu_Ordonnee; + + Ligne_horizontale_XOR(Debut_X,Mouse_Y,Fin_X-Debut_X); + Ligne_verticale_XOR (Mouse_X,Debut_Y,Fin_Y-Debut_Y); + break; + default: //case FORME_CURSEUR_ROTATE_XOR : + Debut_X=1-(Brosse_Largeur>>1); + Debut_Y=1-(Brosse_Hauteur>>1); + Fin_X=Debut_X+Brosse_Largeur-1; + Fin_Y=Debut_Y+Brosse_Hauteur-1; + + if (Brosse_Centre_rotation_defini) + { + if ( (Brosse_Centre_rotation_X==Pinceau_X) + && (Brosse_Centre_rotation_Y==Pinceau_Y) ) + { + cosA=1.0; + sinA=0.0; + } + else + { + Pos_X=Pinceau_X-Brosse_Centre_rotation_X; + Pos_Y=Pinceau_Y-Brosse_Centre_rotation_Y; + cosA=(float)Pos_X/sqrt((Pos_X*Pos_X)+(Pos_Y*Pos_Y)); + sinA=sin(acos(cosA)); + if (Pos_Y>0) sinA=-sinA; + } + + Transformer_point(Debut_X,Debut_Y, cosA,sinA, &X1,&Y1); + Transformer_point(Fin_X ,Debut_Y, cosA,sinA, &X2,&Y2); + Transformer_point(Debut_X,Fin_Y , cosA,sinA, &X3,&Y3); + Transformer_point(Fin_X ,Fin_Y , cosA,sinA, &X4,&Y4); + + X1+=Brosse_Centre_rotation_X; + Y1+=Brosse_Centre_rotation_Y; + X2+=Brosse_Centre_rotation_X; + Y2+=Brosse_Centre_rotation_Y; + X3+=Brosse_Centre_rotation_X; + Y3+=Brosse_Centre_rotation_Y; + X4+=Brosse_Centre_rotation_X; + Y4+=Brosse_Centre_rotation_Y; + Pixel_figure_Preview_xor(Brosse_Centre_rotation_X,Brosse_Centre_rotation_Y,0); + Tracer_ligne_Preview_xor(Brosse_Centre_rotation_X,Brosse_Centre_rotation_Y,Pinceau_X,Pinceau_Y,0); + } + else + { + X1=X3=1-Brosse_Largeur; + Y1=Y2=Debut_Y; + X2=X4=Pinceau_X; + Y3=Y4=Fin_Y; + + X1+=Pinceau_X; + Y1+=Pinceau_Y; + Y2+=Pinceau_Y; + X3+=Pinceau_X; + Y3+=Pinceau_Y; + Y4+=Pinceau_Y; + Pixel_figure_Preview_xor(Pinceau_X-Fin_X,Pinceau_Y,0); + Tracer_ligne_Preview_xor(Pinceau_X-Fin_X,Pinceau_Y,Pinceau_X,Pinceau_Y,0); + } + + Tracer_ligne_Preview_xor(X1,Y1,X2,Y2,0); + Tracer_ligne_Preview_xor(X2,Y2,X4,Y4,0); + Tracer_ligne_Preview_xor(X4,Y4,X3,Y3,0); + Tracer_ligne_Preview_xor(X3,Y3,X1,Y1,0); + } +} + + + +//---- Fentre demandant de confirmer une action et renvoyant la rponse ----- +byte Demande_de_confirmation(char * Message) +{ + short Bouton_clicke; + word Largeur_de_la_fenetre; + + Largeur_de_la_fenetre=(strlen(Message)<<3)+20; + + if (Largeur_de_la_fenetre<120) + Largeur_de_la_fenetre=120; + + Ouvrir_fenetre(Largeur_de_la_fenetre,60,"Confirmation"); + + Print_dans_fenetre((Largeur_de_la_fenetre>>1)-(strlen(Message)<<2),20,Message,CM_Noir,CM_Clair); + + Fenetre_Definir_bouton_normal((Largeur_de_la_fenetre/3)-20 ,37,40,14,"Yes",1,1,0x0015); // 1 + Fenetre_Definir_bouton_normal(((Largeur_de_la_fenetre<<1)/3)-20,37,40,14,"No" ,1,1,0x0031); // 2 + + Afficher_curseur(); + + do + { + Bouton_clicke=Fenetre_Bouton_clicke(); + if (Touche==0x001C) Bouton_clicke=1; + if (Touche==0x0001) Bouton_clicke=2; + } + while (Bouton_clicke<=0); + + Fermer_fenetre(); + Afficher_curseur(); + + return (Bouton_clicke==1)? 1 : 0; +} + + + +//---- Fentre avertissant de quelque chose et attendant un click sur OK ----- +void Warning_message(char * Message) +{ + short Bouton_clicke; + word Largeur_de_la_fenetre; + + Largeur_de_la_fenetre=(strlen(Message)<<3)+20; + if (Largeur_de_la_fenetre<120) + Largeur_de_la_fenetre=120; + + Ouvrir_fenetre(Largeur_de_la_fenetre,60,"Warning!"); + + Print_dans_fenetre((Largeur_de_la_fenetre>>1)-(strlen(Message)<<2),20,Message,CM_Noir,CM_Clair); + Fenetre_Definir_bouton_normal((Largeur_de_la_fenetre>>1)-20 ,37,40,14,"OK",1,1,0x001C); // 1 + Afficher_curseur(); + + do + Bouton_clicke=Fenetre_Bouton_clicke(); + while ((Bouton_clicke<=0) && (Touche!=0x0001) && (Touche!=0x0018)); + + Fermer_fenetre(); + Afficher_curseur(); +} + + + +// -- Fonction diverses d'affichage ------------------------------------------ + + // -- Reafficher toute l'image (en prenant en compte le facteur de zoom) -- + +void Afficher_ecran(void) +{ + word Largeur; + word Hauteur; + + // ---/\/\/\ Partie non zoome: /\/\/\--- + if (Loupe_Mode) + { + if (Principal_Largeur_image 64 lignes fct(Menu_Facteur) + word Nb_couleurs =(Debut_block<=Fin_block)?Fin_block-Debut_block+1:Debut_block-Fin_block+1; + word Ligne_en_cours=(Debut_block<=Fin_block)?0:Total_lignes-1; + + word Debut_X =Fenetre_Pos_X+(Menu_Facteur_X*Pos_X); + word Largeur_ligne =Menu_Facteur_X<<4; // <=> 16 pixels fct(Menu_Facteur) + + word Debut_Y =Fenetre_Pos_Y+(Menu_Facteur_Y*Pos_Y); + word Fin_Y =Debut_Y+Total_lignes; + word Indice; + + if (Debut_block>Fin_block) + { + Indice=Debut_block; + Debut_block=Fin_block; + Fin_block=Indice; + } + + for (Indice=Debut_Y;IndiceFin_X) + { + Temporaire=Debut_X; + Debut_X =Fin_X; + Fin_X =Temporaire; + } + if (Debut_Y>Fin_Y) + { + Temporaire=Debut_Y; + Debut_Y =Fin_Y; + Fin_Y =Temporaire; + } + + // On ne capture la nouvelle brosse que si elle est au moins partiellement + // dans l'image: + + if ((Debut_XPrincipal_Largeur_image) + Nouvelle_Brosse_Largeur=Principal_Largeur_image-Debut_X; + if (Debut_Y+Nouvelle_Brosse_Hauteur>Principal_Hauteur_image) + Nouvelle_Brosse_Hauteur=Principal_Hauteur_image-Debut_Y; + + if ( (((long)Brosse_Hauteur)*Brosse_Largeur) != + (((long)Nouvelle_Brosse_Hauteur)*Nouvelle_Brosse_Largeur) ) + { + free(Brosse); + Brosse=(byte *)malloc(((long)Nouvelle_Brosse_Hauteur)*Nouvelle_Brosse_Largeur); + if (!Brosse) + { + Erreur(0); + + Brosse=(byte *)malloc(1*1); + Nouvelle_Brosse_Hauteur=Nouvelle_Brosse_Largeur=1; + *Brosse=Fore_color; + } + } + Brosse_Largeur=Nouvelle_Brosse_Largeur; + Brosse_Hauteur=Nouvelle_Brosse_Hauteur; + + free(Smear_Brosse); + Smear_Brosse_Largeur=(Brosse_Largeur>TAILLE_MAXI_PINCEAU)?Brosse_Largeur:TAILLE_MAXI_PINCEAU; + Smear_Brosse_Hauteur=(Brosse_Hauteur>TAILLE_MAXI_PINCEAU)?Brosse_Hauteur:TAILLE_MAXI_PINCEAU; + Smear_Brosse=(byte *)malloc(((long)Smear_Brosse_Hauteur)*Smear_Brosse_Largeur); + + if (!Smear_Brosse) // On ne peut mme pas allouer la brosse du smear! + { + Erreur(0); + + free(Brosse); + Brosse=(byte *)malloc(1*1); + Brosse_Hauteur=1; + Brosse_Largeur=1; + + Smear_Brosse=(byte *)malloc(TAILLE_MAXI_PINCEAU*TAILLE_MAXI_PINCEAU); + Smear_Brosse_Hauteur=TAILLE_MAXI_PINCEAU; + Smear_Brosse_Largeur=TAILLE_MAXI_PINCEAU; + } + + Copier_image_dans_brosse(Debut_X,Debut_Y,Brosse_Largeur,Brosse_Hauteur,Principal_Largeur_image); + + // On regarde s'il faut effacer quelque chose: + if (Effacement) + { + for (Pos_Y=Debut_Y;Pos_Y>1); + Brosse_Decalage_Y=(Brosse_Hauteur>>1); + } +} + + +void Rotate_90_deg() +{ + short Temporaire; + byte * Nouvelle_Brosse; + + Nouvelle_Brosse=(byte *)malloc(((long)Brosse_Hauteur)*Brosse_Largeur); + if (Nouvelle_Brosse) + { + Rotate_90_deg_LOWLEVEL(Brosse,Nouvelle_Brosse); + free(Brosse); + Brosse=Nouvelle_Brosse; + + Temporaire=Brosse_Largeur; + Brosse_Largeur=Brosse_Hauteur; + Brosse_Hauteur=Temporaire; + + Temporaire=Smear_Brosse_Largeur; + Smear_Brosse_Largeur=Smear_Brosse_Hauteur; + Smear_Brosse_Hauteur=Temporaire; + + // On centre la prise sur la brosse + Brosse_Decalage_X=(Brosse_Largeur>>1); + Brosse_Decalage_Y=(Brosse_Hauteur>>1); + } + else + Erreur(0); +} + + +void Remap_brosse(void) +{ + short Pos_X; // Variable de balayage de la brosse + short Pos_Y; // Variable de balayage de la brosse + byte Utilisee[256]; // Tableau de boolens "La couleur est utilise" + int Couleur; + + + // On commence par initialiser le tableau de boolens faux + for (Couleur=0;Couleur<=255;Couleur++) + Utilisee[Couleur]=0; + + // On calcule la table d'utilisation des couleurs + for (Pos_Y=0;Pos_Y>1); + Brosse_Decalage_Y=(Brosse_Hauteur>>1); + + free(Temporaire); // Libration de l'ancienne brosse + + // Rallocation d'un buffer de Smear + free(Smear_Brosse); + Smear_Brosse_Largeur=(Brosse_Largeur>TAILLE_MAXI_PINCEAU)?Brosse_Largeur:TAILLE_MAXI_PINCEAU; + Smear_Brosse_Hauteur=(Brosse_Hauteur>TAILLE_MAXI_PINCEAU)?Brosse_Hauteur:TAILLE_MAXI_PINCEAU; + Smear_Brosse=(byte *)malloc(((long)Smear_Brosse_Largeur)*Smear_Brosse_Hauteur); + } + else + Erreur(0); // Pas assez de mmoire! +} + + +void Nibble_brush(void) +{ + long Pos,Pos_X,Pos_Y; + byte Etat; + byte * Nouvelle_brosse; + byte * Temporaire; + word Largeur; + word Hauteur; + + if ( (Brosse_Largeur>2) && (Brosse_Hauteur>2) ) + { + Largeur=Brosse_Largeur-2; + Hauteur=Brosse_Hauteur-2; + Nouvelle_brosse=(byte *)malloc(((long)Largeur)*Hauteur); + + if (Nouvelle_brosse) + { + // On copie la brosse courante dans la nouvelle + Copier_une_partie_d_image_dans_une_autre(Brosse, // Source + 1, + 1, + Largeur, + Hauteur, + Brosse_Largeur, + Nouvelle_brosse, // Destination + 0, + 0, + Largeur); + + // On intervertit la nouvelle et l'ancienne brosse: + Temporaire=Brosse; + Brosse=Nouvelle_brosse; + Brosse_Largeur-=2; + Brosse_Hauteur-=2; + Largeur+=2; + Hauteur+=2; + + // 1er balayage (horizontal) + for (Pos_Y=0; Pos_Y0) + Pixel_dans_brosse(Pos_X-1,Pos_Y,Back_color); + Etat=0; + } + } + else + { + if (!Etat) + { + Pixel_dans_brosse(Pos_X,Pos_Y,Back_color); + Etat=1; + } + } + } + // Cas du dernier pixel droite de la ligne + if (Temporaire[((Pos_Y+1)*Largeur)+Pos_X+1]==Back_color) + Pixel_dans_brosse(Pos_X-1,Pos_Y,Back_color); + } + + // 2me balayage (vertical) + for (Pos_X=0; Pos_X0) + Pixel_dans_brosse(Pos_X,Pos_Y-1,Back_color); + Etat=0; + } + } + else + { + if (!Etat) + { + Pixel_dans_brosse(Pos_X,Pos_Y,Back_color); + Etat=1; + } + } + } + // Cas du dernier pixel en bas de la colonne + if (Temporaire[((Pos_Y+1)*Largeur)+Pos_X+1]==Back_color) + Pixel_dans_brosse(Pos_X,Pos_Y-1,Back_color); + } + + // On recentre la prise sur la brosse + Brosse_Decalage_X=(Brosse_Largeur>>1); + Brosse_Decalage_Y=(Brosse_Hauteur>>1); + + free(Temporaire); // Libration de l'ancienne brosse + + // Rallocation d'un buffer de Smear + free(Smear_Brosse); + Smear_Brosse_Largeur=(Brosse_Largeur>TAILLE_MAXI_PINCEAU)?Brosse_Largeur:TAILLE_MAXI_PINCEAU; + Smear_Brosse_Hauteur=(Brosse_Hauteur>TAILLE_MAXI_PINCEAU)?Brosse_Hauteur:TAILLE_MAXI_PINCEAU; + Smear_Brosse=(byte *)malloc(((long)Smear_Brosse_Largeur)*Smear_Brosse_Hauteur); + } + else + Erreur(0); // Pas assez de mmoire! + } +} + + +#include "pages.c" + + +////////////////////////////////////////////////////////////////////////////// +////////////////////////////// GESTION DU FILLER ///////////////////////////// +////////////////////////////////////////////////////////////////////////////// + + +void Fill(short * Limite_atteinte_Haut , short * Limite_atteinte_Bas, + short * Limite_atteinte_Gauche, short * Limite_atteinte_Droite) +// +// Cette fonction fait un remplissage classique d'une zone dlimite de +// l'image. Les limites employes sont Limite_Haut, Limite_Bas, Limite_Gauche +// et Limite_Droite. Le point de dpart du remplissage est Pinceau_X,Pinceau_Y +// et s'effectue en thorie sur la couleur 1 et emploie la couleur 2 pour le +// remplissage. Ces restrictions sont des l'utilisation qu'on en fait dans +// la fonction principale "Remplir", qui se charge de faire une gestion de +// tous les effets. +// Cette fonction ne doit pas tre directement appele. +// +{ + short Pos_X; // Abscisse de balayage du segment, utilise lors de l'"affichage" + short Ligne; // Ordonne de la ligne en cours de traitement + short Debut_X; // Abscisse de dpart du segment trait + short Fin_X; // Abscisse de fin du segment trait + int Modifs_effectuees; // Boolen "On a fait une modif dans le dernier passage" + int Propagation_possible; // Boolen "On peut propager la couleur dans le segment" + short Limite_courante_Bas; // Intervalle vertical restreint + short Limite_courante_Haut; + int Ligne_modifiee; // Boolen "On a fait une modif dans la ligne" + + Modifs_effectuees=1; + Limite_courante_Haut=Pinceau_Y; + Limite_courante_Bas =Min(Pinceau_Y+1,Limite_Bas); + *Limite_atteinte_Gauche=Pinceau_X; + *Limite_atteinte_Droite=Pinceau_X+1; + Pixel_dans_ecran_courant(Pinceau_X,Pinceau_Y,2); + + while (Modifs_effectuees) + { + Modifs_effectuees=0; + + for (Ligne=Limite_courante_Haut;Ligne<=Limite_courante_Bas;Ligne++) + { + Ligne_modifiee=0; + // On va traiter le cas de la ligne n Ligne. + + // On commence le traitement la gauche de l'cran + Debut_X=Limite_Gauche; + + // Pour chaque segment de couleur 1 que peut contenir la ligne + while (Debut_X<=Limite_Droite) + { + // On cherche son dbut + for (;(Debut_X<=Limite_Droite) && + (Lit_pixel_dans_ecran_courant(Debut_X,Ligne)!=1);Debut_X++); + + if (Debut_X<=Limite_Droite) + { + // Un segment de couleur 1 existe et commence la position Debut_X. + // On va donc en chercher la fin. + for (Fin_X=Debut_X+1;(Fin_X<=Limite_Droite) && + (Lit_pixel_dans_ecran_courant(Fin_X,Ligne)==1);Fin_X++); + + // On sait qu'il existe un segment de couleur 1 qui commence en + // Debut_X et qui se termine en Fin_X-1. + + // On va maintenant regarder si une couleur sur la priphrie + // permet de colorier ce segment avec la couleur 2. + + Propagation_possible=( + // Test de la prsence d'un point gauche du segment + ((Debut_X>Limite_Gauche) && + (Lit_pixel_dans_ecran_courant(Debut_X-1,Ligne)==2)) || + // Test de la prsence d'un point droite du segment + ((Fin_X-1Limite_Haut)) + for (Pos_X=Debut_X;Pos_X*Limite_atteinte_Droite) + *Limite_atteinte_Droite=Fin_X; + // On remplit le segment de Debut_X Fin_X-1. + for (Pos_X=Debut_X;Pos_XLimite_Haut) + Limite_courante_Haut--; + + for (Ligne=Limite_courante_Bas;Ligne>=Limite_courante_Haut;Ligne--) + { + Ligne_modifiee=0; + // On va traiter le cas de la ligne n Ligne. + + // On commence le traitement la gauche de l'cran + Debut_X=Limite_Gauche; + + // Pour chaque segment de couleur 1 que peut contenir la ligne + while (Debut_X<=Limite_Droite) + { + // On cherche son dbut + for (;(Debut_X<=Limite_Droite) && + (Lit_pixel_dans_ecran_courant(Debut_X,Ligne)!=1);Debut_X++); + + if (Debut_X<=Limite_Droite) + { + // Un segment de couleur 1 existe et commence la position Debut_X. + // On va donc en chercher la fin. + for (Fin_X=Debut_X+1;(Fin_X<=Limite_Droite) && + (Lit_pixel_dans_ecran_courant(Fin_X,Ligne)==1);Fin_X++); + + // On sait qu'il existe un segment de couleur 1 qui commence en + // Debut_X et qui se termine en Fin_X-1. + + // On va maintenant regarder si une couleur sur la priphrie + // permet de colorier ce segment avec la couleur 2. + + Propagation_possible=( + // Test de la prsence d'un point gauche du segment + ((Debut_X>Limite_Gauche) && + (Lit_pixel_dans_ecran_courant(Debut_X-1,Ligne)==2)) || + // Test de la prsence d'un point droite du segment + ((Fin_X-1*Limite_atteinte_Droite) + *Limite_atteinte_Droite=Fin_X; + // On remplit le segment de Debut_X Fin_X-1. + for (Pos_X=Debut_X;Pos_XLimite_Haut) ) + Limite_courante_Haut--; // On monte cette limite vers le haut + } + } + + *Limite_atteinte_Haut=Limite_courante_Haut; + *Limite_atteinte_Bas =Limite_courante_Bas; + (*Limite_atteinte_Droite)--; +} // Fin de la routine de remplissage "Fill" + + +void Remplir(byte Couleur_de_remplissage) +// +// Cette fonction fait un remplissage qui gre tous les effets. Elle fait +// appel "Fill()". +// +{ + byte Forme_curseur_avant_remplissage; + byte * FX_Feedback_Ecran_avant_remplissage; + short Pos_X,Pos_Y; + short Limite_atteinte_Haut ,Limite_atteinte_Bas; + short Limite_atteinte_Gauche,Limite_atteinte_Droite; + byte Table_de_remplacement[256]; + + + // Avant toute chose, on vrifie que l'on n'est pas en train de remplir + // en dehors de l'image: + + if ( (Pinceau_X>=Limite_Gauche) && + (Pinceau_X<=Limite_Droite) && + (Pinceau_Y>=Limite_Haut) && + (Pinceau_Y<=Limite_Bas) ) + { + // On suppose que le curseur est dj cach. + // Effacer_curseur(); + + // On va faire patienter l'utilisateur en lui affichant un joli petit + // sablier: + Forme_curseur_avant_remplissage=Forme_curseur; + Forme_curseur=FORME_CURSEUR_SABLIER; + Afficher_curseur(); + + // On commence par effectuer un backup de l'image. + Backup(); + + // On fait attention au Feedback qui DOIT se faire avec le backup. + FX_Feedback_Ecran_avant_remplissage=FX_Feedback_Ecran; + FX_Feedback_Ecran=Ecran_backup; + + // On va maintenant "purer" la zone visible de l'image: + memset(Table_de_remplacement,0,256); + Table_de_remplacement[Lit_pixel_dans_ecran_courant(Pinceau_X,Pinceau_Y)]=1; + Remplacer_toutes_les_couleurs_dans_limites(Table_de_remplacement); + + // On fait maintenant un remplissage classique de la couleur 1 avec la 2 + Fill(&Limite_atteinte_Haut ,&Limite_atteinte_Bas, + &Limite_atteinte_Gauche,&Limite_atteinte_Droite); + + // On s'apprte faire des oprations qui ncessitent un affichage. Il + // faut donc retirer de l'cran le curseur: + Effacer_curseur(); + Forme_curseur=Forme_curseur_avant_remplissage; + + // Il va maintenant falloir qu'on "turn" ce gros caca "into" un truc qui + // ressemble un peu plus ce quoi l'utilisateur peut s'attendre. + if (Limite_atteinte_Haut>Limite_Haut) + Copier_une_partie_d_image_dans_une_autre(Ecran_backup, + Limite_Gauche,Limite_Haut, + (Limite_Droite-Limite_Gauche)+1, + Limite_atteinte_Haut-Limite_Haut, + Principal_Largeur_image,Principal_Ecran, + Limite_Gauche,Limite_Haut,Principal_Largeur_image); + if (Limite_atteinte_BasLimite_Gauche) + Copier_une_partie_d_image_dans_une_autre(Ecran_backup, + Limite_Gauche,Limite_atteinte_Haut, + Limite_atteinte_Gauche-Limite_Gauche, + (Limite_atteinte_Bas-Limite_atteinte_Haut)+1, + Principal_Largeur_image,Principal_Ecran, + Limite_Gauche,Limite_atteinte_Haut,Principal_Largeur_image); + if (Limite_atteinte_Droite=Limite_Gauche) && + (Pos_X<=Limite_Droite) && + (Pos_Y>=Limite_Haut) && + (Pos_Y<=Limite_Bas) ) + Pixel_Preview(Pos_X,Pos_Y,Couleur); + } + + // Affichage d'un point pour une preview en xor + void Pixel_figure_Preview_xor(short Pos_X,short Pos_Y,byte Couleur) + { + if ( (Pos_X>=Limite_Gauche) && + (Pos_X<=Limite_Droite) && + (Pos_Y>=Limite_Haut) && + (Pos_Y<=Limite_Bas) ) + Pixel_Preview(Pos_X,Pos_Y,~Lit_pixel(Pos_X-Principal_Decalage_X, + Pos_Y-Principal_Decalage_Y)); + } + + // Effacement d'un point de preview + void Pixel_figure_Effacer_preview(short Pos_X,short Pos_Y,byte Couleur) + { + if ( (Pos_X>=Limite_Gauche) && + (Pos_X<=Limite_Droite) && + (Pos_Y>=Limite_Haut) && + (Pos_Y<=Limite_Bas) ) + Pixel_Preview(Pos_X,Pos_Y,Lit_pixel_dans_ecran_courant(Pos_X,Pos_Y)); + } + + // Affichage d'un point dans la brosse + void Pixel_figure_Dans_brosse(short Pos_X,short Pos_Y,byte Couleur) + { + Pos_X-=Brosse_Decalage_X; + Pos_Y-=Brosse_Decalage_Y; + if ( (Pos_X>=0) && + (Pos_X=0) && + (Pos_YLimite_Bas) + Fin_Y=Limite_Bas; + if (Debut_XLimite_Droite) + Fin_X=Limite_Droite; + + // Affichage du cercle + for (Pos_Y=Debut_Y,Cercle_Curseur_Y=(long)Debut_Y-Centre_Y;Pos_Y<=Fin_Y;Pos_Y++,Cercle_Curseur_Y++) + for (Pos_X=Debut_X,Cercle_Curseur_X=(long)Debut_X-Centre_X;Pos_X<=Fin_X;Pos_X++,Cercle_Curseur_X++) + if (Pixel_dans_cercle()) + Afficher_pixel(Pos_X,Pos_Y,Couleur); +} + + + // -- Tracer gnral d'une ellipse vide ----------------------------------- + +void Tracer_ellipse_vide_General(short Centre_X,short Centre_Y,short Rayon_horizontal,short Rayon_vertical,byte Couleur) +{ + short Debut_X; + short Debut_Y; + short Pos_X; + short Pos_Y; + + Debut_X=Centre_X-Rayon_horizontal; + Debut_Y=Centre_Y-Rayon_vertical; + + // Calcul des limites de l'ellipse + Ellipse_Calculer_limites(Rayon_horizontal+1,Rayon_vertical+1); + + // Affichage des extremites de l'ellipse sur chaque quart de l'ellipse: + for (Pos_Y=Debut_Y,Ellipse_Curseur_Y=-Rayon_vertical;Pos_YLimite_Bas) + Fin_Y=Limite_Bas; + if (Debut_XLimite_Droite) + Fin_X=Limite_Droite; + + // Affichage de l'ellipse + for (Pos_Y=Debut_Y,Ellipse_Curseur_Y=Debut_Y-Centre_Y;Pos_Y<=Fin_Y;Pos_Y++,Ellipse_Curseur_Y++) + for (Pos_X=Debut_X,Ellipse_Curseur_X=Debut_X-Centre_X;Pos_X<=Fin_X;Pos_X++,Ellipse_Curseur_X++) + if (Pixel_dans_ellipse()) + Afficher_pixel(Pos_X,Pos_Y,Couleur); +} + + + // -- Tracer gnral d'une ligne ------------------------------------------ + +void Tracer_ligne_General(short Debut_X,short Debut_Y,short Fin_X,short Fin_Y, byte Couleur) +{ + short Pos_X,Pos_Y; + short Incr_X,Incr_Y; + short i,Cumul; + short Delta_X,Delta_Y; + + + Pos_X=Debut_X; + Pos_Y=Debut_Y; + + if (Debut_XDelta_X) + { + Cumul=Delta_Y>>1; + for (i=1; i=Delta_Y) + { + Cumul-=Delta_Y; + Pos_X+=Incr_X; + } + Pixel_figure(Pos_X,Pos_Y,Couleur); + } + } + else + { + Cumul=Delta_X>>1; + for (i=1; i=Delta_X) + { + Cumul-=Delta_X; + Pos_Y+=Incr_Y; + } + Pixel_figure(Pos_X,Pos_Y,Couleur); + } + } + + if ( (Debut_X!=Fin_X) || (Debut_Y!=Fin_Y) ) + Pixel_figure(Fin_X,Fin_Y,Couleur); +} + + // -- Tracer dfinitif d'une ligne -- + +void Tracer_ligne_Definitif(short Debut_X,short Debut_Y,short Fin_X,short Fin_Y, byte Couleur) +{ + Pixel_figure=Pixel_figure_Definitif; + Tracer_ligne_General(Debut_X,Debut_Y,Fin_X,Fin_Y,Couleur); +} + + // -- Tracer la preview d'une ligne -- + +void Tracer_ligne_Preview(short Debut_X,short Debut_Y,short Fin_X,short Fin_Y,byte Couleur) +{ + Pixel_figure=Pixel_figure_Preview; + Tracer_ligne_General(Debut_X,Debut_Y,Fin_X,Fin_Y,Couleur); +} + + // -- Tracer la preview d'une ligne en xor -- + +void Tracer_ligne_Preview_xor(short Debut_X,short Debut_Y,short Fin_X,short Fin_Y,byte Couleur) +{ + Pixel_figure=Pixel_figure_Preview_xor; + Tracer_ligne_General(Debut_X,Debut_Y,Fin_X,Fin_Y,Couleur); +} + + // -- Effacer la preview d'une ligne -- + +void Effacer_ligne_Preview(short Debut_X,short Debut_Y,short Fin_X,short Fin_Y) +{ + Pixel_figure=Pixel_figure_Effacer_preview; + Tracer_ligne_General(Debut_X,Debut_Y,Fin_X,Fin_Y,0); +} + + + // -- Tracer un rectangle vide -- + +void Tracer_rectangle_vide(short Debut_X,short Debut_Y,short Fin_X,short Fin_Y,byte Couleur) +{ + short Tempo; + short Pos_X; + short Pos_Y; + + + // On vrifie que les bornes soient dans le bon sens: + if (Debut_X>Fin_X) + { + Tempo=Debut_X; + Debut_X=Fin_X; + Fin_X=Tempo; + } + if (Debut_Y>Fin_Y) + { + Tempo=Debut_Y; + Debut_Y=Fin_Y; + Fin_Y=Tempo; + } + + // On trace le rectangle: + + for (Pos_X=Debut_X;Pos_X<=Fin_X;Pos_X++) + Afficher_pinceau(Pos_X,Debut_Y,Couleur,0); + + for (Pos_Y=Debut_Y+1;Pos_YFin_X) + { + Tempo=Debut_X; + Debut_X=Fin_X; + Fin_X=Tempo; + } + if (Debut_Y>Fin_Y) + { + Tempo=Debut_Y; + Debut_Y=Fin_Y; + Fin_Y=Tempo; + } + + // Correction en cas de dpassement des limites de l'image + if (Fin_X>Limite_Droite) + Fin_X=Limite_Droite; + if (Fin_Y>Limite_Bas) + Fin_Y=Limite_Bas; + + // On trace le rectangle: + for (Pos_Y=Debut_Y;Pos_Y<=Fin_Y;Pos_Y++) + for (Pos_X=Debut_X;Pos_X<=Fin_X;Pos_X++) + Afficher_pixel(Pos_X,Pos_Y,Couleur); +} + + + + + // -- Tracer une courbe de Bzier -- + +void Tracer_courbe_General(short X1, short Y1, + short X2, short Y2, + short X3, short Y3, + short X4, short Y4, + byte Couleur) +{ + float Delta,T,T2,T3; + short X,Y,Old_X,Old_Y; + word i; + int CX[4]; + int CY[4]; + + // Calcul des vecteurs de coefficients + CX[0]= - X1 + 3*X2 - 3*X3 + X4; + CX[1]= + 3*X1 - 6*X2 + 3*X3; + CX[2]= - 3*X1 + 3*X2; + CX[3]= + X1; + CY[0]= - Y1 + 3*Y2 - 3*Y3 + Y4; + CY[1]= + 3*Y1 - 6*Y2 + 3*Y3; + CY[2]= - 3*Y1 + 3*Y2; + CY[3]= + Y1; + + // Traage de la courbe + Old_X=X1; + Old_Y=Y1; + Pixel_figure(Old_X,Old_Y,Couleur); + Delta=0.05; // 1.0/20 + T=0; + for (i=1; i<=20; i++) + { + T=T+Delta; T2=T*T; T3=T2*T; + X=Round(T3*CX[0] + T2*CX[1] + T*CX[2] + CX[3]); + Y=Round(T3*CY[0] + T2*CY[1] + T*CY[2] + CY[3]); + Tracer_ligne_General(Old_X,Old_Y,X,Y,Couleur); + Old_X=X; + Old_Y=Y; + } +} + + // -- Tracer une courbe de Bzier dfinitivement -- + +void Tracer_courbe_Definitif(short X1, short Y1, + short X2, short Y2, + short X3, short Y3, + short X4, short Y4, + byte Couleur) +{ + Pixel_figure=Pixel_figure_Definitif; + Tracer_courbe_General(X1,Y1,X2,Y2,X3,Y3,X4,Y4,Couleur); +} + + // -- Tracer la preview d'une courbe de Bzier -- + +void Tracer_courbe_Preview(short X1, short Y1, + short X2, short Y2, + short X3, short Y3, + short X4, short Y4, + byte Couleur) +{ + Pixel_figure=Pixel_figure_Preview; + Tracer_courbe_General(X1,Y1,X2,Y2,X3,Y3,X4,Y4,Couleur); +} + + // -- Effacer la preview d'une courbe de Bzier -- + +void Effacer_courbe_Preview(short X1, short Y1, + short X2, short Y2, + short X3, short Y3, + short X4, short Y4, + byte Couleur) +{ + Pixel_figure=Pixel_figure_Effacer_preview; + Tracer_courbe_General(X1,Y1,X2,Y2,X3,Y3,X4,Y4,Couleur); +} + + + + + // -- Spray : un petit coup de Pschiitt! -- + +void Aerographe(short Bouton_clicke) +{ + short Pos_X,Pos_Y; + short Rayon=Spray_Size>>1; + long Rayon_au_carre=(long)Rayon*Rayon; + short Indice,Count; + byte Indice_couleur; + byte Sens; + + + Effacer_curseur(); + + if (Spray_Mode) + { + for (Count=1; Count<=Spray_Mono_flow; Count++) + { + Pos_X=(rand()%Spray_Size)-Rayon; + Pos_Y=(rand()%Spray_Size)-Rayon; + if ( (Pos_X*Pos_X)+(Pos_Y*Pos_Y) <= Rayon_au_carre ) + { + Pos_X+=Pinceau_X; + Pos_Y+=Pinceau_Y; + if (Bouton_clicke==1) + Afficher_pinceau(Pos_X,Pos_Y,Fore_color,0); + else + Afficher_pinceau(Pos_X,Pos_Y,Back_color,0); + } + } + } + else + { + // On essaye de se balader dans la table des flux de faon ce que ce + // ne soit pas toujours la dernire couleur qui soit affiche en dernier + // Pour a, on part d'une couleur au pif dans une direction alatoire. + Sens=rand()&1; + for (Indice=0,Indice_couleur=rand()/*%256*/; Indice<256; Indice++) + { + for (Count=1; Count<=Spray_Multi_flow[Indice_couleur]; Count++) + { + Pos_X=(rand()%Spray_Size)-Rayon; + Pos_Y=(rand()%Spray_Size)-Rayon; + if ( (Pos_X*Pos_X)+(Pos_Y*Pos_Y) <= Rayon_au_carre ) + { + Pos_X+=Pinceau_X; + Pos_Y+=Pinceau_Y; + if (Bouton_clicke==A_GAUCHE) + Afficher_pinceau(Pos_X,Pos_Y,Indice_couleur,0); + else + Afficher_pinceau(Pos_X,Pos_Y,Back_color,0); + } + } + if (Sens) + Indice_couleur++; + else + Indice_couleur--; + } + } + + Afficher_curseur(); + + for (Count=1; Count<=Spray_Delay; Count++) + Wait_VBL(); +} + + + + ////////////////////////////////////////////////////////////////////////// + ////////////////////////// GESTION DES DEGRADES ////////////////////////// + ////////////////////////////////////////////////////////////////////////// + + + // -- Gestion d'un dgrad de base (le plus moche) -- + +void Degrade_de_base(long Indice,short Pos_X,short Pos_Y) +{ + long Position; + + // On fait un premier calcul partiel + Position=(Indice*Degrade_Intervalle_bornes); + + // On gre un dplacement au hasard + Position+=(Degrade_Intervalle_total*(rand()%Degrade_Melange_aleatoire)) >>6; + Position-=(Degrade_Intervalle_total*Degrade_Melange_aleatoire) >>7; + + Position/=Degrade_Intervalle_total; + + // On va vrifier que nos petites idioties n'ont pas ject la valeur hors + // des valeurs autorises par le dgrad dfini par l'utilisateur. + + if (Position<0) + Position=0; + else if (Position>=Degrade_Intervalle_bornes) + Position=Degrade_Intervalle_bornes-1; + + // On ramne ensuite la position dans le dgrad vers un numro de couleur + if (Degrade_Inverse) + Traiter_pixel_de_degrade(Pos_X,Pos_Y,Degrade_Borne_Superieure-Position); + else + Traiter_pixel_de_degrade(Pos_X,Pos_Y,Degrade_Borne_Inferieure+Position); +} + + + // -- Gestion d'un dgrad par trames simples -- + +void Degrade_de_trames_simples(long Indice,short Pos_X,short Pos_Y) +{ + long Position_dans_degrade; + long Position_dans_segment; + + // + // But de l'opration: en plus de calculer la position de base (dsigne + // dans cette procdure par "Position_dans_degrade", on calcule la position + // de l'indice dans le schma suivant: + // + // Les indices qui tranent de ce ct du segment se voient subir + // une incrmentation conditionnelle leur position dans l'cran. + // v + // + // ^ + // Les indices qui tranent de ce ct du segment se voient subir une + // dcrmentation conditionnelle leur position dans l'cran. + + // On fait d'abord un premier calcul partiel + Position_dans_degrade=(Indice*Degrade_Intervalle_bornes); + + // On gre un dplacement au hasard... + Position_dans_degrade+=(Degrade_Intervalle_total*(rand()%Degrade_Melange_aleatoire)) >>6; + Position_dans_degrade-=(Degrade_Intervalle_total*Degrade_Melange_aleatoire) >>7; + + if (Position_dans_degrade<0) + Position_dans_degrade=0; + + // ... qui nous permet de calculer la position dans le segment + Position_dans_segment=((Position_dans_degrade<<2)/Degrade_Intervalle_total)&3; + + // On peut ensuite terminer le calcul de l'indice dans le dgrad + Position_dans_degrade/=Degrade_Intervalle_total; + + // On va pouvoir discuter de la valeur de Position_dans_degrade en fonction + // de la position dans l'cran et de la Position_dans_segment. + + switch (Position_dans_segment) + { + case 0 : // On est sur la gauche du segment + if (((Pos_X+Pos_Y)&1)==0) + Position_dans_degrade--; + break; + + // On n'a pas traiter les cas 1 et 2 car ils reprsentent des valeurs + // suffisament au centre du segment pour ne pas avoir subir la trame + + case 3 : // On est sur la droite du segment + if (((Pos_X+Pos_Y)&1)!=0) // Note: on doit faire le test inverse au cas gauche pour synchroniser les 2 cts de la trame. + Position_dans_degrade++; + } + + // On va vrifier que nos petites idioties n'ont pas ject la valeur hors + // des valeurs autorises par le dgrad dfini par l'utilisateur. + + if (Position_dans_degrade<0) + Position_dans_degrade=0; + else if (Position_dans_degrade>=Degrade_Intervalle_bornes) + Position_dans_degrade=Degrade_Intervalle_bornes-1; + + // On ramne ensuite la position dans le dgrad vers un numro de couleur + if (Degrade_Inverse) + Position_dans_degrade=Degrade_Borne_Superieure-Position_dans_degrade; + else + Position_dans_degrade=Degrade_Borne_Inferieure+Position_dans_degrade; + + Traiter_pixel_de_degrade(Pos_X,Pos_Y,Position_dans_degrade); +} + + + // -- Gestion d'un dgrad par trames tendues -- + +void Degrade_de_trames_etendues(long Indice,short Pos_X,short Pos_Y) +{ + long Position_dans_degrade; + long Position_dans_segment; + + // + // But de l'opration: en plus de calculer la position de base (dsigne + // dans cette procdure par "Position_dans_degrade", on calcule la position + // de l'indice dans le schma suivant: + // + // Les indices qui tranent de ce ct du segment se voient subir + // une incrmentation conditionnelle leur position dans l'cran. + // v + // + // ^ + // Les indices qui tranent de ce ct du segment se voient subir une + // dcrmentation conditionnelle leur position dans l'cran. + + // On fait d'abord un premier calcul partiel + Position_dans_degrade=(Indice*Degrade_Intervalle_bornes); + + // On gre un dplacement au hasard + Position_dans_degrade+=(Degrade_Intervalle_total*(rand()%Degrade_Melange_aleatoire)) >>6; + Position_dans_degrade-=(Degrade_Intervalle_total*Degrade_Melange_aleatoire) >>7; + + if (Position_dans_degrade<0) + Position_dans_degrade=0; + + // Qui nous permet de calculer la position dans le segment + Position_dans_segment=((Position_dans_degrade<<3)/Degrade_Intervalle_total)&7; + + // On peut ensuite terminer le calcul de l'indice dans le dgrad + Position_dans_degrade/=Degrade_Intervalle_total; + + // On va pouvoir discuter de la valeur de Position_dans_degrade en fonction + // de la position dans l'cran et de la Position_dans_segment. + + switch (Position_dans_segment) + { + case 0 : // On est sur l'extrme gauche du segment + if (((Pos_X+Pos_Y)&1)==0) + Position_dans_degrade--; + break; + + case 1 : // On est sur la gauche du segment + case 2 : // On est sur la gauche du segment + if (((Pos_X & 1)==0) && ((Pos_Y & 1)==0)) + Position_dans_degrade--; + break; + + // On n'a pas traiter les cas 3 et 4 car ils reprsentent des valeurs + // suffisament au centre du segment pour ne pas avoir subir la trame + + case 5 : // On est sur la droite du segment + case 6 : // On est sur la droite du segment + if (((Pos_X & 1)==0) && ((Pos_Y & 1)!=0)) + Position_dans_degrade++; + break; + + case 7 : // On est sur l'extreme droite du segment + if (((Pos_X+Pos_Y)&1)!=0) // Note: on doit faire le test inverse au cas gauche pour synchroniser les 2 cts de la trame. + Position_dans_degrade++; + } + + // On va vrifier que nos petites idioties n'ont pas ject la valeur hors + // des valeurs autorises par le dgrad dfini par l'utilisateur. + + if (Position_dans_degrade<0) + Position_dans_degrade=0; + else if (Position_dans_degrade>=Degrade_Intervalle_bornes) + Position_dans_degrade=Degrade_Intervalle_bornes-1; + + // On ramne ensuite la position dans le dgrad vers un numro de couleur + if (Degrade_Inverse) + Position_dans_degrade=Degrade_Borne_Superieure-Position_dans_degrade; + else + Position_dans_degrade=Degrade_Borne_Inferieure+Position_dans_degrade; + + Traiter_pixel_de_degrade(Pos_X,Pos_Y,Position_dans_degrade); +} + + + + + + + + // -- Tracer un cercle degrad (une sphre) -- + +void Tracer_cercle_degrade(short Centre_X,short Centre_Y,short Rayon,short Eclairage_X,short Eclairage_Y) +{ + long Debut_X; + long Debut_Y; + long Pos_X; + long Pos_Y; + long Fin_X; + long Fin_Y; + long Distance_X; // Distance (au carr) sur les X du point en cours au centre d'clairage + long Distance_Y; // Distance (au carr) sur les Y du point en cours au centre d'clairage + + Debut_X=Centre_X-Rayon; + Debut_Y=Centre_Y-Rayon; + Fin_X=Centre_X+Rayon; + Fin_Y=Centre_Y+Rayon; + + // Correction des bornes d'aprs les limites + if (Debut_YLimite_Bas) + Fin_Y=Limite_Bas; + if (Debut_XLimite_Droite) + Fin_X=Limite_Droite; + + Degrade_Intervalle_total=Cercle_Limite+ + ((Centre_X-Eclairage_X)*(Centre_X-Eclairage_X))+ + ((Centre_Y-Eclairage_Y)*(Centre_Y-Eclairage_Y))+ + (2L*Rayon*sqrt( + ((Centre_X-Eclairage_X)*(Centre_X-Eclairage_X))+ + ((Centre_Y-Eclairage_Y)*(Centre_Y-Eclairage_Y)))); + + if (Degrade_Intervalle_total==0) + Degrade_Intervalle_total=1; + + // Affichage du cercle + for (Pos_Y=Debut_Y,Cercle_Curseur_Y=(long)Debut_Y-Centre_Y;Pos_Y<=Fin_Y;Pos_Y++,Cercle_Curseur_Y++) + { + Distance_Y =(Pos_Y-Eclairage_Y); + Distance_Y*=Distance_Y; + for (Pos_X=Debut_X,Cercle_Curseur_X=(long)Debut_X-Centre_X;Pos_X<=Fin_X;Pos_X++,Cercle_Curseur_X++) + if (Pixel_dans_cercle()) + { + Distance_X =(Pos_X-Eclairage_X); + Distance_X*=Distance_X; + Traiter_degrade(Distance_X+Distance_Y,Pos_X,Pos_Y); + } + } +} + + + // -- Tracer une ellipse degrade -- + +void Tracer_ellipse_degradee(short Centre_X,short Centre_Y,short Rayon_horizontal,short Rayon_vertical,short Eclairage_X,short Eclairage_Y) +{ + long Debut_X; + long Debut_Y; + long Pos_X; + long Pos_Y; + long Fin_X; + long Fin_Y; + long Distance_X; // Distance (au carr) sur les X du point en cours au centre d'clairage + long Distance_Y; // Distance (au carr) sur les Y du point en cours au centre d'clairage + + + Debut_X=Centre_X-Rayon_horizontal; + Debut_Y=Centre_Y-Rayon_vertical; + Fin_X=Centre_X+Rayon_horizontal; + Fin_Y=Centre_Y+Rayon_vertical; + + // Calcul des limites de l'ellipse + Ellipse_Calculer_limites(Rayon_horizontal+1,Rayon_vertical+1); + + // On calcule la distance maximale: + Degrade_Intervalle_total=(Rayon_horizontal*Rayon_horizontal)+ + (Rayon_vertical*Rayon_vertical)+ + ((Centre_X-Eclairage_X)*(Centre_X-Eclairage_X))+ + ((Centre_Y-Eclairage_Y)*(Centre_Y-Eclairage_Y))+ + (2L + *sqrt( + (Rayon_horizontal*Rayon_horizontal)+ + (Rayon_vertical *Rayon_vertical )) + *sqrt( + ((Centre_X-Eclairage_X)*(Centre_X-Eclairage_X))+ + ((Centre_Y-Eclairage_Y)*(Centre_Y-Eclairage_Y)))); + + if (Degrade_Intervalle_total==0) + Degrade_Intervalle_total=1; + + // Correction des bornes d'aprs les limites + if (Debut_YLimite_Bas) + Fin_Y=Limite_Bas; + if (Debut_XLimite_Droite) + Fin_X=Limite_Droite; + + // Affichage de l'ellipse + for (Pos_Y=Debut_Y,Ellipse_Curseur_Y=Debut_Y-Centre_Y;Pos_Y<=Fin_Y;Pos_Y++,Ellipse_Curseur_Y++) + { + Distance_Y =(Pos_Y-Eclairage_Y); + Distance_Y*=Distance_Y; + for (Pos_X=Debut_X,Ellipse_Curseur_X=Debut_X-Centre_X;Pos_X<=Fin_X;Pos_X++,Ellipse_Curseur_X++) + if (Pixel_dans_ellipse()) + { + Distance_X =(Pos_X-Eclairage_X); + Distance_X*=Distance_X; + Traiter_degrade(Distance_X+Distance_Y,Pos_X,Pos_Y); + } + } +} + + + + + + + + // -- Tracer un polygne plein -- + +typedef struct POLYGON_EDGE /* an active edge */ +{ + short top; /* top y position */ + short bottom; /* bottom y position */ + float x, dx; /* floating point x position and gradient */ + float w; /* width of line segment */ + struct POLYGON_EDGE *prev; /* doubly linked list */ + struct POLYGON_EDGE *next; +} POLYGON_EDGE; + + + +/* fill_edge_structure: + * Polygon helper function: initialises an edge structure for the 2d + * rasteriser. + */ +void fill_edge_structure(POLYGON_EDGE *edge, short *i1, short *i2) +{ + short *it; + + if (i2[1] < i1[1]) + { + it = i1; + i1 = i2; + i2 = it; + } + + edge->top = i1[1]; + edge->bottom = i2[1] - 1; + edge->dx = ((float) i2[0] - (float) i1[0]) / ((float) i2[1] - (float) i1[1]); + edge->x = i1[0] + 0.4999999; + edge->prev = NULL; + edge->next = NULL; + + if (edge->dx+1 < 0.0) + edge->x += edge->dx+1; + + if (edge->dx >= 0.0) + edge->w = edge->dx; + else + edge->w = -(edge->dx); + + if (edge->w-1.0<0.0) + edge->w = 0.0; + else + edge->w = edge->w-1; +} + + + +/* add_edge: + * Adds an edge structure to a linked list, returning the new head pointer. + */ +POLYGON_EDGE * add_edge(POLYGON_EDGE *list, POLYGON_EDGE *edge, int sort_by_x) +{ + POLYGON_EDGE *pos = list; + POLYGON_EDGE *prev = NULL; + + if (sort_by_x) + { + while ( (pos) && ((pos->x+((pos->w+pos->dx)/2)) < (edge->x+((edge->w+edge->dx)/2))) ) + { + prev = pos; + pos = pos->next; + } + } + else + { + while ((pos) && (pos->top < edge->top)) + { + prev = pos; + pos = pos->next; + } + } + + edge->next = pos; + edge->prev = prev; + + if (pos) + pos->prev = edge; + + if (prev) + { + prev->next = edge; + return list; + } + else + return edge; +} + + + +/* remove_edge: + * Removes an edge structure from a list, returning the new head pointer. + */ +POLYGON_EDGE * remove_edge(POLYGON_EDGE *list, POLYGON_EDGE *edge) +{ + if (edge->next) + edge->next->prev = edge->prev; + + if (edge->prev) + { + edge->prev->next = edge->next; + return list; + } + else + return edge->next; +} + + + +/* polygon: + * Draws a filled polygon with an arbitrary number of corners. Pass the + * number of vertices, then an array containing a series of x, y points + * (a total of vertices*2 values). + */ +void Polyfill_General(int Vertices, short * Points, int Color) +{ + short c; + short top = 0x7FFF; + short bottom = 0; + short *i1, *i2; + short Pos_X,Fin_X; + POLYGON_EDGE *edge, *next_edge, *initial_edge; + POLYGON_EDGE *active_edges = NULL; + POLYGON_EDGE *inactive_edges = NULL; + + + /* allocate some space and fill the edge table */ + initial_edge=edge=(POLYGON_EDGE *) malloc(sizeof(POLYGON_EDGE) * Vertices); + + i1 = Points; + i2 = Points + ((Vertices-1)<<1); + + for (c=0; cbottom >= edge->top) + { + if (edge->top < top) + top = edge->top; + + if (edge->bottom > bottom) + bottom = edge->bottom; + + inactive_edges = add_edge(inactive_edges, edge, 0); + edge++; + } + } + i2 = i1; + i1 += 2; + } + + /* for each scanline in the polygon... */ + for (c=top; c<=bottom; c++) + { + /* check for newly active edges */ + edge = inactive_edges; + while ((edge) && (edge->top == c)) + { + next_edge = edge->next; + inactive_edges = remove_edge(inactive_edges, edge); + active_edges = add_edge(active_edges, edge, 1); + edge = next_edge; + } + + /* draw horizontal line segments */ + if ((c>=Limite_Haut) && (c<=Limite_Bas)) + { + edge = active_edges; + while ((edge) && (edge->next)) + { + Pos_X=/*Round*/(edge->x); + Fin_X=/*Round*/(edge->next->x+edge->next->w); + if (Pos_XLimite_Droite) + Fin_X=Limite_Droite; + for (; Pos_X<=Fin_X; Pos_X++) + Pixel_figure(Pos_X,c,Color); + edge = edge->next->next; + } + } + + /* update edges, sorting and removing dead ones */ + edge = active_edges; + while (edge) + { + next_edge = edge->next; + if (c >= edge->bottom) + active_edges = remove_edge(active_edges, edge); + else + { + edge->x += edge->dx; + while ((edge->prev) && ( (edge->x+(edge->w/2)) < (edge->prev->x+(edge->prev->w/2))) ) + { + if (edge->next) + edge->next->prev = edge->prev; + edge->prev->next = edge->next; + edge->next = edge->prev; + edge->prev = edge->prev->prev; + edge->next->prev = edge; + if (edge->prev) + edge->prev->next = edge; + else + active_edges = edge; + } + } + edge = next_edge; + } + } + + free(initial_edge); +} + + +void Polyfill(int Vertices, short * Points, int Color) +{ + Pixel_figure=Afficher_pixel; + Polyfill_General(Vertices,Points,Color); +} + + + +void Capturer_brosse_au_lasso(int Vertices, short * Points,short Effacement) +{ + short Debut_X=Limite_Droite+1; + short Debut_Y=Limite_Bas+1; + short Fin_X=Limite_Gauche-1; + short Fin_Y=Limite_Haut-1; + short Temporaire; + short Pos_X; + short Pos_Y; + word Nouvelle_Brosse_Largeur; + word Nouvelle_Brosse_Hauteur; + + + // On recherche les bornes de la brosse: + for (Temporaire=0; TemporaireFin_X) + Fin_X=Pos_X; + if (Pos_YFin_Y) + Fin_Y=Pos_Y; + } + + // On clippe ces bornes l'cran: + if (Debut_XLimite_Droite) + Fin_X=Limite_Droite; + if (Debut_YLimite_Bas) + Fin_Y=Limite_Bas; + + // On ne capture la nouvelle brosse que si elle est au moins partiellement + // dans l'image: + + if ((Debut_XTAILLE_MAXI_PINCEAU)?Brosse_Largeur:TAILLE_MAXI_PINCEAU; + Smear_Brosse_Hauteur=(Brosse_Hauteur>TAILLE_MAXI_PINCEAU)?Brosse_Hauteur:TAILLE_MAXI_PINCEAU; + Smear_Brosse=(byte *)malloc(((long)Smear_Brosse_Hauteur)*Smear_Brosse_Largeur); + + if (!Smear_Brosse) // On ne peut mme pas allouer la brosse du smear! + { + Erreur(0); + + free(Brosse); + Brosse=(byte *)malloc(1*1); + Brosse_Hauteur=1; + Brosse_Largeur=1; + + Smear_Brosse=(byte *)malloc(TAILLE_MAXI_PINCEAU*TAILLE_MAXI_PINCEAU); + Smear_Brosse_Hauteur=TAILLE_MAXI_PINCEAU; + Smear_Brosse_Largeur=TAILLE_MAXI_PINCEAU; + } + + Brosse_Decalage_X=Debut_X; + Brosse_Decalage_Y=Debut_Y; + Pixel_figure=Pixel_figure_Dans_brosse; + + memset(Brosse,Back_color,(long)Brosse_Largeur*Brosse_Hauteur); + Polyfill_General(Vertices,Points,~Back_color); + + // On retrace les bordures du lasso: + for (Temporaire=1; Temporaire>1); + Brosse_Decalage_Y=(Brosse_Hauteur>>1); + } +} + + + +//------------ Remplacement de la couleur pointe par une autre -------------- + +void Remplacer(byte Nouvelle_couleur) +{ + byte Ancienne_couleur; + + if ((Pinceau_X=0) + Pos_X_initial = 0; // Pas d'inversion en X de la brosse + else + Pos_X_initial = (Brosse_Largeur<<16)-1; // Inversion en X de la brosse + + free(Smear_Brosse); // On libre un peu de mmoire + + if (New_Brosse=(byte *)malloc(New_Brosse_Largeur*New_Brosse_Hauteur)) + { + Offset=0; + + // Calcul de la valeur initiale de Pos_Y: + if (Dy>=0) + Pos_Y_dans_brosse=0; // Pas d'inversion en Y de la brosse + else + Pos_Y_dans_brosse=(Brosse_Hauteur<<16)-1; // Inversion en Y de la brosse + + // Pour chaque ligne + for (Ligne=0;Ligne>16,Pos_Y_dans_brosse>>16); + // On passe la colonne de brosse suivante: + Pos_X_dans_brosse+=Delta_X_dans_brosse; + // On passe au pixel suivant de la nouvelle brosse: + Offset++; + } + + // On passe la ligne de brosse suivante: + Pos_Y_dans_brosse+=Delta_Y_dans_brosse; + } + + free(Brosse); + Brosse=New_Brosse; + + Brosse_Largeur=New_Brosse_Largeur; + Brosse_Hauteur=New_Brosse_Hauteur; + + Smear_Brosse_Largeur=(Brosse_Largeur>TAILLE_MAXI_PINCEAU)?Brosse_Largeur:TAILLE_MAXI_PINCEAU; + Smear_Brosse_Hauteur=(Brosse_Hauteur>TAILLE_MAXI_PINCEAU)?Brosse_Hauteur:TAILLE_MAXI_PINCEAU; + Smear_Brosse=(byte *)malloc(((long)Smear_Brosse_Hauteur)*Smear_Brosse_Largeur); + + if (!Smear_Brosse) // On ne peut mme pas allouer la brosse du smear! + { + Erreur(0); + + free(Brosse); + Brosse=(byte *)malloc(1*1); + Brosse_Hauteur=1; + Brosse_Largeur=1; + + Smear_Brosse=(byte *)malloc(TAILLE_MAXI_PINCEAU*TAILLE_MAXI_PINCEAU); + Smear_Brosse_Hauteur=TAILLE_MAXI_PINCEAU; + Smear_Brosse_Largeur=TAILLE_MAXI_PINCEAU; + } + + Brosse_Decalage_X=(Brosse_Largeur>>1); + Brosse_Decalage_Y=(Brosse_Hauteur>>1); + } + else + { + // Ici la libration de mmoire n'a pas suffit donc on remet dans l'tat + // o c'etait avant. On a juste rallouer la Smear_Brosse car il y a + // normalement la place pour elle puisque rien d'autre n'a pu tre allou + // entre temps. + Smear_Brosse=(byte *)malloc(((long)Smear_Brosse_Hauteur)*Smear_Brosse_Largeur); + Erreur(0); + } +} + + + +void Etirer_brosse_preview(short X1, short Y1, short X2, short Y2) +{ + int Pos_X_src,Pos_Y_src; + int Pos_X_src_Initiale,Pos_Y_src_Initiale; + int Delta_X,Delta_Y; + int Pos_X_dest,Pos_Y_dest; + int Pos_X_dest_Initiale,Pos_Y_dest_Initiale; + int Pos_X_dest_Finale,Pos_Y_dest_Finale; + int Largeur_dest,Hauteur_dest; + byte Couleur; + + + // 1er calcul des positions destination extremes: + Pos_X_dest_Initiale=Min(X1,X2); + Pos_Y_dest_Initiale=Min(Y1,Y2); + Pos_X_dest_Finale =Max(X1,X2); + Pos_Y_dest_Finale =Max(Y1,Y2); + + // Calcul des dimensions de la destination: + Largeur_dest=Pos_X_dest_Finale-Pos_X_dest_Initiale+1; + Hauteur_dest=Pos_Y_dest_Finale-Pos_Y_dest_Initiale+1; + + // Calcul des vecteurs d'incrmentation : + Delta_X=(Brosse_Largeur<<16)/Largeur_dest; + Delta_Y=(Brosse_Hauteur<<16)/Hauteur_dest; + + // 1er calcul de la position X initiale dans la source: + Pos_X_src_Initiale=(Brosse_Largeur<<16)* + (Max(Pos_X_dest_Initiale,Limite_Gauche)- + Pos_X_dest_Initiale)/Largeur_dest; + // Calcul du clip de la destination: + Pos_X_dest_Initiale=Max(Pos_X_dest_Initiale,Limite_Gauche); + Pos_X_dest_Finale =Min(Pos_X_dest_Finale ,Limite_visible_Droite); + // On discute selon l'inversion en X + if (X1>X2) + { + // Inversion -> Inversion du signe de Delta_X + Delta_X=-Delta_X; + Pos_X_src_Initiale=(Brosse_Largeur<<16)-1-Pos_X_src_Initiale; + } + + // 1er calcul de la position Y initiale dans la source: + Pos_Y_src_Initiale=(Brosse_Hauteur<<16)* + (Max(Pos_Y_dest_Initiale,Limite_Haut)- + Pos_Y_dest_Initiale)/Hauteur_dest; + // Calcul du clip de la destination: + Pos_Y_dest_Initiale=Max(Pos_Y_dest_Initiale,Limite_Haut); + Pos_Y_dest_Finale =Min(Pos_Y_dest_Finale ,Limite_visible_Bas); + // On discute selon l'inversion en Y + if (Y1>Y2) + { + // Inversion -> Inversion du signe de Delta_Y + Delta_Y=-Delta_Y; + Pos_Y_src_Initiale=(Brosse_Hauteur<<16)-1-Pos_Y_src_Initiale; + } + + // Pour chaque ligne : + Pos_Y_src=Pos_Y_src_Initiale; + for (Pos_Y_dest=Pos_Y_dest_Initiale;Pos_Y_dest<=Pos_Y_dest_Finale;Pos_Y_dest++) + { + // Pour chaque colonne: + Pos_X_src=Pos_X_src_Initiale; + for (Pos_X_dest=Pos_X_dest_Initiale;Pos_X_dest<=Pos_X_dest_Finale;Pos_X_dest++) + { + Couleur=Lit_pixel_dans_brosse(Pos_X_src>>16,Pos_Y_src>>16); + if (Couleur!=Back_color) + Pixel_Preview(Pos_X_dest,Pos_Y_dest,Couleur); + + Pos_X_src+=Delta_X; + } + + Pos_Y_src+=Delta_Y; + } +} + + + +//------------------------- Rotation de la brosse --------------------------- + +#define INDEFINI (-1.0e20F) +float * ScanY_Xt[2]; +float * ScanY_Yt[2]; +float * ScanY_X[2]; + + +void Interpoler_texture(int Debut_X,int Debut_Y,int Xt1,int Yt1, + int Fin_X ,int Fin_Y ,int Xt2,int Yt2,int Hauteur) +{ + int Pos_X,Pos_Y; + int Incr_X,Incr_Y; + int i,Cumul; + int Delta_X,Delta_Y; + int Delta_Xt=Xt2-Xt1; + int Delta_Yt=Yt2-Yt1; + int Delta_X2=Fin_X-Debut_X; + int Delta_Y2=Fin_Y-Debut_Y; + float Xt,Yt; + + + Pos_X=Debut_X; + Pos_Y=Debut_Y; + + if (Debut_XDelta_Y) + { + Cumul=Delta_X>>1; + for (i=0; i<=Delta_X; i++) + { + if (Cumul>=Delta_X) + { + Cumul-=Delta_X; + Pos_Y+=Incr_Y; + } + + if ((Pos_Y>=0) && (Pos_Y=ScanY_X[0][Pos_Y]) + { + if ((ScanY_X[1][Pos_Y]==INDEFINI) // Droit non dfini + || (Pos_X>ScanY_X[1][Pos_Y])) + { + ScanY_X[1][Pos_Y]=Pos_X; + ScanY_Xt[1][Pos_Y]=Xt; + ScanY_Yt[1][Pos_Y]=Yt; + } + } + else + { + if (ScanY_X[1][Pos_Y]==INDEFINI) // Droit non dfini + { + ScanY_X[1][Pos_Y]=ScanY_X[0][Pos_Y]; + ScanY_Xt[1][Pos_Y]=ScanY_Xt[0][Pos_Y]; + ScanY_Yt[1][Pos_Y]=ScanY_Yt[0][Pos_Y]; + ScanY_X[0][Pos_Y]=Pos_X; + ScanY_Xt[0][Pos_Y]=Xt; + ScanY_Yt[0][Pos_Y]=Yt; + } + else + { + ScanY_X[0][Pos_Y]=Pos_X; + ScanY_Xt[0][Pos_Y]=Xt; + ScanY_Yt[0][Pos_Y]=Yt; + } + } + } + } + Pos_X+=Incr_X; + Cumul+=Delta_Y; + } + } + else + { + Cumul=Delta_Y>>1; + for (i=0; i<=Delta_Y; i++) + { + if (Cumul>=Delta_Y) + { + Cumul-=Delta_Y; + Pos_X+=Incr_X; + } + + if ((Pos_Y>=0) && (Pos_Y=ScanY_X[0][Pos_Y]) + { + if ((ScanY_X[1][Pos_Y]==INDEFINI) // Droit non dfini + || (Pos_X>ScanY_X[1][Pos_Y])) + { + ScanY_X[1][Pos_Y]=Pos_X; + ScanY_Xt[1][Pos_Y]=Xt; + ScanY_Yt[1][Pos_Y]=Yt; + } + } + else + { + if (ScanY_X[1][Pos_Y]==INDEFINI) // Droit non dfini + { + ScanY_X[1][Pos_Y]=ScanY_X[0][Pos_Y]; + ScanY_Xt[1][Pos_Y]=ScanY_Xt[0][Pos_Y]; + ScanY_Yt[1][Pos_Y]=ScanY_Yt[0][Pos_Y]; + ScanY_X[0][Pos_Y]=Pos_X; + ScanY_Xt[0][Pos_Y]=Xt; + ScanY_Yt[0][Pos_Y]=Yt; + } + else + { + ScanY_X[0][Pos_Y]=Pos_X; + ScanY_Xt[0][Pos_Y]=Xt; + ScanY_Yt[0][Pos_Y]=Yt; + } + } + } + } + Pos_Y+=Incr_Y; + Cumul+=Delta_X; + } + } +} + + + +void Calculer_quad_texture(int X1,int Y1,int Xt1,int Yt1, + int X2,int Y2,int Xt2,int Yt2, + int X3,int Y3,int Xt3,int Yt3, + int X4,int Y4,int Xt4,int Yt4, + byte * Buffer, int Largeur, int Hauteur) +{ + int Xmin,Xmax,Ymin,Ymax; + int X,Y,Xt,Yt; + int Debut_X,Fin_X,Largeur_ligne; + float Temp; + byte Couleur; + + Xmin=Min(Min(X1,X2),Min(X3,X4)); + Ymin=Min(Min(Y1,Y2),Min(Y3,Y4)); + + ScanY_Xt[0]=(float *)malloc(Hauteur*sizeof(float)); + ScanY_Xt[1]=(float *)malloc(Hauteur*sizeof(float)); + ScanY_Yt[0]=(float *)malloc(Hauteur*sizeof(float)); + ScanY_Yt[1]=(float *)malloc(Hauteur*sizeof(float)); + ScanY_X[0] =(float *)malloc(Hauteur*sizeof(float)); + ScanY_X[1] =(float *)malloc(Hauteur*sizeof(float)); + + // Remplir avec des valeurs gales INDEFINI. + for (Y=0; Y>1); + Debut_Y=1-(Brosse_Hauteur>>1); + Fin_X=Debut_X+Brosse_Largeur-1; + Fin_Y=Debut_Y+Brosse_Hauteur-1; + + Transformer_point(Debut_X,Debut_Y, cosA,sinA, &X1,&Y1); + Transformer_point(Fin_X ,Debut_Y, cosA,sinA, &X2,&Y2); + Transformer_point(Debut_X,Fin_Y , cosA,sinA, &X3,&Y3); + Transformer_point(Fin_X ,Fin_Y , cosA,sinA, &X4,&Y4); + + // Calcul des nouvelles dimensions de la brosse: + Xmin=Min(Min((int)X1,(int)X2),Min((int)X3,(int)X4)); + Xmax=Max(Max((int)X1,(int)X2),Max((int)X3,(int)X4)); + Ymin=Min(Min((int)Y1,(int)Y2),Min((int)Y3,(int)Y4)); + Ymax=Max(Max((int)Y1,(int)Y2),Max((int)Y3,(int)Y4)); + + New_Brosse_Largeur=Xmax+1-Xmin; + New_Brosse_Hauteur=Ymax+1-Ymin; + + free(Smear_Brosse); // On libre un peu de mmoire + + if (New_Brosse=(byte *)malloc(New_Brosse_Largeur*New_Brosse_Hauteur)) + { + // Et maintenant on calcule la nouvelle brosse tourne. + Calculer_quad_texture(X1,Y1, 0, 0, + X2,Y2,Brosse_Largeur-1, 0, + X3,Y3, 0,Brosse_Hauteur-1, + X4,Y4,Brosse_Largeur-1,Brosse_Hauteur-1, + New_Brosse,New_Brosse_Largeur,New_Brosse_Hauteur); + + free(Brosse); + Brosse=New_Brosse; + + Brosse_Largeur=New_Brosse_Largeur; + Brosse_Hauteur=New_Brosse_Hauteur; + + Smear_Brosse_Largeur=(Brosse_Largeur>TAILLE_MAXI_PINCEAU)?Brosse_Largeur:TAILLE_MAXI_PINCEAU; + Smear_Brosse_Hauteur=(Brosse_Hauteur>TAILLE_MAXI_PINCEAU)?Brosse_Hauteur:TAILLE_MAXI_PINCEAU; + Smear_Brosse=(byte *)malloc(((long)Smear_Brosse_Hauteur)*Smear_Brosse_Largeur); + + if (!Smear_Brosse) // On ne peut mme pas allouer la brosse du smear! + { + Erreur(0); + + free(Brosse); + Brosse=(byte *)malloc(1*1); + Brosse_Hauteur=1; + Brosse_Largeur=1; + + Smear_Brosse=(byte *)malloc(TAILLE_MAXI_PINCEAU*TAILLE_MAXI_PINCEAU); + Smear_Brosse_Hauteur=TAILLE_MAXI_PINCEAU; + Smear_Brosse_Largeur=TAILLE_MAXI_PINCEAU; + } + + Brosse_Decalage_X=(Brosse_Largeur>>1); + Brosse_Decalage_Y=(Brosse_Hauteur>>1); + } + else + { + // Ici la libration de mmoire n'a pas suffit donc on remet dans l'tat + // o c'etait avant. On a juste rallouer la Smear_Brosse car il y a + // normalement la place pour elle puisque rien d'autre n'a pu tre allou + // entre temps. + Smear_Brosse=(byte *)malloc(((long)Smear_Brosse_Hauteur)*Smear_Brosse_Largeur); + Erreur(0); + } +} + + + +void Dessiner_quad_texture_preview(int X1,int Y1,int Xt1,int Yt1, + int X2,int Y2,int Xt2,int Yt2, + int X3,int Y3,int Xt3,int Yt3, + int X4,int Y4,int Xt4,int Yt4) +{ + int Xmin,Xmax,Ymin,Ymax; + int X,Y,Xt,Yt; + int Y_,Ymin_; + int Debut_X,Fin_X,Largeur,Hauteur; + float Temp; + byte Couleur; + + Xmin=Min(Min(X1,X2),Min(X3,X4)); + Xmax=Max(Max(X1,X2),Max(X3,X4)); + Ymin=Min(Min(Y1,Y2),Min(Y3,Y4)); + Ymax=Max(Max(Y1,Y2),Max(Y3,Y4)); + Hauteur=1+Ymax-Ymin; + + ScanY_Xt[0]=(float *)malloc(Hauteur*sizeof(float)); + ScanY_Xt[1]=(float *)malloc(Hauteur*sizeof(float)); + ScanY_Yt[0]=(float *)malloc(Hauteur*sizeof(float)); + ScanY_Yt[1]=(float *)malloc(Hauteur*sizeof(float)); + ScanY_X[0] =(float *)malloc(Hauteur*sizeof(float)); + ScanY_X[1] =(float *)malloc(Hauteur*sizeof(float)); + + // Remplir avec des valeurs gales INDEFINI. + for (Y=0; YLimite_Bas) Ymax=Limite_Bas; + + for (Y_=Ymin; Y_<=Ymax; Y_++) + { + Y=Y_-Ymin_; + Debut_X=Round(ScanY_X[0][Y]); + Fin_X =Round(ScanY_X[1][Y]); + + Largeur=1+Fin_X-Debut_X; + + if (Debut_XLimite_Droite) Fin_X=Limite_Droite; + + for (X=Debut_X; X<=Fin_X; X++) + { + Temp=(float)(0.5+(float)X-ScanY_X[0][Y])/(float)Largeur; + Xt=Round((float)(ScanY_Xt[0][Y])+(Temp*(ScanY_Xt[1][Y]-ScanY_Xt[0][Y]))); + Yt=Round((float)(ScanY_Yt[0][Y])+(Temp*(ScanY_Yt[1][Y]-ScanY_Yt[0][Y]))); + + Couleur=Lit_pixel_dans_brosse(Xt,Yt); + if (Couleur!=Back_color) + Pixel_Preview(X,Y_,Couleur); + } + } + + free(ScanY_Xt[0]); + free(ScanY_Xt[1]); + free(ScanY_Yt[0]); + free(ScanY_Yt[1]); + free(ScanY_X[0]); + free(ScanY_X[1]); +} + + +void Tourner_brosse_preview(float Angle) +{ + short X1,Y1,X2,Y2,X3,Y3,X4,Y4; + int Debut_X,Fin_X,Debut_Y,Fin_Y; + float cosA=cos(Angle); + float sinA=sin(Angle); + + // Calcul des coordonnes des 4 coins: + // 1 2 + // 3 4 + + Debut_X=1-(Brosse_Largeur>>1); + Debut_Y=1-(Brosse_Hauteur>>1); + Fin_X=Debut_X+Brosse_Largeur-1; + Fin_Y=Debut_Y+Brosse_Hauteur-1; + + Transformer_point(Debut_X,Debut_Y, cosA,sinA, &X1,&Y1); + Transformer_point(Fin_X ,Debut_Y, cosA,sinA, &X2,&Y2); + Transformer_point(Debut_X,Fin_Y , cosA,sinA, &X3,&Y3); + Transformer_point(Fin_X ,Fin_Y , cosA,sinA, &X4,&Y4); + + X1+=Brosse_Centre_rotation_X; + Y1+=Brosse_Centre_rotation_Y; + X2+=Brosse_Centre_rotation_X; + Y2+=Brosse_Centre_rotation_Y; + X3+=Brosse_Centre_rotation_X; + Y3+=Brosse_Centre_rotation_Y; + X4+=Brosse_Centre_rotation_X; + Y4+=Brosse_Centre_rotation_Y; + + // Et maintenant on dessine la brosse tourne. + Dessiner_quad_texture_preview(X1,Y1, 0, 0, + X2,Y2,Brosse_Largeur-1, 0, + X3,Y3, 0,Brosse_Hauteur-1, + X4,Y4,Brosse_Largeur-1,Brosse_Hauteur-1); +} diff --git a/graph.h b/graph.h new file mode 100644 index 00000000..1d7ec5bc --- /dev/null +++ b/graph.h @@ -0,0 +1,154 @@ +//byte Meilleure_couleur(byte Rouge, byte Vert, byte Bleu); + +void Remapper_ecran_apres_changement_couleurs_menu(void); +void Calculer_couleurs_menu_optimales(struct Composantes * Palette); + +dword Memoire_libre(void); + +void Liste2tables(word * Liste,short Pas,byte Mode,byte * Table_inc,byte * Table_dec); + +void Num2str(dword Nombre,char * Chaine,byte Taille); +int Str2num(char * Chaine); + +short Round(float Valeur); +short Round_max(short Numerateur,short Diviseur); +short Round_div_max(short Numerateur,short Diviseur); + +int Min(int A,int B); + +void Transformer_point(short X, short Y, + float cosA, float sinA, short * Xr, short * Yr); + +void Recadrer_ecran_par_rapport_au_zoom(void); +void Calculer_split(void); +void Calculer_donnees_loupe(void); +void Calculer_limites(void); +void Calculer_coordonnees_pinceau(void); + +char* Libelle_mode(int Mode); + +void Initialiser_mode_video(int Numero); +void Pixel_dans_barre_d_outil(word X,word Y,byte Couleur); +void Pixel_dans_fenetre(word X,word Y,byte Couleur); +void Encadrer_couleur_menu(byte Couleur); +void Afficher_palette_du_menu(void); +void Afficher_menu(void); +void Recadrer_palette(void); + +void Print_general(short X,short Y,char * Chaine,byte Couleur_texte,byte Couleur_fond); +void Print_dans_fenetre(short X,short Y,char * Chaine,byte Couleur_texte,byte Couleur_fond); +void Print_char_dans_fenetre(short Pos_X,short Pos_Y,char Caractere,byte Couleur_texte,byte Couleur_fond); +void Print_char_transparent_dans_fenetre(short Pos_X,short Pos_Y,char Caractere,byte Couleur); +void Print_dans_menu(char * Chaine, short Position); +void Print_coordonnees(void); +void Print_nom_fichier(void); + +byte Aucun_effet(word X,word Y,byte Couleur); +byte Effet_Shade(word X,word Y,byte Couleur); +byte Effet_Quick_shade(word X,word Y,byte Couleur); +byte Effet_Tiling(word X,word Y,byte Couleur); +byte Effet_Smooth(word X,word Y,byte Couleur); + +void Afficher_foreback(void); + + +void Afficher_pixel(short X,short Y,byte Couleur); + +void Afficher_pinceau(short X,short Y,byte Couleur,byte Preview); +void Effacer_pinceau(short X,short Y); +void Effacer_curseur(void); +void Afficher_curseur(void); + +byte Demande_de_confirmation(char * Message); +void Warning_message(char * Message); + +void Afficher_limites_de_l_image(void); +void Afficher_ecran(void); +void Fenetre_Afficher_cadre_general(word Pos_X,word Pos_Y,word Largeur,word Hauteur, + byte Couleur_HG,byte Couleur_BD,byte Couleur_S,byte Couleur_CHG,byte Couleur_CBD); +void Fenetre_Afficher_cadre_mono(word Pos_X,word Pos_Y,word Largeur,word Hauteur,byte Couleur); +void Fenetre_Afficher_cadre_creux(word Pos_X,word Pos_Y,word Largeur,word Hauteur); +void Fenetre_Afficher_cadre_bombe(word Pos_X,word Pos_Y,word Largeur,word Hauteur); +void Fenetre_Afficher_cadre(word Pos_X,word Pos_Y,word Largeur,word Hauteur); + +void Afficher_sprite_dans_menu(int Numero_bouton,int Numero_sprite); +void Afficher_pinceau_dans_menu(void); +void Afficher_pinceau_dans_fenetre(word X,word Y,int Numero); + +void Dessiner_zigouigoui(word X,word Y, byte Couleur, short Sens); +void Bloc_degrade_dans_fenetre(word Pos_X,word Pos_Y,word Debut_block,word Fin_block); +void Redimentionner_image(word Largeur_choisie,word Hauteur_choisie); + +void Fenetre_Afficher_sprite_drive(word Pos_X,word Pos_Y,byte Type); + +void Capturer_brosse(short Debut_X,short Debut_Y,short Fin_X,short Fin_Y,short Effacement); +void Rotate_90_deg(void); +void Etirer_brosse(short X1, short Y1, short X2, short Y2); +void Etirer_brosse_preview(short X1, short Y1, short X2, short Y2); +void Tourner_brosse(float Angle); +void Tourner_brosse_preview(float Angle); + +void Remap_brosse(void); +void Get_colors_from_brush(void); +void Outline_brush(void); +void Nibble_brush(void); + +void Remplir(byte Couleur_de_remplissage); +void Remplacer(byte Nouvelle_couleur); + +void Pixel_figure_Preview (short Pos_X,short Pos_Y,byte Couleur); +void Pixel_figure_Preview_xor(short Pos_X,short Pos_Y,byte Couleur); + +void Tracer_cercle_vide_Definitif(short Centre_X,short Centre_Y,short Rayon,byte Couleur); +void Tracer_cercle_vide_Preview (short Centre_X,short Centre_Y,short Rayon,byte Couleur); +void Effacer_cercle_vide_Preview (short Centre_X,short Centre_Y,short Rayon); +void Tracer_cercle_plein (short Centre_X,short Centre_Y,short Rayon,byte Couleur); + +void Tracer_ellipse_vide_Definitif(short Centre_X,short Centre_Y,short Rayon_horizontal,short Rayon_vertical,byte Couleur); +void Tracer_ellipse_vide_Preview (short Centre_X,short Centre_Y,short Rayon_horizontal,short Rayon_vertical,byte Couleur); +void Effacer_ellipse_vide_Preview (short Centre_X,short Centre_Y,short Rayon_horizontal,short Rayon_vertical); +void Tracer_ellipse_pleine (short Centre_X,short Centre_Y,short Rayon_horizontal,short Rayon_vertical,byte Couleur); + +void Tracer_ligne_Definitif (short Debut_X,short Debut_Y,short Fin_X,short Fin_Y,byte Couleur); +void Tracer_ligne_Preview (short Debut_X,short Debut_Y,short Fin_X,short Fin_Y,byte Couleur); +void Tracer_ligne_Preview_xor(short Debut_X,short Debut_Y,short Fin_X,short Fin_Y,byte Couleur); +void Effacer_ligne_Preview (short Debut_X,short Debut_Y,short Fin_X,short Fin_Y); + +void Tracer_rectangle_vide(short Debut_X,short Debut_Y,short Fin_X,short Fin_Y,byte Couleur); +void Tracer_rectangle_plein(short Debut_X,short Debut_Y,short Fin_X,short Fin_Y,byte Couleur); + +void Tracer_courbe_Definitif(short X1, short Y1, short X2, short Y2, short X3, short Y3, short X4, short Y4, byte Couleur); +void Tracer_courbe_Preview (short X1, short Y1, short X2, short Y2, short X3, short Y3, short X4, short Y4, byte Couleur); +void Effacer_courbe_Preview (short X1, short Y1, short X2, short Y2, short X3, short Y3, short X4, short Y4, byte Couleur); + +void Aerographe(short Bouton_clicke); + +void Degrade_de_base (long Indice,short Pos_X,short Pos_Y); +void Degrade_de_trames_simples (long Indice,short Pos_X,short Pos_Y); +void Degrade_de_trames_etendues(long Indice,short Pos_X,short Pos_Y); +void Degrade_aleatoire (long Indice,short Pos_X,short Pos_Y); + +void Tracer_cercle_degrade (short Centre_X,short Centre_Y,short Rayon,short Eclairage_X,short Eclairage_Y); +void Tracer_ellipse_degradee(short Centre_X,short Centre_Y,short Rayon_horizontal,short Rayon_vertical,short Eclairage_X,short Eclairage_Y); + +void Polyfill(int Vertices, short * Points, int Color); +void Capturer_brosse_au_lasso(int Vertices, short * Points,short Effacement); + +// Gestion des backups: +void Download_infos_page_principal(S_Page * Page); +void Upload_infos_page_principal(S_Page * Page); +void Download_infos_page_brouillon(S_Page * Page); +void Upload_infos_page_brouillon(S_Page * Page); +void Download_infos_backup(S_Liste_de_pages * Liste); +int Initialiser_les_listes_de_backups_en_debut_de_programme(int Taille,int Largeur,int Hauteur); +void Detruire_les_listes_de_backups_en_fin_de_programme(void); +void Nouveau_nombre_de_backups(int Nouveau); +int Backup_avec_nouvelles_dimensions(int Upload,int Largeur,int Hauteur); +int Backuper_et_redimensionner_brouillon(int Largeur,int Hauteur); +void Backup(void); +void Undo(void); +void Redo(void); +void Detruire_la_page_courante(void); +void Interchanger_image_principale_et_brouillon(void); + +void Changer_facteur_loupe(byte Indice_facteur); diff --git a/history.txt b/history.txt new file mode 100644 index 00000000..eab074ab --- /dev/null +++ b/history.txt @@ -0,0 +1,273 @@ +HISTORY of GRAFX: (in chronological order: latest version at the end) + +* GRAFX 1.0 -> 1.02 (09/??/1995 -> 07/??/1996) + Forget it! + +* GRAFX 2.00 Beta 90% (11/01/1996) - Wired'96 release + This version was 1st shown at the Wired'96 demo party in Belgium. + We gave it to many people there, so let's start history from here. + Note that there were a few different "90%" versions because we didn't + want to change the number just for tiny bug-fixes. + +* GRAFX 2.00 Beta 91% (11/20/1996) + - Fixed: Terrific bug in Help/Messages (one line was too long and + crashed the program!). + - Added: Some new parameters for the settings. + - Added: Now, you can automatically set the best resolution for the + picture loaded and/or slightly adapt the picture to keep the colors of + the menu (for those who want to use GrafX2 as a viewer). + - Fixed: Bug that occured when you wanted to restore your previous + brush while being in "grab brush" mode. + - Added: English user's manual written (will be updated later, and + translated into French). + - Fixed: No more displays pixels out of the preview window when + loading corrupt pictures. + - Fixed: Small bug in LBM loading (for non-standard widths). + - Fixed: Minor error when saving the original screen dimensions in PKM + files. (we didn't save words with Intel conventions) + - Fixed: Exactly the same bug for LBM (but with Motorola conventions) + - Removed: No more saving the current palette when exiting the program + (that was useless and boring when pictures had a weird palette). + +* GRAFX 2.00 Beta 92% (11/27/1996) + - Fixed/Removed: Error message occuring when accessing a drive with no + disk or so finally suppressed! + - Fixed: BMP loading was almost completely bugged and it should now be + completely debugged. + - Fixed/Modified: Set_palette routine (the previous one was fast but + did not work with some weird cards that don't support a REP OUTSB). + - Added: Multi-Undo. + - Added: Backup (*.BAK) files. + +* GRAFX 2.00 Beta 93% (12/12/1996) + - Fixed: Bug that occured when approaching the borders of the screen + in grid mode with the type of cursor used for brush grabbing. + - Fixed: Small but annoying bug when saving files with a name of 9 + characters. + - Fixed: Saved PAL files no longer modify the picture's name (some + mistake must have been done when we implemented the backup option). + - Added: Now, you can stop the loading of previews by pressing a key. + - Improved: Video cards that don't use the same VESA bank for reading + and writing should now work correctly. + - Improved: Frame displayed around the magnifier's preview. + - Improved: Menu of resolutions completely modified, and many new + modes added. + - Modified: The default colors of the menu have been slightly + lightened. + - Improved: The whole configuration is now saved and reloaded in the + settings menu. + +* GRAFX 2.00 Beta 94.0|1|2% (02/13-23/1997) - ACE CD #4 & Volcanic3 releases + (These different versions were too close from each other to be + separated in this file. Just check the last modifications to know + which version you have) + - Added/Improved: (approximative) HAM6 and HAM8 support in IFF(LBM) + files, and improved compatibily with Amiga IFF files => should be + total now. + - Added: The absolutely useless :) CEL and KCF (KISS) file formats. + - Added: The not much more useful SCx (ColoRIX) file format. + - Improved: You can now use the keys to scroll the text in the Help. + - Fixed: Small bug in the scrolling list of resolutions (1 extra line + was displayed at the end of the list when current mode was 640x512). + - Added: English user's manual translated into French (and corrected.. + There can be bugs in text files :)). + - Improved: Now, you can use the brush as an eraser by right clicking. + - Added: X-Invert in the palette editor. + - Fixed: Small bug in the reduce-palette function. + - Improved: GIF saving strongly accelerated (finally!). + - Improved: Shade mode completely modified (customized shades added). + - Fixed: Tiny bug in the block definition of the palette editor. + - Improved: Non-standard PCX files that don't reset the compression + after each line should be supported now (at least for 256-color + pictures). + - Added: Undo in the Shade menu. + - Added: Statistics screen. + +* GRAFX 2.00 Beta 94.666% (03/20/1997) + - Fixed: Statistics screen no longer displays that VESA 1.2 is not + supported. + - Fixed: A few bugs of no consequence. + - Fixed: Bug in the mode-X initialization introduced in the previous + version. + - Added: It is possible to choose between Relative and Absolute + coordinates in the settings menu. + - Improved: The colors of the menu are now calculated from the current + palette, so you won't have to be concerned by the colors of the menu + any more. + - Fixed: The VESA modes are no longer disabled for some video cards. + - Imporoved: "Windows 95" keys are now usable. + - Modified: We now use the EOS dos-extender Copyright (c) 1996 by + Eclipse, so read carefully the docs if you can't use GrafX2 anymore. + +* GRAFX 2.00 Beta 95% (07/18/1997) - Wired'97 release + (It's GrafX2 creation's 1st anniversary! =D (...but still Beta :/) + We wrote the usual "void main(int argc, char * argv[])" one year ago!) + - Fixed: PCX files with odd widths should be supported now. (We fixed + a bug in version 94.1% which added a new one) :( + - Fixed: Small display bug in the grid of the Sieve menu. + - Fixed: Oops! We forgot to remap the colors of the menu when loading + a PAL file. That's stupid! :) + - Improved: The number of predefined paintbrushes has been doubled. + - Added: Outline and Nibble effects for brushes. + - Improved: The "Brush grabbing", "Zoom" and "Pipette" options are no + more stopped by hiding/showing the tool-bar. + - Improved: Now, you can change the current color while drawing. + - Improved: The "auto-set resolution" option works better. + - Added: The 3 color components are displayed in the toolbar when you + want to choose a color. + - Added: A small preview of the color selected by the pipette is + displayed in the tool-bar. + - Fixed: GIF saving (the bug didn't corrupt the file but resulted in a + file that wasn't as well compressed as it should have been). + - Fixed: GIF loading doesn't flash any more on some pictures that were + not corrupt; and LBM neither when loading is interrupted by user. + - Added: Menu where you can choose what you want to copy to the spare + page (pixels, palette, or both...). + - Modified: The size of the palette editor has been very slightly + reduced. + - Modified: The Stencil is now taken into account when using the + "Clear" button. + - Improved: The "magnify" mode is finally displayed with a splitted + screen where you can see both zoomed and unzoomed parts of the picture. + - Added: Now, you can load a picture from the command line (type + "gfx2 /?" for the syntax). + - Added: The preview of a PAL file is now displayed in file-selectors. + - Modified: The tool-bar has been reduced vertically by about 1/3. + - Fixed: Bug in the Grid menu. (The user was able to enter a null grid + step. Doh!) + - Added: "Adjust brush pick" option. + - Fixed: DP2e (LBM-"PBM") files (including new BBM files) with odd + width are now loaded correctly. + - Improved: LBM files are now saved with their exact width and not + with a multiple-of-16 witdh (viewers that can't read these files are + "badly coded" because we save them correctly). + - Improved: The selector bar is now placed on last visited directory + when you change directory. + - Added: "Mask" drawing mode. + - Added: "Smear" drawing mode. + - Improved: "Shade" mode options (normal, loop, saturation). + - Added: You can define if you want Feedback (or not) while drawing + in the drawing modes (effects). + - Improved: The amount of memory used for brushes has been reduced. + - Improved: Scrolling lists speed slightly accelerated. + - Improved: FloodFill slightly accelerated. + +* GRAFX 2.00 Beta 95.5% (09/04/1997) + - Improved: SCx files with less than 256 colors are now supported. + - Fixed: Bug when double-clicking on the Floodfill button. + - Fixed: Bug when "flood-filling" with an effect with feedback. + - Fixed: Bug when filling a vertical-1-pixel-wide area. + - Fixed: Bug of the shape of the cursor when a window is open in + magnify mode. + - Added: Special cursor shape for the pipette. + - Modified: The method to recenter the page when exiting magnifier + mode (the picture recovers its position as it was before zooming). + - Added: Linear Frame Buffer (VESA 2.0 LFB) supported. + - Added: You can now load and save brushes (from the Brush FX menu). + - Fixed: A few video modes (Modes X with a height multiple of 270). + - Fixed: You couldn't save the configuration in the settings menu if + the Auto-save option was off. + - Improved: Polyform has now reached its definitive behaviour. + - Added: Polyfill and filled polyform. + - Added: Lasso (polyformed brushes). + - Added: Concentric lines. + - Added: GFX2.INI file (check its contents for new options). + - Improved: GFX2.CFG file will have ascending compatibility with + future versions from now. + - Added: Some drawing tips have been detailed in the documentation + files. + - Improved: Pipette handling. + +* GRAFX 2.00 Beta 96% (11/03/1997) - Saturne (aborted) party 5 release + - Added: Now, you can increase or decrease the size of the paintbrush. + The default keys are [,<] and [.>] ([;.] and [:/] for azerty). + - Added: Typing the first letters of a filename in file-selectors will + place the selection bar onto it. + - Fixed: Small but annoying bugs in the writing of the GFX2.CFG file + in GFXCFG. The data concerning Shade and Stencil modes were destroyed. + - Added/Improved: It is now possible to define the matrix of the + Smooth mode. We also seized the opportunity to improve the Smooth on + the boundaries of the picture, and to improve the function that + calculates nearest colors. + - Added: The "Replace color" option that replaces all the pixels of + the color pointed by the mouse with the paintbrush color. This tool is + accessible by right clicking on the Floodfill button. + - Improved: FloodFill slightly accelerated (especially with small + surfaces). + - Fixed: The picture was automatically zoomed when choosing a zoom + factor in the menu if the Fast_zoom option was set. + - Added: "Stretch brush". + - Added: Now, you can move windows (menus) and even hide the palette + menu for picking a color that is behind it (with the key just below + ). + - Fixed: Small bug in "Menu_ratio=2" mode when remapping the screen + after color changes. + - Added: "Thin" cursor type (looks like VGApaint's one). + - Fixed: A few video modes (Modes X with a height multiple of 224 and + some others). + - Added: It is now possible to select the colors that can be used for + the smooth and transparency modes, and remapping. + - Fixed: Clicking twice on the Lasso button did not restore the paint- + brush correctly. + - Fixed: the absolute coordinates option wasn't correctly saved in + the .INI file. + - Added: A few new parameters can be defined in the .INI file. + - Added: "Copy palette to spare page and remap destination" option + (accessible from the "Copy to spare page" menu (default: Shift+Tab)). + +* GRAFX 2.00 Beta 96.1% (02/28/1998) - Volcanic Party 4 release + - Fixed: File selector gauges don't bug any more when there are more + than 584 entries :) in the current directory. + - Fixed: The file selector _should_ hang no more on non-image (or + corrupt image) files containing data that look like a known format + signature. + - Fixed: Old and horrible :) video bug. Most of the VESA video cards + that displayed unexpected pixels (when moving the mouse for instance) + should work better (perfectly?) now. + - Fixed: The mouse correction factors didn't work properly. + - Added: Quick-shade mode. + - Improved: You can hide any menu that needs a color selection to pick + up a color behind the window. + - Added: A couple of new parameters in the GFX2.INI file. + +* GRAFX 2.00 Alpha 96.3% (04/11/1998) - Lucky n' Tigrou Party 2 release + !!! Warning: possibly unstable version !!! + - Improved: You can edit pictures bigger than 1024x768, and small + pictures take much less memory, allowing to have many more undo pages! + - Improved: The list of undo pages is preserved when you load a + picture, modify its size, or just go to the spare page. + - Added: You can "kill" a page (i.e. removing it from the list of undo + pages). + - Modified: The Settings menu has been reorganized. + - Improved: The drawing mode is no more set to "discontinuous" by + default. + - Improved: The function to compute the best matching RGB color used + in smooth, colorize, and some other operations has been strongly + accelerated on 486 and Cyrix processors, while it should be about the + same speed or very slightly slower on Intel Pentiums (II) than before. + - Fixed: The program finally works under Windows NT (without dos4gw)! + +* GRAFX 2.00 Beta 96.5% (12/23/1999) - Xmas'99 release + - Fixed: This version seems (is!) stable even with huge pictures. :) + - Fixed: A few options on brushes kept modifying the continuity of the + free-hand drawing mode. + - Fixed: The "nibble brush" operation crashed sometimes. + - Fixed: Remapping the screen after modifying colors in the palette + editor displayed, in rare cases, unexpected pixels or even crashed. + It didn't remap correctly the picture in "Magnify" mode, too. + - Fixed: Catastrophic bug occuring when you "flood-filled" an area + starting at the bottom of the picture. + - Added: An option in GFX2.INI to tell if the number of colors used + must be automatically calculated, and another one for the default + video mode at startup. + - Fixed: The colors of the menu are now correctly remapped when + getting colors from the brush. + - Added: Degas Elite's file formats (PI1,PC1,...) support. + - Added: True-color BMP (Windows) and PCX images can be loaded. They + will be converted to a 256-color image with palette optimization and + Floyd/Steinberg dithering. Note: some other true-color formats will be + added in the next release. + - Fixed: Loading corrupt pictures with null dimensions could crash. + - Improved: Brush streching is now in "real time" (and snaps to the + grid if "Adjust brush picking" is set). + - Added: Brush rotation by any angle. diff --git a/init.c b/init.c new file mode 100644 index 00000000..89f5dce9 --- /dev/null +++ b/init.c @@ -0,0 +1,2137 @@ +#define TAILLE_FICHIER_DATA 84369 // Taille du fichier GFX2.DAT + +#include +#include "const.h" +#include "struct.h" +#include "global.h" +#include "modesvdo.h" +#include "graph.h" +#include "boutons.h" +#include "palette.h" +#include "aide.h" +#include "operatio.h" +#include + +#include +#include +#include +#include +#include +#include +#include "divers.h" + +// On dclare mchamment le prototype de Erreur pour viter de faire un +// fichier "main.h": +void Erreur(int Code); + +// Chercher le rpertoire contenant GFX2.EXE +void Chercher_repertoire_du_programme(char * Chaine) +{ + int Position; + + strcpy(Repertoire_du_programme,Chaine); + for (Position=strlen(Repertoire_du_programme);Repertoire_du_programme[Position]!='\\';Position--); + Repertoire_du_programme[Position+1]='\0'; +} + + +word Drive_Touche[26]= +{ + 0x041E, + 0x0430, + 0x042E, + 0x0420, + 0x0412, + 0x0421, + 0x0422, + 0x0423, + 0x0417, + 0x0424, + 0x0425, + 0x0426, + 0x0432, + 0x0431, + 0x0418, + 0x0419, + 0x0410, + 0x0413, + 0x041F, + 0x0414, + 0x0416, + 0x042F, + 0x0411, + 0x042D, + 0x0415, + 0x042C +}; +// Ajouter un lecteur la liste de lecteurs +void Ajouter_lecteur(byte Numero, byte Type) +{ + Drive[Nb_drives].Lettre=Numero+65; + Drive[Nb_drives].Type =Type; + Drive[Nb_drives].Touche=Drive_Touche[Numero]; + + Nb_drives++; +} + + +// Rechercher la liste et le type des lecteurs de la machine +void Rechercher_drives(void) +{ + byte Lecteur; + byte Nb_lecteurs_disquettes; + byte Lecteur_de_disquettes; + byte Type_de_lecteur; + char Bidon[256]; + + Nb_drives=0; + Nb_lecteurs_disquettes=(Type_de_lecteur_de_disquette(0)>0)+(Type_de_lecteur_de_disquette(1)>0); + + // Test du type des lecteurs A: et B: + if (Nb_lecteurs_disquettes==2) + for (Lecteur=0; Lecteur<=1; Lecteur++) + { + switch (Type_de_lecteur_de_disquette(Lecteur)) + { + case 1 : + case 2 : + Ajouter_lecteur(Lecteur,DRIVE_FLOPPY_5_25); + break; + default: + Ajouter_lecteur(Lecteur,DRIVE_FLOPPY_3_5); + } + } + else // On n'a pas 2 lecteurs donc on regarde si "logiquement" c'est A: ou B: + if (Nb_lecteurs_disquettes==1) + { + if (Disk_map(2)==Disk_map(1)) + { + // Il n'y a pas de lecteur mul par un SUBST + Lecteur_de_disquettes=Disk_map(1)-1; + for (Lecteur=0; Lecteur<=1; Lecteur++) + { + switch (Type_de_lecteur_de_disquette(Lecteur)) + { + case 0 : + break; + case 1 : + case 2 : + Ajouter_lecteur(Lecteur_de_disquettes,DRIVE_FLOPPY_5_25); + break; + default: + Ajouter_lecteur(Lecteur_de_disquettes,DRIVE_FLOPPY_3_5); + } + } + } + else + { + // Il y a un lecteur mul par un SUBST + Lecteur_de_disquettes=Disk_map(1)-1; + + // On cherche d'abord sur quel lecteur le lecteur physique est dispo + for (Lecteur=0; Lecteur<=1; Lecteur++) + { + switch (Type_de_lecteur_de_disquette(Lecteur)) + { + case 0 : + break; + case 1 : + case 2 : + Type_de_lecteur=DRIVE_FLOPPY_5_25; + break; + default: + Type_de_lecteur=DRIVE_FLOPPY_3_5; + } + } + + // On dclare les trucs maintenant + if (Lecteur_de_disquettes==0) + { + // Situation : On a un lecteur A: qui est rel et un lecteur B: mul + Ajouter_lecteur(0,Type_de_lecteur); + Ajouter_lecteur(1,DRIVE_NETWORK); + } + else + { + // Situation : On a un lecteur A: qui est rel et un lecteur B: mul + Ajouter_lecteur(0,DRIVE_NETWORK); + Ajouter_lecteur(1,Type_de_lecteur); + } + } + } + else + // Il n'y a pas de lecteur de D7 physique, mais on vrifie s'il n'y en a + // pas qui seraient muls par SUBST + for (Lecteur=0; Lecteur<=1; Lecteur++) + { + switch (Freespace(Lecteur+1)) + { + case -1: + break; + default: + Ajouter_lecteur(Lecteur,DRIVE_NETWORK); + } + } + + // Test de la prsence d'autres lecteurs (HDD, CD, Rseau) + // On les met tous en rseau avant de tester leur vrai type. + for (Lecteur=2; Lecteur<=25; Lecteur++) + { + if (Disque_dur_present(Lecteur-2)) + Ajouter_lecteur(Lecteur,DRIVE_HDD); + else + if (Lecteur_CDROM_present(Lecteur)) + Ajouter_lecteur(Lecteur,DRIVE_CDROM); + else + if (Freespace(Lecteur+1)!=-1) + Ajouter_lecteur(Lecteur,DRIVE_NETWORK); + } + +} + + +// Fonction de dcryptage + + #define DECRYPT_TAILLE_CLE 14 + byte Decrypt_compteur=0; + char Decrypt_cle[DECRYPT_TAILLE_CLE]="Sunset Design"; + + byte Decrypt(byte Octet) + { + byte Temp; + + Temp=Octet ^ Decrypt_cle[Decrypt_compteur]; + if ((++Decrypt_compteur)>=(DECRYPT_TAILLE_CLE-1)) + Decrypt_compteur=0; + return Temp; + } + +// Dcryptage d'une donne + +void Decrypte(byte * Donnee,int Taille) +{ + int Indice; + + for (Indice=0;Indicest_size; + if (Taille_fichier!=TAILLE_FICHIER_DATA) + Erreur(ERREUR_DAT_CORROMPU); + + if (read(Handle,Palette_defaut,sizeof(T_Palette))!=sizeof(T_Palette)) + Erreur(ERREUR_DAT_CORROMPU); + Decrypte((byte *)Palette_defaut,sizeof(T_Palette)); + + if (read(Handle,BLOCK_MENU,LARGEUR_MENU*HAUTEUR_MENU)!=LARGEUR_MENU*HAUTEUR_MENU) + Erreur(ERREUR_DAT_CORROMPU); + Decrypte(BLOCK_MENU,LARGEUR_MENU*HAUTEUR_MENU); + + if (read(Handle,SPRITE_EFFET,LARGEUR_SPRITE_MENU*HAUTEUR_SPRITE_MENU*NB_SPRITES_EFFETS)!= + LARGEUR_SPRITE_MENU*HAUTEUR_SPRITE_MENU*NB_SPRITES_EFFETS) + Erreur(ERREUR_DAT_CORROMPU); + Decrypte((byte *)SPRITE_EFFET,LARGEUR_SPRITE_MENU*HAUTEUR_SPRITE_MENU*NB_SPRITES_EFFETS); + + if (read(Handle,SPRITE_CURSEUR,LARGEUR_SPRITE_CURSEUR*HAUTEUR_SPRITE_CURSEUR*NB_SPRITES_CURSEUR)!= + LARGEUR_SPRITE_CURSEUR*HAUTEUR_SPRITE_CURSEUR*NB_SPRITES_CURSEUR) + Erreur(ERREUR_DAT_CORROMPU); + Decrypte((byte *)SPRITE_CURSEUR,LARGEUR_SPRITE_CURSEUR*HAUTEUR_SPRITE_CURSEUR*NB_SPRITES_CURSEUR); + + if (read(Handle,SPRITE_MENU,LARGEUR_SPRITE_MENU*HAUTEUR_SPRITE_MENU*NB_SPRITES_MENU)!= + LARGEUR_SPRITE_MENU*HAUTEUR_SPRITE_MENU*NB_SPRITES_MENU) + Erreur(ERREUR_DAT_CORROMPU); + Decrypte((byte *)SPRITE_MENU,LARGEUR_SPRITE_MENU*HAUTEUR_SPRITE_MENU*NB_SPRITES_MENU); + + if (read(Handle,SPRITE_PINCEAU,LARGEUR_PINCEAU*HAUTEUR_PINCEAU*NB_SPRITES_PINCEAU)!= + LARGEUR_PINCEAU*HAUTEUR_PINCEAU*NB_SPRITES_PINCEAU) + Erreur(ERREUR_DAT_CORROMPU); + Decrypte((byte *)SPRITE_PINCEAU,LARGEUR_PINCEAU*HAUTEUR_PINCEAU*NB_SPRITES_PINCEAU); + + if (read(Handle,SPRITE_DRIVE,LARGEUR_SPRITE_DRIVE*HAUTEUR_SPRITE_DRIVE*NB_SPRITES_DRIVES)!= + LARGEUR_SPRITE_DRIVE*HAUTEUR_SPRITE_DRIVE*NB_SPRITES_DRIVES) + Erreur(ERREUR_DAT_CORROMPU); + Decrypte((byte *)SPRITE_DRIVE,LARGEUR_SPRITE_DRIVE*HAUTEUR_SPRITE_DRIVE*NB_SPRITES_DRIVES); + + if (!(Logo_GrafX2=(byte *)malloc(231*56))) + Erreur(ERREUR_MEMOIRE); + if (read(Handle,Logo_GrafX2,231*56)!=(231*56)) + Erreur(ERREUR_DAT_CORROMPU); + Decrypte(Logo_GrafX2,231*56); + + if (read(Handle,TRAME_PREDEFINIE,2*16*NB_TRAMES_PREDEFINIES)!=2*16*NB_TRAMES_PREDEFINIES) + Erreur(ERREUR_DAT_CORROMPU); + Decrypte((byte *)TRAME_PREDEFINIE,2*16*NB_TRAMES_PREDEFINIES); + + // Lecture des fontes 8x8: + if (!(Fonte_temporaire=(byte *)malloc(2048))) + Erreur(ERREUR_MEMOIRE); + + // Lecture de la fonte systme + if (read(Handle,Fonte_temporaire,2048)!=2048) + Erreur(ERREUR_DAT_CORROMPU); + Decrypte(Fonte_temporaire,2048); + for (Indice=0;Indice<256;Indice++) + for (Pos_X=0;Pos_X<8;Pos_X++) + for (Pos_Y=0;Pos_Y<8;Pos_Y++) + Fonte_systeme[(Indice<<6)+(Pos_X<<3)+Pos_Y]=( ((*(Fonte_temporaire+(Indice*8)+Pos_Y))&(0x80>>Pos_X)) ? 1 : 0); + + // Lecture de la fonte alternative + if (read(Handle,Fonte_temporaire,2048)!=2048) + Erreur(ERREUR_DAT_CORROMPU); + Decrypte(Fonte_temporaire,2048); + for (Indice=0;Indice<256;Indice++) + for (Pos_X=0;Pos_X<8;Pos_X++) + for (Pos_Y=0;Pos_Y<8;Pos_Y++) + Fonte_fun[(Indice<<6)+(Pos_X<<3)+Pos_Y]=( ((*(Fonte_temporaire+(Indice*8)+Pos_Y))&(0x80>>Pos_X)) ? 1 : 0); + + free(Fonte_temporaire); + + Fonte=Fonte_systeme; + + // Lecture de la fonte 6x8: (spciale aide) + if (read(Handle,Fonte_help,(315*6*8))!=(315*6*8)) + Erreur(ERREUR_DAT_CORROMPU); + Decrypte((byte*)Fonte_help,(315*6*8)); + + // Lecture des diffrentes sections de l'aide: + + // Pour chaque section "Indice" de l'aide: + for (Indice=0;Indice>1); + Pinceau_predefini_Decalage_Y[Indice]=(Pinceau_predefini_Hauteur[Indice]>>1); + } + + Curseur_Decalage_X[FORME_CURSEUR_FLECHE]=0; + Curseur_Decalage_Y[FORME_CURSEUR_FLECHE]=0; + + Curseur_Decalage_X[FORME_CURSEUR_CIBLE]=7; + Curseur_Decalage_Y[FORME_CURSEUR_CIBLE]=7; + + Curseur_Decalage_X[FORME_CURSEUR_CIBLE_PIPETTE]=7; + Curseur_Decalage_Y[FORME_CURSEUR_CIBLE_PIPETTE]=7; + + Curseur_Decalage_X[FORME_CURSEUR_SABLIER]=7; + Curseur_Decalage_Y[FORME_CURSEUR_SABLIER]=7; + + Curseur_Decalage_X[FORME_CURSEUR_MULTIDIRECTIONNEL]=7; + Curseur_Decalage_Y[FORME_CURSEUR_MULTIDIRECTIONNEL]=7; + + Curseur_Decalage_X[FORME_CURSEUR_HORIZONTAL]=7; + Curseur_Decalage_Y[FORME_CURSEUR_HORIZONTAL]=3; + + Curseur_Decalage_X[FORME_CURSEUR_CIBLE_FINE]=7; + Curseur_Decalage_Y[FORME_CURSEUR_CIBLE_FINE]=7; + + Curseur_Decalage_X[FORME_CURSEUR_CIBLE_PIPETTE_FINE]=7; + Curseur_Decalage_Y[FORME_CURSEUR_CIBLE_PIPETTE_FINE]=7; +} + + +// Initialisation des boutons: + + // Action factice: + +void Rien_du_tout(void) +{} + + // Initialiseur d'un bouton: + +void Initialiser_bouton(byte Numero, + word Decalage_X , word Decalage_Y, + word Largeur , word Hauteur, + byte Forme, + fonction_action Gauche , fonction_action Droite, + fonction_action Desenclencher, + byte Famille) +{ + Bouton[Numero].Decalage_X =Decalage_X; + Bouton[Numero].Decalage_Y =Decalage_Y; + Bouton[Numero].Largeur =Largeur-1; + Bouton[Numero].Hauteur =Hauteur-1; + Bouton[Numero].Enfonce =0; + Bouton[Numero].Forme =Forme; + Bouton[Numero].Gauche =Gauche; + Bouton[Numero].Droite =Droite; + Bouton[Numero].Desenclencher =Desenclencher; + Bouton[Numero].Famille =Famille; +} + + + // Initiliseur de tous les boutons: + +void Initialisation_des_boutons(void) +{ + byte Indice_bouton; + + for (Indice_bouton=0;Indice_boutonst_size; + + if ( (Taille_fichier>8) + { + case 0 : Config_Touche[Ordonnancement[Indice2]&0xFF]=CFG_Infos_touche.Touche; break; + case 1 : Bouton[Ordonnancement[Indice2]&0xFF].Raccourci_gauche=CFG_Infos_touche.Touche; break; + case 2 : Bouton[Ordonnancement[Indice2]&0xFF].Raccourci_droite=CFG_Infos_touche.Touche; break; + } + } + else + goto Erreur_lecture_config; + } + } + } + else + { + if (lseek(Handle,Chunk.Taille,SEEK_CUR)==-1) + goto Erreur_lecture_config; + } + break; + case CHUNK_MODES_VIDEO: // Modes vido + if ((Chunk.Taille/sizeof(CFG_Mode_video))!=NB_MODES_VIDEO) + goto Erreur_lecture_config; + for (Indice=1; Indice<=NB_MODES_VIDEO; Indice++) + { + if (read(Handle,&CFG_Mode_video,sizeof(CFG_Mode_video))!=sizeof(CFG_Mode_video)) + goto Erreur_lecture_config; + else + { + for (Indice2=0; + ( (Indice2>6)) ) ); + Indice2++); + if (Indice2>8) + { + case 0 : CFG_Infos_touche.Touche=Config_Touche[Ordonnancement[Indice]&0xFF]; break; + case 1 : CFG_Infos_touche.Touche=Bouton[Ordonnancement[Indice]&0xFF].Raccourci_gauche; break; + case 2 : CFG_Infos_touche.Touche=Bouton[Ordonnancement[Indice]&0xFF].Raccourci_droite; break; + } + CFG_Infos_touche.Touche2=0x00FF; + if (write(Handle,&CFG_Infos_touche,sizeof(CFG_Infos_touche))!=sizeof(CFG_Infos_touche)) + goto Erreur_sauvegarde_config; + } + + // Sauvegarde de l'tat de chaque mode vido + Chunk.Numero=CHUNK_MODES_VIDEO; + Chunk.Taille=NB_MODES_VIDEO*sizeof(CFG_Mode_video); + if (write(Handle,&Chunk,sizeof(Chunk))!=sizeof(Chunk)) + goto Erreur_sauvegarde_config; + for (Indice=0; Indice + +void _splitpath(char* Buffer, char* Chemin, char* Nom_Fichier) +{ + int i=0, Position_Du_Dernier_Slash; + do + { + Chemin[i]=Buffer[i]; + if (Buffer[i]=='/') + Position_Du_Dernier_Slash=i; + i++; + }while (Buffer[i]!=0); + + i=Position_Du_Dernier_Slash+1; + Chemin[i]=0; + strcpy(Nom_Fichier,Buffer+i); +} diff --git a/linux.h b/linux.h new file mode 100644 index 00000000..79f98714 --- /dev/null +++ b/linux.h @@ -0,0 +1,9 @@ +void _splitpath(char* Buffer, char* Chemin, char* Nom_Fichier); +/* Spare dans la chane passe dans Buffer le chemin d'accs du nom de fichier */ + +struct find_t { + unsigned char attrib; + char name[256]; +}; + +#define _A_SUBDIR 1 diff --git a/loadsave.c b/loadsave.c new file mode 100644 index 00000000..875a48ec --- /dev/null +++ b/loadsave.c @@ -0,0 +1,5321 @@ +#define _XOPEN_SOURCE + +#include "const.h" +#include "struct.h" +#include "global.h" +#include "graph.h" +#include "divers.h" +#include "pages.h" +#include "op_c.h" +#include +#include +#include +#include + +#include +#include +#include "boutons.h" + +// On dclare mchamment le prototype de Erreur pour viter de faire un +// fichier "main.h": +void Erreur(int Code); + + +// Chargement des pixels dans l'cran principal +void Pixel_Chargement_dans_ecran_courant(short Pos_X,short Pos_Y,byte Couleur) +{ + if ((Pos_X>=0) && (Pos_Y>=0)) + if ((Pos_X=0) && (Pos_Y>=0)) + if ((Pos_X=0) && (Pos_Y>=0)) + if ((Pos_X> 5) << 5) | + ((V >> 5) << 2) | + ((B >> 6)); + Pixel(Preview_Pos_X+(Pos_X/Preview_Facteur_X), + Preview_Pos_Y+(Pos_Y/Preview_Facteur_Y), + Couleur); + } +} + +// Cration d'une palette fake +void Palette_fake_24b(T_Palette Palette) +{ + int Couleur; + + // Gnration de la palette + for (Couleur=0;Couleur<256;Couleur++) + { + Palette[Couleur].R=((Couleur & 0xE0)>>5)<<3; + Palette[Couleur].V=((Couleur & 0x1C)>>2)<<3; + Palette[Couleur].B=((Couleur & 0x03)>>0)<<4; + } +} + +// Supplment faire lors de l'initialisation d'une preview dans le cas +// d'une image 24b +void Initialiser_preview_24b(int Largeur,int Hauteur) +{ + if (Pixel_de_chargement==Pixel_Chargement_dans_preview) + { + // Aiguillage du chargement 24b + Pixel_Chargement_24b=Pixel_Chargement_dans_preview_24b; + + // Changement de palette + Palette_fake_24b(Principal_Palette); + Set_palette(Principal_Palette); + Remapper_fileselect(); + } + else + { + // Aiguillage du chargement 24b + Pixel_Chargement_24b=Pixel_Chargement_dans_buffer_24b; + + // Allocation du buffer 24b + Buffer_image_24b= + (struct Composantes *)Emprunter_memoire_de_page(Largeur*Hauteur*sizeof(struct Composantes)); + if (!Buffer_image_24b) + { + // Afficher un message d'erreur + + // Pour tre sr que ce soit lisible. + Calculer_couleurs_menu_optimales(Principal_Palette); + Message_Memoire_insuffisante(); + if (Pixel_de_chargement==Pixel_Chargement_dans_ecran_courant) + Erreur_fichier=1; // 1 => On n'a pas perdu l'image courante + else + Erreur_fichier=3; // 3 => Chargement de brosse chou + } + else + Image_24b=1; // On a un buffer traiter en fin de chargement + } +} + + + + +void Initialiser_preview(short Largeur,short Hauteur,long Taille,int Format) +// +// Cette procdure doit tre appele par les routines de chargement +// d'images. +// Elle doit tre appele entre le moment o l'on connait la dimension de +// l'image (dimension relle, pas dimension tronque) et l'affichage du +// premier point. +// +{ + char Chaine[256]; + int Image_en_24b; + + Image_en_24b=Format & FORMAT_24B; + Format =Format & (~FORMAT_24B); + + if (Pixel_de_chargement==Pixel_Chargement_dans_preview) + { + // Prparation du chargement d'une preview: + + // Affichage des donnes "Image size:" + if ((Largeur<10000) && (Hauteur<10000)) + { + Num2str(Largeur,Chaine,4); + Num2str(Hauteur,Chaine+5,4); + Chaine[4]='x'; + Print_dans_fenetre(226,55,Chaine,CM_Noir,CM_Clair); + } + else + { + Print_dans_fenetre(226,55,"VERY BIG!",CM_Noir,CM_Clair); + } + + // Affichage de la taille du fichier + if (Taille<1048576) + { + // Le fichier fait moins d'un Mega, on affiche sa taille direct + Num2str(Taille,Chaine,9); + Print_dans_fenetre(226,63,Chaine,CM_Noir,CM_Clair); + } + else if ((Taille/1024)<10000000) + { + // Le fichier fait plus d'un Mega, on peut afficher sa taille en Ko + Num2str(Taille/1024,Chaine,7); + Chaine[7]='K'; + Chaine[8]='b'; + Print_dans_fenetre(226,63,Chaine,CM_Noir,CM_Clair); + } + else + { + // Le fichier fait plus de 10 Giga octets (cas trs rare :)) + Print_dans_fenetre(226,63,"TOO BIG!!",CM_Noir,CM_Clair); + } + + // Affichage du vrai format + if (Format!=Principal_Format) + { + Print_dans_fenetre( 27,74,"but is:",CM_Fonce,CM_Clair); + Print_dans_fenetre( 83,74,Format_Extension[Format-1],CM_Noir,CM_Clair); + } + + // On efface le commentaire prcdent + Block(Fenetre_Pos_X+46*Menu_Facteur_X,Fenetre_Pos_Y+176*Menu_Facteur_Y, + Menu_Facteur_X<<8,Menu_Facteur_Y<<3,CM_Clair); + // Affichage du commentaire + if (Format_Commentaire[Format-1]) + Print_dans_fenetre(46,176,Principal_Commentaire,CM_Noir,CM_Clair); + + // Calculs des donnes ncessaires l'affichage de la preview: + Preview_Facteur_X=Round_div_max(Largeur,122*Menu_Facteur_X); + Preview_Facteur_Y=Round_div_max(Hauteur, 82*Menu_Facteur_Y); + + if ( (!Config.Maximize_preview) && (Preview_Facteur_X!=Preview_Facteur_Y) ) + { + if (Preview_Facteur_X>Preview_Facteur_Y) + Preview_Facteur_Y=Preview_Facteur_X; + else + Preview_Facteur_X=Preview_Facteur_Y; + } + + Preview_Pos_X=Fenetre_Pos_X+180*Menu_Facteur_X; + Preview_Pos_Y=Fenetre_Pos_Y+ 89*Menu_Facteur_Y; + + // On nettoie la zone o va s'afficher la preview: + Block(Preview_Pos_X,Preview_Pos_Y, + Round_div_max(Largeur,Preview_Facteur_X), + Round_div_max(Hauteur,Preview_Facteur_Y), + CM_Noir); + } + else + { + if (Pixel_de_chargement==Pixel_Chargement_dans_ecran_courant) + { + if (Backup_avec_nouvelles_dimensions(0,Largeur,Hauteur)) + { + // La nouvelle page a pu tre alloue, elle est pour l'instant pleine + // de 0s. Elle fait Principal_Largeur_image de large. + // Normalement tout va bien, tout est sous contrle... + } + else + { + // Afficher un message d'erreur + + // Pour tre sr que ce soit lisible. + Calculer_couleurs_menu_optimales(Principal_Palette); + Message_Memoire_insuffisante(); + Erreur_fichier=1; // 1 => On n'a pas perdu l'image courante + } + } + else // chargement dans la brosse + { + free(Brosse); + free(Smear_Brosse); + Brosse=(byte *)malloc(Largeur*Hauteur); + Brosse_Largeur=Largeur; + Brosse_Hauteur=Hauteur; + if (Brosse) + { + Smear_Brosse=(byte *)malloc(Largeur*Hauteur); + if (!Smear_Brosse) + Erreur_fichier=3; + } + else + Erreur_fichier=3; + } + } + + if (!Erreur_fichier) + if (Image_en_24b) + Initialiser_preview_24b(Largeur,Hauteur); +} + + + +void Dessiner_preview_palette(void) +{ + short Indice; + short Preview_Pos_X=Fenetre_Pos_X+186*Menu_Facteur_X; + short Preview_Pos_Y=Fenetre_Pos_Y+ 90*Menu_Facteur_Y; + + if (Pixel_de_chargement==Pixel_Chargement_dans_preview) + for (Indice=0; Indice<256; Indice++) + Block(Preview_Pos_X+(((Indice>>4)*7)*Menu_Facteur_X), + Preview_Pos_Y+(((Indice&15)*5)*Menu_Facteur_Y), + 5*Menu_Facteur_X,5*Menu_Facteur_Y,Indice); +} + + + +// Calcul du nom complet du fichier +void Nom_fichier_complet(char * Nom_du_fichier, byte Sauve_Colorix) +{ + byte Pos; + + strcpy(Nom_du_fichier,Principal_Repertoire_fichier); + + if (Nom_du_fichier[strlen(Nom_du_fichier)-1]!='\\') + strcat(Nom_du_fichier,"\\"); + + // Si on est en train de sauvegarder une image Colorix, on calcule son ext. + if (Sauve_Colorix) + { + Pos=strlen(Principal_Nom_fichier)-1; + if (Principal_Nom_fichier[Pos]=='?') + { + if (Principal_Largeur_image<=320) + Principal_Nom_fichier[Pos]='I'; + else + { + if (Principal_Largeur_image<=360) + Principal_Nom_fichier[Pos]='Q'; + else + { + if (Principal_Largeur_image<=640) + Principal_Nom_fichier[Pos]='F'; + else + { + if (Principal_Largeur_image<=800) + Principal_Nom_fichier[Pos]='N'; + else + Principal_Nom_fichier[Pos]='O'; + } + } + } + } + } + + strcat(Nom_du_fichier,Principal_Nom_fichier); +} + + +///////////////////////////////////////////////////////////////////////////// +// Gestion des lectures et critures // +///////////////////////////////////////////////////////////////////////////// + +byte * Tampon_lecture; +word Index_lecture; + +void Init_lecture(void) +{ + Tampon_lecture=(byte *)malloc(64000); + Index_lecture=64000; +} + +byte Lire_octet(int Fichier) +{ + if (++Index_lecture>=64000) + { + if (read(Fichier,Tampon_lecture,64000)<=0) + Erreur_fichier=2; + Index_lecture=0; + } + return Tampon_lecture[Index_lecture]; +} + +void Close_lecture(void) +{ + free(Tampon_lecture); +} + +// -------------------------------------------------------------------------- + +byte * Tampon_ecriture; +word Index_ecriture; + +void Init_ecriture(void) +{ + Tampon_ecriture=(byte *)malloc(64000); + Index_ecriture=0; +} + +void Ecrire_octet(int Fichier, byte Octet) +{ + Tampon_ecriture[Index_ecriture++]=Octet; + if (Index_ecriture>=64000) + { + if (write(Fichier,Tampon_ecriture,64000)==-1) + Erreur_fichier=1; + Index_ecriture=0; + } +} + +void Close_ecriture(int Fichier) +{ + if (Index_ecriture) + if (write(Fichier,Tampon_ecriture,Index_ecriture)==-1) + Erreur_fichier=1; + free(Tampon_ecriture); +} + + + +///////////////////////////////////////////////////////////////////////////// + +void (/*__interrupt __near*/ *Ancien_handler_clavier)(void); +void /*__interrupt __near*/ Nouveau_handler_clavier(void) +{ + /* A revoir ... + _disable(); + if (!Erreur_fichier) + Erreur_fichier=-1; + _enable(); + _chain_intr(Ancien_handler_clavier); + */ + ; +} + + +// -------- Modifier la valeur du code d'erreur d'accs un fichier -------- +// On n'est pas oblig d'utiliser cette fonction chaque fois mais il est +// important de l'utiliser dans les cas du type: +// if (!Erreur_fichier) *** else Erreur_fichier=***; +// En fait, dans le cas o l'on modifie Erreur_fichier alors qu'elle contient +// dj un code d'erreur. +void Modif_Erreur_fichier(int Nouvelle_valeur) +{ + if (Erreur_fichier>=0) + Erreur_fichier=Nouvelle_valeur; +} + + +// -- Charger n'importe connu quel type de fichier d'image (ou palette) ----- +void Charger_image(byte Image) +{ + int Indice; // Indice de balayage des formats + int Format; // Format du fichier charger + + + // On place par dfaut Erreur_fichier vrai au cas o on ne sache pas + // charger le format du fichier: + Erreur_fichier=1; + + if (Principal_Format!=0) + { + Format_Test[Principal_Format-1](); + if (!Erreur_fichier) + // Si dans le slecteur il y a un format valide on le prend tout de suite + Format=Principal_Format-1; + } + + if (Erreur_fichier) + { + // Sinon, on va devoir scanner les diffrents formats qu'on connait pour + // savoir quel format est le fichier: + for (Indice=0;Indice0) + Erreur(0); + + if (Image_24b) + { + // On vient de charger une image 24b + if (!Erreur_fichier) + { + // Le chargement a russi, on peut faire la conversion en 256 couleurs + if (Pixel_de_chargement==Pixel_Chargement_dans_ecran_courant) + { + // Cas d'un chargement dans l'image + if (Convert_bitmap_24B_to_256(Principal_Ecran,Buffer_image_24b,Principal_Largeur_image,Principal_Hauteur_image,Principal_Palette)) + Erreur_fichier=2; + } + else + { + // Cas d'un chargement dans la brosse + if (Convert_bitmap_24B_to_256(Brosse,Buffer_image_24b,Brosse_Largeur,Brosse_Hauteur,Principal_Palette)) + Erreur_fichier=2; + } + if (!Erreur_fichier) + Palette_256_to_64(Principal_Palette); + } + + free(Buffer_image_24b); + } + + if (Image) + { + if ( (Erreur_fichier!=1) && (Format_Backup_done[Format]) ) + { + // On considre que l'image charge n'est plus modifie + Principal_Image_modifiee=0; + // Et on documente la variable Principal_Format_fichier avec la valeur: + Principal_Format_fichier=Format+1; + + // Correction des dimensions + if (Principal_Largeur_image<1) + Principal_Largeur_image=1; + if (Principal_Hauteur_image<1) + Principal_Hauteur_image=1; + } + else if (Erreur_fichier!=1) + { + // On considre que l'image charge est encore modifie + Principal_Image_modifiee=1; + // Et on documente la variable Principal_Format_fichier avec la valeur: + Principal_Format_fichier=Format+1; + } + else + { + // Dans ce cas, on sait que l'image n'a pas chang, mais ses + // paramtres (dimension, palette, ...) si. Donc on les restaures. + Download_infos_page_principal(Principal_Backups->Pages); + } + } + } + else + // Sinon, l'appelant sera au courant de l'chec grce Erreur_fichier; + // et si on s'apprtait faire un chargement dfinitif de l'image (pas + // une preview), alors on flash l'utilisateur. + if (Pixel_de_chargement!=Pixel_Chargement_dans_preview) + Erreur(0); +} + + +// -- Sauver n'importe quel type connu de fichier d'image (ou palette) ------ +void Sauver_image(byte Image) +{ + // On place par dfaut Erreur_fichier vrai au cas o on ne sache pas + // sauver le format du fichier: (Est-ce vraiment utile??? Je ne crois pas!) + Erreur_fichier=1; + + Lit_pixel_de_sauvegarde=(Image)?Lit_pixel_dans_ecran_courant:Lit_pixel_dans_brosse; + + Format_Save[Principal_Format_fichier-1](); + + if (Erreur_fichier) + Erreur(0); + else + { + if ((Image) && (Format_Backup_done[Principal_Format_fichier-1])) + Principal_Image_modifiee=0; + } +} + + +///////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// +//////////////////////////////////// PAL //////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// + +// -- Tester si un fichier est au format PAL -------------------------------- +void Test_PAL(void) +{ + int Fichier; // Handle du fichier + char Nom_du_fichier[256]; // Nom complet du fichier + long Taille_du_fichier; // Taille du fichier + struct stat* Informations_Fichier=NULL; + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=1; + + // Ouverture du fichier + Fichier=open(Nom_du_fichier,O_RDONLY); + if (Fichier!=-1) + { + stat(Nom_du_fichier,Informations_Fichier); + // Lecture de la taille du fichier + Taille_du_fichier=Informations_Fichier->st_size; + close(Fichier); + // Le fichier ne peut tre au format PAL que si sa taille vaut 768 octets + if (Taille_du_fichier==sizeof(T_Palette)) + Erreur_fichier=0; + } +} + + +// -- Lire un fichier au format PAL ----------------------------------------- +void Load_PAL(void) +{ + int Handle; // Handle du fichier + char Nom_du_fichier[256]; // Nom complet du fichier + long Taille_du_fichier; // Taille du fichier + + + Nom_fichier_complet(Nom_du_fichier,0); + Erreur_fichier=0; + + // Ouverture du fichier + Handle=open(Nom_du_fichier,O_RDONLY); + if (Handle!=-1) + { + // Initialiser_preview(???); // Pas possible... pas d'image... + + // Lecture du fichier dans Principal_Palette + if (read(Handle,Principal_Palette,sizeof(T_Palette))==sizeof(T_Palette)) + { + Set_palette(Principal_Palette); + Remapper_fileselect(); + + // On dessine une preview de la palette (si chargement=preview) + Dessiner_preview_palette(); + } + else + Erreur_fichier=2; + + // Fermeture du fichier + close(Handle); + } + else + // Si on n'a pas russi ouvrir le fichier, alors il y a eu une erreur + Erreur_fichier=1; +} + + +// -- Sauver un fichier au format PAL --------------------------------------- +void Save_PAL(void) +{ + int Fichier; // Handle du fichier + char Nom_du_fichier[256]; // Nom complet du fichier + long Taille_du_fichier; // Taille du fichier + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=0; + + // Ouverture du fichier + Fichier=open(Nom_du_fichier,O_WRONLY|O_CREAT|O_TRUNC,S_IRUSR|S_IWUSR|S_IRGRP); + if (Fichier!=-1) + { + // Enregistrement de Principal_Palette dans le fichier + if (write(Fichier,Principal_Palette,sizeof(T_Palette))==-1) + { + Erreur_fichier=1; + close(Fichier); + remove(Nom_du_fichier); + } + else // Ecriture correcte => Fermeture normale du fichier + close(Fichier); + } + else // Si on n'a pas russi ouvrir le fichier, alors il y a eu une erreur + { + Erreur_fichier=1; + close(Fichier); + remove(Nom_du_fichier); + // On se fout du rsultat de l'opration car si a + // renvoie 0 c'est que le fichier avait t partiel- + // -lement crit, sinon pas du tout. Or dans tous les + // cas a revient au mme pour nous: Sauvegarde rate! + } +} + + +///////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// +//////////////////////////////////// IMG //////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// + + +// -- Tester si un fichier est au format IMG -------------------------------- +void Test_IMG(void) +{ + int Handle; // Handle du fichier + char Nom_du_fichier[256]; // Nom complet du fichier + struct Header + { + byte Filler1[6]; + word Largeur; + word Hauteur; + byte Filler2[118]; + T_Palette Palette; + } IMG_Header; + byte Signature[6]={0x01,0x00,0x47,0x12,0x6D,0xB0}; + + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=1; + + // Ouverture du fichier + Handle=open(Nom_du_fichier,O_RDONLY); + if (Handle!=-1) + { + // Lecture et vrification de la signature + if ((read(Handle,&IMG_Header,sizeof(struct Header)))==sizeof(struct Header)) + { + if ( (!memcmp(IMG_Header.Filler1,Signature,6)) + && IMG_Header.Largeur && IMG_Header.Hauteur) + Erreur_fichier=0; + } + // Fermeture du fichier + close(Handle); + } +} + + +// -- Lire un fichier au format IMG ----------------------------------------- +void Load_IMG(void) +{ + char Nom_du_fichier[256]; // Nom complet du fichier + byte * Buffer; + int Fichier; + word Pos_X,Pos_Y; + long Largeur_lue; + long Taille_du_fichier; + struct Header + { + byte Filler1[6]; + word Largeur; + word Hauteur; + byte Filler2[118]; + T_Palette Palette; + } IMG_Header; + struct stat* Informations_Fichier=NULL; + + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=0; + + if ((Fichier=open(Nom_du_fichier,O_RDONLY))!=-1) + { + stat(Nom_du_fichier,Informations_Fichier); + Taille_du_fichier=Informations_Fichier->st_size; + + if (read(Fichier,&IMG_Header,sizeof(struct Header))==sizeof(struct Header)) + { + Buffer=(byte *)malloc(IMG_Header.Largeur); + + Initialiser_preview(IMG_Header.Largeur,IMG_Header.Hauteur,Taille_du_fichier,FORMAT_IMG); + if (Erreur_fichier==0) + { + // On commence par passer la palette en 256 comme a, si la nouvelle + // palette a moins de 256 coul, la prcdente ne souffrira pas d'un + // assombrissement prjudiciable. + Palette_64_to_256(Principal_Palette); + // On peut maintenant transfrer la nouvelle palette + memcpy(Principal_Palette,IMG_Header.Palette,sizeof(T_Palette)); + Palette_256_to_64(Principal_Palette); + Set_palette(Principal_Palette); + Remapper_fileselect(); + + Principal_Largeur_image=IMG_Header.Largeur; + Principal_Hauteur_image=IMG_Header.Hauteur; + + for (Pos_Y=0;(Pos_Yst_size; + + if (read(Fichier,&Head,sizeof(struct Header))==sizeof(struct Header)) + { + Principal_Commentaire[0]='\0'; // On efface le commentaire + if (Head.Jump) + { + Indice=0; + while ( (IndiceTAILLE_COMMENTAIRE) + { + Couleur=Octet; // On se sert de Couleur comme + Octet=TAILLE_COMMENTAIRE; // variable temporaire + Couleur-=TAILLE_COMMENTAIRE; + } + else + Couleur=0; + + if (read(Fichier,Principal_Commentaire,Octet)==Octet) + { + Indice+=Octet; + Principal_Commentaire[Octet]='\0'; + if (Couleur) + if (lseek(Fichier,Couleur,SEEK_CUR)==-1) + Erreur_fichier=2; + } + else + Erreur_fichier=2; + } + else + Erreur_fichier=2; + break; + + case 1 : // Dimensions de l'cran d'origine + if (read(Fichier,&Octet,1)==1) + { + if (Octet==4) + { + Indice+=4; + if ( (read(Fichier,&Ecran_original_X,2)!=2) + || (read(Fichier,&Ecran_original_Y,2)!=2) ) + Erreur_fichier=2; + } + else + Erreur_fichier=2; + } + else + Erreur_fichier=2; + break; + + case 2 : // Couleur de transparence + if (read(Fichier,&Octet,1)==1) + { + if (Octet==1) + { + Indice++; + if (read(Fichier,&Back_color,1)!=1) + Erreur_fichier=2; + } + else + Erreur_fichier=2; + } + else + Erreur_fichier=2; + break; + + default: + if (read(Fichier,&Octet,1)==1) + { + Indice+=Octet; + if (lseek(Fichier,Octet,SEEK_CUR)==-1) + Erreur_fichier=2; + } + else + Erreur_fichier=2; + } + } + else + Erreur_fichier=2; + } + if ( (!Erreur_fichier) && (Indice!=Head.Jump) ) + Erreur_fichier=2; + } + + Init_lecture(); + + if (!Erreur_fichier) + { + Initialiser_preview(Head.Largeur,Head.Hauteur,Taille_du_fichier,FORMAT_PKM); + if (Erreur_fichier==0) + { + Principal_Largeur_image=Head.Largeur; + Principal_Hauteur_image=Head.Hauteur; + Taille_image=(dword)(Principal_Largeur_image*Principal_Hauteur_image); + + memcpy(Principal_Palette,Head.Palette,sizeof(T_Palette)); + Set_palette(Principal_Palette); + Remapper_fileselect(); + + Compteur_de_donnees_packees=0; + Compteur_de_pixels=0; + Taille_pack=(Informations_Fichier->st_size)-sizeof(struct Header)-Head.Jump; + + // Boucle de dcompression: + while ( (Compteur_de_pixels>8); + Ecrire_octet(Fichier,Hauteur_ecran&0xFF); + Ecrire_octet(Fichier,Hauteur_ecran>>8); + // Ecriture de la back-color + Ecrire_octet(Fichier,2); + Ecrire_octet(Fichier,1); + Ecrire_octet(Fichier,Back_color); + + // Routine de compression PKM de l'image + Taille_image=(dword)(Principal_Largeur_image*Principal_Hauteur_image); + Compteur_de_pixels=0; + Valeur_pixel=Lit_pixel_de_sauvegarde(0,0); + + while ( (Compteur_de_pixels2) && (Compteur_de_repetitions<256) ) + { // RECON1/couleur/nombre + Ecrire_octet(Fichier,Head.Recon1); + Ecrire_octet(Fichier,Derniere_couleur); + Ecrire_octet(Fichier,Compteur_de_repetitions&0xFF); + } + else + if (Compteur_de_repetitions>=256) + { // RECON2/couleur/hi(nombre)/lo(nombre) + Ecrire_octet(Fichier,Head.Recon2); + Ecrire_octet(Fichier,Derniere_couleur); + Ecrire_octet(Fichier,Compteur_de_repetitions>>8); + Ecrire_octet(Fichier,Compteur_de_repetitions&0xFF); + } + } + else + { + if (Compteur_de_repetitions<256) + { + Ecrire_octet(Fichier,Head.Recon1); + Ecrire_octet(Fichier,Derniere_couleur); + Ecrire_octet(Fichier,Compteur_de_repetitions&0xFF); + } + else + { + Ecrire_octet(Fichier,Head.Recon2); + Ecrire_octet(Fichier,Derniere_couleur); + Ecrire_octet(Fichier,Compteur_de_repetitions>>8); + Ecrire_octet(Fichier,Compteur_de_repetitions&0xFF); + } + } + } + + Close_ecriture(Fichier); + } + else + Erreur_fichier=1; + close(Fichier); + } + else + { + Erreur_fichier=1; + close(Fichier); + } + // S'il y a eu une erreur de sauvegarde, on ne va tout de mme pas laisser + // ce fichier pourri traner... Ca fait pas propre. + if (Erreur_fichier) + remove(Nom_du_fichier); +} + + +///////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// +//////////////////////////////////// LBM //////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// + + +// -- Tester si un fichier est au format LBM -------------------------------- + + int LBM_Fichier; + + // ------------ Lire et traduire une valeur au format Motorola ------------ + dword Lire_long(void) + { + dword Temp; + dword Valeur; + + if (read(LBM_Fichier,&Valeur,4)!=4) + Erreur_fichier=1; + swab((char *)&Valeur,(char *)&Temp,4); + return ((Temp>>16)+(Temp<<16)); + } + + +void Test_LBM(void) +{ + char Nom_du_fichier[256]; + char Format[4]; + char Section[4]; + + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=0; + + if ((LBM_Fichier=open(Nom_du_fichier,O_RDONLY))!=-1) + { + if (read(LBM_Fichier,Section,4)!=4) + Erreur_fichier=1; + else + if (memcmp(Section,"FORM",4)) + Erreur_fichier=1; + else + { + Lire_long(); // On aurait pu vrifier que ce long est gal la taille + // du fichier - 8, mais a aurait interdit de charger des + // fichiers tronqus (et dj que c'est chiant de perdre + // une partie du fichier il faut quand mme pouvoir en + // garder un peu... Sinon, moi je pleure :'( !!! ) + if (read(LBM_Fichier,Format,4)!=4) + Erreur_fichier=1; + else + if ( (memcmp(Format,"ILBM",4)) && (memcmp(Format,"PBM ",4)) ) + Erreur_fichier=1; + } + close(LBM_Fichier); + } + else + Erreur_fichier=1; +} + + +// -- Lire un fichier au format LBM ----------------------------------------- + + byte * LBM_Buffer; + byte Image_HAM; + byte HBPm1; // Header.BitPlanes-1 + + // ---------------- Adapter la palette pour les images HAM ---------------- + void Adapter_Palette_HAM(void) + { + short I,J,Temp; + byte Couleur; + + if (Image_HAM==6) + { + for (I=1; I<=14; I++) + { + // On recopie a palette de base + memcpy(Principal_Palette+(I<<4),Principal_Palette,48); + // On modifie les teintes de cette palette + for (J=0; J<16; J++) + { + Couleur=(I<<4)+J; + if (I<=7) + { + if (I&1) + { + Temp=Principal_Palette[J].R+16; + Principal_Palette[Couleur].R=(Temp<63)?Temp:63; + } + if (I&2) + { + Temp=Principal_Palette[J].V+16; + Principal_Palette[Couleur].V=(Temp<63)?Temp:63; + } + if (I&4) + { + Temp=Principal_Palette[J].B+16; + Principal_Palette[Couleur].B=(Temp<63)?Temp:63; + } + } + else + { + if ((I-7)&1) + { + Temp=Principal_Palette[J].R-16; + Principal_Palette[Couleur].R=(Temp>=0)?Temp:0; + } + if ((I-7)&2) + { + Temp=Principal_Palette[J].V-16; + Principal_Palette[Couleur].V=(Temp>=0)?Temp:0; + } + if ((I-7)&4) + { + Temp=Principal_Palette[J].B-16; + Principal_Palette[Couleur].B=(Temp>=0)?Temp:0; + } + } + } + } + // Ici, il reste les 16 dernires couleurs modifier + for (I=240,J=0; J<16; I++,J++) + { + Temp=Principal_Palette[J].R+8; + Principal_Palette[I].R=(Temp<63)?Temp:63; + Temp=Principal_Palette[J].V+8; + Principal_Palette[I].V=(Temp<63)?Temp:63; + Temp=Principal_Palette[J].B+8; + Principal_Palette[I].B=(Temp<63)?Temp:63; + } + } + else if (Image_HAM==8) + { + for (I=1; I<=3; I++) + { + // On recopie la palette de base + memcpy(Principal_Palette+(I<<6),Principal_Palette,192); + // On modifie les teintes de cette palette + for (J=0; J<64; J++) + { + Couleur=(I<<6)+J; + switch (I) + { + case 1 : + Temp=Principal_Palette[J].R+16; + Principal_Palette[Couleur].R=(Temp<63)?Temp:63; + break; + case 2 : + Temp=Principal_Palette[J].V+16; + Principal_Palette[Couleur].V=(Temp<63)?Temp:63; + break; + default: + Temp=Principal_Palette[J].B+16; + Principal_Palette[Couleur].B=(Temp<63)?Temp:63; + } + } + } + } + else // Image 64 couleurs sauve en 32. + { + for (I=0; I<32; I++) + { + J=I+32; + Principal_Palette[J].R=Principal_Palette[I].R>>1; + Principal_Palette[J].V=Principal_Palette[I].V>>1; + Principal_Palette[J].B=Principal_Palette[I].B>>1; + } + } + } + + // ------------------------- Attendre une section ------------------------- + byte Wait_for(byte * Section_attendue) + { + // Valeur retourne: 1=Section trouve, 0=Section non trouve (erreur) + dword Taille_section; + byte Section_lue[4]; + + if (read(LBM_Fichier,Section_lue,4)!=4) + return 0; + while (memcmp(Section_lue,Section_attendue,4)) // Sect. pas encore trouve + { + Taille_section=Lire_long(); + if (Erreur_fichier) + return 0; + if (Taille_section&1) + Taille_section++; + if (lseek(LBM_Fichier,Taille_section,SEEK_CUR)==-1) + return 0; + if (read(LBM_Fichier,Section_lue,4)!=4) + return 0; + } + return 1; + } + + // ----------------------- Afficher une ligne ILBM ------------------------ + void Draw_ILBM_line(short Pos_Y, short Vraie_taille_ligne) + { + byte Couleur; + byte Rouge,Vert,Bleu; + byte Temp; + short Pos_X; + + if (Image_HAM<=1) // ILBM + { + for (Pos_X=0; Pos_X>2; + Couleur=Meilleure_couleur(Rouge,Vert,Bleu); + break; + case 0x02: // Rouge + Rouge=Temp>>2; + Couleur=Meilleure_couleur(Rouge,Vert,Bleu); + break; + case 0x03: // Vert + Vert=Temp>>2; + Couleur=Meilleure_couleur(Rouge,Vert,Bleu); + break; + default: // Nouvelle couleur + Couleur=Temp; + Rouge=Principal_Palette[Couleur].R; + Vert =Principal_Palette[Couleur].V; + Bleu =Principal_Palette[Couleur].B; + } + Pixel_de_chargement(Pos_X,Pos_Y,Couleur); + } + } + } + + +void Load_LBM(void) +{ + char Nom_du_fichier[256]; + int Fichier; + struct Header_LBM + { + word Width; + word Height; + short Xorg; // Inutile + short Yorg; // Inutile + byte Bit_planes; + byte Mask; + byte Compression; + byte Pad1; // Inutile + word Transp_col; + byte Xaspect; // Inutile + byte Yaspect; // Inutile + short Xscreen; + short Yscreen; + } Header; + char Format[4]; + char Section[4]; + byte Octet; + short B256; + dword Nb_couleurs; + dword Taille_image; + short Pos_X; + short Pos_Y; + short Compteur; + short Taille_ligne; // Taille d'une ligne en octets + short Vraie_taille_ligne; // Taille d'une ligne en pixels + byte Couleur; + long Taille_du_fichier; + struct stat* Informations_Fichier=NULL; + + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=0; + + if ((LBM_Fichier=open(Nom_du_fichier,O_RDONLY))!=-1) + { + stat(Nom_du_fichier,Informations_Fichier); + Taille_du_fichier=Informations_Fichier->st_size; + + // On avance dans le fichier (pas besoin de tester ce qui l'a dj t) + read(LBM_Fichier,Section,4); + Lire_long(); + read(LBM_Fichier,Format,4); + if (!Wait_for("BMHD")) + Erreur_fichier=1; + Lire_long(); + + // Maintenant on lit le header pour pouvoir commencer le chargement de l'image + if ( (read(LBM_Fichier,&Header,sizeof(struct Header_LBM))==sizeof(struct Header_LBM)) + && Header.Width && Header.Height) + { + if ( (Header.Bit_planes) && (Wait_for("CMAP")) ) + { + Nb_couleurs=Lire_long()/3; + + if (((int)1< il faut copier les 32 coul. + } // sur les 32 suivantes et assombrir ces dernires. + else + { + if ((Header.Bit_planes==6) || (Header.Bit_planes==8)) + Image_HAM=Header.Bit_planes; + else + // Erreur_fichier=1; /* C'est cens tre incorrect mais j'ai */ + Image_HAM=0; /* trouv un fichier comme a, alors... */ + } + } + else + Image_HAM=0; + + if ( (!Erreur_fichier) && (Nb_couleurs>=2) && (Nb_couleurs<=256) ) + { + HBPm1=Header.Bit_planes-1; + if (Header.Mask==1) + Header.Bit_planes++; + + // Deluxe paint le fait... alors on le fait... + Back_color=Header.Transp_col; + + // On commence par passer la palette en 256 comme a, si la nouvelle + // palette a moins de 256 coul, la prcdente ne souffrira pas d'un + // assombrissement prjudiciable. + if (Config.Clear_palette) + memset(Principal_Palette,0,sizeof(T_Palette)); + else + Palette_64_to_256(Principal_Palette); + // On peut maintenant charger la nouvelle palette + if (read(LBM_Fichier,Principal_Palette,3*Nb_couleurs)==(3*Nb_couleurs)) + { + Palette_256_to_64(Principal_Palette); + if (Image_HAM) + Adapter_Palette_HAM(); + Set_palette(Principal_Palette); + Remapper_fileselect(); + + // On lit l'octet de padding du CMAP si la taille est impaire + if (Nb_couleurs&1) + if (read(LBM_Fichier,&Octet,1)==1) + Erreur_fichier=2; + + if ( (Wait_for("BODY")) && (!Erreur_fichier) ) + { + Taille_image=Lire_long(); + swab((char *)&Header.Width ,(char *)&Principal_Largeur_image,2); + swab((char *)&Header.Height,(char *)&Principal_Hauteur_image,2); + + swab((char *)&Header.Xscreen,(char *)&Ecran_original_X,2); + swab((char *)&Header.Yscreen,(char *)&Ecran_original_Y,2); + + Initialiser_preview(Principal_Largeur_image,Principal_Hauteur_image,Taille_du_fichier,FORMAT_LBM); + if (Erreur_fichier==0) + { + if (!memcmp(Format,"ILBM",4)) // "ILBM": InterLeaved BitMap + { + // Calcul de la taille d'une ligne ILBM (pour les images ayant des dimensions exotiques) + if (Principal_Largeur_image & 15) + { + Vraie_taille_ligne=( (Principal_Largeur_image+16) >> 4 ) << 4; + Taille_ligne=( (Principal_Largeur_image+16) >> 4 )*(Header.Bit_planes<<1); + } + else + { + Vraie_taille_ligne=Principal_Largeur_image; + Taille_ligne=(Principal_Largeur_image>>3)*Header.Bit_planes; + } + + if (!Header.Compression) + { // non compress + LBM_Buffer=(byte *)malloc(Taille_ligne); + for (Pos_Y=0; ((Pos_Y127) + { + Couleur=Lire_octet(LBM_Fichier); + B256=(short)(256-Octet); + for (Compteur=0; Compteur<=B256; Compteur++) + if (Pos_X127) + { + Couleur=Lire_octet(LBM_Fichier); + B256=256-Octet; + for (Compteur=0; Compteur<=B256; Compteur++) + Pixel_de_chargement(Pos_X++,Pos_Y,Couleur); + } + else + for (Compteur=0; Compteur<=Octet; Compteur++) + Pixel_de_chargement(Pos_X++,Pos_Y,Lire_octet(LBM_Fichier)); + } + } + Close_lecture(); + } + } + } + } + else + Modif_Erreur_fichier(2); + } + else + { + // On restore l'ancienne palette en cas d'erreur... + Palette_256_to_64(Principal_Palette); + // ... ce qui permet de ne renvoyer qu'une erreur 1 (pas de modif) + Erreur_fichier=1; + } + } + else + Modif_Erreur_fichier(1); + } + else + Erreur_fichier=1; + } + else + Erreur_fichier=1; + + close(LBM_Fichier); + } + else + Erreur_fichier=1; +} + + +// -- Sauver un fichier au format LBM --------------------------------------- + + byte LBM_File_de_couleurs[129]; + word LBM_Taille_de_file; + byte LBM_Mode_repetition; + + // ----------- Traduire et crire une valeur au format Motorola ----------- + void Ecrire_long(dword Valeur) + { + dword Temp; + + swab((char *)&Valeur,(char *)&Temp,4); + Valeur=(Temp>>16)+(Temp<<16); + if (write(LBM_Fichier,&Valeur,4)==-1) + Erreur_fichier=1; + } + + // ------------- Ecrire les couleurs que l'on vient de traiter ------------ + void Transferer_couleurs(void) + { + byte Indice; + + if (LBM_Taille_de_file>0) + { + if (LBM_Mode_repetition) + { + Ecrire_octet(LBM_Fichier,257-LBM_Taille_de_file); + Ecrire_octet(LBM_Fichier,LBM_File_de_couleurs[0]); + } + else + { + Ecrire_octet(LBM_Fichier,LBM_Taille_de_file-1); + for (Indice=0; Indice et on a 3 couleurs qui se suivent + { + LBM_Taille_de_file-=2; + Transferer_couleurs(); + LBM_File_de_couleurs[0]=Couleur; + LBM_File_de_couleurs[1]=Couleur; + LBM_File_de_couleurs[2]=Couleur; + LBM_Taille_de_file=3; + LBM_Mode_repetition=1; + } + } + else // La couleur n'est pas la mme que la prcdente + { + if (!LBM_Mode_repetition) // On conserve le mode... + { + LBM_File_de_couleurs[LBM_Taille_de_file++]=Couleur; + if (LBM_Taille_de_file==128) + Transferer_couleurs(); + } + else // On change de mode... + { + Transferer_couleurs(); + LBM_File_de_couleurs[LBM_Taille_de_file]=Couleur; + LBM_Taille_de_file++; + } + } + } + } + + +void Save_LBM(void) +{ + char Nom_du_fichier[256]; + struct Header_LBM + { + word Width; + word Height; + short Xorg; // Inutile + short Yorg; // Inutile + byte BitPlanes; + byte Mask; + byte Compression; + byte Pad1; // Inutile + word Transp_col; // Inutile + byte Xaspect; // Inutile + byte Yaspect; // Inutile + short Xscreen; + short Yscreen; + } Header; + word Pos_X; + word Pos_Y; + byte Octet; + word Vraie_largeur; + struct stat* Informations_Fichier=NULL; + + + Erreur_fichier=0; + Nom_fichier_complet(Nom_du_fichier,0); + + // Ouverture du fichier + LBM_Fichier=open(Nom_du_fichier,O_WRONLY|O_CREAT|O_TRUNC,S_IRUSR|S_IWUSR|S_IRGRP); + if (LBM_Fichier!=-1) + { + write(LBM_Fichier,"FORM",4); + Ecrire_long(0); // On mettra la taille jour la fin + + write(LBM_Fichier,"PBM BMHD",8); + Ecrire_long(20); + + // On corrige la largeur de l'image pour qu'elle soit multiple de 2 + Vraie_largeur=Principal_Largeur_image+(Principal_Largeur_image&1); + + //swab((byte *)&Vraie_largeur,(byte *)&Header.Width,2); + swab((byte *)&Principal_Largeur_image,(byte *)&Header.Width,2); + swab((byte *)&Principal_Hauteur_image,(byte *)&Header.Height,2); + Header.Xorg=0; + Header.Yorg=0; + Header.BitPlanes=8; + Header.Mask=0; + Header.Compression=1; + Header.Pad1=0; + Header.Transp_col=Back_color; + Header.Xaspect=1; + Header.Yaspect=1; + swab((byte *)&Largeur_ecran,(byte *)&Header.Xscreen,2); + swab((byte *)&Hauteur_ecran,(byte *)&Header.Yscreen,2); + + write(LBM_Fichier,&Header,sizeof(struct Header_LBM)); + + write(LBM_Fichier,"CMAP",4); + Ecrire_long(sizeof(T_Palette)); + + Palette_64_to_256(Principal_Palette); + write(LBM_Fichier,Principal_Palette,sizeof(T_Palette)); + Palette_256_to_64(Principal_Palette); + + write(LBM_Fichier,"BODY",4); + Ecrire_long(0); // On mettra la taille jour la fin + + Init_ecriture(); + + LBM_Taille_de_file=0; + + for (Pos_Y=0; ((Pos_Yst_size)-824); + + if (!Erreur_fichier) + { + lseek(LBM_Fichier,4,SEEK_SET); + + // Si la taille de la section de l'image (taille fichier-8) est + // impaire, on rajoute un 0 (Padding) la fin. + if ((Informations_Fichier->st_size) & 1) + { + Ecrire_long((Informations_Fichier->st_size)-7); + lseek(LBM_Fichier,0,SEEK_END); + Octet=0; + if (write(LBM_Fichier,&Octet,1)==-1) + Erreur_fichier=1; + } + else + Ecrire_long((Informations_Fichier->st_size)-8); + + close(LBM_Fichier); + + if (Erreur_fichier) + remove(Nom_du_fichier); + } + else + { + Erreur_fichier=1; + close(LBM_Fichier); + remove(Nom_du_fichier); + } + } + else // Il y a eu une erreur lors du compactage => on efface le fichier + remove(Nom_du_fichier); + } + else + Erreur_fichier=1; +} + + + +///////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// +//////////////////////////////////// BMP //////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// + + +// -- Tester si un fichier est au format BMP -------------------------------- +void Test_BMP(void) +{ + char Nom_du_fichier[256]; + int Fichier; + struct BMP_Header + { + word Signature; // ='BM' = 0x4D42 + long Taille_1; // =Taille du fichier + word Reserv_1; // =0 + word Reserv_2; // =0 + long Decalage; // Nb octets avant les donnes bitmap + + long Taille_2; // =40 + long Largeur; + long Hauteur; + word Plans; // =1 + word Nb_bits; // =1,4,8 ou 24 + long Compression; + long Taille_3; + long XPM; + long YPM; + long Nb_Clr; + long Clr_Imprt; + } Header; + + + Erreur_fichier=1; + Nom_fichier_complet(Nom_du_fichier,0); + + if ((Fichier=open(Nom_du_fichier,O_RDONLY))!=-1) + { + if (read(Fichier,&Header,sizeof(struct BMP_Header))==sizeof(struct BMP_Header)) + if ( (Header.Signature==0x4D42) && (Header.Taille_2==40) + && Header.Largeur && Header.Hauteur ) + Erreur_fichier=0; + close(Fichier); + } +} + + +// -- Charger un fichier au format BMP -------------------------------------- +void Load_BMP(void) +{ + char Nom_du_fichier[256]; + int Fichier; + struct BMP_Header + { + word Signature; // ='BM' = 0x4D42 + long Taille_1; // =Taille du fichier + word Reserv_1; // =0 + word Reserv_2; // =0 + long Decalage; // Nb octets avant les donnes bitmap + + long Taille_2; // =40 + long Largeur; + long Hauteur; + word Plans; // =1 + word Nb_bits; // =1,4,8 ou 24 + long Compression; + long Taille_3; + long XPM; + long YPM; + long Nb_Clr; + long Clr_Imprt; + } Header; + byte * Buffer; + word Indice; + byte Palette_locale[256][4]; // R,V,B,0 + word Nb_Couleurs; + short Pos_X; + short Pos_Y; + word Taille_ligne; + byte A,B,C=0; + long Taille_du_fichier; + struct stat* Informations_Fichier=NULL; + + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=0; + + if ((Fichier=open(Nom_du_fichier,O_RDONLY))!=-1) + { + stat(Nom_du_fichier,Informations_Fichier); + Taille_du_fichier=Informations_Fichier->st_size; + + if (read(Fichier,&Header,sizeof(struct BMP_Header))==sizeof(struct BMP_Header)) + { + switch (Header.Nb_bits) + { + case 1 : + case 4 : + case 8 : + if (Header.Nb_Clr) + Nb_Couleurs=Header.Nb_Clr; + else + Nb_Couleurs=1<>3; + + Buffer=(byte *)malloc(Taille_ligne); + for (Pos_Y=Principal_Hauteur_image-1; ((Pos_Y>=0) && (!Erreur_fichier)); Pos_Y--) + { + if (read(Fichier,Buffer,Taille_ligne)==Taille_ligne) + for (Pos_X=0; Pos_X>1] & 0xF); + else + Pixel_de_chargement(Pos_X,Pos_Y,Buffer[Pos_X>>1] >> 4 ); + break; + case 1 : + if ( Buffer[Pos_X>>3] & (0x80>>(Pos_X&7)) ) + Pixel_de_chargement(Pos_X,Pos_Y,1); + else + Pixel_de_chargement(Pos_X,Pos_Y,0); + } + else + Erreur_fichier=2; + } + free(Buffer); + break; + + case 1 : // Compression RLE 8 bits + Pos_X=0; + Pos_Y=Principal_Hauteur_image-1; + + Init_lecture(); + A=Lire_octet(Fichier); + B=Lire_octet(Fichier); + while ( (!Erreur_fichier) && ((A)||(B!=1)) ) + { + if (A) // Encoded mode + for (Indice=1; Indice<=A; Indice++) + Pixel_de_chargement(Pos_X++,Pos_Y,B); + else // Absolute mode + switch (B) + { + case 0 : // End of line + Pos_X=0; + Pos_Y--; + break; + case 1 : // End of bitmap + break; + case 2 : // Delta + A=Lire_octet(Fichier); + B=Lire_octet(Fichier); + Pos_X+=A; + Pos_Y-=B; + break; + default: // Nouvelle srie + while (B) + { + A=Lire_octet(Fichier); + C=Lire_octet(Fichier); + Pixel_de_chargement(Pos_X++,Pos_Y,A); + if (--B) + { + Pixel_de_chargement(Pos_X++,Pos_Y,C); + B--; + } + } + } + A=Lire_octet(Fichier); + B=Lire_octet(Fichier); + } + Close_lecture(); + break; + + case 2 : // Compression RLE 4 bits + Pos_X=0; + Pos_Y=Principal_Hauteur_image-1; + + Init_lecture(); + A=Lire_octet(Fichier); + B=Lire_octet(Fichier); + while ( (!Erreur_fichier) && ((A)||(B!=1)) ) + { + if (A) // Encoded mode (A fois les 1/2 pixels de B) + for (Indice=1; Indice<=A; Indice++) + { + if (Indice & 1) + Pixel_de_chargement(Pos_X,Pos_Y,B>>4); + else + Pixel_de_chargement(Pos_X,Pos_Y,B&0xF); + Pos_X++; + } + else // Absolute mode + switch (B) + { + case 0 : //End of line + Pos_X=0; + Pos_Y--; + break; + case 1 : // End of bitmap + break; + case 2 : // Delta + A=Lire_octet(Fichier); + B=Lire_octet(Fichier); + Pos_X+=A; + Pos_Y-=B; + break; + default: // Nouvelle srie (B 1/2 pixels bruts) + for (Indice=1; ((Indice<=B) && (!Erreur_fichier)); Indice++,Pos_X++) + { + if (Indice&1) + { + C=Lire_octet(Fichier); + Pixel_de_chargement(Pos_X,Pos_Y,C>>4); + } + else + Pixel_de_chargement(Pos_X,Pos_Y,C&0xF); + } + // On lit l'octet rendant le nombre d'octets pair, si + // ncessaire. Encore un truc de crtin "made in MS". + if ( ((B&3)==1) || ((B&3)==2) ) + Lire_octet(Fichier); + } + A=Lire_octet(Fichier); + B=Lire_octet(Fichier); + } + Close_lecture(); + } + close(Fichier); + } + else + { + close(Fichier); + Erreur_fichier=1; + } + } + } + else + { + // Image 24 bits!!! + Erreur_fichier=0; + + Principal_Largeur_image=Header.Largeur; + Principal_Hauteur_image=Header.Hauteur; + Initialiser_preview(Header.Largeur,Header.Hauteur,Taille_du_fichier,FORMAT_BMP | FORMAT_24B); + + if (Erreur_fichier==0) + { + Taille_ligne=Principal_Largeur_image*3; + Pos_X=(Taille_ligne % 4); // Pos_X sert de variable temporaire + if (Pos_X>0) + Taille_ligne+=(4-Pos_X); + + Buffer=(byte *)malloc(Taille_ligne); + for (Pos_Y=Principal_Hauteur_image-1; ((Pos_Y>=0) && (!Erreur_fichier)); Pos_Y--) + { + if (read(Fichier,Buffer,Taille_ligne)==Taille_ligne) + for (Pos_X=0,Indice=0; Pos_X> 3)+1) << 3; + else + Taille_ligne=Principal_Largeur_image; + + Header.Signature =0x4D42; + Header.Taille_1 =(Taille_ligne*Principal_Hauteur_image)+1078; + Header.Reserv_1 =0; + Header.Reserv_2 =0; + Header.Decalage =1078; + Header.Taille_2 =40; + Header.Largeur =Taille_ligne; + Header.Hauteur =Principal_Hauteur_image; + Header.Plans =1; + Header.Nb_bits =8; + Header.Compression=0; + Header.Taille_3 =0; + Header.XPM =0; + Header.YPM =0; + Header.Nb_Clr =0; + Header.Clr_Imprt =0; + + if (write(Fichier,&Header,sizeof(struct BMP_Header))!=-1) + { + // Chez Bill, ils ont dit: "On va mettre les couleur dans l'ordre + // inverse, et pour faire chier, on va les mettre sur une chelle de + // 0 255 parce que le standard VGA c'est de 0 63 (logique!). Et + // puis comme c'est pas assez dbile, on va aussi y rajouter un octet + // toujours 0 pour forcer les gens s'acheter des gros disques + // durs... Comme a, a fera passer la pillule lorsqu'on sortira + // Windows 95." ... + Palette_64_to_256(Principal_Palette); + for (Indice=0; Indice<256; Indice++) + { + Palette_locale[Indice][0]=Principal_Palette[Indice].B; + Palette_locale[Indice][1]=Principal_Palette[Indice].V; + Palette_locale[Indice][2]=Principal_Palette[Indice].R; + Palette_locale[Indice][3]=0; + } + Palette_256_to_64(Principal_Palette); + + if (write(Fichier,Palette_locale,1024)!=-1) + { + Init_ecriture(); + + // ... Et Bill, il a dit: "OK les gars! Mais seulement si vous rangez + // les pixels dans l'ordre inverse, mais que sur les Y quand-mme + // parce que faut pas pousser." + for (Pos_Y=Principal_Hauteur_image-1; ((Pos_Y>=0) && (!Erreur_fichier)); Pos_Y--) + for (Pos_X=0; Pos_X>=Nb_bits_en_cours; + Nb_bits_traites +=Nb_bits_en_cours; + Nb_bits_a_traiter-=Nb_bits_en_cours; + GIF_Rest_bits -=Nb_bits_en_cours; + } + + return GIF_Code_actuel; + } + + // -- Affiche un nouveau pixel -- + + void GIF_Nouveau_pixel(byte Couleur) + { + Pixel_de_chargement(GIF_Pos_X,GIF_Pos_Y,Couleur); + + GIF_Pos_X++; + + if (GIF_Pos_X>=Principal_Largeur_image) + { + GIF_Pos_X=0; + + if (!GIF_Entrelacee) + GIF_Pos_Y++; + else + { + switch (GIF_Passe) + { + case 0 : GIF_Pos_Y+=8; + break; + case 1 : GIF_Pos_Y+=8; + break; + case 2 : GIF_Pos_Y+=4; + break; + default: GIF_Pos_Y+=2; + } + + if (GIF_Pos_Y>=Principal_Hauteur_image) + { + switch(++GIF_Passe) + { + case 1 : GIF_Pos_Y=4; + break; + case 2 : GIF_Pos_Y=2; + break; + case 3 : GIF_Pos_Y=1; + break; + case 4 : GIF_Image_entrelacee_terminee=1; + } + } + } + } + } + + +void Load_GIF(void) +{ + char Nom_du_fichier[256]; + char Signature[6]; + + word * Alphabet_Pile; // Pile de dcodage d'une chane + word * Alphabet_Prefixe; // Table des prfixes des codes + word * Alphabet_Suffixe; // Table des suffixes des codes + word Alphabet_Free; // Position libre dans l'alphabet + word Alphabet_Max; // Nombre d'entres possibles dans l'alphabet + word Alphabet_Pos_pile; // Position dans la pile de dcodage d'un chane + + struct Type_LSDB + { + word Largeur; // Largeur de l'cran virtuel + word Hauteur; // Hauteur de l'cran virtuel + byte Resol; // Informations sur la rsolution (et autres) + byte Backcol; // Couleur de fond + byte Aspect; // Informations sur l'aspect ratio (et autres) + } LSDB; // Logical Screen Descriptor Block + + struct Type_IDB + { + word Pos_X; // Abscisse o devrait tre affiche l'image + word Pos_Y; // Ordonne o devrait tre affiche l'image + word Largeur_image; // Largeur de l'image + word Hauteur_image; // Hauteur de l'image + byte Indicateur; // Informations diverses sur l'image + byte Nb_bits_pixel; // Nb de bits par pixel + } IDB; // Image Descriptor Block + + word Nb_couleurs; // Nombre de couleurs dans l'image + word Indice_de_couleur; // Indice de traitement d'une couleur + word Taille_de_lecture; // Nombre de donnes lire (divers) + word Indice_de_lecture; // Indice de lecture des donnes (divers) + byte Block_indicateur; // Code indicateur du type de bloc en cours + word Nb_bits_initial; // Nb de bits au dbut du traitement LZW + word Cas_special=0; // Mmoire pour le cas spcial + word Code_ancien=0; // Code prcdent + word Read_byte; // Sauvegarde du code en cours de lecture + word Valeur_Clr; // Valeur <=> Clear tables + word Valeur_Eof; // Valeur <=> Fin d'image + long Taille_du_fichier; + struct stat* Informations_Fichier=NULL; + + + /////////////////////////////////////////////////// FIN DES DECLARATIONS // + + + GIF_Pos_X=0; + GIF_Pos_Y=0; + GIF_Last_byte=0; + GIF_Rest_bits=0; + GIF_Rest_byte=0; + + Nom_fichier_complet(Nom_du_fichier,0); + + if ((GIF_Fichier=open(Nom_du_fichier,O_RDONLY))!=-1) + { + stat(Nom_du_fichier,Informations_Fichier); + Taille_du_fichier=Informations_Fichier->st_size; + + if ( (read(GIF_Fichier,Signature,6)==6) && + ( (memcmp(Signature,"GIF87a",6)==0) || + (memcmp(Signature,"GIF89a",6)==0) ) ) + { + // Allocation de mmoire pour les tables & piles de traitement: + Alphabet_Pile =(word *)malloc(4096*sizeof(word)); + Alphabet_Prefixe=(word *)malloc(4096*sizeof(word)); + Alphabet_Suffixe=(word *)malloc(4096*sizeof(word)); + + if (read(GIF_Fichier,&LSDB,sizeof(struct Type_LSDB))==sizeof(struct Type_LSDB)) + { + // Lecture du Logical Screen Descriptor Block russie: + + Ecran_original_X=LSDB.Largeur; + Ecran_original_Y=LSDB.Hauteur; + + // Palette globale dispo = (LSDB.Resol and $80) + // Profondeur de couleur =((LSDB.Resol and $70) shr 4)+1 + // Nombre de bits/pixel = (LSDB.Resol and $07)+1 + // Ordre de Classement = (LSDB.Aspect and $80) + + Alphabet_Pos_pile=0; + GIF_Last_byte =0; + GIF_Rest_bits =0; + GIF_Rest_byte =0; + + Nb_couleurs=(1 << ((LSDB.Resol & 0x07)+1)); + Nb_bits_initial=(LSDB.Resol & 0x07)+2; + + if (LSDB.Resol & 0x80) + { + // Palette globale dispo: + + // On commence par passer la palette en 256 comme a, si la + // nouvelle palette a moins de 256 coul, la prcdente ne souffrira + // pas d'un assombrissement prjudiciable. + if (Config.Clear_palette) + memset(Principal_Palette,0,sizeof(T_Palette)); + else + Palette_64_to_256(Principal_Palette); + + // On peut maintenant charger la nouvelle palette: + if (!(LSDB.Aspect & 0x80)) + // Palette dans l'ordre: + read(GIF_Fichier,Principal_Palette,Nb_couleurs*3); + else + { + // Palette trie par composantes: + for (Indice_de_couleur=0;Indice_de_couleurValeur_Clr) + { + Alphabet_Pile[Alphabet_Pos_pile++]=Alphabet_Suffixe[GIF_Code_actuel]; + GIF_Code_actuel=Alphabet_Prefixe[GIF_Code_actuel]; + } + + Cas_special=Alphabet_Pile[Alphabet_Pos_pile++]=GIF_Code_actuel; + + do + GIF_Nouveau_pixel(Alphabet_Pile[--Alphabet_Pos_pile]); + while (Alphabet_Pos_pile!=0); + + Alphabet_Prefixe[Alphabet_Free ]=Code_ancien; + Alphabet_Suffixe[Alphabet_Free++]=GIF_Code_actuel; + Code_ancien=Read_byte; + + if (Alphabet_Free>Alphabet_Max) + { + if (GIF_Nb_bits<12) + Alphabet_Max =((1 << (++GIF_Nb_bits))-1); + } + } + else // Code Clear rencontr + { + GIF_Nb_bits =Nb_bits_initial; + Alphabet_Max =((1 << GIF_Nb_bits)-1); + Alphabet_Free =Nb_couleurs+2; + Cas_special =GIF_Get_next_code(); + Code_ancien =GIF_Code_actuel; + GIF_Nouveau_pixel(GIF_Code_actuel); + } + } + else + Erreur_fichier=2; + } // Code End-Of-Information ou erreur de fichier rencontr + + Close_lecture(); + + if (Erreur_fichier>=0) + if ( /* (GIF_Pos_X!=0) || */ + ( ( (!GIF_Entrelacee) && (GIF_Pos_Y!=Principal_Hauteur_image) ) || + ( (GIF_Entrelacee) && (!GIF_Image_entrelacee_terminee) ) + ) ) + Erreur_fichier=2; + } // Le fichier contenait un IDB + else + Erreur_fichier=2; + + } // Le fichier contenait une image + else + Erreur_fichier=2; + + } // Le fichier contenait un LSDB + else + Erreur_fichier=1; + + // Libration de la mmoire utilise par les tables & piles de traitement: + free(Alphabet_Suffixe); + free(Alphabet_Prefixe); + free(Alphabet_Pile); + } // Le fichier contenait au moins la signature GIF87a ou GIF89a + else + Erreur_fichier=1; + + close(GIF_Fichier); + + } // Le fichier tait ouvrable + else + Erreur_fichier=1; +} + + +// -- Sauver un fichier au format GIF --------------------------------------- + + int GIF_Arret; // "On peut arrter la sauvegarde du fichier" + byte GIF_Buffer[256]; // Buffer d'criture de bloc de donnes compiles + + // -- Vider le buffer GIF dans le buffer KM -- + + void GIF_Vider_le_buffer(void) + { + word Indice; + + if (GIF_Rest_byte) + { + GIF_Buffer[0]=GIF_Rest_byte; + + for (Indice=0;Indice<=GIF_Rest_byte;Indice++) + Ecrire_octet(GIF_Fichier,GIF_Buffer[Indice]); + + GIF_Rest_byte=0; + } + } + + // -- Ecrit un code GIF_Nb_bits -- + + void GIF_Set_code(word Code) + { + word Nb_bits_a_traiter=GIF_Nb_bits; + word Nb_bits_traites =0; + word Nb_bits_en_cours; + + while (Nb_bits_a_traiter) + { + Nb_bits_en_cours=(Nb_bits_a_traiter<=(8-GIF_Rest_bits))?Nb_bits_a_traiter:(8-GIF_Rest_bits); + + GIF_Last_byte|=(Code & ((1<>=Nb_bits_en_cours; + GIF_Rest_bits +=Nb_bits_en_cours; + Nb_bits_traites +=Nb_bits_en_cours; + Nb_bits_a_traiter-=Nb_bits_en_cours; + + if (GIF_Rest_bits==8) // Il ne reste plus de bits coder sur l'octet courant + { + // Ecrire l'octet balancer: + GIF_Buffer[++GIF_Rest_byte]=GIF_Last_byte; + + // Si on a atteint la fin du bloc de Raster Data + if (GIF_Rest_byte==255) + // On doit vider le buffer qui est maintenant plein + GIF_Vider_le_buffer(); + + GIF_Last_byte=0; + GIF_Rest_bits=0; + } + } + } + + + // -- Lire le pixel suivant -- + + byte GIF_Pixel_suivant(void) + { + byte Temp; + + Temp=Lit_pixel_de_sauvegarde(GIF_Pos_X,GIF_Pos_Y); + + if (++GIF_Pos_X>=Principal_Largeur_image) + { + GIF_Pos_X=0; + if (++GIF_Pos_Y>=Principal_Hauteur_image) + GIF_Arret=1; + } + + return Temp; + } + + + +void Save_GIF(void) +{ + char Nom_du_fichier[256]; + + word * Alphabet_Prefixe; // Table des prfixes des codes + word * Alphabet_Suffixe; // Table des suffixes des codes + word * Alphabet_Fille; // Table des chanes filles (plus longues) + word * Alphabet_Soeur; // Table des chanes soeurs (mme longueur) + word Alphabet_Free; // Position libre dans l'alphabet + word Alphabet_Max; // Nombre d'entres possibles dans l'alphabet + word Depart; // Code prcdent (sert au linkage des chanes) + int Descente; // Boolen "On vient de descendre" + + struct Type_LSDB + { + word Largeur; // Largeur de l'cran virtuel |_ Dimensions de l'image si 1 + word Hauteur; // Hauteur de l'cran virtuel | seule image dans le fichier (ce qui est notre cas) + byte Resol; // Informations sur la rsolution (et autres) + byte Backcol; // Couleur de fond + byte Aspect; // Informations sur l'aspect ratio (et autres) + } LSDB; // Logical Screen Descriptor Block + + struct Type_IDB + { + word Pos_X; // Abscisse o devrait tre affiche l'image + word Pos_Y; // Ordonne o devrait tre affiche l'image + word Largeur_image; // Largeur de l'image + word Hauteur_image; // Hauteur de l'image + byte Indicateur; // Informations diverses sur l'image + byte Nb_bits_pixel; // Nb de bits par pixel + } IDB; // Image Descriptor Block + + byte Block_indicateur; // Code indicateur du type de bloc en cours + word Chaine_en_cours; // Code de la chane en cours de traitement + byte Caractere; // Caractre coder + word Indice; // Indice de recherche de chane + + + /////////////////////////////////////////////////// FIN DES DECLARATIONS // + + + GIF_Pos_X=0; + GIF_Pos_Y=0; + GIF_Last_byte=0; + GIF_Rest_bits=0; + GIF_Rest_byte=0; + + Nom_fichier_complet(Nom_du_fichier,0); + + GIF_Fichier=open(Nom_du_fichier,O_WRONLY|O_CREAT|O_TRUNC,S_IRUSR|S_IWUSR|S_IRGRP); + if (GIF_Fichier!=-1) + { + // On crit la signature du fichier + if (write(GIF_Fichier,"GIF87a",6)==6) + { + // La signature du fichier a t correctement crite. + + // Allocation de mmoire pour les tables + Alphabet_Prefixe=(word *)malloc(4096*sizeof(word)); + Alphabet_Suffixe=(word *)malloc(4096*sizeof(word)); + Alphabet_Fille =(word *)malloc(4096*sizeof(word)); + Alphabet_Soeur =(word *)malloc(4096*sizeof(word)); + + // On initialise le LSDB du fichier + if (Config.Taille_ecran_dans_GIF) + { + LSDB.Largeur=Largeur_ecran; + LSDB.Hauteur=Hauteur_ecran; + } + else + { + LSDB.Largeur=Principal_Largeur_image; + LSDB.Hauteur=Principal_Hauteur_image; + } + LSDB.Resol =0x97; // Image en 256 couleurs, avec une palette + LSDB.Backcol=0; + LSDB.Aspect =0; // Palette normale + + // On sauve le LSDB dans le fichier + + if (write(GIF_Fichier,&LSDB,sizeof(struct Type_LSDB))==sizeof(struct Type_LSDB)) + { + // Le LSDB a t correctement crit. + + // On sauve la palette + + Palette_64_to_256(Principal_Palette); + if (write(GIF_Fichier,Principal_Palette,768)==768) + { + // La palette a t correctement crite. + + // Le jour o on se servira des blocks d'extensions pour placer + // des commentaires, on le fera ici. + + // On va crire un block indicateur d'IDB et l'IDB du fichier + + Block_indicateur=0x2C; + IDB.Pos_X=0; + IDB.Pos_Y=0; + IDB.Largeur_image=Principal_Largeur_image; + IDB.Hauteur_image=Principal_Hauteur_image; + IDB.Indicateur=0x07; // Image non entrelace, pas de palette locale. + IDB.Nb_bits_pixel=8; // Image 256 couleurs; + + if ( (write(GIF_Fichier,&Block_indicateur,1)==1) && + (write(GIF_Fichier,&IDB,sizeof(struct Type_IDB))==sizeof(struct Type_IDB)) ) + { + // Le block indicateur d'IDB et l'IDB ont ts correctements + // crits. + + Init_ecriture(); + + Indice=4096; + Erreur_fichier=0; + GIF_Arret=0; + + // Rintialisation de la table: + Alphabet_Free=258; + GIF_Nb_bits =9; + Alphabet_Max =511; + GIF_Set_code(256); + for (Depart=0;Depart<4096;Depart++) + { + Alphabet_Fille[Depart]=4096; + Alphabet_Soeur[Depart]=4096; + } + + ////////////////////////////////////////////// COMPRESSION LZW // + + Depart=Chaine_en_cours=GIF_Pixel_suivant(); + Descente=1; + + do + { + Caractere=GIF_Pixel_suivant(); + + // On regarde si dans la table on aurait pas une chane + // quivalente Chaine_en_cours+Caractere + + while ( (Indice0xFFF) + { + // Rintialisation de la table: + GIF_Set_code(256); + Alphabet_Free=258; + GIF_Nb_bits =9; + Alphabet_Max =511; + for (Depart=0;Depart<4096;Depart++) + { + Alphabet_Fille[Depart]=4096; + Alphabet_Soeur[Depart]=4096; + } + } + else if (Alphabet_Free>Alphabet_Max+1) + { + // On augmente le nb de bits + + GIF_Nb_bits++; + Alphabet_Max=(1< 16c , 1 => 256c + word Bytes_per_plane_line;// Doit toujours tre pair + word Palette_info; // 1 => Couleur , 2 => Gris (ignor partir de la version 4) + word Screen_X; // |_ Dimensions de + word Screen_Y; // | l'cran d'origine + byte Filler[54]; // Ca... J'adore! + } Header; // Je hais ce header! + + + Erreur_fichier=0; + Nom_fichier_complet(Nom_du_fichier,0); + + if ((Fichier=open(Nom_du_fichier,O_RDONLY))!=-1) + { + if (read(Fichier,&Header,sizeof(struct PCX_Header))==sizeof(struct PCX_Header)) + { + // Vu que ce header a une signature de merde et peu significative, il + // va falloir que je teste diffrentes petites valeurs dont je connais + // l'intervalle. Grrr! + if ( (Header.Manufacturer!=10) + || (Header.Compression>1) + || ( (Header.Depth!=1) && (Header.Depth!=2) && (Header.Depth!=4) && (Header.Depth!=8) ) + || ( (Header.Plane!=1) && (Header.Plane!=2) && (Header.Plane!=4) && (Header.Plane!=8) && (Header.Plane!=3) ) + || (Header.X_max>((Reduction_moins_1-(Pos_X%Reduction))*Depth)) & Masque; + Pixel_de_chargement(Pos_X,Pos_Y,Couleur); + } + } + +void Load_PCX(void) +{ + char Nom_du_fichier[256]; + int Fichier; + struct PCX_Header + { + byte Manufacturer; // |_ Il font chier ces cons! Ils auraient pu + byte Version; // | mettre une vraie signature! + byte Compression; // L'image est-elle compresse? + byte Depth; // Nombre de bits pour coder un pixel (inutile puisqu'on se sert de Plane) + word X_min; // |_ Coin haut-gauche | + word Y_min; // | de l'image |_ (Crtin!) + word X_max; // |_ Coin bas-droit | + word Y_max; // | de l'image | + word X_dpi; // |_ Densit de |_ (Presque inutile parce que + word Y_dpi; // | l'image | aucun moniteur n'est pareil!) + byte Palette_16c[48]; // Palette 16 coul (inutile pour 256c) (dbile!) + byte Reserved; // Ca me plait a aussi! + byte Plane; // 4 => 16c , 1 => 256c , ... + word Bytes_per_plane_line;// Doit toujours tre pair + word Palette_info; // 1 => Couleur , 2 => Gris (ignor partir de la version 4) + word Screen_X; // |_ Dimensions de + word Screen_Y; // | l'cran d'origine + byte Filler[54]; // Ca... J'adore! + } Header; // Je hais ce header! + short Taille_ligne; + short Vraie_taille_ligne; // Largeur de l'image corrige + short Largeur_lue; + short Pos_X; + short Pos_Y; + byte Octet1; + byte Octet2; + byte Indice; + dword Nb_couleurs; + long Taille_du_fichier; + byte Palette_CGA[9]={ 84,252,252, 252, 84,252, 252,252,252}; + + long Position; + long Taille_image; + byte * Buffer; + struct stat* Informations_Fichier =NULL; + + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=0; + + if ((Fichier=open(Nom_du_fichier,O_RDONLY))!=-1) + { + stat(Nom_du_fichier,Informations_Fichier); + Taille_du_fichier=Informations_Fichier->st_size; + + if (read(Fichier,&Header,sizeof(struct PCX_Header))==sizeof(struct PCX_Header)) + { + Principal_Largeur_image=Header.X_max-Header.X_min+1; + Principal_Hauteur_image=Header.Y_max-Header.Y_min+1; + + Ecran_original_X=Header.Screen_X; + Ecran_original_Y=Header.Screen_Y; + + if (Header.Plane!=3) + { + Initialiser_preview(Principal_Largeur_image,Principal_Hauteur_image,Taille_du_fichier,FORMAT_PCX); + if (Erreur_fichier==0) + { + // On prpare la palette accueillir les valeurs du fichier PCX + if (Config.Clear_palette) + memset(Principal_Palette,0,sizeof(T_Palette)); + else + Palette_64_to_256(Principal_Palette); + Nb_couleurs=(dword)(1<4) + memcpy(Principal_Palette,Header.Palette_16c,48); + else + { + Principal_Palette[1].R=0; + Principal_Palette[1].V=0; + Principal_Palette[1].B=0; + Octet1=Header.Palette_16c[3]>>5; + if (Nb_couleurs==4) + { // Pal. CGA "alakon" (du Turc Allahkoum qui signifie " la con" :)) + memcpy(Principal_Palette+1,Palette_CGA,9); + if (!(Octet1&2)) + { + Principal_Palette[1].B=84; + Principal_Palette[2].B=84; + Principal_Palette[3].B=84; + } + } // Palette monochrome (on va dire que c'est du N&B) + else + { + Principal_Palette[1].R=252; + Principal_Palette[1].V=252; + Principal_Palette[1].B=252; + } + } + + // On se positionne la fin du fichier - 769 octets pour voir s'il y + // a une palette. + if ( (Header.Depth==8) && (Header.Version>=5) && (Taille_du_fichier>sizeof(T_Palette)) ) + { + lseek(Fichier,Taille_du_fichier-(sizeof(T_Palette)+1),SEEK_SET); + // On regarde s'il y a une palette aprs les donnes de l'image + if (read(Fichier,&Octet1,1)==1) + if (Octet1==12) // Lire la palette si c'est une image en 256 couleurs + { + // On lit la palette 256c que ces crtins ont foutue la fin du fichier + if (read(Fichier,Principal_Palette,sizeof(T_Palette))!=sizeof(T_Palette)) + Erreur_fichier=2; + } + } + Palette_256_to_64(Principal_Palette); + Set_palette(Principal_Palette); + Remapper_fileselect(); + + // Maintenant qu'on a lu la palette que ces crtins sont alls foutre + // la fin, on retourne juste aprs le header pour lire l'image. + lseek(Fichier,sizeof(struct PCX_Header),SEEK_SET); + + if (!Erreur_fichier) + { + Taille_ligne=Header.Bytes_per_plane_line*Header.Plane; + Vraie_taille_ligne=(short)Header.Bytes_per_plane_line<<3; + // On se sert de donnes LBM car le dessin de ligne en moins de 256 + // couleurs se fait comme avec la structure ILBM. + Image_HAM=0; + HBPm1=Header.Plane-1; + LBM_Buffer=(byte *)malloc(Taille_ligne); + + // Chargement de l'image + if (Header.Compression) // Image compresse + { + Init_lecture(); + + Taille_image=(long)Header.Bytes_per_plane_line*Principal_Hauteur_image; + + if (Header.Depth==8) // 256 couleurs (1 plan) + { + for (Position=0; ((Position=Taille_ligne) + { + for (Pos_X=0; Pos_X=Taille_ligne) + { + for (Pos_X=0; Pos_X1) || (Last_pixel>=0xC0) ) + Ecrire_octet(Fichier,Compteur|0xC0); + Ecrire_octet(Fichier,Last_pixel); + + } + } + + // Ecriture de l'octet (12) indiquant que la palette arrive + if (!Erreur_fichier) + Ecrire_octet(Fichier,12); + + Close_ecriture(Fichier); + + // Ecriture de la palette + if (!Erreur_fichier) + { + if (write(Fichier,Principal_Palette,sizeof(T_Palette))==-1) + Erreur_fichier=1; + } + } + else + Erreur_fichier=1; + + close(Fichier); + + if (Erreur_fichier) + remove(Nom_du_fichier); + + // On remet la palette son tat normal + Palette_256_to_64(Principal_Palette); + } + else + Erreur_fichier=1; +} + + +///////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// +//////////////////////////////////// CEL //////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// + + +// -- Tester si un fichier est au format CEL -------------------------------- + +void Test_CEL(void) +{ + char Nom_du_fichier[256]; + int Taille; + int Fichier; + struct CEL_Header1 + { + word Width; // Largeur de l'image + word Height; // Hauteur de l'image + } Header1; + struct CEL_Header2 + { + byte Signa[4]; // Signature du format + byte Kind; // Type de fichier ($10=PALette $20=BitMaP) + byte Nbbits; // Nombre de bits + word Filler1; // ??? + word Largeur; // Largeur de l'image + word Hauteur; // Hauteur de l'image + word Decalage_X; // Decalage en X de l'image + word Decalage_Y; // Decalage en Y de l'image + byte Filler2[16]; // ??? + } Header2; + struct stat* Informations_Fichier =NULL; + + Erreur_fichier=0; + Nom_fichier_complet(Nom_du_fichier,0); + if ((Fichier=open(Nom_du_fichier,O_RDONLY))!=-1) + { + if (read(Fichier,&Header1,sizeof(struct CEL_Header1))==sizeof(struct CEL_Header1)) + { + // Vu que ce header n'a pas de signature, il va falloir tester la + // cohrence de la dimension de l'image avec celle du fichier. + stat(Nom_du_fichier,Informations_Fichier); + Taille=(Informations_Fichier->st_size)-sizeof(struct CEL_Header1); + if ( (!Taille) || ( (((Header1.Width+1)>>1)*Header1.Height)!=Taille ) ) + { + // Tentative de reconnaissance de la signature des nouveaux fichiers + + lseek(Fichier,0,SEEK_SET); + if (read(Fichier,&Header2,sizeof(struct CEL_Header2))==sizeof(struct CEL_Header2)) + { + if (memcmp(Header2.Signa,"KiSS",4)==0) + { + if (Header2.Kind!=0x20) + Erreur_fichier=1; + } + else + Erreur_fichier=1; + } + else + Erreur_fichier=1; + } + } + else + Erreur_fichier=1; + + close(Fichier); + } + else + Erreur_fichier=1; +} + + +// -- Lire un fichier au format CEL ----------------------------------------- + +void Load_CEL(void) +{ + char Nom_du_fichier[256]; + int Fichier; + struct CEL_Header1 + { + word Width; // Largeur de l'image + word Height; // Hauteur de l'image + } Header1; + struct CEL_Header2 + { + byte Signa[4]; // Signature du format + byte Kind; // Type de fichier ($10=PALette $20=BitMaP) + byte Nbbits; // Nombre de bits + word Filler1; // ??? + word Largeur; // Largeur de l'image + word Hauteur; // Hauteur de l'image + word Decalage_X; // Decalage en X de l'image + word Decalage_Y; // Decalage en Y de l'image + byte Filler2[16]; // ??? + } Header2; + short Pos_X; + short Pos_Y; + byte Dernier_octet=0; + long Taille_du_fichier; + struct stat* Informations_Fichier=NULL; + + + Erreur_fichier=0; + Nom_fichier_complet(Nom_du_fichier,0); + if ((Fichier=open(Nom_du_fichier,O_RDONLY))!=-1) + { + if (read(Fichier,&Header1,sizeof(struct CEL_Header1))==sizeof(struct CEL_Header1)) + { + stat(Nom_du_fichier,Informations_Fichier); + Taille_du_fichier=Informations_Fichier->st_size; + if ( (Taille_du_fichier>sizeof(struct CEL_Header1)) + && ( (((Header1.Width+1)>>1)*Header1.Height)==(Taille_du_fichier-sizeof(struct CEL_Header1)) ) ) + { + // Chargement d'un fichier CEL sans signature (vieux fichiers) + Principal_Largeur_image=Header1.Width; + Principal_Hauteur_image=Header1.Height; + Ecran_original_X=Principal_Largeur_image; + Ecran_original_Y=Principal_Hauteur_image; + Initialiser_preview(Principal_Largeur_image,Principal_Hauteur_image,Taille_du_fichier,FORMAT_CEL); + if (Erreur_fichier==0) + { + // Chargement de l'image + Init_lecture(); + for (Pos_Y=0;((Pos_Y> 4)); + } + else + Pixel_de_chargement(Pos_X,Pos_Y,(Dernier_octet & 15)); + Close_lecture(); + } + } + else + { + // On ressaye avec le nouveau format + + lseek(Fichier,0,SEEK_SET); + if (read(Fichier,&Header2,sizeof(struct CEL_Header2))==sizeof(struct CEL_Header2)) + { + // Chargement d'un fichier CEL avec signature (nouveaux fichiers) + + Principal_Largeur_image=Header2.Largeur+Header2.Decalage_X; + Principal_Hauteur_image=Header2.Hauteur+Header2.Decalage_Y; + Ecran_original_X=Principal_Largeur_image; + Ecran_original_Y=Principal_Hauteur_image; + Initialiser_preview(Principal_Largeur_image,Principal_Hauteur_image,Taille_du_fichier,FORMAT_CEL); + if (Erreur_fichier==0) + { + // Chargement de l'image + Init_lecture(); + + if (!Erreur_fichier) + { + // Effacement du dcalage + for (Pos_Y=0;Pos_Y> 4)); + } + else + Pixel_de_chargement(Pos_X+Header2.Decalage_X,Pos_Y+Header2.Decalage_Y,(Dernier_octet & 15)); + break; + + case 8: + for (Pos_Y=0;((Pos_Y16 sont utilises dans l'image + for (Pos_X=16;((Pos_X<256) && (!Utilisation[Pos_X]));Pos_X++); + + if (Pos_X==256) + { + // Cas d'une image 16 couleurs (criture l'ancien format) + + Header1.Width =Principal_Largeur_image; + Header1.Height=Principal_Hauteur_image; + + if (write(Fichier,&Header1,sizeof(struct CEL_Header1))!=-1) + { + // Sauvegarde de l'image + Init_ecriture(); + for (Pos_Y=0;((Pos_Y>4)!=0) + Erreur_fichier=1; + } + else + { + if (read(Fichier,&Header2,sizeof(struct CEL_Header2))==sizeof(struct CEL_Header2)) + { + if (memcmp(Header2.Signa,"KiSS",4)==0) + { + if (Header2.Kind!=0x10) + Erreur_fichier=1; + } + else + Erreur_fichier=1; + } + else + Erreur_fichier=1; + } + close(Fichier); + } + else + Erreur_fichier=1; +} + + +// -- Lire un fichier au format KCF ----------------------------------------- + +void Load_KCF(void) +{ + char Nom_du_fichier[256]; + int Fichier; + struct KCF_Header + { + struct + { + struct + { + byte Octet1; + byte Octet2; + } Couleur[16]; + } Palette[10]; + } Buffer; + struct CEL_Header2 + { + byte Signa[4]; // Signature du format + byte Kind; // Type de fichier ($10=PALette $20=BitMaP) + byte Nbbits; // Nombre de bits + word Filler1; // ??? + word Largeur; // Largeur de l'image ou nb de couleurs dfinies + word Hauteur; // Hauteur de l'image ou nb de palettes dfinies + word Decalage_X; // Decalage en X de l'image + word Decalage_Y; // Decalage en Y de l'image + byte Filler2[16]; // ??? + } Header2; + byte Octet[3]; + int Indice_palette; + int Indice_couleur; + int Indice; + long Taille_du_fichier; + + + Erreur_fichier=0; + Nom_fichier_complet(Nom_du_fichier,0); + if ((Fichier=open(Nom_du_fichier,O_RDONLY))!=-1) + { + Taille_du_fichier=filelength(Fichier); + if (Taille_du_fichier==sizeof(struct KCF_Header)) + { + // Fichier KCF l'ancien format + + if (read(Fichier,&Buffer,sizeof(struct KCF_Header))==sizeof(struct KCF_Header)) + { + // Initialiser_preview(???); // Pas possible... pas d'image... + + if (Config.Clear_palette) + memset(Principal_Palette,0,sizeof(T_Palette)); + + // Chargement de la palette + for (Indice_palette=0;Indice_palette<10;Indice_palette++) + for (Indice_couleur=0;Indice_couleur<16;Indice_couleur++) + { + Indice=16+(Indice_palette*16)+Indice_couleur; + Principal_Palette[Indice].R=((Buffer.Palette[Indice_palette].Couleur[Indice_couleur].Octet1 >> 4) << 2); + Principal_Palette[Indice].B=((Buffer.Palette[Indice_palette].Couleur[Indice_couleur].Octet1 & 15) << 2); + Principal_Palette[Indice].V=((Buffer.Palette[Indice_palette].Couleur[Indice_couleur].Octet2 & 15) << 2); + } + + for (Indice=0;Indice<16;Indice++) + { + Principal_Palette[Indice].R=Principal_Palette[Indice+16].R; + Principal_Palette[Indice].V=Principal_Palette[Indice+16].V; + Principal_Palette[Indice].B=Principal_Palette[Indice+16].B; + } + + Set_palette(Principal_Palette); + Remapper_fileselect(); + } + else + Erreur_fichier=1; + } + else + { + // Fichier KCF au nouveau format + + if (read(Fichier,&Header2,sizeof(struct CEL_Header2))==sizeof(struct CEL_Header2)) + { + // Initialiser_preview(???); // Pas possible... pas d'image... + + Indice=(Header2.Nbbits==12)?16:0; + for (Indice_palette=0;Indice_palette> 4) << 2; + Principal_Palette[Indice].B=(Octet[0] & 15) << 2; + Principal_Palette[Indice].V=(Octet[1] & 15) << 2; + break; + + case 24: // RRRR RRRR | VVVV VVVV | BBBB BBBB + read(Fichier,Octet,3); + Principal_Palette[Indice].R=Octet[0]>>2; + Principal_Palette[Indice].V=Octet[1]>>2; + Principal_Palette[Indice].B=Octet[2]>>2; + } + + Indice++; + } + } + + if (Header2.Nbbits==12) + for (Indice=0;Indice<16;Indice++) + { + Principal_Palette[Indice].R=Principal_Palette[Indice+16].R; + Principal_Palette[Indice].V=Principal_Palette[Indice+16].V; + Principal_Palette[Indice].B=Principal_Palette[Indice+16].B; + } + + Set_palette(Principal_Palette); + Remapper_fileselect(); + } + else + Erreur_fichier=1; + } + close(Fichier); + } + else + Erreur_fichier=1; + + if (!Erreur_fichier) Dessiner_preview_palette(); +} + + +// -- Ecrire un fichier au format KCF --------------------------------------- + +void Save_KCF(void) +{ + char Nom_du_fichier[256]; + int Fichier; + struct KCF_Header + { + struct + { + struct + { + byte Octet1; + byte Octet2; + } Couleur[16]; + } Palette[10]; + } Buffer; + struct CEL_Header2 + { + byte Signa[4]; // Signature du format + byte Kind; // Type de fichier ($10=PALette $20=BitMaP) + byte Nbbits; // Nombre de bits + word Filler1; // ??? + word Largeur; // Largeur de l'image ou nb de couleurs dfinies + word Hauteur; // Hauteur de l'image ou nb de palettes dfinies + word Decalage_X; // Decalage en X de l'image + word Decalage_Y; // Decalage en Y de l'image + byte Filler2[16]; // ??? + } Header2; + byte Octet[3]; + int Indice_palette; + int Indice_couleur; + int Indice; + dword Utilisation[256]; // Table d'utilisation de couleurs + + // On commence par compter l'utilisation de chaque couleurs + Palette_Compter_nb_couleurs_utilisees(Utilisation); + + Erreur_fichier=0; + Nom_fichier_complet(Nom_du_fichier,0); + if ((Fichier=open(Nom_du_fichier,O_WRONLY|O_CREAT|O_TRUNC,S_IRUSR|S_IWUSR|S_IRGRP))!=-1) + { + // Sauvegarde de la palette + + // On regarde si des couleurs >16 sont utilises dans l'image + for (Indice=16;((Indice<256) && (!Utilisation[Indice]));Indice++); + + if (Indice==256) + { + // Cas d'une image 16 couleurs (criture l'ancien format) + + for (Indice_palette=0;Indice_palette<10;Indice_palette++) + for (Indice_couleur=0;Indice_couleur<16;Indice_couleur++) + { + Indice=16+(Indice_palette*16)+Indice_couleur; + Buffer.Palette[Indice_palette].Couleur[Indice_couleur].Octet1=((Principal_Palette[Indice].R>>2)<<4) | (Principal_Palette[Indice].B>>2); + Buffer.Palette[Indice_palette].Couleur[Indice_couleur].Octet2=Principal_Palette[Indice].V>>2; + } + + if (write(Fichier,&Buffer,sizeof(struct KCF_Header))!=sizeof(struct KCF_Header)) + Erreur_fichier=1; + } + else + { + // Cas d'une image 256 couleurs (criture au nouveau format) + + memcpy(Header2.Signa,"KiSS",4); // Initialisation de la signature + Header2.Kind=0x10; // Initialisation du type (PALette) + Header2.Nbbits=24; // Initialisation du nombre de bits + Header2.Filler1=0; // Initialisation du filler 1 (???) + Header2.Largeur=256; // Initialisation du nombre de couleurs + Header2.Hauteur=1; // Initialisation du nombre de palettes + Header2.Decalage_X=0; // Initialisation du dcalage X + Header2.Decalage_Y=0; // Initialisation du dcalage Y + for (Indice=0;Indice<16;Indice++) // Initialisation du filler 2 (???) + Header2.Filler2[Indice]=0; + + if (write(Fichier,&Header2,sizeof(struct CEL_Header2))!=sizeof(struct CEL_Header2)) + Erreur_fichier=1; + + for (Indice=0;(Indice<256) && (!Erreur_fichier);Indice++) + { + Octet[0]=Principal_Palette[Indice].R<<2; + Octet[1]=Principal_Palette[Indice].V<<2; + Octet[2]=Principal_Palette[Indice].B<<2; + if (write(Fichier,Octet,3)!=3) + Erreur_fichier=1; + } + } + + close(Fichier); + + if (Erreur_fichier) + remove(Nom_du_fichier); + } + else + Erreur_fichier=1; +} + + + + + +///////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// +//////////////////////////////////// SCx //////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// + + +// -- Tester si un fichier est au format SCx -------------------------------- +void Test_SCx(void) +{ + int Handle; // Handle du fichier + char Nom_du_fichier[256]; // Nom complet du fichier + byte Signature[3]; + struct Header + { + byte Filler1[4]; + word Largeur; + word Hauteur; + byte Filler2; + byte Plans; + } SCx_Header; + + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=1; + + // Ouverture du fichier + Handle=open(Nom_du_fichier,O_RDONLY); + if (Handle!=-1) + { + // Lecture et vrification de la signature + if ((read(Handle,&SCx_Header,sizeof(struct Header)))==sizeof(struct Header)) + { + if ( (!memcmp(SCx_Header.Filler1,"RIX",3)) + && SCx_Header.Largeur && SCx_Header.Hauteur) + Erreur_fichier=0; + } + // Fermeture du fichier + close(Handle); + } +} + + +// -- Lire un fichier au format SCx ----------------------------------------- +void Load_SCx(void) +{ + char Nom_du_fichier[256]; // Nom complet du fichier + int Fichier; + word Pos_X,Pos_Y; + long Taille,Vraie_taille; + long Taille_du_fichier; + struct Header + { + byte Filler1[4]; + word Largeur; + word Hauteur; + byte Filler2; + byte Plans; + } SCx_Header; + T_Palette SCx_Palette; + + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=0; + + if ((Fichier=open(Nom_du_fichier,O_RDONLY))!=-1) + { + Taille_du_fichier=filelength(Fichier); + + if ((read(Fichier,&SCx_Header,sizeof(struct Header)))==sizeof(struct Header)) + { + Initialiser_preview(SCx_Header.Largeur,SCx_Header.Hauteur,Taille_du_fichier,FORMAT_SCx); + if (Erreur_fichier==0) + { + if (!SCx_Header.Plans) + Taille=sizeof(T_Palette); + else + Taille=sizeof(struct Composantes)*(1<>3)*SCx_Header.Plans; + Vraie_taille=(Taille/SCx_Header.Plans)<<3; + LBM_Buffer=(byte *)malloc(Taille); + HBPm1=SCx_Header.Plans-1; + Image_HAM=0; + + for (Pos_Y=0;(Pos_Y>=1; + } +} + +//// CODAGE d'une partie d'IMAGE //// + +void PI1_16p_to_8b(byte * Src,byte * Dst) +{ + int i; // Indice du pixel calculer + word masque; // Masque de codage + word w0,w1,w2,w3; // Les 4 words bien ordonns de la destination + + masque=0x8000; + w0=w1=w2=w3=0; + for (i=0;i<16;i++) + { + // Pour coder le pixel ni, il faut modifier les 4 words sur leur bit + // correspondant celui du masque + + w0|=(Src[i] & 0x01)?masque:0x00; + w1|=(Src[i] & 0x02)?masque:0x00; + w2|=(Src[i] & 0x04)?masque:0x00; + w3|=(Src[i] & 0x08)?masque:0x00; + masque>>=1; + } + Dst[0]=w0 >> 8; + Dst[1]=w0 & 0x00FF; + Dst[2]=w1 >> 8; + Dst[3]=w1 & 0x00FF; + Dst[4]=w2 >> 8; + Dst[5]=w2 & 0x00FF; + Dst[6]=w3 >> 8; + Dst[7]=w3 & 0x00FF; +} + +//// DECODAGE de la PALETTE //// + +void PI1_Decoder_palette(byte * Src,byte * Pal) +{ + int i; // Numro de la couleur traite + int ip; // Indice dans la palette + word w; // Word contenant le code + + // Schma d'un word = + // + // Low High + // VVVV RRRR | 0000 BBBB + // 0321 0321 | 0321 + + ip=0; + for (i=0;i<16;i++) + { + w=((word)Src[(i*2)+1]<<8) | Src[(i*2)+0]; + + // Traitement des couleurs rouge, verte et bleue: + Pal[ip++]=(((w & 0x0007) << 1) | ((w & 0x0008) >> 3)) << 2; + Pal[ip++]=(((w & 0x7000) >> 11) | ((w & 0x8000) >> 15)) << 2; + Pal[ip++]=(((w & 0x0700) >> 7) | ((w & 0x0800) >> 11)) << 2; + } +} + +//// CODAGE de la PALETTE //// + +void PI1_Coder_palette(byte * Pal,byte * Dst) +{ + int i; // Numro de la couleur traite + int ip; // Indice dans la palette + word w; // Word contenant le code + + // Schma d'un word = + // + // Low High + // VVVV RRRR | 0000 BBBB + // 0321 0321 | 0321 + + ip=0; + for (i=0;i<16;i++) + { + // Traitement des couleurs rouge, verte et bleue: + w =(((word)Pal[ip] & 0x38) >> 3) | (((word)Pal[ip] & 0x04) << 1); ip++; + w|=(((word)Pal[ip] & 0x38) << 9) | (((word)Pal[ip] & 0x04) << 13); ip++; + w|=(((word)Pal[ip] & 0x38) << 5) | (((word)Pal[ip] & 0x04) << 9); ip++; + + Dst[(i*2)+0]=w & 0x00FF; + Dst[(i*2)+1]=(w>>8); + } +} + + +// -- Tester si un fichier est au format PI1 -------------------------------- +void Test_PI1(void) +{ + int Handle; // Handle du fichier + char Nom_du_fichier[256]; // Nom complet du fichier + int Taille; // Taille du fichier + word Res; // Rsolution de l'image + + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=1; + + // Ouverture du fichier + Handle=open(Nom_du_fichier,O_RDONLY); + if (Handle!=-1) + { + // Vrification de la taille + Taille=filelength(Handle); + if ((Taille==32034) || (Taille==32066)) + { + // Lecture et vrification de la rsolution + if ((read(Handle,&Res,2))==2) + { + if (Res==0x0000) + Erreur_fichier=0; + } + } + // Fermeture du fichier + close(Handle); + } +} + + +// -- Lire un fichier au format PI1 ----------------------------------------- +void Load_PI1(void) +{ + char Nom_du_fichier[256]; // Nom complet du fichier + int Fichier; + word Pos_X,Pos_Y; + byte * buffer; + byte * ptr; + byte pixels[320]; + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=0; + if ((Fichier=open(Nom_du_fichier,O_RDONLY))!=-1) + { + // allocation d'un buffer mmoire + buffer=(byte *)malloc(32034); + if (buffer!=NULL) + { + // Lecture du fichier dans le buffer + if (read(Fichier,buffer,32034)==32034) + { + // Initialisation de la preview + Initialiser_preview(320,200,filelength(Fichier),FORMAT_PI1); + if (Erreur_fichier==0) + { + // Initialisation de la palette + if (Config.Clear_palette) + memset(Principal_Palette,0,sizeof(T_Palette)); + PI1_Decoder_palette(buffer+2,(byte *)Principal_Palette); + Set_palette(Principal_Palette); + Remapper_fileselect(); + + Principal_Largeur_image=320; + Principal_Hauteur_image=200; + + // Chargement/dcompression de l'image + ptr=buffer+34; + for (Pos_Y=0;Pos_Y<200;Pos_Y++) + { + for (Pos_X=0;Pos_X<(320>>4);Pos_X++) + { + PI1_8b_to_16p(ptr,pixels+(Pos_X<<4)); + ptr+=8; + } + for (Pos_X=0;Pos_X<320;Pos_X++) + Pixel_de_chargement(Pos_X,Pos_Y,pixels[Pos_X]); + } + } + } + else + Erreur_fichier=1; + free(buffer); + } + else + Erreur_fichier=1; + close(Fichier); + } + else + Erreur_fichier=1; +} + + +// -- Sauver un fichier au format PI1 --------------------------------------- +void Save_PI1(void) +{ + char Nom_du_fichier[256]; // Nom complet du fichier + int Fichier; + short Pos_X,Pos_Y; + byte * buffer; + byte * ptr; + byte pixels[320]; + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=0; + // Ouverture du fichier + Fichier=open(Nom_du_fichier,O_WRONLY|O_CREAT|O_TRUNC,S_IRUSR|S_IWUSR|S_IRGRP); + if (Fichier!=-1) + { + // allocation d'un buffer mmoire + buffer=(byte *)malloc(32034); + // Codage de la rsolution + buffer[0]=0x00; + buffer[1]=0x00; + // Codage de la palette + PI1_Coder_palette((byte *)Principal_Palette,buffer+2); + // Codage de l'image + ptr=buffer+34; + for (Pos_Y=0;Pos_Y<200;Pos_Y++) + { + // Codage de la ligne + memset(pixels,0,320); + if (Pos_Y>4);Pos_X++) + { + PI1_16p_to_8b(pixels+(Pos_X<<4),ptr); + ptr+=8; + } + } + + if (write(Fichier,buffer,32034)==32034) + { + close(Fichier); + } + else // Erreur d'criture (disque plein ou protg) + { + close(Fichier); + remove(Nom_du_fichier); + Erreur_fichier=1; + } + // Libration du buffer mmoire + free(buffer); + } + else + { + close(Fichier); + remove(Nom_du_fichier); + Erreur_fichier=1; + } +} + + + + + +///////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// +//////////////////////////////////// PC1 //////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////// + + +//// DECOMPRESSION d'un buffer selon la mthode PACKBITS //// + +void PC1_Decompresser_PackBits(byte * Src,byte * Dst) +{ + int is,id; // Les indices de parcour des buffers + int n; // Octet de contrle + + for (is=id=0;id<32000;) + { + n=Src[is++]; + + if (n & 0x80) + { + // Recopier Src[is] -n+1 fois + n=257-n; + for (;(n>0) && (id<32000);n--) + Dst[id++]=Src[is]; + is++; + } + else + { + // Recopier n+1 octets littralement + n=n+1; + for (;(n>0) && (id<32000);n--) + Dst[id++]=Src[is++]; + } + + // Contrle des erreurs + if (n>0) + Erreur_fichier=1; + } +} + +//// COMPRESSION d'un buffer selon la mthode PACKBITS //// + +void PC1_Compresser_PackBits(byte * Src,byte * Dst,int TailleS,int * TailleD) +{ + int is; // Indice dans la source + int id; // Indice dans la destination + int ir; // Indice de la rptition + int n; // Taille des squences + int repet; // "Il y a rptition" + + for (is=id=0;is0;n--) + Dst[id++]=Src[is++]; + } + + // On code la partie sans rptitions + if (repet) + { + // On compte la quantit de fois qu'il faut rpter la valeur + for (ir+=3;ir>=1; + } + } +} + +//// CODAGE d'une partie d'IMAGE //// + +// Transformation d'1 ligne de pixels en 4 plans de bits + +void PC1_1lp_to_4pb(byte * Src,byte * Dst0,byte * Dst1,byte * Dst2,byte * Dst3) +{ + int i,j; // Compteurs + int ip; // Indice du pixel calculer + byte masque; // Masque de decodage + byte b0,b1,b2,b3; // Les 4 octets des plans bits sources + + ip=0; + // Pour chacun des 40 octets des plans de bits + for (i=0;i<40;i++) + { + // Pour chacun des 8 bits des octets + masque=0x80; + b0=b1=b2=b3=0; + for (j=0;j<8;j++) + { + b0|=(Src[ip] & 0x01)?masque:0x00; + b1|=(Src[ip] & 0x02)?masque:0x00; + b2|=(Src[ip] & 0x04)?masque:0x00; + b3|=(Src[ip] & 0x08)?masque:0x00; + ip++; + masque>>=1; + } + Dst0[i]=b0; + Dst1[i]=b1; + Dst2[i]=b2; + Dst3[i]=b3; + } +} + + +// -- Tester si un fichier est au format PC1 -------------------------------- +void Test_PC1(void) +{ + int Handle; // Handle du fichier + char Nom_du_fichier[256]; // Nom complet du fichier + int Taille; // Taille du fichier + word Res; // Rsolution de l'image + + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=1; + + // Ouverture du fichier + Handle=open(Nom_du_fichier,O_RDONLY); + if (Handle!=-1) + { + // Vrification de la taille + Taille=filelength(Handle); + if ((Taille<=32066)) + { + // Lecture et vrification de la rsolution + if ((read(Handle,&Res,2))==2) + { + if (Res==0x0080) + Erreur_fichier=0; + } + } + // Fermeture du fichier + close(Handle); + } +} + + +// -- Lire un fichier au format PC1 ----------------------------------------- +void Load_PC1(void) +{ + char Nom_du_fichier[256]; // Nom complet du fichier + int Fichier; + int Taille; + word Pos_X,Pos_Y; + byte * buffercomp; + byte * bufferdecomp; + byte * ptr; + byte pixels[320]; + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=0; + if ((Fichier=open(Nom_du_fichier,O_RDONLY))!=-1) + { + Taille=filelength(Fichier); + // allocation des buffers mmoire + buffercomp=(byte *)malloc(Taille); + bufferdecomp=(byte *)malloc(32000); + if ( (buffercomp!=NULL) && (bufferdecomp!=NULL) ) + { + // Lecture du fichier dans le buffer + if (read(Fichier,buffercomp,Taille)==Taille) + { + // Initialisation de la preview + Initialiser_preview(320,200,filelength(Fichier),FORMAT_PC1); + if (Erreur_fichier==0) + { + // Initialisation de la palette + if (Config.Clear_palette) + memset(Principal_Palette,0,sizeof(T_Palette)); + PI1_Decoder_palette(buffercomp+2,(byte *)Principal_Palette); + Set_palette(Principal_Palette); + Remapper_fileselect(); + + Principal_Largeur_image=320; + Principal_Hauteur_image=200; + + // Dcompression du buffer + PC1_Decompresser_PackBits(buffercomp+34,bufferdecomp); + + // Dcodage de l'image + ptr=bufferdecomp; + for (Pos_Y=0;Pos_Y<200;Pos_Y++) + { + // Dcodage de la scanline + PC1_4pb_to_1lp(ptr,ptr+40,ptr+80,ptr+120,pixels); + ptr+=160; + // Chargement de la ligne + for (Pos_X=0;Pos_X<320;Pos_X++) + Pixel_de_chargement(Pos_X,Pos_Y,pixels[Pos_X]); + } + } + } + else + Erreur_fichier=1; + free(bufferdecomp); + free(buffercomp); + } + else + { + Erreur_fichier=1; + if (bufferdecomp) free(bufferdecomp); + if (buffercomp) free(buffercomp); + } + close(Fichier); + } + else + Erreur_fichier=1; +} + + +// -- Sauver un fichier au format PC1 --------------------------------------- +void Save_PC1(void) +{ + char Nom_du_fichier[256]; // Nom complet du fichier + int Fichier; + int Taille; + short Pos_X,Pos_Y; + byte * buffercomp; + byte * bufferdecomp; + byte * ptr; + byte pixels[320]; + + Nom_fichier_complet(Nom_du_fichier,0); + + Erreur_fichier=0; + // Ouverture du fichier + Fichier=open(Nom_du_fichier,O_WRONLY|O_CREAT|O_TRUNC,S_IRUSR|S_IWUSR|S_IRGRP); + if (Fichier!=-1) + { + // Allocation des buffers mmoire + bufferdecomp=(byte *)malloc(32000); + buffercomp =(byte *)malloc(64066); + // Codage de la rsolution + buffercomp[0]=0x80; + buffercomp[1]=0x00; + // Codage de la palette + PI1_Coder_palette((byte *)Principal_Palette,buffercomp+2); + // Codage de l'image + ptr=bufferdecomp; + for (Pos_Y=0;Pos_Y<200;Pos_Y++) + { + // Codage de la ligne + memset(pixels,0,320); + if (Pos_Y +#include + +#include +#include +#include +#include +#include +#include "linux.h" //Fichier avec diverses fonctions qui existaient sous dos mais pas sous linux... +#include "pages.h" +#include "files.h" +#include "loadsave.h" +#include "sdlscreen.h" + +byte Ancien_nb_lignes; // Ancien nombre de lignes de l'cran + + +//--- Affichage de la syntaxe, et de la liste des modes vidos disponibles --- +void Afficher_syntaxe(void) +{ + printf("Syntax: GFX2 [] [