/* Sample application to demonstrat FT800 primitives, widgets and customized screen shots */

#include "FT_Platform.h"
#include "FT_RotaryDial.h"

#include "FT_Font_Table.h"


#include<time.h>


#define STARTUP_ADDRESS	100*1024L
#define ICON_ADDRESS	250*1024L
#define SAMAPP_DELAY_BTW_APIS (1000)
#define SAMAPP_ENABLE_DELAY() Ft_Gpu_Hal_Sleep(SAMAPP_DELAY_BTW_APIS)
#define SAMAPP_ENABLE_DELAY_VALUE(x) Ft_Gpu_Hal_Sleep(x)
#define BLK_LEN	  1024

#define CLOCK_HANDLE	(0x01)

#define DIAL		1

ft_int32_t BaseTrackVal = 0,BaseTrackValInit = 0,BaseTrackValSign = 0,MemLoc=0;
/* Global variables for display resolution to support various display panels */
/* Default is WQVGA - 480x272 */
#ifdef SAMAPP_DISPLAY_WQVGA	
ft_int16_t FT_DispWidth = 480;
ft_int16_t FT_DispHeight = 272;
ft_int16_t FT_DispHCycle =  548;
ft_int16_t FT_DispHOffset = 43;
ft_int16_t FT_DispHSync0 = 0;
ft_int16_t FT_DispHSync1 = 41;
ft_int16_t FT_DispVCycle = 292;
ft_int16_t FT_DispVOffset = 12;
ft_int16_t FT_DispVSync0 = 0;
ft_int16_t FT_DispVSync1 = 10;
ft_uint8_t FT_DispPCLK = 5;
ft_char8_t FT_DispSwizzle = 0;
ft_char8_t FT_DispPCLKPol = 1;

#else  SAMAPP_DISPLAY_QVGA	
	/* Values specific to QVGA LCD display */
ft_int16_t	FT_DispWidth = 320;
ft_int16_t	FT_DispHeight = 240;
ft_int16_t	FT_DispHCycle =  408;
ft_int16_t	FT_DispHOffset = 70;
ft_int16_t	FT_DispHSync0 = 0;
ft_int16_t	FT_DispHSync1 = 10;
ft_int16_t	FT_DispVCycle = 263;
ft_int16_t	FT_DispVOffset = 13;
ft_int16_t	FT_DispVSync0 = 0;
ft_int16_t	FT_DispVSync1 = 2;
ft_uint8_t	FT_DispPCLK = 8;
ft_char8_t	FT_DispSwizzle = 2;
ft_char8_t	FT_DispPCLKPol = 0;
#endif

const ft_uint8_t FT_DLCODE_BOOTUP[12] = 
{
    0,255,0,2,//GPU instruction CLEAR_COLOR_RGB
    7,0,0,38, //GPU instruction CLEAR
    0,0,0,0,  //GPU instruction DISPLAY
};


/* Global used for buffer optimization */
Ft_Gpu_Hal_Context_t host,*phost;


ft_uint32_t Ft_CmdBuffer_Index;
ft_uint32_t Ft_DlBuffer_Index;

#ifdef BUFFER_OPTIMIZATION
ft_uint8_t  Ft_DlBuffer[FT_DL_SIZE];
ft_uint8_t  Ft_CmdBuffer[FT_CMD_FIFO_SIZE];
#endif

ft_void_t Ft_App_WrCoCmd_Buffer(Ft_Gpu_Hal_Context_t *phost,ft_uint32_t cmd)
{
#ifdef  BUFFER_OPTIMIZATION
   /* Copy the command instruction into buffer */
   ft_uint32_t *pBuffcmd;
   pBuffcmd =(ft_uint32_t*)&Ft_CmdBuffer[Ft_CmdBuffer_Index];
   *pBuffcmd = cmd;
#endif
#ifdef ARDUINO_PLATFORM
   Ft_Gpu_Hal_WrCmd32(phost,cmd);
#endif

   /* Increment the command index */
   Ft_CmdBuffer_Index += FT_CMD_SIZE;  
}

ft_void_t Ft_App_WrDlCmd_Buffer(Ft_Gpu_Hal_Context_t *phost,ft_uint32_t cmd)
{
#ifdef BUFFER_OPTIMIZATION  
   /* Copy the command instruction into buffer */
   ft_uint32_t *pBuffcmd;
   pBuffcmd =(ft_uint32_t*)&Ft_DlBuffer[Ft_DlBuffer_Index];
   *pBuffcmd = cmd;
#endif

#ifdef ARDUINO_PLATFORM
   Ft_Gpu_Hal_Wr32(phost,(RAM_DL+Ft_DlBuffer_Index),cmd);
#endif
   /* Increment the command index */
   Ft_DlBuffer_Index += FT_CMD_SIZE;  
}

ft_void_t Ft_App_WrCoStr_Buffer(Ft_Gpu_Hal_Context_t *phost,const ft_char8_t *s)
{
#ifdef  BUFFER_OPTIMIZATION  
  ft_uint16_t length = 0;
  length = strlen(s) + 1;//last for the null termination
  
  strcpy(&Ft_CmdBuffer[Ft_CmdBuffer_Index],s);  

  /* increment the length and align it by 4 bytes */
  Ft_CmdBuffer_Index += ((length + 3) & ~3);  
#endif  
}

ft_void_t Ft_App_Flush_DL_Buffer(Ft_Gpu_Hal_Context_t *phost)
{
#ifdef  BUFFER_OPTIMIZATION    
   if (Ft_DlBuffer_Index > 0)
     Ft_Gpu_Hal_WrMem(phost,RAM_DL,Ft_DlBuffer,Ft_DlBuffer_Index);
#endif     
   Ft_DlBuffer_Index = 0;
   
}

ft_void_t Ft_App_Flush_Co_Buffer(Ft_Gpu_Hal_Context_t *phost)
{
#ifdef  BUFFER_OPTIMIZATION    
   if (Ft_CmdBuffer_Index > 0)
     Ft_Gpu_Hal_WrCmdBuf(phost,Ft_CmdBuffer,Ft_CmdBuffer_Index);
#endif     
   Ft_CmdBuffer_Index = 0;
}

/* Startup Screen Information*/ 

char *info[] = {  "FT800 Rotary Dial Application",
                          "APP to demonstrate interactive rotary dial,",
                          "using Points, Track",
                          "& Stencil"
                       }; 

/*Deflated Icon bitmap array*/   

