Vol.890 8.Mar.2024

デジタルバッテリーチェッカー 確定申告で医療費控除 PICミニBBシリーズ(1)4x3キー

B デジタルバッテリーチェッカー

by fjk

 電池の残容量チェックにアナログで「使える・使えない」と表示される物を使っていたが、使用する電気製品によっては、使えないと表示されていてもまだ使える物もある。
 そこで、テスターを使って電池の残電圧を測っているが、測定の都度、ケーブルを接続し、プローブを電池の端子に当てているのが面倒である。
 と、思っていたところ、百均のキャンドゥで「デジタルバッテリーチェッカ」(330円)を見つけ、入手した。
 形状は同型アナログの物と同じだが、どれくらいの電池容量が残っているのか、具体的に電圧をデジタルで確認できる。単1〜単5型電池用で、充電式電池には使用できないと書かれているが、電圧が低いニッカド電池やニッケル水素電池(1.2V)であれば測定できる。間違っても電圧が高いボタン電池(3V)やリチウム電池(3.3V)には使用しないこと。


乾電池を測ってみると


E 確定申告で医療費控除

by fjk

 確定申告で「医療費控除は10万円を超える分」で、今まで支払金額が10万円を超えることはなかった。しかし、昨年は入院したので医療費が10万円を超えており、医療費控除について調べて見た。
 控除の対象となる医療費は国税庁で紹介されているが、簡単に主なものを纏めると、

 ※条件があるものもあるので、控除申請時には確認すること(下記も参照)。

★ e-TAXで医療費控除を申請するには以下の方法がある
   [詳細は、国税庁

@ 医療費通知(xmlデータ)を利用して入力する
医療保険者から交付された「医療費通知データ」を利用する方法で、データも一緒に送信。
医療通知にない医療費は別途入力する必要あり)
A 医療費通知(書面)を利用して入力する
医療保険者から交付された「医療費通知データ」の合計額を入力。
q (医療通知にない医療費は別途入力する必要あり)
B 医療費の領収書から入力する
支払った医療費の内容を1件ずつ入力。領収書が多い場合、「医療を受けた方の氏名」「病院・薬局などの支払先の名称」毎にまとめて入力も可。
C 医療費集計フォームを読み込む
入力データが多い場合、「医療費集計フォーム」(xmlファイル)をダウンロード後、表計算ソフトで入力し、申告書とともにe-Taxで送信。
D 医療費の合計額のみ入力する
別途、自身で作成した「医療費控除の明細書」を元に、「支払った医療費の合計額」や「生命保険や社会保険などで補填される金額」の合計額のみ入力。この場合、e-Taxでは「医療費の明細書」を作成できないので、別途、書面で「医療費に明細書」を提出する必要がある。

【注】いずれの場合も、領収書などの必要な書類を5年間は保管する義務があります。
★ 右のページも参考になる。 <税金の知恵袋>


P PICミニBBシリーズ(1)   〜I2C接続4x3キーユニット

by fjk

 abc889で、PIC用の汎用で使えるLCD表示ユニットをミニブレッドボード(BB-601)で作成した。そこで、同じように「I2C接続4x3キー」ユニットも作ってみることにした。ユニット間の接続はフラットケーブルもしくは、L型ソケット+L型ピンヘッダー(標準のピンヘッダーはピン長さが短いので、「連結ピンヘッダ(秋月電子 102959)」を加工)を使用した。L型コネクターへの曲げ加工方法は以下、

バイスに鉄板とピンを鋏み一気に曲げる
(ピンは少し隙間を空けてセット)

ピンヘッダーはソケットに刺して曲げる
(ピンヘッダーは強度が弱いので)

●● ハードウェア ●●
【PIC-BASE14】 (回路・MCC設定の詳細についてはabc887を参照)
 14ピンPICの汎用マイクロコントローラユニット(PIC-BASE14)として、ミニブレッドボードBB-601(秋月電子、105155、150円)で作成した。ユニットはPIC16F18xx系の14ピンPICが使えるものとし、(PPS使用を含め)ピン配置が同じPIC16F15xxやPIC16F17xxも利用可能である。
 回路は、基本的にはabc887とほぼ同じだが、LEDとプッシュスイッチを各1個搭載(他のものに置き換え可)。チップの右側に、Vcc,Gnd,I2C,SPIなどに使用するピンが取り出せるようにした。

  • 14ピンPIC搭載ユニットで、シリアル(USB)、I2C、SPIインターフェースを備える
  • PIC-BASE14で使用可能なPICは、PIC16F1823/4/5、PIC16F18323/4/5/6、PIC16F18424/5/6、およびピン互換PIC(PIC16F1503、PIC16F15325,PIC16F1705,PIC16F1765など)

PIC-BASE14回路図
 

BB-601で作成したPICユニット
(abc889のLCDユニットと接続した例)

