5
10

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

テキストファイルを読み込み、Excelなどの外部アプリに自動入力するフォームアプリを作成する

Last updated at Posted at 2021-11-19

最初に

テキストファイルの数値データを読み込み、Excelなど他のソフトに自動で入力してくれるプログラムを組んでみました。
最初.png

今回の目的

VisualStudio2019のWindowsフォームアプリケーション(.NET Framework)を作成して、あるフォルダーの中のテキストファイルを読み込み、Excelなどの外部アプリに自動入力するフォームアプリを作成します。
今回はテキストファイルから「X」、「Y」を判別し文字列から数字を抽出後、Excelに「X」の数字は左の列に、「Y」の数字は右の列に入力します。手動でExcelに数字を入力する場合、操作は「Xの数字」→「TAB」→「Yの数字」→「ENTER」→「次のXの数字」→...と入力していくのですが、この操作を自動でするプログラムを作ります。
メモ帳excel.png

完成したフォームアプリはこんな感じ

フォルダーを参照、ファイル名を入力して、入力開始ボタンを押すとテキストファイルの数字をExcelに自動で打ち込んでくれます。

フォームアプリ完成系.png

開発環境

Visual Studio 2019

プロジェクトの作成

Visual Studio 2019を開き、新しいプロジェクトの作成します。
プロジェクト作成.png

Windowsフォームアプリケーション(.NET Framework)を選択して次へ。
プロジェクト作成2.png

プロジェクト名を入力後、プロジェクトの保存場所を任意の場所にして、作成をクリック。
プロジェクト名は自分のわかりやすい名前であればなんでもいいです。
プロジェクト作成3.png

フォームの作成

ボタンやテキストボックス、ラベルなどを配置します。

・画面の設定

画面のサイズは赤丸のところで調整できます。右下のプロパティ画面でも調整でき、細かい調整ができます。
ウインドウの名前がForm1になっていますが、変更したい場合はこれも右下のプロパティ画面で変更できます。Textの欄がForm1となっているので変えたい名前に変更しましょう。
UI作成1.png

・ボタンなどの配置

画面左にツールボックスがあるので使いたいものをドラックアンドドロップすることで追加できます。Buttonを追加します。
ツールボックスがない場合は上のバーの「表示」にツールボックスがあるのでそこをクリックすると出てきます。
UI作成2.png

プロパティで背景の色やフォントのサイズ、字体、ボタンのテキストなど設定できます。
UI作成4.png

同様にしてButton、TextBox、Labelを配置します。ツールボックスの検索機能を使うと便利です。
こんな感じに配置↓
UI作成5.png

・フォルダーの参照

「フォルダの選択」ダイアログを表示するのにFolderBrowserDialogを追加します。これで下準備はOKです。

UI作成6.png

コードの記述

ボタンをダブルクリックします。
プログラム1.png

コード編集画面が開き、Clickイベントハンドラ(button1_Click メソッド)が作成されます。
このbutton1_Click メソッド内にボタンクリック時に実行するコードを記述します。

Form1
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace TextFileInputOutput
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void button1_Click(object sender, EventArgs e)
        {

        }
    }
}
};

フォルダーの参照ボタンのClickイベントハンドラも同様に作成しましょう。

・イベントハンドラメソッドの名前について

メソッドには任意の名前を付けることができます。
例えば、今回のフォルダーの参照のbutton2というボタンのClickイベントのイベントハンドラーメソッドには button2_Click()という名前が付けられます。詳しくはこちらを参考にしてください。

プログラム2.png

また、イベントハンドラーメソッドを作成した後にやっぱりそのメソッドを削除したいと思ったときは、フォームデザインの画面に戻り、イベントのアクションのClickを消してから削除するようにしてください。先にコードに記述してあるメソッドを消してしまうとエラーが出てしまいます。

プログラム3_3.png

↓イベントのアクションのClickの名前を削除してからコードのほうを消す。(button2_Clickメソッドを削除したい場合)
プログラム4.png

・usingディレクティブ追加

まず、次のusingディレクティブを使うので追加しておきましょう。
using System.Threading;
using System.IO;

Form1
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Threading;
using System.IO;

namespace TextFileInputOutput
{//省略
}

・フォルダーの参照のコードの記述

テキストボックスにフォルダー参照ダイアログボックスで選択したフォルダのパスを表示します。

Form1
private void button2_Click(object sender, EventArgs e)
        {
            DialogResult dr = folderBrowserDialog1.ShowDialog();
            if (dr == System.Windows.Forms.DialogResult.OK)
            {
                textBox1.Text = folderBrowserDialog1.SelectedPath;
            }
        }

下記のコードでフォルダー参照ダイアログを表示します。

DialogResult dr = folderBrowserDialog1.ShowDialog();     

ダイアログボックスが[OK]ボタンで閉じられた場合、テキストボックスにフォルダー参照ダイアログボックスで選択したフォルダのパスを表示します。

if (dr == System.Windows.Forms.DialogResult.OK)
            {
                textBox1.Text = folderBrowserDialog1.SelectedPath;
            }

・自動入力のコードの記述

