CCS C Software and Maintenance Offers
FAQFAQ   FAQForum Help   FAQOfficial CCS Support   SearchSearch  RegisterRegister 

ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

CCS does not monitor this forum on a regular basis.

Please do not post bug reports on this forum. Send them to support@ccsinfo.com

Touch Sensor - I hope you can help me?!?
Goto page 1, 2  Next
 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
igelkotze



Joined: 15 Dec 2015
Posts: 12

View user's profile Send private message

Touch Sensor - I hope you can help me?!?
PostPosted: Mon Dec 21, 2015 1:26 pm     Reply with quote

Hi!

I'm new to the whole Microcontroller thing. I think I read everything (in this forum) about the Touch functions CCS offers, but I have not found a solution I understood. I am only a Web programmer ;P

First of all here is my code so far.

Code:

//Cap Touch Testing
#include <16f726.h>

#fuses NOWDT,NOPROTECT,MCLR
#use delay (INTERNAL=4M)

#use TOUCHPAD (Range=H,scantime=32ms,threshold=6,PIN_B0='A',PIN_B1='B',PIN_B2='C',PIN_B3='D')

#define LED1 PIN_A0
#define LED2 PIN_A1

void main(){
   char c;
   
   TOUCHPAD_STATE(1);
   enable_interrupts(GLOBAL);

   output_low(LED1);
   output_low(LED2);

   for (;;){

      if (TOUCHPAD_HIT()){
         c=TOUCHPAD_GETC();
         
         switch (c) {
            case 'A':
               output_high(LED1);
               delay_ms(500);            
               break;
            case 'B':
               output_high(LED2);
               break;
            case 'C':
               output_high(LED1);
               output_high(LED2);
               break;
            case 'D':
               output_high(LED1);
               break;

         }
               output_low(LED1);
               output_low(LED2);
      }
   }   
}   


The first question:
I want my touch fields to work like that: the LED should be ON as long as I am pressing the Touch field... is there something similar to output_toggle or output_high that can solve my Problem?

And my second question:
I read something about the possibility to program a multi-touch function by using the test-mode (touchpad_state(2)) and read the values directly from the "touchdata"-array... Is it possible to get a coding-example? It is much easier for me to understand than an explanation. Both would be perfect! Rolling Eyes

Thank for all your help and sorry for my bad English

Clemens Wink
Ttelmah



Joined: 11 Mar 2010
Posts: 19369

View user's profile Send private message

PostPosted: Mon Dec 21, 2015 2:43 pm     Reply with quote

Web programming, and hardware programming are very different things.

The touchpad library using getc, is designed to replicate a keyboard, and avoid having to think about numbers read, etc..

However, you need to access the next layer 'lower'.

If you call 'touchpad_state(2)', the library puts the actual numeric values read from the pins, into the array CTMU_THRESHOLD[x], where 'x' is the number of keys defined in the setup. The number is the value read from the hardware. You have to decide how high you want the number before you accept it.

You can then test for multiple keys at the same time, and continuous 'touch', rather than just 'change'.

Have a look at this thread. As you will see the manual is wrong, but he got a slider working based on using the threshold numbers:

<http://www.ccsinfo.com/forum/viewtopic.php?t=52358&highlight=touchpad>

Also note they are int8, not int16...
asmboy



Joined: 20 Nov 2007
Posts: 2128
Location: albany ny

View user's profile Send private message AIM Address

PostPosted: Mon Dec 21, 2015 6:18 pm     Reply with quote

Are you able to test your code with an actual pic and a circuit,
or is this for emulation/simulation?
igelkotze



Joined: 15 Dec 2015
Posts: 12

View user's profile Send private message

PostPosted: Tue Dec 22, 2015 2:01 am     Reply with quote

Hi Ttelmah and asmboy!

Yeah... At first it looked similar to PHP... but that was totaly wrong Very Happy

Ok... lets see if i got that Wink
The code till "void main" stays the same:
Code:

