using System;
using System.Drawing;
using System.Drawing.Imaging;
using System.Web.UI;
namespace Xcrm.Module.Report
{
public class DrawChart : Page
{
protected void Page_Load(object sender, EventArgs e)
{
// 依需求切換:DrawBarChart() 或 DrawPieChart()
DrawBarChart();
}
// 長條圖
private void DrawBarChart()
{
Bitmap bmp = new Bitmap(400, 300);
using (Graphics g = Graphics.FromImage(bmp))
{
g.Clear(Color.Snow);
string[] labels = { "很好", "好", "普通", "差" };
int[] values = { 1000, 69, 90, 2000 };
int count = values.Length;
int barWidth = 40;
float[] heights = new float[count];
// 計算相對高度 (最大值對應 200 像素)
int total = 0;
foreach (int v in values) total += v;
for (int i = 0; i < count; i++)
heights[i] = 200f * values[i] / total;
// 標題
g.DrawString("調查統計結果一覽圖", new Font("微軟正黑體", 12, FontStyle.Bold), Brushes.Black, 75, 10);
// 圖例區域
Point legendRect = new Point(300, 40);
Point legendText = new Point(320, 40);
for (int i = 0; i < count; i++)
{
Color c = GetColor(i);
// 圖例色塊
g.DrawRectangle(Pens.Black, legendRect.X, legendRect.Y, 20, 10);
g.FillRectangle(new SolidBrush(c), legendRect.X, legendRect.Y, 20, 10);
g.DrawString(" " + labels[i], new Font("微軟正黑體", 9), Brushes.Black, legendText);
legendRect.Y += 15;
legendText.Y += 15;
// 長條圖 (從底部 290 向上畫)
float h = heights[i];
int x = i * barWidth + 15;
int y = 290 - (int)h;
g.DrawRectangle(Pens.Black, x, y, 20, (int)h + 5);
g.FillRectangle(new SolidBrush(c), x, y, 20, (int)h + 5);
g.DrawString(values[i].ToString(), new Font("微軟正黑體", 9), Brushes.Black, x + 5, y - 15);
}
// 邊框
g.DrawRectangle(Pens.Black, 1, 1, 398, 298);
// 輸出 JPEG
Response.ContentType = "image/jpeg";
bmp.Save(Response.OutputStream, ImageFormat.Jpeg);
}
}
// 圓餅圖
private void DrawPieChart()
{
Bitmap bmp = new Bitmap(400, 300);
using (Graphics g = Graphics.FromImage(bmp))
{
g.Clear(Color.Snow);
string[] labels = { "很好", "好", "普通", "差" };
int[] values = { 1000, 69, 90, 20 };
int count = values.Length;
float[] angles = new float[count];
int total = 0;
foreach (int v in values) total += v;
for (int i = 0; i < count; i++)
angles[i] = 360f * values[i] / total;
g.DrawString("調查統計結果一覽圖", new Font("微軟正黑體", 12, FontStyle.Bold), Brushes.Black, 75, 10);
g.DrawString("單位:次", new Font("微軟正黑體", 9), Brushes.Black, 300, 25);
Point legendRect = new Point(300, 40);
Point legendText = new Point(320, 40);
float startAngle = 0;
Rectangle pieRect = new Rectangle(50, 50, 200, 200);
for (int i = 0; i < count; i++)
{
Color c = GetColor(i);
float sweep = (i == count - 1) ? 360 - startAngle : angles[i]; // 修正累積誤差
// 圖例
g.DrawRectangle(Pens.Black, legendRect.X, legendRect.Y, 20, 10);
g.FillRectangle(new SolidBrush(c), legendRect.X, legendRect.Y, 20, 10);
g.DrawString($" {labels[i]} {values[i]}", new Font("微軟正黑體", 9), Brushes.Black, legendText);
legendRect.Y += 15;
legendText.Y += 15;
// 扇形
g.FillPie(new SolidBrush(c), pieRect, startAngle, sweep);
g.DrawPie(Pens.Black, pieRect, startAngle, sweep);
startAngle += sweep;
}
g.DrawRectangle(Pens.Black, 1, 1, 398, 298);
Response.ContentType = "image/jpeg";
bmp.Save(Response.OutputStream, ImageFormat.Jpeg);
}
}
private Color GetColor(int index)
{
Color[] colors = { Color.Red, Color.Blue, Color.Yellow, Color.Green,
Color.Pink, Color.Plum, Color.Gray, Color.Salmon,
Color.RosyBrown, Color.Teal, Color.Orange, Color.Thistle, Color.Maroon };
return colors[index % colors.Length];
}
}
}
<img src="DrawChart.aspx" alt="統計圖表" />
或動態切換:DrawChart.aspx?type=pie 在 Page_Load 判斷 Request["type"]。
Bitmap + Graphics.FromImage 離屏繪圖。FillRectangle/DrawRectangle 繪製長條;FillPie/DrawPie 繪製扇形。y = bottom - height。Response.OutputStream 直接輸出二進位圖片,無需暫存檔。using 確保 Graphics/Bitmap 及時釋放非受控 GDI 資源。System.Drawing.Common (僅支援 Windows)。