Vol.951 18.Sep.2026

和欧文間空白を解除 パーテションMiniTool CLB)ADC利用の電圧計

I 一太郎で「和欧文間空白」を部分的に解除

by fjk

 一太郎には、和文と欧文(数値等を含む)が混在する場合、和文と欧文の文字の間に空白を自動で挿入し、見やすくしてくれる機能があります(「文書スタイル(F9)/体裁/和欧文間スペース」で設定)。
 しかし、この機能を有効にしていると、「470 Ω」など数値と単位の間が空きすぎることがあります。
 この様なとき、編集画面の右側に並ぶ基本編集パレットの「調整パレット」を利用すると、視覚的に確認しながら文字間隔の調整ができます。

・調整した例: 「470Ω
 
   0からΩを範囲選択し、
  「字間狭く」アイコン(赤丸)
  を何度かクリック
 
        調整パレット→

 基本編集パレットには、「調整」以外にも「フォント・飾り」など便利な機能が揃っており、文字修飾や見栄えに関する設定がほとんどできるので、編集時は常にONにしておくのが良い。


M パーテションMiniTool

by fjk

 abc950ではハードディスクやUSBメモリ等の低レベルフォーマットができるツールを紹介しましたが、MiniTool Partition Wizardはパーテションサイズの変更などを行いたい時のツールです。
 同ソフトには、無料版(Free)と有料版(Pro)があり、無料版は個人ユーザー向けのパーティション管理ソフトです。なお、動作環境はWindows11/10/8.1/8/7。
   紹 介: tekunotes
   入 手: minitool

<無料版(Free)の主な機能>

・パーティション管理:
新規作成/サイズ変更/移動/結合/分割/フォーマット/削除/データ抹消/など
・パーティション変換:
MBR/GPTの相互変換、パーティションの相互変換、FATからNTFSへ変換
・パーティション診断:
ファイルシステムのエラー修正、不良セクター診断、ディスク使用状況分析

<有料版(Pro)との違い>

・OSのクローン作製:
ProはOSを丸ごと別ドライブにコピーできる(Freeはデータのみ)
・データ復元ができない:
Proは削除したデータなどの復元ができる(Freeは検索のみ)
・高度フォーマット変換:
ProはNTFSからFATへの変換ができる(FreeはFAT→NTFSのみ)

同社のソフトとして、以下のものもあります。

・バックアップソフト:
MiniTool Shadow Free
・データー復元ソフト:
MiniTool Power Data Recovery


P PIC16F13145 (8)   〜7segLEDの応用(ADC利用の電圧計)

by fjk

 abc950まで、小数点付数値を2桁7セグメントLEDで表示できるようになったので、PICのADC入力を利用し、簡単な電圧計を作ってみる。
 なお、電圧データの小数点は固定で、データ確認のためUSBシリアルでパソコンにもデータを送信

【ハード】
「abc950のおまけ」回路(小数点付2桁7segLEDとVR付)をそのまま使用
 
【ソフト】
RA2に接続したVRを回すと、ADCにより電圧を10ビットデータとして取得し、そのデータを電圧値に変換、さらにBCD変換後、2桁7セグメントLEDに表示(小数点表示あり)する。
また、USBシリアル端末から数値データを送信すると、下2桁の数値をBCD値として2桁7セグメントLEDに2秒間だけ表示(小数点表示なし)する。
 
<使用するMCCデバイス>
・Clock:
HFINTOSC=32MHz、Divider=1
・UART1:
abc945と同じ。speed=115200bps、割込有り(Driver名がUARTなので注意)
・TMR0:
abc950と同じ。period =8mS
・CLB1:
abc950と同じ。abc950-7seg2B-DM.clbを利用
・CLC:
abc950と同じ(jk-FF使用)
・ADC:
下記「ADCの設定」を参照

MCC:System (clock=32MHz)、TMR0 (Period=8mS)
<ADCの設定> (下記条件以外はdefaultのまま)
hardwareSetting
ResultAlignment:
right (右詰め)
Positive input Channel:
ANA2(PinGrid、Pinsで確認)
PositivVoltageReference:
VDD(上限は5V)
ComputerationSettings
Computation Mode:
Basic_mode
ADC Clock Setting
Clock Source:
FOSC
Clock Divider:
FOSC/32 (1MHz= 1μs)
CVD Settinng:       (CVDを使用しない)
Interrupt Settings:    (割込を使用しない)
Analog Channels:     (ADCのグループ化をしない)

ADC設定
<ADCデータ(aDat)を最大5Vの電圧データ(vVal)に変換>
・2桁BCD用:
vVal = aDat × 50 / 1023 (vValの最大値が50)
・3桁BCD用:
vVal = aDat × 500 / 1023 (vValの最大値が500)
・4桁BCD用:
vVal = aDat × 5000 / 1023 (vValの最大値が5000)

浮動小数点演算を使用してもよいが、符号無し32bit整数に変換して、32bit整数演算。
uint16_t vVal = (uint16_t)((uint32_t)aDat * 500UL / 1023UL); // 3桁の場合

ただし、10bit2進数から2桁BCDなら16bit計算で桁溢れしないので、下記演算(切捨)が可能
uint16_t vVal = (uint16_t)(aDat * 50 / 1023);  // 1,023×50=51,150 < 65,536
 
<バイナリーデータをBCDへ変換>
 vValデータは2進数なので、7segLEDに表示するにはBCDに変換する必要がある。
 BCDへの変換方法は多数あるが、XC8に標準実装されている以下の div() 関数を使うのが便利そう
div_t div (int numer, int denom)

