Continue to Site

Welcome to our site!

Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

  • Welcome to our site! Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

AR1020 Touch Controller

Status
Not open for further replies.

AtomSoft

Well-Known Member
Hey guys i have been working on this for a day now and am stuck. I have tried so many things and no luck.

I have this Touch Screen Controller "AR1020"... im trying to communicate via SPI with no success. Can someone point to me where i am going wrong?

Code:
/* *****************************************************************************
;                                                                             *
;    Filename:                     				                              *
;    Date:                                         	                          *
;    File Version: 001                                                        *
;                                                                             *
;    Author:   Jason Lopez                                                    *
;    Company:  AtomSoft                                                       *
;                                                                             *
;***************************************************************************** */

#include <p18f248.h>
#include <delays.h>
#include <string.h>

#pragma config WDT = OFF, LVP = OFF, OSC = HS

/************************************
Prototypes
*************************************/
void main(void);
unsigned char writeSPI( unsigned char b);
void initSPI( void);

unsigned char buff[13];
#define NDSCS LATCbits.LATC2
/************************************
Main
*************************************/
void main(void){
	unsigned char x=0;

	TRISA = TRISB = TRISC = 0x00;
	LATA = LATB = LATC = 0x00;
	initSPI();
	
	NDSCS = 0;		//ONLY 1 SPI Device so leave low

	while(1){

		for(x=0;x<13;x++)
			buff[x] = 0;

		buff[0] = writeSPI(0x55);
		buff[0] = writeSPI(0x01);
		buff[0] = writeSPI(0x12);

		while(x<8){
			buff[x] = writeSPI(0);			
		}

		Delay10KTCYx(20);
	}
}

void initSPI( void)
{
    TRISC = 0b00010000;

   	SSPCON1 = 1;
    SSPCON1bits.SSPEN = 0;

	SSPCON1bits.CKP = 0;
    SSPSTATbits.CKE = 1;//1
    SSPSTATbits.SMP = 0;

    SSPCON1bits.SSPEN = 1;
}   


unsigned char writeSPI( unsigned char b)
{
    SSPBUF = b;                  // write to buffer for TX
    while( !SSPSTATbits.BF); // wait transfer complete
    return SSPBUF;               // read the received value
}
 
You can't just leave the card select/slave select line low like that. It is generally used as a start of frame indicator. That's the first thing that jumps out at me.

EDIT: Well, that's wrong. The datasheet specifically states you can tie it low for single chip use.
 
Last edited:
Looking at the datasheet, is the M1 pin tied to VDD to activate SPI mode?

Have you tried using that Pickit logic analyzer to see what's coming and going? Are the lines doing anything... clock? data? Are you sure the phase is correct, the AR1020 has valid data on the falling clock edge.
 
You can't just leave the card select/slave select line low like that. It is generally used as a start of frame indicator. That's the first thing that jumps out at me.

EDIT: Well, that's wrong. The datasheet specifically states you can tie it low for single chip use.

Yeah heh...

Oh yeah as for M1 here is my schematic:
ds2-jpg.40743
 

Attachments

  • DS2..jpg
    DS2..jpg
    115.9 KB · Views: 2,115
making a new board now tho... with all required parts but that above schematic is the bare minimum so i should get data to/from ic with no issue
 
Hello Jason,

Have you solved your issue with AR1020 ?

We spoke together regarding GLCD library, now i really would like to add a resistive touch screen on it.

Did you successfully get your test code working ?

I'm not yet confortable with SPI yet, a test code will help me a lot.


Many thanks,
 
Yes, i'm using C ( C18 from Microchip )


Thanks for the document, i will read it.

Did you succeeded to get a touch panel working with a 128x64 GLCD, ( whatever controller used ) ?
 
SPI stuffs

Hey i have this controller too (AR1020 on spi)

your code is correct, The problem is that once you send data to it, you have to wait for it to "do its thing" to send data back. to check if its ready to be read from, pol the SIQ line until it is high, then read in the spi data by sending the spi bus a 0. This will let you read from it with no problem, If data is clocked out when the controller has no valid data to provide, then 0x4d (ASCII "M") will be presented.
 
Last edited:
Thanks... I will be making a new board to test it.. But most likely a nice breakout... with caps and stuff to make sure its all clean power and stuff heh
 