//Cap Touch Testing
#include <16f726.h>

#fuses NOWDT,NOPROTECT,MCLR
#use delay (INTERNAL=4M)

#use TOUCHPAD (Range=H,scantime=32ms,threshold=6,PIN_B0='A',PIN_B1='B',PIN_B2='C',PIN_B3='D')

#define LED1 PIN_A0
#define LED2 PIN_A1


In my "Void main" i just have to call the Touchpad_State(2); and set the LEDs to output_low (like before).

Am I right, that CTMU_Treshold [0] would be my Pad A, CTMU_Treshold[1] would be my Pad B and so on?

If this is correct i just have to write something like this in my main function?
Code:

if (CTMU_TRESHOLD[0] > 600){
      output_high(LED1);
}else{
      output_low(LED1);
}



So the first thing i need to know is the "standard" capacitiy of each pad.
Is there any stored standard value that i can use to calculate my threshold (like before %)

@ asmboy

Yeah i have real hardware... The PIC i am using is the 16f726... an the programmer is the DIAMEX PIC PROGAMMER (PIC KIT 2).

Thank you for your help!
Clemens
Ttelmah



Joined: 11 Mar 2010
Posts: 19369

View user's profile Send private message

PostPosted: Tue Dec 22, 2015 2:29 am     Reply with quote

Now, 'no guarantees' on this. I haven't got one of those chips to test at present, or anything else setup to use the CTMU.

However comments:
At the end of the thread I pointed to earlier, the poster said that CCS would fix the array name in the next release. A quick look at the symbol file, says they have done this. So I'm using the array name from the manual.

This duplicates your existing code, except that the LED's should remain on while the pad is held, and if both pad a, and pad b are touched together, the first LED should toggle (to show a 'double key' detection). Also since the scanning is sequential other than this, if you held pad a and pad c, both LED's would come on.

As I say, 'no guarantees', but this is where I would be starting:
Code:

#include <16f726.h>

#fuses NOWDT,NOPROTECT,MCLR
#use delay (INTERNAL=4M)

#use TOUCHPAD (Range=H,scantime=32ms,threshold=6,PIN_B0='A',PIN_B1='B',PIN_B2='C',PIN_B3='D')
#define KEYS 4
int16 touch_init[KEYS]; //global array for initial state
#define THRESHOLD 6 //threshold for the raw data

#define LED1 PIN_A0
#define LED2 PIN_A1
#define KEYA 0
#define KEYB 1
#define KEYC 2
#define KEYD 3 //defines for the key positions in the data array

int16 change(int8 keyno)
{
   //routine to return the change value from the selected key number
   if (TOUCHDATA[keyno]<touch_init[keyno])
   {
      touch_init[keyno]=TOUCHDATA[keyno];
      return 0;
   } //handle error that capacitance has dropped since initialisation
   return TOUCHDATA[keyno]-touch_init[keyno]; //return change value
}
#define KEYON(keyno) change(keyno)>THRESHOLD

void main(void)
{
   int8 ctr;
   int1 flag=FALSE;

   
   TOUCHPAD_STATE(1);
   enable_interrupts(GLOBAL);
   delay_ms(300);
   //now store the initial values
   for (ctr=0;ctr<KEYS;ctr++)
      touch_init[ctr]=TOUCHDATA[ctr];

   output_low(LED1);
   output_low(LED2);

   for (;;)
   {
      delay_ms(32); //allow touch to rescan
      flag=FALSE; //flag for a key being seen
      if (KEYON(KEYA))
      {
         //now check a second key here
         if (KEYON(KEYB))
         {
            output_toggle(LED1);
            continue; //no further checking for the double key
         }
         output_high(LED1);
         flag=TRUE; //a key has been seen
      }
      if (KEYON(KEYB))
      {
         output_high(LED2);
         flag=TRUE;
      }
      if (KEYON(KEYC))
      {
         output_high(LED1);
         output_high(LED2);
         flag=TRUE;
      }
      if (KEYON(KEYD))
      {
         output_high(LED1);
         flag=TRUE;
      }
      if (flag==FALSE)
      {
         //here no key is pressed
         output_low(LED1);
         output_low(LED2);
      }
   }   
}   


