/********************************************************************

  Module: TiPawnDebug

  Author: Carlo Ordonez

  Description:

    Pawn debugger UI

  Copyright 2006 Sony Online Entertainment.  All rights reserved.

*********************************************************************/

#include "TiPawnDebug.h"
#include "TiUIControl.h"
#include "TiUI.h"
#include "InputConsole.h"
#include "SyDebug.h"

//***********************************************************************
// Constructor/Destructor
//***********************************************************************

TiPawnDebug::TiPawnDebug( TiWindow* pParent )
: TiDialog( pParent )
{
  mpCtrl = SyNew TiUIControl();
  mScroll = 0;
}

TiPawnDebug::~TiPawnDebug()
{
  delete mpCtrl;
}

//***********************************************************************
// DrawSelf
//***********************************************************************

void TiPawnDebug::DrawSelf()
{
  int32 w, h;
  TiUI::Instance()->GetDisplaySize( &w, &h );

  int32 rows = 13;
  int32 width = int32( (float32)w * .75f );
  int32 margin = 20;
  int32 tbWidth = width-(margin<<1);
  int32 line = 1;
  int32 numLines = 5; // number of lines for each text box

  mpCtrl->Init( width, rows, TiUIControl::kNone );
  mpCtrl->Draw();

  // top pane
  mpCtrl->DrawTextBox( "Script Debugger", 0, 0, width, 1, TiUIControl::kSelected, TI_TF_SHADOW );
  mpCtrl->DrawTextBox( mVariables, margin, line, tbWidth, numLines, TiUIControl::kNormal, TI_TF_SHADOW|TI_TF_ELLIPSIS|TI_TF_FRAME );

  mScroll = SY_CLAMP( mScroll, 0, SY_MAX(0,mLines.Size()-numLines) );

  // bottom pane
  line = 6;
  int32 i;
  for( i = mScroll; i < mLines.Size() && line < rows-2; i++, line++ )
  {
    SyColor32F color = i == mLineNum ? SyColor32F(1.f,.83f,0.f,mpCtrl->GetOpacity()) : SyColor32F(.9f,.9f,.9f,mpCtrl->GetOpacity());
    mpCtrl->DrawTextBox( mLines(i), margin, line, tbWidth, 1, color, TI_TF_HARD_BREAK|TI_TF_SHADOW|TI_TF_FRAME );
  }

  // buttons
  mpCtrl->DrawTextBox( "R: Run  S: Step  TAB: Debug Off", margin, rows-1, tbWidth, 1, TiUIControl::kNormal, TI_TF_SHADOW );
}

//***********************************************************************
// ProcessKeyDown
//***********************************************************************

bool TiPawnDebug::ProcessKeyDown( int32 KeyCode )
{
  switch( KeyCode )
  {
  case SyInputEvent::KEYCODE_TAB:
    EndModal(kDebugOff);
    return( true );

  case SyInputEvent::KEYCODE_R:
    EndModal(kRun);
  	return( true );

  case SyInputEvent::KEYCODE_S:
    EndModal(kStep);
    return( true );

  case SyInputEvent::KEYCODE_UP:
    mScroll--;
    return( true );

  case SyInputEvent::KEYCODE_DOWN:
    mScroll++;
    return( true );

  default:
    return( TiWindow::ProcessKeyDown( KeyCode ) );
  }
}

//***********************************************************************
// ProcessButtonDown
//***********************************************************************

bool TiPawnDebug::ProcessButtonDown( int32 DeviceId, int32 ButtonId )
{
  switch( TiWindow::GetButton( ButtonId ) )
  {
  case TiButtonMap::kTriangle:
    EndModal(0);
    return( true );

  default:
    return( TiWindow::ProcessButtonDown( DeviceId, ButtonId ) );
  }
}

//***********************************************************************
// ProcessMessage
//***********************************************************************

void TiPawnDebug::ProcessMessage( TiWindowMessage* pMessage )
{
  TiWindow::ProcessMessage( pMessage );
}

//***********************************************************************
// SetVariables
//***********************************************************************

void TiPawnDebug::SetVariables( const char8* pVariables )
{
  mVariables = pVariables;
}

//***********************************************************************
// SetSource
//***********************************************************************

void TiPawnDebug::SetSource( const char8* pSource, int32 LineNum )
{
  mSource = pSource;
  mLineNum = LineNum;
  mScroll = mLineNum; // ensure current line visible

  mLines.Init();

  // chop up source text into individual lines
  SyString buff;
  for( int32 i = 0; i < mSource.Length(); i++ )
  {
    if( mSource(i) == '\n' )
    {
      AddLine( buff );
    }
    else if( mSource(i) == '\t' )
    {
      buff.Concat( "  " );
    }
    else
    {
      buff.Concat( mSource(i) );
    }
  }
}

//***********************************************************************
// AddLine
//***********************************************************************

void TiPawnDebug::AddLine( SyString& Line )
{
  char8 num[32];
  SyStr::snprintf( num, sizeof(num), "%03d: ", mLines.Size() );

  SyString newline;
  newline.Concat( num );
  newline.Concat( Line );
  mLines.Add( newline );

  // reset
  Line.Init( "" );
}