uhh my code is very long, and it contains a header file, I will post the initialization, the rest is just putting this data onto an spi bus and reading the data sheet. Although I have one issue still, and thats calibrating the pen with the screen, if anyone know how to do it let me know because I am stuck on the last part of the initialization ( after 4 points have been taped) .. good luck with this thing, if you get it to all work well let me know. :)

Also there is a bunch of d1,d2,d3,temp... stuff, it is used for debugging and could be removed to save code space.... but it makes it easy to test..

Code:
#ifndef __touchS_H
#define __touchS_H
#include <p24HJ128GP202.h>
#include <libpic30.h>
#include <libq.h>
#include <spi.h>
/**********************
Touch Screen functions
AR1020 IC
To ensure command communication is not interrupted by touch activity, it is recommended that the controller touch is disabled, prior to other commands. This can be done as follows.
1) Send Disable Touch command
2) Wait 50ms
3) Send desired command/s
4) Send Enable Touch command
The format for sending commands is: <Header><DataSize><Command><Data>…<Data>

<Header> is defined as a value of 0x55 and is used to mark the beginning of the command packet.
<DataSize> is the number of bytes being sent in the command packet, after <DataSize>.
<Command> is a value assigned to a specific command.
<Data> represent from zero to eight bytes of command specific data.
**********************/

#define   CS_TOUCH                  LATAbits.LATA4    //Chip select
#define   CS_TOUCH_TRIS          TRISAbits.TRISA4
#define   INT_TOUCH_TRIS         TRISAbits.TRISA0 //Touch interupt
#define   INT_TOUCH                  PORTAbits.RA0
#define   HEADER_T		        0x55 //Header
#define   TOUCH_EN 		        0x12 //Enable Touch
#define   TOUCH_DIS 		        0x13 //Disable Touch
#define   TOUCH_CALIB	        0x14 //Calibrate Mode
#define   TOUCH_READ		0x20 //Register Read
#define   TOUCH_WRITE		0x21 //Register Write
#define   TOUCH_REGSTART	0x22 //Register Start address
#define   TOUCH_OP_REG           0x0D
#define   TOUCH_CAL_REG		0x0E // reg for cal

This is the c file.....

Code:
int  writeTouch (int data);
int  readTouch  (void);
void waitTouch  (void);


int touchcalSet(void); // Has cal been done already?
int touchDisable(void);
int touchEnable(void);
int touchgetOffset(void);
int touchsetmode(int offset,int mode,int calib);

//***************************
//Write to the touch screen
//***************************
int writeTouch (int data)
{
SPI1BUF = data;		
while(!SPI1STATbits.SPITBF);
return(ReadSPI1());
}

int readTouch (void)
{
SPI1BUF = 0;		
while(SPI1STATbits.SPIRBF);
return(ReadSPI1());
}

void waitTouch (void)
{
while(!INT_TOUCH)
   __delay32(100);
}
//***************************
//Initialize touch screen
//***************************
void initialize_Touch(void)
{
int  regOffset;
CS_TOUCH_TRIS     = 0;  //Output CS
Nop();
CS_TOUCH             = 1;  //Active Low
Nop();
INT_TOUCH_TRIS    = 1;  //tris input
Nop();

touchDisable();
regOffset = touchgetOffset();
touchsetmode(regOffset,TOUCH_M_4,0); //4wire mode !
touchCaibrate(); // cal the touch ic
__delay32(900000);     //50ms Delay 100000, wait a bit
touchEnable();

} 

//***************************
//Get offset register data
//***************************
int touchgetOffset(void)       // get Reg start address
{   					//Receive : <0x55><0x03><0x00><0x22>REG>
int d1,d2,d3,pass,regStart;
CS_TOUCH          = 0;
d1 = writeTouch(HEADER_T); //GET add offset	
d1 = writeTouch(0x01);         //number of bytes		
d1 = writeTouch(TOUCH_REGSTART);

waitTouch();
d1   = readTouch();
d2   = readTouch();
pass = readTouch();
d3   = readTouch();
regStart = readTouch();
CS_TOUCH        = 1;

return regStart;
}

//***************************
//Disable Touch screen
//***************************
int touchDisable(void)
{
int d1,d2,d3,d4;
Nop();
__delay32(200000);     //50ms Delay 100000
CS_TOUCH          = 0;  //Active Low
Nop();
__delay32(100);
d1 = writeTouch(HEADER_T); //Disable	
d1 = writeTouch(0x01);  //number of bytes		
d1 = writeTouch(TOUCH_DIS);

waitTouch();
d1 = readTouch();  //0x85
d2 = readTouch();  //data
d3 = readTouch();  //0 if sucsess
d4 = readTouch();
CS_TOUCH          = 1;
__delay32(200000);     //50ms Delay 100000
return d3; // 0 = good
}

