/*
    wmimagedock

  Copyright (c) 2018 Michael Heras

  This program is free software; you can redistribute it and/or modify
  it under the terms of the GNU General Public License as published by
  the Free Software Foundation; either version 2 of the License, or
  (at your option) any later version.

  This program is distributed in the hope that it will be useful,
  but WITHOUT ANY WARRANTY; without even the implied warranty of
  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  GNU General Public License for more details.

  You should have received a copy of the GNU General Public License
  along with this program; if not, write to the Free Software
  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111-1307,
  USA.
*/


#include <cstdlib> // call external program
#include <unistd.h>
#include <sys/time.h>
#include <X11/Xlib.h>

#include "imagefiles.hpp"
#include "wmimagedock.hpp"
#include "setBG.hpp"
#include "selection.hpp"

using std::cout;
using std::endl;

void Selection_a(WMWindowDock doc)
{
    XEvent report ;
    int laptime = 0;
    struct timeval interval;
    struct timeval next_tick;
    Time lastTime = 0;
    laptime = doc.getStime();
    // if user forgets to add -t option
    //deaults to this time in set in seconds
    if (laptime == 0)
        laptime = 350;
    interval.tv_sec = laptime;
    interval.tv_usec = 0;
    next_tick = interval;

    if (doc.getRandom()) { randomizeFiles();  }

    doc.DisplayImage();

    while (1)
    {
        if (XNextEventTimed( doc.getDisplay(), &report, &next_tick ) )
        {
            switch (report.type)
            {
                case ButtonRelease:
                    if (report.xbutton.button == Button1)
                    {
                        if (report.xbutton.time - lastTime < 250 )
                        {
                            std::string cmd = doc.getCommandOne();
                            cmd += " &";
                            if (cmd.length() > 2 )
                            {
                                cout<<cmd<<" Requested"<<endl;
                                system( cmd.c_str() );
                            }
                        }
                        else
                        {
                            lastTime = report.xbutton.time;
                        }
                    }
                    else if ( report.xbutton.button == Button3)
                    {
                        if (report.xbutton.time - lastTime < 250 )
                        {
                            std::string cmd = doc.getCommandTwo();
                            cmd += " &";
                            if (cmd.length() > 2 )
                            {
                                cout<<cmd<<" Requested"<<endl;
                                system( cmd.c_str() );
                            }
                        }
                        else
                        {
                            lastTime = report.xbutton.time;
                        }
                    }
                    break;
                default:
                    break;
            }
        }
        else
        {
            doc.DisplayImage();
            next_tick = interval;
        }
    }
}
void Selection_b(WMWindowDock doc)
{
    // cout<<"B function"<<endl;
     XEvent report ;
    int laptime = 0;
    struct timeval interval;
    struct timeval next_tick;
    Time lastTime = 0;
    laptime = doc.getStime();
    // if user forgets to add -t option
    //deaults to this time in set in seconds
    if (laptime == 0)
        laptime = 350;
    interval.tv_sec = laptime;
    interval.tv_usec = 0;
    next_tick = interval;

    if (doc.getRandom()) { randomizeFiles();  }

    doc.DisplayImage();

    while (1)
    {   XNextEvent(doc.getDisplay(), &report);
        switch (report.type)
        {
            case ButtonRelease:
                if (report.xbutton.button == Button1)
                {
                    if (report.xbutton.time - lastTime < 250 )
                    {
                        setBG();
                    }
                    else
                    {
                        lastTime = report.xbutton.time;
                    }
                }
                else if ( report.xbutton.button == Button3)
                {
                    if (report.xbutton.time - lastTime < 250 )
                    {
                        setBGTile();
                    }
                    else
                    {
                        lastTime = report.xbutton.time;
                    }
                }
                else if (report.xbutton.button == Button4)
                {
                    doc.transverseImage();
                }
                else if (report.xbutton.button == Button5)
                {
                    doc.reverseImage();
                }
                break;
            default:
                break;
        }
    }
}
void Selection_c(WMWindowDock doc)
{

    XEvent report ;
    int laptime = 0;
    struct timeval interval;
    struct timeval next_tick;
    Time lastTime = 0;
    laptime = doc.getStime();
    // if user forgets to add -t option
    //deaults to this time in set in seconds
    if (laptime == 0)
        laptime = 350;
    interval.tv_sec = laptime;
    interval.tv_usec = 0;
    next_tick = interval;

    if (doc.getRandom()) { randomizeFiles();  }

    doc.DisplayImage();

    while (1)
    {
        if (XNextEventTimed( doc.getDisplay(), &report, &next_tick ) )
        {
            switch (report.type)
            {
                case ButtonRelease:
                    if (report.xbutton.button == Button1)
                    {
                        if (report.xbutton.time - lastTime < 250 )
                        {
                               setBG(doc.getLoadedFileName());
                        }
                        else
                        {
                            lastTime = report.xbutton.time;
                        }
                    }
                    else if ( report.xbutton.button == Button3)
                    {
                        if (report.xbutton.time - lastTime < 250 )
                        {
                            setBGTile(doc.getLoadedFileName());
                        }
                        else
                        {
                            lastTime = report.xbutton.time;
                        }
                    }
                    break;
                default:
                    break;
            }
        }
        else
        {
            doc.DisplayImage();
            next_tick = interval;
        }
    }
}


bool XNextEventTimed(Display *display, XEvent *event_return, struct timeval *timeout)
{
    /*
     *  Usage:
     *    struct timeval = { .tv_sec = 5, .tv_usec = 0 };
     *    if (XNextEventTimed(display, &event, &timeout) == True) {
     *        //.. do your event processing switch
     *    } else {
     *        //.. do your timeout thing
     *    }
     *
     *  Return:
     *    True if an event was selected, or False when no event
     *    was found prior to the timeout or when select returned
     *    an error (most likely EINTR).
    */

    if (timeout == NULL) {
        XNextEvent(display, event_return);
        return true;
    }

    if (XPending(display) == 0) {
        int fd = ConnectionNumber(display);
        fd_set readset;
        FD_ZERO(&readset);
        FD_SET(fd, &readset);
        if (select(fd + 1, &readset, NULL, NULL, timeout) > 0) {
            XNextEvent(display, event_return);
            return true;
        } else {
            return false;
        }
    } else {
        XNextEvent(display, event_return);
        return true;
    }
}
