none
Microsoftチャートコントロールの印刷に関して RRS feed

  • 質問

  • Microsoft Chart Control を使用しています。
    デザイン上に、ChartControlを配置し、以下のソースで、プロパティの設定をしました。

    -----
    Default.aspx.cs
    -----
    using System.Web.UI.DataVisualization.Charting;
                 【  ・・・・・略】
     private void SetChart()
     {
                // グラフ種類
                Chart_test.Series["Series1"].ChartType = SeriesChartType.Line;

                // ライン色
                Chart_test.Series["Series1"].Color = System.Drawing.Color.Black;
                Chart_test.Series["Series1"].MarkerStyle = MarkerStyle.Star10;
                Chart_test.Series["Series1"].MarkerColor = System.Drawing.Color.Black;
                Chart_test.Series["Series1"].MarkerBorderColor = System.Drawing.Color.Black;

                // Y軸
                Chart_test.ChartAreas["ChartArea1"].AxisY.Minimum = 20;
                Chart_test.ChartAreas["ChartArea1"].AxisY.Maximum = 50;
                Chart_test.ChartAreas["ChartArea1"].AxisY.Interval = 5;

                // X軸
                Chart_test.ChartAreas["ChartArea1"].AxisX.Minimum = 0;
                Chart_test.ChartAreas["ChartArea1"].AxisX.Maximum = 30;
                Chart_test.ChartAreas["ChartArea1"].AxisX.Interval = 2;
                Chart_test.ChartAreas["ChartArea1"].AxisX.MajorGrid.LineColor = System.Drawing.Color.Silver;
                Chart_test.ChartAreas["ChartArea1"].AxisX.Interval = 2;

                Chart_test.ChartAreas["ChartArea1"].AxisX.MinorGrid.LineColor = System.Drawing.Color.Silver;
                Chart_test.ChartAreas["ChartArea1"].AxisX.MinorGrid.Enabled = true;
                Chart_test.ChartAreas["ChartArea1"].AxisX.MinorGrid.Interval = 1;

         Random    random = new Random();
                // 描画
                for (int i = 1; i < 30; i++)
                {
                    Chart_test.Series["Series1"].Points.AddY(random.Next(45, 95));
                }
     }
    -----

    -----
    Web.configで追加した部分は、以下の3カ所
    -----
      <appSettings>
        <add key="ChartImageHandler" value="storage=file;timeout=20;Url=~/tempChart/;" />

      <system.web>
          <controls>
            <add tagPrefix="asp" namespace="System.Web.UI.DataVisualization.Charting"
             assembly="System.Web.DataVisualization, Version=3.5.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35"/>

        <httpHandlers>
          <add path="ChartImg.axd" verb="GET,HEAD" type="System.Web.UI.DataVisualization.Charting.ChartHttpHandler, System.Web.DataVisualization, Version=3.5.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35" validate="false" />
    -----


    これをInternetExploer7.0で表示させ、印刷をしたのですが、
    実際に、レーザープリンターでモノクロ印刷してみると、
    数字やラインが、小さい画像を拡大した時に見られる様なにじみ方をします。
    (カラー画像を、モノクロプリンタで印刷した際に見られる様なグレーがかった色になります)

    作成されたChartのイメージは、PNGファイルでした。

    Chartを生成して、ブラウザで印刷する場合に、
    Chartイメージ内の文字やラインが、にじまない様にする方法が
    (高解像度のチャート画像の生成方法、モノクロ画像の生成方法など)
    ありましたらご教授のほどよろしくおねがいします。

    ---
    環境 VisualStudio2008/C#/.NetFramework3.5
    2009年3月26日 0:38

