Day17

タスク管理帳ソフトの作成

Topへ

Day16へ

はじめに

今回は、ベタですがタスク管理帳を作成しようと思います。
巷には、この関係のソフトは溢れておりますが、敢えて挑戦します。
また、タスク管理とは、小さな最小単位の仕事や作業(タスク)を管理することで、 プロジェクトにおいては、誰がいつまでにどのタスクを完了させなければならないのか、現在の進捗状況はどうなのかなどを管理することを指すようです。

Step1

テーマ欄の作成

image

新規プロジェクトを立ち上げます。
新しいプロジェクトから「Windowsフォームアプリケーション」を使用します。

image

フォームデザイを行っていきます。
今回は、画面を最大化した時にも画面配置(リサイズ)が対応できるようにしたいと思います。
そのため、新しいツールを採用していきます。
ツールボックスから「Panel」を選択し、フォームにドラックアンドドロップします。

image

この「Panel」を画像のとおり適当なサイズで配置します。
ちなみに「Panel」は3つ使います。

image

左の「Panel」のプロパティの「Dock」を「Left」にします。
これを設定することにより、フォームのサイズが変更されても、フォームの左端に併せてパネルサイズも変更されるようになります。
ただし、「Panel」の幅は手動で調整する必要があります。

image

右の「Panel」のプロパティの「Dock」を「Right」にします。

image

真ん中の「Panel」のプロパティの「Dock」を「Fill」にします。
こうすることにより、両端の「Panel」の間を埋めるようにサイズを常に変更するようになります。

image

それでは、左の「Panel」内のデザインをしていきます。
この中には、「テーマ」を入力できるようにツールを配置していきます。
デザインは画像のとおりで、「Panel」の背景色を変更し、リストボックスとボタンを2つ配置しました。

image

次に各コントロールがフォームのリサイズ時に合わせてサイズを変更するようにします。
と言っても、リストボックスだけ設定します。
リストボックスのプロパティの「Anchor」を「Top、Bottom、Left」にします。
こうすることで、リサイズされても「Panel」とリストボックスとの上、下、左端の間隔をそのまま保ちます。
つまり、その間隔を保とうとするため、リストボックスのサイズはリサイズ時に変更されます。 また、「Panel」を今回使用したのは、この「Panel」との間隔を保つようにするためになります。今回のように 画面を3つに分ける必要が無ければ「Panel」は必要ありません。

image

ここでは、テーマを格納する変数を宣言します。
「Form1」の上部に配列で宣言します。

image