//***************************
//Enable touch screen
//***************************
int touchEnable(void)
{
int d1,d2,d3,pass;
Nop();
CS_TOUCH          = 0;  //Active Low
Nop();
CS_TOUCH          = 1;
Nop();
CS_TOUCH          = 0;  //Active Low
d1 = writeTouch(0x55); //	
d1 = writeTouch(0x01);  //number of bytes		
d1 = writeTouch(0x12);
waitTouch();
d1 =   readTouch();
d2 =   readTouch();
pass = readTouch();
d3 =   readTouch();
Nop();
CS_TOUCH          = 1;
__delay32(200000);     //50ms Delay 100000
return pass;
}
//***************************
//Setup touch screen mode
//***************************
int touchsetmode(int offset,int mode,int calib)
{
int d1,d2,d3,pass;
int data = 0;

data = ((mode<<1)|(calib));
CS_TOUCH          = 0;  //Active Low
Nop();
__delay32(100);

d1 = writeTouch(HEADER_T); 
d1 = writeTouch((0x04+0x01)); 	 		// 4 bytes
d1 = writeTouch(TOUCH_WRITE); 		    // 
d1 = writeTouch(0x00);			// Reg high byte = 0x00
d1 = writeTouch(offset + TOUCH_OP_REG);
d1 = writeTouch(0x01);			// Number of Reg to write
d1 = writeTouch(data);          // Mode data

waitTouch();

d1   = readTouch();
d2   = readTouch();
pass = readTouch();
d3   = readTouch();
CS_TOUCH          = 1;
return pass;
}
//***************************
//Touch screen was pressed!  get x/y
//***************************
void  touchPress (void)
{
int pen,xlo,xhi,ylo,yhi;
CS_TOUCH          = 0;
Nop();
pen = readTouch();
xlo  = readTouch();
xhi  = readTouch();
ylo  = readTouch();
yhi  = readTouch();
CS_TOUCH          = 1;

pen = (pen>>7)&0x00FF;
yhi = (((yhi<<7)|ylo)&0x0FFF);  // set it to a 0-1024 type thing
xhi = (((xhi<<7)|xlo)&0x0FFF);
}
 
Last edited:
I2C would be identical... The data sheets says exactly how to send the data.
Send the commands,size of commands. Then wait for IRQ to go high, then read in the data.
The data will be the instructions,size, and a status type thing...
Grab a data sheet from Microchip, it explains it there. Or post some code and we can take a look at what you've done.
 
Hello,
I had problems with this controller because SPI timings are very touchy: you need to wait at least 50us between each byte to let the controller do its own work.
I posted a chronogram on the microchip forum:
Interfacing AR1020 over SPI
(I used a pic18f8722 with a 10MHz oscillator and PLLx4, SPI is clocked with Fosc/64).
 
thaks edman 22, now i can write and read comands, but i have a question, how can i read a data packet, do i need to write a register direction before to read a packet?. in the datasheet only say

send 0x9B,read (pen),read(xlo),read(xhi),read(ylo),read(yhi)

but how the driver know where start it. thanks

READ_TOUCH

CALL S_START
MOVLW B'10011011'
CALL S_BYTE
CALL R_BYTE
CALL R_BYTE
CALL R_BYTE
CALL R_BYTE
CALL R_BYTE
CALL S_STOP
CALL BANK_1
BCF SSPCON2,RCEN
CALL BANK_0
GOTO DESPLEGAR_DATO_X_LOW
 
I think you can read it when ever it is touched, there is no need to send commands. (figure 9 on the data sheet). I think you can just wait for IRQ to go high then send the address, then start clocking in bits from the AR1020.
Just like the format of Figure 8 (I2C operates in slave mode with 7-bit address of 0x9A.)..
So try that and let me know if it works..(don't forget to send it it's address)

I think it just sends the whole data byte in 5 packs(you need to keep reading it ) and you have to then figure out what you want to do with this data in your code. (7.11 Touch Reporting Protocol)
 
thanks edman, it is works, i only send the direction 9a and read the 5 bytes. The code in my last commentary is ok. thanks.
 
Status
Not open for further replies.

Latest threads

New Articles From Microcontroller Tips

Back
Top