【PIC-4x3_Key】 (回路・MCCの設定の詳細はabc858を参照)
 キーユニットは「4x3キーパッド作成キット用基板」(秋月電子、112316、105円)にタクトスイッチを並べた。キーパッド基板が大きいのでブレッドボードとしてEIC-301(秋月電子、100313、300円)を用いた。

  • 4x3マトリクスプッシュキーユニットで、インタフェースはシリアル(USB)、I2C(スレーブ)
  • I2Cスレーブ用のPICはPPSを利用したいのでPIC16F18325を使った。
  • キーマトリクスとBBの接続には、基板内に納めるため8ピンのピンヘッダーとソケットを使い、接続ピンの位置がBBの中心部になるようにした。
  • USBシリアル接続も可能だが、基本的にはUSBとI2Cの同時使用はできない。しかし、USB電源の(赤い)ジャンパー線を外すことで同時使用も可能。。

PIC-4x3_Key回路図

EIC-301で作成したキーユニット
※4x3キーパッドはM3(L=20mm)ビスとM3用プラスチックスペーサー(H=6mm)でEIC-301に固定。

【ユニット組み合わせ応用例】
 PIC-BASE14、PIC-4x3_Key、および前報(abc889)で作成したLCD表示ユニット(PIC-LCD16x2)を接続し、キー入力があれば、LCDにキー入力データを表示し、さらにUSBシリアルでパソコンに送信を行う(キーユニットのUSBは使用していない)。I2CはPIC-LCD16x2ユニットからPIC-4x3_Keyユニットに接続している(手持ちに4ピンソケットがなかったので5ピンソケットを利用)。


●● ソフトウェア ●●
【PIC-Base14】
 PICはPIC16F18325使用し、LCD表示するためi2cLCD_ST7032i.c/.h(zip)ライブラリも利用。
 MCCでは、EUSART(USB)、I2C、A2はinput、A4はoutputに設定。さらにSCK、SDA、A2はWPUでプルアップ指定。なお、eusart.cおよびeusart.h のプログラムの詳細はabc889を参照。
 当初、「C言語&MCCによるPICプログラミング大全」(技術評論社、後閑哲也著)を参考に、MCCでgenarateした関数の利用を試みたが、何故か正常に動作しなかった(要検討)。
 そこで、abc842を参考に、I2Cマスター通信プログラムを作成した。。


MCC画面 (マスターピン設定)

MSSP1設定

EUSART1設定
★プログラム abc890_master.c(zip)(修正済)
※"stdlib.h"のインクルードが抜けていました(3/14追加)
/*************************************************
 *  キーデータ(I2C)取得プログラム
 *   LCD(ACM1602)+I2C Slave key
 ************************************************/
#include "mcc_generated_files/mcc.h"
#include "i2cLCD_ST7032i.h"
#include "stdlib.h"

//#define 	BFSIZE  20            //EUSART.Hで宣言
#define 	SLVADR  0x40

uint8_t 	iBuf[8];
uint8_t		rBuf[BFSIZE];
uint8_t		sBuf[BFSIZE];
uint8_t 	sFlg;

/*------    メイン関数  -----*/
void main(void)
{
    uint16_t key = 0;
    uint16_t keyLate = 0;
    uint16_t rDt;

    SYSTEM_Initialize();
    LCD_init();                 // LCD初期化

    INTERRUPT_GlobalInterruptEnable();
    INTERRUPT_PeripheralInterruptEnable();

    puts("***ready\r");
    LCD_str(">- ready");
    IO_RA4_SetHigh();
    
    while (1) {
        if(sFlg){
            LCD_clr();
            LCD_str(rBuf);
            rDt = atoi(rBuf);
            //--- スレーブへ送信
            if(rDt % 2){
              I2C1_Write1ByteRegister(SLVADR,0,'H');
              puts("> H\r" );
            }else{
              I2C1_Write1ByteRegister(SLVADR,0,'L');
              puts("> L\r");
            }
            sFlg = 0;
        }         
            //---   スレーブから受信
        I2C1_ReadNBytes(SLVADR, &key, 2);
        if(key){
            if(key != keyLate){
                sprintf(sBuf, "%04X\n\r", key);
                LCD_cursor(0,1);
                LCD_str(sBuf);
                puts(sBuf);
                keyLate = key;
            }
        }else{
            keyLate = key;
        }
    }
}

【PIC-4x3_Key】
 I2C-slaveのソフトは「C言語&MCCによるPICプログラミング大全」を参考に少しアレンジした。
 インターフェースはUSBシリアルとI2Cがあるが、5V供給電源がぶつかるので同時使用はできない。USB接続は、キーが押されるたびに、(keyDatデータ送信をコメントにすると)パソコンに1文字を送信する。I2C接続は、(割り込みで)送信要求があれば、現在のキー状態を送信する。
 なお、LEDは使用していない(受信したデータは読み捨て)。