回答

  • たぶん印刷するとにじむというのはブラウザやプリンタが数百dpiといった解像度に拡大印刷しているからです。
    ですからどのように滲むかは環境次第だと思います。
    AntiAliasingプロパティやTextAntiAliasingQualityを変更すれば多少は滲むのは抑えられるでしょうがカクカクした画像になってしまうでしょう。

    任意のサイズに拡大した画像を生成するのは以下の様な感じになります。

    /// <summary>チャートを指定したサイズに拡大してJPEGで送る/summary>
    /// <param name="response">送信するResponse</param>
    /// <param name="chart">元画像とするチャート</param>
    /// <param name="pixcelWidth">拡大する横幅のピクセル数</param>
    /// <param name="pixcelHeight">拡大する高さのピクセル数</param>
    public void ResponseChartImage(HttpResponse response , System.Web.UI.DataVisualization.Charting.Chart chart , int pixcelWidth , int pixcelHeight)
    {
        //送信する画像の大きさのBitmapを作る
        System.Drawing.Bitmap bmp = new Bitmap(pixcelWidth,pixcelHeight);
        System.Drawing.Graphics g = System.Drawing.Graphics.FromImage(bmp);

        //スケール変換する
        //スケール変換せずに単純にBitmapに書かせると文字が小さくなってしまいます
        g.Transform = new System.Drawing.Drawing2D.Matrix((float)((float)pixcelWidth / chart.Width.Value) , 0 , 0 , (float)((float)pixcelHeight / chart.Height.Value) , 0 , 0);
        chart.Paint(g , new Rectangle(0 , 0 , (int)chart.Width.Value  , (int)chart.Height.Value ));
        g.Dispose();

        ///JPEG形式でストリームに出力
        response.ClearContent();
        response.ContentType = "image/jpeg";
        bmp.Save(response.OutputStream , System.Drawing.Imaging.ImageFormat.Jpeg);
    }

    #白黒化はグレースケールといったキーワードで検索すれば見つかります。


    • 編集済み gekkaMVP 2009年3月28日 11:36 HTMLタグがおかしいので修正
    • 回答としてマーク 江藤健二 2009年4月3日 2:46
    2009年3月28日 11:31
  • FireFoxだとストリームのままでも印刷できますが、IE7では印刷できませんね。

    わざわざファイルに保存してアクセスさせると管理が大変になるので、保存させない手段を使ったほうがいいと思います。

    手段の例
    Imageを貼り付けたページを用意する。
    そのImageのImageUrlにイメージ作成aspxを設定してやる。
    イメージ作成aspxにリクエストがあったら、先に例示したように生成した画像ストリームを返すようにします。

    ImageUrlのアドレスはファイルとして存在している必要はありません。
    aspxで生成してしまえばいいのです。
    • 回答としてマーク 江藤健二 2009年4月3日 2:46
    2009年4月1日 11:40
  • その方法でも出来ますが、http://code.msdn.microsoft.com/mschartにあるWebSamplesにはUsingWithLegacyImageというのが含まれています。
    RenderType="BinaryStreaming"を指定するのかな。chart.aspx.cs側はチャート設定以外の処理は不要になります。
    • 回答としてマーク 江藤健二 2009年4月3日 5:50
    2009年4月3日 3:57

