/***************************************************************************
                          cintro.cpp  -  description
                             -------------------
    begin                : mar aoû 12 2003
    copyright            : (C) 2003 by Eric Coquelle
    email                : coquelle@caramail.com
 ***************************************************************************/

/***************************************************************************
 *                                                                         *
 *   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.                                   *
 *                                                                         *
 ***************************************************************************/

#include "cintro.h"
#include "score.h"

#include <qpainter.h>
#include <qfont.h>
#include <kapp.h>
#include <kconfig.h>
#include <kglobal.h>
#include <kstandarddirs.h>
#include <klocale.h>
#include <kdebug.h>
#include <qmessagebox.h>
#include <unistd.h>

CIntro::CIntro(){
  QString basename;
  bool imagesok;
  QString ressource_credits;
  dy=46;
  ballscale=1;
  shiftballscale=0.01;
  choice=0;
  ymin=128;
  choicemax=4;
  creditmax=4;
  yanimplayername=height();
  operation=MAIN_MENU;

  basename=KGlobal::dirs()->findResourceDir("data","kslide/kslideui.rc");
  basename+="kslide/pics/";
  setFixedSize(697,350);
  imagesok=background.load(basename+"kslide.jpg");
  imagesok=ball.load(basename+"ball.png");
  ball.setAlphaBuffer(true);
  imagesok=playernamebg.load(basename+"playername.jpg");

  int rx,ry,j;
  bool intersects;
  for(int i=0;i<creditmax;i++)
  {
    credits.append( QPixmap(basename+ressource_credits.sprintf("credits%i.png",i)));
    do
    {
      intersects=false;
      rx=rand()%535;
      ry=rand()%190;
      for(j=0;j<i;j++)
      {
        if((*creditpos.at(j)).r.intersects(QRect(rx,ry,159,160)))
          intersects=true;
      }
    }while(intersects);
    if(rand()%2>1)    
      creditpos.append(CCredits(rx,ry,0,rand()%10));
    else
      creditpos.append(CCredits(rx,ry,rand()%10,0));
  }
  if(!imagesok)
  {
    QMessageBox::critical(this, i18n("Missing some files !"),basename);
    operation=choicemax;
    reject();
  }
  playername=new QLineEdit(this);
  playername->setGeometry(230,200,200,25);
  playername->setBackgroundPixmap(QPixmap(basename+"texture.jpg"));
  playername->setFont(QFont("Helvetica", 14, QFont::Bold));
  playername->setAlignment(Qt::AlignHCenter);
  playername->hide();
  KConfig *config = kapp->config();
  config->setGroup("Player");
  playername->setText(config->readEntry("playername",QString(cuserid(NULL))));
  playername->selectAll();

  setMouseTracking(true);

  timer = new QTimer( this );
  connect( timer, SIGNAL(timeout()), this, SLOT(timerDone()) );
  timer->start( 25, false );
}

CIntro::~CIntro(){
}

void CIntro::paintEvent(QPaintEvent*)
{
  bitBlt(this, 0, 0, &background);
  if((operation==ANIM_PLAYERNAME)||(operation==WAITING_PLAYERNAME))
    bitBlt(this,175,yanimplayername,&playernamebg,0,0,-1,-1);
}

