49章:独自の折れ線グラフの作成 (WPF)

    作成2013.05.02

     数値計算結果はよく折れ線グラフにして表示します。こんなとき、独自の折れ線グラフクラスを作成すると便利 です。


  1. 独自の折れ線グラフの作成(WPF)
     独自の折れ線グラフの作成 (WPF)の完成ファイルは以下からダウンロードできます。
     ダウンロード後は解凍してから使用してください。
     
    [独自の折れ線グラフの作成 (WPF)]をダウンロードする。
     解凍すると「49MyGraph2」フォルダーがあります。
    注(1)「49MyGraph2」フォルダーのMyGraph.sln」ファイルをダブルクリックすると「Express 2012 for Windows Desktop」が起動します。
    注(2)メニューの「ウインド」_「ウインドレイアウトのリセット」で標準に戻ります。
    注(3)「ソリューションエクスプローラ」ウインドウ内の「MainWindow.xaml」をダブルクリックすると「デザイン」と「XAML」が表示されます。
    注(4)メニューの「表示」_「コード」を選択するとコードが表示されます。
    注(5)「MyGraph.sln」の動作確認は「デバッグ」_「デバッグ開始」で実行します。デバッグ機能を用いて動作確認を行います。


  2. DataGrid_WPF01.slnの実行
    (1)「Express 2012 for Windows Desktop」のデバッグ機能を使用します。
    (2)「デバッグ」_「デバッグ開始」を選択します。
    (3)色合いの異なる折れ線グラフが画面に表示されます。
    (4)クローズボックスで終了します。


  3. プロジェクトの構成
    (1)MainWindow.xaml
    ・Button1を配置します。
    (2)MainWindow.xaml.cs
    ・コードを配置します。


  4. MainWindow.xamlの全コード
    <Window x:Class="MyGraph.MainWindow"	
            xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"	
            xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"	
            Title="MainWindow" Height="400" Width="500">	
        <Grid>	
            <StackPanel  Name="StackPanel1"  Orientation="Horizontal" Height="30" VerticalAlignment="Top">	
                <Button Content="実行" Height="23" Name="Button1" Width="75" Click="Button1_Click" />	
            </StackPanel>	
            <Grid  Name="Grid1">	
            </Grid>	
        </Grid>	
    </Window>	
    
    

    (1)一般的なコードのみです。



  5. MainWindow.xaml.csの全コード

    using System;
    using System.Windows;
    using System.Windows.Controls;
    using System.Windows.Media;
    using System.Windows.Shapes;
    
    namespace MyGraph
    {
        public partial class MainWindow : Window
        {
            public MainWindow()
            {
                InitializeComponent();
            }
    
            private void Button1_Click(object sender, RoutedEventArgs e)
            {
                myGraph myG = new myGraph();
                myG.SetMyC();
                int n0 = 18; int n1 = 40;
                double[,] array = new double[n0, n1];
                myG.TestData(array);
                myG.normaliz(array);
                myG.graph(array, Grid1);
            }
        }
    
        public class myGraph
        {
            public Color[] c = new Color[18];
            public void SetMyC()
            {
                int i;
                for (i = 0; i < 3; i++)
                {
                    c[i] = Color.FromArgb(255, Convert.ToByte(255 - 75 * i), 0, 0);
                    c[i + 3] = Color.FromArgb(255, Convert.ToByte(150 - 40 * i), Convert.ToByte(150 - 40 * i), 0);
                    c[i + 6] = Color.FromArgb(255, 0, Convert.ToByte(255 - 75 * i), 0);
                    c[i + 9] = Color.FromArgb(255, 0, Convert.ToByte(150 - 40 * i), Convert.ToByte(150 - 40 * i));
                    c[i + 12] = Color.FromArgb(255, 0, 0, Convert.ToByte(255 - 75 * i));
                    c[i + 15] = Color.FromArgb(255, Convert.ToByte(150 - 40 * i), 0, Convert.ToByte(150 - 40 * i));
                }
            }
    
            public void TestData(double[,] array)
            {
                int n0 = array.GetUpperBound(0) + 1;
                int n1 = array.GetUpperBound(1) + 1;
                int i; int j; double x;
    
                for (j = 0; j < n1; j++)
                {
                    x = (double)j / 40.0;
                    array[0, j] = x;
                }
                for (i = 1; i < n0; i++)
                {
                    for (j = 0; j < n1; j++)
                    {
                        x = array[0, j];
                        array[i, j] = Math.Pow(x, 0.2 * i);
                    }
                }
            }
    
            public void normaliz(double[,] array)
            {
                int n0 = array.GetUpperBound(0) + 1;
                int n1 = array.GetUpperBound(1) + 1;
                double[] max = new double[n0];
                double[] min = new double[n0];
                int i; int j;
                for (i = 0; i < n0; i++)
                {
                    max[i] = -1e12;
                    min[i] = 1e12;
                    for (j = 0; j < n1; j++)
                    {
                        if (array[i, j] > max[i]) { max[i] = array[i, j]; }
                        if (array[i, j] < min[i]) { min[i] = array[i, j]; }
                    }
                }
                for (i = 0; i < n0; i++)
                {
                    for (j = 0; j < n1; j++)
                    {
                        array[i, j] = (array[i, j] - min[i]) / (max[i] - min[i]);
                    }
                }
            }
    
            public void graph(double[,] array, Grid Grid1)
            {
                int n0 = array.GetUpperBound(0) + 1;
                int n1 = array.GetUpperBound(1) + 1;
    
                Grid1.Children.Clear();
                double x0 = 50; double y0 = 350;
                int i; int j;
                for (i = 1; i < n0; i++)
                {
                    PathFigure myPathFigure = new PathFigure();
                    myPathFigure.StartPoint = new Point(x0, y0);
                    Path myPath = new Path();
                    myPath.Stroke = new SolidColorBrush(c[i - 1]);
                    myPath.StrokeThickness = 2;
                    for (j = 0; j < n1; j++)
                    {
                        myPathFigure.Segments.Add(new LineSegment(new Point(x0 + 400 * array[0, j], y0 - 300 * array[i, j]), true));
                    }
                    PathGeometry myPathGeometry = new PathGeometry();
                    myPathGeometry.Figures.Add(myPathFigure);
                    myPath.Data = myPathGeometry;
                    Grid1.Children.Add(myPath);
                }
            }
        }
    }
    

    (1)myGraph myG = new myGraph();で変数myGをmyGraph型で生成します。
    (2)myG.SetMyC();で独自定義に色配列を設定します。
    (3)int n0 = 18; int n1 = 40; double[,] array = new double[n0, n1];で2次元配列変数arrayを生成します。
    (4)myG.TestData(array);で作図用のテストデータを作成します。
    (5)myG.normaliz(array);でテストデータを正規化(最小が0、最大が1)します。
    (6)myG.graph(array, Grid1);で16本の折れ線グラフを描きます。


    感想:
    (1)数値計算で得られた結果を視覚的に理解するため、折れ線グラフが良く使用されます。
    (2)折れ線グラフ作成にあたって、スケールの倍率やオフセット調整は面倒です。このような場合、データを正規化してグラフにするとスケールの倍率やオフセット調整が不要となります。
    (3)正確な値は、数表を参照する必要がありますが、おおままなグラフの形状変化を確認するにはこれで十分です。








トップページに戻る。