Texte Dans Image

Vous avez développé un logiciel en PureBasic et vous souhaitez le faire connaitre ?
Avatar de l’utilisateur
venom
Messages : 3071
Inscription : jeu. 29/juil./2004 16:33
Localisation : Klyntar
Contact :

Texte Dans Image

Message par venom »

Bonjour a tous,

Suite aux différents post sur la stéganographie, je me suis amusé a faire une petite interface qui permet de mettre / lire du texte contenu dans une image.

J'ai ajouté une option de cryptage XOR via un mot de passe, avant d'envoyé le texte dans l'image. (histoire de corsé la chose)

les procédures qui envoient / récupères / cryptes le texte, sont tous de Dobro :lol:

L'interface est en 2 onglets. 1 pour le cryptage et l'autre pour le décryptage.
Voici le code:

Code : Tout sélectionner

; ///////////////////////////////////////////////
; //      Autor :         Venom                //
; //      Project name :  Texte In Image       //
; //      Version :       V 1.0                //
; //      Compilator :    PureBasic V5.71      //
; //      Date :          03/07/2019           //
; //      OS :            Windows 10           //
; ///////////////////////////////////////////////


;- Window Constants
Enumeration
  #Window_0
EndEnumeration

;- gadgets Constants
Enumeration
  #Panel_0
  ; onglet 1
  #Frame_Load_image_Cryptage
  #Button_Load_image_Cryptage
  #String_Load_image_Cryptage
      
  #Frame_Load_Texte_Cryptage
  #String_Load_Texte_Cryptage
      
  #Frame_Mots_De_Passe_Cryptage
  #String_Mots_De_Passe_Cryptage
  #String_Verf_Mots_De_Passe_Cryptage
      
  #Frame_Lancer_Cryptage
  #Button_Lancer_Cryptage
      
  #Image_Cryptage
  ; onglet 2
  #Frame_Load_image_Decodage
  #Button_Load_image_Decodage
  #String_Load_image_Decodage
  
  #Frame_Load_Texte_Decodage
  #String_Load_Texte_Decodage
  
  #Frame_Mots_De_Passe_Decodage
  #String_Mots_De_Passe_Decodage
  #String_Verf_Mots_De_Passe_Decodage
      
  #Frame_Lancer_Decodage
  #Button_Lancer_Decodage
  
  #Image_Decodage
EndEnumeration

UsePNGImageEncoder()
UsePNGImageDecoder()
Declare encode_steganosorus2(ID,name_image$,message$)
Declare.s decode_steganosorus2(ID, name_image$)
Declare.s Encodage_Decodage_XOR(chaine$,Pass$,Mode)


Global Chemin_De_Image$
Global Texte_A_Encoder$
Global Mots_De_Passe_Final$


