Changeset 1087 for toilet/trunk


Ignore:
Timestamp:
Sep 23, 2006, 1:36:35 AM (13 years ago)
Author:
Sam Hocevar
Message:
  • Import toilet source code from libcaca's repository.
Location:
toilet/trunk
Files:
4 edited

Legend:

Unmodified
Added
Removed
  • toilet/trunk

    • Property svn:ignore
      •  

        old new  
        22Makefile.in
        33aclocal.m4
         4autom4te.cache
        45autotools
        56config.h
  • toilet/trunk/configure.ac

    r1084 r1087  
    2626fi
    2727
     28AC_CHECK_HEADERS(getopt.h)
     29AC_CHECK_FUNCS(getopt_long,
     30 [AC_DEFINE(HAVE_GETOPT_LONG, 1, Define to 1 if you have the `getopt_long' function.)],
     31 [AC_CHECK_LIB(gnugetopt, getopt_long,
     32   [AC_DEFINE(HAVE_GETOPT_LONG, 1, Define to 1 if you have the `getopt_long' function.)
     33    GETOPT_LIBS="${GETOPT_LIBS} -lgnugetopt"])])
     34AC_SUBST(GETOPT_LIBS)
     35
    2836CUCUL="no"
    29 PKG_CHECK_MODULES(cucul, cucul,
     37PKG_CHECK_MODULES(cucul, cucul >= 0.99.beta5,
    3038 [CUCUL="yes"],
    3139 [AC_MSG_RESULT(no)
    32   AC_MSG_ERROR([you need libcucul version 0.99 or later])])
     40  AC_MSG_ERROR([you need libcucul version 0.99.beta5 or later])])
    3341
    3442# Optimizations
  • toilet/trunk/src/Makefile.am

    r1084 r1087  
    44toilet_SOURCES = main.c
    55toilet_CFLAGS = `pkg-config --cflags cucul`
    6 toilet_LDFLAGS = `pkg-config --libs cucul`
     6toilet_LDFLAGS = `pkg-config --libs cucul` @GETOPT_LIBS@
    77
  • toilet/trunk/src/main.c

    r1084 r1087  
    11/*
    2  *   $Id$
     2 *  TOIlet        The Other Implementation’s letters
     3 *  Copyright (c) 2006 Sam Hocevar <sam@zoy.org>
     4 *                All Rights Reserved
    35 *
    4  *   This program is free software; you can redistribute it and/or modify
    5  *   it under the terms of the GNU General Public License as published by
    6  *   the Free Software Foundation; either version 2 of the License, or
    7  *   (at your option) any later version.
     6 *  $Id$
    87 *
    9  *   This program is distributed in the hope that it will be useful,
    10  *   but WITHOUT ANY WARRANTY; without even the implied warranty of
    11  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    12  *   GNU General Public License for more details.
    13  *
    14  *   You should have received a copy of the GNU General Public License
    15  *   along with this program; if not, write to the Free Software
    16  *   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
     8 *  This program is free software; you can redistribute it and/or
     9 *  modify it under the terms of the Do What The Fuck You Want To
     10 *  Public License, Version 2, as published by Sam Hocevar. See
     11 *  http://sam.zoy.org/wtfpl/COPYING for more details.
    1712 */
    1813
    1914#include "config.h"
    2015
    21 #include <caca.h>
    22 
    23 int main (int argc, char **argv)
    24 {
     16#if defined(HAVE_INTTYPES_H)
     17#   include <inttypes.h>
     18#endif
     19#if defined(HAVE_GETOPT_H)
     20#   include <getopt.h>
     21#endif
     22#include <stdio.h>
     23#include <string.h>
     24#include <stdlib.h>
     25
     26#include "cucul.h"
     27#include "caca.h"
     28
     29/* String to canvas transformations */
     30static cucul_canvas_t *cuculize_big(uint32_t const *, unsigned int);
     31static cucul_canvas_t *cuculize_tiny(uint32_t const *, unsigned int);
     32
     33/* Canvas special effects */
     34static void filter_autocrop(cucul_canvas_t *);
     35static void filter_gay(cucul_canvas_t *);
     36
     37int main(int argc, char *argv[])
     38{
     39    cucul_canvas_t *cv;
     40    cucul_buffer_t *buffer;
     41
     42    uint32_t *string = NULL;
     43    unsigned int length;
     44
     45    int i;
     46
     47    char const *export = "utf8";
     48    unsigned flag_gay = 0;
     49
     50#if defined(HAVE_GETOPT_H)
     51    for(;;)
     52    {
     53#   ifdef HAVE_GETOPT_LONG
     54#       define MOREINFO "Try `%s --help' for more information.\n"
     55        int option_index = 0;
     56        static struct option long_options[] =
     57        {
     58            /* Long option, needs arg, flag, short option */
     59            { "gay", 0, NULL, 'g' },
     60            { "irc", 0, NULL, 'i' },
     61            { "help", 0, NULL, 'h' },
     62            { "version", 0, NULL, 'v' },
     63            { NULL, 0, NULL, 0 }
     64        };
     65
     66        int c = getopt_long(argc, argv, "gihv", long_options, &option_index);
     67#   else
     68#       define MOREINFO "Try `%s -h' for more information.\n"
     69        int c = getopt(argc, argv, "gihv");
     70#   endif
     71        if(c == -1)
     72            break;
     73
     74        switch(c)
     75        {
     76        case 'h': /* --help */
     77            printf("Usage: %s [ -gihv ] [ message ]\n", argv[0]);
     78#   ifdef HAVE_GETOPT_LONG
     79            printf("  -g, --gay        add a rainbow effect to the text\n");
     80            printf("  -i, --irc        output IRC colour codes\n");
     81            printf("  -h, --help       display this help and exit\n");
     82            printf("  -v, --version    output version information and exit\n");
     83#   else
     84            printf("  -g    add a rainbow effect to the text\n");
     85            printf("  -i    output IRC colour codes\n");
     86            printf("  -h    display this help and exit\n");
     87            printf("  -v    output version information and exit\n");
     88#   endif
     89            return 0;
     90        case 'g': /* --gay */
     91            flag_gay = 1;
     92            break;
     93        case 'i': /* --irc */
     94            export = "irc";
     95            break;
     96        case 'v': /* --version */
     97            printf("TOIlet Copyright 2006 Sam Hocevar %s\n", VERSION);
     98            printf("Internet: <sam@zoy.org> Version: 0, date: 21 Sep 2006\n");
     99            printf("\n");
     100            return 0;
     101        case '?':
     102            printf(MOREINFO, argv[0]);
     103            return 1;
     104        default:
     105            printf("%s: invalid option -- %i\n", argv[0], c);
     106            printf(MOREINFO, argv[0]);
     107            return 1;
     108        }
     109    }
     110#else
     111#   define MOREINFO "Usage: %s message...\n"
     112    int optind = 1;
     113#endif
     114
     115    if(optind >= argc)
     116    {
     117        printf("%s: too few arguments\n", argv[0]);
     118        printf(MOREINFO, argv[0]);
     119        return 1;
     120    }
     121
     122    /* Load rest of commandline into a UTF-32 string */
     123    for(i = optind, length = 0; i < argc; i++)
     124    {
     125        unsigned int k, guessed_len, real_len;
     126
     127        guessed_len = strlen(argv[i]);
     128
     129        if(i > optind)
     130            string[length++] = (uint32_t)' ';
     131
     132        string = realloc(string, (length + guessed_len + 1) * 4);
     133
     134        for(k = 0, real_len = 0; k < guessed_len; real_len++)
     135        {
     136            unsigned int char_len;
     137
     138            string[length + real_len] =
     139                cucul_utf8_to_utf32(argv[i] + k, &char_len);
     140
     141            k += char_len;
     142        }
     143
     144        length += real_len;
     145    }
     146
     147    /* Do gay stuff with our string (léopard) */
     148    cv = cuculize_big(string, length);
     149    filter_autocrop(cv);
     150    if(flag_gay)
     151        filter_gay(cv);
     152
     153    /* Output char */
     154    buffer = cucul_export_canvas(cv, export);
     155    fwrite(cucul_get_buffer_data(buffer),
     156           cucul_get_buffer_size(buffer), 1, stdout);
     157    cucul_free_buffer(buffer);
     158
     159    cucul_free_canvas(cv);
     160
    25161    return 0;
    26162}
    27163
     164static cucul_canvas_t *cuculize_big(uint32_t const *string,
     165                                    unsigned int length)
     166{
     167    cucul_canvas_t *cv;
     168    cucul_font_t *f;
     169    char const * const * fonts;
     170    unsigned char *buf;
     171    unsigned int w, h, x, y, miny, maxy;
     172
     173    cv = cucul_create_canvas(length, 1);
     174    for(x = 0; x < length; x++)
     175        cucul_putchar(cv, x, 0, string[x]);
     176
     177    fonts = cucul_get_font_list();
     178    f = cucul_load_font(fonts[0], 0);
     179
     180    /* Create our bitmap buffer (32-bit ARGB) */
     181    w = cucul_get_canvas_width(cv) * cucul_get_font_width(f);
     182    h = cucul_get_canvas_height(cv) * cucul_get_font_height(f);
     183    buf = malloc(4 * w * h);
     184
     185    /* Render the canvas onto our image buffer */
     186    cucul_render_canvas(cv, f, buf, w, h, 4 * w);
     187
     188    /* Free our canvas, and allocate a bigger one */
     189    cucul_free_font(f);
     190    cucul_free_canvas(cv);
     191    cv = cucul_create_canvas(w, h);
     192
     193    /* Render the image buffer on the canvas */
     194    cucul_set_color(cv, CUCUL_COLOR_WHITE, CUCUL_COLOR_TRANSPARENT);
     195    cucul_clear_canvas(cv);
     196
     197    miny = h; maxy = 0;
     198
     199    for(y = 0; y < h; y++)
     200       for(x = 0; x < w; x++)
     201    {
     202        unsigned char c = buf[4 * (x + y * w) + 2];
     203
     204        if(c >= 0xa0)
     205            cucul_putstr(cv, x, y, "█");
     206        else if(c >= 0x80)
     207            cucul_putstr(cv, x, y, "▓");
     208        else if(c >= 0x40)
     209            cucul_putstr(cv, x, y, "▒");
     210        else if(c >= 0x20)
     211            cucul_putstr(cv, x, y, "░");
     212    }
     213
     214    free(buf);
     215
     216    return cv;
     217}
     218
     219static cucul_canvas_t *cuculize_tiny(uint32_t const *string,
     220                                     unsigned int length)
     221{
     222    unsigned int x;
     223    cucul_canvas_t *cv = cucul_create_canvas(length, 1);
     224
     225    for(x = 0; x < length; x++)
     226        cucul_putchar(cv, x, 0, string[x]);
     227
     228    return cv;
     229}
     230
     231static void filter_autocrop(cucul_canvas_t *cv)
     232{
     233    unsigned int x, y, w, h;
     234    unsigned int xmin, xmax, ymin, ymax;
     235
     236    xmin = w = cucul_get_canvas_width(cv);
     237    xmax = 0;
     238    ymin = h = cucul_get_canvas_height(cv);
     239    ymax = 0;
     240
     241    for(y = 0; y < h; y++)
     242        for(x = 0; x < w; x++)
     243    {
     244        unsigned long int ch = cucul_getchar(cv, x, y);
     245        if(ch != (unsigned char)' ')
     246        {
     247            if(x < xmin)
     248                xmin = x;
     249            if(x > xmax)
     250                xmax = x;
     251            if(y < ymin)
     252                ymin = y;
     253            if(y > ymax)
     254                ymax = y;
     255        }
     256    }
     257
     258    cucul_set_canvas_boundaries(cv, xmin, ymin,
     259                                xmax - xmin + 1, ymax - ymin + 1);
     260}
     261
     262static void filter_gay(cucul_canvas_t *cv)
     263{
     264    static unsigned char const rainbow[] =
     265    {
     266        CUCUL_COLOR_LIGHTMAGENTA,
     267        CUCUL_COLOR_LIGHTRED,
     268        CUCUL_COLOR_YELLOW,
     269        CUCUL_COLOR_LIGHTGREEN,
     270        CUCUL_COLOR_LIGHTCYAN,
     271        CUCUL_COLOR_LIGHTBLUE,
     272    };
     273    unsigned int x, y, w, h;
     274
     275    w = cucul_get_canvas_width(cv);
     276    h = cucul_get_canvas_height(cv);
     277
     278    for(y = 0; y < h; y++)
     279        for(x = 0; x < w; x++)
     280    {
     281        unsigned long int ch = cucul_getchar(cv, x, y);
     282        if(ch != (unsigned char)' ')
     283        {
     284            cucul_set_color(cv, rainbow[(x / 2 + y) % 6],
     285                                CUCUL_COLOR_TRANSPARENT);
     286            cucul_putchar(cv, x, y, ch);
     287        }
     288    }
     289}
     290
Note: See TracChangeset for help on using the changeset viewer.