There is also a TOUCPADSTATUS variable, which should (I think), contain bits corresponding to whether a key is pressed. If I'm right on this (haven't got time to disassemble the listing and see if this is right), then instead one could use:
Code:

#define KEYON(keyno) bit_test(TOUCHPADSTATUS,keyno)
igelkotze



Joined: 15 Dec 2015
Posts: 12

View user's profile Send private message

PostPosted: Tue Dec 22, 2015 3:33 am     Reply with quote

Hi Ttelmah!

All i can say is WWOOWW!!
I think it will take some time to understand that! Wink

Please tell me if i am right:

The "new" threshold you are using in this code is not a precentage limit, am i right?

Code:
#define THRESHOLD 6 //threshold for the raw data


You used it here:
Code:
int16 change(int8 keyno)
{
   //routine to return the change value from the selected key number
   if (TOUCHDATA[keyno]<touch_init[keyno])
   {
      touch_init[keyno]=TOUCHDATA[keyno];
      return 0;
   } //handle error that capacitance has dropped since initialisation
   return TOUCHDATA[keyno]-touch_init[keyno]; //return change value
}
#define KEYON(keyno) change(keyno)>THRESHOLD


This means if the difference between the stored "standard-value" and the current value of the button pressed is bigger than 6 (not 6%) KEYNO stores the Keynumber pressed... am i right?

Thank you for your help!... I can hardly wait for testing this... after work in 6 hours Rolling Eyes

Thank you!
Clemens
Ttelmah



Joined: 11 Mar 2010
Posts: 19369

View user's profile Send private message

PostPosted: Tue Dec 22, 2015 4:23 am     Reply with quote

It's 'counts' on the CTMU value returned.

The raw array, returns the numeric values physically read from the CTMU (or CSM) peripheral, for each connection. So if these rise by more than 'THRESHOLD' from the initial values read, I'm treating this as a 'pressed' action. These should be updated every 'scantime' (done by a timer interrupt), so there is no point in re-trying more frequently than this (hence the delay in the loop). Now how CCS actually scale the values returned I don't know, without dismantling what they do, so 'experiment' will definitely be needed!...

Very Happy
igelkotze



Joined: 15 Dec 2015
Posts: 12

View user's profile Send private message

PostPosted: Tue Dec 22, 2015 1:29 pm     Reply with quote

OK... So far so good...

I tried it... and you were right. The version with Touchpadstatus worked, the other one didnt worked at all... but the problem is that the LED's go on, but they doesnt go off... is it possible that there is someting worng with the flags?

An other Problem is that if i am pressing pad-D LED1 and LED2 are going on...

I tried the following:
Code:
if (KEYON(KEYA))
      {
         output_toggle(LED1);
         flag=TRUE; //a key has been seen
      }

If i am touching Key A the led starts blinking rapidly! And the funny thing is if i am pressing Key D the LED1 blinks and LED 2 is just on!

Is it a problem that i am using the compiler version 4.140...?

Thank you!
Clemens
Ttelmah



Joined: 11 Mar 2010
Posts: 19369

View user's profile Send private message

PostPosted: Tue Dec 22, 2015 3:45 pm     Reply with quote

Try increasing the threshold in the #use touchpad line.

It's behaving as if it is still seeing one of the pads being touched. 6 is quite a low threshold. Something like 20 is more typical to be needed.

The LED's will only clear if all the pads are seen as 'off'.

Simplify it to just access (say) two pads.
Then you can have one LED for each pad.
Will make debugging easier. Then add a third etc..
igelkotze



Joined: 15 Dec 2015
Posts: 12

View user's profile Send private message

PostPosted: Tue Dec 22, 2015 3:58 pm     Reply with quote

No... doesnt change anything... Sad