テーマを入力するフォームは別フォームで入力することにします。
ソリューションエクスプローラーの下の「タスク管理」を右クリックして「追加」を選択し、[新しい項目」を選びます。

image

その中の「フォーム」を選びます。
名前はデフォルトの「Form2」のままにします。

image

「Form2」の画面をデザインします。
単純にテキストボックスとボタンを2つ配置します。

image

次に「Form2」のコードに移ります。
まずは、フォームのロードイベント時にテキストボックスを空白にします。

image

今回は、テーマをCSVデータとして保存することにしますので、コード上部に「using System.IO;」を追加します。

image

それでは「登録」ボタンクリックイベントの処理を行っていきます。
まずは、テキストボックスに何も入力されていない場合の処理をします。
この場合は、イベントから抜けることにします。

image

テキストボックスにテーマが入力されていたら、そのテーマを「themedata.csv」に保存します。
保存先は、カレントディレクトリ(このソフトのある場所と同じディレクトリ)になります。
ただし、「themedata.csv」が存在している場合は、上書き保存とし、存在していなければファイルを新規作成して 保存することにします。
また、保存するメソッドとして、「StreamWriter」を使用します。このインスタンス時の引数に「true」か「false」を選びますが、 これが、新規作成か上書保存かの違いになります。
さらに、「Format」関数を使用していますが、この場合は必要ありません。習慣とするために敢えて使用しています。

image

「キャンセル」ボタンにもコードを入力しましす。
単純に、このフォームを閉じるコードになります。これで、「Form2」のコードはすべて完了になります。

image

「Form1」でもCSVデータを取り扱いますので、コード上部に「using System.IO;」を追加します。

image

「Form2」の変数を宣言します。

image

画像は「Form1」ロードイベントのコードになります。
ここでは、まず、「Form2」用に変数をインスタンスします。
次に、「themedata.csv」が存在しているか確認し、存在していれば「StreamReader」で データを読み込みます。
最後に、読み込んだデータをリストに表示するようにしています。

image

「+」ボタンのクリックイベントに「Form2」を表示するコードを入力します。

image

テーマの入力は、ソフト起動時以外でも行います。
そのため、フォームのロードイベント時のみ、リストに追加表示する機能を持たせてもすべてのテーマを反映できません。
なので、「Form1」がアクティブになった場合も。リストに追加する機能を持たせます。
「Form1」デザイン画面に移動しイベント(カミナリマーク)の「Active」をダブルクリックします。

image

コードはロードイベントと同様の内容になります。

image

次は、「×」ボタン(テーマの削除)の処理を行います。「×」ボタンをダブルクリックして、クリックイベントに移動します。
まずは、リストボックス内のテーマが選択されているかの確認をします。
「listBox1.SelectedItem == null」で、選択されているかどうかの確認ができるます。選択されていない場合は、イベントを抜けるようにします。

image

続いて、変数を3つ宣言します。変数は、csvファイル名、テーマ、テーマ数をそれぞれ格納するように使用します。
その次に、メッセージボックスを表示させます。やはり消す作業は慎重にしたいので、再度確認をとるための機能として 使用します。これで、「No」であればイベントを抜けるようになります。

image

「Yes」の場合の処理をします。
まず、csvデータを読み込みます。
その後、再度保存しますが、その際に、選択されているテーマだけは保存しないようにします。
これにより、削除ができたことになります。
最後に、「Form1_Activated(sender, e);」を実行することにより、リストの再表示を行います。

image

突然ですが、テーマを検索する機能をどうしても付けたくなりました。
なので、デザインを少し変えます。
画像は、変更後のデザイン画面になります。

image

検索マークのボタンイベントのコードを入力していきます。
まずは、「textBox1」が未入力の場合、つまり検索したいテーマが入力されていない場合の処理をします。
これは単純にイベントを抜ける処理にします。
次に、入力されたデータを変数に格納します。
最後に、CSV関係の変数を宣言しています。

image

何回もしていますが、またCSVデータを読み込みます。
次にリストに表示を行いますが、「Contains(item)」を使って、検索したいテーマが含まれている場合のみ リストに表示するようにします。
これで、検索機能の追加は完了になります。

image

「全」ボタンはすべてのテーマを表示させるボタンとします。
なので、コードはフォームロードイベントを実行するようにします。

Step2

タスク欄の作成

image

最初に画面デザインから行います。
今回は、右のパネルのデザインになります。
このパネル内に、さらにパネルを3つ(Top、Fill、Bottom)を配置し、ラベルとテキストボックス等を配置します。
パネルを追加した理由としては、リサイズ時に縦方向のサイズ調整を行いたかったためです。

image

今回は、新しく「RichTextBox」というものを使用します。
「RichTextBox」は、普通の「TextBox」は1行の入力に対し、あらかじめ複数行に対応できるテキストボックスのようです。

image

この「RichTextBox」のプロパティの「Anchor」を「Top, Bottom, Left, Right」に変更し、 リサイズ時に拡大・縮小出来るようにしておきます。

image

「RichTextBox」の設定を行います。
「Form1」のロードイベントに画像のコードを追加します。
内容はコード内の説明のとおりになります。

image

ころころ変更して申し訳ないのですが、画像のとおりデザインを変更します。

image

追加したテキストボックスの設定を行います。
先程入力した「RichTextBox1」のところに追記します。

image

真ん中のデザインをします。
センスがないですが、画像のとおりのレイアウトにしてみました。
この範囲でテーマごとのタスクを管理するようにし、そのタスクの内容を右の範囲に表示するようにしたいと思います。

image

それでは、一つ一つの処理をしていこうと思います。
まずは、「新規タスク」ボタンから始めます。
このボタンを押すと新しいフォームを表示させ、そこに内容を入力出来るようにしたいと思います。
なので、ソリューションエクスプローラーの下の「タスク管理」を右クリックして「追加」を選択し、[新しい項目」を選びます。

image

その中の「フォーム」を選びます。
名前はデフォルトの「Form3」のままにします。

image

「Form3」のデザイン画面です。基本的に「Form1」の右側の範囲のデザインを再現する形になります。

image

「Form3」のコードの作成の前に「Form1」で少しコードを加えます。
まずは、変数の宣言と「Form3」のインスタンスになります。
変数は、「Form3」用の他に、選んだテーマを格納する変数も用意します。

image

タスク欄にある「+」ボタンをダブルクリックしてコード入力画面に移動します。
コードは画像のとおりで、選んだテーマを変数に格納し、「Form3」を表示するようにしておきます。

image

「Form3」のコードに移ります
まずは、「Form3」のロードイベントにテキストボックスの設定を行います。
コードは画像のとおりで、「Form1」で書いた内容と同様になります。

image

現在のままでは、「Form3」再ロード時に以前のテキストボックスの入力値が残っていればそれを表示する状態になります。
なので、ロードイベント時に、テキストボックスを空白にする処理をします。

image

おいさんは、歳を取り過ぎたせいか、どこにファイルを保存したか忘れてしまいます。
なので、今回、「関連ファイルの格納場所」を設けることにしました。といっても、ファイルの保存先を手入力するのは面倒なので ファイルダイアログを使用することにしました。
ということで、画像の赤枠で囲っているボタンの処理をしていきます。

image

コードは画像のとおりとなります。「C#」では、ファイルダイアログの開く用が用意されているようです。
なので、これをインスタンスして使用します。

image

試しに実行してみました。画像のとおり、無事ファイルダイアログが表示されました。

image

次は、画像登録にあるボタンの処理をしていきます。
この機能は、タスクの内容で、文字のみでは表現できない時のために画像をみて理解出来るためようです。
なので、単純にどの画像登録するかの処理をするだけものになります。

image

こちらも先程使用した開く用のファイルダイアログを使用します。
その後、ピクチャーボックスにその画像を表示するようにしました。

image

いよいよ「登録」ボタンのコードを書いていきます。
結構面倒な感じがするので、あまり気がすすみませんが、頑張るしかないです。
ということで、「登録」ボタンをダブルクリックしてコード画面に移り、恒例の未入力処理をします。

image

また、CSVデータを扱いますので、コード画面上部に「using System.IO;」を入力します。

image

ボタンイベントに戻り、続きのコードを書いていきます。
まずは、ファイル名を「taskdat.csv」とし、このファイルが存在しない場合、新規作成でデータを保存するようにします。

image

「taskdat.csv」が存在する場合は、まずタスクのタイトルの重複を避けたいため、その対策を行っていきます。
最初に、すでにあるファイルのデータを読み込んでいきます。

image

CSVデータ数分だけ繰り返し、入力されたタイトル(TextBox2)と同じ内容がるか確認します。
同じ内容のデータがあれば、「break」文で処理を中止し、メッセージボックスを表示するようにします。

image

タイトル重複がない場合の処理になります。
「taskdat.csv」にデータを追加します。

image

画像は、すべて1つのフォルダに集めて保存していく形にします。
保存先は、ソフトのある階層に「imageDat」というフォルダ内にします。
まずは、そのフォルダが存在しない場合は、そのフォルダを作成し、その中に画像を保存するようにします。
コードは画像のとおりとなります。

image

フォルダが存在しているときの処理になります。
単純にデータを保存するだけになります。

image

「キャンセル」ボタンには、フォームを閉じるコードを入力しておきます。

image

一つ処理を忘れていたので、コードの追加をします。
追加する箇所は、「taskdat.csv」が存在していない時になります。
ここにも、写真を保存する機能を持たせる必要がありました。

image

ここからは、左のリストボックス(listBox1)のテーマを選択したら、その隣のリストボックス(listBox2)にそのテーマに関するタスクを表示 するようにします。
まずは、「taskdat.csv」を読み込みます。

image

読み込んだデータから、選択されているテーマのタスクを抽出して、リストに表示するようにします。
画像のとおりコードは単純です。

image

ここからは、タスクの削除の処理をしていきます。
まず、タスクのデザイン画面の「×」ボタンをダブルクリックし、コード入力画面に移動します。
そこに、まず、リストボックス(listBox2)の選択がされていない場合の処理をします。
単純に、「return」でイベントを抜けるようにします。

image

次に、メッセージボックスを表示し、再度「削除」の確認をします。「Yes」の場合は次に進み、「No」 の場合は、イベントを抜けるようにします。

image

「taskdat.csv」を読み込みます。

image

読み込んだデータを再度保存します。
その際、選ばれているタスクのみ保存しないようにします。これにより、「taskdat.csv」のデータから 選ばれたタスクは削除されることになります。

image

すみません。1つコードの抜けがありました。
listBox1の選択時に「selectTheme」変数にその選んだ内容を格納する処理を忘れていました。

image

削除イベントに戻ります。
最後は、リストの再表示と、対象画像の削除になります。
削除の関数は、「File.Delete()」で行えるようで大変便利です。これで、削除処理はすべて終了になります。

image

ここからは「更新」ボタンの処理を行っていきます。
まず、新しいフォームを追加したいので、ソリューションエクスプローラーの下の「タスク管理」を右クリックして 「追加」を選択し、[新しい項目」を選びます。

image

その中の「フォーム」を選びます。
名前はデフォルトの「Form4」のままにします。

image

「Form4」のデザイン画面です。「Form3」とほぼ同じになります。

image

「Form1」にコードを加えます。
「Form4」の変数の宣言とインスタンスになります。

image

タスク欄にある「更」ボタンをダブルクリックしてコード入力画面に移動します。 コードは画像のとおりで、選んだテーマとタスクを変数に格納し、「Form4」を表示するようにしておきます。

image

「Form4」のコードに移ります
まずは、「Form4」のロードイベントにテキストボックスの設定を行います。
コードは画像のとおりで、「Form3」で書いた内容と同様になります。
また、画像のパス用の変数も宣言しておきます。

image

画像の赤枠ボタンのコードを入力していきます。
まずは、上のボタンのコードを入力します。

image

コードは画像のとおりとなります。「Form3」と同様になります。

image

画像は、下のボタンのコードになります。これも「Form3」と同様になります。

image

「Form4」でもCSVデータを取り扱いますので、コード上部に「using System.IO;」を追加します。

image

ロードイベントに戻ります。
ここに追加で、CSVファイルの読み込みを行います。

image

選択されているタスクの内容を表示します。
ビビって、「try」文を使用しています。
コードは画像のとおりで、「for」文と「if」文で制御しています。
最後に、タスクの内容を書き換えできないように、「TextBox2」を読み込みのみとしています。(入力できないように制限をしています。)

image

いよいよ「変更」ボタンのコードを入力します。
ボタンをダブルクリックして、クリックイベントに移動します。
まずはじめは、CSVデータの読み込みします。
コードは画像のとおりで、これまで出てきたコードと同様になります。

image

次に、メッセージボックスを表示させ、再度変更して良いか確認するようにします。

image

CSVを書き換えるコードになります。
削除の時とほぼ同様のコードになりますが、選択されたタスクの場合は、各テキストボックス等の内容を保存するようにします。

image

すみません。ここで修正です。これから画像ファイルを更新しようと思って作業を進めていると、そのファイルは別のところで 使用中とのことでエラーが出てしまいました。
なので、それを解決すべく検索すると、画像の表示(pictuerBoxのイメージ)方法を変更すれば良いことがわかりました。
なので、そのコードを修正します。
一つ目は、ロードイベントになります。そのコードの最後の画像表示を修正します。

image

次に、デザイン画面の下のファイルを開くボタンのコードを修正します。
これで、修正作業は完了になります。

image

「変更」ボタンの続きに戻ります。
ここで、画像ファイルの更新を行います。ただし、ビビって一回対象ファイルを削除して、改めて保存する形にしています。

image

「キャンセル」ボタンのコードになります。
これで、「Form4」の作業はすべて完了になります。

image

ふと、タスクの検索機能はそんなに必要ないのではないか思い、この機能は無しにすることにしました。
なので、少しデザインを変更します。

image

ここからは、選択したタスクの内容を右のツールに表示する作業をします。
デザイン画面のリストボックス2をダブルクリックして、コード入力画面に移動します。
まずは、すでに表示されている内容がる場合を想定して、ツールの表示内容をクリアします。

image

次に、恒例のファイルの読み込みになります。

image

右のツールに選択されたタスクを表示するコードになります。
これも、「Form4」で書いた内容と同様になります。

Step3

その他の処理

image

「Form1」ロードイベントに画面の最大化とタイトルのコードを追加します。

image

今の機能では、表示されている画像は小さいままで、見えづらい状況です。
なので、これを拡大表示できる機能を追加し、さらに、クリップボードにコピーできる機能を付加したいと思います。
最初に、「Form1」のデザイン画面に移動し、ツールボックスの「contextMenuStrip」をデザイン画面側へドラックアンドドロップします。

image

そうすると、デザイン画面の下部に「contextMenuStrip1」が表示されます。
これをクリックすると、画面上部にウインドウが表示されます。
そこに「画面の表示」と入力します。これで、この「contextMenuStrip1」を指定すると小さなウインドウが表示されるようになります。

image

「contextMenuStrip1」ウインドウを表示させるコードを入力作業をしていきます
。 デザイン画面のピクチャーボックスのイベントの「MouseClick」をダブルクリックして、コード画面を表示させます。

image

右クリックされた場合のコードを入力して、そこに「contextMenuStrip1」を表示するコードを追記します。

image

画像を拡大表示するために新しいフォームを使用します。
なので、新しいフォームの追加とその変数の宣言とインスタンスをします。
やり方はこれまでと同様なので割愛します。

image

追加した「Form5」のデザインを行います。
リサイズ用にパネルを2つ配置します。それぞれの「Dock」を「Fill」と「Bottom」にします。

image

「Form5]のデザイン画面です。
リサイズしても拡大縮小表示できるように、プロパティの「Anchor」を「Top、Bottom、Left、Right」にしておきます。

image

「Form5」のロードイベントの入力をします。
コードは画像のとおりとなります。ここまで処理したら、一旦「Form1」に戻ります。

image

写真のパスとファイル名を格納する変数を宣言します。

image

宣言した変数に、パスとファイル名を格納します。
格納する場所は、リストボックス2の選択イベントの中にしました。

image

「contextMenuStrip1」の「画像の表示」をダブルクリックしイベントコードを開きます。
ここに、「Form5」を表示するコードを入力します。

image

「Form5」のコード画面に移動します。
画像のとおりのコードを追記します。これで一連の作業の完了になります。

image

試しに、実行してみます。
画像のところで右クリックすると、無事メニューウインドウが表示されました。

image

今の状態は、あるテーマを削除しても、それに付随するタスクは削除されないままになっています。
なので、テーマの削除に連動してタスクを削除するようにします。
テーマの「×」ボタンのクリックイベントに移動します。
まずは、ファイルの読み込みを行います。

image

次に、CSVファイルのから該当するタスクを削除します。
最後に、該当するファイルを削除すると完了になります。
これで、すべての作業が完了しましたので、後は実行ファイル化(exe化)するのみですが、その内容は以前紹介しましたので割愛します。
最後に使用方法ですが、実行ファイルと同じフォルダに各ファイルが作成されますので、どこか一箇所のまとめておく方は良いと思います。
以上になります。結構エラー処理が多く大変でした。