#include <stdio.h>
#include <gdk-pixbuf/gdk-pixbuf.h>

#define IMAGE_TYPE "gif"
#define IMAGE_FILENAME "aero.gif"
//#define IMAGE_TYPE "ico"
//#define IMAGE_FILENAME "squares32.ico"

/*
 * Reads count_bytes from the channel and write them to the loader.
 * Returns number of bytes written.
 * count_bytes = G_MAXSIZE means read as many bytes as possible.  
 */
gsize loader_write_from_channel(GdkPixbufLoader* loader, GIOChannel *channel, gsize count_bytes)
{
    guchar* buffer = NULL;
    gsize bytes_read = 0;
    GIOStatus read_status;
    GError* error = NULL;
    if(count_bytes < G_MAXSIZE)
    { 
        //read no more than 'count_bytes' bytes
        buffer = g_malloc(count_bytes);
        read_status = 
            g_io_channel_read_chars(channel, (gchar*)buffer, count_bytes, &bytes_read, NULL);
    }
    else
    {
        //read up to end
        read_status = 
            g_io_channel_read_to_end(channel, (gchar**)&buffer, &bytes_read, NULL);
    }
    if((read_status != G_IO_STATUS_NORMAL) && (read_status != G_IO_STATUS_EOF))
    {
        printf("Cannot read bytes from channel.\n");
        g_free(buffer);
        return 0;    
    }
    
    if(!gdk_pixbuf_loader_write(loader, buffer, bytes_read, &error))
    {
        printf("gdk_pixbuf_loader_write() returned FALSE.\n");
        printf("Error is '%s'.\n", error->message);
        g_free(buffer);
        return 0;
    }
    g_free(buffer);
    return bytes_read;
}


int main()
{
    g_type_init();
    //create channel from IMAGE_FILENAME
    GIOChannel* channel = g_io_channel_new_file(IMAGE_FILENAME, "r", NULL);
    if(channel == NULL)
    {
        printf("Cannot open file '%s' for read.\n", IMAGE_FILENAME);
        return 1;
    }
    g_io_channel_set_encoding(channel, NULL, NULL);
    //create loader
    //GdkPixbufLoader* loader = gdk_pixbuf_loader_new();    
    GdkPixbufLoader* loader = gdk_pixbuf_loader_new_with_type(IMAGE_TYPE, NULL);
    if(loader == NULL)
    {
        printf("Cannot create loader of type '%s'.\n", IMAGE_TYPE);
        g_io_channel_unref(channel);
        return 1;
    }

    loader_write_from_channel(loader, channel, 10);
    loader_write_from_channel(loader, channel, G_MAXSIZE);

    g_io_channel_unref(channel);

    gdk_pixbuf_loader_close(loader, NULL);
    g_object_unref(loader);

    return 0;
}