Is it possible that there is a wrong value for the untouched value stored? So if i pressed the button the "pressed"-value becomes the new unpressed-value?

Thanks
Ttelmah



Joined: 11 Mar 2010
Posts: 19369

View user's profile Send private message

PostPosted: Wed Dec 23, 2015 4:43 am     Reply with quote

The 'untouched' value is stored by the CCS code, when you call touchpad_state(1). That is what this does. So as simplified test code:

Code:

#include <16f726.h>

#fuses NOWDT,NOPROTECT,MCLR
#use delay (INTERNAL=4M)

#use TOUCHPAD (Range=H,scantime=32ms,threshold=16,PIN_B0='A',PIN_B1='B',PIN_B2='C',PIN_B3='D')

#define LED1 PIN_A0
#define LED2 PIN_A1
#define KEYA 0
#define KEYB 1
#define KEYC 2
#define KEYD 3 //defines for the key positions in the data array

#define KEYON(keyno) bit_test(TOUCHPADSTATUS,keyno)

void main(void)
{
   int8 ctr;
   enable_interrupts(GLOBAL);
   delay_ms(300);
   //Allow time for the touchpad code to have scanned the pads
   TOUCHPAD_STATE(1); //This 'calibrates' the touchpad
   //The touchpad needs to be running _before_ you call this

   output_low(LED1);
   output_low(LED2);
   //now simplified code to just turn each LED on/off for a touchpad

   for (;;)
   {
      delay_ms(32); //allow touch to rescan
      if (KEYON(KEYA))
         output_high(LED1);
      else
         output_low(LED1);

      if (KEYON(KEYB))
         output_high(LED2);
      else
         output_low(LED2);
   }   
}   
igelkotze



Joined: 15 Dec 2015
Posts: 12

View user's profile Send private message

PostPosted: Wed Dec 23, 2015 4:57 am     Reply with quote

I am studying your code for hours now... but i don't understand two thing... maybe three Wink

Can you tell me what the line does exactly?
Code:
#define KEYON(keyno) bit_test (TOUCHPADSTATUS, keyno)

What is behind TOUCHPADSTATUS?

My next question is why are you calculating the difference between the current reading of the Pad (=i think this is TOUCHDATA) and the stored Value (Touch_init)? Where do you use the value?

In this If-query you say that if the current reading is smaller than the stored one, the current reading is equal to the stored one and returns 0... I don't understand why you are setting them equal?

I just saw you wrote a simplified test code... I'll try that!
Is keyno a variable that is already in the CCS code??

Thank you!
Ttelmah



Joined: 11 Mar 2010
Posts: 19369

View user's profile Send private message

PostPosted: Wed Dec 23, 2015 8:30 am     Reply with quote

You said that the delta version did not work. So I don't use the delta values. They are removed in this code.

TOUCHPADSTATUS is a bit array created by the compiler, with 1's for every pad that has a value 'threshold' above it's calibration value.

There are two arrays created for you. TOUCHDATA, which is an int16 array, and TOUCHPADSTATUS. The former contains the raw data (in my original code I was using this and looking for the actual value to change), and the status array which contains the 'I am touched' status for each pad. You said the status version was working, so I have used this. There have been numerous changes since the touchpad functions were added, and I was not sure whether your compiler was supporting these.
igelkotze



Joined: 15 Dec 2015
Posts: 12

View user's profile Send private message

PostPosted: Wed Dec 23, 2015 11:22 am     Reply with quote

Hmm... They are still always "on" if i touch the pad... the only difference is that just the right one is on, the other one is off. With the last code they were always on...

Do you have any further ideas??

Thank you
asmboy



Joined: 20 Nov 2007
Posts: 2128
Location: albany ny

View user's profile Send private message AIM Address

PostPosted: Wed Dec 23, 2015 11:36 am     Reply with quote

Can you post the circuit schematic you are using so a hardware issue might be dismissed ?
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Goto page 1, 2  Next
Page 1 of 2

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group