完成図
この動画では点を適当に追加→名前を付けて保存→新規作成でグラフリセット→開くを行っています。
データの読み書き
・menuScriptの設定
まずは設定したい項目のクリックイベントを作成します。 (今回は開くと名前を付けて保存) 次にファイルの読み込みと書き込みを行うためにツールバーからsaveFileDialogとopenFileDailogをForm上に追加させます。
次に作成したクリックイベントに~FileDialog1.ShowDialog();を呼べば各項目を選択したとき下記の画像がでるようになります。
あとはファイルを選択した際に呼ばれるFindOKイベント内で データの読み書きをすれば完成です。 ファイル名は~FileDialog1.FileNameで取得できます。
・データの保存形式
データはCSVで保存しています。 保存している情報は一行ごとに開始点、制御点、終了点の座標データを保存しています。
保存はSaveでやっており、座標は0~1に変換した状態で保存しています。(今後別のところでグラフデータを読み込みする際データの確認をわかりやすくするため)
クラスを分割
いままでFormクラスに記述してたChageNomalPosXなどの数学系の関数を新しく作成したCMathクラスにまとめました。
ソースコード
Formクラスまで書くと長くなるので追加したクラスだけ掲載します。
class Form1 { /// <summary> /// 開く /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void menuPoen_Click(object sender, EventArgs e) { openFileDialog1.ShowDialog(); } /// <summary> /// CSVを開いてグラフを表示 /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void openFileDialog1_FileOk(object sender, CancelEventArgs e) { m_CurvePointControl.LoadGraph(openFileDialog1.FileName); pictureBox1.Refresh();//再描画 } /// <summary> /// 名前を付けて保存 /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void menuSaveAdd_Click(object sender, EventArgs e) { saveFileDialog1.FileName = "new.csv"; saveFileDialog1.ShowDialog(); } /// <summary> /// ファイルをCSVに保存 /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void saveFileDialog1_FileOk(object sender, CancelEventArgs e) { m_CurvePointControl.SaveGraph(saveFileDialog1.FileName); } }
class CurvePointControl { //データ読み書き機能 CurveEditorStream m_stream = new CurveEditorStream(); /// <summary> /// CSVデータからグラフの点データを読み込む /// </summary> /// <returns></returns> public void LoadGraph(string s) { CurveEditorInit(); m_list = m_stream.Load(s); } /// <summary> /// CSVデータにグラフの点データを書き込む /// </summary> /// <returns></returns> public void SaveGraph(string s) { m_stream.Save(ref m_list,s); } }
//CSVからグラフを読み書きするクラス class CurveEditorStream { /// <summary> /// 文字列から座標に変換 /// </summary> /// <param name="values"></param> CurvePointControl.BezierPoint ToBezierPoint(string[] values) { //文字列を数値に変換 CurvePointControl.BezierPoint bp = new CurvePointControl.BezierPoint(); bp.startPoint.X = CMath.ChageNomalPosX(decimal.Parse(values[0])); bp.startPoint.Y = CMath.ChageNomalPosY(decimal.Parse(values[1])); bp.controlPoint1.X = CMath.ChageNomalPosX(decimal.Parse(values[2])); bp.controlPoint1.Y = CMath.ChageNomalPosY(decimal.Parse(values[3])); bp.controlPoint2.X = CMath.ChageNomalPosX(decimal.Parse(values[4])); bp.controlPoint2.Y = CMath.ChageNomalPosY(decimal.Parse(values[5])); bp.endPoint.X = CMath.ChageNomalPosX(decimal.Parse(values[6])); bp.endPoint.Y = CMath.ChageNomalPosY(decimal.Parse(values[7])); return bp; } /// <summary> /// CSVからデータを読み込み /// </summary> /// <param name="s"></param> /// <returns></returns> public List<CurvePointControl.BezierPoint> Load(string s) { List<CurvePointControl.BezierPoint> list = new List<CurvePointControl.BezierPoint>(); StreamReader file = new StreamReader(s); //末尾まで繰り返す while (!file.EndOfStream) { // CSVファイルの一行を読み込む string line = file.ReadLine(); // 読み込んだ一行をカンマ毎に分けて配列に格納する string[] values = line.Split(','); CurvePointControl.BezierPoint b = ToBezierPoint(values); list.Add(b); } file.Close(); return list; } /// <summary> /// CSVにデータを書き込む /// </summary> /// <param name="List"></param> public void Save(ref List<CurvePointControl.BezierPoint> List,string s) { try { StreamWriter file = new StreamWriter(s, false, Encoding.UTF8); int size = List.Count; for(int i = 0; i < size;i++) { //座標を0~1の間に変換し文字列化させる string [] name = new string[4]; name = ToSting(List[i]); file.Write(name[0]+ "," + name[1] + "," + name[2] + "," + name[3] + "\n"); } file.Close(); } catch (Exception e) { MessageBox.Show(e.Message); Console.WriteLine(e.Message); // エラーメッセージを表示 } } /// <summary> /// //座標を0~1の間に変換し文字列化させる /// </summary> /// <param name="bs"></param> /// <returns></returns> public string[] ToSting( CurvePointControl.BezierPoint bs) { //座標を0~1の間に変換し文字列化させる string[] name = new string[4]; name[0] = CMath.ChageDecimalPosX(bs.startPoint.X).ToString() + "," + CMath.ChageDecimalPosY(bs.startPoint.Y).ToString(); name[1] = CMath.ChageDecimalPosX(bs.controlPoint1.X).ToString() + "," + CMath.ChageDecimalPosY(bs.controlPoint1.Y).ToString(); name[2] = CMath.ChageDecimalPosX(bs.controlPoint2.X).ToString() + "," + CMath.ChageDecimalPosY(bs.controlPoint2.Y).ToString(); name[3] = CMath.ChageDecimalPosX(bs.endPoint.X).ToString() + "," + CMath.ChageDecimalPosY(bs.endPoint.Y).ToString(); return name; } }
//カーブエディタで使う数学関数 class CMath { /// <summary> /// 小数から元の座標に変換 /// </summary> /// <param name="Value"></param> /// <returns></returns> public static int ChageNomalPosX(decimal Value) { decimal num = Value; decimal num2 = (num * (decimal)500); int num3 = Convert.ToInt32(num2); num3 += 10;//10からグラフが始まってるので右に+10 return num3; } /// <summary> /// 元の座標から0~1の間に変換 /// </summary> /// <param name="posX"></param> /// <returns></returns> public static decimal ChageDecimalPosX(int posX) { posX = Math.Max(0, posX - 10); //10からグラフが始まってるので右に-10 return (decimal)posX / (decimal)500; } /// <summary> /// 小数から元の座標に変換 /// </summary> /// <param name="Value"></param> /// <returns></returns> public static int ChageNomalPosY(decimal Value) { decimal num = Value; decimal num2 = num * (decimal)500; int num3 = Convert.ToInt32(num2); num3 = num3 - 500; num3 = num3 * -1; num3 += 10;//10からグラフが始まってるので右に+10 return num3; } /// <summary> /// 元の座標から0~1の間に変換 /// </summary> /// <param name="posY"></param> /// <returns></returns> public static decimal ChageDecimalPosY(int posY) { // posY = Math.Min(500, posY - 10); //10からグラフが始まってるので右に-10 posY = Math.Max(0, posY - 10); posY = posY - 500; posY = posY * -1; return Math.Max(0, (decimal)posY / (decimal)500); } /// <summary> /// 値を制限させる /// </summary> /// <param name="x"></param> /// <param name="minVal"></param> /// <param name="maxVal"></param> /// <returns></returns> public static int Clamp(int x, int minVal, int maxVal) { return Math.Min(Math.Max(minVal, x), maxVal); } }
終わりに
カーブエディタ作成もだんだん終わりが近づいてきました。 次は上書き保存を実装していきます。
次の記事