• 模仿CSDN的投票饼图(conanlwl的个人BLOG)


    模仿了CSDN的饼图源代码

    看了http://dev.csdn.net/里右侧的投票饼图,觉得挺有趣的,

    所以就自己也模仿了一个..演示页面:http://www.conanlwl.net/bbspic/TestVote.aspx

    具体步骤如下..(C#) 

    本例子中利用XML文件来保存投票数据.XML文件格式如下,文件名称为Vote.XML 

    <?xml version="1.0" encoding="utf-8"?>
    <Vote>
      
    <VoteInfo>
        
    <ID>1</ID>
        
    <VoteTitle>以下三国人物你喜欢谁?</VoteTitle>
        
    <Item>
          
    <VoteID>1</VoteID>
          
    <Title>曹操</Title>
          
    <Count>2</Count>
        
    </Item>
        
    <Item>
          
    <VoteID>2</VoteID>
          
    <Title>刘备</Title>
          
    <Count>2</Count>
        
    </Item>
        
    <Item>
          
    <VoteID>3</VoteID>
          
    <Title>孙权</Title>
          
    <Count>2</Count>
        
    </Item>
        
    <Item>
          
    <VoteID>4</VoteID>
          
    <Title>司马懿</Title>
          
    <Count>2</Count>
        
    </Item>
        
    <Item>
          
    <VoteID>5</VoteID>
          
    <Title>诸葛亮</Title>
          
    <Count>1</Count>
        
    </Item>
        
    <Item>
          
    <VoteID>6</VoteID>
          
    <Title>陆逊</Title>
          
    <Count>1</Count>
        
    </Item>
        
    <Item>
          
    <VoteID>7</VoteID>
          
    <Title>吕布</Title>
          
    <Count>1</Count>
        
    </Item>
        
    <Item>
          
    <VoteID>8</VoteID>
          
    <Title>姜维</Title>
          
    <Count>1</Count>
        
    </Item>
        
    <Item>
          
    <VoteID>9</VoteID>
          
    <Title>其它</Title>
          
    <Count>2</Count>
        
    </Item>
      
    </VoteInfo>
    </Vote>

    第一步,就是投票页面了,我们就通过这个页面来进行对选项的投票.新建一个WebForm,并命名为TestVote.aspx

    <HTML>
        
    <HEAD>
            
    <title>模仿CSDN的投票结果</title>
            
    <meta name="GENERATOR" Content="Microsoft Visual Studio .NET 7.1">
            
    <meta name="CODE_LANGUAGE" Content="C#">
            
    <meta name="vs_defaultClientScript" content="JavaScript">
            
    <meta name="vs_targetSchema" content="http://schemas.microsoft.com/intellisense/ie5">
            
        
    </HEAD>
        
    <body>
            
    <form id="Form1" method="post" runat="server">
                
                
    <fieldset style="WIDTH:20%;float:left">
                
    <legend accesskey="F"  style="FONT-WEIGHT:bold;COLOR:#000000;font-size:12px" align=center>
                        
    <%=VoteTitle%></legend>
                        
    <ul style="list-style-type:none;margin-left:50px">
                        
    <%for(int i=0;i<xnl.Count;i++)
                        {
                         System.Xml.XmlNode xn 
    = xnl.Item(i);
    %>
                        
    <li>
                        
    <input type=checkbox name="vote" value="<%=xn.SelectSingleNode("VoteID").InnerText%>" /><%=xn.SelectSingleNode("Title").InnerText%> 
                    
    <%}%>
                    
    </li>
                    
    </ul>
                    
    <div align=center><asp:Button id="Button1" runat="server" Text="投票"></asp:Button>&nbsp;&nbsp;<input type=button value="查看结果" onclick="javascript:var url='ShowVote.aspx?i=0&voteid=<%=Request.QueryString["VoteID"]%>';window.open(url,'_blank','left=10,top=20,width=675,height=360');return false;" /></div>
                
    </fieldset>
                
            
    </form>
        
    </body>
    </HTML>

    以下是testvote.aspx.cs的代码

    using System;
    using System.Collections;
    using System.ComponentModel;
    using System.Data;
    using System.Drawing;
    using System.Web;
    using System.Web.SessionState;
    using System.Web.UI;
    using System.Web.UI.WebControls;
    using System.Web.UI.HtmlControls;

    using System.Xml;

    namespace BbsPic
    {
        
    /// <summary>
        
    /// TestVote 的摘要说明。
        
    /// </summary>

        public class TestVote : System.Web.UI.Page
        
    {
            
    protected XmlNodeList xnl;
            
    protected string VoteTitle = "";
            
    protected System.Web.UI.WebControls.Button Button1;

            
    private XmlDocument myDoc = new XmlDocument();
            
    private void Page_Load(object sender, System.EventArgs e)
            
    {
                
    // 在此处放置用户代码以初始化页面
                if(!IsPostBack)
                    BindXML(
    "1");
            }


            
    Web 窗体设计器生成的代码
            
    private void BindXML(string VoteID)
            
    {
                
                myDoc.Load(Server.MapPath(
    "Vote.xml"));

                XmlNode xn 
    = myDoc.SelectSingleNode("//VoteInfo[ID='" + VoteID + "']");        
                VoteTitle 
    = xn.SelectSingleNode("VoteTitle").InnerText;
                xnl 
    = xn.SelectNodes("Item");
            }


            
    private void Button1_Click(object sender, System.EventArgs e)
            
    {
                
    //string VoteID = Request.QueryString["VoteID"];
                string VoteID = "1";
                
    if(Request.Cookies["IsVote"]!=null)
                
    {
                    Response.Write(
    "<script>alert('对不起,你已投过票!');document.location=document.location;</script>");
                }

                
    else
                
    {
                    
                    
    if(Request.Form["Vote"!= null && Request.Form["Vote"!= "")
                    
    {
                        
    string[] votes = Request.Form["Vote"].Split(',');
                        myDoc.Load(Server.MapPath(
    "Vote.xml"));

                        XmlNode xn 
    = myDoc.SelectSingleNode("//VoteInfo[ID='" + VoteID + "']");        

                        
    for(int i=0;i<votes.Length;i++)
                        
    {
                            XmlNode xn0 
    = xn.SelectSingleNode("Item[VoteID='" + votes[i] + "']");
                            xn0.SelectSingleNode(
    "Count").InnerText = Convert.ToString(Convert.ToInt32(xn0.SelectSingleNode("Count").InnerText) + 1);
                        }

                        myDoc.Save(Server.MapPath(
    "Vote.xml"));
                    }

                    Response.Cookies[
    "IsVote"].Value = "true";
                    Response.Cookies[
    "IsVote"].Expires.AddHours(1);

                    Response.Write(
    "<script>window.open('ShowVote.aspx?i=0&voteid=" + VoteID + "','_blank','left=10,top=20,width=675,height=360');document.location='TestVote.aspx?voteid=" + VoteID + "';</script>");
                    
                }

                Response.End();
            }

        }

    }

    第二步,就是我们的饼图图片页面,最后以二进制流的方式显示出来..本饼图有两种状态,一是没被点中时的全圆饼图,第二就是当某个选项被点中时分离出来的饼图.新建一WebForm窗体,命名为Vote.aspx

    在Vote.aspx里把除了<%page ....%>以外的HTML代码全部删掉.

    接着是Vote.aspx.cs的代码

    using System;
    using System.Collections;
    using System.ComponentModel;
    using System.Data;
    using System.Drawing;
    using System.Web;
    using System.Web.SessionState;
    using System.Web.UI;
    using System.Web.UI.WebControls;
    using System.Web.UI.HtmlControls;

    using System.Xml;

    namespace BbsPic
    {
        
    /// <summary>
        
    /// Vote 的摘要说明。
        
    /// </summary>

        public class Vote : System.Web.UI.Page
        
    {
            
    private void Page_Load(object sender, System.EventArgs e)
            
    {
                DrawPic(Convert.ToInt32(Request.QueryString[
    "i"]==""?"0":Request.QueryString["i"]),1);
            }


            
    Web 窗体设计器生成的代码

            
    private void DrawPic(int iSelect,int VoteID)
            
    {
                XmlDocument myDoc 
    = new XmlDocument();
                myDoc.Load(Server.MapPath(
    "Vote.xml"));

                XmlNode xn 
    = myDoc.SelectSingleNode("//VoteInfo[ID='" + VoteID + "']");        
        
                XmlNodeList xnl 
    = xn.SelectNodes("Item");
                
                
                
    float[] angle = new float[xnl.Count];
                
    string[] sTxt = new string[xnl.Count];
                
    float AllCount = 0;
                
                
    for(int i=0;i<xnl.Count;i++)
                
    {
                    
                    AllCount 
    += Convert.ToSingle(xnl.Item(i).SelectSingleNode("Count").InnerText);

                }


                
    for(int i=0;i<xnl.Count;i++)
                
    {
                    XmlNode xn0 
    = xnl.Item(i);
                    angle[i] 
    = Convert.ToSingle(xn0.SelectSingleNode("Count").InnerText) * 360.0f / AllCount;
                    sTxt[i] 
    = xn0.SelectSingleNode("Title").InnerText;
                }

    //
    //            float[] angle    = new float[]{32,58,40,40,28,27,33,72,30};
    //            string[] sTxt = new string[]{"一","二","三三三三三","四四四四四四","五五","六六","七七七","八八八八","九九九九"};
                


                
    float x=120.0f,y=80.0f,d=200.0f,offset=15.0f,x1=0.0f,y1=0.0f;//圆形x,y坐标,半径,偏移距离,x,y方向的偏移值
                float curangle=0.0f;//当前已转的角度

                
    int ox=0,oy=0;//圆心坐标
                int px1=0,py1=0,px2=0,py2=0;//直线的端点
                
                System.Drawing.Image bitmap 
    = new Bitmap(675,360,System.Drawing.Imaging.PixelFormat.Format32bppPArgb);
                Graphics g 
    = Graphics.FromImage(bitmap);

                g.InterpolationMode 
    = System.Drawing.Drawing2D.InterpolationMode.High;
                g.SmoothingMode
    = System.Drawing.Drawing2D.SmoothingMode.HighQuality;

                
    //20项颜色。
                Color[] color=new Color[]{Color.Black,Color.Blue,Color.Coral,Color.DarkGoldenrod,Color.Firebrick,Color.Gold,Color.Honeydew,Color.Indigo,Color.Khaki,Color.LemonChiffon,Color.Maroon,Color.Navy,
                                             Color.Orange,Color.PapayaWhip,Color.Red,Color.Salmon,Color.Thistle,Color.Violet,Color.Wheat,Color.YellowGreen}
    ;

                g.Clear(Color.FromArgb(
    255,228,181));//清屏

                StringFormat sf 
    = new StringFormat();
                sf.Alignment 
    = StringAlignment.Center;
                
                g.DrawString(xn.SelectSingleNode(
    "VoteTitle").InnerText,new Font(FontFamily.GenericSansSerif,12),new SolidBrush(Color.Black),new RectangleF(0.0f,10.0f,675.0f,20.0f),sf);
                g.DrawString(
    "Power By Http://www.conanlwl.net/",new Font(FontFamily.GenericSansSerif,12),new SolidBrush(Color.Black),new RectangleF(300.0f,300.0f,375.0f,20.0f),sf);


                
    //画右侧的大矩形
                g.FillRectangle(new SolidBrush(Color.FromArgb(128,128,128)),482,122,80,(angle.Length+1* 12);//阴影
                g.FillRectangle(new SolidBrush(Color.FromArgb(253,245,230)),480,120,80,(angle.Length+1* 12);//前景
                g.DrawRectangle(new Pen(Color.FromArgb(128,128,128),1),480,120,80,(angle.Length+1* 12);//轮廓
                /////////////////////////////////////////////
                
                
    for(int i=0;i< angle.Length;i++)
                
    {

                    
                    sf.Alignment 
    = StringAlignment.Near;

                    
    if(i == iSelect-1)
                    
    {
                        x1 
    = Convert.ToSingle(offset * Math.Cos((curangle + angle[i]/2)*Math.PI/180.0f));
                        y1 
    = Convert.ToSingle(offset * Math.Sin((curangle + angle[i]/2)*Math.PI/180.0f));

                        ox 
    = Convert.ToInt32(x + d/2 + x1);
                        oy 
    = Convert.ToInt32(y + d/2 + y1);

                        px1 
    = Convert.ToInt32((d/2 + 20)  * Math.Cos((curangle + angle[i]/2)*Math.PI/180.0f)) + ox;
                        py2 
    = py1 = Convert.ToInt32((d/2 + 20)  * Math.Sin((curangle + angle[i]/2)*Math.PI/180.0f)) + oy;

                        
    if((curangle + angle[i]/2)>=270 || (curangle + angle[i]/2)<90) px2=px1 + 20;
                        
    else px2=px1 - 20;

                        

                        g.DrawLine(
    new Pen(Color.FromArgb(120,120,120),1),new Point(ox,oy),new Point(px1,py1));//画直线-标释用。
                        g.DrawLine(new Pen(Color.FromArgb(120,120,120),1),new Point(px1,py1),new Point(px2,py2));//直线
                        
                        
    if((curangle + angle[i]/2)>=270 || (curangle + angle[i]/2)<90//写文字
                        {
                            
                            g.DrawString(sTxt[i],
    new Font(FontFamily.GenericSansSerif,8),new SolidBrush(Color.FromArgb(120,120,120)),px2 ,py2 - 4,sf);
                        }

                        
    else
                        
    {
                            
                            g.DrawString(sTxt[i],
    new Font(FontFamily.GenericSansSerif,8),new SolidBrush(Color.FromArgb(120,120,120)),px2 - sTxt[i].Length * 12-2 ,py2 - 4,sf);
                        }


                        g.FillPie(
    new SolidBrush(Color.FromArgb(128,128,128)),x + x1 + 2,y + y1 + 2,d,d,curangle,angle[i]);//画饼图的阴影
                        g.FillPie(new SolidBrush(color[i]),x + x1,y + y1,d,d,curangle,angle[i]);                    //画饼图
                        g.DrawPie(new Pen(Color.FromArgb(128,128,128),1),x + x1,y + y1,d,d,curangle,angle[i]); //画轮廓


                        

                    }

                    
    else
                    
    {        
                        ox 
    = Convert.ToInt32(x + d/2);
                        oy 
    = Convert.ToInt32(y + d/2);

                        px1 
    = Convert.ToInt32((d/2 + 20)  * Math.Cos((curangle + angle[i]/2)*Math.PI/180.0f)) + ox;
                        py2 
    = py1 = Convert.ToInt32((d/2 + 20)  * Math.Sin((curangle + angle[i]/2)*Math.PI/180.0f)) + oy;

                        
    if((curangle + angle[i]/2)>=270 || (curangle + angle[i]/2)<90) px2=px1 + 20;
                        
    else px2=px1 - 20;

                        

                        g.DrawLine(
    new Pen(Color.FromArgb(120,120,120),1),new Point(ox,oy),new Point(px1,py1));
                        g.DrawLine(
    new Pen(Color.FromArgb(120,120,120),1),new Point(px1,py1),new Point(px2,py2));

                        
    if((curangle + angle[i]/2)>=270 || (curangle + angle[i]/2)<90
                        
    {
                            
                            g.DrawString(sTxt[i],
    new Font(FontFamily.GenericSansSerif,8),new SolidBrush(Color.FromArgb(120,120,120)),px2 ,py2 - 4,sf);
                        }

                        
    else
                        
    {
                            
                            g.DrawString(sTxt[i] ,
    new Font(FontFamily.GenericSansSerif,8),new SolidBrush(Color.FromArgb(120,120,120)),px2 - sTxt[i].Length * 12-2 ,py2 - 4,sf);
                        }


                        g.FillPie(
    new SolidBrush(Color.FromArgb(128,128,128)),x+2,y+2,d,d,curangle,angle[i]);
                        g.FillPie(
    new SolidBrush(color[i]),x,y,d,d,curangle,angle[i]);
                        
                        g.DrawPie(
    new Pen(Color.FromArgb(128,128,128),1),x,y,d,d,curangle,angle[i]);
                        
                    }

                    curangle 
    += angle[i];

                    
    //画右侧的小矩形,与文字
                    g.FillRectangle(new SolidBrush(Color.FromArgb(128,128,128)),492,i*12 + 6 + 120 + 2,20,8);//阴影
                    g.FillRectangle(new SolidBrush(color[i]),490,i*12 + 6 + 120,20,8);//前景
                    g.DrawRectangle(new Pen(Color.FromArgb(120,120,120),1),490,i*12+6+120,20,8);//轮廓

                    g.DrawString(sTxt[i],
    new Font(FontFamily.GenericSansSerif,7),new SolidBrush(Color.FromArgb(80,80,80)),515,i*12 + 6+ 120,sf);


                }


                

                System.IO.MemoryStream ms 
    = new System.IO.MemoryStream(); 
                bitmap.Save(ms, System.Drawing.Imaging.ImageFormat.Png); 
                Response.ClearContent(); 
                Response.ContentType 
    = "image/Png"
                Response.BinaryWrite(ms.ToArray()); 
            }

        }

    }

    第三步,因为要使图片里的饼图的某个选项能够点击,就必须要由另外一个页面来装载这个图片,并在图片上描绘热点.所以就必须新建一个窗体,这个窗体也是"显示投票结果"的显示页面.

    新建一个WebForm窗体,并命名为ShowVote.aspx

    以下是ShowVote.aspx的HTML代码:

    <HTML>
        
    <HEAD>
            
    <title>查看投票结果</title>
            
    <meta name="GENERATOR" Content="Microsoft Visual Studio .NET 7.1">
            
    <meta name="CODE_LANGUAGE" Content="C#">
            
    <meta name="vs_defaultClientScript" content="JavaScript">
            
    <meta name="vs_targetSchema" content="http://schemas.microsoft.com/intellisense/ie5">
        
    </HEAD>
          
    <body topmargin=0 leftmargin=0>
        
    <img src="Vote.Aspx?i=<%=Request.QueryString["i"]%>&voteid=<%=Request.QueryString["voteid"]%>" USEMAP="#Map" border=0>
        
        
    <MAP NAME="Map">
            
    <%=Map%>
        
    </map>
        
      
    </body>
    </HTML>

    以下是ShowVote.aspx.cs的代码:

    using System;
    using System.Collections;
    using System.ComponentModel;
    using System.Data;
    using System.Drawing;
    using System.Web;
    using System.Web.SessionState;
    using System.Web.UI;
    using System.Web.UI.WebControls;
    using System.Web.UI.HtmlControls;

    using System.Xml;

    namespace BbsPic
    {
        
    /// <summary>
        
    /// ShowVote 的摘要说明。
        
    /// </summary>

        public class ShowVote : System.Web.UI.Page
        
    {
            
    protected string Map = "";
            
    private void Page_Load(object sender, System.EventArgs e)
            
    {
                
    if(Request.QueryString["i"]!="" && Request.QueryString["i"!= null)
                    Map 
    = DrawMap(Convert.ToInt32(Request.QueryString["i"]),1);
            }


            
    Web 窗体设计器生成的代码

            
    private string DrawMap(int iSelect,int VoteID)
            
    {
                
    string str = "";

                
    //float[] angle    = new float[]{32,58,40,40,28,27,33,72,30};
                
    //string[] sTxt = new string[]{"一","二","三三三三三","四四四四四四","五五","六六","七七七","八八八八","九九九九"};        

                XmlDocument myDoc 
    = new XmlDocument();
                myDoc.Load(Server.MapPath(
    "Vote.xml"));

                XmlNode xn 
    = myDoc.SelectSingleNode("//VoteInfo[ID='" + VoteID + "']");        
        
                XmlNodeList xnl 
    = xn.SelectNodes("Item");
                
                
                
    float[] angle = new float[xnl.Count];
                
    string[] sTxt = new string[xnl.Count];
                
    float AllCount = 0;
                
                
    for(int i=0;i<xnl.Count;i++)
                
    {
                    
                    AllCount 
    += Convert.ToSingle(xnl.Item(i).SelectSingleNode("Count").InnerText);

                }


                
    for(int i=0;i<xnl.Count;i++)
                
    {
                    XmlNode xn0 
    = xnl.Item(i);
                    angle[i] 
    = Convert.ToSingle(xn0.SelectSingleNode("Count").InnerText) * 360.0f / AllCount;
                    sTxt[i] 
    = xn0.SelectSingleNode("Title").InnerText;
                }


                

                
    float x=120.0f,y=80.0f,d=200.0f,offset=15.0f,x1=0.0f,y1=0.0f;//圆形x,y坐标,半径,偏移距离,x,y方向的偏移值
                float curangle=0.0f;//当前已转的角度    

                
    int oAngle = 4;//描点偏移的度数,越小,圆弧就越圆滑。
                
                
    int ox=0,oy=0;//圆心坐标
                
                
    for(int i=0;i< angle.Length;i++)
                
    {
                    
    if(i == iSelect-1)
                    
    {
                        x1 
    = Convert.ToSingle(offset * Math.Cos((curangle + angle[i]/2)*Math.PI/180.0f));
                        y1 
    = Convert.ToSingle(offset * Math.Sin((curangle + angle[i]/2)*Math.PI/180.0f));                        
                        
                        ox 
    = Convert.ToInt32(x + d/2 + x1);
                        oy 
    = Convert.ToInt32(y + d/2 + y1);
                    }

                    
    else
                    
    {
                        ox
    =Convert.ToInt32(x + d/2);
                        oy
    =Convert.ToInt32(y + d/2);
                    }

                

                    str 
    += "<AREA SHAPE="poly" HREF="?i=" + (i+1+ "&VoteID=" + VoteID + "" TITLE="" + sTxt[i] + ";票数:"  + xnl.Item(i).SelectSingleNode("Count").InnerText + ""  COORDS="";
                    str 
    += ox + "," + oy; //圆心    
                    str += "," + (Convert.ToInt32(d/2 *  Math.Cos(curangle * Math.PI/180.0f)) + ox) + "," + (Convert.ToInt32(d/2 *  Math.Sin(curangle * Math.PI/180.0f)) + oy);//圆弧的第一个端点的坐标
                    float MaxAngle = curangle + angle[i];
                    
    while(true)
                    
    {
                        curangle 
    += oAngle;
                        
    if(curangle >= MaxAngle)//圆弧上的另一个端点,也即最后一个点
                        {
                            curangle 
    = MaxAngle;
                            str 
    += "," + (Convert.ToInt32(d/2 *  Math.Cos(curangle * Math.PI/180.0f)) + ox) + "," + (Convert.ToInt32(d/2 *  Math.Sin(curangle * Math.PI/180.0f)) + oy);
                            
    break;
                        }

                        
    else //圆弧上的点
                        {
                            str 
    += "," + (Convert.ToInt32(d/2 *  Math.Cos(curangle * Math.PI/180.0f)) + ox) + "," + (Convert.ToInt32(d/2 *  Math.Sin(curangle * Math.PI/180.0f)) + oy);
                        }

                    }

                        
        

                    str 
    += ""> ";
                    
    //490,i*12 + 6 + 120,20,8
                }


                
    for(int i=0;i< angle.Length;i++)//描右侧小方形的点
                {
                    str 
    += "<AREA SHAPE="rect" HREF="?i=" + (i+1+ "&voteid=" + VoteID + "" TITLE="" + Convert.ToSingle(Convert.ToSingle(xnl.Item(i).SelectSingleNode("Count").InnerText)*100.0f/AllCount).ToString("F"+ "%" COORDS="";
                    
                    str 
    += "490," + (i*12+6+120+ "," + (490+20+ "," + (i*12+6+120+8);            
                    
                    str 
    += ""> ";
                }


                
    return str;
            }

        }

    }

  • 相关阅读:
    [转载]Delphi 2009 (Tiburon) 新特性之 Exit 函数的新用法
    [转载][转]Delphi 2009 泛型+闭包能带来什么?
    [转载]现有 Delphi 项目迁移到 Tiburon 中的注意事项 (中)
    [转载]现有 Delphi 项目迁移到 Tiburon 中的注意事项 (上)
    [转载]现有 Delphi 项目迁移到 Tiburon 中的注意事项 (下)
    [转载]Delphi 2009 (Tiburon) 新特性之 Unicode 支持!
    [转载]Tiburon 支持 Unicode 的 LoadFromFile, SaveToFile
    GdiPlus[37]: IGPGraphicsPath (四) 路径变换
    GdiPlus[36]: IGPGraphicsPath (三) 路径中的数据
    GdiPlus[43]: IGPGraphics (二) 关于文本绘制
  • 原文地址:https://www.cnblogs.com/mephisto/p/765925.html
Copyright © 2020-2023  润新知