If OpenWindow(#Window_0, 0, 0, 400, 405, "Stega Texte In Image", #PB_Window_SystemMenu | #PB_Window_MinimizeGadget | #PB_Window_TitleBar | #PB_Window_ScreenCentered)
  PanelGadget(#Panel_0, 0, 0, 400, 405)
   ;{ onglet 1
   AddGadgetItem (#Panel_0, 1, "Inseret un texte dans une image           ")

    FrameGadget(#Frame_Load_image_Cryptage, 10, 10, 380, 50, "Image qui dissimulera le texte", 0)
    ButtonGadget(#Button_Load_image_Cryptage, 20, 30, 100, 20, "Choisir une image", 0)
    StringGadget(#String_Load_image_Cryptage, 130, 30, 250, 20, "", #PB_String_ReadOnly)
      
    FrameGadget(#Frame_Load_Texte_Cryptage, 10, 70, 380, 150, "Texte qui sera dissimuler dans l'image", 0)
    EditorGadget(#String_Load_Texte_Cryptage, 20, 90, 360, 120, #PB_Editor_WordWrap)
      
    FrameGadget(#Frame_Mots_De_Passe_Cryptage, 10, 230, 380, 80, "Mots de passe pour crypter le texte", 0)
    StringGadget(#String_Mots_De_Passe_Cryptage, 20, 250, 360, 20, "", #PB_String_Password)
    StringGadget(#String_Verf_Mots_De_Passe_Cryptage, 20, 280, 360, 20, "", #PB_String_Password)
      
    FrameGadget(#Frame_Lancer_Cryptage, 10, 320, 380, 50, "Lancer le cryptage", 0)
    ButtonGadget(#Button_Lancer_Cryptage, 20, 340, 360, 20, "Lancer le cryptage", 0)
   ;}
    
   ;{ onglet 2
   AddGadgetItem (#Panel_0, 2, "Récuperer le texte d'une image            ")
    FrameGadget(#Frame_Load_image_Decodage, 10, 10, 380, 50, "Image qui contient le texte", 0)
    ButtonGadget(#Button_Load_image_Decodage, 20, 30, 100, 20, "Choisir une image", 0)
    StringGadget(#String_Load_image_Decodage, 130, 30, 250, 20, "", #PB_String_ReadOnly)
    
    FrameGadget(#Frame_Mots_De_Passe_Decodage, 10, 70, 380, 80, "Mots de passe pour décrypter le texte", 0)
    StringGadget(#String_Mots_De_Passe_Decodage, 20, 90, 360, 20, "", #PB_String_Password)
    StringGadget(#String_Verf_Mots_De_Passe_Decodage, 20, 120, 360, 20, "", #PB_String_Password)
      
    FrameGadget(#Frame_Lancer_Decodage, 10, 160, 380, 50, "Lancer le décryptage", 0)
    ButtonGadget(#Button_Lancer_Decodage, 20, 180, 360, 20, "Lancer le décryptage", 0)
    
    FrameGadget(#Frame_Load_Texte_Decodage, 10, 220, 380, 150, "Texte qui est dans l'image", 0)
    EditorGadget(#String_Load_Texte_Decodage, 20, 240, 360, 120, #PB_String_ReadOnly | #PB_Editor_WordWrap)
    
    
   ;}
EndIf



Repeat
  EventID = WaitWindowEvent()
   If EventID = #PB_Event_Gadget
    Select EventGadget()
    ;{ onglet 1              
     Case #Button_Load_image_Cryptage
      name_image$ = OpenFileRequester("Choisir une image", "", "Image Compatible|*.png;*.bmp", 0)

       If name_image$   <>""                  
        SetGadgetText(#String_Load_image_Cryptage,name_image$)         
         LoadImage(#image_Cryptage,name_image$)
       EndIf
                  
                  
     Case #Button_Lancer_Cryptage
      ; vérification qu'il y a bien une image de séléctionner
      Resultat_Image = Len(GetGadgetText(#String_Load_image_Cryptage))
       If Resultat_Image = 0
        MessageRequester("Information", "Une image doit être choisi pour lancer le cryptage.", #PB_MessageRequester_Error)
         Resultat_Image = 0
       Else
        Resultat_Image = 1
       EndIf
                  
       ; vérification qu'il y a bien un texte a crypter
       Resultat_Load_Texte.s = GetGadgetText(#String_Load_Texte_Cryptage)
        If Resultat_Load_Texte.s = ""
         MessageRequester("Information", "Un texte doit être entrée pour le dissimuler dans l'image.", #PB_MessageRequester_Error)
          Resultat_Load_T = 0
        Else
         Texte_A_Encoder$ = GetGadgetText(#String_Load_Texte_Cryptage)
          Resultat_Load_T = 1
        EndIf
                  
       ; verification qu'un mot de passe est entrée et que les 2 mots de passes sont identiques
       Resultat_Mots_De_Passe = Len(GetGadgetText(#String_Mots_De_Passe_Cryptage))
       Resultat_Verif_Mots_De_Passe = Len(GetGadgetText(#String_Verf_Mots_De_Passe_Cryptage))
        If Resultat_Mots_De_Passe = 0 Or Resultat_Verif_Mots_De_Passe = 0
         MessageRequester("Information", "Le mots de passe doit être entrée dans les 2 chants.", #PB_MessageRequester_Error)
          Resultat_Mots_De_Passe = 0
        ElseIf GetGadgetText(#String_Mots_De_Passe_Cryptage) = GetGadgetText(#String_Verf_Mots_De_Passe_Cryptage)
         Mots_De_Passe_Final$ = GetGadgetText(#String_Mots_De_Passe_Cryptage)
         Resultat_Mots_De_Passe = 1
        Else
         MessageRequester("Information", "Les mots de passes ne sont pas identiques.", #PB_MessageRequester_Error)
          Resultat_Mots_De_Passe = 0
        EndIf
                  
       ; lancement du cryptage
       If Resultat_Image And Resultat_Load_T And Resultat_Mots_De_Passe = 1
        Texte_Crypter$ = Encodage_Decodage_XOR(Texte_A_Encoder$, Mots_De_Passe_Final$, #True)
        encode_steganosorus2(#image_Cryptage, name_image$, Texte_Crypter$)
       EndIf
     ;}
       
       
     ;{ onglet 2
      Case #Button_Load_image_Decodage
      name_image$ = OpenFileRequester("Choisir une image", "", "Image Compatible|*.png;*.bmp", 0)

       If name_image$   <>""                  
        SetGadgetText(#String_Load_image_Decodage,name_image$)         
         LoadImage(#Image_Decodage,name_image$)
       EndIf
                  
                  
     Case #Button_Lancer_Decodage
      ; vérification qu'il y a bien une image de séléctionner
      Resultat_Image = Len(GetGadgetText(#String_Load_image_Decodage))
       If Resultat_Image = 0
        MessageRequester("Information", "Une image doit être choisi pour lancer le décryptage.", #PB_MessageRequester_Error)
         Resultat_Image = 0
       Else
        Resultat_Image = 1
       EndIf
       
       
       ; verification qu'un mot de passe est entrée et que les 2 mots de passes sont identiques
       Resultat_Mots_De_Passe = Len(GetGadgetText(#String_Mots_De_Passe_Decodage))
       Resultat_Verif_Mots_De_Passe = Len(GetGadgetText(#String_Verf_Mots_De_Passe_Decodage))
        If Resultat_Mots_De_Passe = 0 Or Resultat_Verif_Mots_De_Passe = 0
         MessageRequester("Information", "Le mots de passe doit être entrée dans les 2 chants.", #PB_MessageRequester_Error)
          Resultat_Mots_De_Passe = 0
        ElseIf GetGadgetText(#String_Mots_De_Passe_Decodage) = GetGadgetText(#String_Verf_Mots_De_Passe_Decodage)
         Mots_De_Passe_Final$ = GetGadgetText(#String_Mots_De_Passe_Decodage)
         Resultat_Mots_De_Passe = 1
        Else
         MessageRequester("Information", "Les mots de passes ne sont pas identiques.", #PB_MessageRequester_Error)
          Resultat_Mots_De_Passe = 0
        EndIf
                  
       ; lancement du décryptage
       If Resultat_Image And Resultat_Mots_De_Passe = 1
        decode_steganosorus2(ID, name_image$)
         MessageRequester("Information","le texte a bien était décrypter.", #PB_MessageRequester_Info)
       EndIf 
     ;}
    EndSelect
   EndIf
Until EventID = #PB_Event_CloseWindow





Procedure encode_steganosorus2(ID,name_image$, message$)
; By Dobro
; encodeur

largeur=ImageWidth(ID)
hauteur=ImageHeight(ID)
StartDrawing(ImageOutput(ID))
 compteur_pos=1
 ; on encodera la longueur du text dans le dernier point de l'image
 longueur=Len(message$)+1   
  For y=0 To hauteur-1
   For x=0 To largeur-9 Step 8
    octet_rouge$="":octet_vert$="":octet_bleu$=""
    lettre.s=Mid(message$,compteur_pos,1)
    lettre2.s=Mid(message$,compteur_pos+1,1)
    lettre3.s=Mid(message$,compteur_pos+2,1)
    Letter_rouge=Asc(lettre.s)   :Letter_vert=Asc(lettre2.s):Letter_bleu=Asc(lettre3.s)      
    octet_lettre.s=Bin(letter_rouge,#PB_Ascii)
    octet_lettre.s=RSet(octet_lettre.s,8,"0")
    octet_lettre2.s=Bin(letter_vert,#PB_Ascii)
    octet_lettre2.s=RSet(octet_lettre2.s,8,"0")
    octet_lettre3.s=Bin(letter_bleu,#PB_Ascii)
    octet_lettre3.s=RSet(octet_lettre3.s,8,"0")
     If compteur_pos<longueur
      For i=0 To 7 ; paquet de 8 bits pour encoder 1 lettre
       coul=Point(x+i,y)
       rouge=Red(coul)   
       vert=Green(coul)
       bleu=Blue(coul)
       octet_rouge$=Bin(rouge,#PB_Ascii  )
       octet_rouge$=RSet(octet_rouge$,8,"0")
       ;
       octet_vert$=Bin(vert,#PB_Ascii  )
       octet_vert$=RSet(octet_vert$,8,"0")
       ;
       octet_bleu$=Bin(bleu,#PB_Ascii  )
       octet_bleu$=RSet(octet_bleu$,8,"0")
       ;
       bit$=Mid(octet_lettre.s,i+1,1); prend l'extrait du bit de la lettre
       bit2$=Mid(octet_lettre2.s,i+1,1); prend l'extrait du bit de la lettre
       bit3$=Mid(octet_lettre3.s,i+1,1); prend l'extrait du bit de la lettre
       ;                                    
       If bit$<>""
        octet_rouge_ap$=Left(octet_rouge$,Len(octet_rouge$)-1)+bit$ ; le colle a la fin de l'octet rouge en cours
       EndIf
       If bit2$<>""
        octet_vert_ap$=Left(octet_vert$,Len(octet_vert$)-1)+bit2$ ; le colle a la fin de l'octet rouge en cours
       EndIf
       If bit3$<>""
        octet_bleu_ap$=Left(octet_bleu$,Len(octet_bleu$)-1)+bit3$ ; le colle a la fin de l'octet rouge en cours
       EndIf
        Plot(x+i,y,RGB(Val("%"+octet_rouge_ap$),Val("%"+octet_vert_ap$),Val("%"+octet_bleu_ap$)))
      Next i
       compteur_pos=compteur_pos+3
     Else ; si on est la, c'est que le message est fini et qu'il reste des pixel a dessiner
      coul=Point(x,y)
      rouge=Red(coul)
      vert=Green(coul)
      bleu=Blue(coul)
      Plot(x,y,RGB(rouge,vert,bleu))
     EndIf
   Next x
  Next y
  Plot(largeur-1,hauteur-1,longueur) ; on pose la longueur du message dans le dernier point de l'image
MessageRequester("Information","le texte a bien était caché dans l'image.", #PB_MessageRequester_Info )
StopDrawing()
      
Extention$ = GetExtensionPart(name_image$)
 Chemin_De_Image_Sans_Extention$ = Left(name_image$, Len(name_image$)-4)       
  SaveImage(ID, Chemin_De_Image_Sans_Extention$+" MOD."+Extention$)
EndProcedure


Procedure.s decode_steganosorus2(ID, name_image$)
LoadImage(ID,name_image$)
largeur=ImageWidth(ID)
hauteur=ImageHeight(ID)
StartDrawing(ImageOutput(ID))
; By Dobro
;decodeur
longueur= Point(largeur-1,hauteur-1)-1 ; la longueur du message se trouve dans le dernier point de l'image

For y=0 To hauteur-1
 For x=0 To largeur-9 Step 8
  octetrouge$="" :octetvert$="":octetbleu$=""
   For i=0 To 7
    coul=Point(x+i,y)
    rouge=Red(coul)                              
    vert=Green(coul)
    bleu=Blue(coul)
    ;premiere lettre
    bit$=Bin(rouge,#PB_Ascii  )
    bit$=RSet(bit$,8,"0") ; alignement
    octetrouge$=octetrouge$+Right(bit$,1)
    ;deuxieme lettre
    bit2$=Bin(vert,#PB_Ascii  )
    bit2$=RSet(bit2$,8,"0") ; alignement
    octetvert$=octetvert$+Right(bit2$,1)
    ;troisieme lettre
    bit3$=Bin(bleu,#PB_Ascii  )
    bit3$=RSet(bit3$,8,"0") ; alignement
    octetbleu$=octetbleu$+Right(bit3$,1)                              
   Next i
    car=Val("%"+octetrouge$)
    car2=Val("%"+octetvert$)
    car3=Val("%"+octetbleu$)                     
    l$=l$+Chr(car)+Chr(car2)+Chr(car3)   ; pose 3 lettres d'un coup
 Next x         
Next y

;- on recupere le texte crypter et on le decrypte
Texte_Decrypter$ = Encodage_Decodage_XOR(Left(L$,longueur), Mots_De_Passe_Final$, #False)
SetGadgetText(#String_Load_Texte_Decodage, Texte_Decrypter$)

StopDrawing()
EndProcedure


Procedure.s Encodage_Decodage_XOR(chaine$,Pass$,Mode)
; By Zorro
; ENCODAGE XOR 
For i=1 To Len(chaine$)
 pos=pos+1
  If pos>Len(pass$):Pos=1:EndIf
            
   cclair=Asc(Mid(chaine$,i,1))
   cpass=Asc(Mid(pass$,pos,1))
    Select Mode                  
     Case #True ; encodage XOR                  
      cencode=cclair!(cpass)
       If cencode=0 ; Cas ou le pass et le clair soit pareil , ou le le code soit plus petit que "l'espace"
        cencode=255   ; recodage si pareil en fait on creer un Flag "255" signifiera qu'on utilisera le meme caractere que le pass donc on encode pas vraiment
       EndIf                  
        encode$=encode$+Chr(cencode)
     Case #False ; decodage XOR
      If cclair=255 ; si le code analysé et encodé est 255 alors cela signifie que
       cdecod= cpass ;le caractere est le meme que le pass ....
      Else
       cdecod=cclair!(cpass)
      EndIf
       decode$=decode$+Chr(cdecod)
    EndSelect
Next i

If Mode=#True
 ProcedureReturn encode$
Else
 ProcedureReturn decode$
EndIf
      
EndProcedure
Ps: Le code creer une nouvelle image il ne deteriore pas l'image d'origine. :wink:






@++
Windows 10 x64, PureBasic 5.73 x86 & x64
GPU : radeon HD6370M, CPU : p6200 2.13Ghz