Chart PR

【C# WindowsForm】Chartコントロール X軸を日時にする方法

記事内に商品プロモーションを含む場合があります

はじめに

Windows FormのChartコントロールで、グラフのX軸を日時にする方法について解説します。

この記事の手順やソースコードは、Windows Formアプリケーション(.NET Framework)のプロジェクトが作成済みであることを前提にしています。

Windows Formアプリケーションの作り方から知りたい。という方は以下の記事からご覧ください。

環境

この記事は以下の環境で作成しています。

環境 バージョンなど 備考
Visual Studio 2022 (Community) 2017でもOKです
言語 C#
.NET Framework 4.7.2
プロジェクト WindowsFormアプリケーション
OS Windows 11 Home/Pro はどちらでもOK。Win10でも使えます。

実行結果

後述するコードを実行すると、以下のようにX軸を日付と時間にしたグラフが表示されます。

X軸を日時にするプログラムの実行結果

全体コード

全体コードは以下の通りです。詳細は次の「コードのポイント」で解説します。

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;

// Chartクラスの宣言を簡略化するために
// Usingを追加しています
using System.Windows.Forms.DataVisualization.Charting;

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

            // FormにChartコントロール(chart1)を
            // 貼り付け済みであることを前提にしています。

            // サンプル用のデータです。 
            double[] pointX = { 1.0, 2.0, 3.0, 4.0, 5.0 };
            double[] pointY = { 1.0, 2.0, 3.0, 4.0, 5.0 };

            // 現在の日時を取得します(例:6時55分10秒)
            DateTime detail = DateTime.Now;

            // 現在日時から秒の部分を取得します(例:10秒)
            long sec = detail.Ticks % TimeSpan.TicksPerMinute;

            // 現在時刻を分までにします(例:6時55分10秒 - 10秒)
            DateTime baseDt = new DateTime(detail.Ticks - sec);      

            // 日時の格納用配列です
            DateTime[] dtArray = new DateTime[5];

            // X用の日時データとY用のポイントデータを生成します
            for (int i = 0; i < dtArray.Length; i++)
            {
                // 基準の日時 + 1分の日時を生成します
                DateTime tempDt = baseDt.AddMinutes(i);

                // 生成した日時をDouble型に変換します
                pointX[i] = tempDt.ToOADate();

                // Y用のデータ配列に格納します
                pointY[i] = i + 1.0;
            }

            //
            // 貼り付けたChartコントロールには
            // 初期値のデータがセットされているので、一旦クリアします
            //
            chart1.ChartAreas.Clear();
            chart1.Series.Clear();

            // 「chartArea」という名前のエリアを生成します
            ChartArea chartAria = new ChartArea("chartArea");

            // 生成したエリアをChartコントロールに追加します。
            chart1.ChartAreas.Add(chartAria);

            // Series(系列)を生成します
            Series series = new Series();

            // 系列の種類を折れ線グラフ(Line)に設定します
            series.ChartType = SeriesChartType.Line;

            // 系列の凡例を設置します
            series.LegendText = "凡例1";

            // X軸の値を日時であることを知らせます
            series.XValueType = ChartValueType.DateTime;

            // 系列のポイント情報をセットします
            for (int i = 0; i < 5; i++)
            {
                series.Points.AddXY(pointX[i], pointY[i]);
            }
            // 生成・設定した系列をChartコントロールに追加します
            chart1.Series.Add(series);

            // X軸のラベルのフォーマットを設定します
            chart1.ChartAreas["chartArea"].AxisX.LabelStyle.Format = "yyyy/MM/dd hh:mm";
        }
    }
}

コードのポイント

現在日時の取得

X軸を日時にするため、まずはDateTime型のNowプロパティを使って、基準となる現在日時を取得します。

今回のプログラムでは、取得した日時をポイントデータ始まりとして使用し、その後は「1分毎」の固定データを追加していきます。

しかし、上記で取得した情報には「秒」までの時間が含まれおり、プログラムの実行ごとに取得時刻は変化するため、毎回ポイントデータの始まりが変化する見ずらいグラフとなってしまいます。

秒の分、ポイントのスタート位置がずれた状態

そのため、現在時刻から秒の部分をマイナスし、分ごとの見やすいグラフになるよう、下記の処理を行っています。

            // 日時の格納用配列です
            DateTime[] dtArray = new DateTime[5];

            // X用の日時データとY用のポイントデータを生成します
            for (int i = 0; i < dtArray.Length; i++)
            {
                // 基準の日時 + 1分の日時を生成します
                DateTime tempDt = baseDt.AddMinutes(i);

                // 生成した日時をDouble型に変換します
                pointX[i] = tempDt.ToOADate();

                // Y用のデータ配列に格納します
                pointY[i] = i + 1.0;
            }

日時データの作成