static ft_uint8_t icon[] = {0x78,0x9C,0xE5,0x94,0xBF,0x4E,0xC2,0x40,0x1C,0xC7,0x7F,0x2D,0x04,0x8B,0x20,0x45,0x76,0x14,0x67,0xA3,0xF1,0x0D,0x64,0x75,0xD2,0xD5,0x09,0x27,0x17,0x13,0xE1,0x0D,0xE4,0x0D,0x78,0x04,0x98,0x5D,0x30,0x26,0x0E,0x4A,0xA2,0x3E,0x82,0x0E,0x8E,0x82,0xC1,0x38,0x62,0x51,0x0C,0x0A,0x42,0x7F,0xDE,0xB5,0x77,0xB4,0x77,0x17,0x28,0x21,0x26,0x46,0xFD,0x26,0xCD,0xE5,0xD3,0x7C,0xFB,0xBB,0xFB,0xFD,0xB9,0x02,0xCC,0xA4,0xE8,0x99,0x80,0x61,0xC4,0x8A,0x9F,0xCB,0x6F,0x31,0x3B,0xE3,0x61,0x7A,0x98,0x84,0x7C,0x37,0xF6,0xFC,0xC8,0xDD,0x45,0x00,0xDD,0xBA,0xC4,0x77,0xE6,0xEE,0x40,0xEC,0x0E,0xE6,0x91,0xF1,0xD2,0x00,0x42,0x34,0x5E,0xCE,0xE5,0x08,0x16,0xA0,0x84,0x68,0x67,0xB4,0x86,0xC3,0xD5,0x26,0x2C,0x20,0x51,0x17,0xA2,0xB8,0x03,0xB0,0xFE,0x49,0xDD,0x54,0x15,0xD8,0xEE,0x73,0x37,0x95,0x9D,0xD4,0x1A,0xB7,0xA5,0x26,0xC4,0x91,0xA9,0x0B,0x06,0xEE,0x72,0xB7,0xFB,0xC5,0x16,0x80,0xE9,0xF1,0x07,0x8D,0x3F,0x15,0x5F,0x1C,0x0B,0xFC,0x0A,0x90,0xF0,0xF3,0x09,0xA9,0x90,0xC4,0xC6,0x37,0xB0,0x93,0xBF,0xE1,0x71,0xDB,0xA9,0xD7,0x41,0xAD,0x46,0xEA,0x19,0xA9,0xD5,0xCE,0x93,0xB3,0x35,0x73,0x0A,0x69,0x59,0x91,0xC3,0x0F,0x22,0x1B,0x1D,0x91,0x13,0x3D,0x91,0x73,0x43,0xF1,0x6C,0x55,0xDA,0x3A,0x4F,0xBA,0x25,0xCE,0x4F,0x04,0xF1,0xC5,0xCF,0x71,0xDA,0x3C,0xD7,0xB9,0xB2,0x48,0xB4,0x89,0x38,0x20,0x4B,0x2A,0x95,0x0C,0xD5,0xEF,0x5B,0xAD,0x96,0x45,0x8A,0x41,0x96,0x7A,0x1F,0x60,0x0D,0x7D,0x22,0x75,0x82,0x2B,0x0F,0xFB,0xCE,0x51,0x3D,0x2E,0x3A,0x21,0xF3,0x1C,0xD9,0x38,0x86,0x2C,0xC6,0x05,0xB6,0x7B,0x9A,0x8F,0x0F,0x97,0x1B,0x72,0x6F,0x1C,0xEB,0xAE,0xFF,0xDA,0x97,0x0D,0xBA,0x43,0x32,0xCA,0x66,0x34,0x3D,0x54,0xCB,0x24,0x9B,0x43,0xF2,0x70,0x3E,0x42,0xBB,0xA0,0x95,0x11,0x37,0x46,0xE1,0x4F,0x49,0xC5,0x1B,0xFC,0x3C,0x3A,0x3E,0xD1,0x65,0x0E,0x6F,0x58,0xF8,0x9E,0x5B,0xDB,0x55,0xB6,0x41,0x34,0xCB,0xBE,0xDB,0x87,0x5F,0xA9,0xD1,0x85,0x6B,0xB3,0x17,0x9C,0x61,0x0C,0x9B,0xA2,0x5D,0x61,0x10,0xED,0x2A,0x9B,0xA2,0x5D,0x61,0x10,0xED,0x2A,0x9B,0xA2,0x5D,0x61,0x10,0xED,0x2A,0x9B,0xED,0xC9,0xFC,0xDF,0x14,0x54,0x8F,0x80,0x7A,0x06,0xF5,0x23,0xA0,0x9F,0x41,0xF3,0x10,0x30,0x4F,0x41,0xF3,0x18,0x30,0xCF,0xCA,0xFC,0xFF,0x35,0xC9,0x79,0xC9,0x89,0xFA,0x33,0xD7,0x1D,0xF6,0x5E,0x84,0x5C,0x56,0x6E,0xA7,0xDA,0x1E,0xF9,0xFA,0xAB,0xF5,0x97,0xFF,0x2F,0xED,0x89,0x7E,0x29,0x9E,0xB4,0x9F,0x74,0x1E,0x69,0xDA,0xA4,0x9F,0x81,0x94,0xEF,0x4F,0xF6,0xF9,0x0B,0xF4,0x65,0x51,0x08};

/* Optimized implementation of sin and cos table - precision is 16 bit */
FT_PROGMEM ft_prog_uint16_t sintab[] = {
0, 402, 804, 1206, 1607, 2009, 2410, 2811, 3211, 3611, 4011, 4409, 4807, 5205, 5601, 5997, 6392, 
6786, 7179, 7571, 7961, 8351, 8739, 9126, 9511, 9895, 10278, 10659, 11038, 11416, 11792, 12166, 12539,
12909, 13278, 13645, 14009, 14372, 14732, 15090, 15446, 15799, 16150, 16499, 16845, 17189, 17530, 17868,
18204, 18537, 18867, 19194, 19519, 19840, 20159, 20474, 20787, 21096, 21402, 21705, 22004, 22301, 22594, 
22883, 23169, 23452, 23731, 24006, 24278, 24546, 24811, 25072, 25329, 25582, 25831, 26077, 26318, 26556, 26789, 
27019, 27244, 27466, 27683, 27896, 28105, 28309, 28510, 28706, 28897, 29085, 29268, 29446, 29621, 29790, 29955, 
30116, 30272, 30424, 30571, 30713, 30851, 30984, 31113, 31236, 31356, 31470, 31580, 31684, 31785, 31880, 31970, 
32056, 32137, 32213, 32284, 32350, 32412, 32468, 32520, 32567, 32609, 32646, 32678, 32705, 32727, 32744, 32757, 
32764, 32767, 32764};

ft_int16_t SAMAPP_qsin(ft_uint16_t a)
{
  ft_uint8_t f;
  ft_int16_t s0,s1;

  if (a & 32768)
    return -SAMAPP_qsin(a & 32767);
  if (a & 16384)
      a = 32768 - a;
  f = a & 127;
  s0 = ft_pgm_read_word(sintab + (a >> 7));
  s1 = ft_pgm_read_word(sintab + (a >> 7) + 1);
  return (s0 + ((ft_int32_t)f * (s1 - s0) >> 7));
}

/* cos funtion */
ft_int16_t SAMAPP_qcos(ft_uint16_t a)
{
  return (SAMAPP_qsin(a + 16384));
}
//#endif


/* API to check the status of previous DLSWAP and perform DLSWAP of new DL */
/* Check for the status of previous DLSWAP and if still not done wait for few ms and check again */
ft_void_t SAMAPP_GPU_DLSwap(ft_uint8_t DL_Swap_Type)
{
	ft_uint8_t Swap_Type = DLSWAP_FRAME,Swap_Done = DLSWAP_FRAME;

	if(DL_Swap_Type == DLSWAP_LINE)
	{
		Swap_Type = DLSWAP_LINE;
	}

	/* Perform a new DL swap */
	Ft_Gpu_Hal_Wr8(phost,REG_DLSWAP,Swap_Type);

	/* Wait till the swap is done */
	while(Swap_Done)
	{
		Swap_Done = Ft_Gpu_Hal_Rd8(phost,REG_DLSWAP);

		if(DLSWAP_DONE != Swap_Done)
		{
			Ft_Gpu_Hal_Sleep(10);//wait for 10ms
		}
	}	
}




	static void polarxy(ft_uint32_t r, float th, ft_int16_t *x, ft_int16_t *y,ft_uint16_t ox,ft_uint16_t oy)
{
	//	th = th * 32768 / 180;
		*x = (16 * ox + (((long)r * SAMAPP_qsin(th)) >> 11) + 16);
		*y = (16 * oy - (((long)r * SAMAPP_qcos(th)) >> 11));
}