Form1
private void button1_Click(object sender, EventArgs e)
       {
               Microsoft.VisualBasic.Interaction.AppActivate("Excel");
               string filePass = $@"{textBox1.Text}\{textBox2.Text}.txt";
               var lines = File.ReadAllLines(filePass);
               Thread.Sleep(1000);
               foreach (var line in lines)
               {
                   if (line.Contains("X"))
                   {
                       string xNum = line.Replace("X=", "").Replace(" ", "");

                       SendKeys.Send(xNum);
                       SendKeys.Send("{TAB}");
                   }
                   if (line.Contains("Y"))
                   {
                       string yNum = line.Replace("Y=", "").Replace(" ", "");
                       SendKeys.Send(yNum);
                       SendKeys.Send("{ENTER}");
                   }
                   Thread.Sleep(100);
               }
       }

「型または名前空間の名前'Interaction'が名前空間'Microsoft.VisualBasic'に存在しません。」と出てきた場合は、ソリューションエクスプローラーから参照の追加でMicrosoft.VisualBasicにチェックマークを入れます。
プログラム5.png

参照を右クリックし、「参照の追加」
プログラム6-1.png

Microsoft.VisualBasicにチェックを入れてOK。
プログラム6-2.png

コードの解説

Microsoft.VisualBasic.Interaction.AppActivate("Excel");

アクティブにしたいウィンドウのタイトルを指定して呼び出し、そのウィンドウをアクティブ状態にします。(今回はExcel)

string filePass = $@"{textBox1.Text}\{textBox2.Text}.txt";

テキストボックス(textBox1、textBox2)の値を取得し、文字列として定義します。
テキストボックス.png

var lines = File.ReadAllLines(filePass);

System.IO.FileクラスのReadAllLinesメソッドを使います。
引数に定義した文字列を渡し、そのテキストファイルを開き、ファイルのすべての行を読み取った後、ファイルを閉じます。

foreach (var line in lines)
                {
                    if (line.Contains("X"))
                    {
                        string xNum = line.Replace("X=", "").Replace(" ", "");

                        SendKeys.Send(xNum);
                        SendKeys.Send("{TAB}");
                    }
                    if (line.Contains("Y"))
                    {
                        string yNum = line.Replace("Y=", "").Replace(" ", "");
                        SendKeys.Send(yNum);
                        SendKeys.Send("{ENTER}");
                    }
                    Thread.Sleep(100);
                }

foreach文で読み込んだ文字列を1つずつ取り出し、if文でその文字列に「X」が含まれていた場合、「Y」が含まれていた場合で処理を分け、この処理をある文字列の分繰り返します。
if文の中の処理では、まずReplaceメソッドで文字列を置換し、文字列を数字のみにします。次にその数字をSendKeys.Send() メソッドでキーボードから入力したかのように、1つ以上のキーボード操作をアクティブなウィンドウに送信します。その後、「X」の場合はTABの入力操作、「Y」の場合はENTERの入力操作を送信します。
最後にThread.Sleepメソッドで一定時間待機するために指定した時間の長さ(単位はミリ秒)、現在のスレッドを中断します。
今回は100ミリ秒(0.1秒)ごとに処理を繰り返すことになります。

キー操作には他にも様々な操作があるため、他に加えたいキー操作がある場合はこちらを参考にしてみてください。

・try~catchで例外処理を行う。

private void button1_Click(object sender, EventArgs e)
        {
            try
            {
                Microsoft.VisualBasic.Interaction.AppActivate("Excel");
                //省略
                Thread.Sleep(100);
                }
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message, "エラー", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }

        }

try~catchで例外処理を行います。入力開始ボタン(button1)を押したときに、処理に問題が発生すると、エラーのメッセージボックスが開きます。

例1)Excelが起動していない時
エラーメッセージ1.png

例2)ファイルの名前が見つからない時
エラーメッセージ2.png

全コード

usingディレクティブの使わないものは消していいです。

Form
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Threading;
using System.IO;

namespace TextFileInputOutput
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void button1_Click(object sender, EventArgs e)
        {
            try
            {
                Microsoft.VisualBasic.Interaction.AppActivate("Excel");
                string filePass = $@"{textBox1.Text}\{textBox2.Text}.txt";
                var lines = File.ReadAllLines(filePass);
                Thread.Sleep(1000);
                foreach (var line in lines)
                {
                    if (line.Contains("X"))
                    {
                        string xNum = line.Replace("X=", "").Replace(" ", "");

                        SendKeys.Send(xNum);
                        SendKeys.Send("{TAB}");
                    }
                    if (line.Contains("Y"))
                    {
                        string yNum = line.Replace("Y=", "").Replace(" ", "");
                        SendKeys.Send(yNum);
                        SendKeys.Send("{ENTER}");
                    }
                    Thread.Sleep(100);
                }
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message, "エラー", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }

        }

        private void button2_Click(object sender, EventArgs e)
        {
            DialogResult dr = folderBrowserDialog1.ShowDialog();
            if (dr == System.Windows.Forms.DialogResult.OK)
            {
                textBox1.Text = folderBrowserDialog1.SelectedPath;
            }
        }
    }
}

実行する

デバックなしで開始.png
フォルダーを参照(テキストボックスに直接フォルダーの場所を入力でもOK)、ファイル名を入力して、入力開始ボタンを押すとテキストファイルの数字をExcelに自動で打ち込んでくれます。

追記(2023/10/5)

非同期処理の導入や処理の中断機能の追加などをしました。
テキストファイルを読み込み、外部アプリに自動入力するフォームアプリの機能の追加と変更

参考文献

ボタン コントロールの名前を設定する
File.ReadAllLines メソッド
SendKeys
Thread.Sleep メソッド
Application.SendKeys メソッド
.NET TIPS[フォルダの参照]ダイアログを使用するには?
外部アプリケーションのウィンドウをアクティブにする

5
10
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
5
10

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?