Do you think adding on/offf switch on pic12F629 ?
One of the best way is using interruption.
Many developers had made this type of question on the net.
But I have never found any sample source code. Most of all people just give suggestions.
Therefore, I put here my sample source code for other developers.
It was not easy. For example, sw_count variable is from my experience.
Switch part schematics is as follows (Xtal is not mandatory)
(9/21/2016: For long bouncing switch, wait is inserted.)
Hope your help.
— In Japanese
PIC12F629にモーメンタリースイッチを取り付けて、オン、オフしたいと考える人は多いと思う。
ずーっとコーディング例を調べていたけれども具体的なものはなかった。
私の開発したサンプルを置いておく。
以下、前提情報
- まず、PIC12F629の特性に注目する。
PORT3はリセットもしくは入力専用ポートとしてつかわれる。 - PORT3はそのため他のポートと違って、プログラムでプルアップ(抵抗を介して電圧をかける)できない
- ポートの変化による割り込みは、通常はGIEをオンにすると割り込みがかかる
- ポートの変化による割り込みは、SLEEP中はGIEをオンにしなくてもポート変化割り込みの設定をしていれば起きる。この時、割り込みルーチンには飛ばない
- 確認のために記しておくが、GIEをオンにしてSLEEPすると起きてから割り込みルーチンに飛ぶ
/*
*
*/
#include <xc.h>
// #pragma config statements should precede project file includes.
// CONFIG
#pragma config FOSC = HS // (HS oscillator: High speed crystal/resonator on GP4/OSC2/CLKOUT and GP5/OSC1/CLKIN)
#pragma config WDTE = OFF // Watchdog Timer Enable bit (WDT disabled)
#pragma config PWRTE = ON // Power-Up Timer Enable bit (PWRT enabled) DO NOT ON
#pragma config MCLRE = OFF // GP3/MCLR pin function select (GP3/MCLR pin function is digital I/O)
#pragma config BOREN = OFF // Brown-out Detect Enable bit (BOD disabled) DO NOT USE
#pragma config CP = ON // Code Protection bit (Program Memory code protection is enabled)
#pragma config CPD = OFF // Data Code Protection bit (Data memory code protection is disabled)
#define _XTAL_FREQ 10000000
#define BTN GPIO3 // Pic12F629 use this port as MCLR, but I want to use on/off switch.
volatile unsigned int sw_count;
volatile unsigned int req_sleep; // sleep request flag
// main
void main(void){
//Initialization
CMCON = 7; //GPIO use all digital port
TRISIO = 0b00001000; //GPIO port3 is input, others output
IOC = 0b00001000; // port3 interruption enable
GPIO = 0b00000000; //GPIO initialize
GPIE = 1; // INTCON port interrupt enable
INTEDG = 0; // pin down, raise interrupt
GIE = 0;
__delay_ms(500);
LED = 0;
req_sleep = 1;
while(1){
if (req_sleep == 1){
GIE = 0; // After SLEEP, for waking up, you don't need GIE up.
// And if you GIE is off, interruption routine is not inserted.
__delay_ms(400); // wait for chattering
sw_count = 0;
req_sleep = 0; // SLEEP request reset
SLEEP();
NOP();
__delay_ms(300);
GIE = 1; // for switch on detection during running.
}
/*
* here is main work.
*/
}
}
void interrupt ISR(void){
char temp;
GIE = 0;
if (GPIF){
temp = GPIO; // Read for synchronize status.
GPIF = 0; // Once off to protect interruption
sw_count++; // chattering count
if (sw_count >2){ // Tentative value 3
req_sleep = 1; // Enough. DO NOT allow interruption any more
} else {
GIE = 1; // Still allow interruption
}
}
}
If you know better code, please let me know.