ft_uint16_t da(ft_int32_t i)
{
//  return (45) * (16384) / 180;
	return (i+90) * 65536 / 360;
}


/********API to return the assigned TAG value when penup,for the primitives/widgets******/

static ft_uint8_t sk=0;
ft_uint8_t Read_Keys()
{
  static ft_uint8_t Read_tag=0,temp_tag=0,ret_tag=0;	
  Read_tag = Ft_Gpu_Hal_Rd8(phost,REG_TOUCH_TAG);
  ret_tag = NULL;
  if(Read_tag!=NULL)		
  {
    if(temp_tag!=Read_tag)
    {
      temp_tag = Read_tag;	
      sk = Read_tag;										
    }  
  }
  else
  {
    if(temp_tag!=0)
    {
      ret_tag = temp_tag;
    }  
    sk = 0;
  }
  return ret_tag;
}
/***********************API used to SET the ICON******************************************/
/*Refer the code flow in the flowchart availble in the Application Note */



ft_void_t Info()
{
  ft_uint16_t dloffset = 0,z;
// Touch Screen Calibration
  Ft_CmdBuffer_Index = 0;  
  Ft_Gpu_CoCmd_Dlstart(phost); 
  Ft_App_WrCoCmd_Buffer(phost,CLEAR(1,1,1));
  Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(255,255,255));
  Ft_Gpu_CoCmd_Text(phost,FT_DispWidth/2,FT_DispHeight/2,28,OPT_CENTERX|OPT_CENTERY,"Please tap on a dot");
  Ft_Gpu_CoCmd_Calibrate(phost,0);
  Ft_App_WrCoCmd_Buffer(phost,DISPLAY());
  Ft_Gpu_CoCmd_Swap(phost);
  Ft_App_Flush_Co_Buffer(phost);
  Ft_Gpu_Hal_WaitCmdfifo_empty(phost);
// Ftdi Logo animation  
  Ft_Gpu_CoCmd_Logo(phost);
  Ft_App_Flush_Co_Buffer(phost);
  while(0!=Ft_Gpu_Hal_Rd16(phost,REG_CMD_READ)); 
//Copy the Displaylist from DL RAM to GRAM
  dloffset = Ft_Gpu_Hal_Rd16(phost,REG_CMD_DL);
  dloffset -=4; 
  Ft_Gpu_Hal_WrCmd32(phost,CMD_MEMCPY);
  Ft_Gpu_Hal_WrCmd32(phost,STARTUP_ADDRESS);
  Ft_Gpu_Hal_WrCmd32(phost,RAM_DL);
  Ft_Gpu_Hal_WrCmd32(phost,dloffset);
//Enter into Info Screen
  do
  {
	Ft_CmdBuffer_Index = 0;  
    Ft_Gpu_CoCmd_Dlstart(phost);   
    Ft_Gpu_CoCmd_Append(phost,STARTUP_ADDRESS,dloffset);
//Reset the BITMAP properties used during Logo animation
    Ft_App_WrCoCmd_Buffer(phost,BITMAP_TRANSFORM_A(256));
    Ft_App_WrCoCmd_Buffer(phost,BITMAP_TRANSFORM_A(256));
    Ft_App_WrCoCmd_Buffer(phost,BITMAP_TRANSFORM_B(0));
    Ft_App_WrCoCmd_Buffer(phost,BITMAP_TRANSFORM_C(0));
    Ft_App_WrCoCmd_Buffer(phost,BITMAP_TRANSFORM_D(0));
    Ft_App_WrCoCmd_Buffer(phost,BITMAP_TRANSFORM_E(256));
    Ft_App_WrCoCmd_Buffer(phost,BITMAP_TRANSFORM_F(0));  
//Display the information with transparent Logo using Edge Strip  
	
    Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(219,180,150));
    Ft_App_WrCoCmd_Buffer(phost,COLOR_A(220));
    Ft_App_WrCoCmd_Buffer(phost,BEGIN(EDGE_STRIP_A));
    Ft_App_WrCoCmd_Buffer(phost,VERTEX2F(0,FT_DispHeight*16));
    Ft_App_WrCoCmd_Buffer(phost,VERTEX2F(FT_DispWidth*16,FT_DispHeight*16));
    Ft_App_WrCoCmd_Buffer(phost,COLOR_A(255));
    Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(0,0,0));

    Ft_Gpu_CoCmd_Text(phost,FT_DispWidth/2,20,28,OPT_CENTERX|OPT_CENTERY,info[0]);
    Ft_Gpu_CoCmd_Text(phost,FT_DispWidth/2,60,26,OPT_CENTERX|OPT_CENTERY,info[1]);
    Ft_Gpu_CoCmd_Text(phost,FT_DispWidth/2,90,26,OPT_CENTERX|OPT_CENTERY,info[2]);  
    Ft_Gpu_CoCmd_Text(phost,FT_DispWidth/2,120,26,OPT_CENTERX|OPT_CENTERY,info[3]);  
    Ft_Gpu_CoCmd_Text(phost,FT_DispWidth/2,FT_DispHeight-30,26,OPT_CENTERX|OPT_CENTERY,"Click to play");

	
//	Check if the Play key and change the color
    if(sk!='P')
    Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(255,255,255));
    else
	{
		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(100,100,100));		
	}
    Ft_App_WrCoCmd_Buffer(phost,BEGIN(FTPOINTS));   
	
    Ft_App_WrCoCmd_Buffer(phost,POINT_SIZE(20*16));
    Ft_App_WrCoCmd_Buffer(phost,TAG('P'));
    Ft_App_WrCoCmd_Buffer(phost,VERTEX2F((FT_DispWidth/2)*16,(FT_DispHeight-60)*16));
	 Ft_App_WrCoCmd_Buffer(phost,CLEAR(0,1,0));

	  Ft_App_WrCoCmd_Buffer(phost, COLOR_RGB(255, 0, 0) );
	Ft_App_WrCoCmd_Buffer(phost, STENCIL_OP(INCR,INCR) );
	Ft_App_WrCoCmd_Buffer(phost, COLOR_MASK(0,0,0,0) );//mask all the colors
	Ft_App_WrCoCmd_Buffer(phost, BEGIN(EDGE_STRIP_L));

	Ft_App_WrCoCmd_Buffer(phost, VERTEX2II(((FT_DispWidth/2)-14+10),(FT_DispHeight-77+5),0,0));
	Ft_App_WrCoCmd_Buffer(phost, VERTEX2II(((FT_DispWidth/2)-2+15),(FT_DispHeight-67+8),0,0));
	Ft_App_WrCoCmd_Buffer(phost, VERTEX2II(((FT_DispWidth/2)-14+10),(FT_DispHeight-57+11),0,0));
	Ft_App_WrCoCmd_Buffer(phost, VERTEX2II(((FT_DispWidth/2)-14+10),(FT_DispHeight-77+5),0,0));
	Ft_App_WrCoCmd_Buffer(phost, END());
	Ft_App_WrCoCmd_Buffer(phost, COLOR_MASK(1,1,1,1) );//enable all the colors
	Ft_App_WrCoCmd_Buffer(phost, STENCIL_FUNC(EQUAL,1,255));
	Ft_App_WrCoCmd_Buffer(phost, BEGIN(EDGE_STRIP_L));
	Ft_App_WrCoCmd_Buffer(phost, VERTEX2II(FT_DispWidth,0,0,0));
	Ft_App_WrCoCmd_Buffer(phost, VERTEX2II(FT_DispWidth,FT_DispHeight,0,0));
	//Ft_App_WrCoCmd_Buffer(phost, END());
	
	Ft_App_WrCoCmd_Buffer(phost, STENCIL_OP(KEEP,KEEP));
	Ft_App_WrCoCmd_Buffer(phost, STENCIL_FUNC(ALWAYS,0,255));
	Ft_App_WrCoCmd_Buffer(phost,LINE_WIDTH(1*16));
	//Ft_App_WrCoCmd_Buffer(phost, COLOR_RGB(0, 0, 0) );
	Ft_App_WrCoCmd_Buffer(phost, BEGIN(LINE_STRIP));
	Ft_App_WrCoCmd_Buffer(phost, VERTEX2II(((FT_DispWidth/2)-14+10),(FT_DispHeight-77+5),0,0));
	Ft_App_WrCoCmd_Buffer(phost, VERTEX2II(((FT_DispWidth/2)-2+15),(FT_DispHeight-67+8),0,0));
	Ft_App_WrCoCmd_Buffer(phost, VERTEX2II(((FT_DispWidth/2)-14+10),(FT_DispHeight-57+11),0,0));
	Ft_App_WrCoCmd_Buffer(phost, VERTEX2II(((FT_DispWidth/2)-14+10),(FT_DispHeight-77+5),0,0));
	//Ft_App_WrCoCmd_Buffer(phost, END());



    //Ft_App_WrCoCmd_Buffer(phost,VERTEX2II((FT_DispWidth/2)-14,(FT_DispHeight-75),14,4));
    Ft_App_WrCoCmd_Buffer(phost,DISPLAY());
    Ft_Gpu_CoCmd_Swap(phost);
    Ft_App_Flush_Co_Buffer(phost);
    Ft_Gpu_Hal_WaitCmdfifo_empty(phost);
  }while(Read_Keys()!='P');