/** Updates the animation */
void CIntro::timerDone(){
  if(operation==MAIN_MENU)
  {
    int yposball=ymin+choice*dy;
    int ballx=(int)((1-ballscale)/2*ball.width());
    int bally=(int)((1-ballscale)/2*ball.height());
    QPixmap pbuff(ball.size());
    QPainter p;
    p.begin(&pbuff);
    p.drawPixmap(0,0,background,200,yposball,ball.width(),ball.height());

    ballscale+=shiftballscale;
    if(ballscale<.3)
      shiftballscale=-shiftballscale;
    else if(ballscale>1)
    {  shiftballscale=-shiftballscale; }
    p.drawImage(ballx,bally,ball.smoothScale((int)(ballscale*ball.width()),(int)(ballscale*ball.height())));
    p.end();

    bitBlt(this, 200, yposball, &pbuff,0,0,-1,-1);
  }
  else if(operation==ANIM_PLAYERNAME)
  {
    yanimplayername-=3;
    if(yanimplayername<115)
    {
      operation=WAITING_PLAYERNAME;
      timer->stop();
      playername->show();
      playername->setFocus();
    }
    bitBlt(this,175,yanimplayername,&playernamebg,0,0,-1,-1);
  }
  else if(operation==CREDITS)
  {
    QPainter p;
    int i;
    CCredits cred;
    QPixmap buff(background.size());
    p.begin(&buff);

    p.drawPixmap(0,0,background,0,0,-1,-1);
    for(i=0;i<creditmax;i++)
    {
      cred=*creditpos.at(i);

      cred.updatePosition();
      if(rand()%10>8)
        cred.swap();
      *creditpos.at(i)=cred;
      p.drawPixmap(cred.r.left(),cred.r.top(),*credits.at(i),0,0,-1,-1);        
    }
    p.end();
    bitBlt(this, 0, 0, &buff,0,0,-1,-1);  
  }
}

/** Moves the ball if necessaty */
void CIntro::keyPressEvent(QKeyEvent* e){
  if((e->key()==Qt::Key_Up)&&(operation==MAIN_MENU))
  {
    bitBlt(this,200,ymin+choice*dy,&background,200,ymin+choice*dy,ball.width(),ball.height());
    choice--;
    if(choice<0)
      choice=choicemax;;
  }
  else if((e->key()==Qt::Key_Down)&&(operation==MAIN_MENU))
  {
    bitBlt(this,200,ymin+choice*dy,&background,200,ymin+choice*dy,ball.width(),ball.height());
    choice++;
    if(choice>choicemax)
      choice=0;
  }
  else if(e->key()==Qt::Key_Return)
  {
    if(operation==MAIN_MENU)
    {
      CScore score;
      switch(choice)
      {
        case 0:
          operation=ANIM_PLAYERNAME;
          break;
        case 2:
          score.exec();
          break;
        case 3:
          operation=CREDITS;
          break;
        case 4:
          reject();
          break;
        default:
          accept();
      }
    }
    else
      accept();
  }
  else if(e->key()==Qt::Key_Escape)
  {
    if((operation==ANIM_PLAYERNAME)||(operation==WAITING_PLAYERNAME)||(operation==CREDITS))
    {
      operation=MAIN_MENU;
      yanimplayername=height();
      playername->hide();
      update();
      timer->start( 25, false );
    }
    else
      reject();
  }
  else
    e->ignore();
}

void CIntro::mouseMoveEvent( QMouseEvent* e)
{
  int newchoice;
  newchoice=(e->y()-120)/46;

  if((operation==MAIN_MENU)&&(e->x()>180)&&(e->x()<480)&&(e->y()>120)&&(newchoice!=choice))
  {    
    bitBlt(this,200,ymin+choice*dy,&background,200,ymin+choice*dy,ball.width(),ball.height());
    choice=newchoice;
  }
}

void CIntro::mousePressEvent( QMouseEvent* e)
{
  if(e->button()!=Qt::LeftButton)
    return;

  if(operation==MAIN_MENU)
  {
    CScore score;
    switch(choice)
    {
      case 0:
        operation=ANIM_PLAYERNAME;
        break;
      case 2:
        score.exec();
        break;
      case 3:
        operation=CREDITS;
        break;
      case 4:
        reject();
        break;
      default:
        accept();
    }
  }
  else if((operation==ANIM_PLAYERNAME)||(operation==WAITING_PLAYERNAME)||(operation==CREDITS))
  {
    operation=MAIN_MENU;
    yanimplayername=height();
    playername->hide();
    update();
    timer->start( 25, false );
  }    
}

/** return user's choice */
int CIntro::getChoice(){
  return choice;
}

/** No descriptions */
QString CIntro::getPlayerName(){
  return playername->text();
}