すべての返信

  • たぶん印刷するとにじむというのはブラウザやプリンタが数百dpiといった解像度に拡大印刷しているからです。
    ですからどのように滲むかは環境次第だと思います。
    AntiAliasingプロパティやTextAntiAliasingQualityを変更すれば多少は滲むのは抑えられるでしょうがカクカクした画像になってしまうでしょう。

    任意のサイズに拡大した画像を生成するのは以下の様な感じになります。

    /// <summary>チャートを指定したサイズに拡大してJPEGで送る/summary>
    /// <param name="response">送信するResponse</param>
    /// <param name="chart">元画像とするチャート</param>
    /// <param name="pixcelWidth">拡大する横幅のピクセル数</param>
    /// <param name="pixcelHeight">拡大する高さのピクセル数</param>
    public void ResponseChartImage(HttpResponse response , System.Web.UI.DataVisualization.Charting.Chart chart , int pixcelWidth , int pixcelHeight)
    {
        //送信する画像の大きさのBitmapを作る
        System.Drawing.Bitmap bmp = new Bitmap(pixcelWidth,pixcelHeight);
        System.Drawing.Graphics g = System.Drawing.Graphics.FromImage(bmp);

        //スケール変換する
        //スケール変換せずに単純にBitmapに書かせると文字が小さくなってしまいます
        g.Transform = new System.Drawing.Drawing2D.Matrix((float)((float)pixcelWidth / chart.Width.Value) , 0 , 0 , (float)((float)pixcelHeight / chart.Height.Value) , 0 , 0);
        chart.Paint(g , new Rectangle(0 , 0 , (int)chart.Width.Value  , (int)chart.Height.Value ));
        g.Dispose();

        ///JPEG形式でストリームに出力
        response.ClearContent();
        response.ContentType = "image/jpeg";
        bmp.Save(response.OutputStream , System.Drawing.Imaging.ImageFormat.Jpeg);
    }

    #白黒化はグレースケールといったキーワードで検索すれば見つかります。


    • 編集済み gekkaMVP 2009年3月28日 11:36 HTMLタグがおかしいので修正
    • 回答としてマーク 江藤健二 2009年4月3日 2:46
    2009年3月28日 11:31
  • お世話になります。

    gekkaさま、アドバイスありがとうございます。
    サンプルソースを参考にさせて頂き、
    チャートのイメージを、滲みが少ないストリーム形式の状態で表示するとは可能になりました。


    今回の目的は、チャート(折れ線グラフ)と、そのデータの一覧表(TABLEで囲んだデータ一覧)の印刷なのですが、
    作成されたチャート画像の印刷ができなかったので、
     (ブラウザからそのまま印刷をしたら、イメージ部分が白紙状態で印刷されました。
     「ストリーム形式のイメージは印刷が出来ない」と認識しているのですが…その時点でそれを思い出した次第です)
    印刷が可能な画像を生成する方法を考えてみようと思います。


    現在、以下のようにして、PNG画像を動的に生成しようとしています。
    -----
       (略)
        :
        :
    // chartimage.pngを生成する
    bmp.Save("c:\\chartimage.png", System.Drawing.Imaging.ImageFormat.Png);
    -----

    現在、自PC(localhost)でテストを行っております。
    その場合、保存先の設定を、上記のような絶対パスではなく、
    現在実行中のaspxファイルが格納されているディレクトリ内に作成できる様に
    相対パスに変更できないものかと四苦八苦しつつ行き詰まっております。

    (パスを 以下の様に
    bmp.Save("chartimage.png", System.Drawing.Imaging.ImageFormat.Png);
     と設定すると、 dllが大量に格納されている
    C:\Program Files\Microsoft Visual Studio 9.0\Common7\IDE
     に画像が作成されてしまいます)

    引き続き、良い参考資料がないか、探してみようと思います。

    2009年4月1日 0:01
  • FireFoxだとストリームのままでも印刷できますが、IE7では印刷できませんね。

    わざわざファイルに保存してアクセスさせると管理が大変になるので、保存させない手段を使ったほうがいいと思います。

    手段の例
    Imageを貼り付けたページを用意する。
    そのImageのImageUrlにイメージ作成aspxを設定してやる。
    イメージ作成aspxにリクエストがあったら、先に例示したように生成した画像ストリームを返すようにします。

    ImageUrlのアドレスはファイルとして存在している必要はありません。
    aspxで生成してしまえばいいのです。
    • 回答としてマーク 江藤健二 2009年4月3日 2:46
    2009年4月1日 11:40
  • お世話になっております。
    早速、「Image」でストリームが表示できるように、サンプルアプリを作成してみました。

    --------------------
    ■プロジェクト内の同ディレクトリ内に、以下のaspxを準備
      chart.aspx
       (ChartControlの画像イメージをストリーム形式で生成するaspx)
      Default.aspx
       (Image、TextBox、Labelなどを配置したaspx)

    --------------------
    ---------------
    chart.aspx.cs
    ---------------
    protected void Page_Load(object sender, EventArgs e)
    {
        // チャート設定
        SetChart();
        // ストリーム画像
        ResponseChartImage(System.Web.HttpContext.Current.Response, チャート名, 1000, 700);
    }
    ---------------
    Default.aspx
    ---------------
          :
       <asp:Image ID="Image" runat="server" ImageUrl="~/chart.aspx" Width="500px" Height="350px" />
         (略)
    ---------------

    Default.aspxに、ストリーム形式のチャート画像がImageに返されるようになりました。
    こちらの方法で、Microsoftチャートコントロールを含む印刷について解決しました。


    アドバイスいただき、ありがとうございました!

    [追記]
    PNG形式でストリーム出力できる様、以下を参照させていただきました。

    [@IT会議室:GDI+で一般的なエラーが発生しました]
    http://www.atmarkit.co.jp/bbs/phpBB/viewtopic.php?topic=13363&forum=7

    2009年4月3日 2:44
  • その方法でも出来ますが、http://code.msdn.microsoft.com/mschartにあるWebSamplesにはUsingWithLegacyImageというのが含まれています。
    RenderType="BinaryStreaming"を指定するのかな。chart.aspx.cs側はチャート設定以外の処理は不要になります。
    • 回答としてマーク 江藤健二 2009年4月3日 5:50
    2009年4月3日 3:57
  • 情報をありがとうございます!

    RenderType="BinaryStreaming" をキーワードに、サンプルを検索してみました。

    http://code.msdn.microsoft.com/mschart/Release/ProjectReleases.aspx?ReleaseId=1591
     サンプルをダウンロードし、とりあえずlocalhostで実行中)

    Rendering のサンプルに、BinaryStreaming の事例がありました。

    こちらもどこまでの処理が可能なのか試してみたいと思います。

    2009年4月3日 5:50