/* wait until Play key is not pressed*/ 
  /* To cover up some distortion while demo is being loaded */
    Ft_App_WrCoCmd_Buffer(phost, CMD_DLSTART);
  Ft_App_WrCoCmd_Buffer(phost,CLEAR_COLOR_RGB(255,255,255));
  Ft_App_WrCoCmd_Buffer(phost,CLEAR(1,1,1));
  Ft_App_WrCoCmd_Buffer(phost,DISPLAY());
  Ft_Gpu_CoCmd_Swap(phost);
  Ft_App_Flush_Co_Buffer(phost);
  Ft_Gpu_Hal_WaitCmdfifo_empty(phost);
}

ft_uint32_t Load_RawDataFromfile(ft_uchar8_t ImageArrayname[],/* Image Array*/
								 ft_uint32_t ptr,/* Array Size*/
								 ft_uint32_t RamAddr,
								 ft_int16_t Handle,
								 ft_int16_t Format,
								 ft_int16_t Stride,
								 ft_int16_t Width,
								 ft_int16_t Height,
								 ft_uint8_t i
								 )
{
	FILE *pRawDataFile = NULL;
	ft_uint8_t *pbuff = NULL;
	ft_int32_t FileLen=0,fsize=0;
	
		/* Make the RAM address align of 8 */
		RamAddr = (ft_uint32_t)(RamAddr + 7) & (~7);

		
		fsize = SAMAPP_Uncompressed_FileSize[i];
		
		Ft_Gpu_Hal_WrCmd32(phost,  CMD_INFLATE);
		Ft_Gpu_Hal_WrCmd32(phost,  RamAddr);
#ifdef MSVC_PLATFORM 
        Ft_Gpu_Hal_WrCmdBuf(phost,ImageArrayname,ptr);
#endif
#ifdef ARDUINO_PLATFORM
		Ft_Gpu_Hal_WrCmdBufFromFlash(pphost,ImageArrayname,ptr);
#endif
		

		Ft_App_WrCoCmd_Buffer(phost,BITMAP_HANDLE(Handle));
		Ft_App_WrCoCmd_Buffer(phost,BITMAP_SOURCE(RamAddr));
		Ft_App_WrCoCmd_Buffer(phost, BITMAP_LAYOUT(Format,Stride,Height));		
		Ft_App_WrCoCmd_Buffer(phost, BITMAP_SIZE(NEAREST,BORDER,BORDER,Width,Height));		
		Ft_App_WrCoCmd_Buffer(phost, VERTEX2II(0,0,Handle,0));				
		
		
	fsize = (fsize + 7) & (~7);//align the buffer to 8
	return (RamAddr + fsize);
}

