본문 바로가기
PHP

PHP 막대그래프 그리기

by ethanjoh 2009. 1. 26.
이상하게 graphite나 jpgraph를 단독으로 쓰면 그래프 예제 등이 잘 보이는데 다른 소스 내에 포함시켜
쓰려니 꼭 헤더가 이미 보내졌다면서 문제가 발생하더군요.

그래서 그냥 하나 만들어서 쓰려고 여기 저기 찾던 중 아래와 같은 소스를 구했습니다.

<?php
function bar_graph($val,$x,$y,$x_val,$img_url,$legend,$theme)   { //-- 막대 그래프 만들어주는 함수
     /*
     $val : 값을 원소로 하는 배열
     $x : 그래프 가로축 크기
     $y : 그래프 세로축 크기
     $x_val : x축 값의 이름 배열
     $img_url : 저장할 파일의 경로와 이름(png)
     */
    
     $gaesu = count($val);   //-- 그래프 막대 갯수
     $makde_pok = ($x / $gaesu) / 3;   //-- 막대 하나 폭
     $real_y = $y - 40;    //-- 그래프가 그려질 실제 위치
    
     $max_value = $val[0];
     for ($i=0;$i<$gaesu;$i++)     {
         if($val[$i] > $max_value)   $max_value = $val[$i];
         }

     $im =  @ImageCreate($x,$y) or die ("이미지를 초기화 하지 못했습니다");
	  
	  switch($theme) {
	  	case "red" :
	  		$backgroundcolor=ImageColorAllocate($im,208,208,208);  //-- 그래프 바탕색
     		$rectanglecolor = ImageColorAllocate($im,198,34,34); //-- 그래프 색깔
     		$white=ImageColorAllocate($im,255,255,240);            //-- 그래프 바닥색
     		$color_x = imagecolorallocate($im, 0, 0, 0); //x 값, (black)
	  		$color_y = imagecolorallocate($im, 255, 233, 53); // y 값 (white) 
	  		$legend_color = imagecolorallocate($im, 255, 0, 0); // 그래프 제목 
	  		break;
	  	case "green" :
	  		$backgroundcolor=ImageColorAllocate($im,208,208,208);  
     		$rectanglecolor = ImageColorAllocate($im,46,87,30); 
     		$white=ImageColorAllocate($im,255,255,240);            
     		$color_x = imagecolorallocate($im, 0, 0, 0); 
	  		$color_y = imagecolorallocate($im, 255, 233, 53); 
	  		$legend_color = imagecolorallocate($im, 255, 0, 0);
	  		break;   	
	  	case "blue" :
	  		$backgroundcolor=ImageColorAllocate($im,208,208,208);  
     		$rectanglecolor = ImageColorAllocate($im,65,127,250); 
     		$white=ImageColorAllocate($im,255,255,240);            
     		$color_x = imagecolorallocate($im, 0, 0, 0); 
	  		$color_y = imagecolorallocate($im, 255, 233, 53);  
	  		$legend_color = imagecolorallocate($im, 255, 0, 0);
	  		break;  	  	
	  	default :
	  		$backgroundcolor=ImageColorAllocate($im,208,208,208);
     		$rectanglecolor = ImageColorAllocate($im,65,127,250); 
     		$white=ImageColorAllocate($im,255,255,240);            
     		$color_x = imagecolorallocate($im, 0, 0, 0); 
	  		$color_y = imagecolorallocate($im, 255, 233, 53); 
	  		$legend_color = imagecolorallocate($im, 255, 0, 0);
	  		break;   	
	  }

     ImageFilledRectAngle($im,0,$real_y,$x,$y,$white);    
     for ($i=0;$i<$gaesu;$i++)   {
           ($i == 0) ? $makde_x[$i] = $makde_pok: $makde_x[$i] = ($makde_x[$i - 1] + $makde_pok * 3);
           $makde_y[$i] = $real_y - ($val[$i]/$max_value) * $real_y; //-- 각각의 막대 y 좌표

           ImageFilledRectAngle($im,$makde_x[$i],$makde_y[$i],$makde_x[$i]+$makde_pok,$real_y,$rectanglecolor);          
           ($makde_y[$i] < 0) ? $y_string = 0 : $y_string = $makde_y[$i]+10;
			  ImageTTFtext($im,8,0,$makde_x[$i],$y_string,$color_y, "nanum.ttf", $val[$i]); //Y축 값
           ImageTTFtext($im,8,90,$makde_x[$i]-2,$y-40,$color_x, "nanum.ttf", $x_val[$i]); //X축 값 ImageTTFtext (이미지 구분자, 크기, 각도, X좌표, Y좌표, 색 구분자, TTF파일, 문자열);       
     }
     ImageTTFtext($im,8,0,10,$y-10,$legend_color, "nanum.ttf", $legend); //타이틀 (이미지 구분자, 크기, 각도, X좌표, Y좌표, 색 구분자, TTF파일, 문자열);
     
     ImagePNG($im,$img_url);
     ImageDestroy($im);
     
     echo "<img src=\"$img_url\" border=\"0\" />";
    
}

$data = array();
$x_index = array();

$data[0] = 10;
$data[1] = 50;
$data[2] = 30;
$data[3] = 90;
$data[4] = 100;

$x_index[0] = "사과";
$x_index[1] = "배";
$x_index[2] = "귤";
$x_index[3] = "오렌지";
$x_index[4] = "바나나";

$width = 400;
$height = 300;
$img = "graph.png";
$title = "[판매 수량 그래프]";
$theme = "blue"; //red, blue, green 중 하나

bar_graph($data,$width,$height,$x_index,$img,$title,$theme);

echo "<p>";
$img = "graph1.png";
$theme = "red"; //red, blue, green 중 하나
bar_graph($data,$width,$height,$x_index,$img,$title,$theme);
echo "</p>";
?>






원래의 소스는 한글 출력에 문제가 있어서 조금 수정을 했습니다.
함수 인자들도 조금 추가를 했구요.

네이버 나눔폰트를 사용해서 출력하게끔 했습니다.
다른 트루타입폰트를 쓴다면 소스 내에서 폰트명을 바꿔주면 됩니다.
물론 서버에 해당 폰트가 업로드되어 있어야 합니다. (편하게는 같은 디렉토리에)

$theme는 원소스에는 없는건데 조금 수정하다 말았습니다. ^^;
그냥 막대 그래프 색깔만 바뀌게...