#include <stdio.h>
#include <sp/spBaseLib.h>
#include <sp/spComponentLib.h>
#include <sp/spComponentMain.h>


#define CANVAS_WIDTH 300
#define CANVAS_HEIGHT 300

#define IMAGE_WIDTH 150
#define IMAGE_HEIGHT 150

static spGraphics graphics = NULL;
static spComponent image = NULL, file_image = NULL;

static int copy_count = 0;

static void imageDrawCB(spComponent component, void *data)
{
    int width = 0, height = 0;
    int file_width = 0, file_height = 0;
    
    if (graphics == NULL || spGetClientSize(component, &width, &height) == SP_FALSE) return;
    
    spDebug(10, "imageDrawCB", "width = %d, height = %d\n", width, height);

    spSetGraphicsParams(graphics, SppForeground, "white", NULL);
    spFillRectangle(component, graphics, 0, 0, width, height);
    
    spSetGraphicsParams(graphics, SppForeground, "red", NULL);

    spDrawLine(component, graphics, 0, 0, width, height);
    spDrawLine(component, graphics, width, 0, 0, height);
    
    spFillRectangle(component, graphics, 80, 80, 100, 50);

    spFillArc(component, graphics, width / 2 - 50, height / 2 - 50,
              100, 100, 0, 45);
    spDrawArc(component, graphics, width / 2 - 50, height / 2 - 50,
              100, 100, 90, 45);

    if (spGetClientSize(file_image, &file_width, &file_height) == SP_TRUE) {
        spDebug(10, "imageDrawCB", "file_width = %d, file_height = %d\n", file_width, file_height);
        spCopyImage(file_image, component, 0, 0, file_width, file_height,
                    width - file_width - 10, height - file_height - 10);
    }
    
    return;
}

static void canvasCB(spComponent component, void *data)
{
    int width, height;
    int iwidth, iheight;
    int fwidth, fheight;

    if (spGetClientSize(component, &width, &height) == SP_TRUE
        && spGetClientSize(image, &iwidth, &iheight) == SP_TRUE) {
        spDebug(50, "canvasCB", "width = %d, height = %d, iwidth = %d, iheight = %d\n",
                width, height, iwidth, iheight);

        spSetGraphicsParams(graphics, SppForeground, "white", NULL);
        spFillRectangle(component, graphics, 0, 0, width, height);

        if (spGetClientSize(file_image, &fwidth, &fheight) == SP_TRUE) {
            spCopyImage(file_image, component, 0, 0, fwidth, fheight, 10, 10);
        }
        spSetGraphicsParams(graphics, SppForeground, "black", NULL);
        spDrawLine(component, graphics, 0, 0, width, height);
        spDrawLine(component, graphics, width, 0, 0, height);
        
        spDebug(50, "canvasCB", "copy_count = %d\n", copy_count);
        if ((copy_count / /*10*/4) % 2 == 0) {
            spRedrawImage(image, iwidth, iheight);
            spDrawString(component, graphics, 20, 30, "Redraw image");
        } else {
            spCopyImage(component, image, 30, 10, iwidth / 2, iheight / 2, iwidth / 2, 0);
            spCopyImage(component, image, 0, height - iheight / 2, iwidth / 2, iheight / 2, 0, iheight / 2);
            spDrawString(component, graphics, 20, 30, "Copy component to image");
        }
        spCopyImage(image, component, 0, 0, iwidth, iheight, width - iwidth - 20, height - iheight - 20);
        spCopyImage(image, component, iwidth / 3, iheight / 3, 2 * iwidth / 3, 2 * iheight / 3, iwidth + 40, 40);
        
        ++copy_count;

        spRefreshCanvas(component);
    }
    
    return;
}

int spMain(int argc, char *argv[])
{
    spTopLevel toplevel;
    spComponent frame;
    spComponent menu, menu_bar;
    spComponent canvas;

    /* initialize toolkit */
    toplevel = spInitialize(&argc, &argv, NULL);
    
    /* create main window */
    frame = spCreateMainFrame("Image Test", NULL);

    /* create menu bar */
    menu_bar = spCreateMenuBar(frame, "menuBar", NULL);
    
    /* create menu */
    menu = spCreatePulldownMenu(menu_bar, "fileMenu",
                                SppTitle, "File",
                                NULL);
    
    /* add menu item */
    spAddMenuItem(menu, SP_QUIT_MENU_ITEM_NAME,
                  SppCallbackFunc, spQuitCB,
                  SppTitle, "Quit",
                  SppShortcut, "A-q",
                  NULL);

    /* create canvas */
    canvas = spCreateCanvas(frame, "canvas", CANVAS_WIDTH, CANVAS_HEIGHT,
                            SppBorderOn, SP_TRUE,
                            SppCallbackFunc, canvasCB,
                            SppDrawBackground, SP_TRUE,
                            NULL);

    /* create image */
    image = spCreateImage(canvas, "image", IMAGE_WIDTH, IMAGE_HEIGHT,
                          SppCallbackFunc, imageDrawCB,
                          NULL);
    file_image = spCreateImageFromFile(canvas, "tool_bar",
                                       NULL);
    spDebug(-10, "imageDrawCB", "file_image = %ld\n", (long)file_image);
    
    /* create graphics */
    graphics = spCreateGraphics("graphics1",
                                SppLineType, SP_LINE_DASH_DOT,
                                SppLineWidth, 1,
                                SppFontName, "-*-*-medium-*-normal--16-*-*-*-*-*-*-*",
                                NULL);
    
    /* popup window */
    spPopupWindow(frame);
    
    /* main loop */
    return spMainLoop(toplevel);
}