ft_void_t Rotary_Dial_phone()
{
	ft_uint8_t ReadTag = 0,PrevTag = 0,StoreTag,flag =0, PrintTag=0,Tagcheck=0,Penup = 0,i=0,j;	

	ft_char8_t StringArray[31];	
	ft_int32_t tmprate = 0;	

	ft_int32_t FontWid = 0, FontHt = 0,temp =0,tagval,PrevTh = 0,adjusting = 0, CurrTh,MemLoc=0;	
	ft_int16_t OuterCircleRadius=0, InnerCircleRadius, DiffbetRadius,DiffbetRadiusbytwo, CentreWhiteCircle,FontSizeCentre;
	ft_int16_t ScreenWidthMid,ScreenHeightMid,FontPLaceX[10],FontPLaceY[10],SmallNumCircleRad, k=0,l=0 ,m=0,FontSize,StartTheta,EndTheta,IncTheta;
	ft_int16_t NextTh=0,NoTouch,Touch,PrevTouch = 1,VertexX, VertexY,NoX,NoY,vX,MinTheta,MaxTheta,threshold_angle=0,thresholdflag=0;
	ft_int16_t ButHt, ButWid,FingerstopX,FingerstopY;
	ft_uint32_t RotaryTag=0;
	
	ft_int16_t th,theta;	
	SAMAPP_RotaryDial_Bmps_t BmpBalls[40];//for background animation effects

	ScreenWidthMid = FT_DispWidth/2;
	ScreenHeightMid = FT_DispHeight/2; 

	

	#ifdef SAMAPP_DISPLAY_WQVGA
	OuterCircleRadius = ScreenWidthMid/2 - 19;	
	InnerCircleRadius = OuterCircleRadius - 50;
	SmallNumCircleRad = InnerCircleRadius/2 - 8;
	FingerstopX = ScreenWidthMid + 56;
	FingerstopY = ScreenHeightMid + 17;
	NoX = FT_DispWidth/6;//80; //(ScreenWidthMid)-(ScreenWidthMid/2);
	NoY = FT_DispHeight - (FT_DispHeight - 7);//7;
	ButHt = ScreenHeightMid - 111;
	ButWid = FT_DispWidth - 160;
	#endif
	#ifdef SAMAPP_DISPLAY_QVGA
	OuterCircleRadius = ScreenWidthMid/2 + 5;	
	InnerCircleRadius = OuterCircleRadius - 45;
	SmallNumCircleRad = InnerCircleRadius/4 + 3;
	FingerstopX = ScreenWidthMid + 42;
	FingerstopY = ScreenHeightMid +10;
	NoX = FT_DispWidth/6;//80; //(ScreenWidthMid)-(ScreenWidthMid/2);
	NoY = FT_DispHeight - (FT_DispHeight - 7);//7;
	ButHt = ScreenHeightMid - 95;
	ButWid = FT_DispWidth - 110;
	#endif

	DiffbetRadius = OuterCircleRadius - InnerCircleRadius;
	DiffbetRadiusbytwo = DiffbetRadius/2;
	CentreWhiteCircle = InnerCircleRadius + DiffbetRadiusbytwo;
	
	//DiffbetRadius = 0;
	VertexX = 0;
	VertexY = 0;	

	FontSize = 28;
	FontSizeCentre = 31;

	StartTheta = 50;
	EndTheta = 320;
	IncTheta = 30;
	NoTouch = -32768;

	MinTheta = 60;
	MaxTheta = 90;

	vX = ScreenWidthMid;

	Ft_Gpu_Hal_WrCmd32(phost, CMD_MEMSET);
	Ft_Gpu_Hal_WrCmd32(phost, 0L);//starting address of memset
	Ft_Gpu_Hal_WrCmd32(phost, 55L);//value of memset
	Ft_Gpu_Hal_WrCmd32(phost,256*1024);

	StringArray[0] = '\0';
	tagval = 10;

	/* assign tracks to the white circles outside the do while loop*/
	for(theta = StartTheta; theta<= EndTheta; theta+=IncTheta)
	{
		
		th = theta;	
		th = da(th);

		temp = 0;
		if(theta  == StartTheta +30) i = 9;			
		j = i+'0';
		FontWid = g_Gpu_Fonts[temp].FontWidth[j];
		FontHt =  g_Gpu_Fonts[temp].FontHeightInPixels	;
		polarxy(CentreWhiteCircle,th,&VertexX,&VertexY,ScreenWidthMid,ScreenHeightMid);
		
		FontPLaceX[l] = (VertexX/16) - (FontWid/2);
		FontPLaceY[l] = (VertexY/16) - (FontHt/2);
					
		i--;
		l++;
			
	}

	/* set the vol to max */
	Ft_Gpu_Hal_Wr8(phost, REG_VOL_SOUND,0xFF);

	/* Calculation of balls offsets and rate */
	for(i=0;i<40;i++)
	{
		BmpBalls[i].xOffset = ft_random(FT_DispWidth);
		BmpBalls[i].yOffset = ft_random(FT_DispHeight);

		BmpBalls[i].xDiff = ft_random(16) - 8;
		BmpBalls[i].yDiff = ft_random(8) - 4;
	}
	
	/* Construction of starting screen shot, assign all the bitmap handles here */
	Ft_App_WrCoCmd_Buffer(phost, CMD_DLSTART);
	Ft_App_WrCoCmd_Buffer(phost,CLEAR_COLOR_RGB(255,255,255));
	Ft_App_WrCoCmd_Buffer(phost,CLEAR(1,1,1));
	
	/* track circles outside the while loop */
	for(theta=StartTheta;theta<=EndTheta ;theta+=IncTheta)			
	{	
		th = theta;		
		if(theta == StartTheta + IncTheta) tagval = 9;
		th = da(th);				
		Ft_Gpu_CoCmd_Track(phost,ScreenWidthMid, ScreenHeightMid, DIAL, DIAL, tagval);		
		tagval--;
	}
	
	/* Download the raw data into intended locations */
	{
		ft_uint32_t RamAddrOffest = RAM_G;
		Ft_App_WrCoCmd_Buffer(phost, BEGIN(BITMAPS));
	
		RamAddrOffest = Load_RawDataFromfile(FingerStop,SAMAPP_FingerStop_SIZE,RamAddrOffest,0,ARGB4,56*2,56,38,0);//finger stopper
		RamAddrOffest = Load_RawDataFromfile(Call,SAMAPP_CallIcon,RamAddrOffest,1,ARGB4,56*2,56,56,1);//reject button
		RamAddrOffest = Load_RawDataFromfile(CallCancel,SAMAPP_CallCancelIcon,RamAddrOffest,2,ARGB4,56*2,56,56,2);//call button
		RamAddrOffest = Load_RawDataFromfile(YellowBall20x20,SAMAPP_YellowBall_20x20,RamAddrOffest,3,ARGB4,20*2,20,20,3);//ball 20x20
		RamAddrOffest = Load_RawDataFromfile(YellowBall30x30,SAMAPP_YellowBall_30x30,RamAddrOffest,4,ARGB4,30*2,30,30,4);//ball 30x30
		RamAddrOffest = Load_RawDataFromfile(YellowBall40x40,SAMAPP_YellowBall_40x40,RamAddrOffest,5,ARGB4,40*2,40,40,5);//ball 40x40
		RamAddrOffest = Load_RawDataFromfile(YellowBall60x60,SAMAPP_YellowBall_60x60,RamAddrOffest,6,ARGB4,60*2,60,60,6);//ball 60x60

		Ft_App_WrCoCmd_Buffer(phost, END());
	}

	Ft_App_WrCoCmd_Buffer(phost,DISPLAY());
	Ft_Gpu_CoCmd_Swap(phost);

	/* Download the commands into fifo */
	Ft_App_Flush_Co_Buffer(phost);

	/* Wait till coprocessor completes the operation */
	Ft_Gpu_Hal_WaitCmdfifo_empty(phost);



	do{
		
		Ft_App_WrCoCmd_Buffer(phost, CMD_DLSTART);

		/*Points*/
		Ft_App_WrCoCmd_Buffer(phost, CLEAR_COLOR_RGB(237 ,186 ,17) ); // background color
		Ft_App_WrCoCmd_Buffer(phost,CLEAR(1,1,1));
		/* Draw two gradients, one at the top and another at the bottom. Height of former is 
                   80% of display height and later 20% of display height */
		Ft_App_WrCoCmd_Buffer(phost,SCISSOR_SIZE(512,218));
		Ft_App_WrCoCmd_Buffer(phost,SCISSOR_XY(0,0));
		Ft_Gpu_CoCmd_Gradient(phost,0, 0, 0xEDBA11,0, FT_DispHeight, 0x82660A);
		Ft_App_WrCoCmd_Buffer(phost,SCISSOR_SIZE(512,512));
		Ft_App_WrCoCmd_Buffer(phost,SCISSOR_XY(0,218));
		Ft_Gpu_CoCmd_Gradient(phost,0, 0, 0x2B2205,0, ((FT_DispHeight*0.80))/*218*/, 0x82660A);
		Ft_App_WrCoCmd_Buffer(phost,SCISSOR_SIZE(512,512));
		Ft_App_WrCoCmd_Buffer(phost,SCISSOR_XY(0,0));
		

		/* Draw all the background bitmaps - balls with various resolutions */
		Ft_App_WrCoCmd_Buffer(phost,BEGIN(BITMAPS));
		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(255 ,255 ,255)); // brown outside circle
		for(i = 0;i<40;i++)
		{
			Ft_App_WrCoCmd_Buffer(phost,VERTEX2II(BmpBalls[i].xOffset,BmpBalls[i].yOffset,3+(i%4),0));
			BmpBalls[i].xOffset += BmpBalls[i].xDiff;
			BmpBalls[i].yOffset += BmpBalls[i].yDiff;

			if(BmpBalls[i].xOffset < -80)
			{
				BmpBalls[i].xOffset = FT_DispWidth + 80;
			}
			else if(BmpBalls[i].xOffset > FT_DispWidth + 80)
			{
				BmpBalls[i].xOffset = -80;
			}

			if(BmpBalls[i].yOffset < -80)
			{
				BmpBalls[i].yOffset = FT_DispHeight + 80;
			}
			else if(BmpBalls[i].yOffset > FT_DispHeight + 80)
			{
				BmpBalls[i].yOffset = -80;
			}
		}

		BmpBalls[ft_random(40)].xDiff = ft_random(16) - 6;
		BmpBalls[ft_random(40)].yDiff = ft_random(8) - 4;
		
		//		BmpBalls[ft_random(40)].xDiff = ft_random(16) ;
		//BmpBalls[ft_random(40)].yDiff = ft_random(8) ;

		Ft_App_WrCoCmd_Buffer(phost,POINT_SIZE(OuterCircleRadius * 16) );
		
		Ft_App_WrCoCmd_Buffer(phost,BEGIN(FTPOINTS));
		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(235 ,117 ,0)); // brown outside circle
		Ft_App_WrCoCmd_Buffer(phost,VERTEX2F(ScreenWidthMid*16 - 24,ScreenHeightMid*16 - 24));
		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(0 ,0 ,0)); // brown outside circle
		Ft_App_WrCoCmd_Buffer(phost,VERTEX2F(ScreenWidthMid*16 + 24,ScreenHeightMid*16 + 24));
		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(128 ,64 ,0)); // brown outside circle
		Ft_App_WrCoCmd_Buffer(phost,VERTEX2F(ScreenWidthMid*16,ScreenHeightMid*16));
		

	
		Ft_App_WrCoCmd_Buffer(phost,POINT_SIZE((InnerCircleRadius) * 16) );
		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(87 ,64 ,8)); // inner circle - light brown color
		Ft_App_WrCoCmd_Buffer(phost,VERTEX2F(ScreenWidthMid*16 - 24,ScreenHeightMid*16 - 24));
		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(0 ,0 ,0)); // inner circle - light brown color
		Ft_App_WrCoCmd_Buffer(phost,VERTEX2F(ScreenWidthMid*16 + 24,ScreenHeightMid*16+24));
		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(204 ,151 ,16)); // inner circle - light brown color
		Ft_App_WrCoCmd_Buffer(phost,VERTEX2F(ScreenWidthMid*16,ScreenHeightMid*16));
	

		i = 0;//font inside the white circles - start at 0
		tagval = 10;// tag for the white circles - decrementing tagvalue inside loop
		
		StartTheta = 50;
		EndTheta = 320;
		IncTheta = 30;
		NoTouch = -32768;

		CurrTh = 0;
		threshold_angle = 320;
	
		Touch = Ft_Gpu_Hal_Rd16(phost, REG_TOUCH_SCREEN_XY+2);
		Tagcheck = Ft_Gpu_Hal_Rd8(phost, REG_TOUCH_TAG);

        RotaryTag = Ft_Gpu_Hal_Rd32(phost,REG_TRACKER);
		StoreTag = RotaryTag & 0xff;
		ReadTag = StoreTag;
	
		if((PrevTouch&0x8000) && (0 == PrevTag))
		{
			BaseTrackValInit = (ft_int16_t)((RotaryTag >> 16) & 0xffff);
		}
		else
		{
			BaseTrackValInit = 0;
		}
        /* verify for the track value */
        if((Touch != NoTouch))
		{
			if((StoreTag >= 1) && (StoreTag <= 10))
			{
				CurrTh = (ft_int16_t)((RotaryTag >> 16) & 0xffff);
				  /* BaseTrackVal is the rotary track value of the particular white circle that is moving */
				if(adjusting!=0)
				{
					flag = 0;
					BaseTrackVal += (ft_int16_t)(CurrTh - PrevTh);
					BaseTrackValSign += (ft_int16_t)(CurrTh - PrevTh);
					/* handling of loopback */
					BaseTrackVal &= 0xffff;		
					 /* NextTh value is the track value in degrees */
					NextTh = (ft_uint16_t)(BaseTrackValSign / 182);	
					printf("%d\n",NextTh);
				
				} 
				PrevTh = CurrTh;
				adjusting = (RotaryTag & 0xff);
				PrintTag = ReadTag;

			
			}
		}
        else if(Touch == NoTouch)
        {
			BaseTrackVal=0;		
			flag = 1;
			if(adjusting != 0)
			{
				 /* If white circles have moved beyond their initial value, Nextth value is incremented */
				if(NextTh > 0 )
				{
					
                    /* After the white circle has moved to the desired location, and when penup has been done,
                    the white crcles moved back to its original positon of 0 degrees. */
                    /* NextTh moves back in degrees of twenty in steps. Also sound has to be played when moving back. */
					NextTh-=20;	
					Ft_Gpu_Hal_Wr8(phost, REG_VOL_SOUND,0xff);
					Ft_Gpu_Hal_Wr16(phost, REG_SOUND,0x51);
					Ft_Gpu_Hal_Wr8(phost, REG_PLAY,1);
					MinTheta = 60;
					MaxTheta = 90;
					
				}
				else
				{ 
					/* When the white circles have moved back to its original position, the tag value of the particular white circle 
                    (PrintTag) is stored in the StringArray. StringArray stores upto 17 values. The thresholdflag is also checked 
                    before entering this loop */
					NextTh = 0;
					if((PrintTag >= 1) && (PrintTag <= 10) && (thresholdflag ==1))
					{
						if (PrintTag == 10)PrintTag = 0;
						StringArray[k] = PrintTag + '0';
						
						if(k<17)
						{
							k++;							
						}
						else if (k == 17)
						{
							k = 0;
							StringArray[k] = PrintTag + '0';
							k++;
						}
						thresholdflag=0;
					}
					StringArray[k] = '\0';					
					adjusting = 0;
					_sleep(1);
				}					
			}
			 /* When movement has been finished, the RotaryTag and Printtag are cleared*/
			else if(adjusting == 0)
			{
				RotaryTag = '\0';
				PrintTag = '\0';			
				
			}
			BaseTrackValSign = 0;
		}
		 /* Sound play wrt user touch */
         /* When white circles are touched for the first time after penup - play sound */
		if((PrevTag == 0)&& ((ReadTag !=0)&&(ReadTag !=255)) && ( Penup = 1))
        {
			  Ft_Gpu_Hal_Wr8(phost, REG_VOL_SOUND,0xFF);
		      Ft_Gpu_Hal_Wr16(phost, REG_SOUND,0x51);
		      Ft_Gpu_Hal_Wr8(phost, REG_PLAY,1);
              Penup = 0;
        }
		/* dial button (tag 100) & penup has been done - play dtmf sound */
		if((Tagcheck == 100)  && (flag == 1))
		{
			if(k>0)
			{
				ft_delay(200);
				for(m=0;m<k;m++)
				{
					/* Play the dtmf sound */
					Ft_Gpu_Hal_Wr16(phost, REG_SOUND,StringArray[m]);
					Ft_Gpu_Hal_Wr8(phost, REG_PLAY,1);
					ft_delay(80);
					Ft_Gpu_Hal_Wr16(phost, REG_SOUND,0);
					Ft_Gpu_Hal_Wr8(phost, REG_PLAY,1);
					ft_delay(80);
				}
			}

		}

		/* reject button (tag -200)& penup has been done. clear the string */
		if((Tagcheck == 200) && (flag ==1) )
		{
			for(m =0;m<=k;m++)
			{
				StringArray[m] = '\0';
			}
			k=0;

		}


		Ft_App_WrCoCmd_Buffer(phost,BEGIN(FTPOINTS));
		Ft_App_WrCoCmd_Buffer(phost,STENCIL_OP(INCR,INCR));//pass or fail increment	
		Ft_App_WrCoCmd_Buffer(phost,POINT_SIZE(SmallNumCircleRad * 16) );
		Ft_App_WrCoCmd_Buffer(phost,COLOR_A(255));
		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(255 ,255 ,255));	
	
		Ft_App_WrCoCmd_Buffer(phost,TAG_MASK(1));
		/* Placement of number circles which will move around the rotary */		
		for(theta=StartTheta;theta<=EndTheta ;theta+=IncTheta)			
		{	
			
			th = theta;		
			if(theta == StartTheta + IncTheta) tagval = 9;	
			
			/* limit threshold level near finger stop*/
			/* for value 0 - tag is 10*/
			if((NextTh > threshold_angle) && (ReadTag == 10))
			{
				NextTh = threshold_angle;
				thresholdflag =1;
			}
			
			/* for value 1 to 9 - threshold*/
			for(m = 1,l=9; m<=9, l>=1;m++,l--)
			{
				if((NextTh > threshold_angle - (m*IncTheta)) && (ReadTag == l))
				{
					NextTh = threshold_angle - (m*IncTheta);
					thresholdflag =1;
				}
			}
			/* Stop anticlockwise movement of the dial*/					
			if((BaseTrackValInit + BaseTrackValSign) < BaseTrackValInit)
			{
				NextTh = 0;
			}
			th = th + NextTh;		
			/* calculation of th value in pixels with input in degrees */
			th = da(th);	

			/* calculate x and  y for placing circles according to degree */
			polarxy(CentreWhiteCircle,th,&VertexX ,&VertexY ,ScreenWidthMid,ScreenHeightMid);	
			
		
			Ft_App_WrCoCmd_Buffer(phost,TAG(tagval));
			Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(200 ,99 ,0)); // for 3d effect adding circles of darker color
			Ft_App_WrCoCmd_Buffer(phost,VERTEX2F(VertexX-24,VertexY-24));
			Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(0 ,0 ,0)); 
			Ft_App_WrCoCmd_Buffer(phost,VERTEX2F(VertexX+24,VertexY+24));// for 3d effect adding circles of darker color
			Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(255 ,255 ,255));	
			Ft_App_WrCoCmd_Buffer(phost,VERTEX2F(VertexX,VertexY));// the base number circle
			
			tagval--;	
			
		}
		Ft_App_WrCoCmd_Buffer(phost,TAG_MASK(0));			
		
		/* Play Sound when Nexth(base track value crosses bands within range 30 */
		if((NextTh > MaxTheta) &&(NextTh!=0)&& (Touch != NoTouch))
		{
			Ft_Gpu_Hal_Wr8(phost, REG_VOL_SOUND,0xFF);
			Ft_Gpu_Hal_Wr16(phost, REG_SOUND,0x51);
			Ft_Gpu_Hal_Wr8(phost, REG_PLAY,1);
			MinTheta = MinTheta + IncTheta;
			MaxTheta = MaxTheta + IncTheta;		
		}
		else if(((NextTh < MinTheta) && (NextTh >(MinTheta-30))) && (NextTh!=0)&&(Touch != NoTouch))
		{
			Ft_Gpu_Hal_Wr8(phost, REG_VOL_SOUND,0xFF);
			Ft_Gpu_Hal_Wr16(phost, REG_SOUND,0x51);
			Ft_Gpu_Hal_Wr8(phost, REG_PLAY,1);
			MinTheta = MinTheta - IncTheta;
			MaxTheta = MaxTheta - IncTheta;		
		}
			
		
		/* Placement of NUmbers inside the white circle - using stencil effect*/
		
		Ft_App_WrCoCmd_Buffer(phost,STENCIL_FUNC(GEQUAL,1,255));
		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(0 ,0 ,0));
		Ft_App_WrCoCmd_Buffer(phost,BEGIN(BITMAPS));

			i =0;
			for(l =0; l<=9; l++)
			{
				if(l==1)
				{
					i=9;
				}
				Ft_App_WrCoCmd_Buffer(phost,VERTEX2II(FontPLaceX[l],FontPLaceY[l],FontSize,i+'0'));				
				i--;
			}
		

		Ft_App_WrCoCmd_Buffer(phost,STENCIL_OP(KEEP,KEEP));
        Ft_App_WrCoCmd_Buffer(phost,STENCIL_FUNC(ALWAYS,0,255));
        Ft_App_WrCoCmd_Buffer(phost,COLOR_A(128));

		i =0;
		for(l =0; l<=9; l++)
		{
			if(l==1)
				{
					i=9;
				}				
				Ft_App_WrCoCmd_Buffer(phost,VERTEX2II(FontPLaceX[l],FontPLaceY[l],FontSize,i+'0'));				
				i--;
		}
		
		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(255,255,255));
		Ft_App_WrCoCmd_Buffer(phost,COLOR_A(255));
		Ft_App_WrCoCmd_Buffer(phost,BEGIN(BITMAPS));		

		/* dial image Placement*/
		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(255,255,255));
		Ft_App_WrCoCmd_Buffer(phost,TAG_MASK(1));
		Ft_App_WrCoCmd_Buffer(phost,TAG(100));
		Ft_App_WrCoCmd_Buffer(phost,VERTEX2II(ScreenWidthMid-131,FT_DispHeight-70,2,0));
		Ft_App_WrCoCmd_Buffer(phost,TAG_MASK(0));		
		
		/* display numbers in the centre of the point while dialing*/
		if((PrintTag >0 ) && (PrintTag <= 10) && (Touch != NoTouch))
		{
		
			if (PrintTag == 10)PrintTag = 0;
			Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(0,0,0));
			Ft_Gpu_CoCmd_Number(phost,(ScreenWidthMid - 16)/*225*/,(ScreenHeightMid - 27)/*110*/,FontSizeCentre,0,PrintTag);
			Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(0,0,0));
			Ft_Gpu_CoCmd_Number(phost,(ScreenWidthMid - 14)/*225*/,(ScreenHeightMid - 25)/*110*/,FontSizeCentre,0,PrintTag);
			Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(255,255,255));
			Ft_Gpu_CoCmd_Number(phost,(ScreenWidthMid - 15)/*225*/,(ScreenHeightMid - 26)/*110*/,FontSizeCentre,0,PrintTag);
			if (PrintTag == 0)PrintTag = 10;
		}
		/* fingerstop image placement */		
		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(255,255,255));
		Ft_App_WrCoCmd_Buffer(phost,VERTEX2II(FingerstopX/*296*/,FingerstopY/*153*/,0,0)); //exact location of picture		

		/*reject image placement*/
		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(255,255,255));
		Ft_App_WrCoCmd_Buffer(phost,TAG_MASK(1));
		Ft_App_WrCoCmd_Buffer(phost,TAG(200));
		Ft_App_WrCoCmd_Buffer(phost,VERTEX2II(ScreenWidthMid+80,FT_DispHeight-70,1,0));
		Ft_App_WrCoCmd_Buffer(phost,TAG_MASK(0));


		Ft_Gpu_CoCmd_FgColor(phost, 0xCC9710); // color of number display button
		Ft_Gpu_CoCmd_Button(phost, NoX, NoY -2/*5*/, ButWid, ButHt, FontSize, 0, "");// placement of button

		Ft_App_WrCoCmd_Buffer(phost,COLOR_RGB(0,0,0));//color of number(text) color
	
		Ft_Gpu_CoCmd_Text(phost,(NoX + ButWid/2),(NoY + ButHt/2),FontSize,OPT_CENTER,StringArray);
		Ft_App_WrCoCmd_Buffer(phost, END());

		Ft_App_WrCoCmd_Buffer(phost,DISPLAY());

		Ft_Gpu_CoCmd_Swap(phost);

		/* Download the commands into fifo */
		Ft_App_Flush_Co_Buffer(phost);

		/* Wait till coprocessor completes the operation */
		Ft_Gpu_Hal_WaitCmdfifo_empty(phost);
		PrevTag = ReadTag;
		PrevTouch = Touch;
		tmprate++;
		}while(1);
			

}








