ページを修正する

修正(&U)で取得したテキストでページを修正します。

前田稔(Maeda Minoru)の超初心者のプログラム入門

プログラムの説明

  1. 現在 TextBox に表示されている string と、修正で取得した string を比較してページを修正します。
    TextBox には、16進数と文字で表示されていますが、どちらでも修正出来るようにプログラムします。
  2. Update イベントハンドラから修正したテキストを取得して、edit.bytEdit() メソッドでページを修正します。
    修正したページが描画されるように Pos に -1 を設定して Invalidate() を実行します。
        private void Update(object sender, EventArgs e)
        {
            string  wstr;
            wstr = textBox1.Text;
    //Console.WriteLine(wstr);
            edit.bytEdit(wstr);
            Pos = -1;
            Invalidate();
        }
        
  3. このエディッタは追加や削除には対応していません。
    行がずれると修正位置が混乱するので、最初に str と wstr の長さを調べます。
    str と wstr を1行ずつ比べて、変更されている行を調べます。
    修正された行が見つかったら、16進数と文字のどちらが修正されているかを調べます。
    line が行番号で、col が修正カラムです。
    col<43 のときは、16進数で修正する hexMode() を呼び出します。
    else のときは、文字で修正する charMode() を呼び出します。
    行の修正が終われば、次の行に移ります。
        // str のデータを更新(1行= 6+9*4+2+8+4= 56)
        //0038: 2A000526 20004200 69006E00 61007200   *★ Binar  
        public string bytEdit(string wstr)
        {
            int     i,line,col;
    
            if (str.Length!= wstr.Length)
            {   MessageBox.Show("長さが変わりました。追加/削除はできません!");
                return str;
            }
            for(i=0; i<str.Length; i++)
            {   if (str[i]!=wstr[i])
                {   line = i / 56;
                    col = i % 56;
                    if (col<43)
                    {   hexMode(wstr.Substring(line*56+6,36),line);
                    }
                    else
                    {   charMode(wstr.Substring(line*56+44,8), line);
                    }
                    i = (line+1)*56;
                }
            }
            return str;
        }
        
  4. 文字で修正する charMode() です。
    パラメータで渡された wstr を byt[256] の line が指示する領域に格納します。
    この段階では byt[] が修正されただけで、ファイルは更新されていません。
        // byt[256](8文字*16行)を char で更新
        public void charMode(string wstr, int line)
        {
            int i;
            for(i=0; i<8; i++)
            {   byt[line*16+i*2] = (byte)(wstr[i]&0xFF);
                byt[line*16+i*2+1] = (byte)(wstr[i]>>8);
            }
        }
        
  5. 16進数で修正する hexMode() です。
    パラメータで渡された wstr を byt[256] の line が指示する領域に格納します。
    wstr には空白が含まれているので、スキップします。
    16進数の2桁で1バイトを表します。
    hex2byte() が2桁の16進数を byte に変換するメソッドです。
        // byt[256](8文字*16行)を hex で更新
        public void hexMode(string wstr, int line)
        {
            int     i,j;
            j = 0;
            for(i=0; i<wstr.Length-2; )
            {
                if (wstr[i] == ' ')
                {
                    i++;
                    continue;
                }
                byt[line*16+j] = hex2byte(wstr.Substring(i,2));
                i += 2;
                j++;
                if (j >= 16) return;
            }
        }
        
  6. 2桁の16進数を byte に変換する hex2byte() です。
    0(0030)~9(0039)とA(0041)~F(0046)を4ビットコードの 0000~1111 に変換します。
    C#に便利なメソッドが無いかと調べたのですが、見つからないので直接文字コードを演算しています。
        // 2文字の16進数を byte に変換
        public byte hex2byte(string str)
        {
            byte wk;
    
            if (str[0] <= '9') wk = (byte)((str[0] & 0x0F)<<4);
            else wk = (byte)(((str[0] + 9) & 0x0F)<<4);
            if (str[1] <= '9') wk += (byte)(str[1] & 0x0F);
            else wk += (byte)((str[1] + 9) & 0x0F);
            return wk;
        }
        

【NOTE】

TextBox から一行ずつ取得すれば、行番号がズレルことは防げるのですが、結局文字が違っているカラムを調べなければならず、 面倒な割りに改善されないので中止しました。
TextBox に格納されている行数と、行ごとに取得するコードは次のとおりです。
    string  wstr;
    for(line=0; line<TextBox.Lines.Length; line++)
    {   wstr = TextBox.Lines[line];
        Console.WriteLine(wstr);
    }

[Next Chapter ↓] ベータ版の完成です
[Previous Chapter ↑] 修正(&U)を設定する

超初心者のプログラム入門(C# Frame Work)