Jfreechart本身不能生成SVG圖形,但是可以藉助另外一個東西,輔助生成.好像是這個:batik ,具體代碼請看下文
一:Java生成svg餅圖,附帶了一個標籤顯示各個顏色代表的部分
package com.tellhow.svg;import java.io.File;import java.io.FileOutputStream;/** * * @author 風絮NO.1 * */public class CakySvgWithLabel { //定義不同的顏色static String[] colors ={"#f2e692", "#aa1111", "#799AE1", "#3e941b", "#66cc00", "#297110", "#d6a97b", "#82522b", "#aaaaff", "# 1111aa", "#ff2222", "#ffaaaa"}; static String initialize(double [] percents,String[]names){ StringBuffer sfile = new StringBuffer(); sfile.append("<?xml version='1.0' encoding='UTF-8'?>"); sfile.append("/n"); sfile.append("<svg xmlns:svg='http://www.w3.org/2000/svg'") ; sfile.append("/n"); sfile.append("xmlns='http://www.w3.org/2000/svg'"); sfile.append("/n"); sfile.append( "xmlns:xlink='http://www.w3.org/1999/xlink'"); sfile.append("/n"); sfile.append("xml:space='default'"); sfile. append("/n"); sfile.append("version='1.1' width='100%' height='100%' viewBox='0 0 2024 570'>"); sfile.append("/n" ); sfile.append("<defs></defs>"); sfile.append("/n"); sfile.append("<g stroke-width='1' stroke='#FFFFFF' transform=' matrix(1,0,0,1,16.384,-9.83)' xmlns='http://www.w3.org/2000/svg'>"); sfile.append("/n"); //循環創造path標籤. String path =creatPath(502, 300, 300, percents,names);//中心點式503,300. sfile.append(path); sfile.append("</g>"); sfile.append( "/n"); sfile.append("</svg>"); return sfile.toString(); } /** * * @param x0 中心點橫坐標* @param y0 中心點縱坐標* @param r半徑* @param percents 百分比數組* @param names 顯示顏色代表的名稱* @return */ public static String creatPath(double x0,double y0,double r,double[]percents,String[]names){ StringBuffer sfile =new StringBuffer(); double x1=0; //新扇形的x坐標double y1=0; //新扇形的y坐標double middleX=0; //文本顯示的坐標,包括豎線顯示的坐標double middleY=0 ; double radian =0; //弧度double textRadian=0; //文本顯示位置度弧度double k=0; int N=10; for(int i=0;i<percents.length;i++){ if(i ==0){ radian =getRadian(percents[0]); textRadian=radian/2; x1 = (x0+getCos(radian)*r); y1 = (y0-getSin(radian)*r); middleX=( x0+getCos(textRadian)*r); middleY=(y0-getSin(textRadian)*r); double percent = Math.round(percents[0]*100)/100.0;//獲得精確到兩位小數點的坐標. k=Math.abs((middleY-y0)/(middleX-x0));//獲得扇形終點的坐標,與中心點連成的直線的斜率.(取正值) double sita= Math.atan( k);//求斜角double lineLen=50; double textLen=70; if(radian<6){ lineLen=90; textLen=110;//控制指示線的長度,與文字的位置} if(percents[ i]!=0){//當一個類型為0時,餅圖展示if((textRadian<(Math.PI/2))){ sfile.append("<line x1='"+middleX+"' y1 ='"+middleY+"' x2='"+(middleX+Math.cos(sita)*lineLen)+"' y2='"+(middleY-(Math.sin(sita)*lineLen))+"' stroke ='#000000'/>"); sfile.append("/n"); sfile.append("<text x='"+(middleX+Math.cos(sita)*textLen)+"' y=' "+(middleY-(Math.sin(sita)*textLen))+"' space='preserve' font-family='Tahoma' font-size='21' fill='red' stroke='red' baseline- shift='baseline' >"+percent+"%</text>"); }else if ((textRadian>(Math.PI/2)&&textRadian<Math.PI)){ sfile.append("<line x1=' "+middleX+"' y1='"+middleY+"' x2='"+(middleX-Math.cos(sita)*lineLen)+"' y2='"+(middleY-(Math.sin(sita)*lineLen ))+"' stroke='#000000'/>"); sfile.append("/n"); sfile.append("<text x='"+(middleX-Math.cos(sita)*textLen) +"' y='"+(middleY-(Math.sin(sita)*textLen))+"' space='preserve' font-family='Tahoma' font-size='21' fill='red' stroke ='red' baseline-shift='baseline' >"+percent+"%</text>"); }else if ((textRadian>(Math.PI)&&textRadian<(Math.PI*3/2))){ sfile.append("<line x1='"+middleX+"' y1='"+middleY+"' x2='"+(middleX-Math.cos(sita)*lineLen)+"' y2='"+(middleY+ (Math.sin(sita)*lineLen))+"' stroke='#000000'/>"); sfile.append("/n"); sfile.append("<text x='"+(middleX- Math.cos(sita)*textLen)+"' y='"+(middleY+(Math.sin(sita)*textLen))+"' space='preserve' font-family='Tahoma' font-size=' 21' fill='red' stroke='red' baseline-shift='baseline' >"+percent+"%</text>"); }else if((textRadian>(Math.PI*3/2)&&textRadian< (Math.PI*2))){ sfile.append("<line x1='"+middleX+"' y1='"+middleY+"' x2='"+(middleX+Math.cos(sita)*lineLen) +"' y2='"+(middleY+Math.sin(sita)*lineLen)+"' stroke='#000000'/>"); sfile.append("/n"); sfile.append("< text x='"+(middleX+Math.cos(sita)*textLen)+"' y='"+(middleY+(Math.sin(sita)*textLen))+"' space='preserve' font-family ='Tahoma' font-size='21' fill='red' stroke='red' baseline-shift='baseline' >"+percent+"%</text>"); } sfile.append("/n" ); if(getRadian(percents[0])>Math.PI){ sfile.append("<path d='M "+x0+" "+y0+" L "+(x0+r)+" "+r+" A "+r+" "+r+" 0 1 0 "+x1+" "+y1+" L "+x0+" "+y0+" z' fill='"+colors[0]+"'/>"); }else { sfile.append("<path d='M "+x0+" "+y0+" L "+(x0+r)+" "+r+" A "+r+" "+r+" 0 0 0 "+x1+" "+y1+" L "+x0+" "+y0+" z' fill='"+colors[0]+"'/>"); } sfile.append("/n"); } sfile.append("< rect x='"+(x0+2*r)+"' y='"+(y0-r/2.0+N)+"' width='60' height='30' fill='"+colors[ i]+"' stroke='#FFFFFF' stroke-dasharray='1,1' />"); sfile.append("/n"); sfile.append("<text x='"+(x0+ 2*r+80)+"' y='"+(y0-r/2.0+N+25)+"' space='preserve' font-family='宋體' font-size='28' fill=' "+colors[0]+"' stroke='#000000' stroke-dasharray='1,1' baseline-shift='baseline'>"+names[0]+"</text>"); sfile.append ("/n"); }else{ textRadian = radian+(getRadian(percents[i])/2);//獲取指示線與X軸的弧度. radian =radian+getRadian(percents[i]);//第i個扇形前面的弧度的總和middleX=(x0+getCos(textRadian)*r); middleY=(y0-getSin(textRadian)*r); double percent = Math.round(percents[i]*100)/ 100.0; k=Math.abs((middleY-y0)/(middleX-x0)); double lineLen=50; double textLen=70; if(radian<6){ lineLen=90; textLen=110; } double sita= Math.atan(k); if(percents[i]!=0){//當一個類型為0時,餅圖展示if((textRadian<(Math.PI/2))){ sfile.append(" <line x1='"+middleX+"' y1='"+middleY+"' x2='"+(middleX+Math.cos(sita)*lineLen)+"' y2='"+(middleY-(Math.sin (sita)*lineLen))+"' stroke='#000000'/>"); sfile.append("/n"); sfile.append("<text x='"+(middleX+Math.cos( sita)*textLen)+"' y='"+(middleY-(Math.sin(sita)*textLen))+"' space='preserve' font-family='Tahoma' font-size='21' fill ='red' stroke='red' baseline-shift='baseline' >"+percent+"%</text>"); }else if ((textRadian>(Math.PI/2)&&textRadian<Math.PI)) { sfile.append("<line x1='"+middleX+"' y1='"+middleY+"' x2='"+(middleX-Math.cos(sita)*lineLen)+"' y2='"+( middleY-(Math.sin(sita)*lineLen))+"' stroke='#000000'/>"); sfile.append("/n"); sfile.append("<text x='"+( middleX-Math.cos(sita)*textLen)+"' y='"+(middleY-(Math.sin(sita)*textLen))+"' space='preserve' font-family='Tahoma' font- size='21' fill='red' stroke='red' baseline-shift='baseline' >"+percent+"%</text>"); }else if ((textRadian>(Math.PI)&&textRadian<( Math.PI*3/2))){ sfile.append("<line x1='"+middleX+"' y1='"+middleY+"' x2='"+(middleX-Math.cos(sita)*lineLen )+"' y2='"+(middleY+(Math.sin(sita)*lineLen))+"' stroke='#000000'/>"); sfile.append("/n"); sfile.append( "<text x='"+(middleX-Math.cos(sita)*textLen)+"' y='"+(middleY+(Math.sin(sita)*textLen))+"' space='preserve' font -family='Tahoma' font-size='21' fill='red' stroke='red' baseline-shift='baseline' >"+percent+"%</text>"); }else if((textRadian> (Math.PI*3/2)&&textRadian<(Math.PI*2))){ sfile.append("<line x1='"+middleX+"' y1='"+middleY+"' x2='"+( middleX+Math.cos(sita)*lineLen)+"' y2='"+(middleY+Math.sin(sita)*lineLen)+"' stroke='#000000'/>"); sfile.append(" /n"); sfile.append("<text x='"+(middleX+Math.cos(sita)*textLen)+"' y='"+(middleY+(Math.sin(sita)*textLen)) +"' space='preserve' font-family='Tahoma' font-size='21' fill='red' stroke='red' baseline-shift='baseline' >"+percent+"%</text>" ); } sfile.append("/n"); // 參數1 表示畫大於180的弧, 0 表示畫小於180的弧(這個地方比較重要) if(getRadian(percents[i])>Math.PI ){ sfile.append("<path d='M "+x0+" "+y0+" L "+x1+" "+y1+" A "+r+" "+r+" 0 1 0 "+(x1=x0+getCos (radian)*r)+" "+(y1=y0-getSin(radian)*r)+" L "+x0+" "+y0+" z' fill='"+colors[i]+"'/>" ); }else{ sfile.append("<path d='M "+x0+" "+y0+" L "+x1+" "+y1+" A "+r+" "+r+" 0 0 0 "+(x1= x0+getCos(radian)*r)+" "+(y1=y0-getSin(radian)*r)+" L "+x0+" "+y0+" z' fill='"+colors[i]+"' />"); } sfile.append("/n"); } N+=50; sfile.append("<rect x='"+(x0+2*r)+"' y='"+(y0 -r/2.0+N)+"' width='60' height='30' fill='"+colors[i]+"' stroke='#FFFFFF' stroke-dasharray='1,1' />" ); sfile.append("/n"); sfile.append("<text x='"+(x0+2*r+80)+"' y='"+(y0-r/2.0+N+ 25)+"' space='preserve' font-family='宋體' font-size='28' fill='"+colors[0]+"' stroke='#000000' stroke-dasharray='1,1 ' baseline-shift='baseline'>"+names[i]+"</text>"); sfile.append("/n"); } } return sfile.toString(); } //返回弧度public static double getRadian(double fenshu){ return (fenshu*Math.PI)/50; } //返回正弦public static double getSin(double radian){ return Math.sin(radian); } //返回餘弦public static double getCos( double radian){ return Math.cos(radian); } public static void main(String[] args) { int[] data= {3,64,0,284,10}; String[] names={"主變:" +data[0]+"個","斷路器:"+data[1]+"個","線路:"+data[2]+"個","刀閘:"+data[3]+ "個","母線:"+data[4]+"個"}; create(data,names); } private static void create(int[] data,String[] names) { try { createSVG("d: /a.svg",getPercent(data),names); } catch (Exception e) { e.printStackTrace(); } } private static double[] getPercent(int data[]){ double sum=0; double percents[ ] = new double[data.length]; for(int i=0;i<data.length;i++){ sum+=data[i]; } for(int i=0;i<data.length;i++){ percents[i] =(data[i]/sum)*100; } return percents; } public static void createSVG(String fileRealPath, double[] percents,String[] names) throws Exception { String sFile = initialize(percents,names ); try { byte[] byteFil = sFile.getBytes("UTF-8"); File svgFile = new File(fileRealPath); if (svgFile.exists()) { svgFile.delete(); } FileOutputStream fos = new FileOutputStream (svgFile); fos.write(byteFil); fos.close(); } catch (Exception ex) { System.out.print(ex.getMessage()); } }}二.java生成SVG 3D餅圖.
(這個可以生成圖形,但是不完善,我沒有再修改代碼啦,因為覺得這個東西不值,用jfreechart可能更好.功能更強到,只是這幾個程序,讓我更加了解了svg這個東西,裡面的一些標籤都乾什麼用的.等等.) 3D的這個,生成的效果圖,會有斷層的效果,主要是出現在第一現象和第四象限,即如果第一象限或第四象限,有兩個扇形的話,就會出現斷層,可以用這個工具進行調整:SVGDeveloper. 用它打開svg圖形,然後將斷層的扇形的代碼,重新倒序排列一下.
package com.xj.svg; import java.io.File; import java.io.FileOutputStream; public class Caky3DSVG { static String[] colors ={"#d6a97b", "#22FF22", "#aaffaa", "#799AE1 ", "#9aabEe", "#3e941b", "#f2e692", "#66cc00", "#297110", "#d6a97b", "#82522b", "#aaaaff", "#1111aa", "#ff2222 ", "#ffaaaa", "#aa1111" }; public static void main(String[] args) { double data[] = {20,20,50}; try { createSVG("f:/f.svg", getPercent(data)); } catch (Exception e) { e.printStackTrace(); } } static String initialize(double [] percent){ double percents[] = {10,15,5,20,40,10}; StringBuffer sfile = new StringBuffer(); sfile.append("<?xml version='1.0' encoding='UTF-8'?>"); sfile.append("/n"); sfile.append("<svg xmlns:svg='http://www.w3.org/2000/svg'"); sfile.append("/n"); sfile.append("xmlns='http://www.w3.org/ 2000/svg'"); sfile.append("/n"); sfile.append("xmlns:xlink='http://www.w3.org/1999/xlink'"); sfile.append("/ n"); sfile.append("xml:space='default'"); sfile.append("/n"); sfile.append("version='1.1' width='100%' height='100% ' viewBox='0 0 1024 600'>"); sfile.append("/n"); sfile.append("<defs></defs>"); sfile.append("/n"); String path = createPath(502, 300,300, 150, percents); sfile.append(path); sfile.append("</g>"); sfile.append("/n"); sfile.append("</svg> "); return sfile.toString(); } /** * * @param x0 原點X * @param y0 原點Y * @param langR * @param shortR * @param fenshu * @return */ static String createPath(double x0 ,double y0,double langR,double shortR ,double percents[]){ StringBuffer sfile = new StringBuffer(); double xBottom =0; double yBottom =0; double xBottom1=0; double yBottom1=0; double radian =0; sfile .append("<g stroke-width='1' stroke='#000000' transform='matrix(1,0,0,1,1.638,-9.83)' xmlns='http://www.w3.org /2000/svg'>"); sfile.append("/n"); for(int i=0;i<percents.length;i++){ System.out.println("i:"+i); radian =radian+getRadian(percents[i]);//第i個扇形到第一個扇形,弧度的總和. System.out.println("弧度2:"+radian); if (i==0){ System.out.println("弧度1:"+radian); if(radian==Math.PI/2){ xBottom = x0;//底面的x坐標yBottom = y0-shortR;//底面的y坐標} else if(radian==Math.PI*3/2){ xBottom = x0;//底面的x坐標yBottom = y0+shortR;//底面的y坐標} else{ double tanRadian = Math.abs(Math.tan (radian)); double sqValue=shortR*shortR+tanRadian*tanRadian*langR*langR; if(radian<Math.PI/2){ System.out.println("if1:"+radian); xBottom = x0+(langR *shortR)/Math.sqrt(sqValue);//底面的x坐標yBottom = y0-(tanRadian*langR*shortR)/Math.sqrt(sqValue);//底面的y坐標} else if (radian>Math. PI/2&&radian<=Math.PI){ System.out.println("if2:"+radian); xBottom =x0-(langR*shortR)/Math.sqrt(sqValue); yBottom =y0-(tanRadian*langR* shortR)/Math.sqrt(sqValue); }else if (radian>Math.PI&&radian<Math.PI*3/2){ System.out.println("if3:"+radian); xBottom =x0-(langR* shortR)/Math.sqrt(sqValue); yBottom =y0+(tanRadian*langR*shortR)/Math.sqrt(sqValue); }else if (radian>Math.PI*3/2&&radian<Math.PI*2){ System .out.println("if4:"+radian); xBottom = x0+(langR*shortR)/Math.sqrt(sqValue); yBottom = y0+(tanRadian*langR*shortR)/Math.sqrt(sqValue); } } if (getRadian(percents[0])>Math.PI){//大於PI 弧度,即百分比超過50% sfile.append("<g fill='"+colors[i]+"' >"); sfile. append("/n"); sfile.append("<path d='M "+x0+" "+y0+" L "+(x0+langR)+" "+y0+" A "+langR+" "+shortR+" 0 1 0 "+xBottom+" "+yBottom+" z' />"); sfile.append("/n"); sfile.append("<path d='M "+(x0+langR)+" "+ (y0-50)+" A "+langR+" "+shortR+" 0 1 0 "+xBottom+" "+(yBottom-50)+" L "+xBottom+" "+yBottom+" A "+langR+" "+shortR+" 0 1 1 "+(x0+langR)+" "+y0+" z' />"); sfile.append("/n"); sfile.append("<path d='M "+x0+" "+ (y0-50)+" L "+(x0+langR)+" "+(y0-50)+" A "+langR+" "+shortR+" 0 1 0 "+xBottom+" "+(yBottom-50)+ " z' />"); sfile.append("/n"); sfile.append("</g>"); sfile.append("/n"); }else{ sfile.append("<g fill='"+colors[i]+"' >"); sfile.append("/n"); sfile.append("<path d='M "+x0+" "+y0+" L "+(x0 +langR)+" "+y0+" A "+langR+" "+shortR+" 0 0 0 "+xBottom+" "+yBottom+" z' />"); sfile.append("/n"); sfile.append( "<path d='M "+(x0+langR)+" "+(y0-50)+" A "+langR+" "+shortR+" 0 0 0 "+xBottom+" "+(yBottom-50)+" L "+xBottom+" "+yBottom+" A "+langR+" "+shortR+" 0 0 1 "+(x0+langR)+" "+y0+" z' />"); sfile.append("/n") ; sfile.append("<path d='M "+x0+" "+(y0-50)+" L "+(x0+langR)+" "+(y0-50)+" A "+langR+" " +shortR+" 0 0 0 "+xBottom+" "+(yBottom-50)+" z' />"); sfile.append("/n"); sfile.append("</g>"); sfile. append("/n"); } }else{ if(radian==Math.PI/2){ xBottom1= x0;//底面的x坐標yBottom1= y0-shortR;//底面的y坐標}else if( radian==Math.PI*3/2){ xBottom1 = x0;//底面的x坐標yBottom1 = y0+shortR;//底面的y坐標} else{ double tanRadian = Math.abs(Math.tan(radian) ); double sqValue=shortR*shortR+tanRadian*tanRadian*langR*langR; if(radian<Math.PI/2){ System.out.println("if1:"+radian); xBottom1 = x0+(langR*shortR) /Math.sqrt(sqValue);//底面的x坐標yBottom1 = y0-(tanRadian*langR*shortR)/Math.sqrt(sqValue);//底面的y坐標} else if (radian>Math.PI/2&&radian <=Math.PI){ System.out.println("if2:"+radian); xBottom1 =x0-(langR*shortR)/Math.sqrt(sqValue); yBottom1 =y0-(tanRadian*langR*shortR)/ Math.sqrt(sqValue); }else if (radian>Math.PI&&radian<Math.PI*3/2){ System.out.println("if3:"+radian); xBottom1 =x0-(langR*shortR)/ Math.sqrt(sqValue); yBottom1 =y0+(tanRadian*langR*shortR)/Math.sqrt(sqValue); }else if (radian>Math.PI*3/2){ System.out.println("if4:" +radian); xBottom1 = x0+(langR*shortR)/Math.sqrt(sqValue); yBottom1 = y0+(tanRadian*langR*shortR)/Math.sqrt(sqValue); } } if(getRadian(percents[i])> Math.PI){//大於PI 弧度,即百分比超過50% System.out.println("大於pi"); sfile.append("<g fill='"+colors[i]+"' >") ; sfile.append("/n"); sfile.append("<path d='M "+x0+" "+y0+" L "+xBottom+" "+yBottom+" A "+langR+" "+shortR+" 0 1 0 "+xBottom1+" "+yBottom1+" z' />"); sfile.append("/n"); sfile.append("<path d='M "+(xBottom)+" "+(yBottom-50 )+" A "+langR+" "+shortR+" 0 1 0 "+xBottom1+" "+(yBottom1-50)+" L "+xBottom1+" "+yBottom1+" A "+langR+" "+shortR+" 0 1 1 " +xBottom+" "+yBottom+" z' />"); sfile.append("/n"); sfile.append("<path d='M "+x0+" "+(y0-50)+" L " +(xBottom)+" "+(yBottom-50)+" A "+langR+" "+shortR+" 0 1 0 "+xBottom1+" "+(yBottom1-50)+" z' />"); sfile.append ("/n"); sfile.append("</g>"); sfile.append("/n"); }else{ System.out.println("小於pi"); sfile.append("< g fill='"+colors[i]+"' >"); sfile.append("/n"); sfile.append("<path d='M "+x0+" "+y0+" L "+xBottom+ " "+yBottom+" A "+langR+" "+shortR+" 0 0 0 "+xBottom1+" "+yBottom1+" z' />"); sfile.append("/n"); sfile.append("<path d ='M "+(xBottom)+" "+(yBottom-50)+" A "+langR+" "+shortR+" 0 0 0 "+xBottom1+" "+(yBottom1-50)+" L "+xBottom1+" " +yBottom1+" A "+langR+" "+shortR+" 0 0 1 "+xBottom+" "+yBottom+" z' />"); sfile.append("/n"); sfile.append("<path d=' M "+x0+" "+(y0-50)+" L "+(xBottom)+" "+(yBottom-50)+" A "+langR+" "+shortR+" 0 0 0 "+xBottom1+" "+( yBottom1-50)+" z' />"); sfile.append("/n"); sfile.append("</g>"); sfile.append("/n"); } xBottom=xBottom1; yBottom=yBottom1; } } return sfile.toString(); } //返回弧度public static double getRadian(double percent){ return (percent*Math.PI)/50; } //返回正弦public static double getSin(double radian ){ return Math.sin(radian); } //返回餘弦public static double getCos(double radian){ return Math.cos(radian); } private static double[] getPercent(double data[]){ double sum=0 ; double percents[] = new double[data.length]; for(int i=0;i<data.length;i++){ sum+=data[i]; } for(int i=0;i<data.length ;i++){ percents[i] =(data[i]/sum)*100; } return percents; } public static void createSVG(String fileRealPath, double[] percents) throws Exception { String sFile = initialize(percents); try { byte[] byteFil = sFile.getBytes("UTF-8"); File svgFile = new File(fileRealPath); if (svgFile.exists()) { svgFile.delete(); } FileOutputStream fos = new FileOutputStream(svgFile) ; fos.write(byteFil); fos.close(); } catch (Exception ex) { System.out.print(ex.getMessage()); } } }三.使用Jfreechart動態生成svg圖形:
import java.awt.Rectangle; import java.io.*; import org.jfree.chart.*; import org.apache.batik.dom.GenericDOMImplementation; import org.apache.batik.svggen.SVGGraphics2D; import org.jfree. data.category.CategoryDataset; import org.jfree.data.category.DefaultCategoryDataset; import org.jfree.chart.plot.*; import org.w3c.dom.DOMImplementation; import org.w3c.dom.Document; /** *該類用於演示最簡單的柱狀圖生成*/ public class BarChartDemo { public static void main(String[] args) throws IOException { CategoryDataset dataset = getDataSet(); // 創建JFreeChart對象,在內存中間創建出對應的圖像JFreeChart chart = ChartFactory.createBarChart3D("水果產量圖", // 圖表標題"水果", // 目錄軸的顯示標籤"產量", // 數值軸的顯示標籤dataset, // 數據集PlotOrientation.VERTICAL, // 圖表方向:水平、垂直true, // 是否顯示圖例(對於簡單的柱狀圖必須是false) false, // 是否生成工具false // 是否生成URL鏈接); File fo_svg = new File("D: //fruit3.svg"); Rectangle bounds = new Rectangle(0,0,400,300); exportChartAsSVG(chart,bounds,fo_svg); } private static void exportChartAsJPG() throws FileNotFoundException, IOException { // 得到數據Dataset CategoryDataset dataset = getDataSet( ); // 創建JFreeChart對象,在內存中間創建出對應的圖像JFreeChart chart = ChartFactory.createBarChart3D("水果產量圖", // 圖表標題"水果", // 目錄軸的顯示標籤"產量", //數值軸的顯示標籤dataset, // 數據集PlotOrientation.VERTICAL, // 圖表方向:水平、垂直true, // 是否顯示圖例(對於簡單的柱狀圖必須是false) false, // 是否生成工具false //是否生成URL鏈接); FileOutputStream fos_jpg = null; try { fos_jpg = new FileOutputStream("D:/fruit3.jpg"); ChartUtilities.writeChartAsJPEG(fos_jpg, 1, chart, 400, 300, null); } finally { try { fos_jpg.close(); } catch (Exception e) { } } } /** * 獲取一個演示用的簡單數據集對象* * @return */ private static CategoryDataset getDataSet() { DefaultCategoryDataset dataset = new DefaultCategoryDataset(); dataset.addValue(100, "1", "葡萄"); dataset.addValue(200, "1", "梨子"); dataset.addValue(200, "1", "荔枝"); dataset.addValue(300 , "2", "葡萄"); dataset.addValue(400, "2", "梨子"); dataset.addValue(500, "2", "荔枝"); return dataset; } /** * 獲取一個演示用的組合數據集對象* * @return */ private static CategoryDataset getDataSet2() { DefaultCategoryDataset dataset = new DefaultCategoryDataset(); dataset.addValue(100, "北京", "蘋果"); dataset.addValue(100, "上海", "蘋果"); dataset.addValue(100, "廣州", "蘋果"); dataset.addValue(200, "北京", "梨子"); dataset.addValue(200, "上海", "梨子"); dataset.addValue(200, "廣州", "梨子"); dataset.addValue(300, "北京", "葡萄"); dataset.addValue(300, "上海", "葡萄"); dataset. addValue(300, "廣州", "葡萄"); dataset.addValue(400, "北京", "香蕉"); dataset.addValue(400, "上海", "香蕉"); dataset.addValue(400, "廣州", "香蕉"); dataset.addValue(500, "北京", "荔枝"); dataset.addValue(500, "上海", "荔枝"); dataset.addValue(500, "廣州", "荔枝"); return dataset; } /** * Exports a JFreeChart to a SVG file. * * @param chart JFreeChart to export * @param bounds the dimensions of the viewport * @param svgFile the output file. * @throws IOException if writing the svgFile fails. */ private static void exportChartAsSVG(JFreeChart chart, Rectangle bounds, File svgFile) throws IOException { // Get a DOMImplementation and create an XML document DOMImplementation domImpl = GenericDOMImplementation.getDOMImplementation(); Document document = domImpl.createDocument(null , "svg", null); // Create an instance of the SVG Generator SVGGraphics2D svgGenerator = new SVGGraphics2D(document); // draw the chart in the SVG generator chart.draw(svgGenerator, bounds); // Write svg file OutputStream outputStream = new FileOutputStream(svgFile); Writer out = new OutputStreamWriter(outputStream, "UTF-8"); svgGenerator.stream(out, true /* use css */); outputStream.flush(); outputStream.close(); } }用這個的時候需要注意兩點:
1 .jfreechart本身不能生成svg圖形,需要用到batik .一個java工具包,apache的.
batik-awt-util.jar
batik-dom.jar
batik-svggen.jar
batik-util.jar
batik-xml.jar
jfreechart-1.0.0.jar
2.就是可能生成svg,當你查看的時候不支持中文. 我記得好像是如果是安裝的adobe的那個查看器,在IE裡面瀏覽的話好像是中文亂碼,如果用另外一個叫做Renesis SVG Player ,這個查看器就是支持中文的.
以上內容就是java生成餅圖svg及JFreeChart生成svg圖表的全部內容,希望大家喜歡。