ft_void_t SAMAPP_BootupConfig()
{
	ft_uint8_t Pclk;
	/* Do a power cycle for safer side */
	Ft_Gpu_Hal_Powercycle(phost,FT_TRUE);

	/* Set the clk to external clock */
	Ft_Gpu_HostCommand(phost,FT_GPU_EXTERNAL_OSC);  
	Ft_Gpu_Hal_Sleep(10);
	  

	/* Switch PLL output to 48MHz */
	Ft_Gpu_HostCommand(phost,FT_GPU_PLL_48M);  
	Ft_Gpu_Hal_Sleep(10);

	/* Do a core reset for safer side */
	Ft_Gpu_HostCommand(phost,FT_GPU_CORE_RESET);     

	/* Access address 0 to wake up the FT800 */
	Ft_Gpu_HostCommand(phost,FT_GPU_ACTIVE_M);  

    Ft_Gpu_Hal_Wr8(phost, REG_GPIO_DIR,0x80 | Ft_Gpu_Hal_Rd8(phost,REG_GPIO_DIR));
    Ft_Gpu_Hal_Wr8(phost, REG_GPIO,0x080 | Ft_Gpu_Hal_Rd8(phost,REG_GPIO));
	
	{
		ft_uint8_t chipid;
		//Read Register ID to check if FT800 is ready. 
		chipid = Ft_Gpu_Hal_Rd8(phost, REG_ID);
		while(chipid != 0x7C)
			chipid = Ft_Gpu_Hal_Rd8(phost, REG_ID);
#ifdef MSVC_PLATFORM
		printf("VC1 register ID after wake up %x\n",chipid);
#endif
	}
	Pclk = FT_DispPCLK;

	Ft_Gpu_Hal_Wr8(phost,REG_GPIO,0xFF);//look into data sheet for the various configurations of GPIOs
	Ft_Gpu_Hal_Wr8(phost,REG_VOL_SOUND,255);

	/* Boot up sequence */
	/* Clock is configured in the above code - optional if external clock is not avilable */
	/* By default the display settings are for WQVGA, so first download the first DL into DL memory */
	/* Write FRAME_SWAP into DL_SWAP register */
	/* Followed by enabling PCLK - note that PCLK for WQVGA is 5 and QVGA is 8 - follow DS/PG/AN for more information */
	Ft_Gpu_Hal_WrMem(phost,RAM_DL,(ft_uint8_t *)FT_DLCODE_BOOTUP,12);
	Ft_Gpu_Hal_Wr8(phost,REG_DLSWAP,DLSWAP_FRAME);
	Ft_Gpu_Hal_Wr8(phost,REG_PCLK,Pclk);


Ft_Gpu_Hal_Wr32(phost,REG_TOUCH_TRANSFORM_A,0x00007ce6);
  Ft_Gpu_Hal_Wr32(phost,REG_TOUCH_TRANSFORM_B,0xfffffd67);
  Ft_Gpu_Hal_Wr32(phost,REG_TOUCH_TRANSFORM_C,0xfff55522);
  Ft_Gpu_Hal_Wr32(phost,REG_TOUCH_TRANSFORM_D,0xfffffe6f);
  Ft_Gpu_Hal_Wr32(phost,REG_TOUCH_TRANSFORM_E,0xffffb4be);
  Ft_Gpu_Hal_Wr32(phost,REG_TOUCH_TRANSFORM_F,0x0124bca7);
  

	/* Configuration of LCD display */


    Ft_Gpu_Hal_Wr16(phost, REG_HCYCLE, FT_DispHCycle);
    Ft_Gpu_Hal_Wr16(phost, REG_HOFFSET, FT_DispHOffset);
    Ft_Gpu_Hal_Wr16(phost, REG_HSYNC0, FT_DispHSync0);
    Ft_Gpu_Hal_Wr16(phost, REG_HSYNC1, FT_DispHSync1);
    Ft_Gpu_Hal_Wr16(phost, REG_VCYCLE, FT_DispVCycle);
    Ft_Gpu_Hal_Wr16(phost, REG_VOFFSET, FT_DispVOffset);
    Ft_Gpu_Hal_Wr16(phost, REG_VSYNC0, FT_DispVSync0);
    Ft_Gpu_Hal_Wr16(phost, REG_VSYNC1, FT_DispVSync1);
    Ft_Gpu_Hal_Wr8(phost, REG_SWIZZLE, FT_DispSwizzle);
    Ft_Gpu_Hal_Wr8(phost, REG_PCLK_POL, FT_DispPCLKPol);
    Ft_Gpu_Hal_Wr8(phost, REG_PCLK,FT_DispPCLK);//after this display is visible on the LCD
    Ft_Gpu_Hal_Wr16(phost, REG_HSIZE, FT_DispWidth);
    Ft_Gpu_Hal_Wr16(phost, REG_VSIZE, FT_DispHeight);


    /* Touch configuration - configure the resistance value to 1200 - this value is specific to customer requirement and derived by experiment */
    Ft_Gpu_Hal_Wr16(phost, REG_TOUCH_RZTHRESH,1200);


}

