1年前に、遊戯王真デュエルモンスターズ~封印されし記憶~のポケットステーションで強力なカードを入手するためのツール:チートリモコンを製作記事を作成した。
今回は、チートリモコンの設計を見直し、小型で操作性を向上したLite版を製作する。
<初代チートリモコン>
・封印されし記憶を語る
・概要編
・ハードウェア編
・ソフトウェア編①:動作確認
・ソフトウェア編②:キー操作
・ソフトウェア編③:チャタリング対策
・ソフトウェア編④:NECフォーマット
・ソースコード一覧
・入手カード一覧
<チートリモコンLite>
・回路図編
・ソフトウェア編 ←いまここ
・基板実装編
・ソースコード一覧
以下の内容は、ある程度PICやC言語を知っている前提となります。
何をしているのか分からない部分があったら、参考書やwebのPIC入門などを参照してください。
初代で作ったIrREMlib.hとIrREMlib.cは、ピンや周波数、ディレイ時間などの修正が必要なものの流用することができる。
修正は別記事に載せるとして、マイコンが変更になっているためコンフィグファイルを修正し、pic16f1786_config.hという名称で作った。
// PIC16F1786 Configuration Bit Settings // 'C' source line config statements // CONFIG1 #pragma config FOSC = INTOSC // Oscillator Selection (INTOSC oscillator: I/O function on CLKIN pin) #pragma config WDTE = OFF // Watchdog Timer Enable (WDT disabled) #pragma config PWRTE = ON // Power-up Timer Enable (PWRT enabled) #pragma config MCLRE = OFF // MCLR Pin Function Select (MCLR/VPP pin function is digital input) #pragma config CP = OFF // Flash Program Memory Code Protection (Program memory code protection is disabled) #pragma config CPD = OFF // Data Memory Code Protection (Data memory code protection is disabled) #pragma config BOREN = OFF // Brown-out Reset Enable (Brown-out Reset disabled) #pragma config CLKOUTEN = OFF // Clock Out Enable (CLKOUT function is disabled. I/O or oscillator function on the CLKOUT pin) #pragma config IESO = OFF // Internal/External Switchover (Internal/External Switchover mode is disabled) #pragma config FCMEN = OFF // Fail-Safe Clock Monitor Enable (Fail-Safe Clock Monitor is disabled) // CONFIG2 #pragma config WRT = OFF // Flash Memory Self-Write Protection (Write protection off) #pragma config VCAPEN = OFF // Voltage Regulator Capacitor Enable bit (Vcap functionality is disabled on RA6.) #pragma config PLLEN = ON // PLL Enable (4x PLL enabled) #pragma config STVREN = OFF // Stack Overflow/Underflow Reset Enable (Stack Overflow or Underflow will not cause a Reset) #pragma config BORV = LO // Brown-out Reset Voltage Selection (Brown-out Reset Voltage (Vbor), low trip point selected.) #pragma config LPBOR = OFF // Low Power Brown-Out Reset Enable Bit (Low power brown-out is disabled) #pragma config LVP = OFF // Low-Voltage Programming Enable (High-voltage on MCLR/VPP must be used for programming) // #pragma config statements should precede project file includes. // Use project enums instead of #define for ON and OFF. #include <xc.h>
特に必要なのは以下の4つ。
- FOSC:クロックソースの選択、内部発振を使用するためINTOSCにする、こうすることでRA6とRA7がデジタルIOピンとして使用可能になる
- WDTE:ウォッチドッグタイマーのイネーブル、使用しないのでOFF
- MCLRE:MCLRピンの役割設定、リセットとして使用しないのでOFF
- PLLEN:4倍PLLのイネーブル、使用するのでON
次はmain.c。
まずは#includeや#define部分。
#include "xc.h" #include "pic16f1786_config.h" #include "IrREMlib.h" #define _XTAL_FREQ 32000000 // I/O #define CUSTOM ~PORTA #define DATA PORTC #define SEND_SW RB0 #define LED_ON LATB5 = 1; #define LED_OFF LATB5 = 0;
クロック周波数は内臓8MHz×4倍PLLのため、32MHzとなる。
ピンの定義は回路図に合わせて行い、今回はCUSTOMがPORTA、DATAがPORTCに接続されており、PORTAは正論理のロータリースイッチを使っているため反転にした。
次はint main内の変数定義やコンフィグ。
unsigned char nec_custom = 0; unsigned char nec_data = 0; // Clock Config OSCCONbits.IRCF = 0b1110; // 8MHz(x4 = 32MHz) // I/O Port Init ANSELA = 0x00; //全てデジタル ANSELB = 0x00; //全てデジタル TRISA = 0xFF; //全て入力 TRISB = 0xDF; //RB5のみ出力 TRISC = 0xFF; //全て入力 nWPUEN = 0; //内部プルアップ有効化 WPUA = 0xFF; //全て内部プルアップ有り WPUB = 0x01; //RB0のみ内部プルアップ有り WPUC = 0xFF; //全て内部プルアップ有り LED_OFF;
コメントに書いてある通りで、今回は入力ピンに内部プルアップを使用するため、nWPUENやWPUA/B/Cを使用する。
未使用ポートって入力より出力にした方がいいんだっけ?
肝心のmainループは以下のようにした。
while(1){ if(SEND_SW == 0){ nec_custom = CUSTOM; nec_data = DATA; do{ NecSend(nec_custom, nec_data); __delay_ms(40); } while(SEND_SW == 0); } }
たったこれだけで初代チートリモコンのmainループ、keys.hとkeys.cと同等の動作をする。
特にnec_customとnec_dataは、初代ではLCD表示やロータリーエンコーダーによる値の変更、チャタリング対策に桁の変更など複雑なことをしていたが、それがたったの2行まで圧縮された。
前回の記事でも載せたけど、実験中の写真はこんな感じ。
ICSPはブレッドボードに直接接続している。
今回は内部発振を使用しており、初代より誤差が大きいし0.125us単位での動作となるため、ロジアナでタイミング解析を行い、ディレイ時間を調整した。
うまく動作したため、次回の記事で基板実装を行う。