image to Ascii-art

Partagez votre expérience de PureBasic avec les autres utilisateurs.
Avatar de l’utilisateur
djes
Messages : 4252
Inscription : ven. 11/févr./2005 17:34
Localisation : Arras, France

Re: image to Ascii-art

Message par djes »

J'ai fait un petit code pour montrer ce que je voulais dire. Je ne me suis pas embêté à faire une belle interface comme la tienne, ça convertit en se basant sur la fonte terminal (qui bizarrement ne s'affiche pas dans l'editorgadget...), et ça crée un fichier texte. L'image apparaît sur la gauche avec les caractères choisis. Le rouge correspond au seuil de tolérance (c'est la constante #Threshold au début du programme). Le fichier texte est à visualiser dans un éditeur qui accepte les polices "fixes" ou "OEM" comme ultraedit.

Code : Tout sélectionner

; (c)djes 2016
; Fast and ugly code to convert an image to ASCII based on character design
; http://www.purebasic.fr/french/viewtopic.php?f=6&t=16329

UseJPEGImageDecoder()
UsePNGImageDecoder()

#Threshold = 100 ;"seuil"

If LoadFont(0, "Terminal", 8) = 0
  MessageRequester("Error", "Can't load font", 0)
  End
EndIf

If CreateImage(0, 8 * 256, 8)
  
  If StartDrawing(ImageOutput(0))
    
    ;Creates pixel matrices for all the font characters
    Dim CharsPixels.b(256, 8, 8)
    
    Box(0, 0, 8*256, 8, RGB(255, 255, 255)) 
    DrawingMode(1)
    DrawingFont(FontID(0))
    
    For i = 32 To 255
      DrawText(8 * i, 0, Chr(i), 0)
      For y = 0 To 7
        For x = 0 To 7
          If Point(x + i * 8, y) = 0
            CharsPixels(i, x, y) = 1
          EndIf
        Next x
      Next y
    Next i
    
    StopDrawing()
    
  EndIf
  
  FileName.s = OpenFileRequester("Choose an image file to load", #PB_Compiler_FilePath, "Pictures|*.jpg;*.png", 0)
  SetGadgetFont(#PB_Default, FontID(0)) 
  
  If LoadImage(1, FileName) = 0
    MessageRequester("Error", "Can't load image", 0)
    End
  EndIf
  
  If ImageWidth(1) > 600
    ResizeImage(1, 600, #PB_Ignore)  
  EndIf
  If ImageHeight(1) > 600
    ResizeImage(1, #PB_Ignore, 600)  
  EndIf
  
  If OpenWindow(0, 0, 0, ImageWidth(1) * 2, ImageHeight(1), "GFX2ASCII", #PB_Window_SystemMenu | #PB_Window_ScreenCentered) = 0
    MessageRequester("Error", "Can't open window", 0)
    End
  EndIf
  
  CanvasGadget(0, 0, 0, ImageWidth(1) + 8, ImageHeight(1) + 8)
  EditorGadget(1, ImageWidth(1), 0, ImageWidth(1), ImageHeight(1))
  
  FileName.s = OpenFileRequester("Choose an ASCII file to save", #PB_Compiler_FilePath + "result.txt", "", 0)
  If CreateFile(0, FileName)
    
    StartDrawing(CanvasOutput(0))
    Box(0, 0, ImageWidth(1) + 8, ImageHeight(1) + 8, RGB(255, 255, 255)) ; White background
    DrawImage(ImageID(1), 0, 0) 
    
    For yc = 0 To ImageHeight(1) - 1 Step 8
      
      TextLine.s = ""
      
      For xc = 0 To ImageWidth(1) - 1 Step 8
        
        Dim ThisCharPixels.b(8, 8)
        
        ;Creates a char matrix for each 8x8 block
        For y = 0 To 7
          For x = 0 To 7
            Color = Point(xc + x, yc + y)
            Gray = 0.299 * Red(Color) + 0.587 * Green(Color) + 0.114 * Blue(Color)
            If Gray < #Threshold
              Plot(xc + x, yc + y, RGB($FF, 0, 0))
              ThisCharPixels(x, y) = 1  
            EndIf
          Next x
        Next y
        
        BestKnownScore = 0
        ChoosenChar = 0
        
        For i = 32 To 255
          
          ;Try to find the best char
          ThisCharScore = 0
          For y = 0 To 7
            For x = 0 To 7
              If CharsPixels(i, x, y) = ThisCharPixels(x, y) 
                ThisCharScore + 1
              EndIf
            Next x
          Next y
          
          ;Use the best corresponding char
          If ThisCharScore > BestKnownScore
            ChoosenChar = i
            BestKnownScore = ThisCharScore
            
            ;Draw the corresponding char on the image
            For y = 0 To 7
              For x = 0 To 7
                If CharsPixels(i, x, y) = 1 
                  Plot(xc + x, yc + y, RGB(0, 0, 0))
                EndIf
              Next x
            Next y  
            
          EndIf
          
        Next i
        
        TextLine + Chr(ChoosenChar)
        WriteAsciiCharacter(0, ChoosenChar)
        
      Next xc
      
      AddGadgetItem(1, -1, TextLine) 
      WriteStringN(0, "", #PB_Ascii)
      
    Next yc
    
    StopDrawing()  
    CloseFile(0)
    
    Repeat
      
      Event = WaitWindowEvent()
      
    Until Event = #PB_Event_CloseWindow    ; If the user has pressed on the close button
    
  EndIf
EndIf

End
Avatar de l’utilisateur
Zorro
Messages : 2185
Inscription : mar. 31/mai/2016 9:06

Re: image to Ascii-art

Message par Zorro »

oui, mais c'est pas vraiment comparable


voici une capture de ce que renvoi ton code a gauche, et a droite ce que j'obtiens
avec mon code

Image

tu peux constater que mon code renvoi un text qui tiens compte des niveaux de gris

si le but c'etait juste de faire ressortir un certains niveau de gris ,
il suffit de considérer que au dessus de tel niveau de gris (genre si sup a 200), on affiche un espace.
sinon on affiche un caractere ...

dans mon system on prend un certains nombre de caractere, qui vont etre choisi pour la luminosité
qu'ils dégagent

un "@" paraitra plus foncé qu'un ";"

on se constitue ainsi une palette, qui servira a reproduire l'image
si un pixel = rgb(0,0,0) on dessinera alors un "@"
si un pixel = rgb(200,200,200) on dessinera un ";"
si un pixel =rgb(255,255,255) on dessine un " " (espace)

c'est la seule solution a ma connaissance, pour arriver au meilleurs resultat .

ps: on peut aussi utiliser les caracteres Graphique
comme je l'avais fait avec mon prg Barbouille
voir demo ici :

https://youtu.be/LPKs-xOKsrk

:)

bien sur ton code genere de plus petit morceau de text
mais je ne pense pas qu'on puisse garder un bon rendu en degradé de gris, avec peut de caracteres
Image
Image
Site: http://michel.dobro.free.fr/
Devise :"dis moi ce dont tu as besoin, je t'expliquerai comment t'en passer"
Avatar de l’utilisateur
Zorro
Messages : 2185
Inscription : mar. 31/mai/2016 9:06

Re: image to Ascii-art

Message par Zorro »

Zorro a écrit : mais je ne pense pas qu'on puisse garder un bon rendu en degradé de gris, avec peut de caracteres
je me réponds a moi-même :)

en fait si ce serai possible, a la condition qu'on puisse reconstituer chaque caractère
que chaque caractère soit redessiné avec des points de couleurs différente

par exemple que le caractère utilisé a un moment T soit en fait composé de la couleur de l'image qu'il recouvre :)
si le caractère était a cheval sur une zone noire a gauche et blanche a droite
il faudrait recomposer le caractère ,de sorte que sa partie gauche soit dessiné avec des points noirs
et sa partie droite avec des points blancs :)

ça serai un gros boulot a faire (ou peut etre jouer sur la transparence d'un caractere, mais ça ne peut se faire qu'en mode graphique
on sort du mode Text :)

dans Barbouille , j'utilise une methode text graphique plus simple

je trouve un pixel blanc, je pose une lettre au hasard blanche
je trouve un pixel rouge, je pose une lettre au hasard rouge etc .... :)
Image
Image
Site: http://michel.dobro.free.fr/
Devise :"dis moi ce dont tu as besoin, je t'expliquerai comment t'en passer"
Avatar de l’utilisateur
djes
Messages : 4252
Inscription : ven. 11/févr./2005 17:34
Localisation : Arras, France

Re: image to Ascii-art

Message par djes »

Oui, ce n'est pas tout à fait le même objectif, et je pense aussi qu'il y a possibilité de mixer les deux...

Pour résumer :
  • ton code prend une image et convertit chaque pixel en une nuance de gris, et de là en un caractère qui renvoie une couleur proche calculée selon une formule moyenne de ses pixels.
  • mon code prend une image et convertit chaque matrice de pixels de 8x8 en un caractère dont le dessin (ici 8x8 également) est le plus proche possible.
Les deux mélangés donnerait :
  • On prend une image dont on convertit chaque pixel en une nuance de gris, et de là en un caractère dont le dessin (la répartition des points) renvoie une couleur proche de ce gris.
En tous cas, ça se résume à modifier un peu ton code pour la partie choix de la nuance renvoyée par le caractère. Avec la médiane, ou la détection des contours, ça pourrait le faire aussi ! Voir là : http://images.math.cnrs.fr/Le-traitemen ... mages.html

Je ne comprends pas bien ton idée suivante, sauf peut-être à utiliser les pixels "autour", mais là ça devient compliqué.
Avatar de l’utilisateur
JohnJohnsonSHERMAN
Messages : 648
Inscription : dim. 13/déc./2015 11:05
Localisation : Allez, cherche...
Contact :

Re: image to Ascii-art

Message par JohnJohnsonSHERMAN »

@Dobro : Ca n'a rien à voir, mais t'as pas un lien vers ton programme Barbouille? J'arrive pas à le télécharger sur ton site :(
"Le bug se situe entre la chaise et le clavier"
Votre expert national en bogage et segfaults.

CPU : AMD A8 Quad core - RAM 8Gb - HDD 2To
  • Windows 10 x64 - PB 5.61 x64
  • Linux Ubuntu 16.04 LTS x64 (dual boot) - PB pas encore réinstallé
Avatar de l’utilisateur
Zorro
Messages : 2185
Inscription : mar. 31/mai/2016 9:06

Re: image to Ascii-art

Message par Zorro »

excellent site, j'etais tombé dessus; il y a fort long-temp, pis perdu
merci pour le lien :)

par contre la version
de mon code ici : http://www.purebasic.fr/french/viewtopi ... =6&t=16334
n'utlise plus de formule pour esayer de trouver un caractere plus ou moins clair
elle utilise directement des caracteres bien précis, que j'ai selectionné apres tests sur differents
type de dégradé de gris , l'oeil humain, est quand meme nettement plus precis qu'un algo :)
ça permet d'utiliser moins de caracteres au final , j'aime bien le résultat :)





JohnJohnsonSHERMAN a écrit :@Dobro : Ca n'a rien à voir, mais t'as pas un lien vers ton programme Barbouille? J'arrive pas à le télécharger sur ton site :(
normal, il faut etre membre pour telecharger chez moi :)

extrait de ma page d'accueil
A cause d’écriture de commentaires par des robots
j'ai du modifier les droits de création de commentaires, et les réserver aux Membres

la création d'un compte "Membre" sera validé a la main par moi-même
donc cela peut prendre un peu de temps ..

les téléchargements sont dorénavant réservés aux membres
Image
Image
Site: http://michel.dobro.free.fr/
Devise :"dis moi ce dont tu as besoin, je t'expliquerai comment t'en passer"
Avatar de l’utilisateur
djes
Messages : 4252
Inscription : ven. 11/févr./2005 17:34
Localisation : Arras, France

Re: image to Ascii-art

Message par djes »

Oui, c'est une bonne idée.
Répondre