なお、div_t はstdlib.hで以下のように定義されている
  typedef struct{
     int quot;          // quotient(商)
     int rem;           // remainder(余り)
  } div_t;
最大4桁(9999)のBCDを得る関数の例
  #include <stdio.h>
  #include <stdlib.h>

  uint16_t bin2bcd(int d) {                 // 9999まで(下4桁のみ有効)
      div_t qr;
      int   i, bcd = 0;
      for (i = 0; i < 4; ++i, d = qr.quot) {
          qr = div(d, 10);                  // 商と余りを得る
          bcd += qr.rem << (i * 4);         // 余りをi桁分を左シフトして加算
      }
      return (uint16_t)bcd;
  }

【テスト結果とトラブル】
 AD変換データはVRを回すと0.0−5.0Vで表示され、シリアル入力も指示した数値をチャンと表示した。
 しかし、シリアル出力(Tx)がUSBターミナルに表示されない(RA5から信号が出ていない[RA4に変更しても同じ])。
 そこで、Tx端子をRB6に変更してみたところ、正常にシリアル送信できた(abc945ではRA4を使っても問題なかったのに・・)


UART配線を変更(Tx=RB6)

ADCデータ(電圧)を表示中

abc951-13145.c(zip)

/******************************(abc951-13145.c)******
 *  ADCデータを電圧に変換後7segに表示
 *--------------------------------------------------*/

#include <stdio.h>
#include <stdlib.h>
#include "mcc_generated_files/system/system.h"

//=====  シリアル関係 ================
#define  EU_BFSIZE   80

char     RBuf[EU_BFSIZE];                       // 受信データバッファ
uint8_t  EU_Flg = 0;                            // 受信フラグ

//-----  シリアル受信割り込み関数
void myEusart(void) {
    static uint8_t sIdx = 0;                    // 受信データポインタ
    char     ch;                                // 受信文字

    if(EUSART1_IsRxReady()){                    // 受信データ有り?
        ch = EUSART1_Read();                    // データ受信
        EUSART1_Write(ch);                      // エコーバック
        if((ch == 0x0a)||(ch == 0x0d)){         // 改行処理
            RBuf[sIdx] = 0;                     // 文字列終端文字
            sIdx = 0;                           // ポインタを初期化
            EU_Flg = 1;                         // 受信フラグON
        }else if((ch == 0x08)&&(sIdx > 0)){     // BS処理
            sIdx--;
        }else{                                  // 上記以外の文字
            if(sIdx < EU_BFSIZE){               // バッファサイズ以内?
                RBuf[sIdx++] = ch;              // バッファにデータ格納
            }
        }
    }
}

//----- 文字列シリアル出力(改行なし)
void EU_print(char * msg) {
    while(*msg != 0)  {
        while(!EUSART1_IsTxReady())
            ;                                   // データ送信済確認
        EUSART1_Write(*msg++);                  // 1文字送信
    }
}

//----- 文字列シリアル出力(改行付き)
void EU_puts(char *msg) {
    EU_print( msg );
    EU_print("\n");
}

//=====  4桁BCD変換関数 ==============
uint16_t bin2bcd(int d) {                       // 最大9999(下位4桁)
    div_t    qr;
    int   i, bcd = 0;
    for (i = 0; i < 4; ++i, d = qr.quot) {
        qr = div(d, 10);                        // 商・余りを得る
        bcd += qr.rem << (i * 4);               // i 桁分左シフト後、加算  
    }
    return (uint16_t)bcd;
}

//=========  main  ===================
int main(void) {
    uint16_t aDat;                              // ADCデータ
    uint16_t vVal;                              // 電圧データ
    uint16_t dat;                               // 2進数データ
    uint16_t bcd;                               // 4桁BCD数
    char     sBf[20];                           // 出力文字列

    SYSTEM_Initialize();                        // 初期化
    EUSART1_RxCompleteCallbackRegister(myEusart);
                                                // 割り込みハンドラー設定 
    INTERRUPT_GlobalInterruptEnable();          // 割り込み許可
    INTERRUPT_PeripheralInterruptEnable();

    EU_puts("== Test ADC & 7seg ==");
    ADC_ConversionStart();                      // ADC変換開始

    while(1)  { 
        //---- USB Serial -----------
        if(EU_Flg){                             // 受信データ有?
            EU_Flg = 0;                         // 受信フラグクリア
            dat = (uint16_t)atoi(RBuf);         // 受信文字列を数値に
            bcd = bin2bcd((int)dat);            // 4桁bcdに変換
            sprintf(sBf, "%d -> %x", dat,bcd);  // 表示文字列へ
            EU_puts(sBf);                       // シリアル送信
            CLB1_SWIN_Write16(bcd);             // 7seg表示
            __delay_ms(2000);                   // 2秒間表示
        }
        //---- ADC -------------------
        if(ADC_IsConversionDone()){             // ADC変換が終了?
            aDat = (uint16_t)ADC_ConversionResultGet();
            vVal = (uint16_t)(aDat * 50 / 1023);
            bcd = bin2bcd((int)vVal);           // 4桁BCDに変換
            sprintf(sBf,"%d -> %x", vVal,bcd);  // 表示文字列へ
            EU_puts(sBf);                       // シリアル送信
            bcd |= 0x8000;                      // 小数点表示を加える
            CLB1_SWIN_Write16(bcd);             // 7seg表示
            ADC_ConversionStart();              // ADC変換開始
            __delay_ms(500);                    // ADC変換間隔調整
        }
    }
}


※プログラムのリストをハイライト無しのスタイルで見る場合はここをクリック


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


和欧文間空白を解除 パーテションMiniTool CLB)ADC利用の電圧計