<送信データ>
@ USB(USARTt)(1文字ずつ送信)
'0'〜'9'、'.'、'\n' (テンキー配列時)、または、'0'〜'9'、'*'、'#' (電話機配列時)の12文字
A I2C (2バイト16ビット。キーマトリクスデータで複数キーの同時押し込みも確認できる)
上位12ビット(x)は押されているキーマトリクス情報(押されているビットが1)
下位4ビットは押されているキーで最初のキー位置データ(d、1〜12)
  {xxxx xxxx xxxx dddd} ・・・(キーが押されていなければ、16ビットデータは0)

MCC画面 (スレーブピン設定)

MSSP1設定

EUSART1設定
★プログラム abc890_slave.c(zip)(修正済み)
※ハンドラの設定部分が抜けていました(3/12追加)
/********************************
 *  keyデータ送信(I2Cスレーブ)
 *  Slave Address = 0x40
 ********************************/
#include "mcc_generated_files/mcc.h"
#define	SCN_DELAY() __delay_ms(30)
#define	KEY_DELAY() __delay_ms(500)

uint8_t  wState;         	// I2C書込みステート番号
uint8_t  rState;          	// I2C読込ステート番号
uint16_t rDat;            	// I2C受信16ビットデータ
uint8_t  keyStat;          	// キー入力状態
uint16_t keyM;            	// キーマトリクスデータ
uint8_t  keyP;            	// キーデータ(1−12)
uint16_t keyDat;			// マトリクス+データ
uint8_t  k[] = {'0','1','4','7',
                '.','2','5','8',
               '\r','3','6','9'}; 	// テンキー配列
/*
uint8_t  k[] = {'*','7','4','1',
                '0','8','5','2',
                '#','9','6','3'};	// 電話機配列  
*/
/*****  I2C Read Callback  ****************/
void I2C1_ReadProcess(void) {
    switch (rState) {           // ステートで進む
        case 0:
            rDat = (uint16_t)I2C1_Read();
            rState++;          // 1byte目読込、次へ
            break;
        case 1:
            rDat |= (uint16_t)I2C1_Read() << 8;
            rState = 0;       	// 2byte目読込、最初に
            break;
        default:
            break;
    }
}

/*****  I2C Write Callback *****************/
void I2C1_WriteProcess(void) {
    switch (wState) {
        case 0:
            I2C1_Write((uint8_t)keyDat);
            wState++;		// keyDatの下位送信、次へ
            break;
        case 1:
            I2C1_Write(keyDat >> 8);
            wState++;		// keyDatの上位送信、次へ
            break;
        case 2:              	// 送信完了
            wState = 0;     	// 最初に戻る
            break;
        default:
            break;
    }
}
/**** キースキャン ******/
uint16_t keyScan(){
    uint8_t kt;
    uint16_t kyw;
    X_A0_SetLow();			// X scan
    SCN_DELAY();
    kyw = ~PORTC & 0x0F;
    X_A0_SetHigh();
    Y_A1_SetLow();			// Y scan
    SCN_DELAY();
    kt = ~PORTC & 0x0F;
    kyw |= (uint16_t)kt << 4;
    Y_A1_SetHigh();
    Z_A2_SetLow();			// Z scan
    SCN_DELAY();
    kt = ~PORTC & 0x0F;
    kyw |= (uint16_t)kt << 8;
    Z_A2_SetHigh();    
    return kyw; 
}
uint8_t bitCount(uint16_t w){
    uint16_t wsft = 1;
    uint8_t i;
    for (i = 1; i < 13; i++){
        if(w & wsft)   return i;
        wsft <<= 1;
    }
    return 0;
}
/***** メイン関数 ***************/
void main(void) {
    SYSTEM_Initialize();
    I2C1_Open();    			// I2C1初期化

    I2C1_SlaveSetReadIntHandler(I2C1_ReadProcess);
    I2C1_SlaveSetWriteIntHandler(I2C1_WriteProcess);

    INTERRUPT_GlobalInterruptEnable();
    INTERRUPT_PeripheralInterruptEnable();
    X_A0_SetHigh();  			// キーピン初期化
    Y_A1_SetHigh();
    Z_A2_SetHigh();
    puts("*** Ready ***\n\r");
    while (1){
        keyM = keyScan();
        if(keyM){
            keyP = bitCount(keyM);
            keyDat = (keyM << 4)+(keyP & 0x0F);
            if(keyStat == 0){
                putch(k[keyP - 1]);
                printf(" %04XH\n\r",keyDat);
            }
            keyStat = 1;
            KEY_DELAY();
        }else{
            keyDat = 0;
            keyStat = 0;
        }
    }
}

【実行例】
 スレーブの4x3キーを押すと、マスターがそのデータを読取り、パソコンのテラターム端末に押された16ビットのキー情報を表示することができた。

  • マスターでリアルタイムキーデータを利用する時は、常時受信している 変数key が使える。
  • キー位置とデータの変換は、slaveの配列によるキーデータ変換を参照。

キー入力実行例(4x3キーデータ表示)

テラターム画面(I2C送受信表示例)


※ 本レポートの参考・利用は、あくまでも自己責任でお願いします。


デジタルバッテリーチェッカー 確定申告で医療費控除 PICミニBBシリーズ(1)4x3キー