/* Boot up for FT800 followed by graphics primitive sample cases */
/* Initial boot up DL - make the back ground green color */

#ifdef MSVC_PLATFORM
/* Main entry point */
ft_int32_t main(ft_int32_t argc,ft_char8_t *argv[])
#endif
#ifdef ARDUINO_PLATFORM
ft_void_t setup()
#endif
{
	Ft_Gpu_HalInit_t halinit;
	
	halinit.TotalChannelNum = 1;

              
	Ft_Gpu_Hal_Init(&halinit);
	host.hal_config.channel_no = 0;
#ifdef MSVC_PLATFORM_SPI
	host.hal_config.spi_clockrate_khz = 12000; //in KHz
#endif
#ifdef ARDUINO_PLATFORM_SPI
	host.hal_config.spi_clockrate_khz = 4000; //in KHz
#endif
        Ft_Gpu_Hal_Open(&host);
            
	phost = &host;

    SAMAPP_BootupConfig();

	printf("reg_touch_rz =0x%x ", Ft_Gpu_Hal_Rd16(phost, REG_TOUCH_RZ));
	printf("reg_touch_rzthresh =0x%x ", Ft_Gpu_Hal_Rd32(phost, REG_TOUCH_RZTHRESH));
	printf("reg_touch_tag_xy=0x%x",Ft_Gpu_Hal_Rd32(phost, REG_TOUCH_TAG_XY));
    /*It is optional to clear the screen here*/	
    Ft_Gpu_Hal_WrMem(phost, RAM_DL,(ft_uint8_t *)FT_DLCODE_BOOTUP,sizeof(FT_DLCODE_BOOTUP));
    Ft_Gpu_Hal_Wr8(phost, REG_DLSWAP,DLSWAP_FRAME);
    
    Ft_Gpu_Hal_Sleep(1000);//Show the booting up screen. );
	printf("reg_touch_tag=0x%x",Ft_Gpu_Hal_Rd32(phost, REG_TOUCH_TAG));




	Info();

	
	Rotary_Dial_phone();

  

#ifdef MSVC_PLATFORM
	/* Audio playback api*/    
	Ft_Gpu_Hal_Wr8(phost, REG_VOL_SOUND,255);

#endif




	/* Close all the opened handles */
    Ft_Gpu_Hal_Close(phost);
    Ft_Gpu_Hal_DeInit();
#ifdef MSVC_PLATFORM
	return 0;
#endif
}

void loop()
{
}



/* Nothing beyond this */