前述した基準を作成したら、現在から1分ずつプラスした日時情報を5つ作成し、同じDateTime型の配列に格納していきます

作成後はそのままChartポイント情報としてにセットしたいところですが、Chart用のポイントデータはDouble型しか受け取ってくれないため、DateTimeのToOADate関数を使って、Double型の日時データに変換します。

            // 日時の格納用配列です
            DateTime[] dtArray = new DateTime[5];

            // X用の日時データとY用のポイントデータを生成します
            for (int i = 0; i < dtArray.Length; i++)
            {
                // 基準の日時 + 1分の日時を生成します
                DateTime tempDt = baseDt.AddMinutes(i);

                // 生成した日時をDouble型に変換します
                pointX[i] = tempDt.ToOADate();

                // Y用のデータ配列に格納します
                pointY[i] = i + 1.0;
            }

データタイプの指定

上記でChartに渡した「Double型の日付データ」ですが、Chart側では、通常の「数値のDouble型」なのか、「日時のDouble型」なのかが判断できません。

そのため、XValueTypeをDatetimeに設定して、日時のDoubleであることをChartに知らせます。

            // X軸の値を日付としてセットします
            series.XValueType = ChartValueType.DateTime;

日時の表示フォーマットの設定

デフォルトの表示だと、X軸が年月日の表示になっていしまうので、表示フォーマットを指定してグラフを見やすくします。

            // X軸のフォーマットを設定します
            chart1.ChartAreas["chartArea"].AxisX.LabelStyle.Format = "yyyy/MM/dd hh:mm";

デフォルト
フォーマット指定

まとめ

ChartコントロールのX軸に日時を設定する方法について解説しました。参考になればうれしいです。

お知らせ

今月号のSoftware Designは「もっとTypeScriptの力を引き出そう」

JavaScriptの拡張言語でしょ?と思っているかたへ、Union型などTypeScriptの持つ秘めたる力を解説する特集となっています。

個人的には第2特集の「Ubuntuの現代的な使い方」がの方が気になりました。より詳しい内容は以下のリンクからご覧ください。

もっと少し詳しく知りたい

もっと詳しくC#でのアプリの作り方を知りたい方には、こちらの本がおすすめです。

Formアプリケーションの作り方を分かりやすく解説した本はあまりないのですが、この本はイラストが多めで分かりやすく、環境も記事と同じVS2022なので、最新環境がそのまま使えます。

著:荻原裕之, 著:宮崎昭世
¥2,673 (2024/03/07 06:28時点 | Amazon調べ)

ScottPlotでX軸に日付を設定する

以下の記事で、ScottPlotでX軸を日時にする方法も設定も解説しています。ScottPlotのほうが他の設定も含めてシンプル記述できますので、興味のある方は是非ご覧ください。

質問・要望 大歓迎です

「こんな解説記事作って」「こんなことがしたいけど、〇〇で困ってる」など、コメント欄で教えてください。 質問・要望に、中の人ができる限り対応します。

使えたよ・設定できたよの一言コメントも大歓迎。気軽に足跡を残してみてください。記事を紹介したい方はブログ、SNSにバシバシ貼ってもらってOKです。

ABOUT ME
えす
現役のソフトウェアエンジニアです。 C++ C# Python を使ってます。10年ちょい設計/開発部門にいましたが、今はQAエンジニアっぽいことをしています。

POSTED COMMENT

  1. トム より:

    すみません。以下教えていただけないでしょうか。

    MSChartで株価(ローソク足)を5分足で表示しております。
    その際、市場の休憩時間11:30-12:30については、
    X軸が数値軸のため、株価グラフに隙間ができてしまいます。これを取り除く(データの存在しない11:30-12:30を
    左詰めにしたい)ことは可能でしょうか?
    例えば、X軸を棒グラフの場合のような項目軸にできれば、
    可能かと思っておりますが、やり方がわからず困っております。
    よろしくお願いいたします。

    • えす より:

      トムさん

      こんにちは、えすです。

      ご質問ありがとうございます。
      ちょっと調べてみますね。

  2. トム より:

    ご連絡いただき、ありがとうございます。
    お手数をおかけいたします。

    よろしくお願いいたします。

    • えす より:

      トムさん

      差し支えなければ、株価データの取得元を教えてもらってもいいですか?

      休憩時間の間の株価のデータの値が知りたいです。
      (変動しない、空欄、ゼロなど)

      Yahoo Financeとかでしょうか?

  3. トム より:

    株価は、歩み足や15分足のデータ(購入)のため、
    Yahoo Finance等では取得できません。

    すみません。
    必要であれば、えす様のメールアドレス等に、部分的なデータを送付申し上げます。

    よろしくお願いいたします。

COMMENT

メールアドレスが公開されることはありません。 が付いている欄は必須項目です

Index